Merge branch 'copilot/finish-source-actions-implementation' of https://github.com/kovidgoyal/kitty

This commit is contained in:
Kovid Goyal 2026-05-14 11:24:36 +05:30
commit b7c11166f5
No known key found for this signature in database
GPG key ID: 06BC317B515ACE7C
4 changed files with 34 additions and 0 deletions

View file

@ -1505,6 +1505,15 @@ - (BOOL)wantsPeriodicDraggingUpdates
if (t == GLFW_DROP_ENTER || t == GLFW_DROP_MOVE) d->drag_accepted = accepted_count > 0;
}
static void
update_drop_source_actions(_GLFWwindow *window, id<NSDraggingInfo> sender) {
NSDragOperation src_ops = [sender draggingSourceOperationMask];
window->drop_operation.source_actions = GLFW_DRAG_OPERATION_NONE;
if (src_ops & NSDragOperationCopy) window->drop_operation.source_actions |= GLFW_DRAG_OPERATION_COPY;
if (src_ops & NSDragOperationMove) window->drop_operation.source_actions |= GLFW_DRAG_OPERATION_MOVE;
if (src_ops & NSDragOperationGeneric) window->drop_operation.source_actions |= GLFW_DRAG_OPERATION_GENERIC;
}
// Reset the working copy of mimes so the next callback sees the full original
// list. Returns false on allocation failure.
static bool
@ -1581,6 +1590,7 @@ - (NSDragOperation)draggingEntered:(id <NSDraggingInfo>)sender
window->ns.drop_data.mimes = mime_array;
window->ns.drop_data.mimes_count = mime_count;
bool from_self = ([sender draggingSource] != nil);
update_drop_source_actions(window, sender);
_GLFWDropData *d = &window->ns.drop_data;
if (reset_drop_copy_mimes(d)) {
size_t accepted_count = _glfwInputDropEvent(window, GLFW_DROP_ENTER, xpos, ypos, d->copy_mimes, d->copy_mimes_count, from_self);
@ -1598,6 +1608,7 @@ - (NSDragOperation)draggingUpdated:(id <NSDraggingInfo>)sender
double ypos = contentRect.size.height - pos.y;
bool from_self = ([sender draggingSource] != nil);
update_drop_source_actions(window, sender);
_GLFWDropData *d = &window->ns.drop_data;
if (reset_drop_copy_mimes(d)) {
size_t accepted_count = _glfwInputDropEvent(window, GLFW_DROP_MOVE, xpos, ypos, d->copy_mimes, d->copy_mimes_count, from_self);

2
glfw/x11_init.c vendored
View file

@ -520,6 +520,8 @@ static bool initExtensions(void)
_glfw.x11.XdndFinished = XInternAtom(_glfw.x11.display, "XdndFinished", False);
_glfw.x11.XdndSelection = XInternAtom(_glfw.x11.display, "XdndSelection", False);
_glfw.x11.XdndTypeList = XInternAtom(_glfw.x11.display, "XdndTypeList", False);
_glfw.x11.XdndActionList = XInternAtom(_glfw.x11.display, "XdndActionList", False);
_glfw.x11.XdndActionAsk = XInternAtom(_glfw.x11.display, "XdndActionAsk", False);
_glfw.x11.XdndLeave = XInternAtom(_glfw.x11.display, "XdndLeave", False);
_glfw.x11.XdndProxy = XInternAtom(_glfw.x11.display, "XdndProxy", False);

2
glfw/x11_platform.h vendored
View file

@ -327,6 +327,8 @@ typedef struct _GLFWlibraryX11
Atom XdndFinished;
Atom XdndSelection;
Atom XdndTypeList;
Atom XdndActionList;
Atom XdndActionAsk;
Atom XdndLeave;
Atom XdndProxy;

19
glfw/x11_window.c vendored
View file

@ -1691,6 +1691,24 @@ _glfwPlatformEndDrop(GLFWwindow *w, GLFWDragOperationType op) {
}
static void
update_drop_source_actions(_GLFWwindow *window) {
window->drop_operation.source_actions = GLFW_DRAG_OPERATION_NONE;
Atom *actions = NULL;
unsigned long count = _glfwGetWindowPropertyX11(dnd.source, _glfw.x11.XdndActionList, XA_ATOM, (unsigned char**)&actions);
if (actions) {
for (unsigned long i = 0; i < count; i++) {
if (actions[i] == _glfw.x11.XdndActionCopy) window->drop_operation.source_actions |= GLFW_DRAG_OPERATION_COPY;
else if (actions[i] == _glfw.x11.XdndActionMove) window->drop_operation.source_actions |= GLFW_DRAG_OPERATION_MOVE;
else if (actions[i] == _glfw.x11.XdndActionAsk) window->drop_operation.source_actions |= GLFW_DRAG_OPERATION_GENERIC;
}
XFree(actions);
} else {
// XdndActionList not present; default to copy only
window->drop_operation.source_actions = GLFW_DRAG_OPERATION_COPY;
}
}
static void
drop_start(_GLFWwindow *window, XEvent *event) {
// A drag operation has entered the window
@ -1703,6 +1721,7 @@ drop_start(_GLFWwindow *window, XEvent *event) {
dnd.format_priority = 0;
update_dnd_mimes(event);
dnd.from_self = _glfw.x11.drag.source_window != None && dnd.source == _glfw.x11.drag.source_window;
update_drop_source_actions(window);
// Position is not known yet at enter time, will be updated with XdndPosition
if (reset_dnd_copy_mimes()) {
size_t accepted_count = _glfwInputDropEvent(