Commit 2ce686c0 authored by Po Lu's avatar Po Lu
Browse files

Support dragging multiple files on NS

This has to use a deprecated pasteboard type, since Emacs uses
the "old" (but not deprecated) dragImage: method for
drag-and-drop, which can't drop file URLs.

* lisp/term/ns-win.el (x-begin-drag): Update accordingly.
* src/nsselect.m (ns_decode_data_to_pasteboard):
(Fns_begin_drag): Allow files to be a list of filenames as well.
parent 1289d0c3
Pipeline #18287 failed with stages
in 217 minutes and 55 seconds
......@@ -905,11 +905,21 @@ See the documentation of `create-fontset-from-fontset-spec' for the format.")
(push (cons 'string ns-dnd-selection-value) pasteboard))
(when (and (member "FILE_NAME" targets)
(file-exists-p ns-dnd-selection-value))
(push (cons 'file
(url-encode-url (concat "file://"
(expand-file-name
ns-dnd-selection-value))))
pasteboard))
(let ((value (if (stringp ns-dnd-selection-value)
(or (get-text-property 0 'FILE_NAME
ns-dnd-selection-value)
ns-dnd-selection-value)
ns-dnd-selection-value)))
(if (vectorp value)
(push (cons 'file
(cl-loop for file across value
collect (expand-file-name file)))
pasteboard)
(push (cons 'file
(url-encode-url (concat "file://"
(expand-file-name
ns-dnd-selection-value))))
pasteboard))))
(ns-begin-drag frame pasteboard action return-frame allow-current-frame)))
(defun ns-handle-drag-motion (frame x y)
......
......@@ -562,8 +562,12 @@ Updated by Christian Limpach (chris@nice.ch)
NSPasteboard *pasteboard)
{
NSArray *types, *new;
NSMutableArray *temp;
Lisp_Object tem;
specpdl_ref count;
types = [pasteboard types];
count = SPECPDL_INDEX ();
CHECK_SYMBOL (type);
......@@ -580,10 +584,11 @@ Updated by Christian Limpach (chris@nice.ch)
}
else if (EQ (type, Qfile))
{
CHECK_STRING (data);
#if NS_USE_NSPasteboardTypeFileURL
new = [types arrayByAddingObject: NSPasteboardTypeFileURL];
if (CONSP (data))
new = [types arrayByAddingObject: NSPasteboardTypeURL];
else
new = [types arrayByAddingObject: NSPasteboardTypeFileURL];
#else
new = [types arrayByAddingObject: NSFilenamesPboardType];
#endif
......@@ -591,13 +596,41 @@ Updated by Christian Limpach (chris@nice.ch)
[pasteboard declareTypes: new
owner: nil];
if (STRINGP (data))
{
#if NS_USE_NSPasteboardTypeFileURL
[pasteboard setString: [NSString stringWithLispString: data]
forType: NSPasteboardTypeFileURL];
[pasteboard setString: [NSString stringWithLispString: data]
forType: NSPasteboardTypeFileURL];
#else
[pasteboard setString: [NSString stringWithLispString: data]
forType: NSFilenamesPboardType];
[pasteboard setString: [NSString stringWithLispString: data]
forType: NSFilenamesPboardType];
#endif
}
else
{
CHECK_LIST (data);
temp = [[NSMutableArray alloc] init];
record_unwind_protect_ptr (ns_release_object, temp);
for (tem = data; CONSP (tem); tem = XCDR (tem))
{
CHECK_STRING (XCAR (tem));
[temp addObject: [NSString stringWithLispString: XCAR (tem)]];
}
CHECK_LIST_END (tem, data);
#if NS_USE_NSPasteboardTypeFileURL
[pasteboard setPropertyList: temp
/* We have to use this deprecated pasteboard
type, since Apple doesn't let us use
dragImage:at: to drag multiple file URLs. */
forType: @"NSFilenamesPboardType"];
#else
[pasteboard setPropertyList: temp
forType: NSFilenamesPboardType];
#endif
unbind_to (count, Qnil);
}
}
else
signal_error ("Unknown pasteboard type", type);
......@@ -673,7 +706,8 @@ Updated by Christian Limpach (chris@nice.ch)
be dragged to another program.
- `file' means DATA should be a file URL that will be dragged to
another program.
another program. DATA may also be a list of file names; that
means each file in the list will be dragged to another program.
ACTION is the action that will be taken by the drop target towards the
data inside PBOARD.
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment