forked from AuroraMiddleware/gtk
Bug 658767 - Drag and Drop NSEvent capture is racy
Create a synthetic NSMouseLeftDown to store in the GtkQuartzDragSourceInfo rather than relying on the NSWindow's latest event being the right one (or the right kind).
This commit is contained in:
parent
8ad3d2b296
commit
6906ab88bc
@ -1100,6 +1100,13 @@ gtk_drag_begin_idle (gpointer arg)
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
/* Fake protocol to let us call GdkNSView gdkWindow without including
|
||||
* gdk/GdkNSView.h (which we can't because it pulls in the internal-only
|
||||
* gdkwindow.h).
|
||||
*/
|
||||
@protocol GdkNSView
|
||||
- (GdkWindow *)gdkWindow;
|
||||
@end
|
||||
|
||||
static GdkDragContext *
|
||||
gtk_drag_begin_internal (GtkWidget *widget,
|
||||
@ -1110,14 +1117,47 @@ gtk_drag_begin_internal (GtkWidget *widget,
|
||||
GdkEvent *event)
|
||||
{
|
||||
GtkDragSourceInfo *info;
|
||||
GdkDragContext *context;
|
||||
GdkDevice *pointer;
|
||||
NSWindow *nswindow;
|
||||
GdkWindow *window;
|
||||
GdkDragContext *context = gdk_drag_begin (gtk_widget_get_window (widget),
|
||||
NULL);
|
||||
NSWindow *nswindow = get_toplevel_nswindow (widget);
|
||||
NSPoint point = {0, 0};
|
||||
gdouble x, y;
|
||||
double time = (double)g_get_real_time ();
|
||||
NSEvent *nsevent;
|
||||
NSTimeInterval nstime;
|
||||
|
||||
context = gdk_drag_begin (gtk_widget_get_window (widget), NULL);
|
||||
if (event)
|
||||
{
|
||||
if (gdk_event_get_coords (event, &x, &y))
|
||||
{
|
||||
point.x = x;
|
||||
point.y = y;
|
||||
}
|
||||
time = (double)gdk_event_get_time (event);
|
||||
}
|
||||
nstime = [[NSDate dateWithTimeIntervalSince1970: time / 1000] timeIntervalSinceReferenceDate];
|
||||
nsevent = [NSEvent mouseEventWithType: NSLeftMouseDown
|
||||
location: point
|
||||
modifierFlags: 0
|
||||
timestamp: nstime
|
||||
windowNumber: [nswindow windowNumber]
|
||||
context: [nswindow graphicsContext]
|
||||
eventNumber: 0
|
||||
clickCount: 1
|
||||
pressure: 0.0 ];
|
||||
|
||||
window = [(id<GdkNSView>)[nswindow contentView] gdkWindow];
|
||||
g_return_val_if_fail(nsevent != NULL, NULL);
|
||||
|
||||
context = gdk_drag_begin (window, NULL);
|
||||
g_return_val_if_fail( context != NULL, NULL);
|
||||
|
||||
info = gtk_drag_get_source_info (context, TRUE);
|
||||
|
||||
info->nsevent = nsevent;
|
||||
[info->nsevent retain];
|
||||
|
||||
info->source_widget = g_object_ref (widget);
|
||||
info->widget = g_object_ref (widget);
|
||||
info->target_list = target_list;
|
||||
@ -1160,10 +1200,6 @@ gtk_drag_begin_internal (GtkWidget *widget,
|
||||
}
|
||||
}
|
||||
|
||||
nswindow = get_toplevel_nswindow (widget);
|
||||
info->nsevent = [nswindow currentEvent];
|
||||
[info->nsevent retain];
|
||||
|
||||
/* drag will begin in an idle handler to avoid nested run loops */
|
||||
|
||||
g_idle_add_full (G_PRIORITY_HIGH_IDLE, gtk_drag_begin_idle, context, NULL);
|
||||
@ -1802,7 +1838,7 @@ gtk_drag_source_info_destroy (GtkDragSourceInfo *info)
|
||||
pasteboard = [NSPasteboard pasteboardWithName: NSDragPboard];
|
||||
[pasteboard declareTypes: nil owner: nil];
|
||||
|
||||
[pool relase];
|
||||
[pool release];
|
||||
|
||||
gtk_drag_clear_source_info (info->context);
|
||||
g_object_unref (info->context);
|
||||
|
Loading…
Reference in New Issue
Block a user