Merge lp:~ahmed-a-ammar/pigment/pigment-gles2 into lp:~loic.molinari/pigment/trunk

Proposed by Ahmed Ammar
Status: Needs review
Proposed branch: lp:~ahmed-a-ammar/pigment/pigment-gles2
Merge into: lp:~loic.molinari/pigment/trunk
Diff against target: 1362 lines (+1077/-25)
9 files modified
ChangeLog (+15/-0)
configure.ac (+48/-3)
src/pgm/gst/pgm-gst-image.c (+77/-13)
src/renderers/opengles/Makefile.am (+49/-1)
src/renderers/opengles/backend-native.c (+22/-1)
src/renderers/opengles/backend-x11.c (+26/-5)
src/renderers/opengles/plugin-opengles2.c (+838/-0)
tests/manual/test-geometry-sorting.c (+1/-1)
tests/manual/test-gst-image.c (+1/-1)
To merge this branch: bzr merge lp:~ahmed-a-ammar/pigment/pigment-gles2
Reviewer Review Type Date Requested Status
Loïc Molinari Pending
Review via email: mp+25630@code.launchpad.net
To post a comment you must log in.

Unmerged revisions

255. By Ahmed Ammar

  * configure.ac:
  * src/pgm/gst/pgm-gst-image.c:
  * src/renderers/opengles/Makefile.am:
  * src/renderers/opengles/backend-native.c:
  * src/renderers/opengles/backend-x11.c:
  * src/renderers/opengles/plugin-opengles2.c:
  Implementation for OpenGL ES 2 renderer. Currently supports three texture
  units and no lights.

  * tests/manual/test-geometry-sorting.c:
  * tests/manual/test-gst-image.c:
  Modified tests to use auto renderer selection.

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'ChangeLog'
2--- ChangeLog 2010-05-19 16:53:41 +0000
3+++ ChangeLog 2010-05-19 17:34:31 +0000
4@@ -1,3 +1,18 @@
5+2010-05-19 Ahmed Ammar <ahmed.ammar@connectmetv.com>
6+
7+ * configure.ac:
8+ * src/pgm/gst/pgm-gst-image.c:
9+ * src/renderers/opengles/Makefile.am:
10+ * src/renderers/opengles/backend-native.c:
11+ * src/renderers/opengles/backend-x11.c:
12+ * src/renderers/opengles/plugin-opengles2.c:
13+ Implementation for OpenGL ES 2 renderer. Currently supports three texture
14+ units and no lights.
15+
16+ * tests/manual/test-geometry-sorting.c:
17+ * tests/manual/test-gst-image.c:
18+ Modified tests to use auto renderer selection.
19+
20 2010-05-19 Loïc Molinari <loic@fluendo.com>
21
22 Patch by: Ahmed Ammar <ahmed.ammar@connectmetv.com>
23
24=== modified file 'configure.ac'
25--- configure.ac 2010-05-10 10:09:50 +0000
26+++ configure.ac 2010-05-19 17:34:31 +0000
27@@ -247,6 +247,8 @@
28
29 AC_CHECK_HEADERS([GLES/egl.h], [HAVE_EGL=yes], [HAVE_EGL=no])
30 AC_CHECK_HEADERS([GLES/gl.h], [HAVE_GLES=yes], [HAVE_GLES=no])
31+AC_CHECK_HEADERS([GLES2/gl2.h], [HAVE_GLES2=yes], [HAVE_GLES2=no])
32+AC_CHECK_HEADERS([EGL/egl.h], [HAVE_EGL2=yes], [HAVE_EGL2=no])
33
34 AC_ARG_ENABLE(opengles1-gdl,
35 AS_HELP_STRING([--enable-opengles1-gdl],[enable build of OpenGL ES 1 renderer using Intel GDL backend]),
36@@ -270,6 +272,38 @@
37 ],
38 [ENABLE_OPENGLES1_X11=no])
39
40+AC_ARG_ENABLE(opengles2-x11,
41+ AC_HELP_STRING([--enable-opengles2-x11], [enable build of OpenGL ES 2 renderer using X11 backend]),
42+ [
43+ case "${enableval}" in
44+ yes) ENABLE_OPENGLES2_X11=yes ;;
45+ no) ENABLE_OPENGLES2_X11=no ;;
46+ *) AC_MSG_ERROR(bad value ${enableval} for --enable-opengles2-x11) ;;
47+ esac
48+ ],
49+ [ENABLE_OPENGLES2_X11=no])
50+
51+if test x$HAVE_EGL2 = xyes -a x$HAVE_GLES2 = xyes; then
52+ if test x$ENABLE_OPENGLES2_X11 = xyes -a x$HAVE_X11 = xyes; then
53+ AC_DEFINE([HAVE_EGL2_X11], [1],
54+ [Defined to 1 if the OpenGL ES 2 renderer uses the X11 backend])
55+ HAVE_OPENGLES2_PLUGIN="yes"
56+ OPENGLES2_BACKEND="(X11 backend)"
57+ PGM_GLES2_CFLAGS="$XLIB_CFLAG $GLIB_CFLAGS"
58+ PGM_GLES2_LIBS="$XLIB_LIBS $GLIB_LIBS -lGLESv2 -lEGL"
59+ else
60+ AC_DEFINE([HAVE_EGL2_NATIVE], [1],
61+ [Defined to 1 if the OpenGL ES 2 renderer uses the native backend])
62+ HAVE_OPENGLES2_PLUGIN="yes"
63+ OPENGLES2_BACKEND="(native backend)"
64+ PGM_GLES2_CFLAGS="$GLIB_CFLAGS"
65+ PGM_GLES2_LIBS="$GLIB_LIBS -lGLESv2 -lEGL"
66+ fi
67+else
68+ HAVE_OPENGLES2_PLUGIN="no"
69+ OPENGLES2_BACKEND=""
70+fi
71+
72 if test x$HAVE_EGL = xyes -a x$HAVE_GLES = xyes; then
73 if test x$ENABLE_OPENGLES1_GDL = xyes; then
74 AC_CHECK_HEADERS([libgdl.h], [HAVE_GDL=yes], [HAVE_GDL=no])
75@@ -290,8 +324,8 @@
76 [Defined to 1 if the OpenGL ES 1 renderer uses the X11 backend])
77 HAVE_OPENGLES1_PLUGIN="yes"
78 OPENGLES1_BACKEND="(X11 backend)"
79- PGM_GLES1_CFLAGS="$GLIB_CFLAGS"
80- PGM_GLES1_LIBS="$GLIB_LIBS -lGLES_CM"
81+ PGM_GLES1_CFLAGS="$XLIB_LIBS $GLIB_CFLAGS"
82+ PGM_GLES1_LIBS="$XLIB_LIBS $GLIB_LIBS -lGLES_CM -lEGL"
83 else
84 HAVE_OPENGLES1_PLUGIN="no"
85 OPENGLES1_BACKEND=""
86@@ -302,7 +336,7 @@
87 HAVE_OPENGLES1_PLUGIN="yes"
88 OPENGLES1_BACKEND="(native backend)"
89 PGM_GLES1_CFLAGS="$GLIB_CFLAGS"
90- PGM_GLES1_LIBS="$GLIB_LIBS -lGLES_CM"
91+ PGM_GLES1_LIBS="$GLIB_LIBS -lGLES_CM -lEGL"
92 fi
93 else
94 HAVE_OPENGLES1_PLUGIN="no"
95@@ -313,9 +347,19 @@
96 AC_SUBST(HAVE_OPENGLES1_PLUGIN)
97 AC_SUBST(PGM_GLES1_CFLAGS)
98 AC_SUBST(PGM_GLES1_LIBS)
99+
100+AC_SUBST(OPENGLES2_BACKEND)
101+AC_SUBST(HAVE_OPENGLES2_PLUGIN)
102+AC_SUBST(PGM_GLES2_CFLAGS)
103+AC_SUBST(PGM_GLES2_LIBS)
104+
105 AM_CONDITIONAL(HAVE_OPENGLES1_PLUGIN_COND, test x$HAVE_OPENGLES1_PLUGIN = xyes)
106+AM_CONDITIONAL(HAVE_OPENGLES2_PLUGIN_COND, test x$HAVE_OPENGLES2_PLUGIN = xyes)
107+AM_CONDITIONAL(HAVE_OPENGLES_PLUGIN_COND, test x$HAVE_OPENGLES2_PLUGIN = xyes -o x$HAVE_OPENGLES1_PLUGIN = xyes )
108 AM_CONDITIONAL(HAVE_EGL_GDL_COND, test x$HAVE_EGL = xyes -a x$HAVE_GLES = xyes -a x$ENABLE_OPENGLES1_GDL = xyes)
109 AM_CONDITIONAL(HAVE_EGL_X11_COND, test x$HAVE_EGL = xyes -a x$HAVE_GLES = xyes -a x$ENABLE_OPENGLES1_X11 = xyes)
110+AM_CONDITIONAL(HAVE_EGL2_X11_COND, test x$HAVE_EGL2 = xyes -a x$HAVE_GLES2 = xyes -a x$ENABLE_OPENGLES2_X11 = xyes)
111+AM_CONDITIONAL(HAVE_EGL2_NATIVE_COND, test x$HAVE_EGL2 = xyes -a x$HAVE_GLES2 = xyes -a x$ENABLE_OPENGLES2_X11 = xno)
112 AM_CONDITIONAL(HAVE_EGL_NATIVE_COND, test x$HAVE_EGL = xyes -a x$HAVE_GLES = xyes -a x$ENABLE_OPENGLES1_X11 = xno -a x$ENABLE_OPENGLES1_GDL = xno)
113
114 # *** Documentation ***
115@@ -448,6 +492,7 @@
116 echo " 3D graphics engine: yes"
117 echo " OpenGL renderer: ${HAVE_OPENGL_PLUGIN} ${OPENGL_BACKEND}"
118 echo " OpenGL ES 1 renderer: ${HAVE_OPENGLES1_PLUGIN} ${OPENGLES1_BACKEND}"
119+echo " OpenGL ES 2 renderer: ${HAVE_OPENGLES2_PLUGIN} ${OPENGLES2_BACKEND}"
120 echo " GUI classes: ${HAVE_GUI_CLASSES}"
121 echo " GStreamer classes: ${HAVE_GST_CLASSES}"
122 echo " GTK+ classes: ${HAVE_GTK_CLASSES}"
123
124=== modified file 'src/pgm/gst/pgm-gst-image.c'
125--- src/pgm/gst/pgm-gst-image.c 2009-11-30 18:52:29 +0000
126+++ src/pgm/gst/pgm-gst-image.c 2010-05-19 17:34:31 +0000
127@@ -17,6 +17,7 @@
128 *
129 * Contributor(s):
130 * Loïc Molinari <loic@fluendo.com>
131+ * Ahmed Ammar <ahmed.ammar@connecmetv.com>
132 */
133
134 /**
135@@ -47,10 +48,12 @@
136 static void pgm_gst_image_map (PgmNode*, PgmRenderer*, gfloat, gfloat);
137 static void pgm_gst_image_unmap (PgmNode*);
138
139-/* OpenGL ARB fragment program to convert from YV12/I420 planar YCbCr to RGB
140- * color space using coefficients from the ITU-R BT.601 standard for SDTV and
141- * the equations detailed in the book "Video Demystified, 4th Edition" */
142-static const gchar *ycbcr2rgb_bt601_fp =
143+/* Shaders converting from YV12/I420 planar YCbCr to RGB color space using
144+ * coefficients from the ITU-R BT.601 standard for SDTV and the equations
145+ * detailed in the book "Video Demystified, 4th Edition" */
146+
147+/* OpenGL ARB fragment program */
148+static const gchar *ycbcr2rgb_bt601_glarbfp =
149 "!!ARBfp1.0"
150 "OPTION ARB_precision_hint_fastest;"
151 "ATTRIB position = fragment.texcoord[0];"
152@@ -65,12 +68,52 @@
153 "MUL result.color, fragment.color, color;"
154 "END";
155
156+/* OpenGL ES 2 shaders */
157+static const gchar *ycbcr2rgb_bt601_glslesvp =
158+ "uniform mat4 pgm_projection;\n"
159+ "uniform mat4 pgm_modelview;\n"
160+ "attribute highp vec4 pgm_position;\n"
161+ "attribute highp vec4 pgm_color;\n"
162+ "attribute highp vec4 pgm_texcoord;\n"
163+ "varying highp vec2 frag_texcoord;\n"
164+ "varying highp vec4 frag_color;\n"
165+ "void main() {\n"
166+ " frag_texcoord = pgm_texcoord.xy;\n"
167+ " frag_color = pgm_color/255.0;\n"
168+ " gl_Position = pgm_projection * pgm_modelview * pgm_position;\n"
169+ "}\n";
170+static const gchar *ycbcr2rgb_bt601_glslesfp =
171+ "uniform sampler2D pgm_texture0;\n"
172+ "uniform sampler2D pgm_texture1;\n"
173+ "uniform sampler2D pgm_texture2;\n"
174+ "varying highp vec2 frag_texcoord;\n"
175+ "varying lowp vec4 frag_color;\n"
176+ "void main() {"
177+ " const lowp vec4 kcr = vec4( 1.596, -0.813, 0, 0 );\n"
178+ " const lowp vec4 kcb = vec4( 0, -0.391, 2.018, 0 );\n"
179+ " const lowp vec4 kadj = vec4( -0.871, 0.53, -1.082, 0 );\n"
180+ " lowp float y = texture2D(pgm_texture0, frag_texcoord).x;\n"
181+ " lowp float cb = texture2D(pgm_texture1, frag_texcoord).x;\n"
182+ " lowp float cr = texture2D(pgm_texture2, frag_texcoord).x;\n"
183+ " lowp vec4 color = vec4(y * 1.164);\n"
184+ " color += kcr * cr;\n"
185+ " color += kcb * cb;\n"
186+ " color += kadj;\n"
187+ " gl_FragColor = vec4(color.r, color.g, color.b, 1.0);\n"
188+ "}\n";
189+
190 /* Image negociated format */
191-typedef enum {
192+enum {
193 IMAGE_NOT_NEGOCIATED = 0,
194 IMAGE_RGB,
195 IMAGE_YCBCR
196-} ImageNegociatedFormat;
197+};
198+
199+/* Image available shading language */
200+enum {
201+ IMAGE_SHADING_LANGUAGE_ARBP = (1 << 0),
202+ IMAGE_SHADING_LANGUAGE_GLSLES = (1 << 1)
203+} ;
204
205 /* Private structure */
206 struct _PgmGstImagePimpl {
207@@ -86,6 +129,7 @@
208 gfloat texture_ratio;
209 PgmGstImageLayout layout;
210 guint8 negociated_format;
211+ guint8 shading_language;
212 };
213
214 /* GObject type definition */
215@@ -158,6 +202,7 @@
216 /* pimpl->texture_ratio = 0.0f; */
217 pimpl->layout = PGM_GST_IMAGE_SCALED;
218 /* pimpl->negociated_format = 0; */
219+ /* pimpl->shading_language = 0; */
220 }
221
222 /* Private functions */
223@@ -317,11 +362,18 @@
224 pgm_mesh_set_texture (pimpl->mesh, 1, cb);
225 pgm_mesh_set_texture (pimpl->mesh, 2, cr);
226
227- /* Since we checked the support for ARB fragment program support for the
228- * mapped renderer in the map virtual function, we can safely apply the
229- * color space conversion shader to the mesh */
230- shader = pgm_shader_new ("arbp", NULL, 0, NULL, 0, ycbcr2rgb_bt601_fp,
231- strlen (ycbcr2rgb_bt601_fp), 0);
232+ /* Since we checked the support for shaders for the mapped renderer in the
233+ * map virtual function, we can safely apply the color space conversion
234+ * shader to the mesh depending on the supported language */
235+ if (pimpl->shading_language & IMAGE_SHADING_LANGUAGE_ARBP)
236+ shader = pgm_shader_new ("arbp", NULL, 0, NULL, 0,
237+ ycbcr2rgb_bt601_glarbfp,
238+ strlen (ycbcr2rgb_bt601_glarbfp), 0);
239+ else
240+ shader = pgm_shader_new ("glsles", ycbcr2rgb_bt601_glslesvp,
241+ strlen (ycbcr2rgb_bt601_glslesvp), NULL, 0,
242+ ycbcr2rgb_bt601_glslesfp,
243+ strlen (ycbcr2rgb_bt601_glslesfp), 0);
244 pgm_mesh_set_shader (pimpl->mesh, shader);
245
246 /* Store the texture ratio, no need to check for a height of 0 since such a
247@@ -410,7 +462,20 @@
248 if (strcmp (sl->language, "arbp") == 0)
249 {
250 if (sl->programs | PGM_RENDERER_FRAGMENT_PROGRAM)
251- formats |= PGM_GST_BASE_YCBCR;
252+ {
253+ formats |= PGM_GST_BASE_YCBCR;
254+ pimpl->shading_language = IMAGE_SHADING_LANGUAGE_ARBP;
255+ }
256+ break;
257+ }
258+ else if (strcmp (sl->language, "glsles") == 0)
259+ {
260+ if (sl->programs | PGM_RENDERER_FRAGMENT_PROGRAM
261+ && sl->programs | PGM_RENDERER_VERTEX_PROGRAM)
262+ {
263+ formats |= PGM_GST_BASE_YCBCR;
264+ pimpl->shading_language = IMAGE_SHADING_LANGUAGE_GLSLES;
265+ }
266 break;
267 }
268 walk = walk->next;
269@@ -536,7 +601,6 @@
270 /* Set up the initial average position */
271 pgm_mesh_set_average_position (pimpl->mesh, x + pimpl->width * 0.5f,
272 y + pimpl->height * 0.5f, z);
273-
274 return PGM_NODE (image);
275 }
276
277
278=== modified file 'src/renderers/opengles/Makefile.am'
279--- src/renderers/opengles/Makefile.am 2009-11-04 17:50:39 +0000
280+++ src/renderers/opengles/Makefile.am 2010-05-19 17:34:31 +0000
281@@ -1,7 +1,18 @@
282-if HAVE_OPENGLES1_PLUGIN_COND
283+if HAVE_OPENGLES_PLUGIN_COND
284
285 plugindir = @PLUGIN_PATH@
286+
287+if HAVE_OPENGLES1_PLUGIN_COND
288+if HAVE_OPENGLES2_PLUGIN_COND
289+plugin_LTLIBRARIES = libpgmopengles1.la libpgmopengles2.la
290+else
291 plugin_LTLIBRARIES = libpgmopengles1.la
292+endif
293+else
294+plugin_LTLIBRARIES = libpgmopengles2.la
295+endif
296+
297+if HAVE_OPENGLES1_PLUGIN_COND
298
299 libpgmopengles1_la_DEPENDENCIES = \
300 $(top_builddir)/src/pgm/libpigment-@PGM_MAJORMINOR@.la
301@@ -39,3 +50,40 @@
302 noinst_HEADERS = backend.h
303
304 endif
305+
306+if HAVE_OPENGLES2_PLUGIN_COND
307+
308+
309+libpgmopengles2_la_DEPENDENCIES = \
310+ $(top_builddir)/src/pgm/libpigment-@PGM_MAJORMINOR@.la
311+
312+if HAVE_EGL2_NATIVE_COND
313+libpgmopengles2_la_SOURCES = \
314+ plugin-opengles2.c \
315+ backend-native.c
316+endif
317+if HAVE_EGL2_X11_COND
318+libpgmopengles2_la_SOURCES = \
319+ plugin-opengles2.c \
320+ backend-x11.c
321+endif
322+
323+# egl.h contains non-strictly prototyped function declarations
324+libpgmopengles2_la_CFLAGS = \
325+ -I$(top_srcdir)/src -DHAVE_GLES2 \
326+ $(PGM_CFLAGS) -Wno-strict-prototypes \
327+ $(PGM_GLES2_CFLAGS)
328+
329+libpgmopengles2_la_LIBADD = \
330+ $(top_builddir)/src/pgm/libpigment-@PGM_MAJORMINOR@.la \
331+ $(PGM_GLES2_LIBS)
332+
333+libpgmopengles2_la_LDFLAGS = $(PGM_PLUGIN_LDFLAGS)
334+
335+libpgmopengles2_la_LIBTOOLFLAGS = --tag=disable-static
336+
337+noinst_HEADERS = backend.h
338+
339+endif
340+
341+endif
342
343=== modified file 'src/renderers/opengles/backend-native.c'
344--- src/renderers/opengles/backend-native.c 2010-05-11 08:42:10 +0000
345+++ src/renderers/opengles/backend-native.c 2010-05-19 17:34:31 +0000
346@@ -17,6 +17,7 @@
347 *
348 * Contributor(s):
349 * Loïc Molinari <loic@fluendo.com>
350+ * Ahmed Ammar <ahmed.ammar@connectmetv.com>
351 */
352
353 #ifdef HAVE_CONFIG_H
354@@ -24,7 +25,12 @@
355 #endif /* HAVE_CONFIG_H */
356
357 #include "backend.h"
358+
359+#ifdef HAVE_GLES2
360+#include <EGL/egl.h>
361+#else
362 #include <GLES/egl.h>
363+#endif
364
365 /* Private structure */
366 typedef struct {
367@@ -87,9 +93,21 @@
368 EGL_GREEN_SIZE, 6,
369 EGL_BLUE_SIZE, 5,
370 EGL_DEPTH_SIZE, 16,
371+#ifdef HAVE_GLES2
372+ EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT,
373+#else
374 EGL_RENDERABLE_TYPE, EGL_OPENGL_ES_BIT,
375+#endif
376 EGL_NONE
377 };
378+
379+ const EGLint context_attribs[] = {
380+#ifdef HAVE_GLES2
381+ EGL_CONTEXT_CLIENT_VERSION, 2,
382+#endif
383+ EGL_NONE
384+ };
385+
386 const gchar *version, *vendor, *extensions;
387 BackendNative *native;
388 EGLConfig config;
389@@ -106,6 +124,9 @@
390 PGM_ERROR_OBJECT (native->rdr, "can't open default display");
391 return NULL;
392 }
393+
394+ eglBindAPI(EGL_OPENGL_ES_API);
395+
396 if (eglInitialize (native->dpy, NULL, NULL) == EGL_FALSE)
397 {
398 print_egl_error (native->rdr, "eglInitialize");
399@@ -142,7 +163,7 @@
400 return NULL;
401 }
402 native->context = eglCreateContext (native->dpy, config,
403- EGL_NO_CONTEXT, NULL);
404+ EGL_NO_CONTEXT, context_attribs);
405 if (native->context == EGL_NO_CONTEXT)
406 {
407 print_egl_error (native->rdr, "eglCreateContext");
408
409=== modified file 'src/renderers/opengles/backend-x11.c'
410--- src/renderers/opengles/backend-x11.c 2010-05-11 08:42:10 +0000
411+++ src/renderers/opengles/backend-x11.c 2010-05-19 17:34:31 +0000
412@@ -17,6 +17,7 @@
413 *
414 * Contributor(s):
415 * Loïc Molinari <loic@fluendo.com>
416+ * Ahmed Ammar <ahmed.ammar@connectmetv.com>
417 */
418
419 #ifdef HAVE_CONFIG_H
420@@ -25,7 +26,11 @@
421
422 #include "backend.h"
423 #include <string.h> /* memset */
424+#ifdef HAVE_GLES2
425+#include <EGL/egl.h>
426+#else
427 #include <GLES/egl.h>
428+#endif
429 #include <X11/Xlib.h>
430 #include <X11/Xutil.h>
431 #include <X11/Xatom.h>
432@@ -643,8 +648,19 @@
433 EGL_GREEN_SIZE, 8,
434 EGL_BLUE_SIZE, 8,
435 EGL_DEPTH_SIZE, 0,
436+#ifdef HAVE_GLES2
437+ EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT,
438+#endif
439 EGL_NONE
440 };
441+
442+ const EGLint context_attribs[] = {
443+#ifdef HAVE_GLES2
444+ EGL_CONTEXT_CLIENT_VERSION, 2,
445+#endif
446+ EGL_NONE
447+ };
448+
449 const gchar *version, *vendor, *extensions;
450 BackendX11 *x11;
451 EGLConfig config;
452@@ -670,6 +686,9 @@
453 g_slice_free1 (sizeof (BackendX11), x11);
454 return NULL;
455 }
456+
457+ eglBindAPI(EGL_OPENGL_ES_API);
458+
459 if (eglInitialize (x11->egldpy, NULL, NULL) == EGL_FALSE)
460 {
461 print_egl_error (x11->rdr, "eglInitialize");
462@@ -709,7 +728,8 @@
463 g_slice_free1 (sizeof (BackendX11), x11);
464 return NULL;
465 }
466- x11->context = eglCreateContext (x11->egldpy, config, EGL_NO_CONTEXT, NULL);
467+ x11->context = eglCreateContext (x11->egldpy, config,
468+ EGL_NO_CONTEXT, context_attribs);
469 if (x11->context == EGL_NO_CONTEXT)
470 {
471 print_egl_error (x11->rdr, "eglCreateContext");
472@@ -856,16 +876,17 @@
473 {
474 case PGM_RENDERER_LEFT_ARROW:
475 XDefineCursor (x11->dpy, x11->win, XCreateFontCursor
476- (x11->dpy, XC_top_left_arrow));
477+ (x11->dpy, XC_left_ptr));
478 break;
479
480 case PGM_RENDERER_INHERIT:
481 XDefineCursor (x11->dpy, x11->win, XCreateFontCursor
482- (x11->dpy, XC_top_left_arrow));
483+ (x11->dpy, XC_left_ptr));
484 break;
485
486- case PGM_RENDERER_NONE:
487- XDefineCursor (x11->dpy, x11->win, x11->none_cursor);
488+ case PGM_RENDERER_FLEUR:
489+ XDefineCursor (x11->dpy, x11->win,
490+ XCreateFontCursor (x11->dpy, XC_fleur));
491 break;
492
493 default:
494
495=== added file 'src/renderers/opengles/plugin-opengles2.c'
496--- src/renderers/opengles/plugin-opengles2.c 1970-01-01 00:00:00 +0000
497+++ src/renderers/opengles/plugin-opengles2.c 2010-05-19 17:34:31 +0000
498@@ -0,0 +1,838 @@
499+/*
500+ * Pigment 3D graphics engine
501+ * Rendering plugin based on OpenGL ES 1
502+ *
503+ * Copyright © 2006-2010 Fluendo Embedded S.L.
504+ *
505+ * This library is free software; you can redistribute it and/or modify it under
506+ * the terms of the GNU Lesser General Public License as published by the Free
507+ * Software Foundation; either version 2 of the License, or (at your option) any
508+ * later version. This library is distributed in the hope that it will be
509+ * useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
510+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser
511+ * General Public License for more details. You should have received a copy of
512+ * the GNU Lesser General Public License along with this library; if not, write
513+ * to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
514+ * MA 02111-1307, USA.
515+ *
516+ * Contributor(s):
517+ * Loïc Molinari <loic@fluendo.com>
518+ * Ahmed Ammar <ahmed.ammar@connecmetv.com>
519+ */
520+
521+#ifdef HAVE_CONFIG_H
522+#include "config.h"
523+#endif /* HAVE_CONFIG_H */
524+
525+#include "backend.h"
526+#include <string.h> /* strlen */
527+#include <ctype.h> /* isdigit */
528+#include <stdio.h>
529+#include <stdlib.h>
530+#include <sys/ioctl.h>
531+#include <sys/mman.h>
532+#include <fcntl.h>
533+
534+#define GL_GLEXT_PROTOTYPES
535+#include <GLES2/gl2.h>
536+#include <GLES2/gl2ext.h>
537+#undef GL_GLEXT_PROTOTYPES
538+
539+/* Extension constants */
540+enum {
541+ EXT_BGRA = 0x80e1,
542+ EXT_MIRRORED_REPEAT = 0x8370
543+};
544+
545+/* Extension flags */
546+enum {
547+ FLAG_TEXTURE_FORMAT_BGRA8888 = (1 << 0) ,
548+ FLAG_TEXTURE_STREAM = (1 << 1)
549+/* FLAG_BLEND_FUNC_SEPARATE = (1 << 1) */
550+};
551+
552+/* OpenGL ES 2 attributes */
553+enum {
554+ PGM_APOSITION = 0,
555+ PGM_ACOLOR = 1,
556+ PGM_ATEXCOORD = 2,
557+};
558+
559+/* IMG texture stream structure */
560+typedef struct {
561+ int number;
562+ int width;
563+ int height;
564+ int format;
565+} PluginOpengles2TextureBuffer;
566+
567+/* OpenGL ES 2 vertex shader */
568+static const gchar *default_glslesvp =
569+ "uniform mat4 pgm_projection;\n"
570+ "uniform mat4 pgm_modelview;\n"
571+ "attribute highp vec4 pgm_position;\n"
572+ "attribute mediump vec4 pgm_color;\n"
573+ "attribute mediump vec4 pgm_texcoord;\n"
574+ "varying mediump vec2 frag_texcoord;\n"
575+ "varying mediump vec4 frag_color;\n"
576+ "void main() {\n"
577+ " frag_texcoord = pgm_texcoord.xy;\n"
578+ " frag_color = pgm_color/255.0;\n"
579+ " gl_Position = pgm_projection * pgm_modelview * pgm_position;\n"
580+ "}\n";
581+static const gchar *default_glslesfp =
582+ "uniform sampler2D pgm_texture0;\n"
583+ "varying mediump vec2 frag_texcoord;\n"
584+ "varying mediump vec4 frag_color;\n"
585+ "void main() {\n"
586+ " highp vec4 tex0 = texture2D(pgm_texture0, frag_texcoord);\n"
587+ " gl_FragColor.rgb = frag_color.rgb + tex0.rgb;\n"
588+ " gl_FragColor.a = frag_color.a * tex0.a;\n"
589+ "}\n";
590+
591+/* Wrapper for the opaque PgmPluginTexture pointer */
592+typedef struct {
593+ GLenum type;
594+ GLenum format;
595+ GLuint id;
596+ gfloat sx;
597+ gfloat sy;
598+ guint16 width;
599+ guint16 height;
600+ guint16 miplevels;
601+} PluginOpengles2Texture;
602+
603+/* Wrapper for the opaque PgmPluginShader type */
604+typedef struct {
605+ GLuint vert_index, frag_index, prog_index;
606+ GLint proj_index, modelview_index;
607+ GLint texture0_index, texture1_index, texture2_index;
608+} PluginOpengles2Shader;
609+
610+/* IMG texture stream functions */
611+typedef void (*glGetTexAttrFunc) (GLenum target, GLenum pname, GLint *params);
612+typedef void (*glTexBindStreamFunc) (GLint device, GLint deviceoffset);
613+typedef const GLubyte *(*glGetTexDeviceFunc) (GLenum target);
614+
615+/* Extension functions */
616+typedef struct {
617+ /* IMG texture stream functions */
618+ glTexBindStreamFunc glTexBindStreamIMG;
619+ glGetTexAttrFunc glGetTexAttrIMG;
620+ glGetTexDeviceFunc glGetTexDeviceIMG;
621+} Opengles2ExtensionFunctions;
622+
623+/* Wrapper for the opaque PgmPlugin pointer */
624+typedef struct {
625+ PgmPluginFuncs *funcs;
626+ PgmRendererCapabilities *caps;
627+ PluginOpengles2Texture *default_texture;
628+ PgmRenderer *rdr;
629+ Backend *backend;
630+ PluginOpengles2Texture *texture;
631+ gint32 max_texture_units;
632+ guint8 extension_flags;
633+ /* GLES2 shader variables */
634+ PluginOpengles2Shader *shader;
635+ GLfloat *proj_mat, *modelview_mat;
636+} PluginOpengles2;
637+
638+/* Texture target look-up table */
639+static const GLenum texture_target[] = {
640+ GL_TEXTURE_2D, /* PGM_TEXTURE_2D */
641+ 0 /* PGM_TEXTURE_CUBE */ /* Not supported */
642+};
643+
644+/* Texture format look-up table */
645+static const GLenum texture_format[] = {
646+ GL_LUMINANCE, /* PGM_TEXTURE_L8 */
647+ GL_LUMINANCE_ALPHA, /* PGM_TEXTURE_L8A8 */
648+ GL_RGB, /* PGM_TEXTURE_R8G8B8 */
649+ GL_RGB, /* PGM_TEXTURE_B8G8R8 */ /* Not supported */
650+ GL_RGBA, /* PGM_TEXTURE_R8G8B8A8 */
651+ GL_RGBA /* PGM_TEXTURE_B8G8R8A8 */ /* Not supported */
652+};
653+
654+/* Plugin functions */
655+static void
656+set_sync_to_vblank (PluginOpengles2 *plugin,
657+ gboolean sync)
658+{
659+ backend_set_sync_to_vblank (plugin->backend, sync);
660+}
661+
662+static void
663+wait_for_vblank (PluginOpengles2 *plugin)
664+{
665+ backend_wait_for_vblank (plugin->backend);
666+}
667+
668+static void
669+clear_buffers (PluginOpengles2 *plugin,
670+ PgmPluginClearBuffer flags)
671+{
672+ /* Stencil buffer's not used in Pigment, but graphics hardware stores depth
673+ * and stencil information in the same buffer so for best performance it's
674+ * recommended that both depth and stencil be cleared together. As a side
675+ * note, in the old times filling pixels was expensive and avoided as best
676+ * as possible using convoluted tricks, nowadays this is not true anymore.
677+ * Modern cards now support buffer compression and fast clearing of buffers
678+ * using a constant color. More informations can be found in GPU
679+ * manufacturer's architecture and performance papers. */
680+
681+ /* FIXME: Is that valid for embedded GPUs? */
682+
683+ const GLbitfield mask[] = {
684+ 0,
685+ GL_COLOR_BUFFER_BIT,
686+ GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT,
687+ GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT
688+ };
689+ glClear (mask[flags]);
690+}
691+
692+static void
693+set_clear_color (PluginOpengles2 *plugin,
694+ PgmVec4 *color)
695+{
696+ glClearColor (color->v[0], color->v[1], color->v[2], color->v[3]);
697+}
698+
699+static void
700+set_viewport (PluginOpengles2 *plugin,
701+ gint32 x,
702+ gint32 y,
703+ gint32 width,
704+ gint32 height)
705+{
706+ glViewport (x, y, width, height);
707+}
708+
709+static void
710+set_projection_matrix (PluginOpengles2 *plugin,
711+ PgmMat4x4 *matrix)
712+{
713+ const GLfloat transpose[16] = {
714+ matrix->m[0], matrix->m[4], matrix->m[8], matrix->m[12],
715+ matrix->m[1], matrix->m[5], matrix->m[9], matrix->m[13],
716+ matrix->m[2], matrix->m[6], matrix->m[10], matrix->m[14],
717+ matrix->m[3], matrix->m[7], matrix->m[11], matrix->m[15]
718+ };
719+
720+ memcpy(plugin->proj_mat, transpose, 16*sizeof(GLfloat));
721+ glUniformMatrix4fv(plugin->shader->proj_index, 1, GL_FALSE, plugin->proj_mat);
722+}
723+
724+static void
725+set_modelview_matrix (PluginOpengles2 *plugin,
726+ PgmMat4x4 *matrix)
727+{
728+ const GLfloat transpose[16] = {
729+ matrix->m[0], matrix->m[4], matrix->m[8], matrix->m[12],
730+ matrix->m[1], matrix->m[5], matrix->m[9], matrix->m[13],
731+ matrix->m[2], matrix->m[6], matrix->m[10], matrix->m[14],
732+ matrix->m[3], matrix->m[7], matrix->m[11], matrix->m[15]
733+ };
734+
735+ memcpy(plugin->modelview_mat, transpose, 16*sizeof(GLfloat));
736+ glUniformMatrix4fv(plugin->shader->modelview_index, 1, GL_FALSE, plugin->modelview_mat);
737+}
738+
739+static void
740+draw_primitive (PluginOpengles2 *plugin,
741+ gpointer positions,
742+ PgmVertexBufferType position_type,
743+ guint8 position_size,
744+ gpointer colors,
745+ PgmVertexBufferType color_type,
746+ gpointer texcoords,
747+ PgmVertexBufferType texcoord_type,
748+ guint8 texcoord_size,
749+ guint16 *indices,
750+ PgmMeshPrimitiveType primitive_type,
751+ guint16 index_count)
752+{
753+ static const GLenum type[] = {
754+ 0, /* PGM_VERTEX_BUFFER_NONE */
755+ GL_BYTE, /* PGM_VERTEX_BUFFER_INT8 */
756+ GL_UNSIGNED_BYTE, /* PGM_VERTEX_BUFFER_UINT8 */
757+ GL_SHORT, /* PGM_VERTEX_BUFFER_INT16 */
758+ GL_UNSIGNED_SHORT, /* PGM_VERTEX_BUFFER_UINT16 */
759+ 0, /* PGM_VERTEX_BUFFER_INT32 */
760+ 0, /* PGM_VERTEX_BUFFER_UINT32 */
761+ GL_FLOAT /* PGM_VERTEX_BUFFER_FLOAT */
762+ };
763+ static const GLenum mode[] = {
764+ GL_LINES, /* PGM_MESH_LINE_LIST */
765+ GL_LINE_STRIP, /* PGM_MESH_LINE_STRIP */
766+ GL_TRIANGLES, /* PGM_MESH_TRIANGLE_LIST */
767+ GL_TRIANGLE_STRIP /* PGM_MESH_TRIANGLE_STRIP */
768+ };
769+
770+ glVertexAttribPointer(PGM_APOSITION, position_size, type[position_type], GL_FALSE, 0, positions);
771+ if (texcoord_type == PGM_VERTEX_BUFFER_NONE) {
772+ glEnableVertexAttribArray(PGM_ACOLOR);
773+ glVertexAttribPointer(PGM_ACOLOR, 4, type[color_type], GL_FALSE, 0, colors);
774+ glDrawElements (mode[primitive_type], index_count, GL_UNSIGNED_SHORT, indices);
775+ glDisableVertexAttribArray(PGM_ACOLOR);
776+ } else {
777+ glEnableVertexAttribArray(PGM_ATEXCOORD);
778+ glVertexAttribPointer(PGM_ATEXCOORD, texcoord_size, type[texcoord_type], GL_FALSE, 0, texcoords);
779+ glDrawElements (mode[primitive_type], index_count, GL_UNSIGNED_SHORT, indices);
780+ glDisableVertexAttribArray(PGM_ATEXCOORD);
781+ }
782+}
783+
784+static PgmPluginTexture
785+create_texture (PluginOpengles2 *plugin,
786+ PgmTextureTarget target,
787+ PgmTextureFormat format,
788+ guint16 width,
789+ guint16 height)
790+{
791+ PluginOpengles2Texture *texture = g_slice_new (PluginOpengles2Texture);
792+
793+ texture->type = texture_target[target];
794+ texture->format = texture_format[format];
795+ texture->width = width;
796+ texture->height = height;
797+ texture->miplevels = 0;
798+
799+ glGenTextures (1, &texture->id);
800+
801+ return (PgmPluginTexture) texture;
802+}
803+
804+static void
805+delete_textures (PluginOpengles2 *plugin,
806+ PluginOpengles2Texture **textures,
807+ guint16 count)
808+{
809+ guint32 i;
810+
811+ for (i = 0; i < count; i++)
812+ {
813+ glDeleteTextures (1, &textures[i]->id);
814+ g_slice_free (PluginOpengles2Texture, textures[i]);
815+ }
816+}
817+
818+static void
819+bind_texture (PluginOpengles2 *plugin,
820+ guint8 unit,
821+ PluginOpengles2Texture *texture)
822+{
823+ if (unit < plugin->max_texture_units)
824+ {
825+ glActiveTexture (GL_TEXTURE0 + unit);
826+ if (texture != NULL)
827+ glBindTexture (texture->type, texture->id);
828+ else
829+ glBindTexture (GL_TEXTURE_2D, 0);
830+ plugin->texture = texture;
831+ }
832+ else
833+ {
834+ PGM_WARN_OBJECT (plugin->rdr, "texture unit %d not available on "
835+ "that OpenGL ES 2 implementation", unit);
836+ }
837+}
838+
839+static void
840+upload_texture (PluginOpengles2 *plugin,
841+ guint16 miplevel,
842+ guint16 x_offset,
843+ guint16 y_offset,
844+ guint16 width,
845+ guint16 height,
846+ gpointer texels)
847+{
848+ PluginOpengles2Texture *tex = plugin->texture;
849+
850+ static int idx = 0;
851+ if (tex->miplevels & (1 << miplevel))
852+ {
853+ glTexSubImage2D (tex->type, miplevel, x_offset, y_offset, width,
854+ height, tex->format, GL_UNSIGNED_BYTE, texels);
855+ }
856+ else
857+ {
858+ glTexImage2D (tex->type, miplevel, tex->format, tex->width, tex->height,
859+ 0, tex->format, GL_UNSIGNED_BYTE, NULL);
860+ glTexSubImage2D (tex->type, miplevel, x_offset, y_offset, width, height,
861+ tex->format, GL_UNSIGNED_BYTE, texels);
862+ tex->miplevels |= 1 << miplevel;
863+ }
864+ }
865+
866+static void
867+set_texture_states (PluginOpengles2 *plugin,
868+ PgmTextureFilter min_filter,
869+ PgmTextureFilter mag_filter,
870+ PgmTextureFilter mip_filter,
871+ PgmTextureWrapping wrap_u,
872+ PgmTextureWrapping wrap_v)
873+{
874+ static const GLenum map[] = {
875+ 0, /* PGM_TEXTURE_NONE */
876+ GL_NEAREST, /* PGM_TEXTURE_NEAREST */
877+ GL_LINEAR, /* PGM_TEXTURE_LINEAR */
878+ GL_NEAREST_MIPMAP_NEAREST,
879+ GL_LINEAR_MIPMAP_NEAREST,
880+ GL_NEAREST_MIPMAP_LINEAR,
881+ GL_LINEAR_MIPMAP_LINEAR
882+ };
883+ static const GLenum wrap[] = {
884+ GL_CLAMP_TO_EDGE, /* PGM_PLUGIN_CLAMP */
885+ GL_CLAMP_TO_EDGE, /* PGM_PLUGIN_BORDER */
886+ GL_REPEAT, /* PGM_PLUGIN_REPEAT */
887+ EXT_MIRRORED_REPEAT /* PGM_PLUGIN_MIRROR */
888+ };
889+ const GLenum type = plugin->texture->type;
890+ glTexParameteri (type, GL_TEXTURE_MIN_FILTER, map[min_filter+mip_filter*2]);
891+ glTexParameteri (type, GL_TEXTURE_MAG_FILTER, map[mag_filter]);
892+ glTexParameteri (type, GL_TEXTURE_WRAP_S, wrap[wrap_u]);
893+ glTexParameteri (type, GL_TEXTURE_WRAP_T, wrap[wrap_v]);
894+}
895+
896+static PgmPluginShader
897+create_shader (PluginOpengles2 *plugin,
898+ const gchar *language,
899+ gpointer vertex_program,
900+ gsize vertex_program_size,
901+ gpointer geometry_program,
902+ gsize geometry_program_size,
903+ gpointer fragment_program,
904+ gsize fragment_program_size,
905+ PgmShaderUniformInfo *uniforms_info,
906+ guint8 uniforms_count)
907+{
908+ PluginOpengles2Shader *shader;
909+ gint error_position = 0;
910+ GLint success;
911+
912+ /* XXX Check language validity */
913+
914+ shader = g_slice_new (PluginOpengles2Shader);
915+
916+ shader->prog_index = glCreateProgram();
917+
918+ if ((vertex_program != NULL) || (fragment_program != NULL))
919+ {
920+ if (vertex_program != NULL)
921+ {
922+ PGM_INFO_OBJECT(plugin->rdr, "%s: creating new vertex shader\n", __func__);
923+ shader->vert_index = glCreateShader(GL_VERTEX_SHADER);
924+ glShaderSource(shader->vert_index, 1, (const char**) &vertex_program, (GLint *) &vertex_program_size);
925+ glCompileShader(shader->vert_index);
926+ glGetShaderiv(shader->vert_index, GL_COMPILE_STATUS, &success);
927+ if (!success) PGM_WARN_OBJECT (plugin->rdr, "%s: vertex shader compilation error\n", __func__);
928+ else glAttachShader(shader->prog_index, shader->vert_index);
929+ }
930+
931+ if (fragment_program != NULL)
932+ {
933+ PGM_INFO_OBJECT(plugin->rdr, "%s: creating new fragment shader\n", __func__);
934+ shader->frag_index = glCreateShader(GL_FRAGMENT_SHADER);
935+ glShaderSource(shader->frag_index, 1, (const char**) &fragment_program, (GLint *) &fragment_program_size);
936+ glCompileShader(shader->frag_index);
937+ glGetShaderiv(shader->frag_index, GL_COMPILE_STATUS, &success);
938+ if (!success) PGM_WARN_OBJECT (plugin->rdr, "%s: fragment shader compilation error\n", __func__);
939+ else glAttachShader(shader->prog_index, shader->frag_index);
940+ }
941+
942+ /* Bind attributes */
943+ glBindAttribLocation(shader->prog_index, PGM_APOSITION, "pgm_position");
944+ glBindAttribLocation(shader->prog_index, PGM_ACOLOR, "pgm_color");
945+ glBindAttribLocation(shader->prog_index, PGM_ATEXCOORD, "pgm_texcoord");
946+
947+ glLinkProgram(shader->prog_index);
948+ glGetProgramiv(shader->prog_index, GL_LINK_STATUS, &success);
949+ if (success)
950+ {
951+ glUseProgram(shader->prog_index);
952+ /* Get uniform locations */
953+ shader->proj_index = glGetUniformLocation(shader->prog_index, "pgm_projection");
954+ shader->modelview_index = glGetUniformLocation(shader->prog_index, "pgm_modelview");
955+
956+ shader->texture0_index = glGetUniformLocation(shader->prog_index,"pgm_texture0");
957+ glUniform1i(shader->texture0_index, 0);
958+ shader->texture1_index = glGetUniformLocation(shader->prog_index,"pgm_texture1");
959+ glUniform1i(shader->texture1_index, 1);
960+ shader->texture2_index = glGetUniformLocation(shader->prog_index,"pgm_texture2");
961+ glUniform1i(shader->texture2_index, 2);
962+ }
963+ else
964+ PGM_WARN_OBJECT (plugin->rdr, "program linking error\n");
965+ }
966+ return (PgmPluginShader) shader;
967+}
968+
969+static void
970+delete_shaders (PluginOpengles2 *plugin,
971+ PluginOpengles2Shader *shaders,
972+ guint16 count)
973+{
974+ guint32 i;
975+ for (i = 0; i < count; i++)
976+ {
977+ glDetachShader(shaders[i].prog_index, shaders[i].vert_index);
978+ glDetachShader(shaders[i].prog_index, shaders[i].frag_index);
979+ glDeleteProgram(shaders[i].prog_index);
980+ g_slice_free (PluginOpengles2Shader, &(shaders[i]));
981+ }
982+
983+}
984+
985+static void
986+bind_shader (PluginOpengles2 *plugin,
987+ PluginOpengles2Shader *shader)
988+{
989+ GLint success;
990+
991+ if (shader != NULL) {
992+ glUseProgram(shader->prog_index);
993+ glUniformMatrix4fv(plugin->shader->proj_index, 1, GL_FALSE, plugin->proj_mat);
994+ glUniformMatrix4fv(plugin->shader->modelview_index, 1, GL_FALSE, plugin->modelview_mat);
995+ }
996+ plugin->shader = shader;
997+}
998+
999+static void
1000+set_shader_uniforms (PluginOpengles2 *plugin,
1001+ PgmShaderUniformData *uniforms)
1002+{
1003+ /* Not used, we have some predefined uniforms, have a look at the default shaders */
1004+ PGM_INFO_OBJECT(plugin->rdr, "%s: set shader uniforms\n", __func__);
1005+}
1006+
1007+static void
1008+swap_buffers (PluginOpengles2 *plugin)
1009+{
1010+ backend_swap_buffers (plugin->backend);
1011+}
1012+
1013+static void
1014+get_screen_size (PluginOpengles2 *plugin,
1015+ guint32 *width,
1016+ guint32 *height)
1017+{
1018+ backend_get_screen_size (plugin->backend, width, height);
1019+}
1020+
1021+static void
1022+get_screen_resolution (PluginOpengles2 *plugin,
1023+ guint32 *width,
1024+ guint32 *height)
1025+{
1026+ backend_get_screen_resolution (plugin->backend, width, height);
1027+}
1028+
1029+static void
1030+set_window_title (PluginOpengles2 *plugin,
1031+ const gchar *title)
1032+{
1033+ backend_set_window_title (plugin->backend, title);
1034+}
1035+
1036+static void
1037+set_window_visible (PluginOpengles2 *plugin,
1038+ gboolean visible)
1039+{
1040+ backend_set_window_visible (plugin->backend, visible);
1041+}
1042+
1043+static void
1044+set_window_decorated (PluginOpengles2 *plugin,
1045+ gboolean decorated)
1046+{
1047+ backend_set_window_decorated (plugin->backend, decorated);
1048+}
1049+
1050+static void
1051+set_window_fullscreen (PluginOpengles2 *plugin,
1052+ gboolean fullscreen)
1053+{
1054+ backend_set_window_fullscreen (plugin->backend, fullscreen);
1055+}
1056+
1057+static void
1058+set_window_iconified (PluginOpengles2 *plugin,
1059+ gboolean iconified)
1060+{
1061+ backend_set_window_iconified (plugin->backend, iconified);
1062+}
1063+
1064+static void
1065+set_window_cursor (PluginOpengles2 *plugin,
1066+ PgmRendererCursor cursor)
1067+{
1068+ backend_set_window_cursor (plugin->backend, cursor);
1069+}
1070+
1071+/* static void */
1072+/* set_window_icon (PluginOpengles2 *plugin, */
1073+/* GdkPixbuf *icon) */
1074+/* { */
1075+/* backend_set_window_icon (plugin->backend, icon); */
1076+/* } */
1077+
1078+static void
1079+set_window_size (PluginOpengles2 *plugin,
1080+ guint32 width,
1081+ guint32 height)
1082+{
1083+ backend_set_window_size (plugin->backend, width, height);
1084+}
1085+
1086+static void
1087+set_window_message_filter (PluginOpengles2 *plugin,
1088+ GList *filter)
1089+{
1090+ backend_set_window_message_filter (plugin->backend, filter);
1091+}
1092+
1093+static void
1094+window_focus (PluginOpengles2 *plugin)
1095+{
1096+ backend_window_focus (plugin->backend);
1097+}
1098+
1099+static guint32
1100+get_window_id (PluginOpengles2 *plugin)
1101+{
1102+ return backend_get_window_id (plugin->backend);
1103+}
1104+
1105+static void
1106+set_window_drag_status (PluginOpengles2 *plugin,
1107+ gboolean accept)
1108+{
1109+ backend_set_window_drag_status (plugin->backend, accept);
1110+}
1111+
1112+/* Plugin */
1113+
1114+static gboolean
1115+is_extension_supported (const gchar *extensions,
1116+ const gchar *extension)
1117+{
1118+ if (extensions != NULL && extension != NULL)
1119+ {
1120+ const gsize len = strlen (extension);
1121+ gchar *p = (gchar*) extensions;
1122+ gchar *end = p + strlen (p);
1123+
1124+ while (p < end)
1125+ {
1126+ const gsize size = strcspn (p, " ");
1127+ if (len == size && strncmp (extension, p, size) == 0)
1128+ return TRUE;
1129+ p += size + 1;
1130+ }
1131+ }
1132+
1133+ return FALSE;
1134+}
1135+
1136+static gboolean
1137+init_plugin (PluginOpengles2 *plugin,
1138+ guint32 options)
1139+{
1140+ const struct {
1141+ const gchar *name; guint8 flag;
1142+ } extension_map[] = {
1143+ { "GL_IMG_texture_format_BGRA8888", FLAG_TEXTURE_FORMAT_BGRA8888 },
1144+ { NULL, 0 }
1145+ };
1146+ const gchar *vendor, *renderer, *version, *extensions;
1147+ PluginOpengles2Texture *texture;
1148+ PgmRendererCapabilities *caps;
1149+ PgmPluginFuncs *funcs;
1150+ guint8 extension_flags = 0;
1151+ guint8 caps_flags = 0;
1152+ guint32 i;
1153+
1154+
1155+ /* Get the information strings */
1156+ version = (const gchar*) glGetString (GL_VERSION);
1157+ vendor = (const gchar*) glGetString (GL_VENDOR);
1158+ renderer = (const gchar*) glGetString (GL_RENDERER);
1159+ extensions = (const gchar*) glGetString (GL_EXTENSIONS);
1160+ PGM_INFO_OBJECT (plugin->rdr, "OpenGL ES vendor: %s", vendor);
1161+ PGM_INFO_OBJECT (plugin->rdr, "OpenGL ES renderer: %s", renderer);
1162+ PGM_INFO_OBJECT (plugin->rdr, "OpenGL ES version: %s", version);
1163+ PGM_DEBUG_OBJECT (plugin->rdr, "OpenGL ES extensions: %s", extensions);
1164+
1165+ /* Store the supported extensions in a bitfield */
1166+ for (i = 0; extension_map[i].name != NULL; i++)
1167+ if (is_extension_supported (extensions, extension_map[i].name) == TRUE)
1168+ extension_flags |= extension_map[i].flag;
1169+ plugin->extension_flags = extension_flags;
1170+
1171+ /* Set initial states */
1172+ /* XXX: Some of these must be set from the core with dedicated functions */
1173+ glEnableVertexAttribArray(PGM_APOSITION);
1174+ glEnable (GL_BLEND);
1175+ glDepthFunc (GL_LEQUAL);
1176+ glEnable (GL_DEPTH_TEST);
1177+
1178+ glBlendFunc (GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
1179+ glEnable (GL_TEXTURE_2D);
1180+
1181+ /* Fill the default texture */
1182+ texture = g_slice_alloc (sizeof (PluginOpengles2Texture));
1183+ texture->type = GL_TEXTURE_2D;
1184+ texture->id = 0;
1185+ plugin->default_texture = texture;
1186+
1187+ /* Allocate memory for modelview/projection matrices */
1188+ plugin->proj_mat = (GLfloat*) malloc (16*sizeof(GLfloat));
1189+ plugin->modelview_mat = (GLfloat*) malloc (16*sizeof(GLfloat));
1190+
1191+ /* Fill the caps */
1192+ caps = pgm_renderer_capabilities_new ();
1193+ caps->device_vendor = g_strdup (vendor);
1194+ caps->device_description = g_strconcat (renderer, " (", version, ")", NULL);
1195+ if (backend_is_window_pluggable (plugin->backend))
1196+ caps_flags |= PGM_RENDERER_PLUGGABLE_WINDOW;
1197+ if (backend_is_window_layered (plugin->backend))
1198+ caps_flags |= PGM_RENDERER_LAYERED_WINDOW;
1199+ caps->flags = caps_flags;
1200+
1201+ /* Store supported shading languages */
1202+ caps->shading_languages = g_list_prepend
1203+ (NULL, pgm_renderer_shading_language_new ("glsles", "1.0", PGM_RENDERER_FRAGMENT_PROGRAM | PGM_RENDERER_VERTEX_PROGRAM ));
1204+
1205+ /* Store limits */
1206+ glGetIntegerv (GL_MAX_TEXTURE_SIZE, &caps->max_texture_size);
1207+ plugin->max_texture_units = caps->max_texture_units = 3;
1208+ caps->max_lights = 0;
1209+ plugin->caps = caps;
1210+
1211+ /* Fill the funcs */
1212+ funcs = g_slice_alloc (sizeof (PgmPluginFuncs));
1213+ funcs->set_sync_to_vblank =
1214+ (PgmPluginSetSyncToVBlankFunc) set_sync_to_vblank;
1215+ funcs->wait_for_vblank = (PgmPluginWaitForVBlankFunc) wait_for_vblank;
1216+ funcs->clear_buffers = (PgmPluginClearBuffersFunc) clear_buffers;
1217+ funcs->set_clear_color = (PgmPluginSetClearColorFunc) set_clear_color;
1218+ funcs->set_viewport = (PgmPluginSetViewportFunc) set_viewport;
1219+ funcs->set_projection_matrix =
1220+ (PgmPluginSetProjectionMatrixFunc) set_projection_matrix;
1221+ funcs->set_modelview_matrix =
1222+ (PgmPluginSetModelviewMatrixFunc) set_modelview_matrix;
1223+ funcs->draw_primitive = (PgmPluginDrawPrimitiveFunc) draw_primitive;
1224+ funcs->create_texture = (PgmPluginCreateTextureFunc) create_texture;
1225+ funcs->delete_textures = (PgmPluginDeleteTexturesFunc) delete_textures;
1226+ funcs->bind_texture = (PgmPluginBindTextureFunc) bind_texture;
1227+ funcs->upload_texture = (PgmPluginUploadTextureFunc) upload_texture;
1228+ funcs->set_texture_states =
1229+ (PgmPluginSetTextureStatesFunc) set_texture_states;
1230+ funcs->create_shader = (PgmPluginCreateShaderFunc) create_shader;
1231+ funcs->delete_shaders = (PgmPluginDeleteShadersFunc) delete_shaders;
1232+ funcs->bind_shader = (PgmPluginBindShaderFunc) bind_shader;
1233+ funcs->set_shader_uniforms =
1234+ (PgmPluginSetShaderUniformsFunc) set_shader_uniforms;
1235+ funcs->swap_buffers = (PgmPluginSwapBuffersFunc) swap_buffers;
1236+ funcs->get_screen_size = (PgmPluginGetScreenSizeFunc) get_screen_size;
1237+ funcs->get_screen_resolution =
1238+ (PgmPluginGetScreenResolutionFunc) get_screen_resolution;
1239+ funcs->read_pixels = NULL;
1240+ funcs->set_window_title = (PgmPluginSetWindowTitleFunc) set_window_title;
1241+ funcs->set_window_visible =
1242+ (PgmPluginSetWindowVisibleFunc) set_window_visible;
1243+ funcs->set_window_decorated =
1244+ (PgmPluginSetWindowDecoratedFunc) set_window_decorated;
1245+ funcs->set_window_fullscreen =
1246+ (PgmPluginSetWindowFullscreenFunc) set_window_fullscreen;
1247+ funcs->set_window_iconified =
1248+ (PgmPluginSetWindowIconifiedFunc) set_window_iconified;
1249+ funcs->set_window_cursor =
1250+ (PgmPluginSetWindowCursorFunc) set_window_cursor;
1251+/* funcs->set_window_icon = (PgmPluginSetWindowIconFunc) set_window_icon; */
1252+ funcs->set_window_size = (PgmPluginSetWindowSizeFunc) set_window_size;
1253+ funcs->set_window_message_filter =
1254+ (PgmPluginSetWindowMessageFilterFunc) set_window_message_filter;
1255+ funcs->window_focus = (PgmPluginWindowFocusFunc) window_focus;
1256+ funcs->get_window_id = (PgmPluginGetWindowIdFunc) get_window_id;
1257+ funcs->set_window_drag_status =
1258+ (PgmPluginSetWindowDragStatusFunc) set_window_drag_status;
1259+ plugin->funcs = funcs;
1260+
1261+ return TRUE;
1262+}
1263+
1264+static PgmPlugin
1265+construct (PgmRenderer *renderer,
1266+ GMainContext *context,
1267+ guint32 options,
1268+ PgmPluginFuncs **funcs,
1269+ PgmRendererCapabilities **caps,
1270+ PgmPluginTexture *texture,
1271+ PgmPluginShader *shader)
1272+{
1273+ PluginOpengles2 *plugin = g_slice_alloc0 (sizeof (PluginOpengles2));
1274+ Backend backend = backend_new (renderer, context, options);
1275+
1276+ if (backend != NULL)
1277+ {
1278+ plugin->rdr = renderer;
1279+ plugin->backend = backend;
1280+
1281+ plugin->shader = (PluginOpengles2Shader*) create_shader(plugin, "glsles", (gpointer)default_glslesvp,
1282+ strlen(default_glslesvp), NULL, 0,
1283+ (gpointer) default_glslesfp,
1284+ strlen(default_glslesfp), NULL, 0);
1285+
1286+ if (init_plugin (plugin, options) == TRUE)
1287+ {
1288+ *funcs = plugin->funcs;
1289+ *caps = plugin->caps;
1290+ *texture = plugin->default_texture;
1291+ *shader = plugin->shader;
1292+ return (PgmPlugin) plugin;
1293+ }
1294+ else
1295+ {
1296+ backend_free (backend);
1297+ g_slice_free1 (sizeof (PluginOpengles2), plugin);
1298+ PGM_ERROR_OBJECT (renderer, "can't initialize OpenGL ES plugin");
1299+ return NULL;
1300+ }
1301+ }
1302+ else
1303+ {
1304+ PGM_ERROR_OBJECT (renderer, "can't create OpenGL ES context");
1305+ return NULL;
1306+ }
1307+}
1308+
1309+static void
1310+destruct (PluginOpengles2 *plugin)
1311+{
1312+ /* XXX destruct shaders? */
1313+ g_slice_free1 (sizeof (PgmPluginFuncs), plugin->funcs);
1314+ g_slice_free1 (sizeof (PluginOpengles2Texture), plugin->default_texture);
1315+ pgm_renderer_capabilities_free (plugin->caps);
1316+ backend_free (plugin->backend);
1317+ g_slice_free1 (sizeof (PluginOpengles2), plugin);
1318+}
1319+
1320+#if defined (HAVE_EGL2_NATIVE)
1321+#define description "a plugin based on OpenGL ES 2 (native)"
1322+#elif defined (HAVE_EGL2_X11)
1323+#define description "a plugin based on OpenGL ES 2 (X11)"
1324+#endif
1325+
1326+PGM_PLUGIN_DEFINE (
1327+ "opengles2", /* Name */
1328+ VERSION, /* Version */
1329+ description, /* Description */
1330+ "LGPL", /* License */
1331+ "https://code.fluendo.com/pigment", /* Origin */
1332+ "Ahmed Ammar <ahmed.ammar@connectmetv.com>", /* Author */
1333+ (PgmPluginConstructFunc) construct, /* Constructor */
1334+ (PgmPluginDestructFunc) destruct, /* Destructor */
1335+ PGM_PLUGIN_SECONDARY /* Rank */
1336+)
1337
1338=== modified file 'tests/manual/test-geometry-sorting.c'
1339--- tests/manual/test-geometry-sorting.c 2010-05-07 16:58:25 +0000
1340+++ tests/manual/test-geometry-sorting.c 2010-05-19 17:34:31 +0000
1341@@ -447,7 +447,7 @@
1342 pgm_init (&argc, &argv);
1343
1344 /* OpenGL renderer creation */
1345- renderer = pgm_renderer_factory_make ("opengl", 1);
1346+ renderer = pgm_renderer_factory_make_auto ();
1347 if (!renderer)
1348 {
1349 g_print ("Cannot create a renderer\n");
1350
1351=== modified file 'tests/manual/test-gst-image.c'
1352--- tests/manual/test-gst-image.c 2010-05-07 16:46:26 +0000
1353+++ tests/manual/test-gst-image.c 2010-05-19 17:34:31 +0000
1354@@ -78,7 +78,7 @@
1355 pgm_init (&argc, &argv);
1356 gst_init (&argc, &argv);
1357
1358- renderer = pgm_renderer_factory_make ("opengl", 0);
1359+ renderer = pgm_renderer_factory_make_auto ();
1360 if (!renderer)
1361 {
1362 g_print ("Cannot create the OpenGL renderer\n");

Subscribers

People subscribed via source and target branches

to all changes: