swc

Unnamed repository; edit this file 'description' to name the repository.
git clone git://git.nihaljere.xyz/swc
Log | Files | Refs | README | LICENSE

commit 6797a556a742c59e837a53510d6eca1e26b6dffc
parent b7805fb9334c8725467c13573aa630cc751af1bc
Author: Michael Forney <mforney@mforney.org>
Date:   Thu, 16 Jan 2014 15:15:28 -0800

view: Add event signal and frame events

Diffstat:
Mlibswc/compositor.c | 2+-
Mlibswc/surface.c | 55++++++++++++++++++++++++++++++++++++-------------------
Mlibswc/surface.h | 8+++-----
Mlibswc/view.c | 9+++++++++
Mlibswc/view.h | 28++++++++++++++++++++++++----
5 files changed, 73 insertions(+), 29 deletions(-)

diff --git a/libswc/compositor.c b/libswc/compositor.c @@ -646,7 +646,7 @@ static void handle_drm_event(struct wl_listener * listener, void * data) if (compositor->pending_flips == 0) { wl_list_for_each(surface, &compositor->surfaces, link) - swc_surface_send_frame_callbacks(surface, event_data->time); + swc_view_frame(surface->view, event_data->time); } /* If we had scheduled updates that couldn't run because we were diff --git a/libswc/surface.c b/libswc/surface.c @@ -339,6 +339,32 @@ static void surface_destroy(struct wl_resource * resource) free(surface); } +static void handle_view_event(struct wl_listener * listener, void * data) +{ + struct swc_surface * surface + = CONTAINER_OF(listener, typeof(*surface), view_listener); + struct swc_event * event = data; + struct swc_view_event_data * event_data = event->data; + + switch (event->type) + { + case SWC_VIEW_EVENT_FRAME: + { + struct wl_resource * resource, * tmp; + + wl_list_for_each_safe(resource, tmp, + &surface->state.frame_callbacks, link) + { + wl_callback_send_done(resource, event_data->frame.time); + wl_resource_destroy(resource); + } + + wl_list_init(&surface->state.frame_callbacks); + break; + } + } +} + /** * Construct a new surface, adding it to the given client as id. * @@ -365,6 +391,7 @@ struct swc_surface * swc_surface_new(struct wl_client * client, surface->pending.commit = 0; surface->window = NULL; surface->view = NULL; + surface->view_listener.notify = &handle_view_event; surface->view_state = NULL; state_initialize(&surface->state, true); @@ -381,33 +408,23 @@ struct swc_surface * swc_surface_new(struct wl_client * client, return surface; } -void swc_surface_send_frame_callbacks(struct swc_surface * surface, - uint32_t time) -{ - struct wl_resource * resource, * tmp; - - wl_list_for_each_safe(resource, tmp, &surface->state.frame_callbacks, link) - { - wl_callback_send_done(resource, time); - wl_resource_destroy(resource); - } - - wl_list_init(&surface->state.frame_callbacks); -} - -void swc_surface_set_view(struct swc_surface * surface, - const struct swc_view * view) +void swc_surface_set_view(struct swc_surface * surface, struct swc_view * view) { if (surface->view == view) return; - if (surface->view && surface->view->impl->remove) - surface->view->impl->remove(surface); + if (surface->view) + { + if (surface->view->impl->remove) + surface->view->impl->remove(surface); + wl_list_remove(&surface->view_listener.link); + } surface->view = view; - if (surface->view) + if (view) { + wl_signal_add(&view->event_signal, &surface->view_listener); surface->view->impl->attach(surface, surface->state.buffer); surface->view->impl->update(surface); } diff --git a/libswc/surface.h b/libswc/surface.h @@ -85,7 +85,8 @@ struct swc_surface } pending; struct swc_window * window; - const struct swc_view * view; + struct swc_view * view; + struct wl_listener view_listener; void * view_state; uint32_t outputs; @@ -98,10 +99,7 @@ struct swc_surface struct swc_surface * swc_surface_new(struct wl_client * client, uint32_t version, uint32_t id); -void swc_surface_send_frame_callbacks(struct swc_surface * surface, - uint32_t time); -void swc_surface_set_view(struct swc_surface * surface, - const struct swc_view * view); +void swc_surface_set_view(struct swc_surface * surface, struct swc_view * view); void swc_surface_update(struct swc_surface * surface); diff --git a/libswc/view.c b/libswc/view.c @@ -22,14 +22,23 @@ */ #include "view.h" +#include "event.h" void swc_view_initialize(struct swc_view * view, const struct swc_view_impl * impl) { view->impl = impl; + wl_signal_init(&view->event_signal); } void swc_view_finalize(struct swc_view * view) { } +void swc_view_frame(struct swc_view * view, uint32_t time) +{ + struct swc_view_event_data data = { .view = view, .frame = { time } }; + + swc_send_event(&view->event_signal, SWC_VIEW_EVENT_FRAME, &data); +} + diff --git a/libswc/view.h b/libswc/view.h @@ -24,16 +24,34 @@ #ifndef SWC_VIEW_H #define SWC_VIEW_H -#include <stdbool.h> -#include <stdint.h> +#include "swc.h" -struct swc_buffer; struct swc_surface; -struct wl_resource; +struct swc_buffer; + +enum swc_view_event +{ + /* Sent when the view has displayed the next frame. */ + SWC_VIEW_EVENT_FRAME, +}; + +struct swc_view_event_data +{ + struct swc_view * view; + union + { + struct + { + uint32_t time; + } frame; + }; +}; struct swc_view { const struct swc_view_impl * impl; + + struct wl_signal event_signal; }; /** @@ -61,5 +79,7 @@ void swc_view_initialize(struct swc_view * view, void swc_view_finalize(struct swc_view * view); +void swc_view_frame(struct swc_view * view, uint32_t time); + #endif