forked from AuroraMiddleware/gtk
Turn GtkDropTarget into an event controller
We are still propagating the drag events manually, but we are now calling gtk_widget_run_controllers to pass them to drop targets.
This commit is contained in:
parent
f960eb6ab4
commit
dfb2cbdfdb
136
gtk/gtkdnd.c
136
gtk/gtkdnd.c
@ -63,26 +63,9 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
typedef struct _GtkDragDestInfo GtkDragDestInfo;
|
|
||||||
|
|
||||||
struct _GtkDragDestInfo
|
|
||||||
{
|
|
||||||
GtkWidget *widget; /* Widget in which drag is in */
|
|
||||||
GdkDrop *drop; /* drop */
|
|
||||||
};
|
|
||||||
|
|
||||||
/* Forward declarations */
|
/* Forward declarations */
|
||||||
static GtkWidget *gtk_drop_find_widget (GtkWidget *widget,
|
static gboolean gtk_drop_find_widget (GtkWidget *widget,
|
||||||
GdkEvent *event);
|
GdkEvent *event);
|
||||||
static void gtk_drag_dest_leave (GtkWidget *widget,
|
|
||||||
GdkDrop *drop);
|
|
||||||
static gboolean gtk_drop_target_handle_event (GtkDropTarget *dest,
|
|
||||||
GdkEvent *event);
|
|
||||||
static void gtk_drag_dest_set_widget (GtkDragDestInfo *info,
|
|
||||||
GtkWidget *widget);
|
|
||||||
|
|
||||||
static GtkDragDestInfo * gtk_drag_get_dest_info (GdkDrop *drop,
|
|
||||||
gboolean create);
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -116,41 +99,17 @@ _gtk_drag_dest_handle_event (GtkWidget *toplevel,
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case GDK_DRAG_LEAVE:
|
case GDK_DRAG_LEAVE:
|
||||||
if (info->widget)
|
if (info->dest)
|
||||||
{
|
{
|
||||||
gtk_drag_dest_leave (info->widget, drop);
|
gtk_drop_target_emit_drag_leave (info->dest, drop);
|
||||||
gtk_drag_dest_set_widget (info, NULL);
|
gtk_drag_dest_set_target (info, NULL);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case GDK_DRAG_MOTION:
|
case GDK_DRAG_MOTION:
|
||||||
case GDK_DROP_START:
|
case GDK_DROP_START:
|
||||||
{
|
{
|
||||||
GtkWidget *widget;
|
if (!gtk_drop_find_widget (toplevel, event))
|
||||||
|
|
||||||
if (event_type == GDK_DROP_START)
|
|
||||||
{
|
|
||||||
/* We send a leave here so that the widget unhighlights
|
|
||||||
* properly.
|
|
||||||
*/
|
|
||||||
if (info->widget)
|
|
||||||
{
|
|
||||||
gtk_drag_dest_leave (info->widget, drop);
|
|
||||||
gtk_drag_dest_set_widget (info, NULL);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
widget = gtk_drop_find_widget (toplevel, event);
|
|
||||||
|
|
||||||
if (info->widget && info->widget != widget)
|
|
||||||
{
|
|
||||||
gtk_drag_dest_leave (info->widget, drop);
|
|
||||||
gtk_drag_dest_set_widget (info, NULL);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (widget)
|
|
||||||
gtk_drag_dest_set_widget (info, widget);
|
|
||||||
else
|
|
||||||
gdk_drop_status (drop, 0);
|
gdk_drop_status (drop, 0);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
@ -160,7 +119,7 @@ _gtk_drag_dest_handle_event (GtkWidget *toplevel,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static GtkWidget *
|
static gboolean
|
||||||
gtk_drop_find_widget (GtkWidget *event_widget,
|
gtk_drop_find_widget (GtkWidget *event_widget,
|
||||||
GdkEvent *event)
|
GdkEvent *event)
|
||||||
{
|
{
|
||||||
@ -170,26 +129,25 @@ gtk_drop_find_widget (GtkWidget *event_widget,
|
|||||||
|
|
||||||
if (!gtk_widget_get_mapped (event_widget) ||
|
if (!gtk_widget_get_mapped (event_widget) ||
|
||||||
!gtk_widget_get_sensitive (event_widget))
|
!gtk_widget_get_sensitive (event_widget))
|
||||||
return NULL;
|
return FALSE;
|
||||||
|
|
||||||
gdk_event_get_coords (event, &x, &y);
|
gdk_event_get_coords (event, &x, &y);
|
||||||
|
|
||||||
widget = gtk_widget_pick (event_widget, x, y, GTK_PICK_DEFAULT);
|
widget = gtk_widget_pick (event_widget, x, y, GTK_PICK_DEFAULT);
|
||||||
|
|
||||||
if (!widget)
|
if (!widget)
|
||||||
return NULL;
|
return FALSE;
|
||||||
|
|
||||||
gtk_widget_translate_coordinates (event_widget, widget, x, y, &wx, &wy);
|
gtk_widget_translate_coordinates (event_widget, widget, x, y, &wx, &wy);
|
||||||
|
|
||||||
while (widget)
|
while (widget)
|
||||||
{
|
{
|
||||||
GtkDropTarget *dest;
|
|
||||||
GtkWidget *parent;
|
GtkWidget *parent;
|
||||||
GList *hierarchy = NULL;
|
GList *hierarchy = NULL;
|
||||||
gboolean found = FALSE;
|
gboolean found = FALSE;
|
||||||
|
|
||||||
if (!gtk_widget_get_mapped (widget))
|
if (!gtk_widget_get_mapped (widget))
|
||||||
return NULL;
|
return FALSE;
|
||||||
|
|
||||||
if (gtk_widget_get_state_flags (widget) & GTK_STATE_FLAG_INSENSITIVE)
|
if (gtk_widget_get_state_flags (widget) & GTK_STATE_FLAG_INSENSITIVE)
|
||||||
{
|
{
|
||||||
@ -207,17 +165,9 @@ gtk_drop_find_widget (GtkWidget *event_widget,
|
|||||||
hierarchy = g_list_prepend (hierarchy, g_object_ref (parent));
|
hierarchy = g_list_prepend (hierarchy, g_object_ref (parent));
|
||||||
}
|
}
|
||||||
|
|
||||||
/* If the current widget is registered as a drop site, check to
|
|
||||||
* emit "drag-motion" to check if we are actually in a drop
|
|
||||||
* site.
|
|
||||||
*/
|
|
||||||
dest = gtk_drop_target_get (widget);
|
|
||||||
if (dest)
|
|
||||||
{
|
|
||||||
gdk_event_set_coords (event, wx, wy);
|
gdk_event_set_coords (event, wx, wy);
|
||||||
found = gtk_drop_target_handle_event (dest, event);
|
found = gtk_widget_run_controllers (widget, event, GTK_PHASE_BUBBLE);
|
||||||
gdk_event_set_coords (event, x, y);
|
gdk_event_set_coords (event, x, y);
|
||||||
}
|
|
||||||
|
|
||||||
if (!found)
|
if (!found)
|
||||||
{
|
{
|
||||||
@ -236,33 +186,33 @@ gtk_drop_find_widget (GtkWidget *event_widget,
|
|||||||
g_list_free_full (hierarchy, g_object_unref);
|
g_list_free_full (hierarchy, g_object_unref);
|
||||||
|
|
||||||
if (found)
|
if (found)
|
||||||
return widget;
|
return TRUE;
|
||||||
|
|
||||||
if (parent)
|
if (parent)
|
||||||
g_object_remove_weak_pointer (G_OBJECT (parent), (gpointer *) &parent);
|
g_object_remove_weak_pointer (G_OBJECT (parent), (gpointer *) &parent);
|
||||||
else
|
else
|
||||||
return NULL;
|
return FALSE;
|
||||||
|
|
||||||
if (!gtk_widget_translate_coordinates (widget, parent, wx, wy, &wx, &wy))
|
if (!gtk_widget_translate_coordinates (widget, parent, wx, wy, &wx, &wy))
|
||||||
return NULL;
|
return FALSE;
|
||||||
|
|
||||||
widget = parent;
|
widget = parent;
|
||||||
}
|
}
|
||||||
|
|
||||||
return NULL;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
void
|
||||||
gtk_drag_dest_set_widget (GtkDragDestInfo *info,
|
gtk_drag_dest_set_target (GtkDragDestInfo *info,
|
||||||
GtkWidget *widget)
|
GtkDropTarget *dest)
|
||||||
{
|
{
|
||||||
if (info->widget)
|
if (info->dest)
|
||||||
g_object_remove_weak_pointer (G_OBJECT (info->widget), (gpointer *) &info->widget);
|
g_object_remove_weak_pointer (G_OBJECT (info->dest), (gpointer *) &info->dest);
|
||||||
|
|
||||||
info->widget = widget;
|
info->dest = dest;
|
||||||
|
|
||||||
if (info->widget)
|
if (info->dest)
|
||||||
g_object_add_weak_pointer (G_OBJECT (info->widget), (gpointer *) &info->widget);
|
g_object_add_weak_pointer (G_OBJECT (info->dest), (gpointer *) &info->dest);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
@ -270,12 +220,12 @@ gtk_drag_dest_info_destroy (gpointer data)
|
|||||||
{
|
{
|
||||||
GtkDragDestInfo *info = (GtkDragDestInfo *)data;
|
GtkDragDestInfo *info = (GtkDragDestInfo *)data;
|
||||||
|
|
||||||
gtk_drag_dest_set_widget (info, NULL);
|
gtk_drag_dest_set_target (info, NULL);
|
||||||
|
|
||||||
g_slice_free (GtkDragDestInfo, data);
|
g_slice_free (GtkDragDestInfo, data);
|
||||||
}
|
}
|
||||||
|
|
||||||
static GtkDragDestInfo *
|
GtkDragDestInfo *
|
||||||
gtk_drag_get_dest_info (GdkDrop *drop,
|
gtk_drag_get_dest_info (GdkDrop *drop,
|
||||||
gboolean create)
|
gboolean create)
|
||||||
{
|
{
|
||||||
@ -295,41 +245,3 @@ gtk_drag_get_dest_info (GdkDrop *drop,
|
|||||||
|
|
||||||
return info;
|
return info;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
* Default drag handlers
|
|
||||||
*/
|
|
||||||
static void
|
|
||||||
gtk_drag_dest_leave (GtkWidget *widget,
|
|
||||||
GdkDrop *drop)
|
|
||||||
{
|
|
||||||
GtkDropTarget *dest;
|
|
||||||
|
|
||||||
dest = gtk_drop_target_get (widget);
|
|
||||||
g_return_if_fail (dest != NULL);
|
|
||||||
|
|
||||||
gtk_drop_target_emit_drag_leave (dest, drop);
|
|
||||||
}
|
|
||||||
|
|
||||||
static gboolean
|
|
||||||
gtk_drop_target_handle_event (GtkDropTarget *dest,
|
|
||||||
GdkEvent *event)
|
|
||||||
{
|
|
||||||
GdkDrop *drop;
|
|
||||||
double x, y;
|
|
||||||
|
|
||||||
drop = gdk_event_get_drop (event);
|
|
||||||
gdk_event_get_coords (event, &x, &y);
|
|
||||||
|
|
||||||
switch ((int)gdk_event_get_event_type (event))
|
|
||||||
{
|
|
||||||
case GDK_DRAG_MOTION:
|
|
||||||
return gtk_drop_target_emit_drag_motion (dest, drop, x, y);
|
|
||||||
case GDK_DROP_START:
|
|
||||||
return gtk_drop_target_emit_drag_drop (dest, drop, x, y);
|
|
||||||
default:
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
return FALSE;
|
|
||||||
}
|
|
||||||
|
@ -20,6 +20,7 @@
|
|||||||
#define __GTK_DND_PRIVATE_H__
|
#define __GTK_DND_PRIVATE_H__
|
||||||
|
|
||||||
#include "gtkwidget.h"
|
#include "gtkwidget.h"
|
||||||
|
#include "gtkdragdest.h"
|
||||||
|
|
||||||
|
|
||||||
G_BEGIN_DECLS
|
G_BEGIN_DECLS
|
||||||
@ -27,6 +28,19 @@ G_BEGIN_DECLS
|
|||||||
void _gtk_drag_dest_handle_event (GtkWidget *toplevel,
|
void _gtk_drag_dest_handle_event (GtkWidget *toplevel,
|
||||||
GdkEvent *event);
|
GdkEvent *event);
|
||||||
|
|
||||||
|
typedef struct _GtkDragDestInfo GtkDragDestInfo;
|
||||||
|
|
||||||
|
struct _GtkDragDestInfo
|
||||||
|
{
|
||||||
|
GtkDropTarget *dest;
|
||||||
|
GdkDrop *drop; /* drop */
|
||||||
|
};
|
||||||
|
|
||||||
|
GtkDragDestInfo * gtk_drag_get_dest_info (GdkDrop *drop,
|
||||||
|
gboolean create);
|
||||||
|
void gtk_drag_dest_set_target (GtkDragDestInfo *info,
|
||||||
|
GtkDropTarget *dest);
|
||||||
|
|
||||||
G_END_DECLS
|
G_END_DECLS
|
||||||
|
|
||||||
#endif /* __GTK_DND_PRIVATE_H__ */
|
#endif /* __GTK_DND_PRIVATE_H__ */
|
||||||
|
@ -31,7 +31,7 @@
|
|||||||
#include "gtkintl.h"
|
#include "gtkintl.h"
|
||||||
#include "gtknative.h"
|
#include "gtknative.h"
|
||||||
#include "gtktypebuiltins.h"
|
#include "gtktypebuiltins.h"
|
||||||
#include "gtkeventcontroller.h"
|
#include "gtkeventcontrollerprivate.h"
|
||||||
#include "gtkmarshalers.h"
|
#include "gtkmarshalers.h"
|
||||||
#include "gtkselectionprivate.h"
|
#include "gtkselectionprivate.h"
|
||||||
|
|
||||||
@ -51,7 +51,7 @@
|
|||||||
|
|
||||||
struct _GtkDropTarget
|
struct _GtkDropTarget
|
||||||
{
|
{
|
||||||
GObject parent_instance;
|
GtkEventController parent_object;
|
||||||
|
|
||||||
GdkContentFormats *formats;
|
GdkContentFormats *formats;
|
||||||
GdkDragAction actions;
|
GdkDragAction actions;
|
||||||
@ -64,7 +64,7 @@ struct _GtkDropTarget
|
|||||||
|
|
||||||
struct _GtkDropTargetClass
|
struct _GtkDropTargetClass
|
||||||
{
|
{
|
||||||
GObjectClass parent_class;
|
GtkEventControllerClass parent_class;
|
||||||
|
|
||||||
gboolean (*drag_motion) (GtkDropTarget *dest,
|
gboolean (*drag_motion) (GtkDropTarget *dest,
|
||||||
int x,
|
int x,
|
||||||
@ -94,7 +94,15 @@ static gboolean gtk_drop_target_drag_motion (GtkDropTarget *dest,
|
|||||||
int x,
|
int x,
|
||||||
int y);
|
int y);
|
||||||
|
|
||||||
G_DEFINE_TYPE (GtkDropTarget, gtk_drop_target, G_TYPE_OBJECT);
|
static gboolean gtk_drop_target_handle_event (GtkEventController *controller,
|
||||||
|
const GdkEvent *event);
|
||||||
|
static gboolean gtk_drop_target_filter_event (GtkEventController *controller,
|
||||||
|
const GdkEvent *event);
|
||||||
|
static void gtk_drop_target_set_widget (GtkEventController *controller,
|
||||||
|
GtkWidget *widget);
|
||||||
|
static void gtk_drop_target_unset_widget (GtkEventController *controller);
|
||||||
|
|
||||||
|
G_DEFINE_TYPE (GtkDropTarget, gtk_drop_target, GTK_TYPE_EVENT_CONTROLLER);
|
||||||
|
|
||||||
static void
|
static void
|
||||||
gtk_drop_target_init (GtkDropTarget *dest)
|
gtk_drop_target_init (GtkDropTarget *dest)
|
||||||
@ -165,11 +173,17 @@ static void
|
|||||||
gtk_drop_target_class_init (GtkDropTargetClass *class)
|
gtk_drop_target_class_init (GtkDropTargetClass *class)
|
||||||
{
|
{
|
||||||
GObjectClass *object_class = G_OBJECT_CLASS (class);
|
GObjectClass *object_class = G_OBJECT_CLASS (class);
|
||||||
|
GtkEventControllerClass *controller_class = GTK_EVENT_CONTROLLER_CLASS (class);
|
||||||
|
|
||||||
object_class->finalize = gtk_drop_target_finalize;
|
object_class->finalize = gtk_drop_target_finalize;
|
||||||
object_class->set_property = gtk_drop_target_set_property;
|
object_class->set_property = gtk_drop_target_set_property;
|
||||||
object_class->get_property = gtk_drop_target_get_property;
|
object_class->get_property = gtk_drop_target_get_property;
|
||||||
|
|
||||||
|
controller_class->handle_event = gtk_drop_target_handle_event;
|
||||||
|
controller_class->filter_event = gtk_drop_target_filter_event;
|
||||||
|
controller_class->set_widget = gtk_drop_target_set_widget;
|
||||||
|
controller_class->unset_widget = gtk_drop_target_unset_widget;
|
||||||
|
|
||||||
class->drag_motion = gtk_drop_target_drag_motion;
|
class->drag_motion = gtk_drop_target_drag_motion;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -445,28 +459,11 @@ void
|
|||||||
gtk_drop_target_attach (GtkDropTarget *dest,
|
gtk_drop_target_attach (GtkDropTarget *dest,
|
||||||
GtkWidget *widget)
|
GtkWidget *widget)
|
||||||
{
|
{
|
||||||
GtkDropTarget *old_dest;
|
|
||||||
|
|
||||||
g_return_if_fail (GTK_IS_DROP_TARGET (dest));
|
g_return_if_fail (GTK_IS_DROP_TARGET (dest));
|
||||||
g_return_if_fail (dest->widget == NULL);
|
|
||||||
g_return_if_fail (GTK_IS_WIDGET (widget));
|
g_return_if_fail (GTK_IS_WIDGET (widget));
|
||||||
|
|
||||||
old_dest = g_object_get_data (G_OBJECT (widget), I_("gtk-drag-dest"));
|
gtk_event_controller_set_propagation_phase (GTK_EVENT_CONTROLLER (dest), GTK_PHASE_BUBBLE);
|
||||||
if (old_dest)
|
gtk_widget_add_controller (widget, GTK_EVENT_CONTROLLER (dest));
|
||||||
{
|
|
||||||
g_signal_handlers_disconnect_by_func (widget, gtk_drag_dest_realized, old_dest);
|
|
||||||
g_signal_handlers_disconnect_by_func (widget, gtk_drag_dest_hierarchy_changed, old_dest);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (gtk_widget_get_realized (widget))
|
|
||||||
gtk_drag_dest_realized (widget);
|
|
||||||
|
|
||||||
dest->widget = widget;
|
|
||||||
|
|
||||||
g_signal_connect (widget, "realize", G_CALLBACK (gtk_drag_dest_realized), dest);
|
|
||||||
g_signal_connect (widget, "notify::root", G_CALLBACK (gtk_drag_dest_hierarchy_changed), dest);
|
|
||||||
|
|
||||||
g_object_set_data_full (G_OBJECT (widget), I_("gtk-drag-dest"), dest, g_object_unref);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -478,17 +475,12 @@ gtk_drop_target_attach (GtkDropTarget *dest,
|
|||||||
void
|
void
|
||||||
gtk_drop_target_detach (GtkDropTarget *dest)
|
gtk_drop_target_detach (GtkDropTarget *dest)
|
||||||
{
|
{
|
||||||
|
GtkWidget *widget;
|
||||||
|
|
||||||
g_return_if_fail (GTK_IS_DROP_TARGET (dest));
|
g_return_if_fail (GTK_IS_DROP_TARGET (dest));
|
||||||
|
|
||||||
if (dest->widget)
|
widget = gtk_event_controller_get_widget (GTK_EVENT_CONTROLLER (dest));
|
||||||
{
|
gtk_widget_remove_controller (widget, GTK_EVENT_CONTROLLER (dest));
|
||||||
g_signal_handlers_disconnect_by_func (dest->widget, gtk_drag_dest_realized, dest);
|
|
||||||
g_signal_handlers_disconnect_by_func (dest->widget, gtk_drag_dest_hierarchy_changed, dest);
|
|
||||||
|
|
||||||
g_object_set_data (G_OBJECT (dest->widget), I_("gtk-drag-dest"), NULL);
|
|
||||||
|
|
||||||
dest->widget = NULL;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -504,7 +496,7 @@ gtk_drop_target_get_target (GtkDropTarget *dest)
|
|||||||
{
|
{
|
||||||
g_return_val_if_fail (GTK_IS_DROP_TARGET (dest), NULL);
|
g_return_val_if_fail (GTK_IS_DROP_TARGET (dest), NULL);
|
||||||
|
|
||||||
return dest->widget;
|
return gtk_event_controller_get_widget (GTK_EVENT_CONTROLLER (dest));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -650,6 +642,10 @@ void
|
|||||||
gtk_drop_target_set_armed (GtkDropTarget *dest,
|
gtk_drop_target_set_armed (GtkDropTarget *dest,
|
||||||
gboolean armed)
|
gboolean armed)
|
||||||
{
|
{
|
||||||
|
GtkWidget *widget;
|
||||||
|
|
||||||
|
widget = gtk_event_controller_get_widget (GTK_EVENT_CONTROLLER (dest));
|
||||||
|
|
||||||
dest->armed_pending = FALSE;
|
dest->armed_pending = FALSE;
|
||||||
|
|
||||||
if (dest->armed == armed)
|
if (dest->armed == armed)
|
||||||
@ -657,13 +653,10 @@ gtk_drop_target_set_armed (GtkDropTarget *dest,
|
|||||||
|
|
||||||
dest->armed = armed;
|
dest->armed = armed;
|
||||||
|
|
||||||
if (dest->widget)
|
|
||||||
{
|
|
||||||
if (armed)
|
if (armed)
|
||||||
gtk_drag_highlight (dest->widget);
|
gtk_drag_highlight (widget);
|
||||||
else
|
else
|
||||||
gtk_drag_unhighlight (dest->widget);
|
gtk_drag_unhighlight (widget);
|
||||||
}
|
|
||||||
|
|
||||||
g_object_notify_by_pspec (G_OBJECT (dest), properties[PROP_ARMED]);
|
g_object_notify_by_pspec (G_OBJECT (dest), properties[PROP_ARMED]);
|
||||||
}
|
}
|
||||||
@ -674,6 +667,104 @@ gtk_drop_target_get_armed (GtkDropTarget *dest)
|
|||||||
return dest->armed;
|
return dest->armed;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static gboolean
|
||||||
|
gtk_drop_target_filter_event (GtkEventController *controller,
|
||||||
|
const GdkEvent *event)
|
||||||
|
{
|
||||||
|
switch ((int)gdk_event_get_event_type (event))
|
||||||
|
{
|
||||||
|
case GDK_DRAG_ENTER:
|
||||||
|
case GDK_DRAG_LEAVE:
|
||||||
|
case GDK_DRAG_MOTION:
|
||||||
|
case GDK_DROP_START:
|
||||||
|
return GTK_EVENT_CONTROLLER_CLASS (gtk_drop_target_parent_class)->filter_event (controller, event);
|
||||||
|
|
||||||
|
default:;
|
||||||
|
}
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
static gboolean
|
||||||
|
gtk_drop_target_handle_event (GtkEventController *controller,
|
||||||
|
const GdkEvent *event)
|
||||||
|
{
|
||||||
|
GtkDropTarget *dest = GTK_DROP_TARGET (controller);
|
||||||
|
GdkDrop *drop;
|
||||||
|
GtkDragDestInfo *info;
|
||||||
|
double x, y;
|
||||||
|
gboolean found = FALSE;
|
||||||
|
|
||||||
|
gdk_event_get_coords (event, &x, &y);
|
||||||
|
|
||||||
|
drop = gdk_event_get_drop (event);
|
||||||
|
info = gtk_drag_get_dest_info (drop, TRUE);
|
||||||
|
|
||||||
|
switch ((int)gdk_event_get_event_type (event))
|
||||||
|
{
|
||||||
|
case GDK_DRAG_MOTION:
|
||||||
|
found = gtk_drop_target_emit_drag_motion (dest, drop, x, y);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case GDK_DROP_START:
|
||||||
|
/* We send a leave before the drop so that the widget unhighlights
|
||||||
|
* properly.
|
||||||
|
*/
|
||||||
|
if (info->dest)
|
||||||
|
{
|
||||||
|
gtk_drop_target_emit_drag_leave (info->dest, drop);
|
||||||
|
gtk_drag_dest_set_target (info, NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
found = gtk_drop_target_emit_drag_drop (dest, drop, x, y);
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (found)
|
||||||
|
{
|
||||||
|
if (info->dest && info->dest != dest)
|
||||||
|
{
|
||||||
|
gtk_drop_target_emit_drag_leave (info->dest, drop);
|
||||||
|
gtk_drag_dest_set_target (info, NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
gtk_drag_dest_set_target (info, dest);
|
||||||
|
}
|
||||||
|
|
||||||
|
return found;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
gtk_drop_target_set_widget (GtkEventController *controller,
|
||||||
|
GtkWidget *widget)
|
||||||
|
{
|
||||||
|
GtkDropTarget *dest = GTK_DROP_TARGET (controller);
|
||||||
|
|
||||||
|
GTK_EVENT_CONTROLLER_CLASS (gtk_drop_target_parent_class)->set_widget (controller, widget);
|
||||||
|
|
||||||
|
if (gtk_widget_get_realized (widget))
|
||||||
|
gtk_drag_dest_realized (widget);
|
||||||
|
|
||||||
|
g_signal_connect (widget, "realize", G_CALLBACK (gtk_drag_dest_realized), dest);
|
||||||
|
g_signal_connect (widget, "notify::root", G_CALLBACK (gtk_drag_dest_hierarchy_changed), dest);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
gtk_drop_target_unset_widget (GtkEventController *controller)
|
||||||
|
{
|
||||||
|
GtkWidget *widget;
|
||||||
|
|
||||||
|
widget = gtk_event_controller_get_widget (controller);
|
||||||
|
|
||||||
|
g_signal_handlers_disconnect_by_func (widget, gtk_drag_dest_realized, controller);
|
||||||
|
g_signal_handlers_disconnect_by_func (widget, gtk_drag_dest_hierarchy_changed, controller);
|
||||||
|
|
||||||
|
GTK_EVENT_CONTROLLER_CLASS (gtk_drop_target_parent_class)->unset_widget (controller);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* gtk_drag_highlight: (method)
|
* gtk_drag_highlight: (method)
|
||||||
* @widget: a widget to highlight
|
* @widget: a widget to highlight
|
||||||
@ -810,13 +901,16 @@ gtk_drop_target_read_selection (GtkDropTarget *dest,
|
|||||||
gpointer user_data)
|
gpointer user_data)
|
||||||
{
|
{
|
||||||
GTask *task;
|
GTask *task;
|
||||||
|
GtkWidget *widget;
|
||||||
|
|
||||||
g_return_if_fail (GTK_IS_DROP_TARGET (dest));
|
g_return_if_fail (GTK_IS_DROP_TARGET (dest));
|
||||||
|
|
||||||
task = g_task_new (dest, NULL, callback, user_data);
|
task = g_task_new (dest, NULL, callback, user_data);
|
||||||
g_object_set_data_full (G_OBJECT (task), "drop", g_object_ref (dest->drop), g_object_unref);
|
g_object_set_data_full (G_OBJECT (task), "drop", g_object_ref (dest->drop), g_object_unref);
|
||||||
if (dest->widget)
|
|
||||||
g_object_set_data (G_OBJECT (task), "display", gtk_widget_get_display (dest->widget));
|
widget = gtk_event_controller_get_widget (GTK_EVENT_CONTROLLER (dest));
|
||||||
|
if (widget)
|
||||||
|
g_object_set_data (G_OBJECT (task), "display", gtk_widget_get_display (widget));
|
||||||
|
|
||||||
gdk_drop_read_async (dest->drop,
|
gdk_drop_read_async (dest->drop,
|
||||||
(const char *[2]) { target, NULL },
|
(const char *[2]) { target, NULL },
|
||||||
|
Loading…
Reference in New Issue
Block a user