2 * Copyright (C) 1999-2001 Brian Paul All Rights Reserved.
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
11 * The above copyright notice and this permission notice shall be included
12 * in all copies or substantial portions of the Software.
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
15 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
17 * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
18 * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
19 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
23 * Ported to X/EGL/GLES. XXX Actually, uses full OpenGL ATM.
29 * Command line options:
30 * -info print GL implementation information
35 #define GL_GLEXT_PROTOTYPES
36 #define EGL_EGLEXT_PROTOTYPES
43 #include <X11/Xutil.h>
44 #include <X11/keysym.h>
48 #include <EGL/eglext.h>
55 /* XXX this probably isn't very portable */
60 /* return current time (in seconds) */
66 (void) gettimeofday(&tv
, NULL
);
69 (void) gettimeofday(&tv
, &tz
);
71 return (double) tv
.tv_sec
+ tv
.tv_usec
/ 1000000.0;
80 /* update this function for other platforms! */
81 static double t
= 0.0;
84 fprintf(stderr
, "Warning: current_time() not implemented!!\n");
95 #define M_PI 3.14159265
99 static GLfloat view_rotx
= 20.0, view_roty
= 30.0, view_rotz
= 0.0;
100 static GLint gear1
, gear2
, gear3
;
101 static GLfloat angle
= 0.0;
105 * Draw a gear wheel. You'll probably want to call this function when
106 * building a display list since we do a lot of trig here.
108 * Input: inner_radius - radius of hole at center
109 * outer_radius - radius at center of teeth
110 * width - width of gear
111 * teeth - number of teeth
112 * tooth_depth - depth of tooth
115 gear(GLfloat inner_radius
, GLfloat outer_radius
, GLfloat width
,
116 GLint teeth
, GLfloat tooth_depth
)
124 r1
= outer_radius
- tooth_depth
/ 2.0;
125 r2
= outer_radius
+ tooth_depth
/ 2.0;
127 da
= 2.0 * M_PI
/ teeth
/ 4.0;
129 glShadeModel(GL_FLAT
);
131 glNormal3f(0.0, 0.0, 1.0);
133 /* draw front face */
134 glBegin(GL_QUAD_STRIP
);
135 for (i
= 0; i
<= teeth
; i
++) {
136 angle
= i
* 2.0 * M_PI
/ teeth
;
137 glVertex3f(r0
* cos(angle
), r0
* sin(angle
), width
* 0.5);
138 glVertex3f(r1
* cos(angle
), r1
* sin(angle
), width
* 0.5);
140 glVertex3f(r0
* cos(angle
), r0
* sin(angle
), width
* 0.5);
141 glVertex3f(r1
* cos(angle
+ 3 * da
), r1
* sin(angle
+ 3 * da
),
147 /* draw front sides of teeth */
149 da
= 2.0 * M_PI
/ teeth
/ 4.0;
150 for (i
= 0; i
< teeth
; i
++) {
151 angle
= i
* 2.0 * M_PI
/ teeth
;
153 glVertex3f(r1
* cos(angle
), r1
* sin(angle
), width
* 0.5);
154 glVertex3f(r2
* cos(angle
+ da
), r2
* sin(angle
+ da
), width
* 0.5);
155 glVertex3f(r2
* cos(angle
+ 2 * da
), r2
* sin(angle
+ 2 * da
),
157 glVertex3f(r1
* cos(angle
+ 3 * da
), r1
* sin(angle
+ 3 * da
),
162 glNormal3f(0.0, 0.0, -1.0);
165 glBegin(GL_QUAD_STRIP
);
166 for (i
= 0; i
<= teeth
; i
++) {
167 angle
= i
* 2.0 * M_PI
/ teeth
;
168 glVertex3f(r1
* cos(angle
), r1
* sin(angle
), -width
* 0.5);
169 glVertex3f(r0
* cos(angle
), r0
* sin(angle
), -width
* 0.5);
171 glVertex3f(r1
* cos(angle
+ 3 * da
), r1
* sin(angle
+ 3 * da
),
173 glVertex3f(r0
* cos(angle
), r0
* sin(angle
), -width
* 0.5);
178 /* draw back sides of teeth */
180 da
= 2.0 * M_PI
/ teeth
/ 4.0;
181 for (i
= 0; i
< teeth
; i
++) {
182 angle
= i
* 2.0 * M_PI
/ teeth
;
184 glVertex3f(r1
* cos(angle
+ 3 * da
), r1
* sin(angle
+ 3 * da
),
186 glVertex3f(r2
* cos(angle
+ 2 * da
), r2
* sin(angle
+ 2 * da
),
188 glVertex3f(r2
* cos(angle
+ da
), r2
* sin(angle
+ da
), -width
* 0.5);
189 glVertex3f(r1
* cos(angle
), r1
* sin(angle
), -width
* 0.5);
193 /* draw outward faces of teeth */
194 glBegin(GL_QUAD_STRIP
);
195 for (i
= 0; i
< teeth
; i
++) {
196 angle
= i
* 2.0 * M_PI
/ teeth
;
198 glVertex3f(r1
* cos(angle
), r1
* sin(angle
), width
* 0.5);
199 glVertex3f(r1
* cos(angle
), r1
* sin(angle
), -width
* 0.5);
200 u
= r2
* cos(angle
+ da
) - r1
* cos(angle
);
201 v
= r2
* sin(angle
+ da
) - r1
* sin(angle
);
202 len
= sqrt(u
* u
+ v
* v
);
205 glNormal3f(v
, -u
, 0.0);
206 glVertex3f(r2
* cos(angle
+ da
), r2
* sin(angle
+ da
), width
* 0.5);
207 glVertex3f(r2
* cos(angle
+ da
), r2
* sin(angle
+ da
), -width
* 0.5);
208 glNormal3f(cos(angle
), sin(angle
), 0.0);
209 glVertex3f(r2
* cos(angle
+ 2 * da
), r2
* sin(angle
+ 2 * da
),
211 glVertex3f(r2
* cos(angle
+ 2 * da
), r2
* sin(angle
+ 2 * da
),
213 u
= r1
* cos(angle
+ 3 * da
) - r2
* cos(angle
+ 2 * da
);
214 v
= r1
* sin(angle
+ 3 * da
) - r2
* sin(angle
+ 2 * da
);
215 glNormal3f(v
, -u
, 0.0);
216 glVertex3f(r1
* cos(angle
+ 3 * da
), r1
* sin(angle
+ 3 * da
),
218 glVertex3f(r1
* cos(angle
+ 3 * da
), r1
* sin(angle
+ 3 * da
),
220 glNormal3f(cos(angle
), sin(angle
), 0.0);
223 glVertex3f(r1
* cos(0), r1
* sin(0), width
* 0.5);
224 glVertex3f(r1
* cos(0), r1
* sin(0), -width
* 0.5);
228 glShadeModel(GL_SMOOTH
);
230 /* draw inside radius cylinder */
231 glBegin(GL_QUAD_STRIP
);
232 for (i
= 0; i
<= teeth
; i
++) {
233 angle
= i
* 2.0 * M_PI
/ teeth
;
234 glNormal3f(-cos(angle
), -sin(angle
), 0.0);
235 glVertex3f(r0
* cos(angle
), r0
* sin(angle
), -width
* 0.5);
236 glVertex3f(r0
* cos(angle
), r0
* sin(angle
), width
* 0.5);
245 glClearColor(0.2, 0.2, 0.2, 0.2);
246 glClear(GL_COLOR_BUFFER_BIT
| GL_DEPTH_BUFFER_BIT
);
249 glRotatef(view_rotx
, 1.0, 0.0, 0.0);
250 glRotatef(view_roty
, 0.0, 1.0, 0.0);
251 glRotatef(view_rotz
, 0.0, 0.0, 1.0);
254 glTranslatef(-3.0, -2.0, 0.0);
255 glRotatef(angle
, 0.0, 0.0, 1.0);
260 glTranslatef(3.1, -2.0, 0.0);
261 glRotatef(-2.0 * angle
- 9.0, 0.0, 0.0, 1.0);
266 glTranslatef(-3.1, 4.2, 0.0);
267 glRotatef(-2.0 * angle
- 25.0, 0.0, 0.0, 1.0);
275 /* new window size or exposure */
277 reshape(int width
, int height
)
279 GLfloat ar
= (GLfloat
) width
/ (GLfloat
) height
;
281 glViewport(0, 0, (GLint
) width
, (GLint
) height
);
283 glMatrixMode(GL_PROJECTION
);
285 glFrustum(-ar
, ar
, -1, 1, 5.0, 60.0);
287 glMatrixMode(GL_MODELVIEW
);
289 glTranslatef(0.0, 0.0, -40.0);
297 static GLfloat pos
[4] = { 5.0, 5.0, 10.0, 0.0 };
298 static GLfloat red
[4] = { 0.8, 0.1, 0.0, 1.0 };
299 static GLfloat green
[4] = { 0.0, 0.8, 0.2, 1.0 };
300 static GLfloat blue
[4] = { 0.2, 0.2, 1.0, 1.0 };
302 glLightfv(GL_LIGHT0
, GL_POSITION
, pos
);
303 glEnable(GL_CULL_FACE
);
304 glEnable(GL_LIGHTING
);
306 glEnable(GL_DEPTH_TEST
);
309 gear1
= glGenLists(1);
310 glNewList(gear1
, GL_COMPILE
);
311 glMaterialfv(GL_FRONT
, GL_AMBIENT_AND_DIFFUSE
, red
);
312 gear(1.0, 4.0, 1.0, 20, 0.7);
315 gear2
= glGenLists(1);
316 glNewList(gear2
, GL_COMPILE
);
317 glMaterialfv(GL_FRONT
, GL_AMBIENT_AND_DIFFUSE
, green
);
318 gear(0.5, 2.0, 2.0, 10, 0.7);
321 gear3
= glGenLists(1);
322 glNewList(gear3
, GL_COMPILE
);
323 glMaterialfv(GL_FRONT
, GL_AMBIENT_AND_DIFFUSE
, blue
);
324 gear(1.3, 2.0, 0.5, 10, 0.7);
327 glEnable(GL_NORMALIZE
);
332 EGLNativeDisplayType xdpy
;
333 EGLNativeWindowType xwin
;
334 EGLNativePixmapType xpix
;
349 static struct egl_manager
*
350 egl_manager_new(EGLNativeDisplayType xdpy
, const EGLint
*attrib_list
,
353 struct egl_manager
*eman
;
357 eman
= calloc(1, sizeof(*eman
));
361 eman
->verbose
= verbose
;
364 eman
->dpy
= eglGetDisplay(eman
->xdpy
);
365 if (eman
->dpy
== EGL_NO_DISPLAY
) {
366 printf("eglGetDisplay() failed\n");
371 if (!eglInitialize(eman
->dpy
, &eman
->major
, &eman
->minor
)) {
372 printf("eglInitialize() failed\n");
377 ver
= eglQueryString(eman
->dpy
, EGL_VERSION
);
378 printf("EGL_VERSION = %s\n", ver
);
380 if (!eglChooseConfig(eman
->dpy
, attrib_list
, &eman
->conf
, 1, &num_conf
) ||
382 printf("eglChooseConfig() failed\n");
383 eglTerminate(eman
->dpy
);
388 eman
->ctx
= eglCreateContext(eman
->dpy
, eman
->conf
, EGL_NO_CONTEXT
, NULL
);
389 if (eman
->ctx
== EGL_NO_CONTEXT
) {
390 printf("eglCreateContext() failed\n");
391 eglTerminate(eman
->dpy
);
400 egl_manager_create_window(struct egl_manager
*eman
, const char *name
,
401 EGLint w
, EGLint h
, EGLBoolean need_surface
,
402 EGLBoolean fullscreen
, const EGLint
*attrib_list
)
404 XVisualInfo vinfo_template
, *vinfo
= NULL
;
405 EGLint val
, num_vinfo
;
407 XSetWindowAttributes attrs
;
411 if (!eglGetConfigAttrib(eman
->dpy
, eman
->conf
,
412 EGL_NATIVE_VISUAL_ID
, &val
)) {
413 printf("eglGetConfigAttrib() failed\n");
417 vinfo_template
.visualid
= (VisualID
) val
;
418 vinfo
= XGetVisualInfo(eman
->xdpy
, VisualIDMask
, &vinfo_template
, &num_vinfo
);
420 /* try harder if window surface is not needed */
421 if (!vinfo
&& !need_surface
&&
422 eglGetConfigAttrib(eman
->dpy
, eman
->conf
, EGL_BUFFER_SIZE
, &val
)) {
425 vinfo_template
.depth
= val
;
426 vinfo
= XGetVisualInfo(eman
->xdpy
, VisualDepthMask
, &vinfo_template
, &num_vinfo
);
430 printf("XGetVisualInfo() failed\n");
434 root
= DefaultRootWindow(eman
->xdpy
);
437 w
= DisplayWidth(eman
->xdpy
, DefaultScreen(eman
->xdpy
));
438 h
= DisplayHeight(eman
->xdpy
, DefaultScreen(eman
->xdpy
));
441 /* window attributes */
442 attrs
.background_pixel
= 0;
443 attrs
.border_pixel
= 0;
444 attrs
.colormap
= XCreateColormap(eman
->xdpy
, root
, vinfo
->visual
, AllocNone
);
445 attrs
.event_mask
= StructureNotifyMask
| ExposureMask
| KeyPressMask
;
446 attrs
.override_redirect
= fullscreen
;
447 mask
= CWBackPixel
| CWBorderPixel
| CWColormap
| CWEventMask
| CWOverrideRedirect
;
449 eman
->xwin
= XCreateWindow(eman
->xdpy
, root
, x
, y
, w
, h
,
450 0, vinfo
->depth
, InputOutput
,
451 vinfo
->visual
, mask
, &attrs
);
454 /* set hints and properties */
456 XSizeHints sizehints
;
460 sizehints
.height
= h
;
461 sizehints
.flags
= USSize
| USPosition
;
462 XSetNormalHints(eman
->xdpy
, eman
->xwin
, &sizehints
);
463 XSetStandardProperties(eman
->xdpy
, eman
->xwin
, name
, name
,
464 None
, (char **)NULL
, 0, &sizehints
);
468 eman
->win
= eglCreateWindowSurface(eman
->dpy
, eman
->conf
,
469 eman
->xwin
, attrib_list
);
470 if (eman
->win
== EGL_NO_SURFACE
) {
471 printf("eglCreateWindowSurface() failed\n");
472 XDestroyWindow(eman
->xdpy
, eman
->xwin
);
478 XMapWindow(eman
->xdpy
, eman
->xwin
);
484 egl_manager_create_pixmap(struct egl_manager
*eman
, EGLNativeWindowType xwin
,
485 EGLBoolean need_surface
, const EGLint
*attrib_list
)
487 XWindowAttributes attrs
;
489 if (!XGetWindowAttributes(eman
->xdpy
, xwin
, &attrs
)) {
490 printf("XGetWindowAttributes() failed\n");
494 eman
->xpix
= XCreatePixmap(eman
->xdpy
, xwin
,
495 attrs
.width
, attrs
.height
, attrs
.depth
);
498 eman
->pix
= eglCreatePixmapSurface(eman
->dpy
, eman
->conf
,
499 eman
->xpix
, attrib_list
);
500 if (eman
->pix
== EGL_NO_SURFACE
) {
501 printf("eglCreatePixmapSurface() failed\n");
502 XFreePixmap(eman
->xdpy
, eman
->xpix
);
512 egl_manager_create_pbuffer(struct egl_manager
*eman
, const EGLint
*attrib_list
)
514 eman
->pbuf
= eglCreatePbufferSurface(eman
->dpy
, eman
->conf
, attrib_list
);
515 if (eman
->pbuf
== EGL_NO_SURFACE
) {
516 printf("eglCreatePbufferSurface() failed\n");
524 egl_manager_destroy(struct egl_manager
*eman
)
526 eglMakeCurrent(eman
->dpy
, EGL_NO_SURFACE
, EGL_NO_SURFACE
, EGL_NO_CONTEXT
);
527 eglTerminate(eman
->dpy
);
529 if (eman
->xwin
!= None
)
530 XDestroyWindow(eman
->xdpy
, eman
->xwin
);
531 if (eman
->xpix
!= None
)
532 XFreePixmap(eman
->xdpy
, eman
->xpix
);
540 GEARS_PIXMAP_TEXTURE
,
542 GEARS_PBUFFER_TEXTURE
546 texture_gears(struct egl_manager
*eman
, int surface_type
)
548 static const GLint verts
[12] =
549 { -5, -6, -10, 5, -6, -10, -5, 4, 10, 5, 4, 10 };
550 static const GLint tex_coords
[8] = { 0, 0, 1, 0, 0, 1, 1, 1 };
552 eglMakeCurrent(eman
->dpy
, eman
->win
, eman
->win
, eman
->ctx
);
554 glClearColor(0, 0, 0, 0);
555 glClear(GL_COLOR_BUFFER_BIT
| GL_DEPTH_BUFFER_BIT
);
557 glEnable(GL_TEXTURE_2D
);
558 glTexEnvf(GL_TEXTURE_ENV
, GL_TEXTURE_ENV_MODE
, GL_REPLACE
);
559 glTexParameterf(GL_TEXTURE_2D
, GL_TEXTURE_WRAP_R
, GL_REPEAT
);
560 glTexParameterf(GL_TEXTURE_2D
, GL_TEXTURE_MIN_FILTER
, GL_NEAREST
);
561 glTexParameterf(GL_TEXTURE_2D
, GL_TEXTURE_MAG_FILTER
, GL_NEAREST
);
563 glEnableClientState(GL_VERTEX_ARRAY
);
564 glEnableClientState(GL_TEXTURE_COORD_ARRAY
);
565 glVertexPointer(3, GL_INT
, 0, verts
);
566 glTexCoordPointer(2, GL_INT
, 0, tex_coords
);
568 if (surface_type
== GEARS_PBUFFER_TEXTURE
)
569 eglBindTexImage(eman
->dpy
, eman
->pbuf
, EGL_BACK_BUFFER
);
571 glDrawArrays(GL_TRIANGLE_STRIP
, 0, 4);
573 glDisableClientState(GL_VERTEX_ARRAY
);
574 glDisableClientState(GL_COLOR_ARRAY
);
575 glDisable(GL_TEXTURE_2D
);
577 if (surface_type
== GEARS_PBUFFER_TEXTURE
)
578 eglReleaseTexImage(eman
->dpy
, eman
->pbuf
, EGL_BACK_BUFFER
);
580 eglSwapBuffers(eman
->dpy
, eman
->win
);
584 event_loop(struct egl_manager
*eman
, EGLint surface_type
, EGLint w
, EGLint h
)
586 GC gc
= XCreateGC(eman
->xdpy
, eman
->xwin
, 0, NULL
);
587 EGLint orig_w
= w
, orig_h
= h
;
589 if (surface_type
== EGL_PBUFFER_BIT
)
590 printf("there will be no screen update if "
591 "eglCopyBuffers() is not implemented\n");
594 while (XPending(eman
->xdpy
) > 0) {
596 XNextEvent(eman
->xdpy
, &event
);
597 switch (event
.type
) {
599 /* we'll redraw below */
601 case ConfigureNotify
:
602 w
= event
.xconfigure
.width
;
603 h
= event
.xconfigure
.height
;
604 if (surface_type
== EGL_WINDOW_BIT
)
611 code
= XLookupKeysym(&event
.xkey
, 0);
612 if (code
== XK_Left
) {
615 else if (code
== XK_Right
) {
618 else if (code
== XK_Up
) {
621 else if (code
== XK_Down
) {
625 r
= XLookupString(&event
.xkey
, buffer
, sizeof(buffer
),
627 if (buffer
[0] == 27) {
637 static int frames
= 0;
638 static double tRot0
= -1.0, tRate0
= -1.0;
639 double dt
, t
= current_time();
646 /* advance rotation for next frame */
647 angle
+= 70.0 * dt
; /* 70 degrees per second */
651 switch (surface_type
) {
653 case GEARS_PBUFFER_TEXTURE
:
654 eglMakeCurrent(eman
->dpy
, eman
->pbuf
, eman
->pbuf
, eman
->ctx
);
658 case GEARS_PIXMAP_TEXTURE
:
659 eglMakeCurrent(eman
->dpy
, eman
->pix
, eman
->pix
, eman
->ctx
);
664 switch (surface_type
) {
666 eglSwapBuffers(eman
->dpy
, eman
->win
);
668 case GEARS_PBUFFER_TEXTURE
:
669 case GEARS_PIXMAP_TEXTURE
:
670 texture_gears(eman
, surface_type
);
673 if (!eglCopyBuffers(eman
->dpy
, eman
->pbuf
, eman
->xpix
))
679 for (x
= 0; x
< w
; x
+= orig_w
) {
680 for (y
= 0; y
< h
; y
+= orig_h
) {
681 XCopyArea(eman
->xdpy
, eman
->xpix
, eman
->xwin
, gc
,
682 0, 0, orig_w
, orig_h
, x
, y
);
692 if (t
- tRate0
>= 5.0) {
693 GLfloat seconds
= t
- tRate0
;
694 GLfloat fps
= frames
/ seconds
;
695 printf("%d frames in %3.1f seconds = %6.3f FPS\n", frames
, seconds
,
703 XFreeGC(eman
->xdpy
, gc
);
711 printf(" -display <displayname> set the display to run on\n");
712 printf(" -fullscreen run in fullscreen mode\n");
713 printf(" -info display OpenGL renderer info\n");
714 printf(" -pixmap use pixmap surface\n");
715 printf(" -pbuffer-copy use pbuffer surface and eglCopyBuffers\n");
716 printf(" -pbuffer-texture use pbuffer surface and eglBindTexImage\n");
719 static const char *names
[] = {
720 "window", "pixmap", "pixmap_texture", "pbuffer", "pbuffer_texture"
724 main(int argc
, char *argv
[])
726 const int winWidth
= 300, winHeight
= 300;
728 char *dpyName
= NULL
;
729 struct egl_manager
*eman
;
731 EGL_SURFACE_TYPE
, EGL_WINDOW_BIT
, /* may be changed later */
736 EGL_RENDERABLE_TYPE
, EGL_OPENGL_BIT
,
739 char win_title
[] = "xeglgears (window/pixmap/pbuffer)";
740 EGLint surface_type
= GEARS_WINDOW
;
741 GLboolean printInfo
= GL_FALSE
;
742 GLboolean fullscreen
= GL_FALSE
;
747 for (i
= 1; i
< argc
; i
++) {
748 if (strcmp(argv
[i
], "-display") == 0) {
752 else if (strcmp(argv
[i
], "-info") == 0) {
755 else if (strcmp(argv
[i
], "-fullscreen") == 0) {
756 fullscreen
= GL_TRUE
;
758 else if (strcmp(argv
[i
], "-pixmap") == 0) {
759 surface_type
= GEARS_PIXMAP
;
760 attribs
[1] = EGL_PIXMAP_BIT
;
762 else if (strcmp(argv
[i
], "-pixmap-texture") == 0) {
763 surface_type
= GEARS_PIXMAP_TEXTURE
;
764 attribs
[1] = EGL_PIXMAP_BIT
;
766 else if (strcmp(argv
[i
], "-pbuffer") == 0) {
767 surface_type
= GEARS_PBUFFER
;
768 attribs
[1] = EGL_PBUFFER_BIT
;
770 else if (strcmp(argv
[i
], "-pbuffer-texture") == 0) {
771 surface_type
= GEARS_PBUFFER_TEXTURE
;
772 attribs
[1] = EGL_PBUFFER_BIT
;
780 x_dpy
= XOpenDisplay(dpyName
);
782 printf("Error: couldn't open display %s\n",
783 dpyName
? dpyName
: getenv("DISPLAY"));
787 eglBindAPI(EGL_OPENGL_API
);
789 eman
= egl_manager_new(x_dpy
, attribs
, printInfo
);
791 XCloseDisplay(x_dpy
);
795 snprintf(win_title
, sizeof(win_title
),
796 "xeglgears (%s)", names
[surface_type
]);
798 /* create surface(s) */
799 switch (surface_type
) {
801 ret
= egl_manager_create_window(eman
, win_title
, winWidth
, winHeight
,
802 EGL_TRUE
, fullscreen
, NULL
);
804 ret
= eglMakeCurrent(eman
->dpy
, eman
->win
, eman
->win
, eman
->ctx
);
807 case GEARS_PIXMAP_TEXTURE
:
808 ret
= (egl_manager_create_window(eman
, win_title
, winWidth
, winHeight
,
809 EGL_TRUE
, fullscreen
, NULL
) &&
810 egl_manager_create_pixmap(eman
, eman
->xwin
,
812 if (surface_type
== GEARS_PIXMAP_TEXTURE
)
813 eman
->image
= eglCreateImageKHR (eman
->dpy
, eman
->ctx
,
814 EGL_NATIVE_PIXMAP_KHR
,
815 (EGLClientBuffer
) eman
->xpix
, NULL
);
817 ret
= eglMakeCurrent(eman
->dpy
, eman
->pix
, eman
->pix
, eman
->ctx
);
820 case GEARS_PBUFFER_TEXTURE
:
822 EGLint pbuf_attribs
[] = {
824 EGL_HEIGHT
, winHeight
,
825 EGL_TEXTURE_FORMAT
, EGL_TEXTURE_RGB
,
826 EGL_TEXTURE_TARGET
, EGL_TEXTURE_2D
,
829 ret
= (egl_manager_create_window(eman
, win_title
, winWidth
, winHeight
,
830 EGL_TRUE
, fullscreen
, NULL
) &&
831 egl_manager_create_pixmap(eman
, eman
->xwin
,
833 egl_manager_create_pbuffer(eman
, pbuf_attribs
));
835 ret
= eglMakeCurrent(eman
->dpy
, eman
->pbuf
, eman
->pbuf
, eman
->ctx
);
843 switch (surface_type
) {
844 case GEARS_PIXMAP_TEXTURE
:
845 glGenTextures(1, &texture
);
846 glBindTexture(GL_TEXTURE_2D
, texture
);
847 glEGLImageTargetTexture2DOES(GL_TEXTURE_2D
, eman
->image
);
849 case GEARS_PBUFFER_TEXTURE
:
850 glGenTextures(1, &texture
);
851 glBindTexture(GL_TEXTURE_2D
, texture
);
856 egl_manager_destroy(eman
);
857 XCloseDisplay(x_dpy
);
862 printf("GL_RENDERER = %s\n", (char *) glGetString(GL_RENDERER
));
863 printf("GL_VERSION = %s\n", (char *) glGetString(GL_VERSION
));
864 printf("GL_VENDOR = %s\n", (char *) glGetString(GL_VENDOR
));
869 /* Set initial projection/viewing transformation.
870 * We can't be sure we'll get a ConfigureNotify event when the window
873 reshape(winWidth
, winHeight
);
875 event_loop(eman
, surface_type
, winWidth
, winHeight
);
877 glDeleteLists(gear1
, 1);
878 glDeleteLists(gear2
, 1);
879 glDeleteLists(gear3
, 1);
881 egl_manager_destroy(eman
);
882 XCloseDisplay(x_dpy
);