summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKristian Høgsberg <krh@bitplanet.net>2010-01-24 18:10:15 -0500
committerKristian Høgsberg <krh@bitplanet.net>2010-01-24 18:10:15 -0500
commita341fa016c54948af4fc76cde864f460f962f9db (patch)
treee03749a18af66b568b5872298cdc29eded71b877
parent450cc8136d5c3c84407b3c621006a1fa6b092085 (diff)
Use FBOs instead of eagle-specific API
-rw-r--r--Makefile.in7
-rw-r--r--gears.c96
-rw-r--r--image.c12
-rw-r--r--terminal.c2
-rw-r--r--wayland-system-compositor.c111
-rw-r--r--window.c32
-rw-r--r--window.h2
7 files changed, 130 insertions, 132 deletions
diff --git a/Makefile.in b/Makefile.in
index cc66c61..3f666e2 100644
--- a/Makefile.in
+++ b/Makefile.in
@@ -8,8 +8,9 @@ libs = libwayland-server.so libwayland.so
8egl_clients = gears 8egl_clients = gears
9cairo_clients = flower screenshot terminal image view 9cairo_clients = flower screenshot terminal image view
10compositors = wayland-system-compositor 10compositors = wayland-system-compositor
11clients = $(egl_clients) $(cairo_clients)
11 12
12all : $(libs) $(compositors) $(egl_clients) $(cairo_clients) 13all : $(libs) $(compositors) $(clients)
13 14
14libwayland-server.so : \ 15libwayland-server.so : \
15 wayland.o \ 16 wayland.o \
@@ -36,7 +37,7 @@ wayland-system-compositor : \
36 wayland-util.o 37 wayland-util.o
37 38
38wayland-system-compositor : CFLAGS += @EGL_COMPOSITOR_CFLAGS@ 39wayland-system-compositor : CFLAGS += @EGL_COMPOSITOR_CFLAGS@
39wayland-system-compositor : LDLIBS += -L. -lwayland-server @EGL_COMPOSITOR_LIBS@ -rdynamic -lrt 40wayland-system-compositor : LDLIBS += ./libwayland-server.so @EGL_COMPOSITOR_LIBS@ -rdynamic -lrt
40 41
41flower : flower.o wayland-glib.o 42flower : flower.o wayland-glib.o
42gears : gears.o window.o wayland-glib.o cairo-util.o 43gears : gears.o window.o wayland-glib.o cairo-util.o
@@ -54,7 +55,7 @@ view : LDLIBS += @POPPLER_LIBS@
54$(egl_clients) : CFLAGS += @EGL_CLIENT_CFLAGS@ 55$(egl_clients) : CFLAGS += @EGL_CLIENT_CFLAGS@
55$(egl_clients) : LDLIBS += -L. -lwayland @EGL_CLIENT_LIBS@ -lrt 56$(egl_clients) : LDLIBS += -L. -lwayland @EGL_CLIENT_LIBS@ -lrt
56$(cairo_clients) : CFLAGS += @CAIRO_CLIENT_CFLAGS@ 57$(cairo_clients) : CFLAGS += @CAIRO_CLIENT_CFLAGS@
57$(cairo_clients) : LDLIBS += -L. -lwayland @CAIRO_CLIENT_LIBS@ -lrt 58$(cairo_clients) : LDLIBS += ./libwayland.so @CAIRO_CLIENT_LIBS@ -lrt
58 59
59install : $(libs) $(compositors) 60install : $(libs) $(compositors)
60 install -d @libdir@ @libdir@/pkgconfig ${udev_rules_dir} 61 install -d @libdir@ @libdir@/pkgconfig ${udev_rules_dir}
diff --git a/gears.c b/gears.c
index def1f99..9a8d503 100644
--- a/gears.c
+++ b/gears.c
@@ -32,6 +32,7 @@
32#include <glib.h> 32#include <glib.h>
33#include <cairo-drm.h> 33#include <cairo-drm.h>
34 34
35#define GL_GLEXT_PROTOTYPES
35#include <GL/gl.h> 36#include <GL/gl.h>
36#include <eagle.h> 37#include <eagle.h>
37 38
@@ -52,14 +53,13 @@ struct gears {
52 struct rectangle rectangle; 53 struct rectangle rectangle;
53 54
54 EGLDisplay display; 55 EGLDisplay display;
55 EGLConfig config;
56 EGLSurface surface;
57 EGLContext context; 56 EGLContext context;
58 int resized; 57 int resized;
59 GLfloat angle; 58 GLfloat angle;
60 cairo_surface_t *cairo_surface; 59 cairo_surface_t *cairo_surface;
61 60
62 GLint gear_list[3]; 61 GLint gear_list[3];
62 GLuint fbo, color_rbo, depth_rbo;
63}; 63};
64 64
65struct gear_template { 65struct gear_template {
@@ -258,19 +258,20 @@ resize_window(struct gears *gears)
258 258
259 window_draw(gears->window); 259 window_draw(gears->window);
260 260
261 if (gears->surface != NULL) 261 glBindRenderbuffer(GL_RENDERBUFFER_EXT, gears->color_rbo);
262 eglDestroySurface(gears->display, gears->surface); 262 glRenderbufferStorage(GL_RENDERBUFFER_EXT,
263 GL_RGBA,
264 gears->rectangle.width,
265 gears->rectangle.height);
263 266
264 gears->surface = eglCreateSurface(gears->display, 267 glBindRenderbuffer(GL_RENDERBUFFER_EXT, gears->depth_rbo);
265 gears->config, 268 glRenderbufferStorage(GL_RENDERBUFFER_EXT,
266 gears->rectangle.width, 269 GL_DEPTH_COMPONENT,
267 gears->rectangle.height, 270 gears->rectangle.width,
268 1, NULL); 271 gears->rectangle.height);
269
270 eglMakeCurrent(gears->display,
271 gears->surface, gears->surface, gears->context);
272 272
273 glViewport(0, 0, gears->rectangle.width, gears->rectangle.height); 273 glViewport(0, 0, gears->rectangle.width, gears->rectangle.height);
274
274 gears->resized = 0; 275 gears->resized = 0;
275} 276}
276 277
@@ -308,13 +309,12 @@ handle_acknowledge(void *data,
308{ 309{
309 struct gears *gears = data; 310 struct gears *gears = data;
310 311
311 if (key != 0) 312 if (key == 10) {
312 return; 313 if (gears->resized)
314 resize_window(gears);
313 315
314 if (gears->resized) 316 draw_gears(gears);
315 resize_window(gears); 317 }
316
317 draw_gears(gears);
318} 318}
319 319
320static void 320static void
@@ -322,14 +322,20 @@ handle_frame(void *data,
322 struct wl_compositor *compositor, 322 struct wl_compositor *compositor,
323 uint32_t frame, uint32_t timestamp) 323 uint32_t frame, uint32_t timestamp)
324{ 324{
325 struct gears *gears = data; 325 struct gears *gears = data;
326 uint32_t name, handle, stride; 326 GLint name, stride;
327 327
328 eglGetColorBuffer(gears->surface, 0, &name, &handle, &stride); 328 glBindRenderbuffer(GL_RENDERBUFFER_EXT, gears->color_rbo);
329 glGetRenderbufferParameteriv(GL_RENDERBUFFER_EXT,
330 GL_RENDERBUFFER_STRIDE_INTEL,
331 &stride);
332 glGetRenderbufferParameteriv(GL_RENDERBUFFER_EXT,
333 GL_RENDERBUFFER_NAME_INTEL,
334 &name);
329 335
330 window_copy(gears->window, &gears->rectangle, name, stride); 336 window_copy(gears->window, &gears->rectangle, name, stride);
331 337
332 wl_compositor_commit(gears->compositor, 0); 338 window_commit(gears->window, 10);
333 339
334 gears->angle = (GLfloat) (timestamp % 8192) * 360 / 8192.0; 340 gears->angle = (GLfloat) (timestamp % 8192) * 360 / 8192.0;
335} 341}
@@ -339,19 +345,11 @@ static const struct wl_compositor_listener compositor_listener = {
339 handle_frame, 345 handle_frame,
340}; 346};
341 347
342static const EGLint config_attribs[] = {
343 EGL_DEPTH_SIZE, 24,
344 EGL_CONFIG_CAVEAT, EGL_NONE,
345 EGL_RED_SIZE, 8,
346 EGL_NONE
347};
348
349static struct gears * 348static struct gears *
350gears_create(struct display *display) 349gears_create(struct display *display)
351{ 350{
352 const int x = 200, y = 200, width = 450, height = 500; 351 const int x = 200, y = 200, width = 450, height = 500;
353 EGLint major, minor, count; 352 EGLint major, minor;
354 EGLConfig configs[64];
355 struct udev *udev; 353 struct udev *udev;
356 struct udev_device *device; 354 struct udev_device *device;
357 struct gears *gears; 355 struct gears *gears;
@@ -373,18 +371,29 @@ gears_create(struct display *display)
373 if (!eglInitialize(gears->display, &major, &minor)) 371 if (!eglInitialize(gears->display, &major, &minor))
374 die("failed to initialize display\n"); 372 die("failed to initialize display\n");
375 373
376 if (!eglGetConfigs(gears->display, configs, 64, &count)) 374 gears->context = eglCreateContext(gears->display, NULL, NULL, NULL);
377 die("failed to get configs\n");
378
379 if (!eglChooseConfig(gears->display, config_attribs, &gears->config, 1, NULL))
380 die("failed to pick a config\n");
381
382 gears->context = eglCreateContext(gears->display, gears->config, NULL, NULL);
383 if (gears->context == NULL) 375 if (gears->context == NULL)
384 die("failed to create context\n"); 376 die("failed to create context\n");
385 377
386 resize_window(gears); 378 if (!eglMakeCurrent(gears->display, NULL, NULL, gears->context))
387 379 die("faile to make context current\n");
380
381 glGenFramebuffers(1, &gears->fbo);
382 glBindFramebuffer(GL_FRAMEBUFFER_EXT, gears->fbo);
383
384 glGenRenderbuffers(1, &gears->color_rbo);
385 glBindRenderbuffer(GL_RENDERBUFFER_EXT, gears->color_rbo);
386 glFramebufferRenderbuffer(GL_DRAW_FRAMEBUFFER_EXT,
387 GL_COLOR_ATTACHMENT0_EXT,
388 GL_RENDERBUFFER_EXT,
389 gears->color_rbo);
390
391 glGenRenderbuffers(1, &gears->depth_rbo);
392 glBindRenderbuffer(GL_RENDERBUFFER_EXT, gears->depth_rbo);
393 glFramebufferRenderbuffer(GL_DRAW_FRAMEBUFFER_EXT,
394 GL_DEPTH_ATTACHMENT_EXT,
395 GL_RENDERBUFFER_EXT,
396 gears->depth_rbo);
388 for (i = 0; i < 3; i++) { 397 for (i = 0; i < 3; i++) {
389 gears->gear_list[i] = glGenLists(1); 398 gears->gear_list[i] = glGenLists(1);
390 glNewList(gears->gear_list[i], GL_COMPILE); 399 glNewList(gears->gear_list[i], GL_COMPILE);
@@ -406,10 +415,13 @@ gears_create(struct display *display)
406 glEnable(GL_DEPTH_TEST); 415 glEnable(GL_DEPTH_TEST);
407 glClearColor(0, 0, 0, 0.92); 416 glClearColor(0, 0, 0, 0.92);
408 417
418 if (glCheckFramebufferStatus (GL_FRAMEBUFFER_EXT) != GL_FRAMEBUFFER_COMPLETE)
419 fprintf(stderr, "framebuffer incomplete\n");
420
409 gears->compositor = display_get_compositor(display); 421 gears->compositor = display_get_compositor(display);
410 422
423 resize_window(gears);
411 draw_gears(gears); 424 draw_gears(gears);
412
413 handle_frame(gears, gears->compositor, 0, 0); 425 handle_frame(gears, gears->compositor, 0, 0);
414 426
415 window_set_resize_handler(gears->window, resize_handler, gears); 427 window_set_resize_handler(gears->window, resize_handler, gears);
diff --git a/image.c b/image.c
index e38da0f..3f206fc 100644
--- a/image.c
+++ b/image.c
@@ -184,7 +184,7 @@ image_draw(struct image *image)
184 &rectangle, 184 &rectangle,
185 image->surface); 185 image->surface);
186 186
187 wl_compositor_commit(image->compositor, image->key); 187 window_commit(image->window, image->key);
188} 188}
189 189
190static gboolean 190static gboolean
@@ -217,6 +217,15 @@ resize_handler(struct window *window, void *data)
217} 217}
218 218
219static void 219static void
220keyboard_focus_handler(struct window *window,
221 struct wl_input_device *device, void *data)
222{
223 struct image *image = data;
224
225 image_schedule_redraw(image);
226}
227
228static void
220handle_acknowledge(void *data, 229handle_acknowledge(void *data,
221 struct wl_compositor *compositor, 230 struct wl_compositor *compositor,
222 uint32_t key, uint32_t frame) 231 uint32_t key, uint32_t frame)
@@ -274,6 +283,7 @@ image_create(struct display *display, uint32_t key, const char *filename)
274 283
275 image->compositor = display_get_compositor(display); 284 image->compositor = display_get_compositor(display);
276 window_set_resize_handler(image->window, resize_handler, image); 285 window_set_resize_handler(image->window, resize_handler, image);
286 window_set_keyboard_focus_handler(image->window, keyboard_focus_handler, image);
277 287
278 wl_compositor_add_listener(image->compositor, &compositor_listener, image); 288 wl_compositor_add_listener(image->compositor, &compositor_listener, image);
279 289
diff --git a/terminal.c b/terminal.c
index 05cdaa1..b4800d5 100644
--- a/terminal.c
+++ b/terminal.c
@@ -227,7 +227,7 @@ terminal_draw(struct terminal *terminal)
227 227
228 window_draw(terminal->window); 228 window_draw(terminal->window);
229 terminal_draw_contents(terminal); 229 terminal_draw_contents(terminal);
230 wl_compositor_commit(terminal->compositor, 0); 230 window_commit(terminal->window, 0);
231} 231}
232 232
233static gboolean 233static gboolean
diff --git a/wayland-system-compositor.c b/wayland-system-compositor.c
index 74b7f0a..851398c 100644
--- a/wayland-system-compositor.c
+++ b/wayland-system-compositor.c
@@ -69,13 +69,13 @@ struct wlsc_output {
69 struct wl_list link; 69 struct wl_list link;
70 struct wlsc_compositor *compositor; 70 struct wlsc_compositor *compositor;
71 struct wlsc_surface *background; 71 struct wlsc_surface *background;
72 EGLSurface surface;
73 int32_t x, y, width, height; 72 int32_t x, y, width, height;
74 73
75 drmModeModeInfo mode; 74 drmModeModeInfo mode;
76 uint32_t crtc_id; 75 uint32_t crtc_id;
77 uint32_t connector_id; 76 uint32_t connector_id;
78 77
78 GLuint rbo[2];
79 uint32_t fb_id[2]; 79 uint32_t fb_id[2];
80 uint32_t current; 80 uint32_t current;
81}; 81};
@@ -102,7 +102,7 @@ struct wlsc_compositor {
102 102
103 EGLDisplay display; 103 EGLDisplay display;
104 EGLContext context; 104 EGLContext context;
105 EGLConfig config; 105 GLuint fbo;
106 struct wl_display *wl_display; 106 struct wl_display *wl_display;
107 107
108 struct wl_list output_list; 108 struct wl_list output_list;
@@ -610,16 +610,11 @@ repaint_output(struct wlsc_output *output)
610 double s = 3000; 610 double s = 3000;
611 int fd; 611 int fd;
612 612
613 if (!eglMakeCurrent(ec->display, output->surface, output->surface, ec->context)) {
614 fprintf(stderr, "failed to make context current\n");
615 return;
616 }
617
618 glViewport(0, 0, output->width, output->height); 613 glViewport(0, 0, output->width, output->height);
619 glMatrixMode(GL_PROJECTION); 614 glMatrixMode(GL_PROJECTION);
620 glLoadIdentity(); 615 glLoadIdentity();
621 glFrustum(-output->width / s, output->width / s, 616 glFrustum(-output->width / s, output->width / s,
622 output->height / s, -output->height / s, 1, 2 * s); 617 -output->height / s, output->height / s, 1, 2 * s);
623 glMatrixMode(GL_MODELVIEW); 618 glMatrixMode(GL_MODELVIEW);
624 glLoadIdentity(); 619 glLoadIdentity();
625 glClearColor(0, 0, 0, 1); 620 glClearColor(0, 0, 0, 1);
@@ -650,7 +645,11 @@ repaint_output(struct wlsc_output *output)
650 645
651 fd = eglGetDisplayFD(ec->display); 646 fd = eglGetDisplayFD(ec->display);
652 output->current ^= 1; 647 output->current ^= 1;
653 eglBindColorBuffer(ec->display, output->surface, output->current); 648
649 glFramebufferRenderbuffer(GL_DRAW_FRAMEBUFFER_EXT,
650 GL_COLOR_ATTACHMENT0_EXT,
651 GL_RENDERBUFFER_EXT,
652 output->rbo[output->current]);
654 drmModePageFlip(fd, output->crtc_id, 653 drmModePageFlip(fd, output->crtc_id,
655 output->fb_id[output->current ^ 1], 654 output->fb_id[output->current ^ 1],
656 DRM_MODE_PAGE_FLIP_EVENT, output); 655 DRM_MODE_PAGE_FLIP_EVENT, output);
@@ -737,8 +736,8 @@ surface_attach(struct wl_client *client,
737 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_R, GL_REPEAT); 736 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_R, GL_REPEAT);
738 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); 737 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
739 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 738 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
740 glTextureExternalMESA(GL_TEXTURE_2D, GL_RGBA, 4, 739 glTextureExternalINTEL(GL_TEXTURE_2D, GL_RGBA, 4,
741 width, height, stride / 4, name); 740 width, height, stride / 4, name);
742 741
743} 742}
744 743
@@ -762,36 +761,6 @@ surface_copy(struct wl_client *client,
762 uint32_t name, uint32_t stride, 761 uint32_t name, uint32_t stride,
763 int32_t x, int32_t y, int32_t width, int32_t height) 762 int32_t x, int32_t y, int32_t width, int32_t height)
764{ 763{
765 struct wlsc_surface *es = (struct wlsc_surface *) surface;
766 GLuint fbo[2], rb;
767
768 glGenFramebuffers(2, fbo);
769
770 glBindFramebuffer(GL_READ_FRAMEBUFFER_EXT, fbo[1]);
771 glGenRenderbuffers(1, &rb);
772 glBindRenderbuffer(GL_RENDERBUFFER_EXT, rb);
773 glRenderbufferExternalMESA(GL_RENDERBUFFER_EXT,
774 GL_RGBA,
775 es->width, es->height,
776 stride / 4, name);
777 glFramebufferRenderbuffer(GL_READ_FRAMEBUFFER_EXT,
778 GL_COLOR_ATTACHMENT0_EXT,
779 GL_RENDERBUFFER_EXT,
780 rb);
781
782 glBindFramebuffer(GL_DRAW_FRAMEBUFFER_EXT, fbo[0]);
783 glFramebufferTexture2D(GL_DRAW_FRAMEBUFFER_EXT,
784 GL_COLOR_ATTACHMENT0_EXT,
785 GL_TEXTURE_2D, es->texture, 0);
786
787 glBlitFramebuffer(x, y, x + width, y + height,
788 dst_x, dst_y, dst_x+ width, dst_y + height,
789 GL_COLOR_BUFFER_BIT, GL_NEAREST);
790
791 glBindFramebuffer(GL_FRAMEBUFFER_EXT, 0);
792 glBindRenderbuffer(GL_RENDERBUFFER_EXT, 0);
793 glDeleteRenderbuffers(1, &rb);
794 glDeleteFramebuffers(2, fbo);
795} 764}
796 765
797static void 766static void
@@ -1138,14 +1107,6 @@ on_drm_input(int fd, uint32_t mask, void *data)
1138static int 1107static int
1139init_egl(struct wlsc_compositor *ec, struct udev_device *device) 1108init_egl(struct wlsc_compositor *ec, struct udev_device *device)
1140{ 1109{
1141 static const EGLint config_attribs[] = {
1142 EGL_DEPTH_SIZE, 0,
1143 EGL_STENCIL_SIZE, 0,
1144 EGL_CONFIG_CAVEAT, EGL_NONE,
1145 EGL_RED_SIZE, 8,
1146 EGL_NONE
1147 };
1148
1149 struct wl_event_loop *loop; 1110 struct wl_event_loop *loop;
1150 EGLint major, minor; 1111 EGLint major, minor;
1151 int fd; 1112 int fd;
@@ -1161,15 +1122,20 @@ init_egl(struct wlsc_compositor *ec, struct udev_device *device)
1161 return -1; 1122 return -1;
1162 } 1123 }
1163 1124
1164 if (!eglChooseConfig(ec->display, config_attribs, &ec->config, 1, NULL)) 1125 ec->context = eglCreateContext(ec->display, NULL, NULL, NULL);
1165 return -1;
1166
1167 ec->context = eglCreateContext(ec->display, ec->config, NULL, NULL);
1168 if (ec->context == NULL) { 1126 if (ec->context == NULL) {
1169 fprintf(stderr, "failed to create context\n"); 1127 fprintf(stderr, "failed to create context\n");
1170 return -1; 1128 return -1;
1171 } 1129 }
1172 1130
1131 if (!eglMakeCurrent(ec->display, EGL_NO_SURFACE, EGL_NO_SURFACE, ec->context)) {
1132 fprintf(stderr, "failed to make context current\n");
1133 return -1;
1134 }
1135
1136 glGenFramebuffers(1, &ec->fbo);
1137 glBindFramebuffer(GL_FRAMEBUFFER_EXT, ec->fbo);
1138
1173 loop = wl_display_get_event_loop(ec->wl_display); 1139 loop = wl_display_get_event_loop(ec->wl_display);
1174 fd = eglGetDisplayFD(ec->display); 1140 fd = eglGetDisplayFD(ec->display);
1175 ec->drm_source = 1141 ec->drm_source =
@@ -1197,7 +1163,7 @@ create_output_for_connector(struct wlsc_compositor *ec,
1197 struct wlsc_output *output; 1163 struct wlsc_output *output;
1198 drmModeEncoder *encoder; 1164 drmModeEncoder *encoder;
1199 drmModeModeInfo *mode; 1165 drmModeModeInfo *mode;
1200 uint32_t name, handle, stride; 1166 GLint handle, stride;
1201 int i, ret, fd; 1167 int i, ret, fd;
1202 1168
1203 fd = eglGetDisplayFD(ec->display); 1169 fd = eglGetDisplayFD(ec->display);
@@ -1243,21 +1209,21 @@ create_output_for_connector(struct wlsc_compositor *ec,
1243 1209
1244 drmModeFreeEncoder(encoder); 1210 drmModeFreeEncoder(encoder);
1245 1211
1246 output->surface = eglCreateSurface(ec->display, 1212 glGenRenderbuffers(2, output->rbo);
1247 ec->config,
1248 output->width,
1249 output->height,
1250 2, NULL);
1251 if (output->surface == NULL) {
1252 fprintf(stderr, "failed to create surface\n");
1253 return -1;
1254 }
1255
1256 for (i = 0; i < 2; i++) { 1213 for (i = 0; i < 2; i++) {
1257 eglGetColorBuffer(output->surface, 1214 glBindRenderbuffer(GL_RENDERBUFFER_EXT, output->rbo[i]);
1258 i, &name, &handle, &stride); 1215 glRenderbufferStorage(GL_RENDERBUFFER_EXT,
1259 1216 GL_RGBA,
1260 ret = drmModeAddFB(fd, mode->hdisplay, mode->vdisplay, 1217 output->width,
1218 output->height);
1219 glGetRenderbufferParameteriv(GL_RENDERBUFFER_EXT,
1220 GL_RENDERBUFFER_STRIDE_INTEL,
1221 &stride);
1222 glGetRenderbufferParameteriv(GL_RENDERBUFFER_EXT,
1223 GL_RENDERBUFFER_HANDLE_INTEL,
1224 &handle);
1225
1226 ret = drmModeAddFB(fd, output->width, output->height,
1261 32, 32, stride, handle, &output->fb_id[i]); 1227 32, 32, stride, handle, &output->fb_id[i]);
1262 if (ret) { 1228 if (ret) {
1263 fprintf(stderr, "failed to add fb %d: %m\n", i); 1229 fprintf(stderr, "failed to add fb %d: %m\n", i);
@@ -1266,6 +1232,10 @@ create_output_for_connector(struct wlsc_compositor *ec,
1266 } 1232 }
1267 1233
1268 output->current = 0; 1234 output->current = 0;
1235 glFramebufferRenderbuffer(GL_DRAW_FRAMEBUFFER_EXT,
1236 GL_COLOR_ATTACHMENT0_EXT,
1237 GL_RENDERBUFFER_EXT,
1238 output->rbo[output->current]);
1269 ret = drmModeSetCrtc(fd, output->crtc_id, 1239 ret = drmModeSetCrtc(fd, output->crtc_id,
1270 output->fb_id[output->current ^ 1], 0, 0, 1240 output->fb_id[output->current ^ 1], 0, 0,
1271 &output->connector_id, 1, &output->mode); 1241 &output->connector_id, 1, &output->mode);
@@ -1279,11 +1249,6 @@ create_output_for_connector(struct wlsc_compositor *ec,
1279 wl_display_add_global(ec->wl_display, &output->base, post_output_geometry); 1249 wl_display_add_global(ec->wl_display, &output->base, post_output_geometry);
1280 wl_list_insert(ec->output_list.prev, &output->link); 1250 wl_list_insert(ec->output_list.prev, &output->link);
1281 1251
1282 if (!eglMakeCurrent(ec->display, output->surface, output->surface, ec->context)) {
1283 fprintf(stderr, "failed to make context current\n");
1284 return -1;
1285 }
1286
1287 output->background = background_create(output, option_background); 1252 output->background = background_create(output, option_background);
1288 1253
1289 return 0; 1254 return 0;
diff --git a/window.c b/window.c
index e27ff32..95f3e21 100644
--- a/window.c
+++ b/window.c
@@ -66,6 +66,7 @@ struct window {
66 uint32_t modifiers; 66 uint32_t modifiers;
67 67
68 cairo_surface_t *cairo_surface, *pending_surface; 68 cairo_surface_t *cairo_surface, *pending_surface;
69 int new_surface;
69 70
70 window_resize_handler_t resize_handler; 71 window_resize_handler_t resize_handler;
71 window_key_handler_t key_handler; 72 window_key_handler_t key_handler;
@@ -113,6 +114,17 @@ window_attach_surface(struct window *window)
113 window->allocation.height); 114 window->allocation.height);
114} 115}
115 116
117void
118window_commit(struct window *window, uint32_t key)
119{
120 if (window->new_surface) {
121 window_attach_surface(window);
122 window->new_surface = 0;
123 }
124
125 wl_compositor_commit(window->display->compositor, key);
126}
127
116static void 128static void
117window_draw_decorations(struct window *window) 129window_draw_decorations(struct window *window)
118{ 130{
@@ -210,8 +222,6 @@ window_draw_decorations(struct window *window)
210 cairo_fill(cr); 222 cairo_fill(cr);
211 } 223 }
212 cairo_destroy(cr); 224 cairo_destroy(cr);
213
214 window_attach_surface(window);
215} 225}
216 226
217static void 227static void
@@ -222,8 +232,6 @@ window_draw_fullscreen(struct window *window)
222 CAIRO_CONTENT_COLOR_ALPHA, 232 CAIRO_CONTENT_COLOR_ALPHA,
223 window->allocation.width, 233 window->allocation.width,
224 window->allocation.height); 234 window->allocation.height);
225
226 window_attach_surface(window);
227} 235}
228 236
229void 237void
@@ -236,6 +244,8 @@ window_draw(struct window *window)
236 window_draw_fullscreen(window); 244 window_draw_fullscreen(window);
237 else 245 else
238 window_draw_decorations(window); 246 window_draw_decorations(window);
247
248 window->new_surface = 1;
239} 249}
240 250
241static void 251static void
@@ -251,13 +261,11 @@ window_handle_acknowledge(void *data,
251 * safely free the old window buffer if we resized and 261 * safely free the old window buffer if we resized and
252 * render the next frame into our back buffer.. */ 262 * render the next frame into our back buffer.. */
253 263
254 if (key == 0) { 264 pending = window->pending_surface;
255 pending = window->pending_surface; 265 window->pending_surface = NULL;
256 window->pending_surface = NULL; 266 if (pending != window->cairo_surface)
257 if (pending != window->cairo_surface) 267 window_attach_surface(window);
258 window_attach_surface(window); 268 cairo_surface_destroy(pending);
259 cairo_surface_destroy(pending);
260 }
261} 269}
262 270
263static void 271static void
@@ -585,7 +593,7 @@ window_copy(struct window *window,
585 cairo_t *cr; 593 cairo_t *cr;
586 594
587 surface = cairo_drm_surface_create_for_name (window->display->device, 595 surface = cairo_drm_surface_create_for_name (window->display->device,
588 name, CAIRO_CONTENT_COLOR_ALPHA, 596 name, CAIRO_FORMAT_ARGB32,
589 rectangle->width, rectangle->height, 597 rectangle->width, rectangle->height,
590 stride); 598 stride);
591 599
diff --git a/window.h b/window.h
index c483400..78e7734 100644
--- a/window.h
+++ b/window.h
@@ -60,6 +60,8 @@ window_create(struct display *display, const char *title,
60void 60void
61window_draw(struct window *window); 61window_draw(struct window *window);
62void 62void
63window_commit(struct window *window, uint32_t key);
64void
63window_get_child_rectangle(struct window *window, 65window_get_child_rectangle(struct window *window,
64 struct rectangle *rectangle); 66 struct rectangle *rectangle);
65void 67void