data-control-v1: update to latest protocol proposal

This commit is contained in:
emersion 2018-12-30 02:52:03 +01:00
parent 340281b48a
commit 69e7fd61b7
No known key found for this signature in database
GPG key ID: 0FDE7BE0E88F5E48
3 changed files with 105 additions and 102 deletions

View file

@ -15,20 +15,20 @@
struct wlr_data_control_manager_v1 { struct wlr_data_control_manager_v1 {
struct wl_global *global; struct wl_global *global;
struct wl_list resources; // wl_resource_get_link struct wl_list resources; // wl_resource_get_link
struct wl_list controls; // wlr_data_control_v1::link struct wl_list devices; // wlr_data_control_device_v1::link
struct { struct {
struct wl_signal destroy; struct wl_signal destroy;
struct wl_signal new_control; // wlr_data_control_v1 struct wl_signal new_device; // wlr_data_control_device_v1
} events; } events;
struct wl_listener display_destroy; struct wl_listener display_destroy;
}; };
struct wlr_data_control_v1 { struct wlr_data_control_device_v1 {
struct wl_resource *resource; struct wl_resource *resource;
struct wlr_data_control_manager_v1 *manager; struct wlr_data_control_manager_v1 *manager;
struct wl_list link; // wlr_data_control_manager_v1::controls struct wl_list link; // wlr_data_control_manager_v1::devices
struct wlr_seat *seat; struct wlr_seat *seat;
struct wl_resource *selection_offer_resource; // current selection offer struct wl_resource *selection_offer_resource; // current selection offer
@ -42,6 +42,7 @@ struct wlr_data_control_manager_v1 *wlr_data_control_manager_v1_create(
void wlr_data_control_manager_v1_destroy( void wlr_data_control_manager_v1_destroy(
struct wlr_data_control_manager_v1 *manager); struct wlr_data_control_manager_v1 *manager);
void wlr_data_control_v1_destroy(struct wlr_data_control_v1 *control); void wlr_data_control_device_v1_destroy(
struct wlr_data_control_device_v1 *device);
#endif #endif

View file

@ -41,8 +41,9 @@
</description> </description>
<interface name="zwlr_data_control_manager_v1" version="1"> <interface name="zwlr_data_control_manager_v1" version="1">
<description summary="manager to create per-seat data controls"> <description summary="manager to control data devices">
This interface is a manager that allows creating per-seat data controls. This interface is a manager that allows creating per-seat data device
controls.
</description> </description>
<request name="create_data_source"> <request name="create_data_source">
@ -53,11 +54,11 @@
summary="data source to create"/> summary="data source to create"/>
</request> </request>
<request name="get_data_control"> <request name="get_data_device">
<description summary="get a data control for a seat"> <description summary="get a data device for a seat">
Create a data control that can be used to manage a seat's data device. Create a data device that can be used to manage a seat's selection.
</description> </description>
<arg name="id" type="new_id" interface="zwlr_data_control_v1"/> <arg name="id" type="new_id" interface="zwlr_data_control_device_v1"/>
<arg name="seat" type="object" interface="wl_seat"/> <arg name="seat" type="object" interface="wl_seat"/>
</request> </request>
@ -69,17 +70,16 @@
</request> </request>
</interface> </interface>
<interface name="zwlr_data_control_v1" version="1"> <interface name="zwlr_data_control_device_v1" version="1">
<description summary="manage a data device for a seat"> <description summary="manage a data device for a seat">
This interface allows a client to manage a data device associated with a This interface allows a client to manage a seat's selection.
seat.
When the seat is destroyed, this object becomes inert. When the seat is destroyed, this object becomes inert.
</description> </description>
<request name="set_selection"> <request name="set_selection">
<description summary="copy data to the selection"> <description summary="copy data to the selection">
All objects created by the manager will still remain valid, until their All objects created by the device will still remain valid, until their
appropriate destroy request has been called. appropriate destroy request has been called.
</description> </description>
<arg name="source" type="object" interface="zwlr_data_control_source_v1" <arg name="source" type="object" interface="zwlr_data_control_source_v1"
@ -87,18 +87,19 @@
</request> </request>
<request name="destroy" type="destructor"> <request name="destroy" type="destructor">
<description summary="destroy this control"> <description summary="destroy this data device">
Destroys the data control object. Destroys the data device object.
</description> </description>
</request> </request>
<event name="data_offer"> <event name="data_offer">
<description summary="introduce a new wlr_data_control_offer"> <description summary="introduce a new wlr_data_control_offer">
The data_offer event introduces a new wlr_data_control_offer object, The data_offer event introduces a new wlr_data_control_offer object,
which will subsequently be used in the wlr_data_control.selection event. which will subsequently be used in the wlr_data_control_device.selection
Immediately following the wlr_data_control.data_offer event, the new event. Immediately following the wlr_data_control_device.data_offer
data_offer object will send out wlr_data_control_offer.offer events to event, the new data_offer object will send out
describe the MIME types it offers. wlr_data_control_offer.offer events to describe the MIME types it
offers.
This event replaces the previous data offer, which should be destroyed This event replaces the previous data offer, which should be destroyed
by the client. by the client.
@ -110,10 +111,10 @@
<description summary="introduce a new wlr_data_control_offer"> <description summary="introduce a new wlr_data_control_offer">
The selection event is sent out to notify the client of a new The selection event is sent out to notify the client of a new
wlr_data_control_offer for the selection for this device. The wlr_data_control_offer for the selection for this device. The
wlr_data_control.data_offer and the wlr_data_control_offer.offer events wlr_data_control_device.data_offer and the wlr_data_control_offer.offer
are sent out immediately before this event to introduce the data offer events are sent out immediately before this event to introduce the data
object. The selection event is sent to a client when a new selection is offer object. The selection event is sent to a client when a new
set. The wlr_data_control_offer is valid until a new selection is set. The wlr_data_control_offer is valid until a new
wlr_data_control_offer or NULL is received. The client must destroy the wlr_data_control_offer or NULL is received. The client must destroy the
previous selection wlr_data_control_offer, if any, upon receiving this previous selection wlr_data_control_offer, if any, upon receiving this
event. event.
@ -140,7 +141,7 @@
<enum name="error"> <enum name="error">
<entry name="invalid_offer" value="1" <entry name="invalid_offer" value="1"
summary="offer sent after wlr_data_control.set_selection"/> summary="offer sent after wlr_data_control_device.set_selection"/>
</enum> </enum>
<request name="offer"> <request name="offer">
@ -148,7 +149,8 @@
This request adds a MIME type to the set of MIME types advertised to This request adds a MIME type to the set of MIME types advertised to
targets. Can be called several times to offer multiple types. targets. Can be called several times to offer multiple types.
Calling this after wlr_data_control.set_selection is a protocol error. Calling this after wlr_data_control_device.set_selection is a protocol
error.
</description> </description>
<arg name="mime_type" type="string" <arg name="mime_type" type="string"
summary="MIME type offered by the data source"/> summary="MIME type offered by the data source"/>

View file

@ -107,7 +107,7 @@ static void source_handle_resource_destroy(struct wl_resource *resource) {
static const struct zwlr_data_control_offer_v1_interface offer_impl; static const struct zwlr_data_control_offer_v1_interface offer_impl;
static struct wlr_data_control_v1 *control_from_offer_resource( static struct wlr_data_control_device_v1 *control_from_offer_resource(
struct wl_resource *resource) { struct wl_resource *resource) {
assert(wl_resource_instance_of(resource, assert(wl_resource_instance_of(resource,
&zwlr_data_control_offer_v1_interface, &offer_impl)); &zwlr_data_control_offer_v1_interface, &offer_impl));
@ -116,12 +116,12 @@ static struct wlr_data_control_v1 *control_from_offer_resource(
static void offer_handle_receive(struct wl_client *client, static void offer_handle_receive(struct wl_client *client,
struct wl_resource *resource, const char *mime_type, int fd) { struct wl_resource *resource, const char *mime_type, int fd) {
struct wlr_data_control_v1 *control = control_from_offer_resource(resource); struct wlr_data_control_device_v1 *device = control_from_offer_resource(resource);
if (control == NULL || control->seat->selection_source == NULL) { if (device == NULL || device->seat->selection_source == NULL) {
close(fd); close(fd);
return; return;
} }
wlr_data_source_send(control->seat->selection_source, mime_type, fd); wlr_data_source_send(device->seat->selection_source, mime_type, fd);
} }
static void offer_handle_destroy(struct wl_client *client, static void offer_handle_destroy(struct wl_client *client,
@ -135,25 +135,25 @@ static const struct zwlr_data_control_offer_v1_interface offer_impl = {
}; };
static void offer_handle_resource_destroy(struct wl_resource *resource) { static void offer_handle_resource_destroy(struct wl_resource *resource) {
struct wlr_data_control_v1 *control = control_from_offer_resource(resource); struct wlr_data_control_device_v1 *device = control_from_offer_resource(resource);
if (control != NULL) { if (device != NULL) {
control->selection_offer_resource = NULL; device->selection_offer_resource = NULL;
} }
} }
static struct wl_resource *create_offer(struct wlr_data_control_v1 *control, static struct wl_resource *create_offer(struct wlr_data_control_device_v1 *device,
struct wlr_data_source *source) { struct wlr_data_source *source) {
struct wl_client *client = wl_resource_get_client(control->resource); struct wl_client *client = wl_resource_get_client(device->resource);
uint32_t version = wl_resource_get_version(control->resource); uint32_t version = wl_resource_get_version(device->resource);
struct wl_resource *resource = wl_resource_create(client, struct wl_resource *resource = wl_resource_create(client,
&zwlr_data_control_offer_v1_interface, version, 0); &zwlr_data_control_offer_v1_interface, version, 0);
if (resource == NULL) { if (resource == NULL) {
return NULL; return NULL;
} }
wl_resource_set_implementation(resource, &offer_impl, control, wl_resource_set_implementation(resource, &offer_impl, device,
offer_handle_resource_destroy); offer_handle_resource_destroy);
zwlr_data_control_v1_send_data_offer(control->resource, resource); zwlr_data_control_device_v1_send_data_offer(device->resource, resource);
char **p; char **p;
wl_array_for_each(p, &source->mime_types) { wl_array_for_each(p, &source->mime_types) {
@ -164,28 +164,28 @@ static struct wl_resource *create_offer(struct wlr_data_control_v1 *control,
} }
static const struct zwlr_data_control_v1_interface control_impl; static const struct zwlr_data_control_device_v1_interface control_impl;
static struct wlr_data_control_v1 *control_from_resource( static struct wlr_data_control_device_v1 *control_from_resource(
struct wl_resource *resource) { struct wl_resource *resource) {
assert(wl_resource_instance_of(resource, assert(wl_resource_instance_of(resource,
&zwlr_data_control_v1_interface, &control_impl)); &zwlr_data_control_device_v1_interface, &control_impl));
return wl_resource_get_user_data(resource); return wl_resource_get_user_data(resource);
} }
static void control_handle_set_selection(struct wl_client *client, static void control_handle_set_selection(struct wl_client *client,
struct wl_resource *control_resource, struct wl_resource *control_resource,
struct wl_resource *source_resource) { struct wl_resource *source_resource) {
struct wlr_data_control_v1 *control = struct wlr_data_control_device_v1 *device =
control_from_resource(control_resource); control_from_resource(control_resource);
struct client_data_source *source = source_from_resource(source_resource); struct client_data_source *source = source_from_resource(source_resource);
if (control == NULL) { if (device == NULL) {
return; return;
} }
struct wlr_data_source *wlr_source = source ? &source->source : NULL; struct wlr_data_source *wlr_source = source ? &source->source : NULL;
struct wl_display *display = wl_client_get_display(client); struct wl_display *display = wl_client_get_display(client);
wlr_seat_set_selection(control->seat, wlr_source, wlr_seat_set_selection(device->seat, wlr_source,
wl_display_next_serial(display)); wl_display_next_serial(display));
} }
@ -194,65 +194,65 @@ static void control_handle_destroy(struct wl_client *client,
wl_resource_destroy(control_resource); wl_resource_destroy(control_resource);
} }
static const struct zwlr_data_control_v1_interface control_impl = { static const struct zwlr_data_control_device_v1_interface control_impl = {
.set_selection = control_handle_set_selection, .set_selection = control_handle_set_selection,
.destroy = control_handle_destroy, .destroy = control_handle_destroy,
}; };
static void control_send_selection(struct wlr_data_control_v1 *control) { static void control_send_selection(struct wlr_data_control_device_v1 *device) {
struct wlr_data_source *source = control->seat->selection_source; struct wlr_data_source *source = device->seat->selection_source;
if (control->selection_offer_resource != NULL) { if (device->selection_offer_resource != NULL) {
// Make the offer inert // Make the offer inert
wl_resource_set_user_data(control->selection_offer_resource, NULL); wl_resource_set_user_data(device->selection_offer_resource, NULL);
} }
control->selection_offer_resource = NULL; device->selection_offer_resource = NULL;
if (source != NULL) { if (source != NULL) {
control->selection_offer_resource = create_offer(control, source); device->selection_offer_resource = create_offer(device, source);
if (control->selection_offer_resource == NULL) { if (device->selection_offer_resource == NULL) {
wl_resource_post_no_memory(control->resource); wl_resource_post_no_memory(device->resource);
return; return;
} }
} }
zwlr_data_control_v1_send_selection(control->resource, zwlr_data_control_device_v1_send_selection(device->resource,
control->selection_offer_resource); device->selection_offer_resource);
} }
static void control_handle_resource_destroy(struct wl_resource *resource) { static void control_handle_resource_destroy(struct wl_resource *resource) {
struct wlr_data_control_v1 *control = control_from_resource(resource); struct wlr_data_control_device_v1 *device = control_from_resource(resource);
wlr_data_control_v1_destroy(control); wlr_data_control_device_v1_destroy(device);
} }
static void control_handle_seat_destroy(struct wl_listener *listener, static void control_handle_seat_destroy(struct wl_listener *listener,
void *data) { void *data) {
struct wlr_data_control_v1 *control = struct wlr_data_control_device_v1 *device =
wl_container_of(listener, control, seat_destroy); wl_container_of(listener, device, seat_destroy);
wlr_data_control_v1_destroy(control); wlr_data_control_device_v1_destroy(device);
} }
static void control_handle_seat_selection(struct wl_listener *listener, static void control_handle_seat_selection(struct wl_listener *listener,
void *data) { void *data) {
struct wlr_data_control_v1 *control = struct wlr_data_control_device_v1 *device =
wl_container_of(listener, control, seat_selection); wl_container_of(listener, device, seat_selection);
control_send_selection(control); control_send_selection(device);
} }
void wlr_data_control_v1_destroy(struct wlr_data_control_v1 *control) { void wlr_data_control_device_v1_destroy(struct wlr_data_control_device_v1 *device) {
if (control == NULL) { if (device == NULL) {
return; return;
} }
zwlr_data_control_v1_send_finished(control->resource); zwlr_data_control_device_v1_send_finished(device->resource);
// Make the resources inert // Make the resources inert
wl_resource_set_user_data(control->resource, NULL); wl_resource_set_user_data(device->resource, NULL);
if (control->selection_offer_resource != NULL) { if (device->selection_offer_resource != NULL) {
wl_resource_set_user_data(control->selection_offer_resource, NULL); wl_resource_set_user_data(device->selection_offer_resource, NULL);
} }
wl_list_remove(&control->seat_destroy.link); wl_list_remove(&device->seat_destroy.link);
wl_list_remove(&control->seat_selection.link); wl_list_remove(&device->seat_selection.link);
wl_list_remove(&control->link); wl_list_remove(&device->link);
free(control); free(device);
} }
@ -287,7 +287,7 @@ static void manager_handle_create_data_source(struct wl_client *client,
source_handle_resource_destroy); source_handle_resource_destroy);
} }
static void manager_handle_get_data_control(struct wl_client *client, static void manager_handle_get_data_device(struct wl_client *client,
struct wl_resource *manager_resource, uint32_t id, struct wl_resource *manager_resource, uint32_t id,
struct wl_resource *seat_resource) { struct wl_resource *seat_resource) {
struct wlr_data_control_manager_v1 *manager = struct wlr_data_control_manager_v1 *manager =
@ -295,41 +295,41 @@ static void manager_handle_get_data_control(struct wl_client *client,
struct wlr_seat_client *seat_client = struct wlr_seat_client *seat_client =
wlr_seat_client_from_resource(seat_resource); wlr_seat_client_from_resource(seat_resource);
struct wlr_data_control_v1 *control = struct wlr_data_control_device_v1 *device =
calloc(1, sizeof(struct wlr_data_control_v1)); calloc(1, sizeof(struct wlr_data_control_device_v1));
if (control == NULL) { if (device == NULL) {
wl_resource_post_no_memory(manager_resource); wl_resource_post_no_memory(manager_resource);
return; return;
} }
control->manager = manager; device->manager = manager;
control->seat = seat_client->seat; device->seat = seat_client->seat;
uint32_t version = wl_resource_get_version(manager_resource); uint32_t version = wl_resource_get_version(manager_resource);
control->resource = wl_resource_create(client, device->resource = wl_resource_create(client,
&zwlr_data_control_v1_interface, version, id); &zwlr_data_control_device_v1_interface, version, id);
if (control->resource == NULL) { if (device->resource == NULL) {
wl_resource_post_no_memory(manager_resource); wl_resource_post_no_memory(manager_resource);
free(control); free(device);
return; return;
} }
wl_resource_set_implementation(control->resource, &control_impl, control, wl_resource_set_implementation(device->resource, &control_impl, device,
control_handle_resource_destroy); control_handle_resource_destroy);
struct wl_resource *resource = control->resource; struct wl_resource *resource = device->resource;
control->seat_destroy.notify = control_handle_seat_destroy; device->seat_destroy.notify = control_handle_seat_destroy;
wl_signal_add(&control->seat->events.destroy, &control->seat_destroy); wl_signal_add(&device->seat->events.destroy, &device->seat_destroy);
control->seat_selection.notify = control_handle_seat_selection; device->seat_selection.notify = control_handle_seat_selection;
wl_signal_add(&control->seat->events.selection, &control->seat_selection); wl_signal_add(&device->seat->events.selection, &device->seat_selection);
wl_list_insert(&manager->controls, &control->link); wl_list_insert(&manager->devices, &device->link);
wlr_signal_emit_safe(&manager->events.new_control, control); wlr_signal_emit_safe(&manager->events.new_device, device);
// At this point maybe the compositor decided to destroy the control. If // At this point maybe the compositor decided to destroy the device. If
// it's the case then the resource will be inert. // it's the case then the resource will be inert.
control = control_from_resource(resource); device = control_from_resource(resource);
if (control != NULL) { if (device != NULL) {
control_send_selection(control); control_send_selection(device);
} }
} }
@ -340,7 +340,7 @@ static void manager_handle_destroy(struct wl_client *client,
static const struct zwlr_data_control_manager_v1_interface manager_impl = { static const struct zwlr_data_control_manager_v1_interface manager_impl = {
.create_data_source = manager_handle_create_data_source, .create_data_source = manager_handle_create_data_source,
.get_data_control = manager_handle_get_data_control, .get_data_device = manager_handle_get_data_device,
.destroy = manager_handle_destroy, .destroy = manager_handle_destroy,
}; };
@ -378,9 +378,9 @@ struct wlr_data_control_manager_v1 *wlr_data_control_manager_v1_create(
return NULL; return NULL;
} }
wl_list_init(&manager->resources); wl_list_init(&manager->resources);
wl_list_init(&manager->controls); wl_list_init(&manager->devices);
wl_signal_init(&manager->events.destroy); wl_signal_init(&manager->events.destroy);
wl_signal_init(&manager->events.new_control); wl_signal_init(&manager->events.new_device);
manager->global = wl_global_create(display, manager->global = wl_global_create(display,
&zwlr_data_control_manager_v1_interface, DATA_CONTROL_MANAGER_VERSION, &zwlr_data_control_manager_v1_interface, DATA_CONTROL_MANAGER_VERSION,
@ -404,9 +404,9 @@ void wlr_data_control_manager_v1_destroy(
wlr_signal_emit_safe(&manager->events.destroy, manager); wlr_signal_emit_safe(&manager->events.destroy, manager);
struct wlr_data_control_v1 *control, *control_tmp; struct wlr_data_control_device_v1 *device, *control_tmp;
wl_list_for_each_safe(control, control_tmp, &manager->controls, link) { wl_list_for_each_safe(device, control_tmp, &manager->devices, link) {
wl_resource_destroy(control->resource); wl_resource_destroy(device->resource);
} }
struct wl_resource *resource, *resource_tmp; struct wl_resource *resource, *resource_tmp;