u/Senior-Question693

What's up with drag&drop in Wayland?

I'm making a file manager from scratch and i can't figure out the drag&drop functionality, after hunting for docs on the internet i found (this)[https://emersion.fr/blog/2020/wayland-clipboard-drag-and-drop/] blog-post, but it mentions only text, what about files (like when you drag&drop a markdown file into a browser to read it or when you drag&drop a video into a player)? Surely it's gotta be different (at least the mime type in the send and cancel callbacks) but i can't figure out in what way, here is the code i came up with:


#include <stdint.h>
#include <stdio.h>
#include <string.h>
#include <wayland-client-core.h>
#include <wayland-client-protocol.h>
#include <wayland-client.h>
#include <wayland-util.h>

typedef struct wayland_data {
    struct wl_data_device_manager* data_device_manager;
    struct wl_data_source* data_source;
    struct wl_seat* seat;
    struct wl_registry* registry;
    struct wl_display* display;
    enum wl_data_device_manager_dnd_action last_dnd_action;
} wayland_data;

void handle_global(void* data, struct wl_registry* registry,
        uint32_t name, const char* interface,
        uint32_t version) {
    wayland_data* wdata = (wayland_data*)data;

    if (strcmp(interface, wl_data_device_manager_interface.name) == 0) {
		wdata->data_device_manager = wl_registry_bind(registry, name,
			&wl_data_device_manager_interface, 3);
	} else if (strcmp(interface, wl_seat_interface.name) == 0 && wdata->seat == NULL) {
		wdata->seat = wl_registry_bind(registry, name, &wl_seat_interface, 1);
	}
}
void handle_global_remove(void* data, struct wl_registry* registry, uint32_t name) {/*who cares*/}

static const struct wl_registry_listener registry_listener = {
    .global = handle_global,   
    .global_remove = handle_global_remove,
};

static void data_source_handle_target(void* data, struct wl_data_source* source, const char* mime_type) {
    if (mime_type != NULL) {
        printf("would accept %s if dropped\n", mime_type);
    } else {
        printf("wouldn't accept if dropped\n");
    }
}

static void data_source_handle_action(void *data, struct wl_data_source *source,
		uint32_t dnd_action) {
    wayland_data* wdata = (wayland_data*)data;
	wdata->last_dnd_action = dnd_action;
	switch (dnd_action) {
	case WL_DATA_DEVICE_MANAGER_DND_ACTION_MOVE:
		printf("Destination would perform a move action if dropped\n");
		break;
	case WL_DATA_DEVICE_MANAGER_DND_ACTION_COPY:
		printf("Destination would perform a copy action if dropped\n");
		break;
	case WL_DATA_DEVICE_MANAGER_DND_ACTION_NONE:
		printf("Destination would reject the drag if dropped\n");
		break;
	}
}

static const struct wl_data_source_listener data_source_listener = {
    .action = data_source_handle_action,
    .target = data_source_handle_target,
};
int main(int argc, char *argv[]) {
    wayland_data data = {0};
    data.last_dnd_action = WL_DATA_DEVICE_MANAGER_DND_ACTION_NONE;
    
    data.display = wl_display_connect(NULL);
    if(!data.display) printf("failed to connect to display\n"); return 1;
    data.registry = wl_display_get_registry(NULL);
    wl_registry_add_listener(data.registry, &registry_listener, &data);
    wl_display_roundtrip(data.display);

    if (data.seat == NULL) {printf("no seat:(\n"); return 1;}
    if (data.data_device_manager == NULL) {printf("no data_device_manager:(\n"); return 1;}

    data.data_source = wl_data_device_manager_create_data_source(data.data_device_manager);
    wl_data_source_add_listener(data.data_source, &data_source_listener, &data);
    return 0;
}

(keep in mind that it's not the final code yet and there is no send and cancel functions)

reddit.com
u/Senior-Question693 — 3 days ago

HEEELP!!! *bashes his head against the wall*

i've been making a library for text rendering for the past few months and i have done a lot of rewrites and i feel kinda stuck so your help will be greatly appreciated. Currently when i read the tables i get a stack overflow and i think scaler type really shouldn't be THAT big (the font i'm using is AdwaitaMono-Bold). there is quite a lot of files so you can find everything over on my github

u/Senior-Question693 — 6 days ago

How to get the string from a string builder?

String builders are cool but how do i get the string? The sb from core:strings appears to be just a [\dynamic\]u8 but i need a string, after quite a bit of googling i didn't find anything (maybe i'm just blind) so your help will be greatly appreciated (also it would be nice if it's a cstring cuz i'm making a c library)

reddit.com
u/Senior-Question693 — 7 days ago