Remove remaining code for the old drop API

X11 and cocoa need to be ported to the new API
This commit is contained in:
Kovid Goyal 2026-02-08 14:45:24 +05:30
parent f3cda7e828
commit 5db41c7ba4
No known key found for this signature in database
GPG key ID: 06BC317B515ACE7C
7 changed files with 55 additions and 263 deletions

77
glfw/glfw3.h vendored
View file

@ -1291,8 +1291,6 @@ typedef struct GLFWcursor GLFWcursor;
*
* @ingroup input
*/
typedef struct GLFWDropData GLFWDropData;
typedef enum {
GLFW_RELEASE = 0,
GLFW_PRESS = 1,
@ -1406,7 +1404,7 @@ typedef struct GLFWDropEvent {
GLFWDropEventType type;
const char **mimes; size_t num_mimes;
double xpos, ypos; // Only valid for GLFW_DROP_ENTER and GLFW_DROP_MOVE
bool from_self;
bool from_self; // Only valid upto GLFW_DROP_DROP
ssize_t (*read_data)(GLFWwindow *w, struct GLFWDropEvent* ev, char *buffer, size_t sz); // Only valid for GLFW_DROP_DATA_AVAILABLE
void (*finish_drop)(GLFWwindow *w, GLFWDragOperationType op); // Only valid for GLFW_DROP_DROP and GLFW_DROP_DATA_AVAILABLE
} GLFWDropEvent;
@ -1811,43 +1809,6 @@ typedef void (* GLFWscrollfun)(GLFWwindow*,const GLFWScrollEvent*);
*/
typedef void (* GLFWkeyboardfun)(GLFWwindow*, GLFWkeyevent*);
/*! @brief The function pointer type for drag and drop callbacks.
*
* This is the function pointer type for drop callbacks. A drop
* callback function has the following signature:
* @code
* void function_name(GLFWwindow* window, GLFWDropData* drop)
* @endcode
*
* @param[in] window The window that received the event.
* @param[in] drop A heap-allocated opaque pointer representing the dropped data. Use
* @ref glfwGetDropMimeTypes to get available MIME types and
* @ref glfwReadDropData to read the data in chunks.
*
* @note The drop object is heap-allocated and remains valid until the
* application calls @ref glfwFinishDrop to free it. The application is
* responsible for calling glfwFinishDrop when it has finished reading
* the dropped data, even if reading fails or is not needed.
*
* @param[in] window The window that received the drop.
* @param[in] drop Opaque drop data pointer (heap-allocated).
* @param[in] from_self true if the drop originated from this application
* (i.e., the application is both the drag source and drop target), false
* if the drop came from an external application.
*
* @sa @ref path_drop
* @sa @ref glfwSetDropCallback
* @sa @ref glfwGetDropMimeTypes
* @sa @ref glfwReadDropData
* @sa @ref glfwFinishDrop
*
* @since Changed in version 4.0 to receive opaque drop data pointer.
* @since Changed in version 4.0 to receive from_self parameter.
*
* @ingroup input
*/
typedef void (* GLFWdropfun)(GLFWwindow*, GLFWDropData*, bool from_self);
/*! @brief Drag event types.
*
* These constants are used to identify the type of drag event.
@ -5030,42 +4991,6 @@ GLFWAPI GLFWcursorenterfun glfwSetCursorEnterCallback(GLFWwindow* window, GLFWcu
*/
GLFWAPI GLFWscrollfun glfwSetScrollCallback(GLFWwindow* window, GLFWscrollfun callback);
/*! @brief Sets the path drop callback.
*
* This function sets the path drop callback of the specified window, which is
* called when one or more dragged paths are dropped on the window.
*
* Because the path array and its strings may have been generated specifically
* for that event, they are not guaranteed to be valid after the callback has
* returned. If you wish to use them after the callback returns, you need to
* make a deep copy.
*
* @param[in] window The window whose callback to set.
* @param[in] callback The new file drop callback, or `NULL` to remove the
* currently set callback.
* @return The previously set callback, or `NULL` if no callback was set or the
* library had not been [initialized](@ref intro_init).
*
* @callback_signature
* @code
* void function_name(GLFWwindow* window, int path_count, const char* paths[])
* @endcode
* For more information about the callback parameters, see the
* [function pointer type](@ref GLFWdropfun).
*
* @errors Possible errors include @ref GLFW_NOT_INITIALIZED.
*
* @remark @wayland File drop is currently unimplemented.
*
* @thread_safety This function must only be called from the main thread.
*
* @sa @ref path_drop
*
* @since Added in version 3.1.
*
* @ingroup input
*/
GLFWAPI GLFWdropfun glfwSetDropCallback(GLFWwindow* window, GLFWdropfun callback);
GLFWAPI GLFWliveresizefun glfwSetLiveResizeCallback(GLFWwindow* window, GLFWliveresizefun callback);
GLFWAPI GLFWdropeventfun glfwSetDropEventCallback(GLFWwindow *window, GLFWdropeventfun callback);

26
glfw/input.c vendored
View file

@ -402,14 +402,6 @@ void _glfwInputCursorEnter(_GLFWwindow* window, bool entered)
window->callbacks.cursorEnter((GLFWwindow*) window, entered);
}
// Notifies shared code of files or directories dropped on a window
//
void _glfwInputDrop(_GLFWwindow* window, GLFWDropData* drop, bool from_self)
{
if (window->callbacks.drop)
window->callbacks.drop((GLFWwindow*) window, drop, from_self);
}
// Notifies shared code of a drag event
//
int _glfwInputDragEvent(_GLFWwindow* window, int event, double xpos, double ypos, const char** mime_types, int* mime_count)
@ -1142,16 +1134,6 @@ GLFWAPI GLFWscrollfun glfwSetScrollCallback(GLFWwindow* handle,
return cbfun;
}
GLFWAPI GLFWdropfun glfwSetDropCallback(GLFWwindow* handle, GLFWdropfun cbfun)
{
_GLFWwindow* window = (_GLFWwindow*) handle;
assert(window != NULL);
_GLFW_REQUIRE_INIT_OR_RETURN(NULL);
_GLFW_SWAP_POINTERS(window->callbacks.drop, cbfun);
return cbfun;
}
GLFWAPI GLFWdragfun glfwSetDragCallback(GLFWwindow* handle, GLFWdragfun cbfun)
{
_GLFWwindow* window = (_GLFWwindow*) handle;
@ -1206,14 +1188,6 @@ GLFWAPI ssize_t glfwSendDragData(GLFWDragSourceData* source_data, const void* da
return _glfwPlatformSendDragData(source_data, data, size);
}
GLFWAPI void glfwFinishDrop(GLFWDropData* drop, GLFWDragOperationType operation, bool success)
{
assert(drop != NULL);
_GLFW_REQUIRE_INIT();
_glfwPlatformFinishDrop(drop, operation, success);
}
GLFWAPI int glfwJoystickPresent(int jid)
{
_GLFWjoystick* js;

32
glfw/internal.h vendored
View file

@ -85,34 +85,6 @@ typedef struct _GLFWjoystick _GLFWjoystick;
typedef struct _GLFWtls _GLFWtls;
typedef struct _GLFWmutex _GLFWmutex;
// Drop data structure for chunked reading of drag and drop data
struct GLFWDropData {
const char** mime_types; // Array of available MIME types (owned by drop object)
int mime_count; // Number of MIME types
int mime_array_size; // Original array size for proper cleanup
char* current_mime; // Currently being read MIME type
int read_fd; // File descriptor for reading data (Wayland/X11)
size_t bytes_read; // Total bytes read so far for current mime
void* platform_data; // Platform-specific data (offer for Wayland, pasteboard for Cocoa)
bool eof_reached; // Whether EOF has been reached for current mime
// Platform-specific data fields
void* current_data; // NSData* (Cocoa) or unsigned char* from XGetWindowProperty (X11)
size_t data_offset; // Read offset in current data (Cocoa/X11)
#ifdef __APPLE__
// Cocoa specific fields
bool data_is_file_promise; // true if current_data is a file promise provider rather than NSData
void *file_handle, *file_io_error;
#endif
#ifdef _GLFW_X11
// X11-specific fields
size_t x11_data_size; // Size of current X11 data
unsigned long x11_drop_target; // Window handle where the drop occurred (X11)
unsigned long x11_drop_time; // Time from the drop event (X11)
unsigned long x11_source; // Source window for XdndFinished (X11)
int x11_version; // Xdnd protocol version (X11)
#endif
};
// Drag source data structure for chunked writing of drag data
// Lifetime is managed by the backend - freed on end of data, error, drag cancellation, or exit
struct GLFWDragSourceData {
@ -519,7 +491,6 @@ struct _GLFWwindow
GLFWkeyboardfun keyboard;
GLFWliveresizefun liveResize;
GLFWdropfun drop;
GLFWdragfun drag;
GLFWdragsourcefun dragSource;
@ -870,9 +841,6 @@ void _glfwInputCursorEnter(_GLFWwindow* window, bool entered);
int _glfwInputDragEvent(_GLFWwindow* window, int event, double xpos, double ypos, const char** mime_types, int* mime_count);
void _glfwInputDragSourceRequest(_GLFWwindow* window, const char* mime_type, GLFWDragSourceData* source_data);
// Platform functions for drop data reading
const char** _glfwPlatformGetDropMimeTypes(GLFWDropData* drop, int* count);
ssize_t _glfwPlatformReadDropData(GLFWDropData* drop, const char* mime, void* buffer, size_t capacity, monotonic_t timeout);
void _glfwPlatformFinishDrop(GLFWDropData* drop, GLFWDragOperationType operation, bool success);
void _glfwPlatformRequestDropUpdate(_GLFWwindow* window);
size_t _glfwInputDropEvent(_GLFWwindow *window, GLFWDropEventType type, double xpos, double ypos, const char** mimes, size_t num_mimes, bool from_self);

47
glfw/wl_window.c vendored
View file

@ -2641,6 +2641,15 @@ motion(void *data UNUSED, struct wl_data_device *wl_data_device UNUSED, uint32_t
}
}
void
_glfwPlatformRequestDropUpdate(_GLFWwindow* window) {
_GLFWWaylandDataOffer *d = &_glfw.wl.drop_data_offer;
if (d->id) {
size_t mime_count = _glfwInputDropEvent(window, GLFW_DROP_STATUS_UPDATE, 0, 0, d->mimes, d->mimes_count, d->is_self_offer);
update_drop_state(d, window, mime_count);
}
}
static const struct wl_data_device_listener data_device_listener = {
.data_offer = handle_data_offer,
.selection = mark_selection_offer,
@ -3353,41 +3362,3 @@ _glfwPlatformSendDragData(GLFWDragSourceData* source_data, const void* data, siz
return written;
}
void
_glfwPlatformRequestDropUpdate(_GLFWwindow* window) {
_GLFWWaylandDataOffer *d = &_glfw.wl.drop_data_offer;
if (d->id) {
size_t mime_count = _glfwInputDropEvent(window, GLFW_DROP_STATUS_UPDATE, 0, 0, d->mimes, d->mimes_count, d->is_self_offer);
update_drop_state(d, window, mime_count);
}
}
void
_glfwPlatformFinishDrop(GLFWDropData* drop, GLFWDragOperationType operation UNUSED, bool success UNUSED) {
if (!drop) return;
free(drop->current_mime); drop->current_mime = NULL;
// Close any open file descriptor
if (drop->read_fd >= 0) {
close(drop->read_fd);
drop->read_fd = -1;
}
// Destroy the associated data offer
// Note: Wayland doesn't have a way to report the operation type or success back to the source
// in the same way as X11, as the source is notified through other means
if (drop->platform_data) wl_data_offer_destroy(drop->platform_data);
drop->platform_data = NULL;
// Free the mime types array (owned by drop object)
if (drop->mime_types) {
for (int i = 0; i < drop->mime_array_size; i++) free((char*)drop->mime_types[i]);
free(drop->mime_types);
drop->mime_types = NULL;
}
// Free the heap-allocated drop data structure
free(drop);
}

88
glfw/x11_window.c vendored
View file

@ -2016,52 +2016,50 @@ static void processEvent(XEvent *event)
if (_glfw.x11.xdnd.drag_accepted && _glfw.x11.xdnd.mimes_count > 0)
{
// Heap-allocate drop data structure for chunked reading
// The application is responsible for freeing this via glfwFinishDrop
GLFWDropData* drop_data = calloc(1, sizeof(GLFWDropData));
if (!drop_data) {
_glfwInputError(GLFW_OUT_OF_MEMORY, "X11: Failed to allocate drop data");
// Send XdndFinished to avoid leaving drag source hanging
if (_glfw.x11.xdnd.version >= 2)
{
XEvent reply = { ClientMessage };
reply.xclient.window = _glfw.x11.xdnd.source;
reply.xclient.message_type = _glfw.x11.XdndFinished;
reply.xclient.format = 32;
reply.xclient.data.l[0] = window->x11.handle;
reply.xclient.data.l[1] = 0; // Failure
reply.xclient.data.l[2] = None;
if (_glfw.x11.xdnd.version >= 2) {
XEvent reply = { ClientMessage };
reply.xclient.window = _glfw.x11.xdnd.source;
reply.xclient.message_type = _glfw.x11.XdndFinished;
reply.xclient.format = 32;
reply.xclient.data.l[0] = window->x11.handle;
reply.xclient.data.l[1] = 0; // Failure
reply.xclient.data.l[2] = None;
XSendEvent(_glfw.x11.display, _glfw.x11.xdnd.source,
False, NoEventMask, &reply);
XFlush(_glfw.x11.display);
}
return;
XSendEvent(_glfw.x11.display, _glfw.x11.xdnd.source,
False, NoEventMask, &reply);
XFlush(_glfw.x11.display);
}
// Transfer ownership of mimes array from global to drop object
drop_data->mime_types = (const char**)_glfw.x11.xdnd.mimes;
drop_data->mime_count = _glfw.x11.xdnd.mimes_count;
drop_data->mime_array_size = _glfw.x11.xdnd.mimes_array_size;
// Clear global references since drop object now owns the mimes
_glfw.x11.xdnd.mimes = NULL;
_glfw.x11.xdnd.mimes_count = 0;
_glfw.x11.xdnd.mimes_array_size = 0;
drop_data->current_mime = NULL;
drop_data->read_fd = -1;
drop_data->bytes_read = 0;
drop_data->platform_data = NULL;
drop_data->eof_reached = false;
drop_data->current_data = NULL;
drop_data->data_offset = 0;
drop_data->x11_data_size = 0;
// Store X11-specific drop state in the drop object
drop_data->x11_drop_target = window->x11.handle;
drop_data->x11_drop_time = (_glfw.x11.xdnd.version >= 1) ?
(unsigned long)event->xclient.data.l[2] : CurrentTime;
drop_data->x11_source = _glfw.x11.xdnd.source;
drop_data->x11_version = _glfw.x11.xdnd.version;
// // Heap-allocate drop data structure for chunked reading
// // The application is responsible for freeing this via glfwFinishDrop
// GLFWDropData* drop_data = calloc(1, sizeof(GLFWDropData));
// if (!drop_data) {
// _glfwInputError(GLFW_OUT_OF_MEMORY, "X11: Failed to allocate drop data");
// // Send XdndFinished to avoid leaving drag source hanging
// // Transfer ownership of mimes array from global to drop object
// drop_data->mime_types = (const char**)_glfw.x11.xdnd.mimes;
// drop_data->mime_count = _glfw.x11.xdnd.mimes_count;
// drop_data->mime_array_size = _glfw.x11.xdnd.mimes_array_size;
// // Clear global references since drop object now owns the mimes
// _glfw.x11.xdnd.mimes = NULL;
// _glfw.x11.xdnd.mimes_count = 0;
// _glfw.x11.xdnd.mimes_array_size = 0;
//
// drop_data->current_mime = NULL;
// drop_data->read_fd = -1;
// drop_data->bytes_read = 0;
// drop_data->platform_data = NULL;
// drop_data->eof_reached = false;
// drop_data->current_data = NULL;
// drop_data->data_offset = 0;
// drop_data->x11_data_size = 0;
// // Store X11-specific drop state in the drop object
// drop_data->x11_drop_target = window->x11.handle;
// drop_data->x11_drop_time = (_glfw.x11.xdnd.version >= 1) ?
// (unsigned long)event->xclient.data.l[2] : CurrentTime;
// drop_data->x11_source = _glfw.x11.xdnd.source;
// drop_data->x11_version = _glfw.x11.xdnd.version;
//
// Check if the drop is from this application
// bool from_self = (_glfw.x11.drag.source_window != None &&
// _glfw.x11.xdnd.source == _glfw.x11.drag.source_window);
@ -4121,6 +4119,7 @@ void _glfwPlatformUpdateDragState(_GLFWwindow* window) {
XFlush(_glfw.x11.display);
}
# if 0
const char**
_glfwPlatformGetDropMimeTypes(GLFWDropData* drop, int* count) {
if (!drop || !count) return NULL;
@ -4233,6 +4232,7 @@ _glfwPlatformReadDropData(GLFWDropData* drop, const char* mime, void* buffer, si
return (ssize_t)to_read;
}
void
_glfwPlatformFinishDrop(GLFWDropData* drop, GLFWDragOperationType operation, bool success) {
if (!drop) return;
@ -4289,4 +4289,4 @@ _glfwPlatformFinishDrop(GLFWDropData* drop, GLFWDragOperationType operation, boo
// Free the heap-allocated drop data structure
free(drop);
}
#endif

3
kitty/glfw-wrapper.c generated
View file

@ -353,9 +353,6 @@ load_glfw(const char* path) {
*(void **) (&glfwSetScrollCallback_impl) = dlsym(handle, "glfwSetScrollCallback");
if (glfwSetScrollCallback_impl == NULL) fail("Failed to load glfw function glfwSetScrollCallback with error: %s", dlerror());
*(void **) (&glfwSetDropCallback_impl) = dlsym(handle, "glfwSetDropCallback");
if (glfwSetDropCallback_impl == NULL) fail("Failed to load glfw function glfwSetDropCallback with error: %s", dlerror());
*(void **) (&glfwSetLiveResizeCallback_impl) = dlsym(handle, "glfwSetLiveResizeCallback");
if (glfwSetLiveResizeCallback_impl == NULL) fail("Failed to load glfw function glfwSetLiveResizeCallback with error: %s", dlerror());

45
kitty/glfw-wrapper.h generated
View file

@ -1019,8 +1019,6 @@ typedef struct GLFWcursor GLFWcursor;
*
* @ingroup input
*/
typedef struct GLFWDropData GLFWDropData;
typedef enum {
GLFW_RELEASE = 0,
GLFW_PRESS = 1,
@ -1134,7 +1132,7 @@ typedef struct GLFWDropEvent {
GLFWDropEventType type;
const char **mimes; size_t num_mimes;
double xpos, ypos; // Only valid for GLFW_DROP_ENTER and GLFW_DROP_MOVE
bool from_self;
bool from_self; // Only valid upto GLFW_DROP_DROP
ssize_t (*read_data)(GLFWwindow *w, struct GLFWDropEvent* ev, char *buffer, size_t sz); // Only valid for GLFW_DROP_DATA_AVAILABLE
void (*finish_drop)(GLFWwindow *w, GLFWDragOperationType op); // Only valid for GLFW_DROP_DROP and GLFW_DROP_DATA_AVAILABLE
} GLFWDropEvent;
@ -1539,43 +1537,6 @@ typedef void (* GLFWscrollfun)(GLFWwindow*,const GLFWScrollEvent*);
*/
typedef void (* GLFWkeyboardfun)(GLFWwindow*, GLFWkeyevent*);
/*! @brief The function pointer type for drag and drop callbacks.
*
* This is the function pointer type for drop callbacks. A drop
* callback function has the following signature:
* @code
* void function_name(GLFWwindow* window, GLFWDropData* drop)
* @endcode
*
* @param[in] window The window that received the event.
* @param[in] drop A heap-allocated opaque pointer representing the dropped data. Use
* @ref glfwGetDropMimeTypes to get available MIME types and
* @ref glfwReadDropData to read the data in chunks.
*
* @note The drop object is heap-allocated and remains valid until the
* application calls @ref glfwFinishDrop to free it. The application is
* responsible for calling glfwFinishDrop when it has finished reading
* the dropped data, even if reading fails or is not needed.
*
* @param[in] window The window that received the drop.
* @param[in] drop Opaque drop data pointer (heap-allocated).
* @param[in] from_self true if the drop originated from this application
* (i.e., the application is both the drag source and drop target), false
* if the drop came from an external application.
*
* @sa @ref path_drop
* @sa @ref glfwSetDropCallback
* @sa @ref glfwGetDropMimeTypes
* @sa @ref glfwReadDropData
* @sa @ref glfwFinishDrop
*
* @since Changed in version 4.0 to receive opaque drop data pointer.
* @since Changed in version 4.0 to receive from_self parameter.
*
* @ingroup input
*/
typedef void (* GLFWdropfun)(GLFWwindow*, GLFWDropData*, bool from_self);
/*! @brief Drag event types.
*
* These constants are used to identify the type of drag event.
@ -2339,10 +2300,6 @@ typedef GLFWscrollfun (*glfwSetScrollCallback_func)(GLFWwindow*, GLFWscrollfun);
GFW_EXTERN glfwSetScrollCallback_func glfwSetScrollCallback_impl;
#define glfwSetScrollCallback glfwSetScrollCallback_impl
typedef GLFWdropfun (*glfwSetDropCallback_func)(GLFWwindow*, GLFWdropfun);
GFW_EXTERN glfwSetDropCallback_func glfwSetDropCallback_impl;
#define glfwSetDropCallback glfwSetDropCallback_impl
typedef GLFWliveresizefun (*glfwSetLiveResizeCallback_func)(GLFWwindow*, GLFWliveresizefun);
GFW_EXTERN glfwSetLiveResizeCallback_func glfwSetLiveResizeCallback_impl;
#define glfwSetLiveResizeCallback glfwSetLiveResizeCallback_impl