diff options
author | Kristian Høgsberg <krh@redhat.com> | 2008-12-22 18:06:49 -0500 |
---|---|---|
committer | Kristian Høgsberg <krh@redhat.com> | 2008-12-22 18:06:49 -0500 |
commit | fabd4395ba309850403f94a459c3a7298351dd0a (patch) | |
tree | ca44b0d51d0560620fe2a1fa2453879cdba192c9 /wayland-client.c | |
parent | 12ea62e2112c754d62113e0656b223fbdbe351dd (diff) |
Track objects client side using a hash too.
This leads up to using the demarshal machinery for decoding events
in the client library.
Diffstat (limited to 'wayland-client.c')
-rw-r--r-- | wayland-client.c | 75 |
1 files changed, 51 insertions, 24 deletions
diff --git a/wayland-client.c b/wayland-client.c index 00ca30c..2087a92 100644 --- a/wayland-client.c +++ b/wayland-client.c @@ -48,8 +48,7 @@ struct wl_global { }; struct wl_proxy { - const struct wl_interface *interface; - uint32_t id; + struct wl_object base; struct wl_display *display; }; @@ -59,6 +58,7 @@ struct wl_display { int fd; uint32_t id, id_count, next_range; uint32_t mask; + struct wl_hash *objects; struct wl_list global_list; struct wl_list visual_list; @@ -119,10 +119,12 @@ add_visual(struct wl_display *display, struct wl_global *global) if (visual == NULL) return; - visual->proxy.interface = &wl_visual_interface; - visual->proxy.id = global->id; + visual->proxy.base.interface = &wl_visual_interface; + visual->proxy.base.id = global->id; + visual->proxy.base.implementation = NULL; visual->proxy.display = display; wl_list_insert(display->visual_list.prev, &visual->link); + wl_hash_insert(display->objects, &visual->proxy.base); } WL_EXPORT struct wl_visual * @@ -177,12 +179,15 @@ wl_display_create(const char *name, size_t name_size) return NULL; } + display->objects = wl_hash_create(); wl_list_init(&display->global_list); wl_list_init(&display->visual_list); - display->proxy.interface = &wl_display_interface; - display->proxy.id = wl_display_get_object_id(display, "display", 1); + display->proxy.base.interface = &wl_display_interface; + display->proxy.base.implementation = NULL; + display->proxy.base.id = 1; display->proxy.display = display; + wl_hash_insert(display->objects, &display->proxy.base); display->connection = wl_connection_create(display->fd, connection_update, @@ -234,6 +239,24 @@ wl_display_get_fd(struct wl_display *display, return display->fd; } +struct wl_output_listener { + void (*geometry)(struct wl_display *display, + struct wl_output *output, + int32_t width, int32_t height); +}; + +static void +handle_geometry(struct wl_display *display, + struct wl_output *output, int32_t width, int32_t height) +{ + output->width = width; + output->height = height; +} + +static const struct wl_output_listener output_listener = { + handle_geometry +}; + static void add_output(struct wl_display *display, struct wl_global *global) { @@ -243,10 +266,12 @@ add_output(struct wl_display *display, struct wl_global *global) if (output == NULL) return; - output->proxy.interface = &wl_output_interface; - output->proxy.id = global->id; + output->proxy.base.interface = &wl_output_interface; + output->proxy.base.implementation = (void(**)(void)) &output_listener; + output->proxy.base.id = global->id; output->proxy.display = display; display->output = output; + wl_hash_insert(display->objects, &output->proxy.base); } static void @@ -303,25 +328,27 @@ handle_output_event(struct wl_display *display, { switch (opcode) { case WL_OUTPUT_GEOMETRY: - display->output->width = p[0]; - display->output->height = p[1]; + handle_geometry(display, display->output, p[0], p[1]); break; } } static void handle_event(struct wl_display *display, - uint32_t object, uint32_t opcode, uint32_t size) + uint32_t id, uint32_t opcode, uint32_t size) { uint32_t p[32]; + struct wl_object *object; wl_connection_copy(display->connection, p, size); - if (object == 1) { + object = wl_hash_lookup(display->objects, id); + + if (object == &display->proxy.base) handle_display_event(display, opcode, p + 2, size); - } else if (object == display->output->proxy.id) { + else if (object == &display->output->proxy.base && opcode == 0) handle_output_event(display, opcode, p + 2, size); - } else if (display->event_handler != NULL) - display->event_handler(display, object, opcode, size, p + 2, + else if (display->event_handler != NULL) + display->event_handler(display, id, opcode, size, p + 2, display->event_handler_data); wl_connection_consume(display->connection, size); } @@ -394,8 +421,8 @@ wl_display_get_compositor(struct wl_display *display) return NULL; compositor = malloc(sizeof *compositor); - compositor->proxy.interface = &wl_compositor_interface; - compositor->proxy.id = id; + compositor->proxy.base.interface = &wl_compositor_interface; + compositor->proxy.base.id = id; compositor->proxy.display = display; return compositor; @@ -404,12 +431,12 @@ wl_display_get_compositor(struct wl_display *display) static void wl_proxy_vmarshal(struct wl_proxy *target, uint32_t opcode, va_list ap) { - struct wl_proxy *proxy; + struct wl_object *object; uint32_t args[32], length, *p, size; const char *s, *signature; int i, count; - signature = target->interface->methods[opcode].signature; + signature = target->base.interface->methods[opcode].signature; count = strlen(signature); /* FIXME: Make sure we don't overwrite args array. */ @@ -429,8 +456,8 @@ wl_proxy_vmarshal(struct wl_proxy *target, uint32_t opcode, va_list ap) break; case 'n': case 'o': - proxy = va_arg(ap, struct wl_proxy *); - *p++ = proxy->id; + object = va_arg(ap, struct wl_object *); + *p++ = object->id; break; default: assert(0); @@ -439,7 +466,7 @@ wl_proxy_vmarshal(struct wl_proxy *target, uint32_t opcode, va_list ap) } size = (p - args) * sizeof *p; - args[0] = target->id; + args[0] = target->base.id; args[1] = opcode | (size << 16); wl_connection_write(target->display->connection, args, size); } @@ -463,8 +490,8 @@ wl_compositor_create_surface(struct wl_compositor *compositor) if (surface == NULL) return NULL; - surface->proxy.interface = &wl_surface_interface; - surface->proxy.id = wl_display_allocate_id(compositor->proxy.display); + surface->proxy.base.interface = &wl_surface_interface; + surface->proxy.base.id = wl_display_allocate_id(compositor->proxy.display); surface->proxy.display = compositor->proxy.display; wl_proxy_marshal(&compositor->proxy, WL_COMPOSITOR_CREATE_SURFACE, surface); |