OSDN Git Service

[Qt][MENU] Fix Screen Rotate.
[csp-qt/common_source_project-fm7.git] / source / src / qt / gui / gl3 / qt_glutil_gl3_0.cpp
1 /*
2  * qt_glutil_gl3_0.cpp
3  * (c) 2016 K.Ohta <whatisthis.sowhat@gmail.com>
4  * License: GPLv2.
5  * Renderer with OpenGL v3.0 (extend from renderer with OpenGL v2.0).
6  * History:
7  * Jan 22, 2016 : Initial.
8  */
9
10 #include "qt_gldraw.h"
11 #include "qt_glpack.h"
12 #include "qt_glutil_gl3_0.h"
13 #include "csp_logger.h"
14 #include "menu_flags.h"
15 #include <QOpenGLTexture>
16 #include <QOpenGLFunctions_3_0>
17
18 //extern USING_FLAGS *using_flags;
19 #if 0
20         // OLD_THREE_PHASE
21 const float luma_filter[24 + 1] = {
22                 -0.000071070,
23                 -0.000032816,
24                 0.000128784,
25                 0.000134711,
26                 -0.000226705,
27                 -0.000777988,
28                 -0.000997809,
29                 -0.000522802,
30                 0.000344691,
31                 0.000768930,
32                 0.000275591,
33                 -0.000373434,
34                 0.000522796,
35                 0.003813817,
36                 0.007502825,
37                 0.006786001,
38                 -0.002636726,
39                 -0.019461182,
40                 -0.033792479,
41                 -0.029921972,
42                 0.005032552,
43                 0.071226466,
44                 0.151755921,
45                 0.218166470,
46                 0.243902439
47         };
48 const float chroma_filter[24 + 1] = {
49                 0.001845562,
50                 0.002381606,
51                 0.003040177,
52                 0.003838976,
53                 0.004795341,
54                 0.005925312,
55                 0.007242534,
56                 0.008757043,
57                 0.010473987,
58                 0.012392365,
59                 0.014503872,
60                 0.016791957,
61                 0.019231195,
62                 0.021787070,
63                 0.024416251,
64                 0.027067414,
65                 0.029682613,
66                 0.032199202,
67                 0.034552198,
68                 0.036677005,
69                 0.038512317,
70                 0.040003044,
71                 0.041103048,
72                 0.041777517,
73                 0.042004791
74         };
75 #else
76 #if 1
77         // THREE_PHASE
78 const float luma_filter[24 + 1] = {
79                 -0.000012020,
80                 -0.000022146,
81                 -0.000013155,
82                 -0.000012020,
83                 -0.000049979,
84                 -0.000113940,
85                 -0.000122150,
86                 -0.000005612,
87                 0.000170516,
88                 0.000237199,
89                 0.000169640,
90                 0.000285688,
91                 0.000984574,
92                 0.002018683,
93                 0.002002275,
94                 -0.000909882,
95                 -0.007049081,
96                 -0.013222860,
97                 -0.012606931,
98                 0.002460860,
99                 0.035868225,
100                 0.084016453,
101                 0.135563500,
102                 0.175261268,
103                 0.190176552
104         };
105 const float chroma_filter[24 + 1] = {
106                 -0.000118847,
107                 -0.000271306,
108                 -0.000502642,
109                 -0.000930833,
110                 -0.001451013,
111                 -0.002064744,
112                 -0.002700432,
113                 -0.003241276,
114                 -0.003524948,
115                 -0.003350284,
116                 -0.002491729,
117                 -0.000721149,
118                 0.002164659,
119                 0.006313635,
120                 0.011789103,
121                 0.018545660,
122                 0.026414396,
123                 0.035100710,
124                 0.044196567,
125                 0.053207202,
126                 0.061590275,
127                 0.068803602,
128                 0.074356193,
129                 0.077856564,
130                 0.079052396
131         };
132 // END "ntsc-decode-filter-3phase.inc" //
133 #else
134                                 // TWO_PHASE
135 const float luma_filter[24 + 1] = {
136                 -0.000012020,
137                 -0.000022146,
138                 -0.000013155,
139                 -0.000012020,
140                 -0.000049979,
141                 -0.000113940,
142                 -0.000122150,
143                 -0.000005612,
144                 0.000170516,
145                 0.000237199,
146                 0.000169640,
147                 0.000285688,
148                 0.000984574,
149                 0.002018683,
150                 0.002002275,
151                 -0.000909882,
152                 -0.007049081,
153                 -0.013222860,
154                 -0.012606931,
155                 0.002460860,
156                 0.035868225,
157                 0.084016453,
158                 0.135563500,
159                 0.175261268,
160                 0.190176552
161         };
162         
163 const float chroma_filter[24 + 1] = {
164                 -0.000118847,
165                 -0.000271306,
166                 -0.000502642,
167                 -0.000930833,
168                 -0.001451013,
169                 -0.002064744,
170                 -0.002700432,
171                 -0.003241276,
172                 -0.003524948,
173                 -0.003350284,
174                 -0.002491729,
175                 -0.000721149,
176                 0.002164659,
177                 0.006313635,
178                 0.011789103,
179                 0.018545660,
180                 0.026414396,
181                 0.035100710,
182                 0.044196567,
183                 0.053207202,
184                 0.061590275,
185                 0.068803602,
186                 0.074356193,
187                 0.077856564,
188                 0.079052396
189         };
190 // END "ntsc-decode-filter-3phase.inc" //
191 #endif
192 #endif
193
194 GLDraw_3_0::GLDraw_3_0(GLDrawClass *parent, USING_FLAGS *p, CSP_Logger *logger, EMU *emu) : GLDraw_2_0(parent, p, logger, emu)
195 {
196         uTmpTextureID = 0;
197         
198         grids_shader = NULL;
199         
200         main_pass = NULL;
201         std_pass = NULL;
202         ntsc_pass1 = NULL;
203         ntsc_pass2 = NULL;
204         led_pass = NULL;
205         for(int i = 0; i < 32; i++) {
206                 led_pass_vao[i] = NULL;
207                 led_pass_vbuffer[i] = NULL;
208                 osd_pass_vao[i] = NULL;
209                 osd_pass_vbuffer[i] = NULL;
210         }
211         grids_horizonal_buffer = NULL;
212         grids_horizonal_vertex = NULL;
213         
214         grids_vertical_buffer = NULL;
215         grids_vertical_vertex = NULL;
216         ringing_phase = 0.0f;
217
218 }
219
220 GLDraw_3_0::~GLDraw_3_0()
221 {
222
223         if(main_pass  != NULL) delete main_pass;
224         if(std_pass   != NULL) delete std_pass;
225         if(ntsc_pass1 != NULL) delete ntsc_pass1;
226         if(ntsc_pass2 != NULL) delete ntsc_pass2;
227         if(led_pass   != NULL) delete led_pass;
228         for(int i = 0; i < 32; i++) {
229                 if(led_pass_vao[i] != NULL) delete led_pass_vao[i];     
230                 if(led_pass_vbuffer[i] != NULL) delete led_pass_vbuffer[i];
231                 if(osd_pass_vao[i] != NULL) delete osd_pass_vao[i];     
232                 if(osd_pass_vbuffer[i] != NULL) delete osd_pass_vbuffer[i];
233         }
234         
235         if(grids_horizonal_buffer != NULL) {
236                 if(grids_horizonal_buffer->isCreated()) grids_horizonal_buffer->destroy();
237         }
238         if(grids_horizonal_vertex != NULL) {
239                 if(grids_horizonal_vertex->isCreated()) grids_horizonal_vertex->destroy();
240         }
241         if(grids_vertical_buffer != NULL) {
242                 if(grids_vertical_buffer->isCreated()) grids_vertical_buffer->destroy();
243         }
244         if(grids_horizonal_vertex != NULL) {
245                 if(grids_vertical_vertex->isCreated()) grids_vertical_vertex->destroy();
246         }
247
248 }
249
250 void GLDraw_3_0::initFBO(void)
251 {
252         glHorizGrids = (GLfloat *)malloc(sizeof(float) * (using_flags->get_real_screen_height() + 2) * 6);
253         if(glHorizGrids != NULL) {
254                 doSetGridsHorizonal(using_flags->get_real_screen_height(), true);
255         }
256         glVertGrids  = (GLfloat *)malloc(sizeof(float) * (using_flags->get_real_screen_width() + 2) * 6);
257         if(glVertGrids != NULL) {
258                 doSetGridsVertical(using_flags->get_real_screen_width(), true);
259         }
260         if(using_flags->get_max_button() > 0) {
261                 initButtons();
262         }
263         // Init view
264         extfunc->glClearColor(0.0, 0.0, 0.0, 1.0);
265 }
266
267 void GLDraw_3_0::setNormalVAO(QOpenGLShaderProgram *prg,
268                                                            QOpenGLVertexArrayObject *vp,
269                                                            QOpenGLBuffer *bp,
270                                                            VertexTexCoord_t *tp,
271                                                            int size)
272 {
273         int vertex_loc = prg->attributeLocation("vertex");
274         int texcoord_loc = prg->attributeLocation("texcoord");
275
276         vp->bind();
277         bp->bind();
278
279         if(tp == NULL) {
280         } else {
281                 bp->write(0, tp, sizeof(VertexTexCoord_t) * size);
282         }
283         prg->setAttributeBuffer(vertex_loc, GL_FLOAT, 0, 3, sizeof(VertexTexCoord_t));
284         prg->setAttributeBuffer(texcoord_loc, GL_FLOAT, 3 * sizeof(GLfloat), 2, sizeof(VertexTexCoord_t));
285         prg->setUniformValue("a_texture", 0);
286                            
287         extfunc->glVertexAttribPointer(vertex_loc, 3, GL_FLOAT, GL_FALSE, sizeof(VertexTexCoord_t), 0); 
288         extfunc->glVertexAttribPointer(texcoord_loc, 2, GL_FLOAT, GL_FALSE, sizeof(VertexTexCoord_t), 
289                                                                (char *)NULL + 3 * sizeof(GLfloat)); 
290         bp->release();
291         vp->release();
292         prg->enableAttributeArray(vertex_loc);
293         prg->enableAttributeArray(texcoord_loc);
294 }
295
296 void GLDraw_3_0::initGLObjects()
297 {
298         extfunc = new QOpenGLFunctions_3_0;
299         extfunc->initializeOpenGLFunctions();
300         extfunc->glGetIntegerv(GL_MAX_TEXTURE_SIZE, &texture_max_size);
301 }       
302
303 void GLDraw_3_0::initPackedGLObject(GLScreenPack **p,
304                                                                         int _width, int _height,
305                                                                         const QString vertex_shader, const QString fragment_shader,
306                                                                         const QString _name)
307 {
308         QString s;
309         GLScreenPack *pp;
310         if(p != NULL) {
311                 pp = new GLScreenPack(_width, _height, _name, p_wid);
312                 *p = pp;
313                 if(pp != NULL) {
314                         pp->initialize(_width, _height, vertex_shader, fragment_shader);
315                         s = pp->getShaderLog();
316                         if(s.size() > 0) {
317                                 csp_logger->debug_log(CSP_LOG_INFO, CSP_LOG_TYPE_GL_SHADER, "In shader of %s ", _name.toLocal8Bit().constData());
318                                 csp_logger->debug_log(CSP_LOG_INFO, CSP_LOG_TYPE_GL_SHADER, "Vertex: %s ",  vertex_shader.toLocal8Bit().constData());
319                                 csp_logger->debug_log(CSP_LOG_INFO, CSP_LOG_TYPE_GL_SHADER, "Fragment: %s ", fragment_shader.toLocal8Bit().constData());
320                                 csp_logger->debug_log(CSP_LOG_INFO, CSP_LOG_TYPE_GL_SHADER, "%s", s.toLocal8Bit().constData());
321                         }
322                         s = pp->getGLLog();
323                         if(s.size() > 0) {
324                                 csp_logger->debug_log(CSP_LOG_INFO, CSP_LOG_TYPE_GL_SHADER, "%s", s.toLocal8Bit().constData());
325                                 pp->clearGLLog();
326                         }
327                 }
328         }
329 }
330                                         
331
332
333 bool GLDraw_3_0::initGridShaders(const QString vertex_fixed, const QString vertex_rotate, const QString fragment)
334 {
335         bool f = false;
336         grids_shader = new QOpenGLShaderProgram(p_wid);
337         if(grids_shader != NULL) {
338                 f = grids_shader->addShaderFromSourceFile(QOpenGLShader::Vertex, vertex_rotate);
339                 f &= grids_shader->addShaderFromSourceFile(QOpenGLShader::Fragment, fragment);
340                 f &= grids_shader->link();
341         }
342         return f;
343 }
344
345 bool GLDraw_3_0::initGridVertexObject(QOpenGLBuffer **vbo, QOpenGLVertexArrayObject **vao, int alloc_size)
346 {
347         QOpenGLBuffer *bp = NULL;
348         QOpenGLVertexArrayObject *ap = NULL;
349         *vao = NULL;
350         *vbo = NULL;
351         *vbo  = new QOpenGLBuffer(QOpenGLBuffer::VertexBuffer);
352         bp = *vbo;
353         if(bp != NULL) {
354                 if(bp->create()) {
355                         bp->bind();
356                         bp->allocate(alloc_size * sizeof(GLfloat) * 3 * 2);
357                         bp->release();
358                 } else {
359                         delete *vbo;
360                         return false;
361                 }
362         } else {
363                 return false;
364         }
365         
366         *vao = new QOpenGLVertexArrayObject;
367         ap = *vao;
368         if(ap == NULL) {
369                 bp->destroy();
370                 delete *vbo;
371                 return false;
372         }
373         if(!ap->create()) {
374                 delete *vao;
375                 bp->destroy();
376                 delete *vbo;
377                 return false;
378         }
379         return true;
380 }
381
382
383 void GLDraw_3_0::initLocalGLObjects(void)
384 {
385
386         int _width = using_flags->get_screen_width();
387         int _height = using_flags->get_screen_height();
388         
389         if((_width * 4) <= texture_max_size) {
390                 _width = _width * 4;
391                 low_resolution_screen = true;
392         } else {
393                 _width = _width * 2;
394         }
395         p_wid->makeCurrent();
396         
397         vertexFormat[0].x = -1.0f;
398         vertexFormat[0].y = -1.0f;
399         vertexFormat[0].z = -0.9f;
400         vertexFormat[0].s = 0.0f;
401         vertexFormat[0].t = 1.0f;
402         
403         vertexFormat[1].x = +1.0f;
404         vertexFormat[1].y = -1.0f;
405         vertexFormat[1].z = -0.9f;
406         vertexFormat[1].s = 1.0f;
407         vertexFormat[1].t = 1.0f;
408         
409         vertexFormat[2].x = +1.0f;
410         vertexFormat[2].y = +1.0f;
411         vertexFormat[2].z = -0.9f;
412         vertexFormat[2].s = 1.0f;
413         vertexFormat[2].t = 0.0f;
414         
415         vertexFormat[3].x = -1.0f;
416         vertexFormat[3].y = +1.0f;
417         vertexFormat[3].z = -0.9f;
418         vertexFormat[3].s = 0.0f;
419         vertexFormat[3].t = 0.0f;
420
421         if(using_flags->is_use_one_board_computer() || (using_flags->get_max_button() > 0)) {
422                 initPackedGLObject(&main_pass,
423                                                    using_flags->get_screen_width() * 2, using_flags->get_screen_height() * 2,
424                                                    ":/gl3/vertex_shader.glsl" , ":/gl3/chromakey_fragment_shader2.glsl",
425                                                    "Main Shader");
426         } else {
427                 initPackedGLObject(&main_pass,
428                                                    using_flags->get_screen_width() * 2, using_flags->get_screen_height() * 2,
429                                                    ":/gl3/vertex_shader.glsl" , ":/gl3/fragment_shader.glsl",
430                                                    "Main Shader");
431         }               
432         if(main_pass != NULL) {
433                 setNormalVAO(main_pass->getShader(), main_pass->getVAO(),
434                                          main_pass->getVertexBuffer(),
435                                          vertexFormat, 4);
436         }
437         initPackedGLObject(&std_pass,
438                                            using_flags->get_screen_width(), using_flags->get_screen_height(),
439                                            ":/gl3/vertex_shader.glsl" , ":/gl3/chromakey_fragment_shader.glsl",
440                                            "Standard Shader");
441         initPackedGLObject(&led_pass,
442                                            10, 10,
443                                            ":/gl3/led_vertex_shader.glsl" , ":/gl3/led_fragment_shader.glsl",
444                                            "LED Shader");
445         for(int i = 0; i < 32; i++) {
446                 led_pass_vao[i] = new QOpenGLVertexArrayObject;
447                 led_pass_vbuffer[i] = new QOpenGLBuffer(QOpenGLBuffer::VertexBuffer);
448                 if(led_pass_vao[i]->create()) {
449                         if(led_pass_vbuffer[i]->create()) {
450                                 led_pass_vbuffer[i]->setUsagePattern(QOpenGLBuffer::DynamicDraw);
451                                 led_pass_vao[i]->bind();
452                                 led_pass_vbuffer[i]->bind();
453                                 led_pass_vbuffer[i]->allocate(sizeof(VertexTexCoord_t) * 4);
454                                 led_pass_vbuffer[i]->release();
455                                 led_pass_vao[i]->release();
456                                 set_led_vertex(i);
457                         }
458                 }
459         }
460         initPackedGLObject(&osd_pass,
461                                            48.0, 48.0,
462                                            ":/gl3/vertex_shader.glsl" , ":/gl3/icon_fragment_shader.glsl",
463                                            "OSD Shader");
464         for(int i = 0; i < 32; i++) {
465                 osd_pass_vao[i] = new QOpenGLVertexArrayObject;
466                 osd_pass_vbuffer[i] = new QOpenGLBuffer(QOpenGLBuffer::VertexBuffer);
467                 if(osd_pass_vao[i]->create()) {
468                         if(osd_pass_vbuffer[i]->create()) {
469                                 osd_pass_vbuffer[i]->setUsagePattern(QOpenGLBuffer::DynamicDraw);
470                                 osd_pass_vao[i]->bind();
471                                 osd_pass_vbuffer[i]->bind();
472                                 osd_pass_vbuffer[i]->allocate(sizeof(VertexTexCoord_t) * 4);
473                                 osd_pass_vbuffer[i]->release();
474                                 osd_pass_vao[i]->release();
475                                 set_osd_vertex(i);
476                         }
477                 }
478         }
479
480         initPackedGLObject(&ntsc_pass1,
481                                            _width, _height,
482                                            ":/gl3/vertex_shader.glsl" , ":/gl3/ntsc_pass1.glsl",
483                                            "NTSC Shader Pass1");
484         initPackedGLObject(&ntsc_pass2,
485                                            _width / 2, _height,
486                                            ":/gl3/vertex_shader.glsl" , ":/gl3/ntsc_pass2.glsl",
487                                            "NTSC Shader Pass2");
488         {
489                 int ii;
490                 QOpenGLShaderProgram *shader = ntsc_pass2->getShader();
491                 shader->bind();
492                 ii = shader->uniformLocation("luma_filter");
493                 if(ii >= 0) {
494                         shader->setUniformValueArray(ii, luma_filter, 24 + 1, 1);
495                 }
496                 ii = shader->uniformLocation("chroma_filter");
497                 if(ii >= 0) {
498                         shader->setUniformValueArray(ii, chroma_filter, 24 + 1, 1);
499                 }
500                 shader->release();
501         }
502    
503         if(using_flags->is_use_one_board_computer()) {
504                 initBitmapVertex();
505                 initPackedGLObject(&bitmap_block,
506                                                    _width * 2, _height * 2,
507                                                    ":/gl3/vertex_shader.glsl", ":/gl3/normal_fragment_shader.glsl",
508                                                    "Background Bitmap Shader");
509                 if(bitmap_block != NULL) {
510                         setNormalVAO(bitmap_block->getShader(), bitmap_block->getVAO(),
511                                                  bitmap_block->getVertexBuffer(),
512                                                  vertexBitmap, 4);
513                 }
514         }
515         initGridShaders(":/gl3/grids_vertex_shader_fixed.glsl", ":/gl3/grids_vertex_shader.glsl", ":/gl3/grids_fragment_shader.glsl");
516         
517         initGridVertexObject(&grids_horizonal_buffer, &grids_horizonal_vertex, using_flags->get_real_screen_height() + 3);
518         doSetGridsHorizonal(using_flags->get_real_screen_height(), true);
519         
520         initGridVertexObject(&grids_vertical_buffer, &grids_vertical_vertex, using_flags->get_real_screen_width() + 3);
521         doSetGridsVertical(using_flags->get_real_screen_width(), true);
522
523         do_set_texture_size(NULL, -1, -1);
524         p_wid->doneCurrent();
525 }
526
527 void GLDraw_3_0::updateGridsVAO(QOpenGLBuffer *bp,
528                                                                 QOpenGLVertexArrayObject *vp,
529                                                                 GLfloat *tp,
530                                                                 int number)
531
532 {
533         bool checkf = false;
534         if((bp != NULL) && (vp != NULL)) {
535                 if(bp->isCreated()) {
536                         if(bp->size() < (int)((number + 1) * sizeof(GLfloat) * 3 * 2)) {
537                                 bp->destroy();
538                                 bp->create();
539                                 checkf = true;
540                         }
541                 } else {
542                         bp->create();
543                         checkf = true;
544                 }
545                 vp->bind();
546                 bp->bind();
547                 if(checkf) {
548                         bp->allocate((number + 1) * sizeof(GLfloat) * 3 * 2);
549                 }
550                 if(tp != NULL) {
551                         bp->write(0, tp, (number + 1) * sizeof(GLfloat) * 3 * 2);
552                 }
553                 bp->release();
554                 vp->release();
555         }
556 }
557 void GLDraw_3_0::drawGridsMain_3(QOpenGLShaderProgram *prg,
558                                                                  QOpenGLBuffer *bp,
559                                                                  QOpenGLVertexArrayObject *vp,
560                                                                  int number,
561                                                                  GLfloat lineWidth,
562                                                                  QVector4D color)
563 {
564         if(number <= 0) return;
565         extfunc->glDisable(GL_TEXTURE_2D);
566         extfunc->glDisable(GL_DEPTH_TEST);
567         extfunc->glDisable(GL_BLEND);
568
569         if((bp == NULL) || (vp == NULL) || (prg == NULL)) return;
570         if((!bp->isCreated()) || (!vp->isCreated()) || (!prg->isLinked())) return;
571         {
572                 bp->bind();
573                 vp->bind();
574                 prg->bind();
575                 //GLfloat ff[2];
576                 //bp->read(8, &ff, sizeof(GLfloat) * 2);
577                 //printf("%d %f %f\n", number, ff[0], ff[1]);
578                 
579                 prg->setUniformValue("color", color);
580                 prg->enableAttributeArray("vertex");
581                 int vertex_loc = prg->attributeLocation("vertex");
582                 
583                 extfunc->glViewport(0, 0, p_wid->width(), p_wid->height());
584                 extfunc->glOrtho(-1.0f, 1.0f, -1.0f, 1.0f, -1.0, 1.0);
585                 //extfunc->glEnable(GL_BLEND);
586                 //extfunc->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
587                 //extfunc->glBlendFunc(GL_SRC_ALPHA, GL_ONE);
588                 extfunc->glVertexAttribPointer(vertex_loc, 3, GL_FLOAT, GL_FALSE, sizeof(GLfloat) * 3, 0); 
589                 extfunc->glEnableVertexAttribArray(vertex_loc);
590                 
591                 extfunc->glEnableClientState(GL_VERTEX_ARRAY);
592                 extfunc->glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
593                 extfunc->glLineWidth(lineWidth);
594                 extfunc->glVertexPointer(3, GL_FLOAT, 0, 0);
595                 extfunc->glDrawArrays(GL_LINES, 0, (number + 1) * 2);
596                 extfunc->glDisableClientState(GL_VERTEX_ARRAY);
597                 //extfunc->glDisable(GL_BLEND);
598                 prg->release();
599                 vp->release();
600                 bp->release();
601         }
602 }
603
604 void GLDraw_3_0::doSetGridsVertical(int pixels, bool force)
605 {
606         GLDraw_2_0::doSetGridsVertical(pixels, force);
607         updateGridsVAO(grids_vertical_buffer,
608                                    grids_vertical_vertex,
609                                    glVertGrids,
610                                    pixels);
611         
612 }
613 void GLDraw_3_0::doSetGridsHorizonal(int lines, bool force)
614 {
615         if((lines == vert_lines) && !force) return;
616         GLDraw_2_0::doSetGridsHorizonal(lines, force);
617         updateGridsVAO(grids_horizonal_buffer,
618                                    grids_horizonal_vertex,
619                                    glHorizGrids,
620                                    lines);
621 }
622
623 void GLDraw_3_0::drawGridsHorizonal(void)
624 {
625         QVector4D c= QVector4D(0.0f, 0.0f, 0.0f, 1.0f);
626         drawGridsMain_3(grids_shader,
627                                         grids_horizonal_buffer,
628                                         grids_horizonal_vertex,
629                                         vert_lines,
630                                         0.15f,
631                                         c);
632 }
633
634 void GLDraw_3_0::drawGridsVertical(void)
635 {
636         QVector4D c= QVector4D(0.0f, 0.0f, 0.0f, 1.0f);
637         drawGridsMain_3(grids_shader,
638                                         grids_vertical_buffer,
639                                         grids_vertical_vertex,
640                                         horiz_pixels,
641                                         0.5f,
642                                         c);
643 }
644
645 void GLDraw_3_0::renderToTmpFrameBuffer_nPass(GLuint src_texture,
646                                                                                           GLuint src_w,
647                                                                                           GLuint src_h,
648                                                                                           GLScreenPack *renderObject,
649                                                                                           GLuint dst_w,
650                                                                                           GLuint dst_h,
651                                                                                           bool use_chromakey)
652 {
653         {
654                 QOpenGLShaderProgram *shader = renderObject->getShader();
655                 int ii;
656                 // NTSC_PASSx
657
658                 extfunc->glClearColor(0.0, 0.0, 0.0, 1.0);
659                 extfunc->glClearDepth(1.0f);
660                 extfunc->glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
661                 {
662                         if((src_texture != 0) && (shader != NULL)) {
663                                 extfunc->glEnable(GL_TEXTURE_2D);
664                                 renderObject->bind();
665                                 //extfunc->glViewport(0, 0, src_w, src_h);
666                                 extfunc->glViewport(0, 0, dst_w, dst_h);
667                                 extfunc->glOrtho(-1.0f, 1.0f, -1.0f, 1.0f, -1.0, 1.0);
668                                 extfunc->glActiveTexture(GL_TEXTURE0);
669                                 extfunc->glBindTexture(GL_TEXTURE_2D, src_texture);
670                                 extfunc->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
671                                 extfunc->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
672                                 //extfunc->glColor4f(1.0, 1.0, 1.0, 1.0);
673                                 shader->setUniformValue("a_texture", 0);
674                                 //shader->setUniformValue("a_texture", src_texture);
675                                 {
676                                         ii = shader->uniformLocation("source_size");
677                                         if(ii >= 0) {
678                                                 QVector4D source_size = QVector4D((float)src_w, (float)src_h, 0, 0);
679                                                 shader->setUniformValue(ii, source_size);
680                                         }
681                                         ii = shader->uniformLocation("target_size");
682                                         if(ii >= 0) {
683                                                 QVector4D target_size = QVector4D((float)dst_w, (float)dst_h, 0, 0);
684                                                 shader->setUniformValue(ii, target_size);
685                                         }
686                                         ii = shader->uniformLocation("phase");
687                                         if(ii >= 0) {
688                                                 ringing_phase = ringing_phase + 0.093;
689                                                 if(ringing_phase > 1.0) ringing_phase = ringing_phase - 1.0;
690                                                 shader->setUniformValue(ii,  ringing_phase);
691                                         }
692                                         //ii = shader->uniformLocation("luma_filter");
693                                         //if(ii >= 0) {
694                                         //      shader->setUniformValueArray(ii, luma_filter, 24 + 1, 1);
695                                         //}
696                                         //ii = shader->uniformLocation("chroma_filter");
697                                         //if(ii >= 0) {
698                                         //      shader->setUniformValueArray(ii, chroma_filter, 24 + 1, 1);
699                                         //}
700                                 }
701                                 {
702                                         QVector4D c(fBrightR, fBrightG, fBrightB, 1.0);
703                                         QVector3D chromakey(0.0, 0.0, 0.0);
704                 
705                                         ii = shader->uniformLocation("color");
706                                         if(ii >= 0) {
707                                                 shader->setUniformValue(ii, c);
708                                         }
709                                         ii = shader->uniformLocation("do_chromakey");
710                                         if(ii >= 0) {
711                                                 if(use_chromakey) {
712                                                         int ij;
713                                                         ij = shader->uniformLocation("chromakey");
714                                                         if(ij >= 0) {
715                                                                 shader->setUniformValue(ij, chromakey);
716                                                         }
717                                                         shader->setUniformValue(ii, GL_TRUE);
718                                                 } else {
719                                                         shader->setUniformValue(ii, GL_FALSE);
720                                                 }
721                                         }
722                                         //shader->setUniformValue("tex_width",  (float)w); 
723                                         //shader->setUniformValue("tex_height", (float)h);
724                                 }
725                                 shader->enableAttributeArray("texcoord");
726                                 shader->enableAttributeArray("vertex");
727                                 
728                                 int vertex_loc = shader->attributeLocation("vertex");
729                                 int texcoord_loc = shader->attributeLocation("texcoord");
730                                 extfunc->glEnableVertexAttribArray(vertex_loc);
731                                 extfunc->glEnableVertexAttribArray(texcoord_loc);
732                                 extfunc->glEnable(GL_VERTEX_ARRAY);
733
734                                 extfunc->glDrawArrays(GL_POLYGON, 0, 4);
735                                 
736                                 extfunc->glViewport(0, 0, dst_w, dst_h);
737                                 extfunc->glOrtho(0.0f, (float)dst_w, 0.0f, (float)dst_h, -1.0, 1.0);
738                                 renderObject->release();
739                                 extfunc->glBindTexture(GL_TEXTURE_2D, 0);
740                                 extfunc->glDisable(GL_TEXTURE_2D);
741                         }
742                 }
743         }
744 }
745
746
747 void GLDraw_3_0::uploadMainTexture(QImage *p, bool use_chromakey)
748 {
749         // set vertex
750         redraw_required = true;
751         if(p == NULL) return;
752         //redraw_required = true;
753         imgptr = p;
754         if(uVramTextureID == NULL) {
755                 uVramTextureID = new QOpenGLTexture(*p);
756         }
757
758         {
759                 // Upload to main texture
760                 extfunc->glBindTexture(GL_TEXTURE_2D, uVramTextureID->textureId());
761                 extfunc->glTexSubImage2D(GL_TEXTURE_2D, 0,
762                                                                  0, 0,
763                                                                  //screen_texture_width * 2,
764                                                                  //screen_texture_height * 2,
765                                                                  p->width(), p->height(),
766                                                                  GL_BGRA, GL_UNSIGNED_BYTE, p->constBits());
767                 extfunc->glBindTexture(GL_TEXTURE_2D, 0);
768         }
769         if(using_flags->is_support_tv_render() && (p_config->rendering_type == CONFIG_RENDER_TYPE_TV)) {
770                 renderToTmpFrameBuffer_nPass(uVramTextureID->textureId(),
771                                                                          screen_texture_width,
772                                                                          screen_texture_height,
773                                                                          ntsc_pass1,
774                                                                          ntsc_pass1->getViewportWidth(),
775                                                                          ntsc_pass1->getViewportHeight());
776                 
777                 renderToTmpFrameBuffer_nPass(ntsc_pass1->getTexture(),
778                                                                          ntsc_pass1->getViewportWidth(),
779                                                                          ntsc_pass1->getViewportHeight(),
780                                                                          ntsc_pass2,
781                                                                          ntsc_pass2->getViewportWidth(),
782                                                                          ntsc_pass2->getViewportHeight());
783                 uTmpTextureID = ntsc_pass2->getTexture();
784         } else {
785 //              renderToTmpFrameBuffer_nPass(uVramTextureID->textureId(),
786 //                                                                       screen_texture_width,
787 //                                                                       screen_texture_height,
788 //                                                                       std_pass,
789 //                                                                       std_pass->getViewportWidth(),
790 //                                                                       std_pass->getViewportHeight(),
791 //                                                                       use_chromakey);
792
793                 //std_pass->bind();
794                 //uTmpTextureID = std_pass->getTexture();
795                 uTmpTextureID = uVramTextureID->textureId();    //std_pass->release();
796         }
797         crt_flag = true;
798 }
799
800 void GLDraw_3_0::drawScreenTexture(void)
801 {
802         if(using_flags->is_use_one_board_computer()) {
803                 extfunc->glEnable(GL_BLEND);
804                 extfunc->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
805         } else {
806                 extfunc->glDisable(GL_BLEND);
807         }
808         
809         QVector4D color;
810         smoosing = p_config->use_opengl_filters;
811         if(set_brightness) {
812                 color = QVector4D(fBrightR, fBrightG, fBrightB, 1.0);
813         } else {
814                 color = QVector4D(1.0, 1.0, 1.0, 1.0);
815         }
816         if(using_flags->is_use_one_board_computer()) {
817                 drawMain(main_pass,
818                                  uTmpTextureID, // v2.0
819                                  color, smoosing,
820                                  true, QVector3D(0.0, 0.0, 0.0));       
821                 extfunc->glDisable(GL_BLEND);
822         } else {
823                 drawMain(main_pass,
824                                  uTmpTextureID, // v2.0
825                                  color, smoosing);      
826         }
827 }
828
829 void GLDraw_3_0::drawMain(QOpenGLShaderProgram *prg,
830                                                   QOpenGLVertexArrayObject *vp,
831                                                   QOpenGLBuffer *bp,
832                                                   GLuint texid,
833                                                   QVector4D color,
834                                                   bool f_smoosing,
835                                                   bool do_chromakey,
836                                                   QVector3D chromakey)
837 {
838         int ii;
839
840    if(texid != 0) {
841                 extfunc->glEnable(GL_TEXTURE_2D);
842                 vp->bind();
843                 bp->bind();
844                 prg->bind();
845                 extfunc->glViewport(0, 0, p_wid->width(), p_wid->height());
846                 extfunc->glOrtho(-1.0f, 1.0f, -1.0f, 1.0f, -1.0, 1.0);
847                 extfunc->glActiveTexture(GL_TEXTURE0);
848                 extfunc->glBindTexture(GL_TEXTURE_2D, texid);
849                 if(!f_smoosing) {
850                         extfunc->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
851                         extfunc->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
852                 } else {
853                         extfunc->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
854                         extfunc->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
855                 }
856                 prg->setUniformValue("a_texture", 0);
857                 
858                 ii = prg->uniformLocation("color");
859                 if(ii >= 0) {
860                         prg->setUniformValue(ii,  color);
861                 }
862                 
863                 ii = prg->uniformLocation("tex_width");
864                 if(ii >= 0) {
865                         prg->setUniformValue(ii,  (float)screen_texture_width);
866                 }
867                 
868                 ii = prg->uniformLocation("tex_height");
869                 if(ii >= 0) {
870                         prg->setUniformValue(ii,  (float)screen_texture_height);
871                 }
872                 
873                 QMatrix2x2 rot;
874                 switch(p_config->rotate_type) {
875                         case 0:
876                                 rot = QMatrix2x2(rot0);
877                                 break;
878                         case 1:
879                                 rot = QMatrix2x2(rot90);
880                                 break;
881                         case 2:
882                                 rot = QMatrix2x2(rot180);
883                                 break;
884                         case 3:
885                                 rot = QMatrix2x2(rot270);
886                                 break;
887                         default:
888                                 rot = QMatrix2x2(rot0);
889                                 break;
890                 }
891                 prg->setUniformValue("rotate_mat", rot);
892
893                 if(do_chromakey) {
894                         ii = prg->uniformLocation("chromakey");
895                         if(ii >= 0) {
896                                 prg->setUniformValue(ii, chromakey);
897                         }
898                         ii = prg->uniformLocation("do_chromakey");
899                         if(ii >= 0) {
900                                 prg->setUniformValue(ii, GL_TRUE);
901                         }
902                 } else {
903                         ii = prg->uniformLocation("do_chromakey");
904                         if(ii >= 0) {
905                                 prg->setUniformValue(ii, GL_FALSE);
906                         }
907                 }
908                 
909                 prg->enableAttributeArray("texcoord");
910                 prg->enableAttributeArray("vertex");
911                 int vertex_loc = prg->attributeLocation("vertex");
912                 int texcoord_loc = prg->attributeLocation("texcoord");
913                 extfunc->glEnableVertexAttribArray(vertex_loc);
914                 extfunc->glEnableVertexAttribArray(texcoord_loc);
915                 extfunc->glEnable(GL_VERTEX_ARRAY);
916                 extfunc->glDrawArrays(GL_POLYGON, 0, 4);
917                 bp->release();
918                 vp->release();
919                 
920                 prg->release();
921                 extfunc->glBindTexture(GL_TEXTURE_2D, 0);
922                 extfunc->glDisable(GL_TEXTURE_2D);
923         }
924         else {
925                 extfunc->glDisable(GL_TEXTURE_2D);
926                 vp->bind();
927                 bp->bind();
928                 prg->bind();
929                 extfunc->glViewport(0, 0, p_wid->width(), p_wid->height());
930                 extfunc->glOrtho(-1.0f, 1.0f, -1.0f, 1.0f, -1.0, 1.0);
931                 ii = prg->uniformLocation("color");
932                 if(ii >= 0) {
933                         prg->setUniformValue(ii,  color);
934                 }
935                 QMatrix2x2 rot;
936                 switch(p_config->rotate_type) {
937                         case 0:
938                                 rot = QMatrix2x2(rot0);
939                                 break;
940                         case 1:
941                                 rot = QMatrix2x2(rot90);
942                                 break;
943                         case 2:
944                                 rot = QMatrix2x2(rot180);
945                                 break;
946                         case 3:
947                                 rot = QMatrix2x2(rot270);
948                                 break;
949                         default:
950                                 rot = QMatrix2x2(rot0);
951                                 break;
952                 }
953                 prg->setUniformValue("rotate_mat", rot);
954
955                 if(do_chromakey) {
956                         ii = prg->uniformLocation("chromakey");
957                         if(ii >= 0) {
958                                 prg->setUniformValue(ii, chromakey);
959                         }
960                         ii = prg->uniformLocation("do_chromakey");
961                         if(ii >= 0) {
962                                 prg->setUniformValue(ii, GL_TRUE);
963                         }
964                 } else {
965                         ii = prg->uniformLocation("do_chromakey");
966                         if(ii >= 0) {
967                                 prg->setUniformValue(ii, GL_FALSE);
968                         }
969                 }
970                 
971                 prg->enableAttributeArray("vertex");
972                 int vertex_loc = prg->attributeLocation("vertex");
973                 extfunc->glEnableVertexAttribArray(vertex_loc);
974                 extfunc->glEnable(GL_VERTEX_ARRAY);
975                 extfunc->glDrawArrays(GL_POLYGON, 0, 4);
976                 extfunc->glDisable(GL_VERTEX_ARRAY);
977                 bp->release();
978                 vp->release();
979                 prg->release();
980                 extfunc->glBindTexture(GL_TEXTURE_2D, 0);
981                 extfunc->glDisable(GL_TEXTURE_2D);
982         }
983 }
984
985 void GLDraw_3_0::drawMain(GLScreenPack *obj,
986                                                   GLuint texid,
987                                                   QVector4D color,
988                                                   bool f_smoosing,
989                                                   bool do_chromakey,
990                                                   QVector3D chromakey)
991                                                    
992 {
993         QOpenGLShaderProgram *prg = obj->getShader();
994         QOpenGLVertexArrayObject *vp = obj->getVAO();
995         QOpenGLBuffer *bp = obj->getVertexBuffer();
996
997         drawMain(prg, vp, bp, texid, color, f_smoosing, do_chromakey, chromakey);
998 }
999
1000 void GLDraw_3_0::drawButtonsMain(int num, bool f_smoosing)
1001 {
1002         GLuint texid;
1003         QOpenGLBuffer *bp = buffer_button_vertex[num];
1004         QOpenGLShaderProgram  *prg = button_shader;
1005         QOpenGLVertexArrayObject *vp = vertex_button[num];
1006         QVector4D color;
1007         int ii;
1008         if(uButtonTextureID[num] == NULL) return;
1009         texid = uButtonTextureID[num]->textureId();
1010         color = QVector4D(1.0, 1.0, 1.0, 1.0);
1011         if((bp != NULL) && (vp != NULL) && (prg != NULL)) {
1012                 if((bp->isCreated()) && (vp->isCreated()) && (prg->isLinked())) {
1013                         bp->bind();
1014                         vp->bind();
1015                         prg->bind();
1016                         extfunc->glViewport(0, 0, p_wid->width(), p_wid->height());
1017                         extfunc->glOrtho(-1.0f, 1.0f, -1.0f, 1.0f, -1.0, 1.0);
1018                         extfunc->glActiveTexture(GL_TEXTURE0);
1019                         extfunc->glBindTexture(GL_TEXTURE_2D, texid);
1020                         if(!f_smoosing) {
1021                                 extfunc->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
1022                                 extfunc->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST_MIPMAP_LINEAR);
1023                         } else {
1024                                 extfunc->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
1025                                 extfunc->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_NEAREST);
1026                         }
1027                         prg->setUniformValue("a_texture", 0);
1028                         
1029                         ii = prg->uniformLocation("color");
1030                         if(ii >= 0) {
1031                                 prg->setUniformValue(ii,  color);
1032                         }
1033                         ii = prg->uniformLocation("do_chromakey");
1034                         if(ii >= 0) {
1035                                 prg->setUniformValue(ii, GL_FALSE);
1036                         }
1037                         QMatrix2x2 rot;
1038                         switch(p_config->rotate_type) {
1039                         case 0:
1040                                 rot = QMatrix2x2(rot0);
1041                                 break;
1042                         case 1:
1043                                 rot = QMatrix2x2(rot90);
1044                                 break;
1045                         case 2:
1046                                 rot = QMatrix2x2(rot180);
1047                                 break;
1048                         case 3:
1049                                 rot = QMatrix2x2(rot270);
1050                                 break;
1051                         default:
1052                                 rot = QMatrix2x2(rot0);
1053                                 break;
1054                         }
1055                         prg->setUniformValue("rotate_mat", rot);
1056                         int vertex_loc = prg->attributeLocation("vertex");
1057                         int texcoord_loc = prg->attributeLocation("texcoord");
1058                         prg->setAttributeBuffer(vertex_loc, GL_FLOAT, 0, 3, sizeof(VertexTexCoord_t));
1059                         prg->setAttributeBuffer(texcoord_loc, GL_FLOAT, 3 * sizeof(GLfloat), 2, sizeof(VertexTexCoord_t));
1060                         prg->enableAttributeArray(vertex_loc);
1061                         prg->enableAttributeArray(texcoord_loc);
1062                         extfunc->glEnableVertexAttribArray(vertex_loc);
1063                         extfunc->glEnableVertexAttribArray(texcoord_loc);
1064                         extfunc->glEnable(GL_VERTEX_ARRAY);
1065                         extfunc->glDrawArrays(GL_POLYGON, 0, 4);
1066                         bp->release();
1067                         vp->release();
1068                         prg->release();
1069                         extfunc->glBindTexture(GL_TEXTURE_2D, 0);
1070                         extfunc->glDisable(GL_TEXTURE_2D);
1071                         return;
1072                         }
1073                 }
1074
1075 }
1076
1077 void GLDraw_3_0::drawButtons(void)
1078 {
1079         for(int i = 0; i < using_flags->get_max_button(); i++) {
1080                 drawButtonsMain(i, false);
1081         }
1082 }
1083
1084 void GLDraw_3_0::drawBitmapTexture(void)
1085 {
1086         QVector4D color = QVector4D(1.0f, 1.0f, 1.0f, 1.0f);
1087         smoosing = p_config->use_opengl_filters;
1088         if(uBitmapTextureID == NULL) return;
1089         if(using_flags->is_use_one_board_computer()) {
1090                 extfunc->glDisable(GL_BLEND);
1091                 drawMain(bitmap_block,
1092                                  uBitmapTextureID->textureId(),
1093                                  color, smoosing);
1094         }
1095 }
1096
1097 void GLDraw_3_0::drawLedMain(GLScreenPack *obj, int num, QVector4D color)
1098 {
1099         QOpenGLShaderProgram *prg = obj->getShader();
1100         QOpenGLVertexArrayObject *vp = led_pass_vao[num];
1101         QOpenGLBuffer *bp = led_pass_vbuffer[num];
1102         int ii;
1103                 
1104         {
1105                 extfunc->glDisable(GL_TEXTURE_2D);
1106                 extfunc->glEnable(GL_BLEND);
1107                 extfunc->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
1108                 vp->bind();
1109                 bp->bind();
1110                 prg->bind();
1111                 extfunc->glViewport(0, 0, p_wid->width(), p_wid->height());
1112                 extfunc->glOrtho(-1.0f, 1.0f, -1.0f, 1.0f, -1.0, 1.0);
1113                 ii = prg->uniformLocation("color");
1114                 if(ii >= 0) {
1115                         prg->setUniformValue(ii,  color);
1116                 }
1117                 
1118                 prg->enableAttributeArray("vertex");
1119                 int vertex_loc = prg->attributeLocation("vertex");
1120                 prg->setAttributeBuffer(vertex_loc, GL_FLOAT, 0, 3, sizeof(VertexTexCoord_t));
1121                 extfunc->glVertexAttribPointer(vertex_loc, 3, GL_FLOAT, GL_FALSE, sizeof(VertexTexCoord_t), 0); 
1122
1123                 extfunc->glEnableVertexAttribArray(vertex_loc);
1124                 extfunc->glEnable(GL_VERTEX_ARRAY);
1125                 extfunc->glDrawArrays(GL_POLYGON, 0, 4);
1126                 bp->release();
1127                 vp->release();
1128                 
1129                 prg->release();
1130                 extfunc->glDisable(GL_TEXTURE_2D);
1131                 extfunc->glDisable(GL_BLEND);
1132         }
1133
1134 }
1135
1136
1137 void GLDraw_3_0::drawOsdLeds()
1138 {
1139         QVector4D color_on;
1140         QVector4D color_off;
1141         uint32_t bit = 0x00000001;
1142         if(osd_onoff) {
1143                 color_on = QVector4D(0.95, 0.0, 0.05, 1.0);
1144                 color_off = QVector4D(0.05,0.05, 0.05, 0.10);
1145         } else {
1146                 color_on = QVector4D(0.00,0.00, 0.00, 0.0);
1147                 color_off = QVector4D(0.00,0.00, 0.00, 0.0);
1148         }
1149         if(osd_onoff) {
1150                 //if(osd_led_status_bak != osd_led_status) {
1151                         for(int i = 0; i < osd_led_bit_width; i++) {
1152                                 if((bit & osd_led_status) == (bit & osd_led_status_bak)) {
1153                                         bit <<= 1;
1154                                         continue;
1155                                 }
1156                                 drawLedMain(led_pass, i,
1157                                                         ((osd_led_status & bit) != 0) ? color_on : color_off);
1158                                 bit <<= 1;
1159                         }
1160                         osd_led_status_bak = osd_led_status;
1161                 //}
1162         }
1163 }
1164
1165 void GLDraw_3_0::drawOsdIcons()
1166 {
1167         QVector4D color_on;
1168         QVector4D color_off;
1169         uint32_t bit = 0x00000001;
1170         if(osd_onoff) {
1171                 color_on = QVector4D(1.0,  1.0, 1.0, 0.8);
1172                 color_off = QVector4D(1.0, 1.0, 1.0, 0.00);
1173         } else {
1174                 color_on = QVector4D(0.00,0.00, 0.00, 0.0);
1175                 color_off = QVector4D(0.00,0.00, 0.00, 0.0);
1176         }
1177         if(osd_onoff) {
1178                 int major, minor;
1179                 //if(osd_led_status_bak != osd_led_status) {
1180                         for(int i = 0; i < osd_led_bit_width; i++) {
1181                                 if((bit & osd_led_status) == (bit & osd_led_status_bak)) {
1182                                         if((bit & osd_led_status) == 0) { 
1183                                                 bit <<= 1;
1184                                                 continue;
1185                                         }
1186                                 }
1187                                 if((i >= 2) && (i < 10)) { // FD
1188                                         major = 2;
1189                                         minor = i - 2;
1190                                 } else if((i >= 10) && (i < 12)) { // QD
1191                                         major = 3;
1192                                         minor = i - 10;
1193                                 } else if((i >= 12) && (i < 14)) { // CMT(R)
1194                                         major = 4;
1195                                         minor = i - 12;
1196                                 } else if((i >= 14) && (i < 16)) { // CMT(W)
1197                                         major = 5;
1198                                         minor = i - 14;
1199                                 } else {
1200                                         major = 0;
1201                                         minor = 0;
1202                                 }
1203                                 if((major != 0) && (icon_texid[major][minor] != NULL)) {
1204                                         drawMain(osd_pass->getShader(), osd_pass_vao[i], osd_pass_vbuffer[i],
1205                                                          icon_texid[major][minor]->textureId(),
1206                                                          ((osd_led_status & bit) != 0) ? color_on : color_off,
1207                                                          false, false, QVector3D(0.0, 0.0, 0.0));
1208                                 }
1209                                 bit <<= 1;
1210                         }
1211                         osd_led_status_bak = osd_led_status;
1212                 //}
1213         }
1214 }
1215
1216 void GLDraw_3_0::paintGL(void)
1217 {
1218         //p_wid->makeCurrent();
1219
1220 //      if(crt_flag || redraw_required) { //return;
1221                 if(emu_launched) {
1222                         crt_flag = false;
1223                 }
1224                 redraw_required = false;
1225                 extfunc->glViewport(0, 0, p_wid->width(), p_wid->height());
1226                 extfunc->glOrtho(-1.0f, 1.0f, -1.0f, 1.0f, -1.0, 1.0);
1227                 
1228                 extfunc->glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
1229                 extfunc->glEnable(GL_DEPTH_TEST);
1230                 extfunc->glDisable(GL_BLEND);
1231                 if(using_flags->is_use_one_board_computer() || using_flags->is_use_bitmap()) {
1232                         extfunc->glEnable(GL_BLEND);
1233                         drawBitmapTexture();
1234                 }
1235                 if(using_flags->get_max_button() > 0) {
1236                         extfunc->glEnable(GL_BLEND);
1237                         drawButtons();
1238                 }
1239                 drawScreenTexture();
1240                 extfunc->glEnable(GL_BLEND);
1241                 extfunc->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
1242                 extfunc->glDisable(GL_DEPTH_TEST);
1243                 //drawOsdLeds();
1244                 if(p_config->use_osd_virtual_media) drawOsdIcons();
1245                 extfunc->glDisable(GL_BLEND);
1246                 if(!using_flags->is_use_one_board_computer() && (using_flags->get_max_button() <= 0)) {
1247                         drawGrids();
1248                 }
1249                 extfunc->glFlush();
1250 //      } else {
1251 //              extfunc->glViewport(0, 0, p_wid->width(), p_wid->height());
1252 ///             extfunc->glOrtho(-1.0f, 1.0f, -1.0f, 1.0f, -1.0, 1.0);
1253 //              //drawOsdLeds();
1254 //              extfunc->glClear(GL_DEPTH_BUFFER_BIT);
1255 //              extfunc->glEnable(GL_DEPTH_TEST);
1256 //              extfunc->glEnable(GL_BLEND);
1257 //              //drawOsdLeds();
1258 //              drawOsdIcons();
1259 //              extfunc->glFlush();
1260 //      }               
1261         //p_wid->doneCurrent();
1262 }
1263
1264 void GLDraw_3_0::setBrightness(GLfloat r, GLfloat g, GLfloat b)
1265 {
1266         fBrightR = r;
1267         fBrightG = g;
1268         fBrightB = b;
1269
1270         if(imgptr != NULL) {
1271                 p_wid->makeCurrent();
1272                 if(uVramTextureID == NULL) {
1273                         uVramTextureID = new QOpenGLTexture(*imgptr);
1274                 }
1275                 if(using_flags->is_use_one_board_computer() || (using_flags->get_max_button() > 0)) {
1276                         uploadMainTexture(imgptr, true);
1277                 } else {
1278                         uploadMainTexture(imgptr, false);
1279                 }
1280                 crt_flag = true;
1281                 p_wid->doneCurrent();
1282         }
1283 }
1284
1285 void GLDraw_3_0::set_texture_vertex(float wmul, float hmul)
1286 {
1287         float wfactor = 1.0f;
1288         float hfactor = 1.0f;
1289
1290         vertexTmpTexture[0].x = -1.0f;
1291         vertexTmpTexture[0].y = -1.0f;
1292         vertexTmpTexture[0].z = -0.1f;
1293         vertexTmpTexture[0].s = 0.0f;
1294         vertexTmpTexture[0].t = 0.0f;
1295         
1296         vertexTmpTexture[1].x = wfactor;
1297         vertexTmpTexture[1].y = -1.0f;
1298         vertexTmpTexture[1].z = -0.1f;
1299         vertexTmpTexture[1].s = wmul;
1300         vertexTmpTexture[1].t = 0.0f;
1301         
1302         vertexTmpTexture[2].x = wfactor;
1303         vertexTmpTexture[2].y = hfactor;
1304         vertexTmpTexture[2].z = -0.1f;
1305         vertexTmpTexture[2].s = wmul;
1306         vertexTmpTexture[2].t = hmul;
1307         
1308         vertexTmpTexture[3].x = -1.0f;
1309         vertexTmpTexture[3].y = hfactor;
1310         vertexTmpTexture[3].z = -0.1f;
1311         vertexTmpTexture[3].s = 0.0f;
1312         vertexTmpTexture[3].t = hmul;
1313 }
1314
1315
1316 void GLDraw_3_0::set_osd_vertex(int xbit)
1317 {
1318         float xbase, ybase, zbase;
1319         VertexTexCoord_t vertex[4];
1320         int major, minor, nl;
1321         int i = xbit;
1322         if((xbit < 0) || (xbit >= 32)) return;
1323         if((i >= 2) && (i < 10)) { // FD
1324                 major = 0;
1325                 minor = i - 2;
1326                 nl = using_flags->get_max_drive();
1327         } else if((i >= 10) && (i < 12)) { // QD
1328                 major = 2;
1329                 minor = i - 10;
1330                 nl = using_flags->get_max_qd();
1331         } else if((i >= 12) && (i < 14)) { // CMT(R)
1332                 major = 1;
1333                 minor = i - 12;
1334                 nl = using_flags->get_max_tape();
1335         } else if((i >= 14) && (i < 16)) { // CMT(W)
1336                 major = 1;
1337                 minor = i - 14;
1338                 nl = using_flags->get_max_tape();
1339         } else if(i >= 16) {
1340                 major = 4 + (i / 8) - 2;
1341                 minor = i % 8;
1342                 nl = 8;
1343         } else {
1344                 major = 6;
1345                 minor = i;
1346                 nl = 2;
1347         }
1348         xbase =  1.0f - (1.0f * 48.0f / 640.0f) * (float)(nl - minor) - (4.0f / 640.0f);;
1349         ybase = -1.0f + (1.0f * 48.0f / 400.0f) * (float)(major + 1) + (4.0f / 400.0f);
1350         zbase = -0.998f;
1351         vertex[0].x = xbase;
1352         vertex[0].y = ybase;
1353         vertex[0].z = zbase;
1354         vertex[0].s = 0.0f;
1355         vertex[0].t = 0.0f;
1356         
1357         vertex[1].x = xbase + (48.0f / 640.0f);
1358         vertex[1].y = ybase;
1359         vertex[1].z = zbase;
1360         vertex[1].s = 1.0f;
1361         vertex[1].t = 0.0f;
1362         
1363         vertex[2].x = xbase + (48.0f / 640.0f);
1364         vertex[2].y = ybase - (48.0f / 400.0f);
1365         vertex[2].z = zbase;
1366         vertex[2].s = 1.0f;
1367         vertex[2].t = 1.0f;
1368         
1369         vertex[3].x = xbase;
1370         vertex[3].y = ybase - (48.0f / 400.0f);
1371         vertex[3].z = zbase;
1372         vertex[3].s = 0.0f;
1373         vertex[3].t = 1.0f;
1374         
1375         setNormalVAO(osd_pass->getShader(), osd_pass_vao[xbit],
1376                                  osd_pass_vbuffer[xbit],
1377                                  vertex, 4);
1378 }
1379
1380 void GLDraw_3_0::set_led_vertex(int xbit)
1381 {
1382         float xbase, ybase, zbase;
1383         VertexTexCoord_t vertex[4];
1384
1385         if((xbit < 0) || (xbit >=32)) return;
1386         xbase = 0.0f + (1.0f / 32.0f) * 31.0f - ((1.0f * (float)xbit) / 32.0f) + (1.0f / 128.0f);
1387         ybase = -1.0f + (2.0f / 64.0f) * 1.5f;
1388         zbase = -0.999f;
1389         vertex[0].x = xbase;
1390         vertex[0].y = ybase;
1391         vertex[0].z = zbase;
1392         vertex[0].s = 0.0f;
1393         vertex[0].t = 0.0f;
1394         
1395         vertex[1].x = xbase + (1.0f / 64.0f);
1396         vertex[1].y = ybase;
1397         vertex[1].z = zbase;
1398         vertex[1].s = 1.0f;
1399         vertex[1].t = 0.0f;
1400         
1401         vertex[2].x = xbase + (1.0f / 64.0f);
1402         vertex[2].y = ybase - (1.0f / 64.0f);
1403         vertex[2].z = zbase;
1404         vertex[2].s = 1.0f;
1405         vertex[2].t = 1.0f;
1406         
1407         vertex[3].x = xbase;
1408         vertex[3].y = ybase - (1.0f / 64.0f);
1409         vertex[3].z = zbase;
1410         vertex[3].s = 0.0f;
1411         vertex[3].t = 1.0f;
1412         
1413         setNormalVAO(led_pass->getShader(), led_pass_vao[xbit],
1414                                  led_pass_vbuffer[xbit],
1415                                  vertex, 4);
1416 }
1417
1418 void GLDraw_3_0::do_set_screen_multiply(float mul)
1419 {
1420         screen_multiply = mul;
1421         do_set_texture_size(imgptr, screen_texture_width, screen_texture_height);
1422 }
1423
1424 void GLDraw_3_0::do_set_texture_size(QImage *p, int w, int h)
1425 {
1426         if(w <= 0) w = using_flags->get_real_screen_width();
1427         if(h <= 0) h = using_flags->get_real_screen_height();
1428         imgptr = p;
1429         float iw, ih;
1430         if(p != NULL) {
1431                 iw = (float)p->width();
1432                 ih = (float)p->height();
1433         } else {
1434                 iw = (float)using_flags->get_real_screen_width();
1435                 ih = (float)using_flags->get_real_screen_height();
1436         }
1437         //if((w == screen_texture_width) && (h == screen_texture_height)) return;
1438         //printf("%dx%d -> %fx%f\n", w, h, iw, ih);
1439         if(p_wid != NULL) {
1440                 screen_texture_width = w;
1441                 screen_texture_height = h;
1442
1443                 p_wid->makeCurrent();
1444                 {
1445                         set_texture_vertex((float)w / iw, (float)h / ih);
1446                         setNormalVAO(std_pass->getShader(), std_pass->getVAO(),
1447                                                  std_pass->getVertexBuffer(),
1448                                                  vertexTmpTexture, 4);
1449                         //set_texture_vertex(p, p_wid->width(), p_wid->height(), w, h);
1450                         set_texture_vertex((float)w / iw, (float)h / ih);
1451                         setNormalVAO(ntsc_pass1->getShader(), ntsc_pass1->getVAO(),
1452                                                  ntsc_pass1->getVertexBuffer(),
1453                                                  vertexTmpTexture, 4);
1454
1455                         set_texture_vertex(1.0f, 1.0f);
1456                         setNormalVAO(ntsc_pass2->getShader(), ntsc_pass2->getVAO(),
1457                                                  ntsc_pass2->getVertexBuffer(),
1458                                                  vertexTmpTexture, 4);
1459                         
1460                 }
1461                 if(p != NULL) {
1462                         if(uVramTextureID != NULL) delete uVramTextureID;
1463                         uVramTextureID = new QOpenGLTexture(*p);
1464                 }
1465                 vertexFormat[0].x = -1.0f;
1466                 vertexFormat[0].y = -1.0f;
1467                 vertexFormat[0].z = -0.9f;
1468                 vertexFormat[1].x =  1.0f;
1469                 vertexFormat[1].y = -1.0f;
1470                 vertexFormat[1].z = -0.9f;
1471                 vertexFormat[2].x =  1.0f;
1472                 vertexFormat[2].y =  1.0f;
1473                 vertexFormat[2].z = -0.9f;
1474                 vertexFormat[3].x = -1.0f;
1475                 vertexFormat[3].y =  1.0f;
1476                 vertexFormat[3].z = -0.9f;
1477
1478                 vertexFormat[0].s = 0.0f;
1479                 //vertexFormat[0].t = (float)h / ih;
1480                 //vertexFormat[1].s = (float)w / iw;
1481                 //vertexFormat[1].t = (float)h / ih;
1482                 //vertexFormat[2].s = (float)w / iw;
1483                 vertexFormat[0].t = 1.0f;
1484                 vertexFormat[1].s = 1.0f;
1485                 vertexFormat[1].t = 1.0f;
1486                 vertexFormat[2].s = 1.0f;
1487                 vertexFormat[2].t = 0.0f;
1488                 vertexFormat[3].s = 0.0f;
1489                 vertexFormat[3].t = 0.0f;
1490                 
1491                 setNormalVAO(main_pass->getShader(), main_pass->getVAO(),
1492                                          main_pass->getVertexBuffer(),
1493                                          vertexFormat, 4);
1494                 
1495                 if(w > using_flags->get_real_screen_width()) {
1496                         w = using_flags->get_real_screen_width();
1497                 }                       
1498                 if(h > using_flags->get_real_screen_height()) {
1499                         h = using_flags->get_real_screen_height();
1500                 }
1501                 this->doSetGridsHorizonal(h, false);
1502                 this->doSetGridsVertical(w, false);
1503                 p_wid->doneCurrent();
1504         }
1505 }
1506 void GLDraw_3_0::do_set_horiz_lines(int lines)
1507 {
1508         if(lines > using_flags->get_real_screen_height()) {
1509                 lines = using_flags->get_real_screen_height();
1510         }                       
1511         this->doSetGridsHorizonal(lines, false);
1512 }
1513
1514 void GLDraw_3_0::resizeGL_Screen(void)
1515 {
1516         if(main_pass != NULL) {
1517                 setNormalVAO(main_pass->getShader(), main_pass->getVAO(),
1518                                          main_pass->getVertexBuffer(),
1519                                          vertexFormat, 4);
1520         }
1521 }       
1522
1523 void GLDraw_3_0::resizeGL(int width, int height)
1524 {
1525         //int side = qMin(width, height);
1526         p_wid->makeCurrent();
1527         extfunc->glViewport(0, 0, width, height);
1528         extfunc->glOrtho(-1.0f, 1.0f, -1.0f, 1.0f, -1.0, 1.0);
1529         crt_flag = true;
1530         if(!using_flags->is_use_one_board_computer() && (using_flags->get_max_button() <= 0)) {
1531                 doSetGridsHorizonal(vert_lines, true);
1532                 if(using_flags->is_use_vertical_pixel_lines()) {
1533                         doSetGridsVertical(horiz_pixels, true);
1534                 }
1535         }
1536         resizeGL_SetVertexs();
1537         resizeGL_Screen();
1538         if(using_flags->is_use_one_board_computer()) {
1539                 setNormalVAO(bitmap_block->getShader(), bitmap_block->getVAO(),
1540                                          bitmap_block->getVertexBuffer(),
1541                                          vertexBitmap, 4);
1542         }       
1543         if(using_flags->get_max_button() > 0) {
1544                 updateButtonTexture();
1545         }
1546         p_wid->doneCurrent();
1547 }