3 namespace gfx::drivers;
11 #if !defined(__ANDROID__) && !defined(__EMSCRIPTEN__) && !defined(__ODROID__)
13 # include "gl_core_3_3.h"
15 # include "gl_compat_4_4.h"
19 #if defined(__ANDROID__) || defined(__ODROID__)
28 #define GL_BGRA_EXT 0x80E1
32 #undef glEnableClientState
33 #undef glDisableClientState
34 #undef GL_VERTEX_ARRAY
35 #undef GL_NORMAL_ARRAY
36 #undef GL_TEXTURE_COORD_ARRAY
39 #define glEnableClientState glEnableVertexAttribArray
40 #define glDisableClientState glDisableVertexAttribArray
41 #define GL_VERTEX_ARRAY GLBufferContents::vertex
42 #define GL_NORMAL_ARRAY GLBufferContents::normal
43 #define GL_TEXTURE_COORD_ARRAY GLBufferContents::texCoord
44 #define GL_COLOR_ARRAY GLBufferContents::color
48 // We were using PBUFFER for alpha compositing on Linux before, but it does not seem to work, nor be required anymore.
50 #if defined(__unix__) || defined(__APPLE__)
52 #if !defined(__MINGW32__)
53 #define GL_GLEXT_PROTOTYPES
56 #define pointer _pointer
59 #if !defined(__ANDROID__) && !defined(__ODROID__) && !defined(__EMSCRIPTEN__)
61 #define property _property
65 #define Window X11Window
66 #define Cursor X11Cursor
68 #define Display X11Display
70 #define KeyCode X11KeyCode
71 #define Picture X11Picture
72 #define Glyph X11Glyph
76 #include <X11/Xutil.h>
78 #include <X11/extensions/XShm.h>
81 #include <X11/extensions/Xrender.h>
82 #include <X11/extensions/shape.h>
101 #if defined(__APPLE__)
102 #include <OpenGl/gl.h>
105 #if defined(__WIN32__) || defined(__unix__) || defined(__APPLE__)
107 #if defined(__WIN32__)
108 //#define WIN32_LEAN_AND_MEAN
110 #define _WIN32_WINNT 0x0502
111 #define String Sting_
116 #if defined(__ANDROID__) || defined(__ODROID__)
117 #if defined(__ODROID__) && !defined(ES1_1)
122 #define property _property
125 #define Window X11Window
126 #define Cursor X11Cursor
128 #define Display X11Display
130 #define KeyCode X11KeyCode
131 #define Picture X11Picture
149 #elif defined(__EMSCRIPTEN__)
153 #define property _property
157 //#include <GLES/gl.h>
158 #include <GLES2/gl2.h>
160 #include <emscripten/emscripten.h>
161 #include <emscripten/html5.h>
174 #if defined(__unix__) || defined(__APPLE__)
176 #if !defined(__ANDROID__) && !defined(__ODROID__) && !defined(__EMSCRIPTEN__)
182 #define glLoadMatrix glLoadMatrixd
183 #define glMultMatrix glMultMatrixd
184 #define glGetMatrix glGetDoublev
185 #define glTranslate glTranslated
186 #define glScale glScaled
189 #define glVertex3v glVertex3dv
190 #define glNormal3v glNormal3dv
194 //#ifdef VERTEX_FORMAT_DOUBLE
196 #define glLoadMatrix glLoadMatrixd
197 #define glMultMatrix glMultMatrixd
198 #define glGetMatrix glGetDoublev
199 #define glVertex3v glVertex3dv
200 #define glNormal3v glNormal3dv
201 #define glTranslate glTranslated
202 #define glScale glScaled
203 //#define GL_VERTEX_FORMAT GL_DOUBLE
207 #define glLoadMatrix glLoadMatrixf
208 #define glMultMatrix glMultMatrixf
209 #define glGetMatrix glGetFloatv
210 #define glVertex3v glVertex3fv
211 #define glNormal3v glNormal3fv
212 #define glTranslate glTranslatef
213 #define glScale glScalef
214 //#define GL_VERTEX_FORMAT GL_FLOAT
219 #define GL_ARRAY_BUFFER_ARB 0x8892
220 #define GL_ELEMENT_ARRAY_BUFFER_ARB 0x8893
221 #define GL_STATIC_DRAW_ARB 0x88E4
222 #define GL_LIGHT_MODEL_COLOR_CONTROL 0x81F8
223 #define GL_SEPARATE_SPECULAR_COLOR 0x81FA
225 #define GL_MULTISAMPLE_ARB 0x809D
227 #if defined(__WIN32__)
230 typedef void (APIENTRY * PFNGLLOCKARRAYSEXTPROC) (GLint first, GLsizei count);
231 typedef void (APIENTRY * PFNGLUNLOCKARRAYSEXTPROC) (void);
233 static PFNGLLOCKARRAYSEXTPROC glLockArraysEXT = null;
234 static PFNGLUNLOCKARRAYSEXTPROC glUnlockArraysEXT = null;
236 static PFNWGLCHOOSEPIXELFORMATARBPROC wglChoosePixelFormatARB = null;
237 static PFNWGLGETEXTENSIONSSTRINGARBPROC wglGetExtensionsStringARB = null;
238 static PFNWGLCREATEPBUFFERARBPROC wglCreatePbufferARB = null;
239 static PFNWGLGETPBUFFERDCARBPROC wglGetPbufferDCARB = null;
240 static PFNWGLQUERYPBUFFERARBPROC wglQueryPbufferARB = null;
241 static PFNWGLDESTROYPBUFFERARBPROC wglDestroyPbufferARB = null;
242 static PFNWGLRELEASEPBUFFERDCARBPROC wglReleasePbufferDCARB = null;
243 static PFNWGLBINDTEXIMAGEARBPROC wglBindTexImageARB = null;
244 static PFNWGLRELEASETEXIMAGEARBPROC wglReleaseTexImageARB = null;
245 static PFNWGLSWAPINTERVALEXTPROC wglSwapIntervalEXT = null;
246 static PFNWGLCREATECONTEXTATTRIBSARBPROC wglCreateContextAttribsARB = null;
250 #if !defined(__ANDROID__) && !defined(__APPLE__) && !defined(__ODROID__) && !defined(__EMSCRIPTEN__)
252 GLAPI void APIENTRY glLockArraysEXT (GLint first, GLsizei count);
253 GLAPI void APIENTRY glUnlockArraysEXT (void);
257 #if defined(__ANDROID__) || defined(__ODROID__)
258 #define GL_FRAMEBUFFER GL_FRAMEBUFFER_OES
259 #define GL_RENDERBUFFER GL_RENDERBUFFER_OES
260 #define GL_COLOR_ATTACHMENT0 GL_COLOR_ATTACHMENT0_OES
261 #define GL_BGRA_EXT 0
264 #if defined(__ANDROID__) || defined(__ODROID__) || defined(__EMSCRIPTEN__)
266 #define GL_POLYGON_STIPPLE 0xFFFF
267 #define GL_LINE_STIPPLE 0xFFFF
268 #define GL_LINE 0xFFFF
269 #define GL_FILL 0xFFFF
270 #define GL_ALL_ATTRIB_BITS 0xFFFF
271 #define GL_LIGHT_MODEL_LOCAL_VIEWER 0xFFFF
277 #define GL_QUAD_STRIP 0
278 //#define GL_DOUBLE 0
279 //#define GL_UNSIGNED_INT 0
282 //#define GL_LINE_STIPPLE 0
283 #define GL_UNPACK_ROW_LENGTH 0
284 #define GL_UNPACK_SKIP_PIXELS 0
285 #define GL_UNPACK_SKIP_ROWS 0
287 #define GL_PACK_ROW_LENGTH 0
288 #define GL_PACK_SKIP_ROWS 0
289 #define GL_PACK_SKIP_PIXELS 0
295 #if defined(__ANDROID__) || defined(__ODROID__)
296 #define glBindFramebuffer glBindFramebufferOES
297 #define glBindRenderbuffer glBindRenderbufferOES
298 #define glFramebufferTexture2D glFramebufferTexture2DOES
299 #define glGenFramebuffers glGenFramebuffersOES
300 #define glGenRenderbuffers glGenRenderbuffersOES
301 #define glDeleteFramebuffers glDeleteFramebuffersOES
302 #define glDeleteRenderbuffers glDeleteRenderbuffersOES
305 #if defined(__ANDROID__) || defined(__ODROID__) || defined(__EMSCRIPTEN__)
306 #define GL_INT 0x1404
307 #define GL_UNSIGNED_INT 0x1405
308 #define GL_DOUBLE 0x140A
312 #if defined(ES1_1) || defined(ES2) || defined(SHADERS)
343 #undef glLoadIdentity
348 #undef glColorMaterial
351 #define glRecti glimtkRecti
352 #define glBegin glimtkBegin
353 #define glTexCoord2i glimtkTexCoord2i
354 #define glVertex2i glimtkVertex2i
355 #define glTexCoord2d glimtkTexCoord2d
356 #define glVertex2d glimtkVertex2d
357 #define glTexCoord2f glimtkTexCoord2f
358 #define glVertex2f glimtkVertex2f
359 #define glEnd glimtkEnd
360 #define glColor3f glimtkColor3f
361 #define glColor4ub glimtkColor4ub
362 #define glColor4fv glimtkColor4fv
363 #define glNormal3fv glimtkNormal3fv
364 #define glNormal3f glimtkNormal3f
365 #define glTexCoord2fv glimtkTexCoord2fv
366 #define glVertex3d glimtkVertex3d
367 #define glVertex3dv glimtkVertex3dv
368 #define glVertex3f glimtkVertex3f
369 #define glVertex3fv glimtkVertex3fv
371 #define glLoadMatrixd glmsLoadMatrixd
372 #define glMultMatrixd glmsMultMatrixd
373 #define glFrustum glmsFrustum
374 #define glOrtho glmsOrtho
375 #define glScaled glmsScaled
376 #define glScalef glmsScaled
377 #define glTranslated glmsTranslated
378 #define glRotated glmsRotated
379 #define glMatrixMode glmsMatrixMode
380 #define glLoadIdentity glmsLoadIdentity
381 #define glPushMatrix glmsPushMatrix
382 #define glPopMatrix glmsPopMatrix
384 #define glLineStipple glesLineStipple
385 #define glColorMaterial glesColorMaterial
386 #define glLightModeli glesLightModeli
390 public void glesColorMaterial(int a, int b)
392 PrintLn("glColorMaterial stub");
395 static GLuint stippleTexture;
396 #if defined(ES1_1) || defined(ES2) || defined(SHADERS)
397 static bool stippleEnabled;
400 public void glesLineStipple( int i, unsigned short j )
404 for(x = 0; x < 16; x++)
406 bool v = (j & (1 << x)) != 0;
407 texture[x] = v ? 0xFFFFFFFF : 0;
410 glGenTextures(1, &stippleTexture);
411 glBindTexture(GL_TEXTURE_2D, stippleTexture);
412 glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 16, 1, 0, GL_RGBA, GL_UNSIGNED_BYTE, texture);
414 // TOOD: Special shading code for stippling?
415 GLSetupTexturing(true);
416 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
417 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
418 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
419 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
420 glMatrixMode(GL_TEXTURE);
422 //glTranslated(1.0/backAttrib->texW/2.0f, 1.0/backAttrib->texH/2.0f, 0.0f);
423 glScaled(i/16.0, 1, 1.0f);
424 glTranslated(0.5, 0.5, 0);
425 glMatrixMode(MatrixMode::projection);
428 public void glesLightModeli( unsigned int pname, int param )
430 #if !defined(SHADERS)
431 if(pname == GL_LIGHT_MODEL_TWO_SIDE)
432 glLightModelf(GL_LIGHT_MODEL_TWO_SIDE, param);
436 #if defined(__ANDROID__) || defined(__ODROID__) || defined(__EMSCRIPTEN__)
437 void glClearDepth( double depth ) { glClearDepthf((float)depth); }
440 #if defined(__ANDROID__) || defined(__ODROID__)
441 void glFogi( unsigned int pname, int param ) { }
442 void glPolygonMode( unsigned int i, unsigned int j ) { }
445 // *** Picking won't be supported for now ***
446 void glPushName( unsigned int i ) { }
447 void glLoadName( unsigned int i ) { }
450 // Probably replace by regular glBlendFunc ...
451 void glBlendFuncSeparate(int a, int b, int c, int d)
456 // For direct pixel blitting...
457 void glRasterPos2d(double a, double b) { }
458 void glPixelZoom(float a, float b) { }
459 void glDrawPixels(int a, int b, int c, int d, void * e) { }
463 #if !defined(ECERE_NO3D) && !defined(ECERE_VANILLA)
464 static int primitiveTypes[RenderPrimitiveType] =
466 GL_POINTS, GL_LINES, GL_TRIANGLES, GL_TRIANGLE_STRIP, GL_TRIANGLE_FAN,
467 #if defined(SHADERS) || defined(ES1_1) || defined(ES2)
468 GL_TRIANGLE_FAN, // NOTE: This will only work for single quads
472 GLIMTKMode::quadStrip,
477 public void GLSetupTexturing(bool enable)
480 shader_texturing(enable);
482 (enable ? glEnable : glDisable)(GL_TEXTURE_2D);
486 public void GLSetupFog(bool enable)
491 (enable ? glEnable : glDisable)(GL_FOG);
495 public void GLSetupLighting(bool enable)
498 shader_lighting(enable);
500 (enable ? glEnable : glDisable)(GL_LIGHTING);
504 // Non OpenGL ES friendly stuff
506 #if defined(ES1_1) || defined(ES2)
508 //#undef GL_UNSIGNED_INT
514 #undef GL_POLYGON_STIPPLE
515 #undef GL_LINE_STIPPLE
518 #undef GL_ALL_ATTRIB_BITS
519 #undef GL_LIGHT_MODEL_LOCAL_VIEWER
523 static int displayWidth, displayHeight;
525 #define GL_CLAMP_TO_EDGE 0x812F
527 static bool vboAvailable;
529 static bool useSingleGLContext = false;
530 class OGLDisplay : struct
532 #if defined(__WIN32__)
543 byte * pboMemory1, * pboMemory2;
545 #elif !defined(__ANDROID__) && !defined(__ODROID__) && !defined(__EMSCRIPTEN__)
546 GLXContext glContext;
549 XShmSegmentInfo shminfo;
551 XShmSegmentInfo shminfoShape;
556 X11Picture windowPicture;
557 X11Picture pixmapPicture;
559 X11Picture shapePicture;
562 ColorAlpha * flippingBuffer;
563 int flipBufH, flipBufW;
569 static void APIENTRY openglCallbackFunction(GLenum source,
574 const GLchar* message,
575 const void* userParam)
577 PrintLn("---------------------opengl-callback-start------------");
578 PrintLn("message: ", message);
582 case GL_DEBUG_TYPE_ERROR: PrintLn("ERROR"); break;
583 case GL_DEBUG_TYPE_DEPRECATED_BEHAVIOR: PrintLn("DEPRECATED_BEHAVIOR"); break;
584 case GL_DEBUG_TYPE_UNDEFINED_BEHAVIOR: PrintLn("UNDEFINED_BEHAVIOR"); break;
585 case GL_DEBUG_TYPE_PORTABILITY: PrintLn("PORTABILITY"); break;
586 case GL_DEBUG_TYPE_PERFORMANCE: PrintLn("PERFORMANCE"); break;
587 case GL_DEBUG_TYPE_OTHER: PrintLn("OTHER"); break;
594 case GL_DEBUG_SEVERITY_LOW: PrintLn("LOW"); break;
595 case GL_DEBUG_SEVERITY_MEDIUM: PrintLn("MEDIUM"); break;
596 case GL_DEBUG_SEVERITY_HIGH: PrintLn("HIGH"); break;
598 PrintLn("---------------------opengl-callback-end--------------");
602 class OGLSystem : struct
607 #if defined(__WIN32__)
608 PIXELFORMATDESCRIPTOR pfd;
613 #elif defined(__EMSCRIPTEN__)
614 EMSCRIPTEN_WEBGL_CONTEXT_HANDLE glc;
615 #elif !defined(__ANDROID__) && !defined(__ODROID__)
616 XVisualInfo * visualInfo;
617 GLXContext glContext;
618 GLXDrawable glxDrawable;
622 class OGLSurface : struct
630 float foreground[4], background[4], bitmapMult[4];
633 class OGLMesh : struct
642 class OGLIndices : struct
652 #if !defined(__ANDROID__) && !defined(__EMSCRIPTEN__) && !defined(__ODROID__)
654 static void setupDebugging()
656 if(glDebugMessageCallback)
658 GLuint unusedIds = 0;
660 glEnable(GL_DEBUG_OUTPUT_SYNCHRONOUS);
662 glDebugMessageCallback(openglCallbackFunction, null);
663 glDebugMessageControl(GL_DONT_CARE,
675 #if defined(__WIN32__)
676 static HGLRC winCreateContext(HDC hdc)
680 if(wglCreateContextAttribsARB)
684 WGL_CONTEXT_MAJOR_VERSION_ARB, 4,
685 WGL_CONTEXT_MINOR_VERSION_ARB, 4,
686 WGL_CONTEXT_FLAGS_ARB, /*WGL_CONTEXT_FORWARD_COMPATIBLE_BIT_ARB | */WGL_CONTEXT_DEBUG_BIT_ARB,
687 WGL_CONTEXT_PROFILE_MASK_ARB, WGL_CONTEXT_COMPATIBILITY_PROFILE_BIT_ARB /*WGL_CONTEXT_CORE_PROFILE_BIT_ARB*/,
690 result = wglCreateContextAttribsARB(hdc, null, attribs);
696 result = wglCreateContextAttribsARB(hdc, null, attribs);
701 result = wglCreateContext(hdc);
706 class OpenGLDisplayDriver : DisplayDriver
708 class_property(name) = "OpenGL";
710 bool LockSystem(DisplaySystem displaySystem)
712 #if defined(__EMSCRIPTEN__)
713 OGLSystem oglSystem = displaySystem.driverData;
714 emscripten_webgl_make_context_current(oglSystem.glc);
715 #elif !defined(__ANDROID__) && !defined(__ODROID__)
716 OGLSystem oglSystem = displaySystem.driverData;
717 if(useSingleGLContext) return true;
718 #if defined(__WIN32__)
719 wglMakeCurrent(oglSystem.hdc, oglSystem.glrc);
720 #elif defined(__unix__) || defined(__APPLE__)
721 //if(previous) return true;
722 // printf("Making SYSTEM current\n");
723 glXMakeCurrent(xGlobalDisplay, (GLXDrawable)oglSystem.glxDrawable, oglSystem.glContext);
724 //previous = oglSystem.glContext;
727 GLABBindBuffer(GL_ARRAY_BUFFER, 0);
728 GLABBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);
732 void UnlockSystem(DisplaySystem displaySystem)
734 if(useSingleGLContext) return;
735 #if defined(__WIN32__)
736 wglMakeCurrent(null, null);
737 #elif defined(__unix__) || defined(__APPLE__)
738 // printf("Making NULL current\n");
739 #if defined(__ANDROID__) || defined(__ODROID__) || defined(__EMSCRIPTEN__)
741 glXMakeCurrent(xGlobalDisplay, None, null);
747 bool Lock(Display display)
749 #if !defined(__ANDROID__) && !defined(__ODROID__) && !defined(__EMSCRIPTEN__)
750 OGLDisplay oglDisplay = display.driverData;
751 if(useSingleGLContext) return true;
752 #if defined(__WIN32__)
753 wglMakeCurrent(oglDisplay.hdc, oglDisplay.glrc);
754 #elif defined(__unix__) || defined(__APPLE__)
755 // if(previous) glXMakeCurrent(xGlobalDisplay, None, null);
756 // printf(" Making DISPLAY current\n");
757 glXMakeCurrent(xGlobalDisplay, (GLXDrawable)display.window, oglDisplay.glContext);
760 GLABBindBuffer(GL_ARRAY_BUFFER, 0);
761 GLABBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);
765 void Unlock(Display display)
767 if(useSingleGLContext) return;
768 //printf(" Making NULL current\n");
769 //glXMakeCurrent(xGlobalDisplay, None, null);
771 LockSystem(display.displaySystem);
774 void DestroyDisplay(Display display)
776 OGLDisplay oglDisplay = display.driverData;
780 #if defined(__WIN32__)
781 wglMakeCurrent( null, null );
784 wglDeleteContext(oglDisplay.glrc);
786 if(oglDisplay.hdc && oglDisplay.pBuffer)
787 wglReleasePbufferDCARB(oglDisplay.pBuffer, oglDisplay.hdc);
789 if(oglDisplay.pBuffer)
790 wglDestroyPbufferARB(oglDisplay.pBuffer);
793 ReleaseDC(display.window, oglDisplay.hdc);
795 if(oglDisplay.memDC) DeleteDC(oglDisplay.memDC);
796 if(oglDisplay.memBitmap) DeleteObject(oglDisplay.memBitmap);
798 #elif defined(__unix__) || defined(__APPLE__)
799 #if defined(__ANDROID__) || defined(__ODROID__) || defined(__EMSCRIPTEN__)
801 if(oglDisplay.shapePixmap)
802 XFreePixmap(xGlobalDisplay, oglDisplay.shapePixmap);
803 if(oglDisplay.pixmap)
804 XFreePixmap(xGlobalDisplay, oglDisplay.pixmap);
807 if(oglDisplay.shminfoShape.shmid != -1)
809 XShmDetach(xGlobalDisplay, &oglDisplay.shminfo);
810 if(oglDisplay.shminfo.shmaddr != (void *)-1)
811 shmdt(oglDisplay.shminfo.shmaddr);
812 shmctl(oglDisplay.shminfo.shmid, IPC_RMID, 0);
815 if(oglDisplay.shapeImage)
817 if(oglDisplay.shminfoShape.shmid != -1)
819 XShmDetach(xGlobalDisplay, &oglDisplay.shminfoShape);
820 if(oglDisplay.shminfoShape.shmaddr != (void *)-1)
821 shmdt(oglDisplay.shminfoShape.shmaddr);
822 shmctl(oglDisplay.shminfoShape.shmid, IPC_RMID, 0);
824 XDestroyImage(oglDisplay.shapeImage);
825 oglDisplay.shapeImage = None;
828 glXMakeCurrent(xGlobalDisplay, None, null);
830 if(oglDisplay.glContext)
831 glXDestroyContext(xGlobalDisplay, oglDisplay.glContext);
834 delete oglDisplay.flippingBuffer;
836 display.driverData = null;
840 void ::CheckExtensions(OGLSystem oglSystem)
842 const char * extensions = (const char *)glGetString(GL_EXTENSIONS);
844 printf("extensions: %s\n", extensions);
847 oglSystem.pow2textures = (extensions && strstr(extensions, "GL_ARB_texture_non_power_of_two")) ? false : true;
848 glGetIntegerv(GL_MAX_TEXTURE_SIZE, &oglSystem.maxTextureSize);
851 bool CreateDisplaySystem(DisplaySystem displaySystem)
854 OGLSystem oglSystem = displaySystem.driverData = OGLSystem { };
857 PrintLn("OpenGL driver's CreateDisplaySystem()");
861 oglSystem.hwnd = CreateWindow("static", null, 0,0,0,0,0,null,null,null,null);
863 oglSystem.hdc = GetDC(oglSystem.hwnd);
867 oglSystem.pfd.nSize = (short)sizeof(oglSystem.pfd);
868 oglSystem.pfd.nVersion = 1;
869 oglSystem.pfd.dwFlags = PFD_DRAW_TO_WINDOW /*PFD_DRAW_TO_BITMAP*/ | PFD_SUPPORT_OPENGL | PFD_DOUBLEBUFFER;
870 oglSystem.pfd.iPixelType = PFD_TYPE_RGBA;
871 oglSystem.pfd.cColorBits = 24;
872 oglSystem.pfd.cAlphaBits = 8;
873 oglSystem.pfd.cDepthBits = 24;
874 oglSystem.pfd.iLayerType = PFD_MAIN_PLANE;
876 oglSystem.format = ChoosePixelFormat(oglSystem.hdc, &oglSystem.pfd);
877 DescribePixelFormat(oglSystem.hdc, oglSystem.format, sizeof(oglSystem.pfd), &oglSystem.pfd);
879 if(oglSystem.pfd.cColorBits > 8)
881 SetPixelFormat(oglSystem.hdc, oglSystem.format, &oglSystem.pfd);
882 oglSystem.glrc = wglCreateContext(oglSystem.hdc);
885 wglMakeCurrent(oglSystem.hdc, oglSystem.glrc);
887 wglChoosePixelFormatARB = (void *) wglGetProcAddress("wglChoosePixelFormatARB");
888 wglGetExtensionsStringARB = (void *)wglGetProcAddress("wglGetExtensionsStringARB");
889 wglCreatePbufferARB = (void *)wglGetProcAddress("wglCreatePbufferARB");
890 wglGetPbufferDCARB = (void *)wglGetProcAddress("wglGetPbufferDCARB");
891 wglQueryPbufferARB = (void *)wglGetProcAddress("wglQueryPbufferARB");
892 wglDestroyPbufferARB = (void *)wglGetProcAddress("wglDestroyPbufferARB");
893 wglReleasePbufferDCARB = (void *)wglGetProcAddress("wglReleasePbufferDCARB");
894 wglBindTexImageARB = (void *)wglGetProcAddress("wglBindTexImageARB");
895 wglReleaseTexImageARB = (void *)wglGetProcAddress("wglReleaseTexImageARB");
896 wglSwapIntervalEXT = (void *)wglGetProcAddress("wglSwapIntervalEXT");
897 wglCreateContextAttribsARB = (void *)wglGetProcAddress("wglCreateContextAttribsARB");
899 glLockArraysEXT = (void *) wglGetProcAddress("glLockArraysEXT" );
900 glUnlockArraysEXT = (void *) wglGetProcAddress("glUnlockArraysEXT");
902 // eSystem_LoggingMode(LOG_MSGBOX, null);
904 if(wglChoosePixelFormatARB)
909 float fAttributes[] = {0,0};
912 WGL_DRAW_TO_WINDOW_ARB,GL_TRUE,
913 WGL_SUPPORT_OPENGL_ARB,GL_TRUE,
914 WGL_ACCELERATION_ARB,WGL_FULL_ACCELERATION_ARB,
915 WGL_COLOR_BITS_ARB,24,
916 WGL_ALPHA_BITS_ARB,8,
917 WGL_DEPTH_BITS_ARB,16,
918 WGL_STENCIL_BITS_ARB,0,
919 WGL_DOUBLE_BUFFER_ARB,GL_TRUE,
920 WGL_SAMPLE_BUFFERS_ARB,GL_TRUE,
921 WGL_SAMPLES_ARB, 4, // Check For 4x Multisampling
925 //Log("Found wglChoosePixelFormatARB\n");
927 valid = wglChoosePixelFormatARB(oglSystem.hdc,iAttributes,fAttributes,1,&pixelFormat,&numFormats);
928 if(!valid || !numFormats)
930 //Log("Can't find 4x multi sampling\n");
932 valid = wglChoosePixelFormatARB(oglSystem.hdc,iAttributes,fAttributes,1,&pixelFormat,&numFormats);
933 if(!valid || !numFormats)
935 // Log("Can't find 2x multi sampling\n");
938 valid = wglChoosePixelFormatARB(oglSystem.hdc,iAttributes,fAttributes,1,&pixelFormat,&numFormats);
941 if(valid && numFormats)
943 oglSystem.format = pixelFormat;
944 wglMakeCurrent(null, null);
945 wglDeleteContext(oglSystem.glrc);
947 // *** DescribePixelFormat does not support WGL pixel formats! ***
948 //DescribePixelFormat(oglSystem.hdc, oglSystem.format, sizeof(oglSystem.pfd), &oglSystem.pfd);
949 SetPixelFormat(oglSystem.hdc, oglSystem.format, &oglSystem.pfd);
950 //Log("Successfully set pixel format\n");
953 PrintLn("winCreateContext()");
955 oglSystem.glrc = winCreateContext(oglSystem.hdc);
957 PrintLn("wglMakeCurrent()");
959 wglMakeCurrent(oglSystem.hdc, oglSystem.glrc);
963 eSystem_Logf("Can't find wglChoosePixelFormatARB\n");*/
967 wglMakeCurrent(null, null);
969 //eSystem_DumpErrors(true);
973 #elif defined(__unix__) || defined(__APPLE__)
975 #if defined(__ANDROID__) || defined(__ODROID__)
976 #if defined(__ANDROID__)
977 egl_init_display(guiApp.desktop.windowHandle);
978 #elif defined(__ODROID__)
979 egl_init_display((uint)displaySystem.window);
980 CheckExtensions(oglSystem);
983 // TODO: Clean this up? Needed here?
984 glEnableClientState(GL_VERTEX_ARRAY);
986 // Initialize GL state.
987 glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_FASTEST);
988 glEnable(GL_CULL_FACE);
989 glShadeModel(GL_SMOOTH);
990 glDisable(GL_DEPTH_TEST);
992 glDisable(GL_CULL_FACE);
993 glDisable(GL_DEPTH_TEST);
995 glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
998 matrixStack[0][0].Identity();
999 matrixStack[1][0].Identity();
1000 matrixStack[2][0].Identity();
1002 glmsMatrixMode(GL_MODELVIEW);
1003 glScaled(1.0, 1.0, -1.0);
1004 glmsMatrixMode(GL_PROJECTION);
1005 glShadeModel(GL_FLAT);
1007 glLightModeli(GL_LIGHT_MODEL_COLOR_CONTROL, GL_SEPARATE_SPECULAR_COLOR);
1008 glFogi(GL_FOG_MODE, GL_EXP);
1009 glFogf(GL_FOG_DENSITY, 0);
1010 glEnable(GL_NORMALIZE);
1011 glDepthFunc(GL_LESS);
1013 glDisable(GL_MULTISAMPLE_ARB);
1015 glViewport(0,0,eglWidth,eglHeight);
1017 glOrtho(0,eglWidth,eglHeight,0,0.0,1.0);
1019 glabCurArrayBuffer = 0;
1020 glabCurElementBuffer = 0;
1023 #elif defined(__EMSCRIPTEN__)
1025 EmscriptenWebGLContextAttributes attribs = { 0 };
1027 attribs.antialias = 1;
1034 EM_BOOL premultipliedAlpha;
1035 EM_BOOL preserveDrawingBuffer;
1036 EM_BOOL preferLowPowerToHighPerformance;
1037 EM_BOOL failIfMajorPerformanceCaveat;
1040 EM_BOOL enableExtensionsByDefault;
1043 emscripten_webgl_init_context_attributes(&attribs);
1044 oglSystem.pow2textures = true;
1045 oglSystem.maxTextureSize = 16384;
1046 oglSystem.glc = emscripten_webgl_create_context("canvas", &attribs);
1047 if(emscripten_webgl_make_context_current(oglSystem.glc) == EMSCRIPTEN_RESULT_SUCCESS)
1050 /*glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
1051 glEnable(GL_BLEND);*/
1055 X11Window root = RootWindow( xGlobalDisplay, DefaultScreen( xGlobalDisplay ) );
1056 XSetWindowAttributes attr;
1061 #ifndef ECERE_MINIGLX
1062 GLX_USE_GL, GLX_DEPTH_SIZE, 1,
1065 GLX_RED_SIZE, 1, GLX_GREEN_SIZE, 1, GLX_BLUE_SIZE, 1,
1069 oglSystem.visualInfo = glXChooseVisual( xGlobalDisplay, DefaultScreen( xGlobalDisplay ), attrList );
1070 attr.background_pixel = 0;
1071 attr.border_pixel = 0;
1072 attr.colormap = XCreateColormap( xGlobalDisplay, root, oglSystem.visualInfo->visual, AllocNone);
1073 attr.event_mask = StructureNotifyMask | ExposureMask | KeyPressMask;
1074 mask = CWBackPixel | CWBorderPixel | CWColormap | CWEventMask;
1076 oglSystem.glxDrawable = XCreateWindow( xGlobalDisplay, root, 0, 0, 1, 1, 0, oglSystem.visualInfo->depth, InputOutput,
1077 oglSystem.visualInfo->visual, mask, &attr );
1079 if(oglSystem.visualInfo)
1081 oglSystem.glContext = glXCreateContext(xGlobalDisplay, oglSystem.visualInfo, null, True);
1082 if(oglSystem.glContext)
1084 glXMakeCurrent(xGlobalDisplay, oglSystem.glxDrawable, oglSystem.glContext);
1086 // CheckExtensions(oglSystem);
1087 glXMakeCurrent(xGlobalDisplay, None, null);
1094 displaySystem.flags.alpha = true;
1095 displaySystem.flags.flipping = true;
1096 displaySystem.pixelFormat = pixelFormat888;
1100 void DestroyDisplaySystem(DisplaySystem displaySystem)
1102 OGLSystem oglSystem = displaySystem.driverData;
1105 glDeleteTextures(1, &stippleTexture);
1111 #if defined(__WIN32__)
1112 wglMakeCurrent( null, null );
1115 wglDeleteContext(oglSystem.glrc);
1118 ReleaseDC(oglSystem.hwnd, oglSystem.hdc);
1119 DestroyWindow(oglSystem.hwnd);
1121 #elif defined(__unix__) || defined(__APPLE__)
1122 #if defined(__ANDROID__) || defined(__ODROID__)
1124 #elif defined(__EMSCRIPTEN__)
1125 emscripten_webgl_destroy_context(oglSystem.glc);
1127 if(oglSystem.visualInfo)
1129 #ifdef ECERE_MINIGLX
1130 __miniglx_XFree(oglSystem.visualInfo);
1132 XFree(oglSystem.visualInfo);
1136 if(oglSystem.glxDrawable)
1138 XDestroyWindow(xGlobalDisplay, oglSystem.glxDrawable);
1139 oglSystem.glxDrawable = 0;
1146 static bool ::initialDisplaySetup(Display display)
1150 loadShaders("<:ecere>shaders/fixed.vertex", "<:ecere>shaders/fixed.frag");
1152 glEnableClientState(GL_VERTEX_ARRAY);
1154 GLABBindBuffer(GL_ARRAY_BUFFER, 0);
1155 GLABBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);
1157 #if defined(__WIN32__)
1158 if(glBlendFuncSeparate)
1159 glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
1161 glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
1163 glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
1167 glMatrixMode(MatrixMode::modelView);
1168 glLoadIdentity(); // For setting up GLES stack
1169 glScaled(1.0, 1.0, -1.0);
1170 // glTranslatef(0.375f, 0.375f, 0.0f);
1171 // glTranslatef(-0.625f, -0.625f, 0.0f);
1172 glMatrixMode(MatrixMode::projection);
1173 #if !defined(EM_MODE) && !defined(SHADERS)
1174 glShadeModel(GL_FLAT);
1176 // #define GL_LIGHT_MODEL_LOCAL_VIEWER 0x0B51
1178 // glLightModeli(GL_LIGHT_MODEL_LOCAL_VIEWER, GL_TRUE);
1180 glLightModeli(GL_LIGHT_MODEL_COLOR_CONTROL, GL_SEPARATE_SPECULAR_COLOR);
1181 glFogi(GL_FOG_MODE, GL_EXP);
1182 glFogf(GL_FOG_DENSITY, 0);
1183 glEnable(GL_NORMALIZE);
1185 glDepthFunc(GL_LESS);
1187 glDisable(GL_MULTISAMPLE_ARB);
1188 #if !defined(ECERE_NO3D) && !defined(ECERE_VANILLA)
1189 display.ambient = Color { 50,50,50 };
1194 bool CreateDisplay(Display display)
1196 bool result = false;
1197 OGLDisplay oglDisplay = display.driverData;
1198 #if !defined(__ANDROID__) && !defined(__ODROID__)
1199 OGLSystem oglSystem = display.displaySystem.driverData;
1203 oglDisplay = display.driverData = OGLDisplay { };
1204 //printf("Inside CreateDisplay\n");
1206 #if defined(__WIN32__) || defined(USEPBUFFER)
1207 if(!display.alphaBlend)
1210 #if defined(__WIN32__)
1211 oglDisplay.hdc = GetDC(display.window);
1212 SetPixelFormat(oglDisplay.hdc, oglSystem.format, &oglSystem.pfd);
1213 if((oglDisplay.glrc = winCreateContext(oglDisplay.hdc)))
1215 wglShareLists(oglSystem.glrc, oglDisplay.glrc);
1216 wglMakeCurrent(oglDisplay.hdc, oglDisplay.glrc);
1220 ReleaseDC(display.window, oglDisplay.hdc);
1221 #elif defined(__unix__) || defined(__APPLE__)
1222 # if defined(__ANDROID__) || defined(__EMSCRIPTEN__) || defined(__ODROID__)
1225 XVisualInfo * visualInfo = ((XWindowData)display.windowDriverData).visual;
1227 #if defined(__APPLE__)
1228 XVisualInfo template = { 0 };
1229 XWindowAttributes winAttr;
1231 XGetWindowAttributes(xGlobalDisplay, (X11Window)display.window, &winAttr);
1232 template.visualid = XVisualIDFromVisual(winAttr.visual);
1233 visualInfo = XGetVisualInfo(xGlobalDisplay, VisualIDMask, &template, &n);
1235 printf("XGetVisualInfo visual ID = %d\n", template.visualid);
1236 printf("visualInfo visual ID = %d\n", visualInfo->visualid);
1237 printf("oglSystem.visualInfo visual ID = %d\n", oglSystem.visualInfo->visualid);
1238 printf("((XWindowData)display.windowDriverData).visual visual ID = %d\n", ((XWindowData)display.windowDriverData).visual->visualid);
1240 // visualInfo = oglSystem.visualInfo;
1245 //printf("visualInfo is not null\n");
1246 // printf("Creating Display Context, sharing with %x!\n", oglSystem.glContext);
1247 oglDisplay.glContext = glXCreateContext(xGlobalDisplay, visualInfo, oglSystem.glContext, True);
1248 //XFree(visualInfo);
1251 // oglDisplay.glContext = glXCreateContext(xGlobalDisplay, oglSystem.visualInfo, oglSystem.glContext, True);
1252 if(oglDisplay.glContext)
1254 //printf("CreateDisplay Got a Context\n");
1255 glXMakeCurrent(xGlobalDisplay, (GLXDrawable)display.window, oglDisplay.glContext);
1261 #if defined(__WIN32__) || defined(USEPBUFFER)
1265 wglMakeCurrent(oglSystem.hdc, oglSystem.glrc);
1270 #if !defined(__ANDROID__) && !defined(__EMSCRIPTEN__) && !defined(__ODROID__)
1273 PrintLn("Calling ogl_LoadFunctions() in CreateDisplay()");
1275 if(ogl_LoadFunctions() == ogl_LOAD_FAILED)
1276 PrintLn("ogl_LoadFunctions() failed!");
1279 PrintLn("CheckExtensions()");
1281 CheckExtensions(oglSystem);
1282 vboAvailable = glBindBuffer != null;
1285 PrintLn("vboAvailable is: ", vboAvailable);
1294 #if defined(__EMSCRIPTEN__)
1295 emscripten_webgl_make_context_current(oglSystem.glc);
1298 initialDisplaySetup(display);
1301 if(!useSingleGLContext)
1303 #if defined(__WIN32__)
1304 wglMakeCurrent(null, null);
1305 #elif defined(__unix__) || defined(__APPLE__)
1306 #if defined(__ANDROID__) || defined(__ODROID__) || defined(__EMSCRIPTEN__)
1309 glXMakeCurrent(xGlobalDisplay, None, null);
1315 #if defined(__ANDROID__) || defined(__EMSCRIPTEN__) || defined(__ODROID__)
1323 bool DisplaySize(Display display, int width, int height)
1325 OGLDisplay oglDisplay = display.driverData;
1327 bool result = false;
1329 //printf("Inside DisplaySize\n");
1330 #if defined(__WIN32__) || defined(USEPBUFFER)
1331 OGLSystem oglSystem = display.displaySystem.driverData;
1332 if(display.alphaBlend)
1334 #if defined(__WIN32__)
1335 const int attributes[]=
1337 /*WGL_TEXTURE_FORMAT_ARB, WGL_TEXTURE_RGBA_ARB,
1338 WGL_TEXTURE_TARGET_ARB, WGL_TEXTURE_2D_ARB, */0
1340 int pixelFormat = 0;
1341 if(wglChoosePixelFormatARB)
1345 float fAttributes[] = {0,0};
1348 //WGL_DRAW_TO_BITMAP_ARB, GL_TRUE,
1349 WGL_DRAW_TO_PBUFFER_ARB,GL_TRUE,
1350 WGL_SUPPORT_OPENGL_ARB,GL_TRUE,
1351 WGL_ACCELERATION_ARB,WGL_FULL_ACCELERATION_ARB,
1352 WGL_COLOR_BITS_ARB,24,
1353 WGL_ALPHA_BITS_ARB,8,
1354 WGL_DEPTH_BITS_ARB,16,
1355 WGL_STENCIL_BITS_ARB,0,
1356 WGL_DOUBLE_BUFFER_ARB,GL_FALSE,
1357 WGL_SAMPLE_BUFFERS_ARB,GL_TRUE,
1358 WGL_SAMPLES_ARB, 4, // Check For 4x Multisampling
1362 //Log("Found wglChoosePixelFormatARB\n");
1364 valid = wglChoosePixelFormatARB(oglSystem.hdc,iAttributes,fAttributes,1,&pixelFormat,&numFormats);
1365 if(!valid || !numFormats)
1367 //Log("Can't find 4x multi sampling\n");
1368 iAttributes[19] = 2;
1369 valid = wglChoosePixelFormatARB(oglSystem.hdc,iAttributes,fAttributes,1,&pixelFormat,&numFormats);
1370 if(!valid || !numFormats)
1372 // Log("Can't find 2x multi sampling\n");
1373 iAttributes[16] = 0;
1374 iAttributes[17] = 0;
1375 valid = wglChoosePixelFormatARB(oglSystem.hdc,iAttributes,fAttributes,1,&pixelFormat,&numFormats);
1376 if(!valid || !numFormats)
1380 WGL_DRAW_TO_PBUFFER_ARB,GL_TRUE,
1381 //WGL_DRAW_TO_BITMAP_ARB,GL_TRUE,
1382 WGL_SUPPORT_OPENGL_ARB,GL_TRUE,
1383 WGL_COLOR_BITS_ARB,24,
1384 WGL_ALPHA_BITS_ARB,8,
1385 WGL_DEPTH_BITS_ARB,16,
1388 valid = wglChoosePixelFormatARB(oglSystem.hdc,iAttributes,fAttributes,1,&pixelFormat,&numFormats);
1392 if(valid && numFormats)
1394 wglMakeCurrent(null, null);
1398 wglMakeCurrent( null, null );
1399 wglMakeCurrent( oglDisplay.hdc, oglDisplay.glrc );
1400 if(oglDisplay.hdc && oglDisplay.pBuffer)
1401 wglReleasePbufferDCARB(oglDisplay.pBuffer, oglDisplay.hdc);
1403 wglDestroyPbufferARB(oglDisplay.pBuffer);
1405 if(!useSingleGLContext)
1406 wglMakeCurrent( null, null );
1409 wglDeleteContext(oglDisplay.glrc);
1411 oglDisplay.pBuffer = wglCreatePbufferARB(oglSystem.hdc, pixelFormat, width, height, attributes);
1412 oglDisplay.hdc = wglGetPbufferDCARB(oglDisplay.pBuffer);
1413 if((oglDisplay.glrc = winCreateContext(oglDisplay.hdc)))
1416 HDC hdc = GetDC(display.window);
1418 wglShareLists(oglSystem.glrc, oglDisplay.glrc);
1419 wglMakeCurrent(oglDisplay.hdc, oglDisplay.glrc);
1421 //wglQueryPbufferARB(pBuffer, WGL_PBUFFER_WIDTH_ARB, &width);
1422 //wglQueryPbufferARB(pBuffer, WGL_PBUFFER_HEIGHT_ARB, &height);
1424 // glDeleteBuffersARB(2, oglDisplay.imageBuffers);
1426 if((info = (BITMAPINFO *)new0 byte[sizeof(BITMAPINFOHEADER)+sizeof(RGBQUAD)*256]))
1430 if(oglDisplay.memDC) DeleteDC(oglDisplay.memDC);
1431 oglDisplay.memDC = CreateCompatibleDC(hdc);
1432 SetMapMode(oglDisplay.memDC, MM_TEXT);
1433 info->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
1434 info->bmiHeader.biPlanes = 1;
1435 info->bmiHeader.biCompression = BI_RGB;
1436 info->bmiHeader.biBitCount = 32; //(uint16)GetDeviceCaps(hdc, BITSPIXEL);
1437 info->bmiHeader.biWidth = width;
1438 info->bmiHeader.biHeight = height;
1439 newBitmap = CreateDIBSection(hdc, info, DIB_RGB_COLORS, &oglDisplay.picture, null, 0);
1442 SelectObject(oglDisplay.memDC, newBitmap);
1443 if(oglDisplay.memBitmap) DeleteObject(oglDisplay.memBitmap);
1446 PIXELFORMATDESCRIPTOR pfd = { 0 };
1447 pfd.nSize = (short)sizeof(pfd);
1449 pfd.dwFlags = PFD_DRAW_TO_BITMAP | PFD_SUPPORT_OPENGL;
1450 pfd.iPixelType = PFD_TYPE_RGBA;
1451 pfd.cColorBits = 32;
1452 //pfd.cAlphaBits = 8;
1453 pfd.cDepthBits = 24;
1454 pfd.iLayerType = PFD_MAIN_PLANE;
1456 oglDisplay.hdc = oglDisplay.memDC;
1458 pixelFormat = ChoosePixelFormat(oglSystem.hdc, &pfd);
1459 DescribePixelFormat(oglDisplay.hdc, pixelFormat, sizeof(pfd), &pfd);
1460 SetPixelFormat(oglDisplay.hdc, pixelFormat, &pfd);
1462 oglDisplay.glrc = wglCreateContext(oglDisplay.hdc);
1463 wglShareLists(oglSystem.glrc, oglDisplay.glrc);
1464 wglMakeCurrent(oglDisplay.hdc, oglDisplay.glrc);
1469 const int imageSize = width * height * 4;
1471 glGenBuffersARB(2, oglDisplay.imageBuffers);
1473 glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, oglDisplay.imageBuffers[0]);
1474 glBufferDataARB(GL_PIXEL_PACK_BUFFER_ARB, imageSize, null, GL_STREAM_READ);
1475 // glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, oglDisplay.imageBuffers[1]);
1476 // glBufferDataARB(GL_PIXEL_PACK_BUFFER_ARB, imageSize / 2, null, GL_STREAM_READ);
1479 oglDisplay.memBitmap = newBitmap;
1480 oglDisplay.stride = width;
1486 ReleaseDC(display.window, hdc);
1488 #elif defined(__unix__) || defined(__APPLE__)
1489 #if defined(__ANDROID__) || defined(__ODROID__) || defined(__EMSCRIPTEN__)
1494 GLX_DOUBLEBUFFER, True,
1500 GLX_STENCIL_SIZE, 1,
1501 //GLX_DEPTH_SIZE, 24,
1502 GLX_RENDER_TYPE, GLX_RGBA_BIT,
1503 GLX_DRAWABLE_TYPE, GLX_PBUFFER_BIT | GLX_WINDOW_BIT,
1509 GLX_PBUFFER_WIDTH, width,
1510 GLX_PBUFFER_HEIGHT, height,
1511 GLX_LARGEST_PBUFFER, False,
1515 // choose a pixel format that meets our minimum requirements
1518 GLXFBConfig *config = glXChooseFBConfig(xGlobalDisplay, DefaultScreen(xGlobalDisplay), attrib, &count);
1521 if(oglDisplay.pixmap)
1523 XFreePixmap(xGlobalDisplay, oglDisplay.pixmap);
1524 oglDisplay.pixmap = None;
1526 if(oglDisplay.shapePixmap)
1528 XFreePixmap(xGlobalDisplay, oglDisplay.shapePixmap);
1529 oglDisplay.shapePixmap = None;
1532 // Free Shared Memory Pixmap
1533 if(oglDisplay.image)
1535 if(oglDisplay.shminfoShape.shmid != -1)
1537 XShmDetach(xGlobalDisplay, &oglDisplay.shminfo);
1538 if(oglDisplay.shminfo.shmaddr != (void *)-1)
1539 shmdt(oglDisplay.shminfo.shmaddr);
1540 shmctl(oglDisplay.shminfo.shmid, IPC_RMID, 0);
1542 XDestroyImage(oglDisplay.image);
1543 oglDisplay.image = None;
1545 if(oglDisplay.shapeImage)
1547 if(oglDisplay.shminfoShape.shmid != -1)
1549 XShmDetach(xGlobalDisplay, &oglDisplay.shminfoShape);
1550 if(oglDisplay.shminfoShape.shmaddr != (void *)-1)
1551 shmdt(oglDisplay.shminfoShape.shmaddr);
1552 shmctl(oglDisplay.shminfoShape.shmid, IPC_RMID, 0);
1554 XDestroyImage(oglDisplay.shapeImage);
1555 oglDisplay.shapeImage = None;
1558 if(oglDisplay.windowPicture)
1559 XRenderFreePicture(xGlobalDisplay, oglDisplay.windowPicture);
1560 if(oglDisplay.pixmapPicture)
1561 XRenderFreePicture(xGlobalDisplay, oglDisplay.pixmapPicture);
1563 if(oglDisplay.pixmap)
1564 XFreePixmap(xGlobalDisplay, oglDisplay.pixmap);
1566 if(oglDisplay.glContext)
1567 glXDestroyContext(xGlobalDisplay, oglDisplay.glContext);
1568 if(oglDisplay.pBuffer)
1569 glXDestroyPbuffer(xGlobalDisplay, oglDisplay.pBuffer);
1571 oglDisplay.pBuffer = glXCreatePbuffer(xGlobalDisplay, config[0], PBattrib);
1572 if(oglDisplay.pBuffer)
1574 oglDisplay.glContext = glXCreateNewContext(xGlobalDisplay, config[0], GLX_RGBA_TYPE, oglSystem.glContext, True);
1575 if(oglDisplay.glContext)
1577 glXMakeCurrent(xGlobalDisplay, None, null);
1578 glXMakeCurrent(xGlobalDisplay, (GLXDrawable)display.window, oglDisplay.glContext);
1580 // Initialize Shared Memory Pixmap
1581 oglDisplay.image = XShmCreateImage(xGlobalDisplay, DefaultVisual(xGlobalDisplay, DefaultScreen(xGlobalDisplay)), 32,
1582 ZPixmap, null, &oglDisplay.shminfo, width, height);
1583 if(oglDisplay.image)
1585 oglDisplay.shminfo.shmid = shmget(IPC_PRIVATE,
1586 oglDisplay.image->bytes_per_line * oglDisplay.image->height, IPC_CREAT|0777);
1587 if(oglDisplay.shminfo.shmid != -1)
1589 oglDisplay.shminfo.shmaddr = shmat(oglDisplay.shminfo.shmid, 0, 0);
1590 if(oglDisplay.shminfo.shmaddr != (void *)-1)
1592 oglDisplay.shminfo.readOnly = False;
1593 if(XShmAttach(xGlobalDisplay, &oglDisplay.shminfo))
1595 oglDisplay.pixmap = XShmCreatePixmap(xGlobalDisplay, (X11Window)display.window, oglDisplay.shminfo.shmaddr,
1596 &oglDisplay.shminfo, width, height, 32);
1598 // Initialize Shared Memory Shape Pixmap
1599 oglDisplay.shapeImage = XShmCreateImage(xGlobalDisplay, DefaultVisual(xGlobalDisplay, DefaultScreen(xGlobalDisplay)), 1,
1600 ZPixmap, null, &oglDisplay.shminfoShape, width, height);
1601 if(oglDisplay.shapeImage)
1603 oglDisplay.shminfoShape.shmid = shmget(IPC_PRIVATE,
1604 oglDisplay.shapeImage->bytes_per_line * oglDisplay.shapeImage->height, IPC_CREAT|0777);
1605 if(oglDisplay.shminfoShape.shmid != -1)
1607 oglDisplay.shminfoShape.shmaddr = shmat(oglDisplay.shminfoShape.shmid, 0, 0);
1608 if(oglDisplay.shminfoShape.shmaddr != (void *)-1)
1610 oglDisplay.shminfoShape.readOnly = False;
1611 if(XShmAttach(xGlobalDisplay, &oglDisplay.shminfoShape))
1613 oglDisplay.shapePixmap = XShmCreatePixmap(xGlobalDisplay, (X11Window)display.window, oglDisplay.shminfoShape.shmaddr,
1614 &oglDisplay.shminfoShape, width, height, 1);
1615 //oglDisplay.shapePixmap = XCreatePixmap(xGlobalDisplay, (X11Window)display.window, width, height, 1);
1618 XRenderPictureAttributes attributes = { 0 };
1619 XRenderPictFormat * format = XRenderFindStandardFormat(xGlobalDisplay, /*PictStandardRGB24*/ PictStandardARGB32);
1620 #if !defined(__APPLE__)
1621 attributes.repeat = RepeatNormal;
1623 attributes.repeat = 1;
1625 oglDisplay.pixmapPicture = XRenderCreatePicture(xGlobalDisplay, oglDisplay.pixmap, format, CPRepeat, &attributes);
1626 oglDisplay.windowPicture = XRenderCreatePicture(xGlobalDisplay, (X11Window)display.window, format, 0, &attributes);
1627 oglDisplay.shapePicture = XRenderCreatePicture(xGlobalDisplay, oglDisplay.shapePixmap,
1628 XRenderFindStandardFormat(xGlobalDisplay, PictStandardA1), 0, &attributes);
1631 oglDisplay.picture = oglDisplay.shminfo.shmaddr;
1632 oglDisplay.stride = oglDisplay.image->bytes_per_line / 4;
1649 CreateDisplay(display);
1650 #if defined(__WIN32__)
1651 wglMakeCurrent(oglDisplay.hdc, oglDisplay.glrc);
1652 #elif defined(__unix__) || defined(__APPLE__)
1653 #if defined(__ANDROID__) || defined(__ODROID__)
1656 #elif defined(__EMSCRIPTEN__)
1657 emscripten_webgl_make_context_current(oglSystem.glc);
1659 glXMakeCurrent(xGlobalDisplay, (GLXDrawable)display.window, oglDisplay.glContext);
1667 if(display.alphaBlend && result)
1668 initialDisplaySetup(display);
1670 if(!result && display.alphaBlend)
1672 printf("Alpha blending windows not supported on this display\n");
1679 glViewport(0,0,width,height);
1680 glMatrixMode(MatrixMode::projection);
1682 glOrtho(0,width,height,0,0.0,1.0);
1683 displayWidth = display.width = width;
1684 displayHeight = display.height = height;
1686 if(!oglDisplay.flippingBuffer || oglDisplay.flipBufW < width || oglDisplay.flipBufH < height)
1688 oglDisplay.flipBufW = width;
1689 oglDisplay.flipBufH = height;
1690 #if defined(ES1_1) || defined(ES2)
1693 oglDisplay.flippingBuffer = renew oglDisplay.flippingBuffer ColorAlpha [width * height];
1696 if(oglDisplay.flippingBuffer || !width || !height)
1702 void DisplayPosition(Display display, int x, int y)
1704 OGLDisplay oglDisplay = display.driverData;
1710 void SetPalette(Display display, ColorAlpha * palette, bool colorMatch)
1714 void RestorePalette(Display display)
1718 void StartUpdate(Display display)
1722 void EndUpdate(Display display)
1726 void Scroll(Display display, Box scroll, int x, int y, Extent dirty)
1730 void Update(Display display, Box updateBox)
1732 #if defined(__WIN32__) || defined(USEPBUFFER)
1733 OGLDisplay oglDisplay = display.driverData;
1735 //Logf("DisplayScreen\n");
1737 #if !defined(__ANDROID__)
1742 #if defined(__WIN32__) || defined(USEPBUFFER)
1743 if(display.alphaBlend)
1745 glPixelStorei(GL_PACK_ALIGNMENT, 4);
1746 glPixelStorei(GL_PACK_ROW_LENGTH, oglDisplay.stride);
1747 glPixelStorei(GL_PACK_SKIP_ROWS, 0);
1748 glPixelStorei(GL_PACK_SKIP_PIXELS, 0);
1749 glReadPixels(0,0,display.width,display.height,GL_BGRA_EXT,GL_UNSIGNED_BYTE, oglDisplay.picture);
1752 #if defined(__WIN32__)
1754 POINT point = { oglDisplay.x, oglDisplay.y};
1755 POINT srcPoint = { 0, 0 };
1756 BLENDFUNCTION blend = { 0 };
1758 size.cx = display.width;
1759 size.cy = display.height;
1760 blend.BlendOp = AC_SRC_OVER;
1761 blend.BlendFlags = 0;
1762 blend.SourceConstantAlpha = 255;
1763 blend.AlphaFormat = AC_SRC_ALPHA;
1766 // Process partial images. Mapping the buffer waits for
1767 // outstanding DMA transfers into the buffer to finish.
1768 glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, oglDisplay.imageBuffers[0]);
1769 oglDisplay.pboMemory1 = (byte *)glMapBufferARB(GL_PIXEL_PACK_BUFFER_ARB, GL_READ_ONLY);
1771 // glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, oglDisplay.imageBuffers[1]);
1772 // oglDisplay.pboMemory2 = (byte *)glMapBufferARB(GL_PIXEL_PACK_BUFFER_ARB,GL_READ_ONLY);
1775 memcpy(oglDisplay.picture, oglDisplay.pboMemory1, display.width * display.height * 4);
1776 //memcpy(oglDisplay.picture + display.width * display.height * 4 / 2, oglDisplay.pboMemory2, display.width * display.height * 4/ 2);
1779 UpdateLayeredWindow(display.window, hdc, &point, &size, oglDisplay.memDC, &srcPoint, 0, &blend, ULW_ALPHA);
1782 // Unmap the image buffers
1783 glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, oglDisplay.imageBuffers[0]);
1784 glUnmapBufferARB(GL_PIXEL_PACK_BUFFER_ARB);
1786 // glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, oglDisplay.imageBuffers[1]);
1787 // glUnmapBufferARB(GL_PIXEL_PACK_BUFFER_ARB);
1789 // Bind two different buffer objects and start the glReadPixels
1790 // asynchronously. Each call will return directly after
1791 // starting the DMA transfer.
1792 glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, oglDisplay.imageBuffers[0]);
1793 glReadPixels(0, 0, display.width, display.height, GL_BGRA, GL_UNSIGNED_BYTE, 0);
1795 // glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, oglDisplay.imageBuffers[1]);
1796 // glReadPixels(0, display.height/2, display.width, display.height/2, GL_BGRA, GL_UNSIGNED_BYTE, 0);
1800 #elif defined(__unix__) || defined(__APPLE__)
1801 #if defined(__ANDROID__) || defined(__ODROID__) || defined(__EMSCRIPTEN__)
1803 XTransform transform =
1806 { (int)(1.0f * (1<<16)), (int)(0.0f * (1<<16)), (int)(0 * (1 << 16)) },
1807 { (int)(0.0f), (int)(-1.0f * (1<<16)), (int)(0 * (1<<16)) },
1808 { (int)(0.0f * (1<<16)), (int)(0.0f * (1<<16)), (int)(1.0f * (1<<16)) }
1811 XRenderSetPictureTransform(xGlobalDisplay, oglDisplay.pixmapPicture, &transform);
1812 XRenderComposite(xGlobalDisplay, PictOpSrc, oglDisplay.pixmapPicture, None, oglDisplay.shapePicture, 0, 0, 0, 0, 0, 0, display.width, display.height);
1813 XRenderComposite(xGlobalDisplay, PictOpSrc, oglDisplay.pixmapPicture, None, oglDisplay.windowPicture, 0, 0, 0, 0, 0, 0, display.width, display.height);
1814 #if !defined(__APPLE__)
1815 XShapeCombineMask(xGlobalDisplay, (X11Window)display.window, ShapeInput, 0, 0, oglDisplay.shapePixmap, ShapeSet);
1817 XShapeCombineMask(xGlobalDisplay, display.window, 2, 0, 0, oglDisplay.shapePixmap, ShapeSet);
1819 XFlush(xGlobalDisplay);
1827 #if defined(__WIN32__)
1828 //wglSwapLayerBuffers(oglDisplay.hdc,WGL_SWAP_MAIN_PLANE);
1829 SwapBuffers(oglDisplay.hdc);
1830 //ecere::sys::Sleep(0.1);
1831 #elif defined(__unix__) || defined(__APPLE__)
1832 #if defined(__ANDROID__) || defined(__ODROID__)
1834 #elif defined(__EMSCRIPTEN__)
1836 glXSwapBuffers(xGlobalDisplay, (GLXDrawable)display.window);
1840 //Logf("Out of DisplayScreen\n");
1843 void FreeBitmap(DisplaySystem displaySystem, Bitmap bitmap)
1845 if(bitmap.driverData)
1847 GLuint tex = (GLuint)(uintptr)bitmap.driverData;
1848 glDeleteTextures(1, &tex);
1849 bitmap.driverData = 0;
1851 bitmap.driver = ((subclass(DisplayDriver))class(LFBDisplayDriver));
1854 bool AllocateBitmap(DisplaySystem displaySystem, Bitmap bitmap, int width, int height, int stride, PixelFormat format, bool allocatePalette)
1856 OGLSystem oglSystem = displaySystem.driverData;
1857 bool result = false;
1859 GLuint glBitmap = 0;
1861 uint w = width, h = height;
1862 if(oglSystem.pow2textures)
1867 w = Min(w, oglSystem.maxTextureSize);
1868 h = Min(h, oglSystem.maxTextureSize);
1870 glGenTextures(1, &glBitmap);
1871 glBindTexture(GL_TEXTURE_2D, glBitmap);
1873 glPixelStorei( GL_UNPACK_ALIGNMENT, 1 );
1875 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
1876 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
1878 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
1879 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
1881 #if !defined(SHADERS)
1882 glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);
1885 mipMap.Allocate(null, w, h, w, pixelFormatRGBA, false);
1887 // glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, w, h, 0, GL_RGBA, GL_UNSIGNED_BYTE, mipMap.picture);
1888 glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, w, h, 0, GL_RGBA, GL_UNSIGNED_BYTE, mipMap.picture);
1892 bitmap.driverData = (void *)(uintptr)glBitmap;
1893 bitmap.driver = displaySystem.driver;
1901 bool MakeDDBitmap(DisplaySystem displaySystem, Bitmap bitmap, bool mipMaps)
1903 bool result = false;
1904 OGLSystem oglSystem = displaySystem.driverData;
1905 Bitmap convBitmap = bitmap;
1909 convBitmap.Copy(bitmap);
1912 // Pre process the bitmap... First make it 32 bit
1913 if(/*bitmap.pixelFormat == pixelFormatRGBA || */convBitmap.Convert(null, pixelFormat888, null))
1916 uint w = bitmap.width, h = bitmap.height;
1917 GLuint glBitmap = 0;
1918 if(oglSystem.pow2textures)
1923 w = Min(w, oglSystem.maxTextureSize);
1924 h = Min(h, oglSystem.maxTextureSize);
1928 while(w * 2 < h) w *= 2;
1929 while(h * 2 < w) h *= 2;
1932 // Switch ARGB to RGBA
1933 //if(bitmap.format != pixelFormatRGBA)
1935 for(c=0; c<bitmap.size; c++)
1937 // ((ColorRGBA *)bitmap.picture)[c] = ((ColorAlpha *)bitmap.picture)[c];
1939 ColorAlpha color = ((ColorAlpha *)convBitmap.picture)[c];
1940 ((ColorRGBA *)convBitmap.picture)[c] = ColorRGBA { color.color.r, color.color.g, color.color.b, color.a };
1943 // convBitmap.pixelFormat = pixelFormat888;
1946 glGenTextures(1, &glBitmap);
1949 //int error = glGetError();
1953 glBindTexture(GL_TEXTURE_2D, glBitmap);
1954 glPixelStorei( GL_UNPACK_ALIGNMENT, 1 );
1956 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, mipMaps ? GL_LINEAR_MIPMAP_LINEAR : GL_LINEAR);
1957 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
1959 //glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
1961 //glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
1962 //glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
1964 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
1965 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
1966 #ifdef GL_TEXTURE_MAX_ANISOTROPY_EXT
1967 glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAX_ANISOTROPY_EXT, 16.0 );
1970 #if !defined(SHADERS)
1971 glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);
1976 for(level = 0; result && (w >= 1 || h >= 1); level++, w >>= 1, h >>= 1)
1981 if(bitmap.width != w || bitmap.height != h)
1983 mipMap = Bitmap { };
1984 if(mipMap.Allocate(null, w, h, w, convBitmap.pixelFormat, false))
1986 Surface mipSurface = mipMap.GetSurface(0,0,null);
1987 mipSurface.Filter(convBitmap, 0,0,0,0, w, h, convBitmap.width, convBitmap.height);
1997 mipMap = convBitmap;
2004 // glTexImage2D(GL_TEXTURE_2D, level, GL_RGBA8, w, h, 0, GL_RGBA, GL_UNSIGNED_BYTE, mipMap.picture);
2005 glTexImage2D(GL_TEXTURE_2D, level, GL_RGBA, w, h, 0, GL_RGBA, GL_UNSIGNED_BYTE, mipMap.picture);
2006 //printf("Calling glTexImage2D\n");
2007 //glGetTexLevelParameteriv(GL_TEXTURE_2D, level, GL_TEXTURE_WIDTH, &width);
2008 //printf("width = %d (Should be %d, %d)\n", width, w, h);
2009 if((error = glGetError()))
2011 //Logf("OpenGL Bitmap MakeDD error: %d...\n", error);
2012 //printf("OpenGL Bitmap MakeDD error: %d...\n", error);
2016 if(mipMap != convBitmap)
2021 convBitmap.driver.FreeBitmap(convBitmap.displaySystem, convBitmap);
2022 bitmap.driverData = (void *)(uintptr)glBitmap;
2023 bitmap.driver = displaySystem.driver;
2028 FreeBitmap(displaySystem, bitmap);
2029 else if(oglSystem.loadingFont)
2031 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
2032 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
2033 oglSystem.loadingFont = false;
2039 void ReleaseSurface(Display display, Surface surface)
2041 glDisable(GL_SCISSOR_TEST);
2042 delete surface.driverData;
2043 surface.driverData = null;
2046 bool GetBitmapSurface(DisplaySystem displaySystem, Surface surface, Bitmap bitmap, int x, int y, Box clip)
2051 bool GetSurface(Display display, Surface surface, int x,int y, Box clip)
2053 bool result = false;
2054 OGLSurface oglSurface = surface.driverData = OGLSurface { };
2056 //Logf("GetSurface\n");
2060 if(displayWidth != display.width || displayHeight != display.height)
2062 displayWidth = display.width;
2063 displayHeight = display.height;
2065 glViewport(0,0,display.width,display.height);
2067 glOrtho(0,display.width,display.height,0,0.0,1.0);
2070 surface.offset.x = x;
2071 surface.offset.y = y;
2072 surface.unclippedBox = surface.box = clip;
2073 oglSurface.bitmapMult[0] = 1;
2074 oglSurface.bitmapMult[1] = 1;
2075 oglSurface.bitmapMult[2] = 1;
2076 oglSurface.bitmapMult[3] = 1;
2078 glEnable(GL_SCISSOR_TEST);
2081 (display.height) -(y+clip.bottom)-1,
2082 clip.right-clip.left+1,
2083 clip.bottom-clip.top+1);
2089 void Clip(Display display, Surface surface, Box clip)
2098 box.Clip(surface.unclippedBox);
2102 box = surface.box = surface.unclippedBox;
2103 box.left += surface.offset.x;
2104 box.top += surface.offset.y;
2105 box.right+= surface.offset.x;
2106 box.bottom += surface.offset.y;
2109 box.left,display.height - box.bottom - 1,
2110 box.right-box.left+1, box.bottom-box.top+1);
2113 bool GrabScreen(Display display, Bitmap bitmap, int x, int y, unsigned int w, unsigned int h)
2115 bool result = false;
2116 OGLDisplay oglDisplay = display.driverData;
2117 ColorAlpha * flippingBuffer = oglDisplay.flippingBuffer;
2119 if(oglDisplay.flippingBuffer)
2121 if(bitmap.pixelFormat != pixelFormat888 || bitmap.width < w || bitmap.height < h)
2124 bitmap.Allocate(null, w,h,w, pixelFormat888, false);
2130 glPixelStorei(GL_PACK_ALIGNMENT, 4);
2131 glPixelStorei(GL_PACK_ROW_LENGTH, bitmap.stride);
2132 glPixelStorei(GL_PACK_SKIP_ROWS, 0);
2133 glPixelStorei(GL_PACK_SKIP_PIXELS, 0);
2134 glReadPixels(x,display.height-h-y,w,h,GL_BGRA_EXT,GL_UNSIGNED_BYTE, flippingBuffer);
2137 for(row = 0; row<h; row++)
2138 CopyBytesBy4(((ColorAlpha *)bitmap.picture) + row * w, ((ColorAlpha *)flippingBuffer) + (h-row-1) * w, w);
2145 void SetForeground(Display display, Surface surface, ColorAlpha color)
2147 OGLSurface oglSurface = surface.driverData;
2149 //Logf("SetForeground\n");
2151 oglSurface.foreground[0] = color.color.r/255.0f;
2152 oglSurface.foreground[1] = color.color.g/255.0f;
2153 oglSurface.foreground[2] = color.color.b/255.0f;
2154 //oglSurface.foreground[3] = 1.0f;
2155 oglSurface.foreground[3] = color.a/255.0f;
2157 //if(!oglSurface.foreground[3])printf("bug");
2160 void SetBackground(Display display, Surface surface, ColorAlpha color)
2162 OGLSurface oglSurface = surface.driverData;
2164 //Logf("SetBackground\n");
2166 oglSurface.background[0] = color.color.r/255.0f;
2167 oglSurface.background[1] = color.color.g/255.0f;
2168 oglSurface.background[2] = color.color.b/255.0f;
2169 //oglSurface.background[3] = 1.0;
2170 oglSurface.background[3] = color.a/255.0f;
2173 void SetBlitTint(Display display, Surface surface, ColorAlpha color)
2175 OGLSurface oglSurface = surface.driverData;
2177 oglSurface.bitmapMult[0] = color.color.r/255.0f;
2178 oglSurface.bitmapMult[1] = color.color.g/255.0f;
2179 oglSurface.bitmapMult[2] = color.color.b/255.0f;
2180 oglSurface.bitmapMult[3] = color.a/255.0f;
2183 ColorAlpha GetPixel(Display display, Surface surface,int x,int y)
2188 void PutPixel(Display display, Surface surface,int x,int y)
2190 OGLSurface oglSurface = surface.driverData;
2192 //Logf("PutPixel\n");
2194 glColor4fv(oglSurface.foreground);
2196 // glVertex2i(x+surface.offset.x, y+surface.offset.y);
2197 glVertex2f(x+surface.offset.x + 0.5f, y+surface.offset.y + 0.5f);
2202 void DrawLine(Display display, Surface surface, int _x1, int _y1, int _x2, int _y2)
2204 OGLSurface oglSurface = surface.driverData;
2205 float x1 = _x1, x2 = _x2, y1 = _y1, y2 = _y2;
2220 x1 += surface.offset.x;
2221 y1 += surface.offset.y;
2222 x2 += surface.offset.x;
2223 y2 += surface.offset.y;
2227 glColor4fv(oglSurface.foreground);
2229 #if defined(ES1_1) || defined(ES2) || defined(SHADERS)
2232 glTexCoord2f(0.5f, 0);
2233 glVertex2f(x1 + 0.5f, y1 + 0.5f);
2234 glTexCoord2f(Max(x2-x1, y2-y1) + 0.5f, 0);
2235 glVertex2f(x2 + 0.5f, y2 + 0.5f);
2244 glVertex2f(x1 + 0.5f, y1 + 0.5f);
2245 glVertex2f(x2 + 0.5f, y2 + 0.5f);
2251 void Rectangle(Display display, Surface surface,int x1,int y1,int x2,int y2)
2253 OGLSurface oglSurface = surface.driverData;
2254 x1 += surface.offset.x;
2255 y1 += surface.offset.y;
2256 x2 += surface.offset.x;
2257 y2 += surface.offset.y;
2259 //Logf("Rectangle\n");
2261 glColor4fv(oglSurface.foreground);
2262 #if defined(ES1_1) || defined(ES2) || defined(SHADERS)
2267 glTexCoord2f(0.5f, 0);
2268 glVertex2f(x1 + 0.5f, y1 + 0.5f);
2269 glTexCoord2f(y2-y1 + 0.5f, 0);
2270 glVertex2f(x1 + 0.5f, y2 + 0.5f);
2272 glTexCoord2f(0.5f, 0);
2273 glVertex2f(x1 + 0.5f, y2 + 0.5f);
2274 glTexCoord2f(x2 - x1 + 0.5f, 0);
2275 glVertex2f(x2 + 0.5f, y2 + 0.5f);
2277 glTexCoord2f(0.5f, 0);
2278 glVertex2f(x2 + 0.5f, y2 + 0.5f);
2279 glTexCoord2f(y1 - y2 + 0.5f, 0);
2280 glVertex2f(x2 + 0.5f, y1 + 0.5f);
2282 glTexCoord2f(0.5f, 0);
2283 glVertex2f(x2 + 0.5f, y1 + 0.5f);
2284 glTexCoord2f(x1 - x2 + 0.5f, 0);
2285 glVertex2f(x1 + 0.5f, y1 + 0.5f);
2290 glBegin(GL_LINE_LOOP);
2297 glVertex2f(x1 + 0.5f, y1 + 0.5f);
2298 glVertex2f(x1 + 0.5f, y2 + 0.5f);
2299 glVertex2f(x2 + 0.5f, y2 + 0.5f);
2300 glVertex2f(x2 + 0.5f, y1 + 0.5f);
2305 void Area(Display display, Surface surface,int x1,int y1,int x2,int y2)
2307 OGLSurface oglSurface = surface.driverData;
2310 glColor4fv(oglSurface.background);
2312 glRecti(x1+surface.offset.x, y1+surface.offset.y,
2313 x2+surface.offset.x + 1, y2+surface.offset.y + 1);
2315 glRectf(x1+surface.offset.x, y1+surface.offset.y,
2316 x2+surface.offset.x + 1, y2+surface.offset.y + 1);
2320 void Clear(Display display, Surface surface, ClearType type)
2322 OGLDisplay oglDisplay = display.driverData;
2323 OGLSurface oglSurface = surface.driverData;
2326 if(type != depthBuffer)
2327 glClearColor(oglSurface.background[0], oglSurface.background[1], oglSurface.background[2], oglSurface.background[3]);
2328 if(type != colorBuffer && !oglDisplay.depthWrite)
2330 glDepthMask((byte)bool::true);
2332 glClear(((type != depthBuffer) ? GL_COLOR_BUFFER_BIT : 0) |
2333 ((type != colorBuffer) ? GL_DEPTH_BUFFER_BIT : 0));
2334 if(type != colorBuffer && !oglDisplay.depthWrite)
2336 glDepthMask((byte)bool::false);
2340 bool ConvertBitmap(DisplaySystem displaySystem, Bitmap bitmap, PixelFormat format, ColorAlpha * palette)
2345 void Blit(Display display, Surface surface, Bitmap bitmap, int dx, int dy, int sx, int sy, int w, int h)
2347 OGLSurface oglSurface = surface.driverData;
2349 if(!oglSurface.writingText)
2351 // glTranslatef(-0.375f, -0.375f, 0.0f);
2352 GLSetupTexturing(true);
2353 glColor4fv(oglSurface.bitmapMult);
2355 else if(oglSurface.xOffset)
2356 glTranslated(oglSurface.xOffset / 64.0/*-0.375*/, 0.0, 0.0);
2358 glBindTexture(GL_TEXTURE_2D, (GLuint)(uintptr)bitmap.driverData);
2359 glBegin(GLIMTKMode::quads);
2363 glTexCoord2f((float)sx/ bitmap.width, (float)(sy-h)/ bitmap.height);
2364 glVertex2i(dx+surface.offset.x, dy+surface.offset.y);
2365 glTexCoord2f((float)(sx+w) / bitmap.width, (float)(sy-h)/ bitmap.height);
2366 glVertex2i(dx+w+surface.offset.x, dy+surface.offset.y);
2367 glTexCoord2f((float)(sx+w)/ bitmap.width, (float)sy/ bitmap.height);
2368 glVertex2i(dx+w+surface.offset.x, dy-h+surface.offset.y);
2369 glTexCoord2f((float)sx / bitmap.width, (float)sy/ bitmap.height);
2370 glVertex2i(dx+surface.offset.x, dy-h+surface.offset.y);
2375 glTexCoord2f((float)sx / bitmap.width, (float)sy/ bitmap.height);
2376 glVertex2i(dx+surface.offset.x, dy+surface.offset.y);
2377 glTexCoord2f((float)(sx+w)/ bitmap.width, (float)sy/ bitmap.height);
2378 glVertex2i(dx+w+surface.offset.x, dy+surface.offset.y);
2379 glTexCoord2f((float)(sx+w) / bitmap.width, (float)(sy+h)/ bitmap.height);
2380 glVertex2i(dx+w+surface.offset.x, dy+h+surface.offset.y);
2381 glTexCoord2f((float)sx/ bitmap.width, (float)(sy+h)/ bitmap.height);
2382 glVertex2i(dx+surface.offset.x, dy+h+surface.offset.y);
2385 glTexCoord2f((float)sx / bitmap.width, (float)sy/ bitmap.height);
2386 glVertex2f((float)dx+surface.offset.x, (float)dy+surface.offset.y);
2387 glTexCoord2f((float)(sx+w)/ bitmap.width, (float)sy/ bitmap.height);
2388 glVertex2f((float)dx+w+surface.offset.x, (float)dy+surface.offset.y);
2389 glTexCoord2f((float)(sx+w) / bitmap.width, (float)(sy+h)/ bitmap.height);
2390 glVertex2f((float)dx+w+surface.offset.x, (float)dy+h+surface.offset.y);
2391 glTexCoord2f((float)sx/ bitmap.width, (float)(sy+h)/ bitmap.height);
2392 glVertex2f((float)dx+surface.offset.x, (float)dy+h+surface.offset.y);
2396 if(!oglSurface.writingText)
2398 GLSetupTexturing(false);
2400 //glTranslate(0.375, 0.375, 0.0);
2402 else if(oglSurface.xOffset)
2403 glTranslated(-oglSurface.xOffset / 64.0/*+0.375*/, 0.0, 0.0);
2406 void Stretch(Display display, Surface surface, Bitmap bitmap, int dx, int dy, int sx, int sy, int w, int h, int sw, int sh)
2408 OGLSurface oglSurface = surface.driverData;
2410 //glTranslate(-0.375, -0.375, 0.0);
2412 GLSetupTexturing(true);
2413 glBindTexture(GL_TEXTURE_2D, (GLuint)(uintptr)bitmap.driverData);
2415 glColor4fv(oglSurface.bitmapMult);
2417 glBegin(GLIMTKMode::quads);
2421 glTexCoord2f((float)(sx)/ bitmap.width, (float)(sy+sh)/ bitmap.height);
2422 glVertex2i(dx+surface.offset.x, dy+surface.offset.y);
2424 glTexCoord2f((float)(sx+sw) / bitmap.width, (float)(sy+sh)/ bitmap.height);
2425 glVertex2i(dx+w+surface.offset.x, dy+surface.offset.y);
2427 glTexCoord2f((float)(sx+sw)/ bitmap.width, (float)(sy)/ bitmap.height);
2428 glVertex2i(dx+w+surface.offset.x, dy-h+surface.offset.y);
2430 glTexCoord2f((float)(sx) / bitmap.width, (float)(sy)/ bitmap.height);
2431 glVertex2i(dx+surface.offset.x, dy-h+surface.offset.y);
2435 glTexCoord2f((float)(sx) / bitmap.width, (float)(sy)/ bitmap.height);
2436 glVertex2i(dx+surface.offset.x, dy+surface.offset.y);
2438 glTexCoord2f((float)(sx+sw)/ bitmap.width, (float)(sy)/ bitmap.height);
2439 glVertex2i(dx+w+surface.offset.x, dy+surface.offset.y);
2441 glTexCoord2f((float)(sx+sw) / bitmap.width, (float)(sy+sh)/ bitmap.height);
2442 glVertex2i(dx+w+surface.offset.x, dy+h+surface.offset.y);
2444 glTexCoord2f((float)(sx)/ bitmap.width, (float)(sy+sh)/ bitmap.height);
2445 glVertex2i(dx+surface.offset.x, dy+h+surface.offset.y);
2450 GLSetupTexturing(false);
2452 //glTranslate(0.375, 0.375, 0.0);
2455 void Filter(Display display, Surface surface, Bitmap bitmap, int dx, int dy, int sx, int sy, int w, int h, int sw, int sh)
2457 Stretch(display, surface, bitmap, dx, dy, sx, sy, w, h, sw, sh);
2460 void StretchDI(Display display, Surface surface, Bitmap bitmap, int dx, int dy, int sx, int sy, int w, int h, int sw, int sh)
2462 float s2dw,s2dh,d2sw,d2sh;
2463 //bool flipX = false, flipY = false;
2465 //Logf("StretchDI\n");
2467 if(Sgn(w) != Sgn(sw))
2473 if(Sgn(h) != Sgn(sh))
2485 //Clip against the edges of the source
2488 dx+=(int)((0-sx) * s2dw);
2489 w-=(int)((0-sx) * s2dw);
2495 dy+=(int)((0-sy) * s2dh);
2496 h-=(int)((0-sy) * s2dh);
2501 if(sx+sw>bitmap.width-1)
2503 w-=(int)((sx+sw-(bitmap.width-1)-1)*s2dw);
2504 sw-=sx+sw-(bitmap.width-1)-1;
2506 if(sy+sh>(bitmap.height-1))
2508 h-=(int)((sy+sh-(bitmap.height-1)-1)*s2dh);
2509 sh-=sy+sh-(bitmap.height-1)-1;
2511 //Clip against the edges of the surfaceination
2512 if(dx<surface.box.left)
2515 sx+=(int)((surface.box.left-dx)*d2sw);
2516 sw-=(int)((surface.box.left-dx)*d2sw);
2517 w-=surface.box.left-dx;
2518 dx=surface.box.left;
2520 if(dy<surface.box.top)
2522 sy+=(int)((surface.box.top-dy)*d2sh);
2523 sh-=(int)((surface.box.top-dy)*d2sh);
2524 h-=surface.box.top-dy;
2527 if(dx+w>surface.box.right)
2529 //if(flip) sx+=(int)((dx+w-surface.box.right-1)*d2sw);
2530 sw-=(int)((dx+w-surface.box.right-1)*d2sw);
2531 w-=dx+w-surface.box.right-1;
2533 if(dy+h>surface.box.bottom)
2535 sh-=(int)((dy+h-surface.box.bottom-1)*d2sh);
2536 h-=dy+h-surface.box.bottom-1;
2538 if((w<=0)||(h<=0)||(sw<=0)||(sh<=0)) return;
2540 dx += surface.offset.x;
2541 dy += surface.offset.y;
2543 if(bitmap.pixelFormat == pixelFormat888 && !bitmap.paletteShades)
2545 glPixelStorei(GL_UNPACK_ALIGNMENT, 4);
2546 glPixelStorei(GL_UNPACK_ROW_LENGTH, bitmap.stride);
2547 glPixelStorei(GL_UNPACK_SKIP_PIXELS, sx);
2548 glPixelStorei(GL_UNPACK_SKIP_ROWS, sy);
2549 #if !defined(SHADERS)
2550 glRasterPos2d(dx,dy);
2551 //glPixelZoom(flipX ? -s2dw : s2dw, flipY ? s2dh : -s2dh);
2552 glPixelZoom(s2dw, -s2dh);
2553 glDrawPixels(sw,sh,GL_BGRA_EXT,GL_UNSIGNED_BYTE, bitmap.picture);
2555 glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
2556 glPixelStorei(GL_UNPACK_ROW_LENGTH, 0);
2557 glPixelStorei(GL_UNPACK_SKIP_PIXELS, 0);
2558 glPixelStorei(GL_UNPACK_SKIP_ROWS, 0);
2562 void BlitDI(Display display, Surface surface, Bitmap bitmap, int dx, int dy, int sx, int sy, int w, int h)
2566 //Clip against the edges of the source
2579 if(sx+w>bitmap.width-1)
2580 w-=sx+w-(bitmap.width-1)-1;
2581 if(sy+h>bitmap.height-1)
2582 h-=sy+h-(bitmap.height-1)-1;
2583 //Clip against the edges of the surfaceination
2584 if(dx<surface.box.left)
2587 sx+=surface.box.left-dx;
2588 w-=surface.box.left-dx;
2589 dx=surface.box.left;
2591 if(dy<surface.box.top)
2593 sy+=surface.box.top-dy;
2594 h-=surface.box.top-dy;
2597 if(dx+w>surface.box.right)
2599 //if(flip) sx+=dx+w-surface.box.right-1;
2600 w-=dx+w-surface.box.right-1;
2602 if(dy+h>surface.box.bottom)
2603 h-=dy+h-surface.box.bottom-1;
2607 dx += surface.offset.x;
2608 dy += surface.offset.y;
2610 if(bitmap.pixelFormat == pixelFormat888 && !bitmap.paletteShades)
2612 glPixelStorei(GL_UNPACK_ALIGNMENT, 4);
2613 glPixelStorei(GL_UNPACK_ROW_LENGTH, bitmap.stride);
2614 glPixelStorei(GL_UNPACK_SKIP_PIXELS, sx);
2615 glPixelStorei(GL_UNPACK_SKIP_ROWS, sy);
2616 #if !defined(SHADERS)
2617 glRasterPos2d(dx,dy);
2619 glDrawPixels(w,h,GL_BGRA_EXT,GL_UNSIGNED_BYTE, bitmap.picture);
2621 glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
2622 glPixelStorei(GL_UNPACK_ROW_LENGTH, 0);
2623 glPixelStorei(GL_UNPACK_SKIP_PIXELS, 0);
2624 glPixelStorei(GL_UNPACK_SKIP_ROWS, 0);
2628 void FilterDI(Display display, Surface surface, Bitmap bitmap, int dx, int dy, int sx, int sy, int w, int h, int sw, int sh)
2630 StretchDI(display, surface, bitmap, dx, dy, sx, sy, w, h, sw, sh);
2633 void UnloadFont(DisplaySystem displaySystem, Font font)
2635 ((subclass(DisplayDriver))class(LFBDisplayDriver)).UnloadFont(displaySystem, font);
2638 Font LoadFont(DisplaySystem displaySystem, const char * faceName, float size, FontFlags flags, float outlineSize, float outlineFade)
2641 OGLSystem oglSystem = displaySystem.driverData;
2642 oglSystem.loadingFont = true;
2643 font = ((subclass(DisplayDriver))class(LFBDisplayDriver)).LoadFont(displaySystem, faceName, size, flags, outlineSize, outlineFade);
2647 void FontExtent(DisplaySystem displaySystem, Font font, const char * text, int len, int * width, int * height, int prevGlyph, int * rPrevGlyph, int * adv)
2649 ((subclass(DisplayDriver))class(LFBDisplayDriver)).FontExtent(displaySystem, font, text, len, width, height, prevGlyph, rPrevGlyph, adv);
2652 void WriteText(Display display, Surface surface, int x, int y, const char * text, int len, int prevGlyph, int * rPrevGlyph)
2654 OGLSurface oglSurface = surface.driverData;
2655 OGLSystem oglSystem = display.displaySystem.driverData;
2656 oglSystem.loadingFont = true;
2658 //glTranslated(-0.375, -0.375, 0.0);
2662 if(surface.textOpacity)
2665 FontExtent(display.displaySystem, surface.font, text, len, &w, &h, 0, null, &adv);
2667 display.displaySystem.driver.Area(display, surface,x,y,x+w-1,y+h-1);
2670 oglSurface.writingText = true;
2672 GLSetupTexturing(true);
2674 if(surface.font.outlineSize)
2676 ColorAlpha outlineColor = surface.outlineColor;
2677 glColor4ub(outlineColor.color.r, outlineColor.color.g, outlineColor.color.b, outlineColor.a);
2678 oglSurface.writingOutline = true;
2679 ((subclass(DisplayDriver))class(LFBDisplayDriver)).WriteText(display, surface, x, y, text, len, prevGlyph, rPrevGlyph);
2680 oglSurface.writingOutline = false;
2682 glColor4fv(oglSurface.foreground);
2684 ((subclass(DisplayDriver))class(LFBDisplayDriver)).WriteText(display, surface, x, y, text, len, prevGlyph, rPrevGlyph);
2685 oglSurface.writingText = false;
2686 oglSystem.loadingFont = false;
2688 GLSetupTexturing(false);
2690 //glTranslated(0.375, 0.375, 0.0);
2693 void TextFont(Display display, Surface surface, Font font)
2695 ((subclass(DisplayDriver))class(LFBDisplayDriver)).TextFont(display, surface, font);
2698 void TextOpacity(Display display, Surface surface, bool opaque)
2700 OGLSurface oglSurface = surface.driverData;
2701 oglSurface.opaqueText = opaque;
2704 void TextExtent(Display display, Surface surface, const char * text, int len, int * width, int * height, int prevGlyph, int * rPrevGlyph, int * adv)
2706 OGLSurface oglSurface = surface.driverData;
2707 OGLSystem oglSystem = display.displaySystem.driverData;
2708 oglSystem.loadingFont = true;
2709 FontExtent(display.displaySystem, oglSurface.font, text, len, width, height, prevGlyph, rPrevGlyph, adv);
2710 oglSystem.loadingFont = false;
2713 void DrawingChar(Display display, Surface surface, char character)
2718 void LineStipple(Display display, Surface surface, uint32 stipple)
2720 //Logf("Stipple\n");
2724 #if defined(ES1_1) || defined(ES2) || defined(SHADERS)
2725 stippleEnabled = true;
2726 glesLineStipple(1, (uint16)stipple);
2728 glLineStipple(1, (uint16)stipple);
2729 glEnable(GL_LINE_STIPPLE);
2734 #if defined(ES1_1) || defined(ES2) || defined(SHADERS)
2735 stippleEnabled = false;
2736 glMatrixMode(GL_TEXTURE);
2738 glMatrixMode(MatrixMode::projection);
2739 GLSetupTexturing(false); // TODO: Special shading code for stipple?
2741 glDisable(GL_LINE_STIPPLE);
2746 #if !defined(ECERE_NO3D) && !defined(ECERE_VANILLA)
2747 void SetRenderState(Display display, RenderState state, uint value)
2749 OGLDisplay oglDisplay = display.driverData;
2750 //Logf("RenderState\n");
2755 #ifndef __EMSCRIPTEN__
2757 glEnable(GL_MULTISAMPLE_ARB);
2759 glDisable(GL_MULTISAMPLE_ARB);
2763 #if !defined(ES1_1) && !defined(ES2)
2764 glPolygonMode(GL_FRONT_AND_BACK, ((FillModeValue)value == solid) ? GL_FILL : GL_LINE);
2768 if(value) glEnable(GL_DEPTH_TEST); else glDisable(GL_DEPTH_TEST);
2771 if(value) glDepthMask((byte)bool::true); else glDepthMask((byte)bool::false);
2772 oglDisplay.depthWrite = (bool)value;
2776 float color[4] = { ((Color)value).r/255.0f, ((Color)value).g/255.0f, ((Color)value).b/255.0f, 1.0f };
2777 #if defined(SHADERS)
2778 shader_fogColor(color[0], color[1], color[2]);
2780 glFogfv(GL_FOG_COLOR, (float *)&color);
2785 #if defined(SHADERS)
2786 shader_fogDensity((float)(RenderStateFloat { ui = value }.f * nearPlane));
2788 glFogf(GL_FOG_DENSITY, (float)(RenderStateFloat { ui = value }.f * nearPlane));
2792 //#if !defined(__EMSCRIPTEN__)
2793 if(value) glEnable(GL_BLEND); else glDisable(GL_BLEND);
2798 #if defined(SHADERS)
2799 shader_setGlobalAmbient(((Color)value).r / 255.0f, ((Color)value).g / 255.0f, ((Color)value).b / 255.0f, 1.0f);
2801 float ambient[4] = { ((Color)value).r/255.0f, ((Color)value).g/255.0f, ((Color)value).b/255.0f, 1.0f };
2802 glLightModelfv(GL_LIGHT_MODEL_AMBIENT, ambient);
2808 if(value) glColorMask(1,1,1,1); else glColorMask(1,1,1,0);
2813 #if defined(__WIN32__)
2814 wglSwapIntervalEXT(value ? 1 : 0);
2821 void SetLight(Display display, int id, Light light)
2823 #if defined(SHADERS)
2824 shader_setLight(display, id, light);
2826 //Logf("SetLight\n");
2830 Object lightObject = light.lightObject;
2831 float position[4] = { 0, 0, 0, 0 };
2832 float color[4] = { 0, 0, 0, 1 };
2834 glEnable(GL_LIGHT0 + id);
2836 glLightfv(GL_LIGHT0 + id, GL_DIFFUSE, (float *)&light.diffuse);
2837 glLightfv(GL_LIGHT0 + id, GL_AMBIENT, (float *)&light.ambient);
2838 glLightfv(GL_LIGHT0 + id, GL_SPECULAR,(float *)&light.specular);
2841 if(!light.multiplier) light.multiplier = 1.0f;
2843 color[0] = light.diffuse.r * light.multiplier;
2844 color[1] = light.diffuse.g * light.multiplier;
2845 color[2] = light.diffuse.b * light.multiplier;
2846 glLightfv(GL_LIGHT0 + id, GL_DIFFUSE, color);
2848 color[0] = light.ambient.r * light.multiplier;
2849 color[1] = light.ambient.g * light.multiplier;
2850 color[2] = light.ambient.b * light.multiplier;
2851 glLightfv(GL_LIGHT0 + id, GL_AMBIENT, color);
2852 color[0] = light.specular.r * light.multiplier;
2853 color[1] = light.specular.g * light.multiplier;
2854 color[2] = light.specular.b * light.multiplier;
2855 glLightfv(GL_LIGHT0 + id, GL_SPECULAR,color);
2859 Vector3D positionVector;
2860 if(light.flags.spot)
2862 if(lightObject.flags.root || !lightObject.parent)
2864 positionVector = lightObject.transform.position;
2865 positionVector.Subtract(positionVector, display.display3D.camera.cPosition);
2869 positionVector.MultMatrix(lightObject.transform.position, lightObject.parent.matrix);
2870 if(display.display3D.camera)
2871 positionVector.Subtract(positionVector, display.display3D.camera.cPosition);
2877 if(!light.direction.x && !light.direction.y && !light.direction.z)
2879 Vector3Df vector { 0,0,-1 };
2881 mat.RotationQuaternion(light.orientation);
2882 positionVector.MultMatrixf(vector, mat);
2886 positionVector = light.direction;
2891 position[0] = (float)positionVector.x;
2892 position[1] = (float)positionVector.y;
2893 position[2] = (float)positionVector.z;
2895 glLightfv(GL_LIGHT0 + id, GL_POSITION, position);
2898 // Display Light Position
2899 glDisable(GL_LIGHTING);
2900 glDisable(GL_DEPTH_TEST);
2904 glVertex3fv(position);
2906 glEnable(GL_DEPTH_TEST);
2907 glEnable(GL_LIGHTING);
2911 if(lightObject.flags.root || !lightObject.parent)
2913 positionVector = light.target.transform.position;
2914 positionVector.Subtract(positionVector, display.camera.cPosition);
2918 positionVector.MultMatrix(light.target.transform.position,
2919 lightObject.light.target.parent.matrix);
2920 positionVector.Subtract(positionVector, display.camera.cPosition);
2923 position[0] = positionVector.x;
2924 position[1] = positionVector.y;
2925 position[2] = positionVector.z;
2927 glDisable(GL_LIGHTING);
2928 glDisable(GL_DEPTH_TEST);
2932 glVertex3fv(position);
2934 glEnable(GL_DEPTH_TEST);
2935 glEnable(GL_LIGHTING);
2938 if(light.flags.attenuation)
2940 glLightf(GL_LIGHT0 + id, GL_CONSTANT_ATTENUATION, light.Kc);
2941 glLightf(GL_LIGHT0 + id, GL_LINEAR_ATTENUATION, light.Kl);
2942 glLightf(GL_LIGHT0 + id, GL_QUADRATIC_ATTENUATION, light.Kq);
2945 if(light.flags.spot)
2948 #define MAXLIGHT 0.9
2949 float direction[4] = { (float)light.direction.x, (float)light.direction.y, (float)light.direction.z, 1 };
2950 // Figure out exponent out of the hot spot
2951 exponent = (float)(log(MAXLIGHT) / log(cos((light.hotSpot / 2))));
2953 glLightfv(GL_LIGHT0 + id, GL_SPOT_DIRECTION, direction);
2954 glLightf(GL_LIGHT0 + id, GL_SPOT_CUTOFF, (float)(light.fallOff / 2));
2955 glLightf(GL_LIGHT0 + id, GL_SPOT_EXPONENT, exponent);
2960 Vector3Df vector { 0,0,-1 };
2961 Vector3Df direction;
2964 mat.RotationQuaternion(light.orientation);
2965 direction.MultMatrix(vector, mat);
2967 position[0] = direction.x;
2968 position[1] = direction.y;
2969 position[2] = direction.z;
2971 glLightfv(GL_LIGHT0 + id, GL_POSITION, position);
2975 glDisable(GL_LIGHT0 + id);
2979 void SetCamera(Display display, Surface surface, Camera camera)
2981 OGLDisplay oglDisplay = display.driverData;
2982 //Logf("SetCamera\n");
2984 if(surface && camera)
2986 int left = surface.box.left + surface.offset.x;
2987 int top = surface.box.top + surface.offset.y;
2988 int right = surface.box.right + surface.offset.x;
2989 int bottom = surface.box.bottom + surface.offset.y;
2990 float origX = surface.offset.x + camera.origin.x;
2991 float origY = surface.offset.y + camera.origin.y;
2993 int y = display.height - bottom - 1;
2994 int w = right - left + 1;
2995 int h = bottom - top + 1;
2998 glViewport(x, y, w, h);
3000 // *** Projection Matrix ***
3001 glMatrixMode(MatrixMode::projection);
3002 if(!display.display3D.camera)
3005 if(display.display3D.collectingHits)
3007 float pickX = display.display3D.pickX + surface.offset.x;
3008 float pickY = display.height - (display.display3D.pickY + surface.offset.y) - 1;
3012 w / display.display3D.pickWidth, 0, 0, 0,
3013 0, h / display.display3D.pickHeight, 0, 0,
3015 (w + 2.0f * (x - pickX)) / display.display3D.pickWidth,
3016 (h + 2.0f * (y - pickY)) / display.display3D.pickHeight, 0, 1
3019 glLoadMatrixd(pickMatrix.array);
3024 (left - origX) * camera.zMin / camera.focalX,
3025 (right - origX) * camera.zMin / camera.focalX,
3026 (bottom - origY) * camera.zMin / camera.focalY,
3027 (top - origY) * camera.zMin / camera.focalY,
3028 camera.zMin, camera.zMax);
3030 glDisable(GL_BLEND);
3032 // *** Z Inverted Identity Matrix ***
3033 glMatrixMode(MatrixMode::modelView);
3034 if(!display.display3D.camera)
3039 glScaled(1.0/nearPlane, 1.0/nearPlane, -1.0/nearPlane);
3041 // *** View Matrix ***
3042 glMultMatrixd(camera.viewMatrix.array);
3047 glEnable(GL_DEPTH_TEST);
3049 GLSetupLighting(true);
3050 #if !defined(SHADERS)
3051 glShadeModel(GL_SMOOTH);
3053 glDepthMask((byte)bool::true);
3054 oglDisplay.depthWrite = true;
3056 #ifndef __EMSCRIPTEN__
3057 glEnable(GL_MULTISAMPLE_ARB);
3060 else if(surface && display.display3D.camera)
3063 oglDisplay.depthWrite = false;
3064 glViewport(0,0,display.width,display.height);
3066 glDisable(GL_CULL_FACE);
3067 glDisable(GL_DEPTH_TEST);
3070 GLSetupTexturing(false);
3071 GLSetupLighting(false);
3074 glDisableClientState(GL_COLOR_ARRAY);
3076 #if defined(SHADERS)
3077 shader_setPerVertexColor(false);
3079 glShadeModel(GL_FLAT);
3082 #if !defined(__EMSCRIPTEN__)
3083 glDisable(GL_MULTISAMPLE_ARB);
3086 // *** Restore 2D MODELVIEW Matrix ***
3089 // *** Restore 2D PROJECTION Matrix ***
3090 glMatrixMode(MatrixMode::projection);
3096 void ApplyMaterial(Display display, Material material, Mesh mesh)
3098 //Logf("ApplyMaterial\n");
3101 if(material.flags.doubleSided)
3103 #if !defined(SHADERS)
3104 glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, !material.flags.singleSideLight);
3106 glDisable(GL_CULL_FACE);
3110 #if !defined(SHADERS)
3111 glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, bool::false);
3113 glEnable(GL_CULL_FACE);
3117 GLSetupFog(!material.flags.noFog);
3120 if(material.baseMap && (mesh.texCoords || mesh.flags.texCoords1))
3122 Bitmap map = material.baseMap;
3123 GLSetupTexturing(true);
3124 glBindTexture(GL_TEXTURE_2D, (GLuint)(uintptr)map.driverData);
3126 glMatrixMode(GL_TEXTURE);
3128 if(material.uScale && material.vScale)
3129 glScalef(material.uScale, material.vScale, 1);
3130 glMatrixMode(MatrixMode::modelView);
3132 if(material.flags.tile)
3134 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
3135 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
3139 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
3140 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
3144 GLSetupTexturing(false);
3146 #if defined(SHADERS)
3147 shader_setMaterial(material, mesh.flags.colors);
3149 if(mesh.flags.colors)
3151 glColorMaterial(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE);
3152 glEnable(GL_COLOR_MATERIAL);
3156 glDisable(GL_COLOR_MATERIAL);
3158 float color[4] = { material.diffuse.r, material.diffuse.g, material.diffuse.b, material.opacity };
3159 glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, color);
3162 float color[4] = { material.ambient.r, material.ambient.g, material.ambient.b, 0 };
3163 glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, color);
3167 float color[4] = { material.specular.r, material.specular.g, material.specular.b, 0 };
3168 glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, color);
3171 float color[4] = { material.emissive.r, material.emissive.g, material.emissive.b, 0 };
3172 glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, color);
3175 glMaterialfv(GL_FRONT_AND_BACK, GL_SHININESS, &material.power);
3179 void FreeMesh(DisplaySystem displaySystem, Mesh mesh)
3181 OGLMesh oglMesh = mesh.data;
3184 if(!mesh.flags.vertices)
3186 oglMesh.vertices.free();
3187 delete mesh.vertices;
3189 if(!mesh.flags.normals)
3191 oglMesh.normals.free();
3192 delete mesh.normals;
3194 if(!mesh.flags.texCoords1)
3196 oglMesh.texCoords.free();
3197 delete mesh.texCoords;
3199 if(!mesh.flags.texCoords2)
3201 oglMesh.texCoords2.free();
3202 // delete mesh.texCoords2;
3204 if(!mesh.flags.colors)
3206 oglMesh.colors.free();
3217 bool AllocateMesh(DisplaySystem displaySystem, Mesh mesh, MeshFeatures flags, int nVertices)
3219 bool result = false;
3222 mesh.data = OGLMesh { };
3225 if(mesh.nVertices == nVertices)
3227 // Same number of vertices, adding features (Leaves the other features pointers alone)
3228 if(mesh.flags != flags)
3230 if(!mesh.flags.vertices && flags.vertices)
3232 if(flags.doubleVertices)
3234 mesh.vertices = (Vector3Df *)new Vector3D[nVertices];
3237 mesh.vertices = new Vector3Df[nVertices];
3239 if(!mesh.flags.normals && flags.normals)
3241 if(flags.doubleNormals)
3243 mesh.normals = (Vector3Df *)new Vector3D[nVertices];
3246 mesh.normals = new Vector3Df[nVertices];
3248 if(!mesh.flags.texCoords1 && flags.texCoords1)
3250 mesh.texCoords = new Pointf[nVertices];
3252 if(!mesh.flags.colors && flags.colors)
3254 mesh.colors = new ColorRGBAf[nVertices];
3260 // New number of vertices, reallocate all current and new features
3261 flags |= mesh.flags;
3264 if(flags.doubleVertices)
3266 mesh.vertices = (Vector3Df *)renew mesh.vertices Vector3D[nVertices];
3269 mesh.vertices = renew mesh.vertices Vector3Df[nVertices];
3273 if(flags.doubleNormals)
3275 mesh.normals = (Vector3Df *)renew mesh.normals Vector3D[nVertices];
3278 mesh.normals = renew mesh.normals Vector3Df[nVertices];
3280 if(flags.texCoords1)
3282 mesh.texCoords = renew mesh.texCoords Pointf[nVertices];
3286 mesh.colors = renew mesh.colors ColorRGBAf[nVertices];
3294 void UnlockMesh(DisplaySystem displaySystem, Mesh mesh, MeshFeatures flags)
3296 OGLMesh oglMesh = mesh.data;
3297 if(!flags) flags = mesh.flags;
3302 oglMesh.vertices.upload(
3303 mesh.nVertices * (mesh.flags.doubleVertices ? sizeof(Vector3D) : sizeof(Vector3Df)), mesh.vertices); //, GL_STATIC_DRAW_ARB );
3306 oglMesh.normals.upload(
3307 mesh.nVertices * (mesh.flags.doubleNormals ? sizeof(Vector3D) : sizeof(Vector3Df)), mesh.normals); //, GL_STATIC_DRAW_ARB );
3309 if(flags.texCoords1)
3310 oglMesh.texCoords.upload(
3311 mesh.nVertices * sizeof(Pointf), mesh.texCoords); //, GL_STATIC_DRAW_ARB );
3314 oglMesh.colors.upload(
3315 mesh.nVertices * sizeof(ColorRGBAf), mesh.colors); //, GL_STATIC_DRAW_ARB );
3319 bool LockMesh(DisplaySystem displaySystem, Mesh mesh, MeshFeatures flags)
3326 void FreeIndices(DisplaySystem displaySystem, OGLIndices oglIndices)
3330 oglIndices.buffer.free();
3331 delete oglIndices.indices;
3336 void * AllocateIndices(DisplaySystem displaySystem, int nIndices, bool indices32bit)
3338 OGLIndices oglIndices = OGLIndices { };
3341 oglIndices.indices = (void *)(indices32bit ? new uint32[nIndices] : new uint16[nIndices]);
3342 oglIndices.nIndices = nIndices;
3347 void UnlockIndices(DisplaySystem displaySystem, OGLIndices oglIndices, bool indices32bit, int nIndices)
3351 #if defined(ES1_1) || defined(ES2)
3354 if(!oglIndices.buffer.buffer)
3355 glGenBuffers(1, &oglIndices.buffer.buffer);
3356 if(glabCurElementBuffer != oglIndices.buffer.buffer)
3357 GLABBindBuffer(GL_ELEMENT_ARRAY_BUFFER, oglIndices.buffer.buffer);
3358 glimtkBufferDatai(GL_ELEMENT_ARRAY_BUFFER, sizeof(uint32) * nIndices, oglIndices.indices, GL_STATIC_DRAW_ARB);
3362 oglIndices.buffer.upload(
3363 nIndices * (indices32bit ? sizeof(uint32) : sizeof(uint16)),
3364 oglIndices.indices); //GL_STATIC_DRAW_ARB);
3368 uint16 * LockIndices(DisplaySystem displaySystem, OGLIndices oglIndices)
3371 return oglIndices.indices;
3374 void SelectMesh(Display display, Mesh mesh)
3376 //Logf("SelectMesh\n");
3378 #if !defined( __ANDROID__) && !defined(__APPLE__) && !defined(__ODROID__) && !defined(__EMSCRIPTEN__)
3380 #if defined(__WIN32__)
3381 if(glUnlockArraysEXT)
3383 if(!vboAvailable && display.display3D.mesh)
3384 glUnlockArraysEXT();
3389 OGLMesh oglMesh = mesh.data;
3391 // *** Vertex Stream ***
3392 glEnableClientState(GL_VERTEX_ARRAY);
3393 if(!display.display3D.collectingHits && oglMesh)
3395 oglMesh.vertices.use(vertex, 3, (mesh.flags.doubleVertices ? GL_DOUBLE : GL_FLOAT), 0, oglMesh.vertices.buffer ? null : (double *)mesh.vertices);
3397 // *** Normals Stream ***
3398 if(mesh.normals || mesh.flags.normals)
3400 glEnableClientState(GL_NORMAL_ARRAY);
3401 oglMesh.normals.use(normal, 3, GL_FLOAT, 0, oglMesh.normals.buffer ? null : mesh.normals);
3404 glDisableClientState(GL_NORMAL_ARRAY);
3406 // *** Texture Coordinates Stream ***
3407 if(mesh.texCoords || mesh.flags.texCoords1)
3409 glEnableClientState(GL_TEXTURE_COORD_ARRAY);
3410 oglMesh.texCoords.use(texCoord, 2, GL_FLOAT, 0, oglMesh.texCoords.buffer ? null : mesh.texCoords);
3413 glDisableClientState(GL_TEXTURE_COORD_ARRAY);
3415 // *** Color Stream ***
3416 if(mesh.colors || mesh.flags.colors)
3418 glEnableClientState(GL_COLOR_ARRAY);
3419 oglMesh.colors.use(color, 4, GL_FLOAT, 0, oglMesh.colors.buffer ? null : mesh.colors);
3422 glDisableClientState(GL_COLOR_ARRAY);
3426 noAB.use(vertex, 3, (mesh.flags.doubleVertices ? GL_DOUBLE : GL_FLOAT), 0, (double *)mesh.vertices);
3427 if((mesh.normals || mesh.flags.normals) && !display.display3D.collectingHits)
3429 glEnableClientState(GL_NORMAL_ARRAY);
3430 noAB.use(normal, 3, GL_FLOAT, 0, mesh.normals);
3433 glDisableClientState(GL_NORMAL_ARRAY);
3434 if((mesh.texCoords || mesh.flags.texCoords1) && !display.display3D.collectingHits)
3436 glEnableClientState(GL_TEXTURE_COORD_ARRAY);
3437 noAB.use(texCoord, 2, GL_FLOAT, 0, mesh.texCoords);
3440 glDisableClientState(GL_TEXTURE_COORD_ARRAY);
3441 if((mesh.colors || mesh.flags.colors) && !display.display3D.collectingHits)
3443 glEnableClientState(GL_COLOR_ARRAY);
3444 noAB.use(color, 4, GL_FLOAT, 0, mesh.colors);
3447 glDisableClientState(GL_COLOR_ARRAY);
3450 #if !defined(__ANDROID__) && !defined(__APPLE__) && !defined(__ODROID__) && !defined(__EMSCRIPTEN__)
3452 #if defined(__WIN32__)
3456 glLockArraysEXT(0, mesh.nVertices);
3462 void DrawPrimitives(Display display, PrimitiveSingle * primitive, Mesh mesh)
3464 //Logf("DrawPrimitives\n");
3466 if(primitive->type.vertexRange)
3467 glDrawArrays(primitiveTypes[primitive->type.primitiveType], primitive->first, primitive->nVertices);
3470 // *** Hoping the data won't be uploaded at all (Won't really work if another group of the mesh is using the mesh ) ***
3471 // HACK TO SPEED THINGS UP...
3473 /*GLABBindBuffer(GL_ELEMENT_ARRAY_BUFFER_ARB, 0);
3474 if(primitive->nIndices < (mesh.nVertices >> 2) && !primitive->type.indices32bit)
3477 glBegin((GLIMTKMode)primitiveTypes[primitive->type.primitiveType]);
3480 OGLIndices oglIndices = primitive->data;
3481 MeshFeatures flags = mesh.flags;
3482 for(c = 0; c<primitive->nIndices; c++)
3484 uint16 index = ((uint16 *) oglIndices.indices)[c];
3485 if(flags.normals) glNormal3fv((float *)&mesh.normals[index]);
3486 if(flags.texCoords1) glTexCoord2fv((float *)&mesh.texCoords[index]);
3487 if(flags.colors) glColor4fv((float *)&mesh.colors[index]);
3488 glVertex3fv((float *)&mesh.vertices[index]);
3497 OGLIndices oglIndices = primitive->data;
3498 GLEAB eab = ((!display.display3D.collectingHits && oglIndices) ? oglIndices.buffer : noEAB);
3500 eab.draw(primitiveTypes[primitive->type.primitiveType], primitive->nIndices,
3501 primitive->type.indices32bit ? GL_UNSIGNED_INT : GL_UNSIGNED_SHORT,
3502 eab.buffer ? 0 : (oglIndices ? oglIndices.indices : primitive->indices));
3503 GLABBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);
3508 void PushMatrix(Display display)
3513 void PopMatrix(Display display, bool setMatrix)
3518 void SetTransform(Display display, Matrix transMatrix, bool viewSpace, bool useCamera)
3520 Matrix matrix = transMatrix;
3521 Camera camera = useCamera ? display.display3D.camera : null;
3526 glScaled(1.0/nearPlane, 1.0/nearPlane, -1.0/nearPlane);
3531 matrix.m[3][0] - camera.cPosition.x,
3532 matrix.m[3][1] - camera.cPosition.y,
3533 matrix.m[3][2] - camera.cPosition.z);
3545 glMultMatrixd(matrix.array);
3550 public void UseSingleGLContext(bool useSingle)
3552 useSingleGLContext = useSingle;
3555 default dllexport void *
3556 #if defined(__WIN32__)
3557 __attribute__((stdcall))
3559 IS_GLGetContext(DisplaySystem displaySystem)
3563 #if defined(__WIN32__)
3564 OGLSystem system = displaySystem.driverData;
3566 #elif defined(__ANDROID__) || defined(__ODROID__)
3568 #elif defined(__EMSCRIPTEN__)
3569 OGLSystem system = displaySystem.driverData;
3570 return (void *)system.glc;
3572 OGLSystem system = displaySystem.driverData;
3573 return system.glContext;