mirror of
				https://gitlab.freedesktop.org/wayland/wayland.git
				synced 2025-11-03 09:01:42 -05:00 
			
		
		
		
	Add preliminary visual support.
This commit is contained in:
		
							parent
							
								
									c8c5d5872d
								
							
						
					
					
						commit
						de31d5ca6f
					
				
					 7 changed files with 148 additions and 29 deletions
				
			
		| 
						 | 
					@ -52,6 +52,10 @@
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#define ARRAY_LENGTH(a) (sizeof (a) / sizeof (a)[0])
 | 
					#define ARRAY_LENGTH(a) (sizeof (a) / sizeof (a)[0])
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					struct wl_visual {
 | 
				
			||||||
 | 
						struct wl_object base;
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct egl_input_device {
 | 
					struct egl_input_device {
 | 
				
			||||||
	struct wl_object base;
 | 
						struct wl_object base;
 | 
				
			||||||
	int32_t x, y;
 | 
						int32_t x, y;
 | 
				
			||||||
| 
						 | 
					@ -66,6 +70,8 @@ struct egl_input_device {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct egl_compositor {
 | 
					struct egl_compositor {
 | 
				
			||||||
	struct wl_compositor base;
 | 
						struct wl_compositor base;
 | 
				
			||||||
 | 
						struct wl_visual argb_visual, premultiplied_argb_visual, rgb_visual;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	EGLDisplay display;
 | 
						EGLDisplay display;
 | 
				
			||||||
	EGLSurface surface;
 | 
						EGLSurface surface;
 | 
				
			||||||
	EGLContext context;
 | 
						EGLContext context;
 | 
				
			||||||
| 
						 | 
					@ -91,6 +97,7 @@ struct egl_compositor {
 | 
				
			||||||
struct egl_surface {
 | 
					struct egl_surface {
 | 
				
			||||||
	struct wl_surface base;
 | 
						struct wl_surface base;
 | 
				
			||||||
	struct egl_compositor *compositor;
 | 
						struct egl_compositor *compositor;
 | 
				
			||||||
 | 
						struct wl_visual *visual;
 | 
				
			||||||
	GLuint texture;
 | 
						GLuint texture;
 | 
				
			||||||
	struct wl_map map;
 | 
						struct wl_map map;
 | 
				
			||||||
	EGLSurface surface;
 | 
						EGLSurface surface;
 | 
				
			||||||
| 
						 | 
					@ -155,7 +162,8 @@ screenshooter_create(struct egl_compositor *ec)
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static struct egl_surface *
 | 
					static struct egl_surface *
 | 
				
			||||||
egl_surface_create_from_cairo_surface(cairo_surface_t *surface,
 | 
					egl_surface_create_from_cairo_surface(struct egl_compositor *ec,
 | 
				
			||||||
 | 
									      cairo_surface_t *surface,
 | 
				
			||||||
				      int x, int y, int width, int height)
 | 
									      int x, int y, int width, int height)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	struct egl_surface *es;
 | 
						struct egl_surface *es;
 | 
				
			||||||
| 
						 | 
					@ -178,11 +186,13 @@ egl_surface_create_from_cairo_surface(cairo_surface_t *surface,
 | 
				
			||||||
	glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0,
 | 
						glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0,
 | 
				
			||||||
		     GL_BGRA, GL_UNSIGNED_BYTE, data);
 | 
							     GL_BGRA, GL_UNSIGNED_BYTE, data);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						es->compositor = ec;
 | 
				
			||||||
	es->map.x = x;
 | 
						es->map.x = x;
 | 
				
			||||||
	es->map.y = y;
 | 
						es->map.y = y;
 | 
				
			||||||
	es->map.width = width;
 | 
						es->map.width = width;
 | 
				
			||||||
	es->map.height = height;
 | 
						es->map.height = height;
 | 
				
			||||||
	es->surface = EGL_NO_SURFACE;
 | 
						es->surface = EGL_NO_SURFACE;
 | 
				
			||||||
 | 
						es->visual = &ec->premultiplied_argb_visual;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	return es;
 | 
						return es;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
| 
						 | 
					@ -213,7 +223,7 @@ pointer_path(cairo_t *cr, int x, int y)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static struct egl_surface *
 | 
					static struct egl_surface *
 | 
				
			||||||
pointer_create(int x, int y, int width, int height)
 | 
					pointer_create(struct egl_compositor *ec, int x, int y, int width, int height)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	struct egl_surface *es;
 | 
						struct egl_surface *es;
 | 
				
			||||||
	const int hotspot_x = 16, hotspot_y = 16;
 | 
						const int hotspot_x = 16, hotspot_y = 16;
 | 
				
			||||||
| 
						 | 
					@ -237,7 +247,8 @@ pointer_create(int x, int y, int width, int height)
 | 
				
			||||||
	cairo_fill(cr);
 | 
						cairo_fill(cr);
 | 
				
			||||||
	cairo_destroy(cr);
 | 
						cairo_destroy(cr);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	es = egl_surface_create_from_cairo_surface(surface,
 | 
						es = egl_surface_create_from_cairo_surface(ec,
 | 
				
			||||||
 | 
											   surface,
 | 
				
			||||||
						   x - hotspot_x,
 | 
											   x - hotspot_x,
 | 
				
			||||||
						   y - hotspot_y,
 | 
											   y - hotspot_y,
 | 
				
			||||||
						   width, height);
 | 
											   width, height);
 | 
				
			||||||
| 
						 | 
					@ -248,7 +259,8 @@ pointer_create(int x, int y, int width, int height)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static struct egl_surface *
 | 
					static struct egl_surface *
 | 
				
			||||||
background_create(const char *filename, int width, int height)
 | 
					background_create(struct egl_compositor *ec,
 | 
				
			||||||
 | 
							  const char *filename, int width, int height)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	struct egl_surface *background;
 | 
						struct egl_surface *background;
 | 
				
			||||||
	GdkPixbuf *pixbuf;
 | 
						GdkPixbuf *pixbuf;
 | 
				
			||||||
| 
						 | 
					@ -281,11 +293,13 @@ background_create(const char *filename, int width, int height)
 | 
				
			||||||
	glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, pixbuf_width, pixbuf_height, 0,
 | 
						glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, pixbuf_width, pixbuf_height, 0,
 | 
				
			||||||
		     GL_BGR, GL_UNSIGNED_BYTE, data);
 | 
							     GL_BGR, GL_UNSIGNED_BYTE, data);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						background->compositor = ec;
 | 
				
			||||||
	background->map.x = 0;
 | 
						background->map.x = 0;
 | 
				
			||||||
	background->map.y = 0;
 | 
						background->map.y = 0;
 | 
				
			||||||
	background->map.width = width;
 | 
						background->map.width = width;
 | 
				
			||||||
	background->map.height = height;
 | 
						background->map.height = height;
 | 
				
			||||||
	background->surface = EGL_NO_SURFACE;
 | 
						background->surface = EGL_NO_SURFACE;
 | 
				
			||||||
 | 
						background->visual = &ec->rgb_visual;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	return background;
 | 
						return background;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
| 
						 | 
					@ -351,7 +365,7 @@ draw_button(cairo_t *cr, int x, int y, int width, int height, const char *text)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static struct egl_surface *
 | 
					static struct egl_surface *
 | 
				
			||||||
overlay_create(int x, int y, int width, int height)
 | 
					overlay_create(struct egl_compositor *ec, int x, int y, int width, int height)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	struct egl_surface *es;
 | 
						struct egl_surface *es;
 | 
				
			||||||
	cairo_surface_t *surface;
 | 
						cairo_surface_t *surface;
 | 
				
			||||||
| 
						 | 
					@ -378,7 +392,8 @@ overlay_create(int x, int y, int width, int height)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	cairo_destroy(cr);
 | 
						cairo_destroy(cr);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	es = egl_surface_create_from_cairo_surface(surface, x, y, width, height);
 | 
						es = egl_surface_create_from_cairo_surface(ec, surface,
 | 
				
			||||||
 | 
											   x, y, width, height);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	cairo_surface_destroy(surface);
 | 
						cairo_surface_destroy(surface);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -388,6 +403,7 @@ overlay_create(int x, int y, int width, int height)
 | 
				
			||||||
static void
 | 
					static void
 | 
				
			||||||
draw_surface(struct egl_surface *es)
 | 
					draw_surface(struct egl_surface *es)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
 | 
						struct egl_compositor *ec = es->compositor;
 | 
				
			||||||
	GLint vertices[12];
 | 
						GLint vertices[12];
 | 
				
			||||||
	GLint tex_coords[12] = { 0, 0,  0, 1,  1, 0,  1, 1 };
 | 
						GLint tex_coords[12] = { 0, 0,  0, 1,  1, 0,  1, 1 };
 | 
				
			||||||
	GLuint indices[4] = { 0, 1, 2, 3 };
 | 
						GLuint indices[4] = { 0, 1, 2, 3 };
 | 
				
			||||||
| 
						 | 
					@ -408,13 +424,18 @@ draw_surface(struct egl_surface *es)
 | 
				
			||||||
	vertices[10] = es->map.y + es->map.height;
 | 
						vertices[10] = es->map.y + es->map.height;
 | 
				
			||||||
	vertices[11] = 0;
 | 
						vertices[11] = 0;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if (es->visual == &ec->argb_visual) {
 | 
				
			||||||
 | 
							glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
 | 
				
			||||||
 | 
							glEnable(GL_BLEND);
 | 
				
			||||||
 | 
						} else if (es->visual == &ec->premultiplied_argb_visual) {
 | 
				
			||||||
 | 
							glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
 | 
				
			||||||
 | 
							glEnable(GL_BLEND);
 | 
				
			||||||
 | 
						} else {
 | 
				
			||||||
 | 
							glDisable(GL_BLEND);
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	glBindTexture(GL_TEXTURE_2D, es->texture);
 | 
						glBindTexture(GL_TEXTURE_2D, es->texture);
 | 
				
			||||||
	glEnable(GL_TEXTURE_2D);
 | 
						glEnable(GL_TEXTURE_2D);
 | 
				
			||||||
	glEnable(GL_BLEND);
 | 
					 | 
				
			||||||
	/* Assume pre-multiplied alpha for now, this probably
 | 
					 | 
				
			||||||
	 * needs to be a wayland visual type of thing. */
 | 
					 | 
				
			||||||
	glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	glEnableClientState(GL_VERTEX_ARRAY);
 | 
						glEnableClientState(GL_VERTEX_ARRAY);
 | 
				
			||||||
	glEnableClientState(GL_TEXTURE_COORD_ARRAY);
 | 
						glEnableClientState(GL_TEXTURE_COORD_ARRAY);
 | 
				
			||||||
	glVertexPointer(3, GL_INT, 0, vertices);
 | 
						glVertexPointer(3, GL_INT, 0, vertices);
 | 
				
			||||||
| 
						 | 
					@ -549,7 +570,8 @@ surface_destroy(struct wl_client *client,
 | 
				
			||||||
static void
 | 
					static void
 | 
				
			||||||
surface_attach(struct wl_client *client,
 | 
					surface_attach(struct wl_client *client,
 | 
				
			||||||
	       struct wl_surface *surface, uint32_t name, 
 | 
						       struct wl_surface *surface, uint32_t name, 
 | 
				
			||||||
	       uint32_t width, uint32_t height, uint32_t stride)
 | 
						       uint32_t width, uint32_t height, uint32_t stride,
 | 
				
			||||||
 | 
						       struct wl_object *visual)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	struct egl_surface *es = (struct egl_surface *) surface;
 | 
						struct egl_surface *es = (struct egl_surface *) surface;
 | 
				
			||||||
	struct egl_compositor *ec = es->compositor;
 | 
						struct egl_compositor *ec = es->compositor;
 | 
				
			||||||
| 
						 | 
					@ -561,6 +583,12 @@ surface_attach(struct wl_client *client,
 | 
				
			||||||
	es->height = height;
 | 
						es->height = height;
 | 
				
			||||||
	es->surface = eglCreateSurfaceForName(ec->display, ec->config,
 | 
						es->surface = eglCreateSurfaceForName(ec->display, ec->config,
 | 
				
			||||||
					      name, width, height, stride, NULL);
 | 
										      name, width, height, stride, NULL);
 | 
				
			||||||
 | 
						if (visual == &ec->argb_visual.base)
 | 
				
			||||||
 | 
							es->visual = &ec->argb_visual;
 | 
				
			||||||
 | 
						else if (visual == &ec->premultiplied_argb_visual.base)
 | 
				
			||||||
 | 
							es->visual = &ec->premultiplied_argb_visual;
 | 
				
			||||||
 | 
						else
 | 
				
			||||||
 | 
							/* FIXME: Smack client with an exception event */;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	glBindTexture(GL_TEXTURE_2D, es->texture);
 | 
						glBindTexture(GL_TEXTURE_2D, es->texture);
 | 
				
			||||||
	glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
 | 
						glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
 | 
				
			||||||
| 
						 | 
					@ -783,7 +811,8 @@ create_input_device(struct egl_compositor *ec, const char *glob)
 | 
				
			||||||
	wl_display_add_object(ec->wl_display, &device->base);
 | 
						wl_display_add_object(ec->wl_display, &device->base);
 | 
				
			||||||
	device->x = 100;
 | 
						device->x = 100;
 | 
				
			||||||
	device->y = 100;
 | 
						device->y = 100;
 | 
				
			||||||
	device->pointer_surface = pointer_create(device->x, device->y, 64, 64);
 | 
						device->pointer_surface = pointer_create(ec,
 | 
				
			||||||
 | 
											 device->x, device->y, 64, 64);
 | 
				
			||||||
	device->ec = ec;
 | 
						device->ec = ec;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	dir = opendir(by_path_dir);
 | 
						dir = opendir(by_path_dir);
 | 
				
			||||||
| 
						 | 
					@ -947,6 +976,31 @@ pick_config(struct egl_compositor *ec)
 | 
				
			||||||
	return 0;
 | 
						return 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static const struct wl_interface visual_interface = {
 | 
				
			||||||
 | 
						"visual", 1,
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static void
 | 
				
			||||||
 | 
					add_visuals(struct egl_compositor *ec)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						ec->argb_visual.base.interface = &visual_interface;
 | 
				
			||||||
 | 
						ec->argb_visual.base.implementation = NULL;
 | 
				
			||||||
 | 
						wl_display_add_object(ec->wl_display, &ec->argb_visual.base);
 | 
				
			||||||
 | 
						wl_display_add_global(ec->wl_display, &ec->argb_visual.base);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						ec->premultiplied_argb_visual.base.interface = &visual_interface;
 | 
				
			||||||
 | 
						ec->premultiplied_argb_visual.base.implementation = NULL;
 | 
				
			||||||
 | 
						wl_display_add_object(ec->wl_display,
 | 
				
			||||||
 | 
								      &ec->premultiplied_argb_visual.base);
 | 
				
			||||||
 | 
						wl_display_add_global(ec->wl_display,
 | 
				
			||||||
 | 
								      &ec->premultiplied_argb_visual.base);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						ec->rgb_visual.base.interface = &visual_interface;
 | 
				
			||||||
 | 
						ec->rgb_visual.base.implementation = NULL;
 | 
				
			||||||
 | 
						wl_display_add_object(ec->wl_display, &ec->rgb_visual.base);
 | 
				
			||||||
 | 
						wl_display_add_global(ec->wl_display, &ec->rgb_visual.base);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static const char gem_device[] = "/dev/dri/card0";
 | 
					static const char gem_device[] = "/dev/dri/card0";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static const char *macbook_air_default_input_device[] = {
 | 
					static const char *macbook_air_default_input_device[] = {
 | 
				
			||||||
| 
						 | 
					@ -1025,15 +1079,16 @@ egl_compositor_create(struct wl_display *display)
 | 
				
			||||||
	glClearColor(0, 0, 0.2, 1);
 | 
						glClearColor(0, 0, 0.2, 1);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	wl_display_set_compositor(display, &ec->base, &compositor_interface); 
 | 
						wl_display_set_compositor(display, &ec->base, &compositor_interface); 
 | 
				
			||||||
 | 
						add_visuals(ec);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	wl_list_init(&ec->input_device_list);
 | 
						wl_list_init(&ec->input_device_list);
 | 
				
			||||||
	for (i = 0; option_input_devices[i]; i++)
 | 
						for (i = 0; option_input_devices[i]; i++)
 | 
				
			||||||
		create_input_device(ec, option_input_devices[i]);
 | 
							create_input_device(ec, option_input_devices[i]);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	wl_list_init(&ec->surface_list);
 | 
						wl_list_init(&ec->surface_list);
 | 
				
			||||||
	ec->background = background_create(option_background,
 | 
						ec->background = background_create(ec, option_background,
 | 
				
			||||||
					   ec->width, ec->height);
 | 
										   ec->width, ec->height);
 | 
				
			||||||
	ec->overlay = overlay_create(0, ec->height, ec->width, 200);
 | 
						ec->overlay = overlay_create(ec, 0, ec->height, ec->width, 200);
 | 
				
			||||||
	ec->overlay_y = ec->height;
 | 
						ec->overlay_y = ec->height;
 | 
				
			||||||
	ec->overlay_target = ec->height;
 | 
						ec->overlay_target = ec->height;
 | 
				
			||||||
	ec->overlay_previous = ec->height;
 | 
						ec->overlay_previous = ec->height;
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
							
								
								
									
										7
									
								
								flower.c
									
										
									
									
									
								
							
							
						
						
									
										7
									
								
								flower.c
									
										
									
									
									
								
							| 
						 | 
					@ -133,6 +133,7 @@ event_handler(struct wl_display *display,
 | 
				
			||||||
int main(int argc, char *argv[])
 | 
					int main(int argc, char *argv[])
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	struct wl_display *display;
 | 
						struct wl_display *display;
 | 
				
			||||||
 | 
						struct wl_visual *visual;
 | 
				
			||||||
	int fd;
 | 
						int fd;
 | 
				
			||||||
	cairo_surface_t *s;
 | 
						cairo_surface_t *s;
 | 
				
			||||||
	struct timespec ts;
 | 
						struct timespec ts;
 | 
				
			||||||
| 
						 | 
					@ -172,8 +173,10 @@ int main(int argc, char *argv[])
 | 
				
			||||||
	s = draw_stuff(flower.width, flower.height);
 | 
						s = draw_stuff(flower.width, flower.height);
 | 
				
			||||||
	buffer = buffer_create_from_cairo_surface(fd, s);
 | 
						buffer = buffer_create_from_cairo_surface(fd, s);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	wl_surface_attach(flower.surface, buffer->name, flower.width, flower.height,
 | 
						visual = wl_display_get_premultiplied_argb_visual(display);
 | 
				
			||||||
			  buffer->stride);
 | 
						wl_surface_attach(flower.surface,
 | 
				
			||||||
 | 
								  buffer->name, flower.width, flower.height,
 | 
				
			||||||
 | 
								  buffer->stride, visual);
 | 
				
			||||||
	wl_display_set_event_handler(display, event_handler, &flower);
 | 
						wl_display_set_event_handler(display, event_handler, &flower);
 | 
				
			||||||
	move_flower(&flower);
 | 
						move_flower(&flower);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -56,6 +56,7 @@ struct wl_display {
 | 
				
			||||||
	uint32_t id;
 | 
						uint32_t id;
 | 
				
			||||||
	uint32_t mask;
 | 
						uint32_t mask;
 | 
				
			||||||
	struct wl_list global_list;
 | 
						struct wl_list global_list;
 | 
				
			||||||
 | 
						struct wl_list visual_list;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	wl_display_update_func_t update;
 | 
						wl_display_update_func_t update;
 | 
				
			||||||
	void *update_data;
 | 
						void *update_data;
 | 
				
			||||||
| 
						 | 
					@ -72,6 +73,11 @@ struct wl_surface {
 | 
				
			||||||
	struct wl_proxy proxy;
 | 
						struct wl_proxy proxy;
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					struct wl_visual {
 | 
				
			||||||
 | 
						struct wl_proxy proxy;
 | 
				
			||||||
 | 
						struct wl_list link;
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static int
 | 
					static int
 | 
				
			||||||
connection_update(struct wl_connection *connection,
 | 
					connection_update(struct wl_connection *connection,
 | 
				
			||||||
		  uint32_t mask, void *data)
 | 
							  uint32_t mask, void *data)
 | 
				
			||||||
| 
						 | 
					@ -86,6 +92,45 @@ connection_update(struct wl_connection *connection,
 | 
				
			||||||
	return 0;
 | 
						return 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static void
 | 
				
			||||||
 | 
					add_visual(struct wl_display *display, struct wl_global *global)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						struct wl_visual *visual;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						visual = malloc(sizeof *visual);
 | 
				
			||||||
 | 
						if (visual == NULL)
 | 
				
			||||||
 | 
							return;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						visual->proxy.display = display;
 | 
				
			||||||
 | 
						visual->proxy.id = global->id;
 | 
				
			||||||
 | 
						wl_list_insert(display->visual_list.prev, &visual->link);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						printf("added visual, id %d\n", global->id);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					WL_EXPORT struct wl_visual *
 | 
				
			||||||
 | 
					wl_display_get_argb_visual(struct wl_display *display)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						return container_of(display->visual_list.next,
 | 
				
			||||||
 | 
								    struct wl_visual, link);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					WL_EXPORT struct wl_visual *
 | 
				
			||||||
 | 
					wl_display_get_premultiplied_argb_visual(struct wl_display *display)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						return container_of(display->visual_list.next->next,
 | 
				
			||||||
 | 
								    struct wl_visual, link);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					WL_EXPORT struct wl_visual *
 | 
				
			||||||
 | 
					wl_display_get_rgb_visual(struct wl_display *display)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						/* FIXME: Where's cddar when you need it... */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return container_of(display->visual_list.next->next->next,
 | 
				
			||||||
 | 
								    struct wl_visual, link);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
WL_EXPORT struct wl_display *
 | 
					WL_EXPORT struct wl_display *
 | 
				
			||||||
wl_display_create(const char *name, size_t name_size)
 | 
					wl_display_create(const char *name, size_t name_size)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
| 
						 | 
					@ -125,6 +170,7 @@ wl_display_create(const char *name, size_t name_size)
 | 
				
			||||||
	read(display->fd, &count, sizeof count);
 | 
						read(display->fd, &count, sizeof count);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	wl_list_init(&display->global_list);
 | 
						wl_list_init(&display->global_list);
 | 
				
			||||||
 | 
						wl_list_init(&display->visual_list);
 | 
				
			||||||
	for (i = 0; i < count; i++) {
 | 
						for (i = 0; i < count; i++) {
 | 
				
			||||||
		/* FIXME: actually discover advertised objects here. */
 | 
							/* FIXME: actually discover advertised objects here. */
 | 
				
			||||||
		read(display->fd, &id, sizeof id);
 | 
							read(display->fd, &id, sizeof id);
 | 
				
			||||||
| 
						 | 
					@ -140,6 +186,9 @@ wl_display_create(const char *name, size_t name_size)
 | 
				
			||||||
		memcpy(global->interface, buffer, length);
 | 
							memcpy(global->interface, buffer, length);
 | 
				
			||||||
		global->interface[length] = '\0';
 | 
							global->interface[length] = '\0';
 | 
				
			||||||
		wl_list_insert(display->global_list.prev, &global->link);
 | 
							wl_list_insert(display->global_list.prev, &global->link);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							if (strcmp(global->interface, "visual") == 0)
 | 
				
			||||||
 | 
								add_visual(display, global);
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	display->proxy.display = display;
 | 
						display->proxy.display = display;
 | 
				
			||||||
| 
						 | 
					@ -327,9 +376,10 @@ wl_surface_destroy(struct wl_surface *surface)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
WL_EXPORT void
 | 
					WL_EXPORT void
 | 
				
			||||||
wl_surface_attach(struct wl_surface *surface, uint32_t name,
 | 
					wl_surface_attach(struct wl_surface *surface, uint32_t name,
 | 
				
			||||||
		  int32_t width, int32_t height, uint32_t stride)
 | 
							  int32_t width, int32_t height, uint32_t stride,
 | 
				
			||||||
 | 
							  struct wl_visual *visual)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	uint32_t request[6];
 | 
						uint32_t request[7];
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	request[0] = surface->proxy.id;
 | 
						request[0] = surface->proxy.id;
 | 
				
			||||||
	request[1] = WL_SURFACE_ATTACH | ((sizeof request) << 16);
 | 
						request[1] = WL_SURFACE_ATTACH | ((sizeof request) << 16);
 | 
				
			||||||
| 
						 | 
					@ -337,6 +387,9 @@ wl_surface_attach(struct wl_surface *surface, uint32_t name,
 | 
				
			||||||
	request[3] = width;
 | 
						request[3] = width;
 | 
				
			||||||
	request[4] = height;
 | 
						request[4] = height;
 | 
				
			||||||
	request[5] = stride;
 | 
						request[5] = stride;
 | 
				
			||||||
 | 
						request[6] = visual->proxy.id;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						printf("attach, visual id is %d\n", visual->proxy.id);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	wl_connection_write(surface->proxy.display->connection,
 | 
						wl_connection_write(surface->proxy.display->connection,
 | 
				
			||||||
			    request, sizeof request);
 | 
								    request, sizeof request);
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -32,6 +32,7 @@
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct wl_display;
 | 
					struct wl_display;
 | 
				
			||||||
struct wl_surface;
 | 
					struct wl_surface;
 | 
				
			||||||
 | 
					struct wl_visual;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#define WL_DISPLAY_READABLE 0x01
 | 
					#define WL_DISPLAY_READABLE 0x01
 | 
				
			||||||
#define WL_DISPLAY_WRITABLE 0x02
 | 
					#define WL_DISPLAY_WRITABLE 0x02
 | 
				
			||||||
| 
						 | 
					@ -58,6 +59,12 @@ void wl_display_set_event_handler(struct wl_display *display,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct wl_compositor *
 | 
					struct wl_compositor *
 | 
				
			||||||
wl_display_get_compositor(struct wl_display *display);
 | 
					wl_display_get_compositor(struct wl_display *display);
 | 
				
			||||||
 | 
					struct wl_visual *
 | 
				
			||||||
 | 
					wl_display_get_argb_visual(struct wl_display *display);
 | 
				
			||||||
 | 
					struct wl_visual *
 | 
				
			||||||
 | 
					wl_display_get_premultiplied_argb_visual(struct wl_display *display);
 | 
				
			||||||
 | 
					struct wl_visual *
 | 
				
			||||||
 | 
					wl_display_get_rgb_visual(struct wl_display *display);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct wl_surface *
 | 
					struct wl_surface *
 | 
				
			||||||
wl_compositor_create_surface(struct wl_compositor *compositor);
 | 
					wl_compositor_create_surface(struct wl_compositor *compositor);
 | 
				
			||||||
| 
						 | 
					@ -65,8 +72,9 @@ void
 | 
				
			||||||
wl_compositor_commit(struct wl_compositor *compositor, uint32_t key);
 | 
					wl_compositor_commit(struct wl_compositor *compositor, uint32_t key);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void wl_surface_destroy(struct wl_surface *surface);
 | 
					void wl_surface_destroy(struct wl_surface *surface);
 | 
				
			||||||
void wl_surface_attach(struct wl_surface *surface,
 | 
					void wl_surface_attach(struct wl_surface *surface, uint32_t name,
 | 
				
			||||||
		       uint32_t name, int32_t width, int32_t height, uint32_t stride);
 | 
							       int32_t width, int32_t height, uint32_t stride,
 | 
				
			||||||
 | 
							       struct wl_visual *visual);
 | 
				
			||||||
void wl_surface_map(struct wl_surface *surface,
 | 
					void wl_surface_map(struct wl_surface *surface,
 | 
				
			||||||
		    int32_t x, int32_t y, int32_t width, int32_t height);
 | 
							    int32_t x, int32_t y, int32_t width, int32_t height);
 | 
				
			||||||
void wl_surface_copy(struct wl_surface *surface, int32_t dst_x, int32_t dst_y,
 | 
					void wl_surface_copy(struct wl_surface *surface, int32_t dst_x, int32_t dst_y,
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -127,7 +127,7 @@ wl_client_demarshal(struct wl_client *client, struct wl_object *target,
 | 
				
			||||||
	ffi_type *types[20];
 | 
						ffi_type *types[20];
 | 
				
			||||||
	ffi_cif cif;
 | 
						ffi_cif cif;
 | 
				
			||||||
	uint32_t *p, result;
 | 
						uint32_t *p, result;
 | 
				
			||||||
	int i, j, count;
 | 
						int i, count;
 | 
				
			||||||
	union {
 | 
						union {
 | 
				
			||||||
		uint32_t uint32;
 | 
							uint32_t uint32;
 | 
				
			||||||
		const char *string;
 | 
							const char *string;
 | 
				
			||||||
| 
						 | 
					@ -161,7 +161,6 @@ wl_client_demarshal(struct wl_client *client, struct wl_object *target,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	wl_connection_copy(client->connection, data, size);
 | 
						wl_connection_copy(client->connection, data, size);
 | 
				
			||||||
	p = &data[2];
 | 
						p = &data[2];
 | 
				
			||||||
	j = 0;
 | 
					 | 
				
			||||||
	for (i = 2; i < count; i++) {
 | 
						for (i = 2; i < count; i++) {
 | 
				
			||||||
		switch (method->signature[i - 2]) {
 | 
							switch (method->signature[i - 2]) {
 | 
				
			||||||
		case 'u':
 | 
							case 'u':
 | 
				
			||||||
| 
						 | 
					@ -180,11 +179,8 @@ wl_client_demarshal(struct wl_client *client, struct wl_object *target,
 | 
				
			||||||
			object = wl_hash_lookup(client->display->objects, *p);
 | 
								object = wl_hash_lookup(client->display->objects, *p);
 | 
				
			||||||
			if (object == NULL)
 | 
								if (object == NULL)
 | 
				
			||||||
				printf("unknown object (%d)\n", *p);
 | 
									printf("unknown object (%d)\n", *p);
 | 
				
			||||||
			if (object->interface != method->types[j])
 | 
					 | 
				
			||||||
				printf("wrong object type\n");
 | 
					 | 
				
			||||||
			values[i].object = object;
 | 
								values[i].object = object;
 | 
				
			||||||
			p++;
 | 
								p++;
 | 
				
			||||||
			j++;
 | 
					 | 
				
			||||||
			break;
 | 
								break;
 | 
				
			||||||
		case 'n':
 | 
							case 'n':
 | 
				
			||||||
			types[i] = &ffi_type_uint32;
 | 
								types[i] = &ffi_type_uint32;
 | 
				
			||||||
| 
						 | 
					@ -369,7 +365,7 @@ wl_client_destroy(struct wl_client *client)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static const struct wl_method surface_methods[] = {
 | 
					static const struct wl_method surface_methods[] = {
 | 
				
			||||||
	{ "destroy", "" },
 | 
						{ "destroy", "" },
 | 
				
			||||||
	{ "attach", "uuuu" },
 | 
						{ "attach", "uuuuo" },
 | 
				
			||||||
	{ "map", "iiii" },
 | 
						{ "map", "iiii" },
 | 
				
			||||||
	{ "copy", "iiuuiiii" },
 | 
						{ "copy", "iiuuiiii" },
 | 
				
			||||||
	{ "damage", "iiii" }
 | 
						{ "damage", "iiii" }
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -142,7 +142,8 @@ struct wl_surface_interface {
 | 
				
			||||||
			struct wl_surface *surface);
 | 
								struct wl_surface *surface);
 | 
				
			||||||
	void (*attach)(struct wl_client *client,
 | 
						void (*attach)(struct wl_client *client,
 | 
				
			||||||
		       struct wl_surface *surface, uint32_t name, 
 | 
							       struct wl_surface *surface, uint32_t name, 
 | 
				
			||||||
		       uint32_t width, uint32_t height, uint32_t stride);
 | 
							       uint32_t width, uint32_t height, uint32_t stride,
 | 
				
			||||||
 | 
							       struct wl_object *visual);
 | 
				
			||||||
	void (*map)(struct wl_client *client,
 | 
						void (*map)(struct wl_client *client,
 | 
				
			||||||
		    struct wl_surface *surface,
 | 
							    struct wl_surface *surface,
 | 
				
			||||||
		    int32_t x, int32_t y, int32_t width, int32_t height);
 | 
							    int32_t x, int32_t y, int32_t width, int32_t height);
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
							
								
								
									
										5
									
								
								window.c
									
										
									
									
									
								
							
							
						
						
									
										5
									
								
								window.c
									
										
									
									
									
								
							| 
						 | 
					@ -84,6 +84,7 @@ window_draw(struct window *window)
 | 
				
			||||||
	int border = 2, radius = 5;
 | 
						int border = 2, radius = 5;
 | 
				
			||||||
	cairo_text_extents_t extents;
 | 
						cairo_text_extents_t extents;
 | 
				
			||||||
	cairo_pattern_t *gradient, *outline, *bright, *dim;
 | 
						cairo_pattern_t *gradient, *outline, *bright, *dim;
 | 
				
			||||||
 | 
						struct wl_visual *visual;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	surface = cairo_image_surface_create(CAIRO_FORMAT_RGB24,
 | 
						surface = cairo_image_surface_create(CAIRO_FORMAT_RGB24,
 | 
				
			||||||
					     window->width + window->margin * 2,
 | 
										     window->width + window->margin * 2,
 | 
				
			||||||
| 
						 | 
					@ -156,11 +157,13 @@ window_draw(struct window *window)
 | 
				
			||||||
	window->buffer = buffer_create_from_cairo_surface(window->fd, surface);
 | 
						window->buffer = buffer_create_from_cairo_surface(window->fd, surface);
 | 
				
			||||||
	cairo_surface_destroy(surface);
 | 
						cairo_surface_destroy(surface);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						visual = wl_display_get_premultiplied_argb_visual(window->display);
 | 
				
			||||||
	wl_surface_attach(window->surface,
 | 
						wl_surface_attach(window->surface,
 | 
				
			||||||
			  window->buffer->name,
 | 
								  window->buffer->name,
 | 
				
			||||||
			  window->buffer->width,
 | 
								  window->buffer->width,
 | 
				
			||||||
			  window->buffer->height,
 | 
								  window->buffer->height,
 | 
				
			||||||
			  window->buffer->stride);
 | 
								  window->buffer->stride,
 | 
				
			||||||
 | 
								  visual);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	wl_surface_map(window->surface,
 | 
						wl_surface_map(window->surface,
 | 
				
			||||||
		       window->x - window->margin,
 | 
							       window->x - window->margin,
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue