Compare commits
29 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| df684b8d04 | |||
| ced714e8be | |||
| 84127c7f7b | |||
| 2b4e9e10c2 | |||
| 435e4e0fb0 | |||
| 3616c33ddd | |||
| 811b1005f9 | |||
| caeb0d3907 | |||
| 4a3e75c123 | |||
| 28aeb01f9b | |||
| ad11933eee | |||
| 27460826b3 | |||
| 9d65f8d5b2 | |||
| 783af4c868 | |||
| 7df168859b | |||
| 29418978f7 | |||
| 63856c4830 | |||
| f207b2be00 | |||
| 132373f032 | |||
| 5d7e637165 | |||
| adab150ac1 | |||
| 63362bcd41 | |||
| 1bc6a25a01 | |||
| 93f1e74bfa | |||
| fef5d7d200 | |||
| cd7b278e77 | |||
| 9809a313db | |||
| f8347cb228 | |||
| 189ff2d99a |
+22
-25
@@ -119,32 +119,27 @@ get_image_paintable (GtkImage *image)
|
||||
}
|
||||
|
||||
static void
|
||||
drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer data)
|
||||
drag_begin (GtkDragSource *source,
|
||||
GtkWidget *widget)
|
||||
{
|
||||
GdkPaintable *paintable;
|
||||
|
||||
paintable = get_image_paintable (GTK_IMAGE (widget));
|
||||
if (paintable)
|
||||
{
|
||||
gtk_drag_set_icon_paintable (drag, paintable, -2, -2);
|
||||
gtk_drag_source_set_icon (source, paintable, -2, -2);
|
||||
g_object_unref (paintable);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data,
|
||||
guint info,
|
||||
gpointer data)
|
||||
static void
|
||||
get_texture (GValue *value,
|
||||
gpointer data)
|
||||
{
|
||||
GdkPaintable *paintable;
|
||||
GdkPaintable *paintable = get_image_paintable (GTK_IMAGE (data));
|
||||
|
||||
paintable = get_image_paintable (GTK_IMAGE (widget));
|
||||
if (GDK_IS_TEXTURE (paintable))
|
||||
gtk_selection_data_set_texture (selection_data, GDK_TEXTURE (paintable));
|
||||
g_value_set_object (value, paintable);
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -247,6 +242,8 @@ do_clipboard (GtkWidget *do_widget)
|
||||
{ "paste", paste_image, NULL, NULL, NULL },
|
||||
};
|
||||
GActionGroup *actions;
|
||||
GdkContentProvider *content = NULL;
|
||||
GtkDragSource *source;
|
||||
|
||||
window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
|
||||
gtk_window_set_display (GTK_WINDOW (window),
|
||||
@@ -305,15 +302,15 @@ do_clipboard (GtkWidget *do_widget)
|
||||
|
||||
/* Create the first image */
|
||||
image = gtk_image_new_from_icon_name ("dialog-warning");
|
||||
gtk_image_set_pixel_size (GTK_IMAGE (image), 48);
|
||||
gtk_container_add (GTK_CONTAINER (hbox), image);
|
||||
|
||||
/* make image a drag source */
|
||||
gtk_drag_source_set (image, GDK_BUTTON1_MASK, NULL, GDK_ACTION_COPY);
|
||||
gtk_drag_source_add_image_targets (image);
|
||||
g_signal_connect (image, "drag-begin",
|
||||
G_CALLBACK (drag_begin), image);
|
||||
g_signal_connect (image, "drag-data-get",
|
||||
G_CALLBACK (drag_data_get), image);
|
||||
content = gdk_content_provider_new_with_callback (GDK_TYPE_TEXTURE, get_texture, image);
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_COPY);
|
||||
g_object_unref (content);
|
||||
gtk_drag_source_attach (source, image, GDK_BUTTON1_MASK);
|
||||
g_signal_connect (source, "drag-begin", G_CALLBACK (drag_begin), image);
|
||||
|
||||
/* accept drops on image */
|
||||
gtk_drag_dest_set (image, GTK_DEST_DEFAULT_ALL,
|
||||
@@ -337,15 +334,15 @@ do_clipboard (GtkWidget *do_widget)
|
||||
|
||||
/* Create the second image */
|
||||
image = gtk_image_new_from_icon_name ("process-stop");
|
||||
gtk_image_set_pixel_size (GTK_IMAGE (image), 48);
|
||||
gtk_container_add (GTK_CONTAINER (hbox), image);
|
||||
|
||||
/* make image a drag source */
|
||||
gtk_drag_source_set (image, GDK_BUTTON1_MASK, NULL, GDK_ACTION_COPY);
|
||||
gtk_drag_source_add_image_targets (image);
|
||||
g_signal_connect (image, "drag-begin",
|
||||
G_CALLBACK (drag_begin), image);
|
||||
g_signal_connect (image, "drag-data-get",
|
||||
G_CALLBACK (drag_data_get), image);
|
||||
content = gdk_content_provider_new_with_callback (GDK_TYPE_TEXTURE, get_texture, image);
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_COPY);
|
||||
g_object_unref (content);
|
||||
g_signal_connect (source, "drag-begin", G_CALLBACK (drag_begin), image);
|
||||
gtk_drag_source_attach (source, image, GDK_BUTTON1_MASK);
|
||||
|
||||
/* accept drops on image */
|
||||
gtk_drag_dest_set (image, GTK_DEST_DEFAULT_ALL,
|
||||
|
||||
@@ -5,9 +5,6 @@
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
/* Drag 'n Drop */
|
||||
static const char *target_table[] = {
|
||||
"text/uri-list"
|
||||
};
|
||||
|
||||
typedef struct
|
||||
{
|
||||
@@ -76,30 +73,11 @@ search_text_changed (GtkEntry *entry, IconBrowserWindow *win)
|
||||
gtk_tree_model_filter_refilter (win->filter_model);
|
||||
}
|
||||
|
||||
static GdkPixbuf *
|
||||
get_icon (GtkWidget *image, const gchar *name, gint size)
|
||||
{
|
||||
GtkIconInfo *info;
|
||||
GtkStyleContext *context;
|
||||
GdkTexture *texture;
|
||||
GdkPixbuf *pixbuf;
|
||||
|
||||
context = gtk_widget_get_style_context (image);
|
||||
info = gtk_icon_theme_lookup_icon (gtk_icon_theme_get_default (), name, size, 0);
|
||||
texture = GDK_TEXTURE (gtk_icon_info_load_symbolic_for_context (info, context, NULL, NULL));
|
||||
pixbuf = gdk_pixbuf_get_from_texture (texture);
|
||||
g_object_unref (texture);
|
||||
g_object_unref (info);
|
||||
|
||||
return pixbuf;
|
||||
}
|
||||
|
||||
static void
|
||||
set_image (GtkWidget *image, const gchar *name, gint size)
|
||||
{
|
||||
gtk_image_set_from_icon_name (GTK_IMAGE (image), name);
|
||||
gtk_image_set_pixel_size (GTK_IMAGE (image), size);
|
||||
gtk_drag_source_set_icon_name (image, name);
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -365,78 +343,104 @@ search_mode_toggled (GObject *searchbar, GParamSpec *pspec, IconBrowserWindow *w
|
||||
gtk_list_box_unselect_all (GTK_LIST_BOX (win->context_list));
|
||||
}
|
||||
|
||||
static void
|
||||
get_image_data (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection,
|
||||
guint target_info,
|
||||
gpointer data)
|
||||
static GdkPaintable *
|
||||
get_image_paintable (GtkImage *image)
|
||||
{
|
||||
GtkWidget *image;
|
||||
const gchar *name;
|
||||
gint size;
|
||||
GdkPixbuf *pixbuf;
|
||||
const gchar *icon_name;
|
||||
GtkIconTheme *icon_theme;
|
||||
GtkIconInfo *icon_info;
|
||||
int size;
|
||||
|
||||
image = gtk_bin_get_child (GTK_BIN (widget));
|
||||
|
||||
name = gtk_image_get_icon_name (GTK_IMAGE (image));
|
||||
size = gtk_image_get_pixel_size (GTK_IMAGE (image));
|
||||
|
||||
pixbuf = get_icon (image, name, size);
|
||||
gtk_selection_data_set_pixbuf (selection, pixbuf);
|
||||
g_object_unref (pixbuf);
|
||||
switch (gtk_image_get_storage_type (image))
|
||||
{
|
||||
case GTK_IMAGE_PAINTABLE:
|
||||
return g_object_ref (gtk_image_get_paintable (image));
|
||||
case GTK_IMAGE_ICON_NAME:
|
||||
icon_name = gtk_image_get_icon_name (image);
|
||||
size = gtk_image_get_pixel_size (image);
|
||||
icon_theme = gtk_icon_theme_get_for_display (gtk_widget_get_display (GTK_WIDGET (image)));
|
||||
icon_info = gtk_icon_theme_lookup_icon (icon_theme, icon_name, size,
|
||||
GTK_ICON_LOOKUP_FORCE_SIZE | GTK_ICON_LOOKUP_GENERIC_FALLBACK);
|
||||
if (icon_info == NULL)
|
||||
return NULL;
|
||||
return gtk_icon_info_load_icon (icon_info, NULL);
|
||||
default:
|
||||
g_warning ("Image storage type %d not handled",
|
||||
gtk_image_get_storage_type (image));
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
get_scalable_image_data (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection,
|
||||
guint target_info,
|
||||
gpointer data)
|
||||
drag_begin (GtkDragSource *source,
|
||||
GtkWidget *widget)
|
||||
{
|
||||
gchar *uris[2];
|
||||
GtkIconInfo *info;
|
||||
GtkWidget *image;
|
||||
GFile *file;
|
||||
const gchar *name;
|
||||
GdkPaintable *paintable;
|
||||
|
||||
image = gtk_bin_get_child (GTK_BIN (widget));
|
||||
name = gtk_image_get_icon_name (GTK_IMAGE (image));
|
||||
paintable = get_image_paintable (GTK_IMAGE (widget));
|
||||
if (paintable)
|
||||
{
|
||||
int w, h;
|
||||
|
||||
w = gdk_paintable_get_intrinsic_width (paintable);
|
||||
h = gdk_paintable_get_intrinsic_height (paintable);
|
||||
gtk_drag_source_set_icon (source, paintable, w, h);
|
||||
g_object_unref (paintable);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
get_texture (GValue *value,
|
||||
gpointer data)
|
||||
{
|
||||
GdkPaintable *paintable = get_image_paintable (GTK_IMAGE (data));
|
||||
|
||||
if (GDK_IS_TEXTURE (paintable))
|
||||
g_value_set_object (value, paintable);
|
||||
}
|
||||
|
||||
static void
|
||||
get_file (GValue *value,
|
||||
gpointer data)
|
||||
{
|
||||
const char *name;
|
||||
GtkIconInfo *info;
|
||||
GFile *file;
|
||||
|
||||
name = gtk_image_get_icon_name (GTK_IMAGE (data));
|
||||
|
||||
info = gtk_icon_theme_lookup_icon (gtk_icon_theme_get_default (), name, -1, 0);
|
||||
file = g_file_new_for_path (gtk_icon_info_get_filename (info));
|
||||
uris[0] = g_file_get_uri (file);
|
||||
uris[1] = NULL;
|
||||
|
||||
gtk_selection_data_set_uris (selection, uris);
|
||||
|
||||
g_free (uris[0]);
|
||||
g_object_unref (info);
|
||||
g_value_set_object (value, file);
|
||||
g_object_unref (file);
|
||||
g_object_unref (info);
|
||||
}
|
||||
|
||||
static void
|
||||
setup_image_dnd (GtkWidget *image)
|
||||
{
|
||||
gtk_drag_source_set (image, GDK_BUTTON1_MASK, NULL, GDK_ACTION_COPY);
|
||||
gtk_drag_source_add_image_targets (image);
|
||||
g_signal_connect (image, "drag-data-get", G_CALLBACK (get_image_data), NULL);
|
||||
GdkContentProvider *content;
|
||||
GtkDragSource *source;
|
||||
|
||||
content = gdk_content_provider_new_with_callback (GDK_TYPE_TEXTURE, get_texture, image);
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_COPY);
|
||||
g_object_unref (content);
|
||||
g_signal_connect (source, "drag-begin", G_CALLBACK (drag_begin), image);
|
||||
gtk_drag_source_attach (source, image, GDK_BUTTON1_MASK);
|
||||
}
|
||||
|
||||
static void
|
||||
setup_scalable_image_dnd (GtkWidget *image)
|
||||
{
|
||||
GtkWidget *parent;
|
||||
GdkContentFormats *targets;
|
||||
GdkContentProvider *content;
|
||||
GtkDragSource *source;
|
||||
|
||||
parent = gtk_widget_get_parent (image);
|
||||
targets = gdk_content_formats_new (target_table, G_N_ELEMENTS (target_table));
|
||||
gtk_drag_source_set (parent, GDK_BUTTON1_MASK,
|
||||
targets,
|
||||
GDK_ACTION_COPY);
|
||||
gdk_content_formats_unref (targets);
|
||||
content = gdk_content_provider_new_with_callback (G_TYPE_FILE, get_file, image);
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_COPY);
|
||||
g_object_unref (content);
|
||||
|
||||
g_signal_connect (parent, "drag-data-get", G_CALLBACK (get_scalable_image_data), NULL);
|
||||
g_signal_connect (source, "drag-begin", G_CALLBACK (drag_begin), image);
|
||||
gtk_drag_source_attach (source, image, GDK_BUTTON1_MASK);
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -459,7 +463,6 @@ icon_browser_window_init (IconBrowserWindow *win)
|
||||
setup_image_dnd (win->image3);
|
||||
setup_image_dnd (win->image4);
|
||||
setup_image_dnd (win->image5);
|
||||
setup_image_dnd (win->image6);
|
||||
setup_scalable_image_dnd (win->image6);
|
||||
|
||||
win->contexts = g_hash_table_new_full (g_str_hash, g_str_equal, NULL, context_free);
|
||||
|
||||
@@ -344,6 +344,11 @@
|
||||
<xi:include href="xml/gtkpadcontroller.xml" />
|
||||
</chapter>
|
||||
|
||||
<chapter>
|
||||
<title>Data exchange, clipboards and Drag-and-Drop</title>
|
||||
<xi:include href="xml/gtkdragsource.xml"/>
|
||||
</chapter>
|
||||
|
||||
</part>
|
||||
|
||||
<part id="gtkbase">
|
||||
|
||||
@@ -451,6 +451,7 @@ gtk_selection_model_unselect_all
|
||||
gtk_selection_model_query_range
|
||||
<SUBSECTION>
|
||||
gtk_selection_model_selection_changed
|
||||
|
||||
<SUBSECTION Standard>
|
||||
GTK_SELECTION_MODEL
|
||||
GTK_SELECTION_MODEL_CLASS
|
||||
@@ -4995,6 +4996,10 @@ gtk_targets_include_text
|
||||
gtk_targets_include_uri
|
||||
gtk_selection_data_copy
|
||||
gtk_selection_data_free
|
||||
<SUBSECTION>
|
||||
gtk_content_formats_add_text_targets
|
||||
gtk_content_formats_add_image_targets
|
||||
gtk_content_formats_add_uri_targets
|
||||
<SUBSECTION Standard>
|
||||
GTK_TYPE_SELECTION_DATA
|
||||
<SUBSECTION Private>
|
||||
@@ -7191,3 +7196,31 @@ gtk_constraint_guide_get_max_size
|
||||
GTK_TYPE_CONSTRAINT_GUIDE
|
||||
gtk_constraint_guide_get_tyoe
|
||||
</SECTION>
|
||||
|
||||
<SECTION>
|
||||
<FILE>gtkdragsource</FILE>
|
||||
GtkDragSource
|
||||
gtk_drag_source_new
|
||||
gtk_drag_source_set_content
|
||||
gtk_drag_source_get_content
|
||||
gtk_drag_source_set_actions
|
||||
gtk_drag_source_get_actions
|
||||
gtk_drag_source_set_icon
|
||||
gtk_drag_source_drag_begin
|
||||
gtk_drag_source_drag_cancel
|
||||
gtk_drag_get_source
|
||||
gtk_drag_source_get_origin
|
||||
gtk_drag_source_get_drag
|
||||
gtk_drag_source_attach
|
||||
gtk_drag_source_detach
|
||||
gtk_drag_check_threshold
|
||||
<SUBSECTION Standard>
|
||||
GTK_TYPE_DRAG_SOURCE
|
||||
GTK_DRAG_SOURCE
|
||||
GTK_DRAG_SOURCE_CLASS
|
||||
GTK_IS_DRAG_SOURCE
|
||||
GTK_IS_DRAG_SOURCE_CLASS
|
||||
GTK_DRAG_SOURCE_GET_CLASS
|
||||
<SUBSECTION Private>
|
||||
gtk_drag_source_get_type
|
||||
</SECTION>
|
||||
|
||||
@@ -57,6 +57,7 @@ gtk_constraint_target_get_type
|
||||
gtk_container_get_type
|
||||
gtk_css_provider_get_type
|
||||
gtk_dialog_get_type
|
||||
gtk_drag_source_get_type
|
||||
gtk_drawing_area_get_type
|
||||
gtk_editable_get_type
|
||||
gtk_entry_buffer_get_type
|
||||
|
||||
@@ -903,6 +903,22 @@
|
||||
gtk_tooltip_set_custom().
|
||||
</para>
|
||||
</section>
|
||||
|
||||
<section>
|
||||
<title>Switch to the new DND api</title>
|
||||
<para>
|
||||
The source-side DND apis in GTK 4 have been changed to use a separate object, #GtkDragSource.
|
||||
</para>
|
||||
<para>
|
||||
Instead of calling gtk_drag_source_set() and connecting to #GtkWidget signals, you create
|
||||
a #GtkDragSource object, attach it to the widget with gtk_drag_source_attach(), and connect
|
||||
to #GtkDragSource signals. The signals themselves are fairly similar.
|
||||
</para>
|
||||
<para>
|
||||
Instead of calling gtk_drag_begin() on a widget, use a #GtkDragSource object and call
|
||||
gtk_drag_source_drag_begin().
|
||||
</para>
|
||||
</section>
|
||||
</section>
|
||||
|
||||
</chapter>
|
||||
|
||||
@@ -24,6 +24,7 @@
|
||||
#include "gdkcontentformats.h"
|
||||
#include "filetransferportalprivate.h"
|
||||
#include "gdktexture.h"
|
||||
#include "gdkrgbaprivate.h"
|
||||
|
||||
#include <gdk-pixbuf/gdk-pixbuf.h>
|
||||
|
||||
@@ -848,6 +849,63 @@ file_uri_deserializer (GdkContentDeserializer *deserializer)
|
||||
g_object_unref (output);
|
||||
}
|
||||
|
||||
static void
|
||||
color_deserializer_finish (GObject *source,
|
||||
GAsyncResult *result,
|
||||
gpointer deserializer)
|
||||
{
|
||||
GOutputStream *stream = G_OUTPUT_STREAM (source);
|
||||
GError *error = NULL;
|
||||
gssize written;
|
||||
|
||||
written = g_output_stream_splice_finish (stream, result, &error);
|
||||
if (written < 0)
|
||||
{
|
||||
gdk_content_deserializer_return_error (deserializer, error);
|
||||
return;
|
||||
}
|
||||
else if (written == 0)
|
||||
{
|
||||
GdkRGBA black = GDK_RGBA ("000");
|
||||
|
||||
/* Never return NULL, we only return that on error */
|
||||
g_value_set_boxed (gdk_content_deserializer_get_value (deserializer), &black);
|
||||
}
|
||||
else
|
||||
{
|
||||
guint16 *data;
|
||||
GdkRGBA rgba;
|
||||
|
||||
data = (guint16 *)g_memory_output_stream_get_data (G_MEMORY_OUTPUT_STREAM (stream));
|
||||
rgba.red = data[0] / 65535.0;
|
||||
rgba.green = data[1] / 65535.0;
|
||||
rgba.blue = data[2] / 65535.0;
|
||||
rgba.alpha = data[3] / 65535.0;
|
||||
|
||||
g_value_set_boxed (gdk_content_deserializer_get_value (deserializer), &rgba);
|
||||
}
|
||||
gdk_content_deserializer_return_success (deserializer);
|
||||
}
|
||||
|
||||
static void
|
||||
color_deserializer (GdkContentDeserializer *deserializer)
|
||||
{
|
||||
GOutputStream *output;
|
||||
guint16 *data;
|
||||
|
||||
data = g_new0 (guint16, 4);
|
||||
output = g_memory_output_stream_new (data, 4 * sizeof (guint16), NULL, g_free);
|
||||
|
||||
g_output_stream_splice_async (output,
|
||||
gdk_content_deserializer_get_input_stream (deserializer),
|
||||
G_OUTPUT_STREAM_SPLICE_CLOSE_SOURCE | G_OUTPUT_STREAM_SPLICE_CLOSE_TARGET,
|
||||
gdk_content_deserializer_get_priority (deserializer),
|
||||
gdk_content_deserializer_get_cancellable (deserializer),
|
||||
color_deserializer_finish,
|
||||
deserializer);
|
||||
g_object_unref (output);
|
||||
}
|
||||
|
||||
static void
|
||||
init (void)
|
||||
{
|
||||
@@ -956,5 +1014,11 @@ init (void)
|
||||
string_deserializer,
|
||||
(gpointer) "ASCII",
|
||||
NULL);
|
||||
|
||||
gdk_content_register_deserializer ("application/x-color",
|
||||
GDK_TYPE_RGBA,
|
||||
color_deserializer,
|
||||
NULL,
|
||||
NULL);
|
||||
}
|
||||
|
||||
|
||||
@@ -280,3 +280,233 @@ gdk_content_provider_new_for_bytes (const char *mime_type,
|
||||
|
||||
return GDK_CONTENT_PROVIDER (content);
|
||||
}
|
||||
|
||||
#define GDK_TYPE_CONTENT_PROVIDER_CALLBACK (gdk_content_provider_callback_get_type ())
|
||||
#define GDK_CONTENT_PROVIDER_CALLBACK(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GDK_TYPE_CONTENT_PROVIDER_CALLBACK, GdkContentProviderCallback))
|
||||
|
||||
typedef struct _GdkContentProviderCallback GdkContentProviderCallback;
|
||||
typedef struct _GdkContentProviderCallbackClass GdkContentProviderCallbackClass;
|
||||
|
||||
struct _GdkContentProviderCallback
|
||||
{
|
||||
GdkContentProvider parent;
|
||||
|
||||
GType type;
|
||||
GdkContentProviderGetValueFunc func;
|
||||
gpointer data;
|
||||
};
|
||||
|
||||
struct _GdkContentProviderCallbackClass
|
||||
{
|
||||
GdkContentProviderClass parent_class;
|
||||
};
|
||||
|
||||
GType gdk_content_provider_callback_get_type (void) G_GNUC_CONST;
|
||||
|
||||
G_DEFINE_TYPE (GdkContentProviderCallback, gdk_content_provider_callback, GDK_TYPE_CONTENT_PROVIDER)
|
||||
|
||||
static GdkContentFormats *
|
||||
gdk_content_provider_callback_ref_formats (GdkContentProvider *provider)
|
||||
{
|
||||
GdkContentProviderCallback *callback = GDK_CONTENT_PROVIDER_CALLBACK (provider);
|
||||
|
||||
return gdk_content_formats_new_for_gtype (callback->type);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
gdk_content_provider_callback_get_value (GdkContentProvider *provider,
|
||||
GValue *value,
|
||||
GError **error)
|
||||
{
|
||||
GdkContentProviderCallback *callback = GDK_CONTENT_PROVIDER_CALLBACK (provider);
|
||||
|
||||
if (G_VALUE_HOLDS (value, callback->type) && callback->func != NULL)
|
||||
{
|
||||
callback->func (value, callback->data);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
return GDK_CONTENT_PROVIDER_CLASS (gdk_content_provider_callback_parent_class)->get_value (provider, value, error);
|
||||
}
|
||||
|
||||
static void
|
||||
gdk_content_provider_callback_class_init (GdkContentProviderCallbackClass *class)
|
||||
{
|
||||
GdkContentProviderClass *provider_class = GDK_CONTENT_PROVIDER_CLASS (class);
|
||||
|
||||
provider_class->ref_formats = gdk_content_provider_callback_ref_formats;
|
||||
provider_class->get_value = gdk_content_provider_callback_get_value;
|
||||
}
|
||||
|
||||
static void
|
||||
gdk_content_provider_callback_init (GdkContentProviderCallback *content)
|
||||
{
|
||||
}
|
||||
|
||||
/**
|
||||
* gdk_content_provider_new_for_callback:
|
||||
* @type: the type that the callback provides
|
||||
* @func: callback to populate a #GValue
|
||||
* @data: data that gets passed to @func
|
||||
*
|
||||
* Create a content provider that provides data that is provided via a callback.
|
||||
*
|
||||
* Returns: a new #GdkContentProvider
|
||||
**/
|
||||
GdkContentProvider *
|
||||
gdk_content_provider_new_with_callback (GType type,
|
||||
GdkContentProviderGetValueFunc func,
|
||||
gpointer data)
|
||||
{
|
||||
GdkContentProviderCallback *content;
|
||||
|
||||
content = g_object_new (GDK_TYPE_CONTENT_PROVIDER_CALLBACK, NULL);
|
||||
content->type = type;
|
||||
content->func = func;
|
||||
content->data = data;
|
||||
|
||||
return GDK_CONTENT_PROVIDER (content);
|
||||
}
|
||||
|
||||
#define GDK_TYPE_CONTENT_PROVIDER_CALLBACK2 (gdk_content_provider_callback2_get_type ())
|
||||
#define GDK_CONTENT_PROVIDER_CALLBACK2(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GDK_TYPE_CONTENT_PROVIDER_CALLBACK2, GdkContentProviderCallback2))
|
||||
|
||||
typedef struct _GdkContentProviderCallback2 GdkContentProviderCallback2;
|
||||
typedef struct _GdkContentProviderCallback2Class GdkContentProviderCallback2Class;
|
||||
|
||||
struct _GdkContentProviderCallback2
|
||||
{
|
||||
GdkContentProvider parent;
|
||||
|
||||
GdkContentFormats *formats;
|
||||
GdkContentProviderGetBytesFunc func;
|
||||
gpointer data;
|
||||
};
|
||||
|
||||
struct _GdkContentProviderCallback2Class
|
||||
{
|
||||
GdkContentProviderClass parent_class;
|
||||
};
|
||||
|
||||
GType gdk_content_provider_callback2_get_type (void) G_GNUC_CONST;
|
||||
|
||||
G_DEFINE_TYPE (GdkContentProviderCallback2, gdk_content_provider_callback2, GDK_TYPE_CONTENT_PROVIDER)
|
||||
|
||||
static GdkContentFormats *
|
||||
gdk_content_provider_callback2_ref_formats (GdkContentProvider *provider)
|
||||
{
|
||||
GdkContentProviderCallback2 *callback = GDK_CONTENT_PROVIDER_CALLBACK2 (provider);
|
||||
|
||||
return gdk_content_formats_ref (callback->formats);
|
||||
}
|
||||
|
||||
static void
|
||||
gdk_content_provider_callback2_write_mime_type_done (GObject *stream,
|
||||
GAsyncResult *result,
|
||||
gpointer task)
|
||||
{
|
||||
GError *error = NULL;
|
||||
|
||||
if (!g_output_stream_write_all_finish (G_OUTPUT_STREAM (stream), result, NULL, &error))
|
||||
g_task_return_error (task, error);
|
||||
else
|
||||
g_task_return_boolean (task, TRUE);
|
||||
|
||||
g_object_unref (task);
|
||||
}
|
||||
|
||||
static void
|
||||
gdk_content_provider_callback2_write_mime_type_async (GdkContentProvider *provider,
|
||||
const char *mime_type,
|
||||
GOutputStream *stream,
|
||||
int io_priority,
|
||||
GCancellable *cancellable,
|
||||
GAsyncReadyCallback callback,
|
||||
gpointer user_data)
|
||||
{
|
||||
GdkContentProviderCallback2 *content = GDK_CONTENT_PROVIDER_CALLBACK2 (provider);
|
||||
GTask *task;
|
||||
GBytes *bytes;
|
||||
|
||||
task = g_task_new (content, cancellable, callback, user_data);
|
||||
g_task_set_priority (task, io_priority);
|
||||
g_task_set_source_tag (task, gdk_content_provider_callback2_write_mime_type_async);
|
||||
|
||||
if (!gdk_content_formats_contain_mime_type (content->formats, mime_type))
|
||||
{
|
||||
g_task_return_new_error (task, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED,
|
||||
_("Cannot provide contents as “%s”"), mime_type);
|
||||
g_object_unref (task);
|
||||
return;
|
||||
}
|
||||
|
||||
bytes = content->func (mime_type, content->data);
|
||||
if (!bytes)
|
||||
{
|
||||
g_task_return_new_error (task, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED,
|
||||
_("Failed to get contents as “%s”"), mime_type);
|
||||
g_object_unref (task);
|
||||
return;
|
||||
}
|
||||
|
||||
g_object_set_data_full (G_OBJECT (task), "bytes", bytes, (GDestroyNotify)g_bytes_unref);
|
||||
|
||||
g_output_stream_write_all_async (stream,
|
||||
g_bytes_get_data (bytes, NULL),
|
||||
g_bytes_get_size (bytes),
|
||||
io_priority,
|
||||
cancellable,
|
||||
gdk_content_provider_callback2_write_mime_type_done,
|
||||
task);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
gdk_content_provider_callback2_write_mime_type_finish (GdkContentProvider *provider,
|
||||
GAsyncResult *result,
|
||||
GError **error)
|
||||
{
|
||||
g_return_val_if_fail (g_task_is_valid (result, provider), FALSE);
|
||||
g_return_val_if_fail (g_task_get_source_tag (G_TASK (result)) == gdk_content_provider_callback2_write_mime_type_async, FALSE);
|
||||
|
||||
return g_task_propagate_boolean (G_TASK (result), error);
|
||||
}
|
||||
|
||||
static void
|
||||
gdk_content_provider_callback2_class_init (GdkContentProviderCallback2Class *class)
|
||||
{
|
||||
GdkContentProviderClass *provider_class = GDK_CONTENT_PROVIDER_CLASS (class);
|
||||
|
||||
provider_class->ref_formats = gdk_content_provider_callback2_ref_formats;
|
||||
provider_class->write_mime_type_async = gdk_content_provider_callback2_write_mime_type_async;
|
||||
provider_class->write_mime_type_finish = gdk_content_provider_callback2_write_mime_type_finish;
|
||||
}
|
||||
|
||||
static void
|
||||
gdk_content_provider_callback2_init (GdkContentProviderCallback2 *content)
|
||||
{
|
||||
}
|
||||
|
||||
/**
|
||||
* gdk_content_provider_new_with_formats:
|
||||
* @formats: formats to advertise
|
||||
* @func: callback to populate a #GValue
|
||||
* @data: data that gets passed to @func
|
||||
*
|
||||
* Create a content provider that provides data that is provided via a callback.
|
||||
*
|
||||
* Returns: a new #GdkContentProvider
|
||||
**/
|
||||
GdkContentProvider *
|
||||
gdk_content_provider_new_with_formats (GdkContentFormats *formats,
|
||||
GdkContentProviderGetBytesFunc func,
|
||||
gpointer data)
|
||||
{
|
||||
GdkContentProviderCallback2 *content;
|
||||
|
||||
content = g_object_new (GDK_TYPE_CONTENT_PROVIDER_CALLBACK2, NULL);
|
||||
content->formats = gdk_content_formats_ref (formats);
|
||||
content->func = func;
|
||||
content->data = data;
|
||||
|
||||
return GDK_CONTENT_PROVIDER (content);
|
||||
}
|
||||
|
||||
@@ -35,6 +35,21 @@ GDK_AVAILABLE_IN_ALL
|
||||
GdkContentProvider * gdk_content_provider_new_for_bytes (const char *mime_type,
|
||||
GBytes *bytes);
|
||||
|
||||
typedef void (*GdkContentProviderGetValueFunc) (GValue *value,
|
||||
gpointer data);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
GdkContentProvider * gdk_content_provider_new_with_callback (GType type,
|
||||
GdkContentProviderGetValueFunc func,
|
||||
gpointer data);
|
||||
|
||||
typedef GBytes * (*GdkContentProviderGetBytesFunc) (const char *mime_type,
|
||||
gpointer data);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
GdkContentProvider * gdk_content_provider_new_with_formats (GdkContentFormats *formats,
|
||||
GdkContentProviderGetBytesFunc func,
|
||||
gpointer data);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
|
||||
@@ -25,6 +25,7 @@
|
||||
#include "gdkpixbuf.h"
|
||||
#include "filetransferportalprivate.h"
|
||||
#include "gdktextureprivate.h"
|
||||
#include "gdkrgba.h"
|
||||
|
||||
#include <gdk-pixbuf/gdk-pixbuf.h>
|
||||
#include <string.h>
|
||||
@@ -862,6 +863,48 @@ file_text_serializer (GdkContentSerializer *serializer)
|
||||
gdk_content_serializer_set_task_data (serializer, path, g_free);
|
||||
}
|
||||
|
||||
static void
|
||||
color_serializer_finish (GObject *source,
|
||||
GAsyncResult *result,
|
||||
gpointer serializer)
|
||||
{
|
||||
GOutputStream *stream = G_OUTPUT_STREAM (source);
|
||||
GError *error = NULL;
|
||||
|
||||
if (!g_output_stream_write_all_finish (stream, result, NULL, &error))
|
||||
gdk_content_serializer_return_error (serializer, error);
|
||||
else
|
||||
gdk_content_serializer_return_success (serializer);
|
||||
}
|
||||
|
||||
static void
|
||||
color_serializer (GdkContentSerializer *serializer)
|
||||
{
|
||||
const GValue *value;
|
||||
GdkRGBA *rgba;
|
||||
guint16 *data;
|
||||
|
||||
value = gdk_content_serializer_get_value (serializer);
|
||||
rgba = g_value_get_boxed (value);
|
||||
data = g_new0 (guint16, 4);
|
||||
if (rgba)
|
||||
{
|
||||
data[0] = (guint16) (rgba->red * 65535);
|
||||
data[1] = (guint16) (rgba->green * 65535);
|
||||
data[2] = (guint16) (rgba->blue * 65535);
|
||||
data[3] = (guint16) (rgba->alpha * 65535);
|
||||
}
|
||||
|
||||
g_output_stream_write_all_async (gdk_content_serializer_get_output_stream (serializer),
|
||||
data,
|
||||
4 * sizeof (guint16),
|
||||
gdk_content_serializer_get_priority (serializer),
|
||||
gdk_content_serializer_get_cancellable (serializer),
|
||||
color_serializer_finish,
|
||||
serializer);
|
||||
gdk_content_serializer_set_task_data (serializer, data, g_free);
|
||||
}
|
||||
|
||||
static void
|
||||
init (void)
|
||||
{
|
||||
@@ -984,5 +1027,11 @@ init (void)
|
||||
string_serializer,
|
||||
(gpointer) "ASCII",
|
||||
NULL);
|
||||
|
||||
gdk_content_register_serializer (GDK_TYPE_RGBA,
|
||||
"application/x-color",
|
||||
color_serializer,
|
||||
NULL,
|
||||
NULL);
|
||||
}
|
||||
|
||||
|
||||
+31
-35
@@ -87,6 +87,7 @@
|
||||
#include "gtkgesturedrag.h"
|
||||
#include "gtkeventcontrollerscroll.h"
|
||||
#include "gtkeventcontrollerkey.h"
|
||||
#include "gtkdragsource.h"
|
||||
|
||||
#define TIMEOUT_INITIAL 500
|
||||
#define TIMEOUT_REPEAT 50
|
||||
@@ -329,9 +330,6 @@ static gboolean gtk_calendar_query_tooltip (GtkWidget *widget,
|
||||
gboolean keyboard_mode,
|
||||
GtkTooltip *tooltip);
|
||||
|
||||
static void gtk_calendar_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data);
|
||||
static void gtk_calendar_drag_data_received (GtkWidget *widget,
|
||||
GdkDrop *drop,
|
||||
GtkSelectionData *selection_data);
|
||||
@@ -392,7 +390,6 @@ gtk_calendar_class_init (GtkCalendarClass *class)
|
||||
widget_class->grab_notify = gtk_calendar_grab_notify;
|
||||
widget_class->query_tooltip = gtk_calendar_query_tooltip;
|
||||
|
||||
widget_class->drag_data_get = gtk_calendar_drag_data_get;
|
||||
widget_class->drag_motion = gtk_calendar_drag_motion;
|
||||
widget_class->drag_leave = gtk_calendar_drag_leave;
|
||||
widget_class->drag_drop = gtk_calendar_drag_drop;
|
||||
@@ -2670,6 +2667,27 @@ gtk_calendar_drag_begin (GtkGestureDrag *gesture,
|
||||
priv->in_drag = TRUE;
|
||||
}
|
||||
|
||||
static GdkContentProvider *
|
||||
get_calendar_content (GtkCalendar *calendar)
|
||||
{
|
||||
GtkCalendarPrivate *priv = gtk_calendar_get_instance_private (calendar);
|
||||
GDate *date;
|
||||
gchar str[128];
|
||||
GValue value = G_VALUE_INIT;
|
||||
GdkContentProvider *content;
|
||||
|
||||
date = g_date_new_dmy (priv->selected_day, priv->month + 1, priv->year);
|
||||
g_date_strftime (str, 127, "%x", date);
|
||||
g_free (date);
|
||||
|
||||
g_value_init (&value, G_TYPE_STRING);
|
||||
g_value_set_string (&value, str);
|
||||
content = gdk_content_provider_new_for_value (&value);
|
||||
g_value_unset (&value);
|
||||
|
||||
return content;
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_calendar_drag_update (GtkGestureDrag *gesture,
|
||||
double x,
|
||||
@@ -2680,8 +2698,9 @@ gtk_calendar_drag_update (GtkGestureDrag *gesture,
|
||||
GtkCalendar *calendar = GTK_CALENDAR (widget);
|
||||
GtkCalendarPrivate *priv = gtk_calendar_get_instance_private (calendar);
|
||||
gdouble start_x, start_y;
|
||||
GdkDrag *drag;
|
||||
GdkContentFormats *targets;
|
||||
GtkDragSource *source;
|
||||
GdkContentProvider *content;
|
||||
GdkDevice *device;
|
||||
|
||||
if (!priv->in_drag)
|
||||
return;
|
||||
@@ -2691,19 +2710,14 @@ gtk_calendar_drag_update (GtkGestureDrag *gesture,
|
||||
|
||||
gtk_gesture_drag_get_start_point (gesture, &start_x, &start_y);
|
||||
|
||||
gtk_event_controller_reset (GTK_EVENT_CONTROLLER (gesture));
|
||||
|
||||
targets = gdk_content_formats_new (NULL, 0);
|
||||
targets = gtk_content_formats_add_text_targets (targets);
|
||||
drag = gtk_drag_begin (widget,
|
||||
gtk_gesture_get_device (GTK_GESTURE (gesture)),
|
||||
targets, GDK_ACTION_COPY,
|
||||
start_x, start_y);
|
||||
content = get_calendar_content (calendar);
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_COPY);
|
||||
g_object_unref (content);
|
||||
device = gtk_gesture_get_device (GTK_GESTURE (gesture));
|
||||
gtk_drag_source_drag_begin (source, widget, device, start_x, start_y);
|
||||
g_object_unref (source);
|
||||
|
||||
priv->in_drag = 0;
|
||||
gdk_content_formats_unref (targets);
|
||||
|
||||
gtk_drag_set_icon_default (drag);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
@@ -2923,24 +2937,6 @@ gtk_calendar_grab_notify (GtkWidget *widget,
|
||||
* Drag and Drop *
|
||||
****************************************/
|
||||
|
||||
static void
|
||||
gtk_calendar_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data)
|
||||
{
|
||||
GtkCalendar *calendar = GTK_CALENDAR (widget);
|
||||
GtkCalendarPrivate *priv = gtk_calendar_get_instance_private (calendar);
|
||||
GDate *date;
|
||||
gchar str[128];
|
||||
gsize len;
|
||||
|
||||
date = g_date_new_dmy (priv->selected_day, priv->month + 1, priv->year);
|
||||
len = g_date_strftime (str, 127, "%x", date);
|
||||
gtk_selection_data_set_text (selection_data, str, len);
|
||||
|
||||
g_free (date);
|
||||
}
|
||||
|
||||
/* Get/set whether drag_motion requested the drag data and
|
||||
* drag_data_received should thus not actually insert the data,
|
||||
* since the data doesn’t result from a drop.
|
||||
|
||||
+21
-50
@@ -45,6 +45,7 @@
|
||||
#include "gtkprivate.h"
|
||||
#include "gtksnapshot.h"
|
||||
#include "gtkstylecontext.h"
|
||||
#include "gtkdragsource.h"
|
||||
|
||||
|
||||
/**
|
||||
@@ -121,15 +122,6 @@ static void gtk_color_button_get_property (GObject *object,
|
||||
static void gtk_color_button_clicked (GtkButton *button,
|
||||
gpointer user_data);
|
||||
|
||||
/* source side drag signals */
|
||||
static void gtk_color_button_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer data);
|
||||
static void gtk_color_button_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data,
|
||||
GtkColorButton *button);
|
||||
|
||||
/* target side drag signals */
|
||||
static void gtk_color_button_drag_data_received (GtkWidget *widget,
|
||||
GdkDrop *drop,
|
||||
@@ -286,50 +278,28 @@ gtk_color_button_drag_data_received (GtkWidget *widget,
|
||||
}
|
||||
|
||||
static void
|
||||
set_color_icon (GdkDrag *drag,
|
||||
const GdkRGBA *rgba)
|
||||
gtk_color_button_drag_begin (GtkDragSource *source,
|
||||
GtkColorButton *button)
|
||||
{
|
||||
GtkColorButtonPrivate *priv = gtk_color_button_get_instance_private (button);
|
||||
GtkSnapshot *snapshot;
|
||||
GdkPaintable *paintable;
|
||||
|
||||
snapshot = gtk_snapshot_new ();
|
||||
gtk_snapshot_append_color (snapshot,
|
||||
rgba,
|
||||
&GRAPHENE_RECT_INIT(0, 0, 48, 32));
|
||||
gtk_snapshot_append_color (snapshot, &priv->rgba, &GRAPHENE_RECT_INIT(0, 0, 48, 32));
|
||||
paintable = gtk_snapshot_free_to_paintable (snapshot, NULL);
|
||||
|
||||
gtk_drag_set_icon_paintable (drag, paintable, 0, 0);
|
||||
gtk_drag_source_set_icon (source, paintable, 0, 0);
|
||||
|
||||
g_object_unref (paintable);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_color_button_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer data)
|
||||
get_rgba_value (GValue *value,
|
||||
gpointer data)
|
||||
{
|
||||
GtkColorButton *button = data;
|
||||
GtkColorButtonPrivate *priv = gtk_color_button_get_instance_private (button);
|
||||
|
||||
set_color_icon (drag, &priv->rgba);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_color_button_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data,
|
||||
GtkColorButton *button)
|
||||
{
|
||||
GtkColorButtonPrivate *priv = gtk_color_button_get_instance_private (button);
|
||||
guint16 dropped[4];
|
||||
|
||||
dropped[0] = (guint16) (priv->rgba.red * 65535);
|
||||
dropped[1] = (guint16) (priv->rgba.green * 65535);
|
||||
dropped[2] = (guint16) (priv->rgba.blue * 65535);
|
||||
dropped[3] = (guint16) (priv->rgba.alpha * 65535);
|
||||
|
||||
gtk_selection_data_set (selection_data,
|
||||
gtk_selection_data_get_target (selection_data),
|
||||
16, (guchar *)dropped, 8);
|
||||
GtkColorButtonPrivate *priv = gtk_color_button_get_instance_private (GTK_COLOR_BUTTON (data));
|
||||
g_value_set_boxed (value, &priv->rgba);
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -340,6 +310,8 @@ gtk_color_button_init (GtkColorButton *button)
|
||||
PangoRectangle rect;
|
||||
GtkStyleContext *context;
|
||||
GdkContentFormats *targets;
|
||||
GdkContentProvider *content;
|
||||
GtkDragSource *source;
|
||||
|
||||
priv->button = gtk_button_new ();
|
||||
g_signal_connect (priv->button, "clicked", G_CALLBACK (gtk_color_button_clicked), button);
|
||||
@@ -370,17 +342,16 @@ gtk_color_button_init (GtkColorButton *button)
|
||||
GTK_DEST_DEFAULT_DROP,
|
||||
targets,
|
||||
GDK_ACTION_COPY);
|
||||
gtk_drag_source_set (priv->button,
|
||||
GDK_BUTTON1_MASK|GDK_BUTTON3_MASK,
|
||||
targets,
|
||||
GDK_ACTION_COPY);
|
||||
gdk_content_formats_unref (targets);
|
||||
g_signal_connect (priv->button, "drag-begin",
|
||||
G_CALLBACK (gtk_color_button_drag_begin), button);
|
||||
g_signal_connect (priv->button, "drag-data-received",
|
||||
G_CALLBACK (gtk_color_button_drag_data_received), button);
|
||||
g_signal_connect (priv->button, "drag-data-get",
|
||||
G_CALLBACK (gtk_color_button_drag_data_get), button);
|
||||
gdk_content_formats_unref (targets);
|
||||
|
||||
content = gdk_content_provider_new_with_callback (GDK_TYPE_RGBA, get_rgba_value, button);
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_COPY);
|
||||
g_object_unref (content);
|
||||
g_signal_connect (source, "drag-begin", G_CALLBACK (gtk_color_button_drag_begin), button);
|
||||
|
||||
gtk_drag_source_attach (source, priv->button, GDK_BUTTON1_MASK|GDK_BUTTON3_MASK);
|
||||
|
||||
context = gtk_widget_get_style_context (GTK_WIDGET (priv->button));
|
||||
gtk_style_context_add_class (context, "color");
|
||||
|
||||
+24
-47
@@ -40,6 +40,7 @@
|
||||
#include "gtkwidgetprivate.h"
|
||||
#include "gtkeventcontrollerkey.h"
|
||||
#include "gtknative.h"
|
||||
#include "gtkdragsource.h"
|
||||
|
||||
#include "a11y/gtkcolorswatchaccessibleprivate.h"
|
||||
|
||||
@@ -113,56 +114,23 @@ swatch_snapshot (GtkWidget *widget,
|
||||
gtk_widget_snapshot_child (widget, priv->overlay_widget, snapshot);
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
drag_set_color_icon (GdkDrag *drag,
|
||||
const GdkRGBA *color)
|
||||
gtk_color_swatch_drag_begin (GtkDragSource *source,
|
||||
GtkColorSwatch *swatch)
|
||||
{
|
||||
GtkColorSwatchPrivate *priv = gtk_color_swatch_get_instance_private (swatch);
|
||||
GtkSnapshot *snapshot;
|
||||
GdkPaintable *paintable;
|
||||
|
||||
snapshot = gtk_snapshot_new ();
|
||||
gtk_snapshot_append_color (snapshot,
|
||||
color,
|
||||
&GRAPHENE_RECT_INIT(0, 0, 48, 32));
|
||||
gtk_snapshot_append_color (snapshot, &priv->color, &GRAPHENE_RECT_INIT(0, 0, 48, 32));
|
||||
paintable = gtk_snapshot_free_to_paintable (snapshot, NULL);
|
||||
|
||||
gtk_drag_set_icon_paintable (drag, paintable, 4, 4);
|
||||
gtk_drag_source_set_icon (source, paintable, 0, 0);
|
||||
|
||||
g_object_unref (paintable);
|
||||
}
|
||||
|
||||
static void
|
||||
swatch_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag)
|
||||
{
|
||||
GtkColorSwatch *swatch = GTK_COLOR_SWATCH (widget);
|
||||
GdkRGBA color;
|
||||
|
||||
gtk_color_swatch_get_rgba (swatch, &color);
|
||||
drag_set_color_icon (drag, &color);
|
||||
}
|
||||
|
||||
static void
|
||||
swatch_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data)
|
||||
{
|
||||
GtkColorSwatch *swatch = GTK_COLOR_SWATCH (widget);
|
||||
guint16 vals[4];
|
||||
GdkRGBA color;
|
||||
|
||||
gtk_color_swatch_get_rgba (swatch, &color);
|
||||
|
||||
vals[0] = color.red * 0xffff;
|
||||
vals[1] = color.green * 0xffff;
|
||||
vals[2] = color.blue * 0xffff;
|
||||
vals[3] = color.alpha * 0xffff;
|
||||
|
||||
gtk_selection_data_set (selection_data,
|
||||
g_intern_static_string ("application/x-color"),
|
||||
16, (guchar *)vals, 8);
|
||||
}
|
||||
|
||||
static void
|
||||
swatch_drag_data_received (GtkWidget *widget,
|
||||
GdkDrop *drop,
|
||||
@@ -523,8 +491,6 @@ gtk_color_swatch_class_init (GtkColorSwatchClass *class)
|
||||
|
||||
widget_class->measure = gtk_color_swatch_measure;
|
||||
widget_class->snapshot = swatch_snapshot;
|
||||
widget_class->drag_begin = swatch_drag_begin;
|
||||
widget_class->drag_data_get = swatch_drag_data_get;
|
||||
widget_class->drag_data_received = swatch_drag_data_received;
|
||||
widget_class->popup_menu = swatch_popup_menu;
|
||||
widget_class->size_allocate = swatch_size_allocate;
|
||||
@@ -601,6 +567,14 @@ static const char *dnd_targets[] = {
|
||||
"application/x-color"
|
||||
};
|
||||
|
||||
static void
|
||||
get_rgba_value (GValue *value,
|
||||
gpointer data)
|
||||
{
|
||||
GtkColorSwatchPrivate *priv = gtk_color_swatch_get_instance_private (GTK_COLOR_SWATCH (data));
|
||||
g_value_set_boxed (value, &priv->color);
|
||||
}
|
||||
|
||||
void
|
||||
gtk_color_swatch_set_rgba (GtkColorSwatch *swatch,
|
||||
const GdkRGBA *color)
|
||||
@@ -612,12 +586,15 @@ gtk_color_swatch_set_rgba (GtkColorSwatch *swatch,
|
||||
|
||||
if (!priv->has_color)
|
||||
{
|
||||
GdkContentFormats *targets = gdk_content_formats_new (dnd_targets, G_N_ELEMENTS (dnd_targets));
|
||||
gtk_drag_source_set (GTK_WIDGET (swatch),
|
||||
GDK_BUTTON1_MASK | GDK_BUTTON3_MASK,
|
||||
targets,
|
||||
GDK_ACTION_COPY | GDK_ACTION_MOVE);
|
||||
gdk_content_formats_unref (targets);
|
||||
GdkContentProvider *content;
|
||||
GtkDragSource *source;
|
||||
|
||||
content = gdk_content_provider_new_with_callback (GDK_TYPE_RGBA, get_rgba_value, swatch);
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_COPY);
|
||||
g_object_unref (content);
|
||||
g_signal_connect (source, "drag-begin", G_CALLBACK (gtk_color_swatch_drag_begin), swatch);
|
||||
|
||||
gtk_drag_source_attach (source, GTK_WIDGET (swatch), GDK_BUTTON1_MASK | GDK_BUTTON3_MASK);
|
||||
}
|
||||
|
||||
priv->has_color = TRUE;
|
||||
|
||||
-792
@@ -63,21 +63,8 @@
|
||||
*/
|
||||
|
||||
|
||||
typedef struct _GtkDragSourceInfo GtkDragSourceInfo;
|
||||
typedef struct _GtkDragDestInfo GtkDragDestInfo;
|
||||
|
||||
struct _GtkDragSourceInfo
|
||||
{
|
||||
GtkWidget *widget;
|
||||
GdkContentFormats *target_list; /* Targets for drag data */
|
||||
GdkDrag *drag; /* drag context */
|
||||
GtkWidget *icon_window; /* Window for drag */
|
||||
GtkWidget *icon_widget; /* Widget for drag */
|
||||
|
||||
guint drop_timeout; /* Timeout for aborting drop */
|
||||
guint destroy_icon : 1; /* If true, destroy icon_widget */
|
||||
};
|
||||
|
||||
struct _GtkDragDestInfo
|
||||
{
|
||||
GtkWidget *widget; /* Widget in which drag is in */
|
||||
@@ -118,33 +105,6 @@ static void gtk_drag_dest_set_widget (GtkDragDestInfo *info,
|
||||
|
||||
static GtkDragDestInfo * gtk_drag_get_dest_info (GdkDrop *drop,
|
||||
gboolean create);
|
||||
static GtkDragSourceInfo *gtk_drag_get_source_info (GdkDrag *drag,
|
||||
gboolean create);
|
||||
static void gtk_drag_clear_source_info (GdkDrag *drag);
|
||||
|
||||
static void gtk_drag_drop (GtkDragSourceInfo *info);
|
||||
static void gtk_drag_drop_finished (GtkDragSourceInfo *info,
|
||||
GtkDragResult result);
|
||||
static void gtk_drag_cancel_internal (GtkDragSourceInfo *info,
|
||||
GtkDragResult result);
|
||||
|
||||
static void gtk_drag_remove_icon (GtkDragSourceInfo *info);
|
||||
static void gtk_drag_source_info_destroy (GtkDragSourceInfo *info);
|
||||
|
||||
static void gtk_drag_drop_performed_cb (GdkDrag *drag,
|
||||
GtkDragSourceInfo *info);
|
||||
static void gtk_drag_cancel_cb (GdkDrag *drag,
|
||||
GdkDragCancelReason reason,
|
||||
GtkDragSourceInfo *info);
|
||||
static void gtk_drag_dnd_finished_cb (GdkDrag *drag,
|
||||
GtkDragSourceInfo *info);
|
||||
|
||||
static gboolean gtk_drag_abort_timeout (gpointer data);
|
||||
|
||||
static void set_icon_helper (GdkDrag *drag,
|
||||
GtkImageDefinition *def,
|
||||
gint hot_x,
|
||||
gint hot_y);
|
||||
|
||||
|
||||
/********************
|
||||
@@ -305,30 +265,6 @@ gtk_drag_get_data (GtkWidget *widget,
|
||||
data);
|
||||
}
|
||||
|
||||
/**
|
||||
* gtk_drag_get_source_widget:
|
||||
* @drag: a drag context
|
||||
*
|
||||
* Determines the source widget for a drag.
|
||||
*
|
||||
* Returns: (nullable) (transfer none): if the drag is occurring
|
||||
* within a single application, a pointer to the source widget.
|
||||
* Otherwise, %NULL.
|
||||
*/
|
||||
GtkWidget *
|
||||
gtk_drag_get_source_widget (GdkDrag *drag)
|
||||
{
|
||||
GtkDragSourceInfo *info;
|
||||
|
||||
g_return_val_if_fail (GDK_IS_DRAG (drag), NULL);
|
||||
|
||||
info = gtk_drag_get_source_info (drag, FALSE);
|
||||
if (info == NULL)
|
||||
return NULL;
|
||||
|
||||
return info->widget;
|
||||
}
|
||||
|
||||
/**
|
||||
* gtk_drag_highlight: (method)
|
||||
* @widget: a widget to highlight
|
||||
@@ -590,33 +526,6 @@ gtk_drag_get_dest_info (GdkDrop *drop,
|
||||
return info;
|
||||
}
|
||||
|
||||
static GQuark dest_info_quark = 0;
|
||||
|
||||
static GtkDragSourceInfo *
|
||||
gtk_drag_get_source_info (GdkDrag *drag,
|
||||
gboolean create)
|
||||
{
|
||||
GtkDragSourceInfo *info;
|
||||
if (!dest_info_quark)
|
||||
dest_info_quark = g_quark_from_static_string ("gtk-source-info");
|
||||
|
||||
info = g_object_get_qdata (G_OBJECT (drag), dest_info_quark);
|
||||
if (!info && create)
|
||||
{
|
||||
info = g_new0 (GtkDragSourceInfo, 1);
|
||||
info->drag = drag;
|
||||
g_object_set_qdata (G_OBJECT (drag), dest_info_quark, info);
|
||||
}
|
||||
|
||||
return info;
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_drag_clear_source_info (GdkDrag *drag)
|
||||
{
|
||||
g_object_set_qdata (G_OBJECT (drag), dest_info_quark, NULL);
|
||||
}
|
||||
|
||||
/*
|
||||
* Default drag handlers
|
||||
*/
|
||||
@@ -722,704 +631,3 @@ gtk_drag_dest_drop (GtkWidget *widget,
|
||||
|
||||
return (site->flags & GTK_DEST_DEFAULT_DROP) ? TRUE : retval;
|
||||
}
|
||||
|
||||
/***************
|
||||
* Source side *
|
||||
***************/
|
||||
|
||||
#define GTK_TYPE_DRAG_CONTENT (gtk_drag_content_get_type ())
|
||||
#define GTK_DRAG_CONTENT(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GTK_TYPE_DRAG_CONTENT, GtkDragContent))
|
||||
#define GTK_IS_DRAG_CONTENT(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GTK_TYPE_DRAG_CONTENT))
|
||||
#define GTK_DRAG_CONTENT_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GTK_TYPE_DRAG_CONTENT, GtkDragContentClass))
|
||||
#define GTK_IS_DRAG_CONTENT_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GTK_TYPE_DRAG_CONTENT))
|
||||
#define GTK_DRAG_CONTENT_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GTK_TYPE_DRAG_CONTENT, GtkDragContentClass))
|
||||
|
||||
typedef struct _GtkDragContent GtkDragContent;
|
||||
typedef struct _GtkDragContentClass GtkDragContentClass;
|
||||
|
||||
struct _GtkDragContent
|
||||
{
|
||||
GdkContentProvider parent;
|
||||
|
||||
GtkWidget *widget;
|
||||
GdkDrag *drag;
|
||||
GdkContentFormats *formats;
|
||||
guint32 time;
|
||||
};
|
||||
|
||||
struct _GtkDragContentClass
|
||||
{
|
||||
GdkContentProviderClass parent_class;
|
||||
};
|
||||
|
||||
GType gtk_drag_content_get_type (void) G_GNUC_CONST;
|
||||
|
||||
G_DEFINE_TYPE (GtkDragContent, gtk_drag_content, GDK_TYPE_CONTENT_PROVIDER)
|
||||
|
||||
static GdkContentFormats *
|
||||
gtk_drag_content_ref_formats (GdkContentProvider *provider)
|
||||
{
|
||||
GtkDragContent *content = GTK_DRAG_CONTENT (provider);
|
||||
|
||||
return gdk_content_formats_ref (content->formats);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_drag_content_write_mime_type_done (GObject *stream,
|
||||
GAsyncResult *result,
|
||||
gpointer task)
|
||||
{
|
||||
GError *error = NULL;
|
||||
|
||||
if (!g_output_stream_write_all_finish (G_OUTPUT_STREAM (stream),
|
||||
result,
|
||||
NULL,
|
||||
&error))
|
||||
{
|
||||
g_task_return_error (task, error);
|
||||
}
|
||||
else
|
||||
{
|
||||
g_task_return_boolean (task, TRUE);
|
||||
}
|
||||
|
||||
g_object_unref (task);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_drag_content_write_mime_type_async (GdkContentProvider *provider,
|
||||
const char *mime_type,
|
||||
GOutputStream *stream,
|
||||
int io_priority,
|
||||
GCancellable *cancellable,
|
||||
GAsyncReadyCallback callback,
|
||||
gpointer user_data)
|
||||
{
|
||||
GtkDragContent *content = GTK_DRAG_CONTENT (provider);
|
||||
GtkSelectionData sdata = { 0, };
|
||||
GTask *task;
|
||||
|
||||
task = g_task_new (content, cancellable, callback, user_data);
|
||||
g_task_set_priority (task, io_priority);
|
||||
g_task_set_source_tag (task, gtk_drag_content_write_mime_type_async);
|
||||
|
||||
sdata.target = g_intern_string (mime_type);
|
||||
sdata.length = -1;
|
||||
sdata.display = gtk_widget_get_display (content->widget);
|
||||
|
||||
g_signal_emit_by_name (content->widget, "drag-data-get",
|
||||
content->drag,
|
||||
&sdata);
|
||||
|
||||
if (sdata.length == -1)
|
||||
{
|
||||
g_task_return_new_error (task, G_IO_ERROR, G_IO_ERROR_FAILED,
|
||||
_("Cannot provide contents as “%s”"), mime_type);
|
||||
g_object_unref (task);
|
||||
return;
|
||||
}
|
||||
g_task_set_task_data (task, sdata.data, g_free);
|
||||
|
||||
g_output_stream_write_all_async (stream,
|
||||
sdata.data,
|
||||
sdata.length,
|
||||
io_priority,
|
||||
cancellable,
|
||||
gtk_drag_content_write_mime_type_done,
|
||||
task);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
gtk_drag_content_write_mime_type_finish (GdkContentProvider *provider,
|
||||
GAsyncResult *result,
|
||||
GError **error)
|
||||
{
|
||||
g_return_val_if_fail (g_task_is_valid (result, provider), FALSE);
|
||||
g_return_val_if_fail (g_task_get_source_tag (G_TASK (result)) == gtk_drag_content_write_mime_type_async, FALSE);
|
||||
|
||||
return g_task_propagate_boolean (G_TASK (result), error);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_drag_content_finalize (GObject *object)
|
||||
{
|
||||
GtkDragContent *content = GTK_DRAG_CONTENT (object);
|
||||
|
||||
g_clear_object (&content->widget);
|
||||
g_clear_pointer (&content->formats, gdk_content_formats_unref);
|
||||
|
||||
G_OBJECT_CLASS (gtk_drag_content_parent_class)->finalize (object);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_drag_content_class_init (GtkDragContentClass *class)
|
||||
{
|
||||
GdkContentProviderClass *provider_class = GDK_CONTENT_PROVIDER_CLASS (class);
|
||||
GObjectClass *object_class = G_OBJECT_CLASS (class);
|
||||
|
||||
object_class->finalize = gtk_drag_content_finalize;
|
||||
|
||||
provider_class->ref_formats = gtk_drag_content_ref_formats;
|
||||
provider_class->write_mime_type_async = gtk_drag_content_write_mime_type_async;
|
||||
provider_class->write_mime_type_finish = gtk_drag_content_write_mime_type_finish;
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_drag_content_init (GtkDragContent *content)
|
||||
{
|
||||
}
|
||||
|
||||
/* Like gtk_drag_begin(), but also takes a GtkImageDefinition
|
||||
* so that we can set the icon from the source site information
|
||||
*/
|
||||
GdkDrag *
|
||||
gtk_drag_begin_internal (GtkWidget *widget,
|
||||
GdkDevice *device,
|
||||
GtkImageDefinition *icon,
|
||||
GdkContentFormats *target_list,
|
||||
GdkDragAction actions,
|
||||
int x,
|
||||
int y)
|
||||
{
|
||||
GtkDragSourceInfo *info;
|
||||
GtkNative *native;
|
||||
GdkDrag *drag;
|
||||
double px, py;
|
||||
int dx, dy;
|
||||
GtkDragContent *content;
|
||||
|
||||
if (gdk_device_get_source (device) == GDK_SOURCE_KEYBOARD)
|
||||
device = gdk_device_get_associated_device (device);
|
||||
|
||||
native = gtk_widget_get_native (widget);
|
||||
gtk_widget_translate_coordinates (widget, GTK_WIDGET (native), x, y, &x, &y);
|
||||
gdk_surface_get_device_position (gtk_native_get_surface (native),
|
||||
device,
|
||||
&px, &py,
|
||||
NULL);
|
||||
dx = round (px) - x;
|
||||
dy = round (py) - y;
|
||||
|
||||
content = g_object_new (GTK_TYPE_DRAG_CONTENT, NULL);
|
||||
content->widget = g_object_ref (widget);
|
||||
content->formats = gdk_content_formats_ref (target_list);
|
||||
|
||||
drag = gdk_drag_begin (gtk_native_get_surface (native), device, GDK_CONTENT_PROVIDER (content), actions, dx, dy);
|
||||
if (drag == NULL)
|
||||
{
|
||||
g_object_unref (content);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
content->drag = drag;
|
||||
g_object_unref (content);
|
||||
|
||||
info = gtk_drag_get_source_info (drag, TRUE);
|
||||
|
||||
g_object_set_data (G_OBJECT (widget), I_("gtk-info"), info);
|
||||
|
||||
info->widget = g_object_ref (widget);
|
||||
|
||||
info->target_list = target_list;
|
||||
gdk_content_formats_ref (target_list);
|
||||
|
||||
info->icon_window = NULL;
|
||||
info->icon_widget = NULL;
|
||||
info->destroy_icon = FALSE;
|
||||
|
||||
gtk_widget_reset_controllers (widget);
|
||||
|
||||
g_signal_emit_by_name (widget, "drag-begin", info->drag);
|
||||
|
||||
/* Ensure that we have an icon before we start the drag; the
|
||||
* application may have set one in ::drag_begin, or it may
|
||||
* not have set one.
|
||||
*/
|
||||
if (!info->icon_widget)
|
||||
{
|
||||
if (icon)
|
||||
{
|
||||
set_icon_helper (info->drag, icon, 0, 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
icon = gtk_image_definition_new_icon_name ("text-x-generic");
|
||||
set_icon_helper (info->drag, icon, 0, 0);
|
||||
gtk_image_definition_unref (icon);
|
||||
}
|
||||
}
|
||||
|
||||
g_signal_connect (drag, "drop-performed",
|
||||
G_CALLBACK (gtk_drag_drop_performed_cb), info);
|
||||
g_signal_connect (drag, "dnd-finished",
|
||||
G_CALLBACK (gtk_drag_dnd_finished_cb), info);
|
||||
g_signal_connect (drag, "cancel",
|
||||
G_CALLBACK (gtk_drag_cancel_cb), info);
|
||||
|
||||
return info->drag;
|
||||
}
|
||||
|
||||
/**
|
||||
* gtk_drag_begin: (method)
|
||||
* @widget: the source widget
|
||||
* @device: (nullable): the device that starts the drag or %NULL to use the default pointer
|
||||
* @targets: The targets (data formats) in which the source can provide the data
|
||||
* @actions: A bitmask of the allowed drag actions for this drag
|
||||
* @x: The initial x coordinate to start dragging from, in the coordinate space of @widget.
|
||||
* @y: The initial y coordinate to start dragging from, in the coordinate space of @widget.
|
||||
*
|
||||
* Initiates a drag on the source side. The function only needs to be used
|
||||
* when the application is starting drags itself, and is not needed when
|
||||
* gtk_drag_source_set() is used.
|
||||
*
|
||||
* Returns: (transfer none): the context for this drag
|
||||
*/
|
||||
GdkDrag *
|
||||
gtk_drag_begin (GtkWidget *widget,
|
||||
GdkDevice *device,
|
||||
GdkContentFormats *targets,
|
||||
GdkDragAction actions,
|
||||
gint x,
|
||||
gint y)
|
||||
{
|
||||
g_return_val_if_fail (GTK_IS_WIDGET (widget), NULL);
|
||||
g_return_val_if_fail (device == NULL || GDK_IS_DEVICE (device), NULL);
|
||||
g_return_val_if_fail (gtk_widget_get_realized (widget), NULL);
|
||||
g_return_val_if_fail (targets != NULL, NULL);
|
||||
|
||||
if (device == NULL)
|
||||
{
|
||||
GdkSeat *seat;
|
||||
|
||||
seat = gdk_display_get_default_seat (gtk_widget_get_display (widget));
|
||||
device = gdk_seat_get_pointer (seat);
|
||||
}
|
||||
|
||||
return gtk_drag_begin_internal (widget,
|
||||
device,
|
||||
NULL,
|
||||
targets,
|
||||
actions,
|
||||
x, y);
|
||||
}
|
||||
|
||||
static void
|
||||
icon_widget_destroyed (GtkWidget *widget,
|
||||
GtkDragSourceInfo *info)
|
||||
{
|
||||
g_clear_object (&info->icon_widget);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_drag_set_icon_widget_internal (GdkDrag *drag,
|
||||
GtkWidget *widget,
|
||||
gint hot_x,
|
||||
gint hot_y,
|
||||
gboolean destroy_on_release)
|
||||
{
|
||||
GtkDragSourceInfo *info;
|
||||
|
||||
g_return_if_fail (!GTK_IS_WINDOW (widget));
|
||||
|
||||
info = gtk_drag_get_source_info (drag, FALSE);
|
||||
if (info == NULL)
|
||||
{
|
||||
if (destroy_on_release)
|
||||
gtk_widget_destroy (widget);
|
||||
return;
|
||||
}
|
||||
|
||||
gtk_drag_remove_icon (info);
|
||||
|
||||
if (widget)
|
||||
g_object_ref (widget);
|
||||
|
||||
info->icon_widget = widget;
|
||||
info->destroy_icon = destroy_on_release;
|
||||
|
||||
if (!widget)
|
||||
return;
|
||||
|
||||
g_signal_connect (widget, "destroy", G_CALLBACK (icon_widget_destroyed), info);
|
||||
|
||||
gdk_drag_set_hotspot (drag, hot_x, hot_y);
|
||||
|
||||
if (!info->icon_window)
|
||||
{
|
||||
info->icon_window = gtk_drag_icon_new ();
|
||||
g_object_ref_sink (info->icon_window);
|
||||
gtk_widget_set_size_request (info->icon_window, 24, 24);
|
||||
gtk_drag_icon_set_surface (GTK_DRAG_ICON (info->icon_window),
|
||||
gdk_drag_get_drag_surface (drag));
|
||||
gtk_widget_show (info->icon_window);
|
||||
}
|
||||
|
||||
gtk_drag_icon_set_widget (GTK_DRAG_ICON (info->icon_window), widget);
|
||||
}
|
||||
|
||||
/**
|
||||
* gtk_drag_set_icon_widget:
|
||||
* @drag: the context for a drag
|
||||
* @widget: a widget to use as an icon
|
||||
* @hot_x: the X offset within @widget of the hotspot
|
||||
* @hot_y: the Y offset within @widget of the hotspot
|
||||
*
|
||||
* Changes the icon for drag operation to a given widget.
|
||||
* GTK+ will not destroy the widget, so if you don’t want
|
||||
* it to persist, you should connect to the “drag-end”
|
||||
* signal and destroy it yourself.
|
||||
*/
|
||||
void
|
||||
gtk_drag_set_icon_widget (GdkDrag *drag,
|
||||
GtkWidget *widget,
|
||||
gint hot_x,
|
||||
gint hot_y)
|
||||
{
|
||||
g_return_if_fail (GDK_IS_DRAG (drag));
|
||||
g_return_if_fail (GTK_IS_WIDGET (widget));
|
||||
|
||||
gtk_drag_set_icon_widget_internal (drag, widget, hot_x, hot_y, FALSE);
|
||||
}
|
||||
|
||||
static void
|
||||
set_icon_helper (GdkDrag *drag,
|
||||
GtkImageDefinition *def,
|
||||
gint hot_x,
|
||||
gint hot_y)
|
||||
{
|
||||
GtkWidget *widget;
|
||||
|
||||
widget = gtk_image_new ();
|
||||
gtk_style_context_add_class (gtk_widget_get_style_context (widget), "drag-icon");
|
||||
gtk_image_set_from_definition (GTK_IMAGE (widget), def);
|
||||
gtk_drag_set_icon_widget_internal (drag, widget, hot_x, hot_y, TRUE);
|
||||
}
|
||||
|
||||
void
|
||||
gtk_drag_set_icon_definition (GdkDrag *drag,
|
||||
GtkImageDefinition *def,
|
||||
gint hot_x,
|
||||
gint hot_y)
|
||||
{
|
||||
g_return_if_fail (GDK_IS_DRAG (drag));
|
||||
g_return_if_fail (def != NULL);
|
||||
|
||||
set_icon_helper (drag, def, hot_x, hot_y);
|
||||
}
|
||||
|
||||
/**
|
||||
* gtk_drag_set_icon_paintable:
|
||||
* @drag: the context for a drag
|
||||
* @paintable: the #GdkPaintable to use as icon
|
||||
* @hot_x: the X offset of the hotspot within the icon
|
||||
* @hot_y: the Y offset of the hotspot within the icon
|
||||
*
|
||||
* Sets @paintable as the icon for a given drag. GTK+ retains
|
||||
* references for the arguments, and will release them when
|
||||
* they are no longer needed.
|
||||
*
|
||||
* To position the @paintable relative to the mouse, its top
|
||||
* left will be positioned @hot_x, @hot_y pixels from the
|
||||
* mouse cursor.
|
||||
*/
|
||||
void
|
||||
gtk_drag_set_icon_paintable (GdkDrag *drag,
|
||||
GdkPaintable *paintable,
|
||||
int hot_x,
|
||||
int hot_y)
|
||||
{
|
||||
GtkWidget *widget;
|
||||
|
||||
g_return_if_fail (GDK_IS_DRAG (drag));
|
||||
g_return_if_fail (GDK_IS_PAINTABLE (paintable));
|
||||
|
||||
widget = gtk_picture_new_for_paintable (paintable);
|
||||
gtk_picture_set_can_shrink (GTK_PICTURE (widget), FALSE);
|
||||
|
||||
gtk_drag_set_icon_widget_internal (drag, widget, hot_x, hot_y, TRUE);
|
||||
}
|
||||
|
||||
/**
|
||||
* gtk_drag_set_icon_name:
|
||||
* @drag: the context for a drag
|
||||
* @icon_name: name of icon to use
|
||||
* @hot_x: the X offset of the hotspot within the icon
|
||||
* @hot_y: the Y offset of the hotspot within the icon
|
||||
*
|
||||
* Sets the icon for a given drag from a named themed icon. See
|
||||
* the docs for #GtkIconTheme for more details. Note that the
|
||||
* size of the icon depends on the icon theme (the icon is
|
||||
* loaded at the symbolic size #GTK_ICON_SIZE_DND), thus
|
||||
* @hot_x and @hot_y have to be used with care.
|
||||
*/
|
||||
void
|
||||
gtk_drag_set_icon_name (GdkDrag *drag,
|
||||
const gchar *icon_name,
|
||||
gint hot_x,
|
||||
gint hot_y)
|
||||
{
|
||||
GtkImageDefinition *def;
|
||||
|
||||
g_return_if_fail (GDK_IS_DRAG (drag));
|
||||
g_return_if_fail (icon_name != NULL && icon_name[0] != '\0');
|
||||
|
||||
def = gtk_image_definition_new_icon_name (icon_name);
|
||||
set_icon_helper (drag, def, hot_x, hot_y);
|
||||
|
||||
gtk_image_definition_unref (def);
|
||||
}
|
||||
|
||||
/**
|
||||
* gtk_drag_set_icon_gicon:
|
||||
* @drag: the context for a drag
|
||||
* @icon: a #GIcon
|
||||
* @hot_x: the X offset of the hotspot within the icon
|
||||
* @hot_y: the Y offset of the hotspot within the icon
|
||||
*
|
||||
* Sets the icon for a given drag from the given @icon.
|
||||
* See the documentation for gtk_drag_set_icon_name()
|
||||
* for more details about using icons in drag and drop.
|
||||
*/
|
||||
void
|
||||
gtk_drag_set_icon_gicon (GdkDrag *drag,
|
||||
GIcon *icon,
|
||||
gint hot_x,
|
||||
gint hot_y)
|
||||
{
|
||||
GtkImageDefinition *def;
|
||||
|
||||
g_return_if_fail (GDK_IS_DRAG (drag));
|
||||
g_return_if_fail (icon != NULL);
|
||||
|
||||
def = gtk_image_definition_new_gicon (icon);
|
||||
set_icon_helper (drag, def, hot_x, hot_y);
|
||||
|
||||
gtk_image_definition_unref (def);
|
||||
}
|
||||
|
||||
/**
|
||||
* gtk_drag_set_icon_default:
|
||||
* @drag: the context for a drag
|
||||
*
|
||||
* Sets the icon for a particular drag to the default
|
||||
* icon.
|
||||
*/
|
||||
void
|
||||
gtk_drag_set_icon_default (GdkDrag *drag)
|
||||
{
|
||||
g_return_if_fail (GDK_IS_DRAG (drag));
|
||||
|
||||
gtk_drag_set_icon_name (drag, "text-x-generic", -2, -2);
|
||||
}
|
||||
|
||||
/* Clean up from the drag, and display snapback, if necessary. */
|
||||
static void
|
||||
gtk_drag_drop_finished (GtkDragSourceInfo *info,
|
||||
GtkDragResult result)
|
||||
{
|
||||
gboolean success;
|
||||
|
||||
success = (result == GTK_DRAG_RESULT_SUCCESS);
|
||||
|
||||
if (!success)
|
||||
g_signal_emit_by_name (info->widget, "drag-failed",
|
||||
info->drag, result, &success);
|
||||
|
||||
gdk_drag_drop_done (info->drag, success);
|
||||
gtk_drag_source_info_destroy (info);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_drag_drop (GtkDragSourceInfo *info)
|
||||
{
|
||||
if (info->icon_window)
|
||||
gtk_widget_hide (info->icon_window);
|
||||
|
||||
info->drop_timeout = g_timeout_add (DROP_ABORT_TIME, gtk_drag_abort_timeout, info);
|
||||
g_source_set_name_by_id (info->drop_timeout, "[gtk] gtk_drag_abort_timeout");
|
||||
}
|
||||
|
||||
/*
|
||||
* Source side callbacks.
|
||||
*/
|
||||
static void
|
||||
gtk_drag_remove_icon (GtkDragSourceInfo *info)
|
||||
{
|
||||
if (info->icon_widget)
|
||||
{
|
||||
GtkWidget *widget;
|
||||
|
||||
widget = info->icon_widget;
|
||||
info->icon_widget = NULL;
|
||||
|
||||
g_signal_handlers_disconnect_by_func (widget, icon_widget_destroyed, info);
|
||||
|
||||
gtk_widget_hide (widget);
|
||||
gtk_widget_set_opacity (widget, 1.0);
|
||||
|
||||
if (info->destroy_icon)
|
||||
gtk_widget_destroy (widget);
|
||||
else
|
||||
gtk_drag_icon_set_widget (GTK_DRAG_ICON (info->icon_window), NULL);
|
||||
|
||||
g_object_unref (widget);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_drag_source_info_free (GtkDragSourceInfo *info)
|
||||
{
|
||||
gtk_drag_remove_icon (info);
|
||||
g_object_unref (info->icon_window);
|
||||
g_free (info);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_drag_source_info_destroy (GtkDragSourceInfo *info)
|
||||
{
|
||||
g_signal_handlers_disconnect_by_func (info->drag, gtk_drag_drop_performed_cb, info);
|
||||
g_signal_handlers_disconnect_by_func (info->drag, gtk_drag_dnd_finished_cb, info);
|
||||
g_signal_handlers_disconnect_by_func (info->drag, gtk_drag_cancel_cb, info);
|
||||
|
||||
g_signal_emit_by_name (info->widget, "drag-end", info->drag);
|
||||
|
||||
g_object_set_data (G_OBJECT (info->widget), I_("gtk-info"), NULL);
|
||||
|
||||
g_clear_object (&info->widget);
|
||||
|
||||
gdk_content_formats_unref (info->target_list);
|
||||
|
||||
if (info->drop_timeout)
|
||||
g_source_remove (info->drop_timeout);
|
||||
|
||||
/* keep the icon_window alive until the (possible) drag cancel animation is done */
|
||||
g_object_set_data_full (G_OBJECT (info->drag), "former-gtk-source-info", info, (GDestroyNotify)gtk_drag_source_info_free);
|
||||
|
||||
gtk_drag_clear_source_info (info->drag);
|
||||
g_object_unref (info->drag);
|
||||
}
|
||||
|
||||
/* Called on cancellation of a drag, either by the user
|
||||
* or programmatically.
|
||||
*/
|
||||
static void
|
||||
gtk_drag_cancel_internal (GtkDragSourceInfo *info,
|
||||
GtkDragResult result)
|
||||
{
|
||||
gtk_drag_drop_finished (info, result);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_drag_drop_performed_cb (GdkDrag *drag,
|
||||
GtkDragSourceInfo *info)
|
||||
{
|
||||
gtk_drag_drop (info);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_drag_cancel_cb (GdkDrag *drag,
|
||||
GdkDragCancelReason reason,
|
||||
GtkDragSourceInfo *info)
|
||||
{
|
||||
GtkDragResult result;
|
||||
|
||||
switch (reason)
|
||||
{
|
||||
case GDK_DRAG_CANCEL_NO_TARGET:
|
||||
result = GTK_DRAG_RESULT_NO_TARGET;
|
||||
break;
|
||||
case GDK_DRAG_CANCEL_USER_CANCELLED:
|
||||
result = GTK_DRAG_RESULT_USER_CANCELLED;
|
||||
break;
|
||||
case GDK_DRAG_CANCEL_ERROR:
|
||||
default:
|
||||
result = GTK_DRAG_RESULT_ERROR;
|
||||
break;
|
||||
}
|
||||
gtk_drag_cancel_internal (info, result);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_drag_dnd_finished_cb (GdkDrag *drag,
|
||||
GtkDragSourceInfo *info)
|
||||
{
|
||||
if (gdk_drag_get_selected_action (drag) == GDK_ACTION_MOVE)
|
||||
{
|
||||
g_signal_emit_by_name (info->widget,
|
||||
"drag-data-delete",
|
||||
drag);
|
||||
}
|
||||
|
||||
gtk_drag_source_info_destroy (info);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
gtk_drag_abort_timeout (gpointer data)
|
||||
{
|
||||
GtkDragSourceInfo *info = data;
|
||||
|
||||
info->drop_timeout = 0;
|
||||
gtk_drag_drop_finished (info, GTK_DRAG_RESULT_TIMEOUT_EXPIRED);
|
||||
|
||||
return G_SOURCE_REMOVE;
|
||||
}
|
||||
|
||||
/**
|
||||
* gtk_drag_check_threshold: (method)
|
||||
* @widget: a #GtkWidget
|
||||
* @start_x: X coordinate of start of drag
|
||||
* @start_y: Y coordinate of start of drag
|
||||
* @current_x: current X coordinate
|
||||
* @current_y: current Y coordinate
|
||||
*
|
||||
* Checks to see if a mouse drag starting at (@start_x, @start_y) and ending
|
||||
* at (@current_x, @current_y) has passed the GTK+ drag threshold, and thus
|
||||
* should trigger the beginning of a drag-and-drop operation.
|
||||
*
|
||||
* Returns: %TRUE if the drag threshold has been passed.
|
||||
*/
|
||||
gboolean
|
||||
gtk_drag_check_threshold (GtkWidget *widget,
|
||||
gint start_x,
|
||||
gint start_y,
|
||||
gint current_x,
|
||||
gint current_y)
|
||||
{
|
||||
gint drag_threshold;
|
||||
|
||||
g_return_val_if_fail (GTK_IS_WIDGET (widget), FALSE);
|
||||
|
||||
drag_threshold = gtk_settings_get_dnd_drag_threshold (gtk_widget_get_settings (widget));
|
||||
|
||||
return (ABS (current_x - start_x) > drag_threshold ||
|
||||
ABS (current_y - start_y) > drag_threshold);
|
||||
}
|
||||
|
||||
/**
|
||||
* gtk_drag_cancel:
|
||||
* @drag: a drag context, as e.g. returned by gtk_drag_begin()
|
||||
*
|
||||
* Cancels an ongoing drag operation on the source side.
|
||||
*
|
||||
* If you want to be able to cancel a drag operation in this way,
|
||||
* you need to keep a pointer to the drag context, either from an
|
||||
* explicit call to gtk_drag_begin(), or by connecting to
|
||||
* #GtkWidget::drag-begin.
|
||||
*
|
||||
* If @context does not refer to an ongoing drag operation, this
|
||||
* function does nothing.
|
||||
*
|
||||
* If a drag is cancelled in this way, the @result argument of
|
||||
* #GtkWidget::drag-failed is set to @GTK_DRAG_RESULT_ERROR.
|
||||
*/
|
||||
void
|
||||
gtk_drag_cancel (GdkDrag *drag)
|
||||
{
|
||||
GtkDragSourceInfo *info;
|
||||
|
||||
g_return_if_fail (GDK_IS_DRAG (drag));
|
||||
|
||||
info = gtk_drag_get_source_info (drag, FALSE);
|
||||
if (info != NULL)
|
||||
gtk_drag_cancel_internal (info, GTK_DRAG_RESULT_ERROR);
|
||||
}
|
||||
|
||||
@@ -44,58 +44,11 @@ void gtk_drag_get_data (GtkWidget *widget,
|
||||
GdkDrop *drop,
|
||||
GdkAtom target);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
GtkWidget *gtk_drag_get_source_widget (GdkDrag *drag);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_highlight (GtkWidget *widget);
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_unhighlight (GtkWidget *widget);
|
||||
|
||||
/* Source side */
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
GdkDrag *gtk_drag_begin (GtkWidget *widget,
|
||||
GdkDevice *device,
|
||||
GdkContentFormats *targets,
|
||||
GdkDragAction actions,
|
||||
gint x,
|
||||
gint y);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_cancel (GdkDrag *drag);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_set_icon_widget (GdkDrag *drag,
|
||||
GtkWidget *widget,
|
||||
gint hot_x,
|
||||
gint hot_y);
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_set_icon_paintable (GdkDrag *drag,
|
||||
GdkPaintable *paintable,
|
||||
int hot_x,
|
||||
int hot_y);
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_set_icon_name (GdkDrag *drag,
|
||||
const gchar *icon_name,
|
||||
gint hot_x,
|
||||
gint hot_y);
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_set_icon_gicon (GdkDrag *drag,
|
||||
GIcon *icon,
|
||||
gint hot_x,
|
||||
gint hot_y);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_set_icon_default (GdkDrag *drag);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
gboolean gtk_drag_check_threshold (GtkWidget *widget,
|
||||
gint start_x,
|
||||
gint start_y,
|
||||
gint current_x,
|
||||
gint current_y);
|
||||
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
|
||||
+722
-297
File diff suppressed because it is too large
Load Diff
+59
-22
@@ -37,36 +37,73 @@
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_source_set (GtkWidget *widget,
|
||||
GdkModifierType start_button_mask,
|
||||
GdkContentFormats *targets,
|
||||
GdkDragAction actions);
|
||||
#define GTK_TYPE_DRAG_SOURCE (gtk_drag_source_get_type ())
|
||||
#define GTK_DRAG_SOURCE(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), GTK_TYPE_DRAG_SOURCE, GtkDragSource))
|
||||
#define GTK_DRAG_SOURCE_CLASS(k) (G_TYPE_CHECK_CLASS_CAST ((k), GTK_TYPE_DRAG_SOURCE, GtkDragSourceClass))
|
||||
#define GTK_IS_DRAG_SOURCE(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), GTK_TYPE_DRAG_SOURCE))
|
||||
#define GTK_IS_DRAG_SOURCE_CLASS(k) (G_TYPE_CHECK_CLASS_TYPE ((k), GTK_TYPE_DRAG_SOURCE))
|
||||
#define GTK_DRAG_SOURCE_GET_CLASS(o) (G_TYPE_INSTANCE_GET_CLASS ((o), GTK_TYPE_DRAG_SOURCE, GtkDragSourceClass))
|
||||
|
||||
typedef struct _GtkDragSource GtkDragSource;
|
||||
typedef struct _GtkDragSourceClass GtkDragSourceClass;
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_source_unset (GtkWidget *widget);
|
||||
GType gtk_drag_source_get_type (void) G_GNUC_CONST;
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
GdkContentFormats * gtk_drag_source_get_target_list (GtkWidget *widget);
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_source_set_target_list (GtkWidget *widget,
|
||||
GdkContentFormats *target_list);
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_source_add_text_targets (GtkWidget *widget);
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_source_add_image_targets (GtkWidget *widget);
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_source_add_uri_targets (GtkWidget *widget);
|
||||
GtkDragSource *gtk_drag_source_new (GdkContentProvider *content,
|
||||
GdkDragAction actions);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_source_set_icon_name (GtkWidget *widget,
|
||||
const gchar *icon_name);
|
||||
void gtk_drag_source_set_content (GtkDragSource *source,
|
||||
GdkContentProvider *content);
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_source_set_icon_gicon (GtkWidget *widget,
|
||||
GIcon *icon);
|
||||
GdkContentProvider *gtk_drag_source_get_content (GtkDragSource *source);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_source_set_icon_paintable (GtkWidget *widget,
|
||||
GdkPaintable *paintable);
|
||||
void gtk_drag_source_set_actions (GtkDragSource *source,
|
||||
GdkDragAction actions);
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
GdkDragAction gtk_drag_source_get_actions (GtkDragSource *source);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_source_set_icon (GtkDragSource *source,
|
||||
GdkPaintable *paintable,
|
||||
int hot_x,
|
||||
int hot_y);
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_source_drag_begin (GtkDragSource *source,
|
||||
GtkWidget *widget,
|
||||
GdkDevice *device,
|
||||
int x,
|
||||
int y);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_source_drag_cancel (GtkDragSource *sourcei);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
GtkDragSource * gtk_drag_get_source (GdkDrag *drag);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
GtkWidget * gtk_drag_source_get_origin (GtkDragSource *source);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
GdkDrag * gtk_drag_source_get_drag (GtkDragSource *source);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_source_attach (GtkDragSource *source,
|
||||
GtkWidget *widget,
|
||||
GdkModifierType start_button_mask);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_drag_source_detach (GtkDragSource *source);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
gboolean gtk_drag_check_threshold (GtkWidget *widget,
|
||||
int start_x,
|
||||
int start_y,
|
||||
int current_x,
|
||||
int current_y);
|
||||
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
+19
-19
@@ -70,6 +70,8 @@
|
||||
#include "gtkwindow.h"
|
||||
#include "gtknative.h"
|
||||
#include "gtkgestureclick.h"
|
||||
#include "gtkdragsource.h"
|
||||
#include "gtkwidgetpaintable.h"
|
||||
|
||||
#include "a11y/gtkentryaccessible.h"
|
||||
|
||||
@@ -172,7 +174,7 @@ struct _EntryIconInfo
|
||||
guint in_drag : 1;
|
||||
|
||||
GdkDragAction actions;
|
||||
GdkContentFormats *target_list;
|
||||
GdkContentProvider *content;
|
||||
};
|
||||
|
||||
enum {
|
||||
@@ -1320,8 +1322,7 @@ gtk_entry_finalize (GObject *object)
|
||||
if (icon_info == NULL)
|
||||
continue;
|
||||
|
||||
if (icon_info->target_list != NULL)
|
||||
gdk_content_formats_unref (icon_info->target_list);
|
||||
g_clear_object (&icon_info->content);
|
||||
|
||||
gtk_widget_unparent (icon_info->widget);
|
||||
|
||||
@@ -1462,17 +1463,21 @@ icon_drag_update_cb (GtkGestureDrag *gesture,
|
||||
pos = get_icon_position_from_controller (entry, GTK_EVENT_CONTROLLER (gesture));
|
||||
icon_info = priv->icons[pos];
|
||||
|
||||
if (icon_info->target_list != NULL &&
|
||||
gtk_drag_check_threshold (icon_info->widget,
|
||||
start_x, start_y,
|
||||
x, y))
|
||||
if (icon_info->content != NULL &&
|
||||
gtk_drag_check_threshold (icon_info->widget, start_x, start_y, x, y))
|
||||
{
|
||||
GtkDragSource *source;
|
||||
GdkPaintable *paintable;
|
||||
GdkDevice *device;
|
||||
|
||||
icon_info->in_drag = TRUE;
|
||||
gtk_drag_begin (GTK_WIDGET (entry),
|
||||
gtk_gesture_get_device (GTK_GESTURE (gesture)),
|
||||
icon_info->target_list,
|
||||
icon_info->actions,
|
||||
start_x, start_y);
|
||||
source = gtk_drag_source_new (icon_info->content, icon_info->actions);
|
||||
paintable = gtk_widget_paintable_new (icon_info->widget);
|
||||
gtk_drag_source_set_icon (source, paintable, -2, -2);
|
||||
g_object_unref (paintable);
|
||||
device = gtk_gesture_get_device (GTK_GESTURE (gesture));
|
||||
gtk_drag_source_drag_begin (source, GTK_WIDGET (entry), device, start_x, start_y);
|
||||
g_object_unref (source);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2742,7 +2747,7 @@ gtk_entry_get_icon_at_pos (GtkEntry *entry,
|
||||
void
|
||||
gtk_entry_set_icon_drag_source (GtkEntry *entry,
|
||||
GtkEntryIconPosition icon_pos,
|
||||
GdkContentFormats *formats,
|
||||
GdkContentProvider *provider,
|
||||
GdkDragAction actions)
|
||||
{
|
||||
GtkEntryPrivate *priv = gtk_entry_get_instance_private (entry);
|
||||
@@ -2754,12 +2759,7 @@ gtk_entry_set_icon_drag_source (GtkEntry *entry,
|
||||
if ((icon_info = priv->icons[icon_pos]) == NULL)
|
||||
icon_info = construct_icon_info (GTK_WIDGET (entry), icon_pos);
|
||||
|
||||
if (icon_info->target_list)
|
||||
gdk_content_formats_unref (icon_info->target_list);
|
||||
icon_info->target_list = formats;
|
||||
if (icon_info->target_list)
|
||||
gdk_content_formats_ref (icon_info->target_list);
|
||||
|
||||
g_set_object (&icon_info->content, provider);
|
||||
icon_info->actions = actions;
|
||||
}
|
||||
|
||||
|
||||
+1
-1
@@ -266,7 +266,7 @@ gchar * gtk_entry_get_icon_tooltip_markup (GtkEntry *
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_entry_set_icon_drag_source (GtkEntry *entry,
|
||||
GtkEntryIconPosition icon_pos,
|
||||
GdkContentFormats *formats,
|
||||
GdkContentProvider *content,
|
||||
GdkDragAction actions);
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
gint gtk_entry_get_current_icon_drag_source (GtkEntry *entry);
|
||||
|
||||
+19
-18
@@ -1995,7 +1995,7 @@ file_list_drag_data_received_cb (GtkWidget *widget,
|
||||
|
||||
/* Allow only drags from other widgets; see bug #533891. */
|
||||
if (gdk_drop_get_drag (drop) &&
|
||||
gtk_drag_get_source_widget (gdk_drop_get_drag (drop)) == widget)
|
||||
gtk_drag_source_get_origin (gtk_drag_get_source (gdk_drop_get_drag (drop))) == widget)
|
||||
{
|
||||
g_signal_stop_emission_by_name (widget, "drag-data-received");
|
||||
return;
|
||||
@@ -2042,15 +2042,13 @@ file_list_drag_drop_cb (GtkWidget *widget,
|
||||
}
|
||||
|
||||
static void
|
||||
file_list_drag_begin_cb (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
file_list_drag_begin_cb (GtkDragSource *source,
|
||||
GtkFileChooserWidget *impl)
|
||||
{
|
||||
GtkFileChooserWidgetPrivate *priv = gtk_file_chooser_widget_get_instance_private (impl);
|
||||
GdkDrag *drag = gtk_drag_source_get_drag (source);
|
||||
|
||||
gtk_places_sidebar_set_drop_targets_visible (GTK_PLACES_SIDEBAR (priv->places_sidebar),
|
||||
TRUE,
|
||||
drag);
|
||||
gtk_places_sidebar_set_drop_targets_visible (GTK_PLACES_SIDEBAR (priv->places_sidebar), TRUE, drag);
|
||||
}
|
||||
|
||||
/* Disable the normal tree drag motion handler, it makes it look like you're
|
||||
@@ -2067,16 +2065,13 @@ file_list_drag_motion_cb (GtkWidget *widget,
|
||||
}
|
||||
|
||||
static void
|
||||
file_list_drag_end_cb (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer user_data)
|
||||
file_list_drag_end_cb (GtkDragSource *source,
|
||||
GtkFileChooserWidget *impl)
|
||||
{
|
||||
GtkFileChooserWidget *impl = GTK_FILE_CHOOSER_WIDGET (user_data);
|
||||
GtkFileChooserWidgetPrivate *priv = gtk_file_chooser_widget_get_instance_private (impl);
|
||||
GdkDrag *drag = gtk_drag_source_get_drag (source);
|
||||
|
||||
gtk_places_sidebar_set_drop_targets_visible (GTK_PLACES_SIDEBAR (priv->places_sidebar),
|
||||
FALSE,
|
||||
drag);
|
||||
gtk_places_sidebar_set_drop_targets_visible (GTK_PLACES_SIDEBAR (priv->places_sidebar), FALSE, drag);
|
||||
}
|
||||
|
||||
/* Sensitizes the "Copy file’s location" and other context menu items if there is actually
|
||||
@@ -8510,17 +8505,23 @@ post_process_ui (GtkFileChooserWidget *impl)
|
||||
GtkCellRenderer *cell;
|
||||
GList *cells;
|
||||
GFile *file;
|
||||
GtkDragSource *source;
|
||||
GdkContentFormats *formats;
|
||||
|
||||
/* Setup file list treeview */
|
||||
selection = gtk_tree_view_get_selection (GTK_TREE_VIEW (priv->browse_files_tree_view));
|
||||
gtk_tree_selection_set_select_function (selection,
|
||||
list_select_func,
|
||||
impl, NULL);
|
||||
gtk_tree_view_enable_model_drag_source (GTK_TREE_VIEW (priv->browse_files_tree_view),
|
||||
GDK_BUTTON1_MASK,
|
||||
NULL,
|
||||
GDK_ACTION_COPY | GDK_ACTION_MOVE);
|
||||
gtk_drag_source_add_uri_targets (priv->browse_files_tree_view);
|
||||
formats = gdk_content_formats_new (NULL, 0);
|
||||
formats = gtk_content_formats_add_uri_targets (formats);
|
||||
source = gtk_tree_view_enable_model_drag_source (GTK_TREE_VIEW (priv->browse_files_tree_view),
|
||||
GDK_BUTTON1_MASK,
|
||||
formats,
|
||||
GDK_ACTION_COPY | GDK_ACTION_MOVE);
|
||||
gdk_content_formats_unref (formats);
|
||||
g_signal_connect (source, "drag-begin", G_CALLBACK (file_list_drag_begin_cb), impl);
|
||||
g_signal_connect (source, "drag-end", G_CALLBACK (file_list_drag_end_cb), impl);
|
||||
|
||||
gtk_drag_dest_set (priv->browse_files_tree_view,
|
||||
GTK_DEST_DEFAULT_ALL,
|
||||
|
||||
@@ -37,7 +37,7 @@
|
||||
#include "gtkgesturelongpressprivate.h"
|
||||
#include "gtkgestureprivate.h"
|
||||
#include "gtkmarshalers.h"
|
||||
#include "gtkdnd.h"
|
||||
#include "gtkdragsource.h"
|
||||
#include "gtkprivate.h"
|
||||
#include "gtkintl.h"
|
||||
#include "gtkmarshalers.h"
|
||||
|
||||
+67
-68
@@ -48,6 +48,8 @@
|
||||
#include "gtkwidgetprivate.h"
|
||||
#include "gtkwindow.h"
|
||||
#include "gtkeventcontrollerkey.h"
|
||||
#include "gtkdragsource.h"
|
||||
#include "gtkselectionprivate.h"
|
||||
|
||||
#include "a11y/gtkiconviewaccessibleprivate.h"
|
||||
|
||||
@@ -279,15 +281,12 @@ static void update_text_cell (GtkIco
|
||||
static void update_pixbuf_cell (GtkIconView *icon_view);
|
||||
|
||||
/* Source side drag signals */
|
||||
static void gtk_icon_view_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
static void gtk_icon_view_drag_end (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
static void gtk_icon_view_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data);
|
||||
static void gtk_icon_view_drag_data_delete (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
static void gtk_icon_view_drag_begin (GtkDragSource *source,
|
||||
GtkWidget *widget);
|
||||
static GBytes * gtk_icon_view_drag_data_get (const char *mime_type,
|
||||
gpointer data);
|
||||
static void gtk_icon_view_drag_data_delete (GtkDragSource *source,
|
||||
GtkWidget *widget);
|
||||
|
||||
/* Target side drag signals */
|
||||
static void gtk_icon_view_drag_leave (GtkWidget *widget,
|
||||
@@ -360,10 +359,6 @@ gtk_icon_view_class_init (GtkIconViewClass *klass)
|
||||
widget_class->measure = gtk_icon_view_measure;
|
||||
widget_class->size_allocate = gtk_icon_view_size_allocate;
|
||||
widget_class->snapshot = gtk_icon_view_snapshot;
|
||||
widget_class->drag_begin = gtk_icon_view_drag_begin;
|
||||
widget_class->drag_end = gtk_icon_view_drag_end;
|
||||
widget_class->drag_data_get = gtk_icon_view_drag_data_get;
|
||||
widget_class->drag_data_delete = gtk_icon_view_drag_data_delete;
|
||||
widget_class->drag_leave = gtk_icon_view_drag_leave;
|
||||
widget_class->drag_motion = gtk_icon_view_drag_motion;
|
||||
widget_class->drag_drop = gtk_icon_view_drag_drop;
|
||||
@@ -5713,27 +5708,27 @@ unset_reorderable (GtkIconView *icon_view)
|
||||
}
|
||||
|
||||
static void
|
||||
set_source_row (GdkDrag *drag,
|
||||
set_source_row (GtkDragSource *source,
|
||||
GtkTreeModel *model,
|
||||
GtkTreePath *source_row)
|
||||
{
|
||||
if (source_row)
|
||||
g_object_set_data_full (G_OBJECT (drag),
|
||||
g_object_set_data_full (G_OBJECT (source),
|
||||
I_("gtk-icon-view-source-row"),
|
||||
gtk_tree_row_reference_new (model, source_row),
|
||||
(GDestroyNotify) gtk_tree_row_reference_free);
|
||||
else
|
||||
g_object_set_data_full (G_OBJECT (drag),
|
||||
g_object_set_data_full (G_OBJECT (source),
|
||||
I_("gtk-icon-view-source-row"),
|
||||
NULL, NULL);
|
||||
}
|
||||
|
||||
static GtkTreePath*
|
||||
get_source_row (GdkDrag *drag)
|
||||
get_source_row (GtkDragSource *source)
|
||||
{
|
||||
GtkTreeRowReference *ref;
|
||||
|
||||
ref = g_object_get_data (G_OBJECT (drag), "gtk-icon-view-source-row");
|
||||
ref = g_object_get_data (G_OBJECT (source), "gtk-icon-view-source-row");
|
||||
|
||||
if (ref)
|
||||
return gtk_tree_row_reference_get_path (ref);
|
||||
@@ -6031,7 +6026,6 @@ gtk_icon_view_maybe_begin_drag (GtkIconView *icon_view,
|
||||
GdkDevice *device)
|
||||
{
|
||||
GtkWidget *widget = GTK_WIDGET (icon_view);
|
||||
GdkDrag *drag;
|
||||
GtkTreePath *path = NULL;
|
||||
GtkTreeModel *model;
|
||||
gboolean retval = FALSE;
|
||||
@@ -6063,8 +6057,7 @@ gtk_icon_view_maybe_begin_drag (GtkIconView *icon_view,
|
||||
goto out;
|
||||
|
||||
if (!GTK_IS_TREE_DRAG_SOURCE (model) ||
|
||||
!gtk_tree_drag_source_row_draggable (GTK_TREE_DRAG_SOURCE (model),
|
||||
path))
|
||||
!gtk_tree_drag_source_row_draggable (GTK_TREE_DRAG_SOURCE (model), path))
|
||||
goto out;
|
||||
|
||||
/* FIXME Check whether we're a start button, if not return FALSE and
|
||||
@@ -6075,14 +6068,13 @@ gtk_icon_view_maybe_begin_drag (GtkIconView *icon_view,
|
||||
|
||||
retval = TRUE;
|
||||
|
||||
drag = gtk_drag_begin (widget,
|
||||
device,
|
||||
gtk_drag_source_get_target_list (widget),
|
||||
icon_view->priv->source_actions,
|
||||
icon_view->priv->press_start_x,
|
||||
icon_view->priv->press_start_y);
|
||||
gtk_drag_source_drag_begin (icon_view->priv->source,
|
||||
widget,
|
||||
device,
|
||||
icon_view->priv->press_start_x,
|
||||
icon_view->priv->press_start_y);
|
||||
|
||||
set_source_row (drag, model, path);
|
||||
set_source_row (icon_view->priv->source, model, path);
|
||||
|
||||
out:
|
||||
if (path)
|
||||
@@ -6093,8 +6085,8 @@ gtk_icon_view_maybe_begin_drag (GtkIconView *icon_view,
|
||||
|
||||
/* Source side drag signals */
|
||||
static void
|
||||
gtk_icon_view_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag)
|
||||
gtk_icon_view_drag_begin (GtkDragSource *source,
|
||||
GtkWidget *widget)
|
||||
{
|
||||
GtkIconView *icon_view;
|
||||
GtkIconViewItem *item;
|
||||
@@ -6123,40 +6115,34 @@ gtk_icon_view_drag_begin (GtkWidget *widget,
|
||||
icon = gtk_icon_view_create_drag_icon (icon_view, path);
|
||||
gtk_tree_path_free (path);
|
||||
|
||||
gtk_drag_set_icon_paintable (drag, icon, x, y);
|
||||
gtk_drag_source_set_icon (source, icon, x, y);
|
||||
|
||||
g_object_unref (icon);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_icon_view_drag_end (GtkWidget *widget,
|
||||
GdkDrag *drag)
|
||||
static GBytes *
|
||||
gtk_icon_view_drag_data_get (const char *mime_type,
|
||||
gpointer data)
|
||||
{
|
||||
/* do nothing */
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_icon_view_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data)
|
||||
{
|
||||
GtkIconView *icon_view;
|
||||
GtkIconView *icon_view = data;
|
||||
GtkTreeModel *model;
|
||||
GtkTreePath *source_row;
|
||||
GtkSelectionData sdata = { 0, };
|
||||
|
||||
sdata.target = g_intern_string (mime_type);
|
||||
|
||||
icon_view = GTK_ICON_VIEW (widget);
|
||||
model = gtk_icon_view_get_model (icon_view);
|
||||
|
||||
if (model == NULL)
|
||||
return;
|
||||
return NULL;
|
||||
|
||||
if (!icon_view->priv->source_set)
|
||||
return;
|
||||
return NULL;
|
||||
|
||||
source_row = get_source_row (drag);
|
||||
source_row = get_source_row (icon_view->priv->source);
|
||||
|
||||
if (source_row == NULL)
|
||||
return;
|
||||
return NULL;
|
||||
|
||||
/* We can implement the GTK_TREE_MODEL_ROW target generically for
|
||||
* any model; for DragSource models there are some other formats
|
||||
@@ -6164,24 +6150,23 @@ gtk_icon_view_drag_data_get (GtkWidget *widget,
|
||||
*/
|
||||
|
||||
if (GTK_IS_TREE_DRAG_SOURCE (model) &&
|
||||
gtk_tree_drag_source_drag_data_get (GTK_TREE_DRAG_SOURCE (model),
|
||||
source_row,
|
||||
selection_data))
|
||||
gtk_tree_drag_source_drag_data_get (GTK_TREE_DRAG_SOURCE (model), source_row, &sdata))
|
||||
goto done;
|
||||
|
||||
/* If drag_data_get does nothing, try providing row data. */
|
||||
if (gtk_selection_data_get_target (selection_data) == g_intern_static_string ("GTK_TREE_MODEL_ROW"))
|
||||
gtk_tree_set_row_drag_data (selection_data,
|
||||
model,
|
||||
source_row);
|
||||
if (gtk_selection_data_get_target (&sdata) == g_intern_static_string ("GTK_TREE_MODEL_ROW"))
|
||||
gtk_tree_set_row_drag_data (&sdata, model, source_row);
|
||||
|
||||
done:
|
||||
gtk_tree_path_free (source_row);
|
||||
|
||||
return g_bytes_new_take ((gpointer)gtk_selection_data_get_data (&sdata),
|
||||
gtk_selection_data_get_length (&sdata));
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_icon_view_drag_data_delete (GtkWidget *widget,
|
||||
GdkDrag *drag)
|
||||
gtk_icon_view_drag_data_delete (GtkDragSource *source,
|
||||
GtkWidget *widget)
|
||||
{
|
||||
GtkTreeModel *model;
|
||||
GtkIconView *icon_view;
|
||||
@@ -6196,17 +6181,16 @@ gtk_icon_view_drag_data_delete (GtkWidget *widget,
|
||||
if (!icon_view->priv->source_set)
|
||||
return;
|
||||
|
||||
source_row = get_source_row (drag);
|
||||
source_row = get_source_row (source);
|
||||
|
||||
if (source_row == NULL)
|
||||
return;
|
||||
|
||||
gtk_tree_drag_source_drag_data_delete (GTK_TREE_DRAG_SOURCE (model),
|
||||
source_row);
|
||||
gtk_tree_drag_source_drag_data_delete (GTK_TREE_DRAG_SOURCE (model), source_row);
|
||||
|
||||
gtk_tree_path_free (source_row);
|
||||
|
||||
set_source_row (drag, NULL, NULL);
|
||||
set_source_row (source, NULL, NULL);
|
||||
}
|
||||
|
||||
/* Target side drag signals */
|
||||
@@ -6341,16 +6325,17 @@ gtk_icon_view_drag_drop (GtkWidget *widget,
|
||||
}
|
||||
|
||||
static GdkDragAction
|
||||
gtk_icon_view_get_action (GtkWidget *treeview,
|
||||
gtk_icon_view_get_action (GtkWidget *widget,
|
||||
GdkDrop *drop)
|
||||
{
|
||||
GtkIconView *iconview = GTK_ICON_VIEW (widget);
|
||||
GdkDrag *drag = gdk_drop_get_drag (drop);
|
||||
GtkWidget *source_widget = gtk_drag_get_source_widget (drag);
|
||||
GtkDragSource *source = drag ? gtk_drag_get_source (drag) : NULL;
|
||||
GdkDragAction actions;
|
||||
|
||||
actions = gdk_drop_get_actions (drop);
|
||||
|
||||
if (source_widget == treeview &&
|
||||
if (source == iconview->priv->source &&
|
||||
actions & GDK_ACTION_MOVE)
|
||||
return GDK_ACTION_MOVE;
|
||||
|
||||
@@ -6448,6 +6433,7 @@ gtk_icon_view_drag_data_received (GtkWidget *widget,
|
||||
}
|
||||
|
||||
/* Drag-and-Drop support */
|
||||
|
||||
/**
|
||||
* gtk_icon_view_enable_model_drag_source:
|
||||
* @icon_view: a #GtkIconView
|
||||
@@ -6458,16 +6444,27 @@ gtk_icon_view_drag_data_received (GtkWidget *widget,
|
||||
*
|
||||
* Turns @icon_view into a drag source for automatic DND. Calling this
|
||||
* method sets #GtkIconView:reorderable to %FALSE.
|
||||
*
|
||||
* Returns: (transfer none): the #GtkDragSource that has been attached to @icon_view
|
||||
**/
|
||||
void
|
||||
GtkDragSource *
|
||||
gtk_icon_view_enable_model_drag_source (GtkIconView *icon_view,
|
||||
GdkModifierType start_button_mask,
|
||||
GdkContentFormats *formats,
|
||||
GdkDragAction actions)
|
||||
{
|
||||
g_return_if_fail (GTK_IS_ICON_VIEW (icon_view));
|
||||
GdkContentProvider *content;
|
||||
|
||||
gtk_drag_source_set (GTK_WIDGET (icon_view), 0, formats, actions);
|
||||
g_return_val_if_fail (GTK_IS_ICON_VIEW (icon_view), NULL);
|
||||
|
||||
content = gdk_content_provider_new_with_formats (formats, gtk_icon_view_drag_data_get, icon_view);
|
||||
icon_view->priv->source = gtk_drag_source_new (content, actions);
|
||||
g_object_unref (content);
|
||||
|
||||
g_signal_connect (icon_view->priv->source, "drag-begin",
|
||||
G_CALLBACK (gtk_icon_view_drag_begin), icon_view);
|
||||
g_signal_connect (icon_view->priv->source, "drag-data-delete",
|
||||
G_CALLBACK (gtk_icon_view_drag_data_delete), icon_view);
|
||||
|
||||
icon_view->priv->start_button_mask = start_button_mask;
|
||||
icon_view->priv->source_actions = actions;
|
||||
@@ -6475,6 +6472,8 @@ gtk_icon_view_enable_model_drag_source (GtkIconView *icon_view,
|
||||
icon_view->priv->source_set = TRUE;
|
||||
|
||||
unset_reorderable (icon_view);
|
||||
|
||||
return icon_view->priv->source;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -6517,7 +6516,7 @@ gtk_icon_view_unset_model_drag_source (GtkIconView *icon_view)
|
||||
|
||||
if (icon_view->priv->source_set)
|
||||
{
|
||||
gtk_drag_source_unset (GTK_WIDGET (icon_view));
|
||||
g_clear_object (&icon_view->priv->source);
|
||||
icon_view->priv->source_set = FALSE;
|
||||
}
|
||||
|
||||
|
||||
+2
-1
@@ -28,6 +28,7 @@
|
||||
#include <gtk/gtkcellarea.h>
|
||||
#include <gtk/gtkselection.h>
|
||||
#include <gtk/gtktooltip.h>
|
||||
#include <gtk/gtkdragsource.h>
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
@@ -213,7 +214,7 @@ void gtk_icon_view_scroll_to_path (GtkIconView *icon_
|
||||
|
||||
/* Drag-and-Drop support */
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_icon_view_enable_model_drag_source (GtkIconView *icon_view,
|
||||
GtkDragSource * gtk_icon_view_enable_model_drag_source (GtkIconView *icon_view,
|
||||
GdkModifierType start_button_mask,
|
||||
GdkContentFormats *formats,
|
||||
GdkDragAction actions);
|
||||
|
||||
@@ -19,6 +19,7 @@
|
||||
#include "gtk/gtkcssnodeprivate.h"
|
||||
#include "gtk/gtkgestureclick.h"
|
||||
#include "gtk/gtkeventcontrollermotion.h"
|
||||
#include "gtk/gtkdragsource.h"
|
||||
|
||||
#ifndef __GTK_ICON_VIEW_PRIVATE_H__
|
||||
#define __GTK_ICON_VIEW_PRIVATE_H__
|
||||
@@ -132,6 +133,8 @@ struct _GtkIconViewPrivate
|
||||
gint press_start_x;
|
||||
gint press_start_y;
|
||||
|
||||
GtkDragSource *source;
|
||||
|
||||
GdkDragAction source_actions;
|
||||
GdkDragAction dest_actions;
|
||||
|
||||
|
||||
+16
-82
@@ -54,6 +54,7 @@
|
||||
#include "gtkwindow.h"
|
||||
#include "gtkpopovermenu.h"
|
||||
#include "gtknative.h"
|
||||
#include "gtkdragsource.h"
|
||||
|
||||
#include "a11y/gtklabelaccessibleprivate.h"
|
||||
|
||||
@@ -501,9 +502,6 @@ static gboolean gtk_label_mnemonic_activate (GtkWidget *widget,
|
||||
static void gtk_label_setup_mnemonic (GtkLabel *label,
|
||||
GtkWidget *toplevel,
|
||||
guint last_key);
|
||||
static void gtk_label_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data);
|
||||
|
||||
static void gtk_label_buildable_interface_init (GtkBuildableIface *iface);
|
||||
static gboolean gtk_label_buildable_custom_tag_start (GtkBuildable *buildable,
|
||||
@@ -652,7 +650,6 @@ gtk_label_class_init (GtkLabelClass *class)
|
||||
widget_class->unroot = gtk_label_unroot;
|
||||
widget_class->mnemonic_activate = gtk_label_mnemonic_activate;
|
||||
widget_class->popup_menu = gtk_label_popup_menu;
|
||||
widget_class->drag_data_get = gtk_label_drag_data_get;
|
||||
widget_class->grab_focus = gtk_label_grab_focus;
|
||||
widget_class->focus = gtk_label_focus;
|
||||
widget_class->get_request_mode = gtk_label_get_request_mode;
|
||||
@@ -4597,16 +4594,10 @@ connect_mnemonics_visible_notify (GtkLabel *label)
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
drag_begin_cb (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer data)
|
||||
static GdkPaintable *
|
||||
get_selection_paintable (GtkLabel *label)
|
||||
{
|
||||
GtkLabel *label = GTK_LABEL (widget);
|
||||
GtkLabelPrivate *priv = gtk_label_get_instance_private (label);
|
||||
GdkPaintable *paintable = NULL;
|
||||
|
||||
g_signal_handlers_disconnect_by_func (widget, drag_begin_cb, NULL);
|
||||
|
||||
if ((priv->select_info->selection_anchor !=
|
||||
priv->select_info->selection_end) &&
|
||||
@@ -4628,20 +4619,10 @@ drag_begin_cb (GtkWidget *widget,
|
||||
if (start > len)
|
||||
start = len;
|
||||
|
||||
paintable = gtk_text_util_create_drag_icon (widget,
|
||||
priv->text + start,
|
||||
end - start);
|
||||
return gtk_text_util_create_drag_icon (GTK_WIDGET (label), priv->text + start, end - start);
|
||||
}
|
||||
|
||||
if (paintable)
|
||||
{
|
||||
gtk_drag_set_icon_paintable (drag, paintable, 0, 0);
|
||||
g_object_unref (paintable);
|
||||
}
|
||||
else
|
||||
{
|
||||
gtk_drag_set_icon_default (drag);
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -4734,27 +4715,21 @@ gtk_label_drag_gesture_update (GtkGestureDrag *gesture,
|
||||
|
||||
if (info->in_drag)
|
||||
{
|
||||
if (gtk_drag_check_threshold (widget,
|
||||
info->drag_start_x,
|
||||
info->drag_start_y,
|
||||
x, y))
|
||||
if (gtk_drag_check_threshold (widget, info->drag_start_x, info->drag_start_y, x, y))
|
||||
{
|
||||
GdkContentFormats *target_list = gdk_content_formats_new (NULL, 0);
|
||||
GtkDragSource *source;
|
||||
GdkPaintable *paintable;
|
||||
GdkDevice *device;
|
||||
|
||||
target_list = gtk_content_formats_add_text_targets (target_list);
|
||||
|
||||
g_signal_connect (widget, "drag-begin",
|
||||
G_CALLBACK (drag_begin_cb), NULL);
|
||||
gtk_drag_begin (widget,
|
||||
gtk_gesture_get_device (GTK_GESTURE (gesture)),
|
||||
target_list,
|
||||
GDK_ACTION_COPY,
|
||||
info->drag_start_x,
|
||||
info->drag_start_y);
|
||||
source = gtk_drag_source_new (info->provider, GDK_ACTION_COPY);
|
||||
paintable = get_selection_paintable (label);
|
||||
gtk_drag_source_set_icon (source, paintable, 9, 0);
|
||||
g_clear_object (&paintable);
|
||||
device = gtk_gesture_get_device (GTK_GESTURE (gesture));
|
||||
gtk_drag_source_drag_begin (source, widget, device, info->drag_start_x, info->drag_start_y);
|
||||
g_object_unref (source);
|
||||
|
||||
info->in_drag = FALSE;
|
||||
|
||||
gdk_content_formats_unref (target_list);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -5140,47 +5115,6 @@ gtk_label_get_selectable (GtkLabel *label)
|
||||
return priv->select_info && priv->select_info->selectable;
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_label_set_selection_text (GtkLabel *label,
|
||||
GtkSelectionData *selection_data)
|
||||
{
|
||||
GtkLabelPrivate *priv = gtk_label_get_instance_private (label);
|
||||
|
||||
if (priv->select_info &&
|
||||
(priv->select_info->selection_anchor !=
|
||||
priv->select_info->selection_end) &&
|
||||
priv->text)
|
||||
{
|
||||
gint start, end;
|
||||
gint len;
|
||||
|
||||
start = MIN (priv->select_info->selection_anchor,
|
||||
priv->select_info->selection_end);
|
||||
end = MAX (priv->select_info->selection_anchor,
|
||||
priv->select_info->selection_end);
|
||||
|
||||
len = strlen (priv->text);
|
||||
|
||||
if (end > len)
|
||||
end = len;
|
||||
|
||||
if (start > len)
|
||||
start = len;
|
||||
|
||||
gtk_selection_data_set_text (selection_data,
|
||||
priv->text + start,
|
||||
end - start);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_label_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data)
|
||||
{
|
||||
gtk_label_set_selection_text (GTK_LABEL (widget), selection_data);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_label_select_region_index (GtkLabel *label,
|
||||
gint anchor_index,
|
||||
|
||||
+77
-36
@@ -124,10 +124,6 @@ static void gtk_link_button_set_property (GObject *object,
|
||||
GParamSpec *pspec);
|
||||
static void gtk_link_button_clicked (GtkButton *button);
|
||||
static gboolean gtk_link_button_popup_menu (GtkWidget *widget);
|
||||
static void gtk_link_button_drag_data_get_cb (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection,
|
||||
gpointer user_data);
|
||||
static gboolean gtk_link_button_query_tooltip_cb (GtkWidget *widget,
|
||||
gint x,
|
||||
gint y,
|
||||
@@ -251,31 +247,96 @@ gtk_link_button_get_menu_model (void)
|
||||
return G_MENU_MODEL (menu);
|
||||
}
|
||||
|
||||
#define GTK_TYPE_LINK_CONTENT (gtk_link_content_get_type ())
|
||||
#define GTK_LINK_CONTENT(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GTK_TYPE_LINK_CONTENT, GtkLinkContent))
|
||||
|
||||
typedef struct _GtkLinkContent GtkLinkContent;
|
||||
typedef struct _GtkLinkContentClass GtkLinkContentClass;
|
||||
|
||||
struct _GtkLinkContent
|
||||
{
|
||||
GdkContentProvider parent;
|
||||
GtkLinkButton *link;
|
||||
};
|
||||
|
||||
struct _GtkLinkContentClass
|
||||
{
|
||||
GdkContentProviderClass parent_class;
|
||||
};
|
||||
|
||||
GType gtk_link_content_get_type (void) G_GNUC_CONST;
|
||||
|
||||
G_DEFINE_TYPE (GtkLinkContent, gtk_link_content, GDK_TYPE_CONTENT_PROVIDER)
|
||||
|
||||
static GdkContentFormats *
|
||||
gtk_link_content_ref_formats (GdkContentProvider *provider)
|
||||
{
|
||||
GtkLinkContent *content = GTK_LINK_CONTENT (provider);
|
||||
|
||||
if (content->link)
|
||||
return gdk_content_formats_union (gdk_content_formats_new_for_gtype (G_TYPE_STRING),
|
||||
gdk_content_formats_new (link_drop_types, G_N_ELEMENTS (link_drop_types)));
|
||||
else
|
||||
return gdk_content_formats_new (NULL, 0);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
gtk_link_content_get_value (GdkContentProvider *provider,
|
||||
GValue *value,
|
||||
GError **error)
|
||||
{
|
||||
GtkLinkContent *content = GTK_LINK_CONTENT (provider);
|
||||
|
||||
if (G_VALUE_HOLDS (value, G_TYPE_STRING) &&
|
||||
content->link != NULL)
|
||||
{
|
||||
GtkLinkButtonPrivate *priv = gtk_link_button_get_instance_private (content->link);
|
||||
char *uri;
|
||||
|
||||
uri = g_strdup_printf ("%s\r\n", priv->uri);
|
||||
g_value_set_string (value, uri);
|
||||
g_free (uri);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
return GDK_CONTENT_PROVIDER_CLASS (gtk_link_content_parent_class)->get_value (provider, value, error);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_link_content_class_init (GtkLinkContentClass *class)
|
||||
{
|
||||
GdkContentProviderClass *provider_class = GDK_CONTENT_PROVIDER_CLASS (class);
|
||||
|
||||
provider_class->ref_formats = gtk_link_content_ref_formats;
|
||||
provider_class->get_value = gtk_link_content_get_value;
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_link_content_init (GtkLinkContent *content)
|
||||
{
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_link_button_init (GtkLinkButton *link_button)
|
||||
{
|
||||
GtkStyleContext *context;
|
||||
GdkContentFormats *targets;
|
||||
GtkGesture *gesture;
|
||||
GdkContentProvider *content;
|
||||
GtkDragSource *source;
|
||||
|
||||
gtk_button_set_relief (GTK_BUTTON (link_button), GTK_RELIEF_NONE);
|
||||
gtk_widget_set_state_flags (GTK_WIDGET (link_button), GTK_STATE_FLAG_LINK, FALSE);
|
||||
gtk_widget_set_has_tooltip (GTK_WIDGET (link_button), TRUE);
|
||||
|
||||
g_signal_connect (link_button, "drag-data-get",
|
||||
G_CALLBACK (gtk_link_button_drag_data_get_cb), NULL);
|
||||
|
||||
g_signal_connect (link_button, "query-tooltip",
|
||||
G_CALLBACK (gtk_link_button_query_tooltip_cb), NULL);
|
||||
|
||||
/* enable drag source */
|
||||
targets = gdk_content_formats_new (link_drop_types, G_N_ELEMENTS (link_drop_types));
|
||||
gtk_drag_source_set (GTK_WIDGET (link_button),
|
||||
GDK_BUTTON1_MASK,
|
||||
targets,
|
||||
GDK_ACTION_COPY);
|
||||
gdk_content_formats_unref (targets);
|
||||
gtk_drag_source_set_icon_name (GTK_WIDGET (link_button), "text-x-generic");
|
||||
content = g_object_new (GTK_TYPE_LINK_CONTENT, NULL);
|
||||
GTK_LINK_CONTENT (content)->link = link_button;
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_COPY);
|
||||
g_object_unref (content);
|
||||
gtk_drag_source_attach (source, GTK_WIDGET (link_button), GDK_BUTTON1_MASK);
|
||||
|
||||
gesture = gtk_gesture_click_new ();
|
||||
gtk_gesture_single_set_touch_only (GTK_GESTURE_SINGLE (gesture), FALSE);
|
||||
@@ -449,26 +510,6 @@ gtk_link_button_popup_menu (GtkWidget *widget)
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_link_button_drag_data_get_cb (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection,
|
||||
gpointer user_data)
|
||||
{
|
||||
GtkLinkButton *link_button = GTK_LINK_BUTTON (widget);
|
||||
GtkLinkButtonPrivate *priv = gtk_link_button_get_instance_private (link_button);
|
||||
gchar *uri;
|
||||
|
||||
uri = g_strdup_printf ("%s\r\n", priv->uri);
|
||||
gtk_selection_data_set (selection,
|
||||
gtk_selection_data_get_target (selection),
|
||||
8,
|
||||
(guchar *) uri,
|
||||
strlen (uri));
|
||||
|
||||
g_free (uri);
|
||||
}
|
||||
|
||||
/**
|
||||
* gtk_link_button_new:
|
||||
* @uri: a valid URI
|
||||
|
||||
@@ -58,6 +58,7 @@ OBJECT:VOID
|
||||
STRING:DOUBLE
|
||||
STRING:STRING
|
||||
VOID:BOOLEAN,BOOLEAN,BOOLEAN
|
||||
VOID:BOXED
|
||||
VOID:BOXED,BOXED
|
||||
VOID:BOXED,BOXED,POINTER
|
||||
VOID:BOXED,ENUM
|
||||
|
||||
+89
-62
@@ -52,6 +52,9 @@
|
||||
#include "gtktypebuiltins.h"
|
||||
#include "gtkwidgetpath.h"
|
||||
#include "gtkwidgetprivate.h"
|
||||
#include "gtkdragsource.h"
|
||||
#include "gtkwidgetpaintable.h"
|
||||
#include "gtkselectionprivate.h"
|
||||
|
||||
#include "a11y/gtknotebookaccessible.h"
|
||||
|
||||
@@ -695,13 +698,13 @@ static gboolean gtk_notebook_focus (GtkWidget *widget,
|
||||
GtkDirectionType direction);
|
||||
|
||||
/*** Drag and drop Methods ***/
|
||||
static void gtk_notebook_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
static void gtk_notebook_drag_end (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
static gboolean gtk_notebook_drag_failed (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkDragResult result);
|
||||
static void gtk_notebook_drag_begin (GtkDragSource *source,
|
||||
GtkWidget *widget);
|
||||
static void gtk_notebook_drag_end (GtkDragSource *source,
|
||||
GtkWidget *widget);
|
||||
static gboolean gtk_notebook_drag_failed (GtkDragSource *source,
|
||||
GdkDragCancelReason reason,
|
||||
GtkWidget *widget);
|
||||
static gboolean gtk_notebook_drag_motion (GtkWidget *widget,
|
||||
GdkDrop *drop,
|
||||
gint x,
|
||||
@@ -712,9 +715,8 @@ static gboolean gtk_notebook_drag_drop (GtkWidget *widget,
|
||||
GdkDrop *drop,
|
||||
gint x,
|
||||
gint y);
|
||||
static void gtk_notebook_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *data);
|
||||
static GBytes * gtk_notebook_drag_data_get (const char *mime_type,
|
||||
gpointer data);
|
||||
static void gtk_notebook_drag_data_received (GtkWidget *widget,
|
||||
GdkDrop *drop,
|
||||
GtkSelectionData *data);
|
||||
@@ -964,14 +966,10 @@ gtk_notebook_class_init (GtkNotebookClass *class)
|
||||
widget_class->grab_notify = gtk_notebook_grab_notify;
|
||||
widget_class->state_flags_changed = gtk_notebook_state_flags_changed;
|
||||
widget_class->focus = gtk_notebook_focus;
|
||||
widget_class->drag_begin = gtk_notebook_drag_begin;
|
||||
widget_class->drag_end = gtk_notebook_drag_end;
|
||||
widget_class->drag_motion = gtk_notebook_drag_motion;
|
||||
widget_class->drag_leave = gtk_notebook_drag_leave;
|
||||
widget_class->drag_drop = gtk_notebook_drag_drop;
|
||||
widget_class->drag_data_get = gtk_notebook_drag_data_get;
|
||||
widget_class->drag_data_received = gtk_notebook_drag_data_received;
|
||||
widget_class->drag_failed = gtk_notebook_drag_failed;
|
||||
widget_class->compute_expand = gtk_notebook_compute_expand;
|
||||
|
||||
container_class->add = gtk_notebook_add;
|
||||
@@ -2881,12 +2879,23 @@ gtk_notebook_motion (GtkEventController *controller,
|
||||
if (page->detachable &&
|
||||
check_threshold (notebook, priv->mouse_x, priv->mouse_y))
|
||||
{
|
||||
GdkContentProvider *content;
|
||||
GtkDragSource *source;
|
||||
|
||||
priv->detached_tab = priv->cur_page;
|
||||
|
||||
gtk_drag_begin (widget,
|
||||
gtk_get_current_event_device (),
|
||||
priv->source_targets, GDK_ACTION_MOVE,
|
||||
priv->drag_begin_x, priv->drag_begin_y);
|
||||
content = gdk_content_provider_new_with_formats (priv->source_targets, gtk_notebook_drag_data_get, widget);
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_MOVE);
|
||||
g_object_unref (content);
|
||||
|
||||
g_signal_connect (source, "drag-begin", G_CALLBACK (gtk_notebook_drag_begin), notebook);
|
||||
g_signal_connect (source, "drag-end", G_CALLBACK (gtk_notebook_drag_end), notebook);
|
||||
g_signal_connect (source, "drag-failed", G_CALLBACK (gtk_notebook_drag_failed), notebook);
|
||||
|
||||
gtk_drag_source_drag_begin (source, widget,
|
||||
gtk_get_current_event_device (),
|
||||
priv->drag_begin_x, priv->drag_begin_y);
|
||||
g_object_unref (source);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -3088,13 +3097,14 @@ update_arrow_nodes (GtkNotebook *notebook)
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_notebook_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag)
|
||||
gtk_notebook_drag_begin (GtkDragSource *source,
|
||||
GtkWidget *widget)
|
||||
{
|
||||
GtkNotebook *notebook = GTK_NOTEBOOK (widget);
|
||||
GtkNotebookPrivate *priv = notebook->priv;
|
||||
graphene_rect_t bounds;
|
||||
GtkWidget *tab_label;
|
||||
GdkPaintable *paintable;
|
||||
|
||||
if (priv->dnd_timer)
|
||||
{
|
||||
@@ -3120,14 +3130,16 @@ gtk_notebook_drag_begin (GtkWidget *widget,
|
||||
|
||||
gtk_style_context_add_class (gtk_widget_get_style_context (priv->dnd_child), "background");
|
||||
|
||||
gtk_drag_set_icon_widget (drag, tab_label, -2, -2);
|
||||
g_object_set_data (G_OBJECT (priv->dnd_child), "drag-context", drag);
|
||||
paintable = gtk_widget_paintable_new (tab_label);
|
||||
gtk_drag_source_set_icon (source, paintable, -2, -2);
|
||||
g_object_set_data (G_OBJECT (priv->dnd_child), "drag-source", source);
|
||||
g_object_unref (paintable);
|
||||
g_object_unref (tab_label);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_notebook_drag_end (GtkWidget *widget,
|
||||
GdkDrag *drag)
|
||||
gtk_notebook_drag_end (GtkDragSource *source,
|
||||
GtkWidget *widget)
|
||||
{
|
||||
GtkNotebook *notebook = GTK_NOTEBOOK (widget);
|
||||
GtkNotebookPrivate *priv = notebook->priv;
|
||||
@@ -3170,16 +3182,16 @@ gtk_notebook_create_window (GtkNotebook *notebook,
|
||||
}
|
||||
|
||||
static gboolean
|
||||
gtk_notebook_drag_failed (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkDragResult result)
|
||||
gtk_notebook_drag_failed (GtkDragSource *source,
|
||||
GdkDragCancelReason reason,
|
||||
GtkWidget *widget)
|
||||
{
|
||||
GtkNotebook *notebook = GTK_NOTEBOOK (widget);
|
||||
GtkNotebookPrivate *priv = notebook->priv;
|
||||
|
||||
priv->rootwindow_drop = FALSE;
|
||||
|
||||
if (result == GTK_DRAG_RESULT_NO_TARGET)
|
||||
if (reason == GDK_DRAG_CANCEL_NO_TARGET)
|
||||
{
|
||||
GtkNotebook *dest_notebook = NULL;
|
||||
|
||||
@@ -3251,30 +3263,39 @@ gtk_notebook_drag_motion (GtkWidget *widget,
|
||||
if (target == tab_target)
|
||||
{
|
||||
GQuark group, source_group;
|
||||
GtkNotebook *source;
|
||||
GtkWidget *source_child;
|
||||
GdkDrag *drag = gdk_drop_get_drag (drop);
|
||||
|
||||
retval = TRUE;
|
||||
|
||||
source = GTK_NOTEBOOK (gtk_drag_get_source_widget (gdk_drop_get_drag (drop)));
|
||||
g_assert (source->priv->cur_page != NULL);
|
||||
source_child = source->priv->cur_page->child;
|
||||
|
||||
group = notebook->priv->group;
|
||||
source_group = source->priv->group;
|
||||
|
||||
if (group != 0 && group == source_group &&
|
||||
!(widget == source_child ||
|
||||
gtk_widget_is_ancestor (widget, source_child)))
|
||||
if (!drag)
|
||||
{
|
||||
gdk_drop_status (drop, GDK_ACTION_MOVE);
|
||||
goto out;
|
||||
gdk_drop_status (drop, 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
/* it's a tab, but doesn't share
|
||||
* ID with this notebook */
|
||||
gdk_drop_status (drop, 0);
|
||||
GtkDragSource *drag_source = gtk_drag_get_source (drag);
|
||||
GtkNotebook *source = GTK_NOTEBOOK (gtk_drag_source_get_origin (drag_source));
|
||||
|
||||
g_assert (source->priv->cur_page != NULL);
|
||||
source_child = source->priv->cur_page->child;
|
||||
|
||||
group = notebook->priv->group;
|
||||
source_group = source->priv->group;
|
||||
|
||||
if (group != 0 && group == source_group &&
|
||||
!(widget == source_child ||
|
||||
gtk_widget_is_ancestor (widget, source_child)))
|
||||
{
|
||||
gdk_drop_status (drop, GDK_ACTION_MOVE);
|
||||
goto out;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* it's a tab, but doesn't share
|
||||
* ID with this notebook */
|
||||
gdk_drop_status (drop, 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3419,30 +3440,32 @@ do_detach_tab (GtkNotebook *from,
|
||||
gtk_notebook_set_current_page (to, page_num);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_notebook_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *data)
|
||||
static GBytes *
|
||||
gtk_notebook_drag_data_get (const char *mime_type,
|
||||
gpointer data)
|
||||
{
|
||||
GtkNotebook *notebook = GTK_NOTEBOOK (widget);
|
||||
GtkNotebook *notebook = GTK_NOTEBOOK (data);
|
||||
GtkNotebookPrivate *priv = notebook->priv;
|
||||
GdkAtom target;
|
||||
GtkSelectionData sdata = { 0, };
|
||||
|
||||
target = gtk_selection_data_get_target (data);
|
||||
if (target == g_intern_static_string ("GTK_NOTEBOOK_TAB"))
|
||||
sdata.target = g_intern_string (mime_type);
|
||||
|
||||
if (sdata.target == g_intern_static_string ("GTK_NOTEBOOK_TAB"))
|
||||
{
|
||||
gtk_selection_data_set (data,
|
||||
target,
|
||||
gtk_selection_data_set (&sdata,
|
||||
sdata.target,
|
||||
8,
|
||||
(void*) &priv->detached_tab->child,
|
||||
sizeof (gpointer));
|
||||
priv->rootwindow_drop = FALSE;
|
||||
}
|
||||
else if (target == g_intern_static_string ("application/x-rootwindow-drop"))
|
||||
else if (sdata.target == g_intern_static_string ("application/x-rootwindow-drop"))
|
||||
{
|
||||
gtk_selection_data_set (data, target, 8, NULL, 0);
|
||||
gtk_selection_data_set (&sdata, sdata.target, 8, NULL, 0);
|
||||
priv->rootwindow_drop = TRUE;
|
||||
}
|
||||
|
||||
return g_bytes_new_take (sdata.data, sdata.length);
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -3457,7 +3480,7 @@ gtk_notebook_drag_data_received (GtkWidget *widget,
|
||||
|
||||
notebook = GTK_NOTEBOOK (widget);
|
||||
drag = gdk_drop_get_drag (drop);
|
||||
source_widget = gtk_drag_get_source_widget (drag);
|
||||
source_widget = drag ? gtk_drag_source_get_origin (gtk_drag_get_source (drag)) : NULL;
|
||||
|
||||
if (source_widget &&
|
||||
(gdk_drop_get_actions (drop) & GDK_ACTION_MOVE) &&
|
||||
@@ -4254,10 +4277,10 @@ gtk_notebook_real_remove (GtkNotebook *notebook,
|
||||
|
||||
if (priv->operation == DRAG_OPERATION_DETACH && !priv->remove_in_detach)
|
||||
{
|
||||
GdkDrag *drag;
|
||||
GtkDragSource *source;
|
||||
|
||||
drag = (GdkDrag *)g_object_get_data (G_OBJECT (priv->dnd_child), "drag-context");
|
||||
gtk_drag_cancel (drag);
|
||||
source = (GtkDragSource *)g_object_get_data (G_OBJECT (priv->dnd_child), "drag-source");
|
||||
gtk_drag_source_drag_cancel (source);
|
||||
}
|
||||
}
|
||||
if (priv->switch_tab == list)
|
||||
@@ -7099,15 +7122,19 @@ gtk_notebook_get_tab_detachable (GtkNotebook *notebook,
|
||||
* |[<!-- language="C" -->
|
||||
* static void
|
||||
* on_drag_data_received (GtkWidget *widget,
|
||||
* GdkDrag *drag,
|
||||
* GdkDrop *drop,
|
||||
* GtkSelectionData *data,
|
||||
* guint time,
|
||||
* gpointer user_data)
|
||||
* {
|
||||
* GtkDrag *drag;
|
||||
* GtkDragSource *source;
|
||||
* GtkWidget *notebook;
|
||||
* GtkWidget **child;
|
||||
*
|
||||
* notebook = gtk_drag_get_source_widget (drag);
|
||||
* drag = gtk_drop_get_drag (drop);
|
||||
* source = gtk_drag_get_source (drag);
|
||||
* notebook = gtk_drag_source_get_origin (source);
|
||||
* child = (void*) gtk_selection_data_get_data (data);
|
||||
*
|
||||
* // process_widget (*child);
|
||||
|
||||
+12
-34
@@ -37,6 +37,7 @@
|
||||
#include "gtkwidgetpath.h"
|
||||
#include "gtkwidgetprivate.h"
|
||||
#include "gtkeventcontrollerscroll.h"
|
||||
#include "gtkdragsource.h"
|
||||
|
||||
typedef struct
|
||||
{
|
||||
@@ -1240,15 +1241,8 @@ set_button_image (GtkPathBar *path_bar,
|
||||
static void
|
||||
button_data_free (ButtonData *button_data)
|
||||
{
|
||||
if (button_data->file)
|
||||
g_object_unref (button_data->file);
|
||||
button_data->file = NULL;
|
||||
|
||||
g_clear_object (&button_data->file);
|
||||
g_free (button_data->dir_name);
|
||||
button_data->dir_name = NULL;
|
||||
|
||||
button_data->button = NULL;
|
||||
|
||||
g_free (button_data);
|
||||
}
|
||||
|
||||
@@ -1312,25 +1306,6 @@ find_button_type (GtkPathBar *path_bar,
|
||||
return NORMAL_BUTTON;
|
||||
}
|
||||
|
||||
static void
|
||||
button_drag_data_get_cb (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data,
|
||||
gpointer data)
|
||||
{
|
||||
ButtonData *button_data;
|
||||
char *uris[2];
|
||||
|
||||
button_data = data;
|
||||
|
||||
uris[0] = g_file_get_uri (button_data->file);
|
||||
uris[1] = NULL;
|
||||
|
||||
gtk_selection_data_set_uris (selection_data, uris);
|
||||
|
||||
g_free (uris[0]);
|
||||
}
|
||||
|
||||
static ButtonData *
|
||||
make_directory_button (GtkPathBar *path_bar,
|
||||
const char *dir_name,
|
||||
@@ -1341,6 +1316,9 @@ make_directory_button (GtkPathBar *path_bar,
|
||||
AtkObject *atk_obj;
|
||||
GtkWidget *child = NULL;
|
||||
ButtonData *button_data;
|
||||
GValue value = G_VALUE_INIT;
|
||||
GdkContentProvider *content;
|
||||
GtkDragSource *source;
|
||||
|
||||
file_is_hidden = !! file_is_hidden;
|
||||
/* Is it a special button? */
|
||||
@@ -1387,13 +1365,13 @@ make_directory_button (GtkPathBar *path_bar,
|
||||
g_object_weak_ref (G_OBJECT (button_data->button),
|
||||
(GWeakNotify) button_data_free, button_data);
|
||||
|
||||
gtk_drag_source_set (button_data->button,
|
||||
GDK_BUTTON1_MASK,
|
||||
NULL,
|
||||
GDK_ACTION_COPY);
|
||||
gtk_drag_source_add_uri_targets (button_data->button);
|
||||
g_signal_connect (button_data->button, "drag-data-get",
|
||||
G_CALLBACK (button_drag_data_get_cb), button_data);
|
||||
g_value_init (&value, G_TYPE_FILE);
|
||||
g_value_set_object (&value, button_data->file);
|
||||
content = gdk_content_provider_new_for_value (&value);
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_COPY);
|
||||
gtk_drag_source_attach (source, button_data->button, GDK_BUTTON1_MASK);
|
||||
g_object_unref (content);
|
||||
g_value_unset (&value);
|
||||
|
||||
return button_data;
|
||||
}
|
||||
|
||||
+32
-35
@@ -63,6 +63,8 @@
|
||||
#include "gtkgestureclick.h"
|
||||
#include "gtkgesturedrag.h"
|
||||
#include "gtknative.h"
|
||||
#include "gtkdragsource.h"
|
||||
#include "gtkwidgetpaintable.h"
|
||||
|
||||
/*< private >
|
||||
* SECTION:gtkplacessidebar
|
||||
@@ -1720,13 +1722,13 @@ stop_drop_feedback (GtkPlacesSidebar *sidebar)
|
||||
}
|
||||
|
||||
static void
|
||||
drag_begin_callback (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
drag_begin_callback (GtkDragSource *source,
|
||||
gpointer user_data)
|
||||
{
|
||||
GtkPlacesSidebar *sidebar = GTK_PLACES_SIDEBAR (user_data);
|
||||
GtkAllocation allocation;
|
||||
GtkWidget *drag_widget;
|
||||
GdkPaintable *paintable;
|
||||
|
||||
gtk_widget_get_allocation (sidebar->drag_row, &allocation);
|
||||
gtk_widget_hide (sidebar->drag_row);
|
||||
@@ -1737,18 +1739,16 @@ drag_begin_callback (GtkWidget *widget,
|
||||
|
||||
gtk_widget_set_opacity (drag_widget, 0.8);
|
||||
|
||||
gtk_drag_set_icon_widget (drag,
|
||||
drag_widget,
|
||||
sidebar->drag_row_x,
|
||||
sidebar->drag_row_y);
|
||||
paintable = gtk_widget_paintable_new (drag_widget);
|
||||
gtk_drag_source_set_icon (source, paintable, sidebar->drag_row_x, sidebar->drag_row_y);
|
||||
g_object_unref (paintable);
|
||||
g_object_set_data_full (G_OBJECT (source), "row-widget", drag_widget, (GDestroyNotify)gtk_widget_destroy);
|
||||
}
|
||||
|
||||
static GtkWidget *
|
||||
create_placeholder_row (GtkPlacesSidebar *sidebar)
|
||||
{
|
||||
return g_object_new (GTK_TYPE_SIDEBAR_ROW,
|
||||
"placeholder", TRUE,
|
||||
NULL);
|
||||
return g_object_new (GTK_TYPE_SIDEBAR_ROW, "placeholder", TRUE, NULL);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
@@ -1950,23 +1950,16 @@ drop_files_as_bookmarks (GtkPlacesSidebar *sidebar,
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
drag_data_get_callback (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *data,
|
||||
gpointer user_data)
|
||||
static GBytes *
|
||||
drag_data_get_callback (const char *mimetype,
|
||||
gpointer user_data)
|
||||
{
|
||||
GtkPlacesSidebar *sidebar = GTK_PLACES_SIDEBAR (user_data);
|
||||
GdkAtom target = gtk_selection_data_get_target (data);
|
||||
|
||||
if (target == g_intern_static_string ("DND_GTK_SIDEBAR_ROW"))
|
||||
{
|
||||
gtk_selection_data_set (data,
|
||||
target,
|
||||
8,
|
||||
(void*)&sidebar->drag_row,
|
||||
sizeof (gpointer));
|
||||
}
|
||||
if (mimetype == g_intern_static_string ("DND_GTK_SIDEBAR_ROW"))
|
||||
return g_bytes_new_take ((gpointer)&sidebar->drag_row, sizeof (gpointer));
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -2088,8 +2081,7 @@ out:
|
||||
}
|
||||
|
||||
static void
|
||||
drag_end_callback (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
drag_end_callback (GtkDragSource *source,
|
||||
gpointer user_data)
|
||||
{
|
||||
stop_drop_feedback (GTK_PLACES_SIDEBAR (user_data));
|
||||
@@ -3778,6 +3770,8 @@ on_row_dragged (GtkGestureDrag *gesture,
|
||||
{
|
||||
gdouble start_x, start_y;
|
||||
gint drag_x, drag_y;
|
||||
GdkContentProvider *content;
|
||||
GtkDragSource *source;
|
||||
|
||||
gtk_gesture_drag_get_start_point (gesture, &start_x, &start_y);
|
||||
gtk_widget_translate_coordinates (GTK_WIDGET (row),
|
||||
@@ -3787,10 +3781,19 @@ on_row_dragged (GtkGestureDrag *gesture,
|
||||
|
||||
sidebar->dragging_over = TRUE;
|
||||
|
||||
gtk_drag_begin (GTK_WIDGET (sidebar),
|
||||
gtk_gesture_get_device (GTK_GESTURE (gesture)),
|
||||
sidebar->source_targets, GDK_ACTION_MOVE,
|
||||
drag_x, drag_y);
|
||||
content = gdk_content_provider_new_with_formats (sidebar->source_targets,
|
||||
drag_data_get_callback,
|
||||
sidebar);
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_MOVE);
|
||||
g_object_unref (content);
|
||||
g_signal_connect (source, "drag-begin", G_CALLBACK (drag_begin_callback), sidebar);
|
||||
g_signal_connect (source, "drag-end", G_CALLBACK (drag_end_callback), sidebar);
|
||||
|
||||
gtk_drag_source_drag_begin (source,
|
||||
GTK_WIDGET (sidebar),
|
||||
gtk_gesture_get_device (GTK_GESTURE (gesture)),
|
||||
drag_x, drag_y);
|
||||
g_object_unref (source);
|
||||
}
|
||||
|
||||
g_object_unref (sidebar);
|
||||
@@ -4090,18 +4093,12 @@ gtk_places_sidebar_init (GtkPlacesSidebar *sidebar)
|
||||
sidebar->source_targets = gdk_content_formats_new (dnd_source_targets, G_N_ELEMENTS (dnd_source_targets));
|
||||
sidebar->source_targets = gtk_content_formats_add_text_targets (sidebar->source_targets);
|
||||
|
||||
g_signal_connect (sidebar->list_box, "drag-begin",
|
||||
G_CALLBACK (drag_begin_callback), sidebar);
|
||||
g_signal_connect (sidebar->list_box, "drag-motion",
|
||||
G_CALLBACK (drag_motion_callback), sidebar);
|
||||
g_signal_connect (sidebar->list_box, "drag-data-get",
|
||||
G_CALLBACK (drag_data_get_callback), sidebar);
|
||||
g_signal_connect (sidebar->list_box, "drag-data-received",
|
||||
G_CALLBACK (drag_data_received_callback), sidebar);
|
||||
g_signal_connect (sidebar->list_box, "drag-drop",
|
||||
G_CALLBACK (drag_drop_callback), sidebar);
|
||||
g_signal_connect (sidebar->list_box, "drag-end",
|
||||
G_CALLBACK (drag_end_callback), sidebar);
|
||||
g_signal_connect (sidebar->list_box, "drag-leave",
|
||||
G_CALLBACK (drag_leave_callback), sidebar);
|
||||
sidebar->drag_row = NULL;
|
||||
|
||||
+39
-92
@@ -67,6 +67,7 @@
|
||||
#include "gtkwindow.h"
|
||||
#include "gtknative.h"
|
||||
#include "gtkactionmuxerprivate.h"
|
||||
#include "gtkdragsource.h"
|
||||
|
||||
#include "a11y/gtktextaccessible.h"
|
||||
|
||||
@@ -344,15 +345,6 @@ static void gtk_text_drag_leave (GtkWidget *widget,
|
||||
static void gtk_text_drag_data_received (GtkWidget *widget,
|
||||
GdkDrop *drop,
|
||||
GtkSelectionData *selection_data);
|
||||
static void gtk_text_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data);
|
||||
static void gtk_text_drag_data_delete (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
static void gtk_text_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
static void gtk_text_drag_end (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
|
||||
|
||||
/* GtkEditable method implementations
|
||||
@@ -729,8 +721,6 @@ gtk_text_class_init (GtkTextClass *class)
|
||||
widget_class->snapshot = gtk_text_snapshot;
|
||||
widget_class->grab_focus = gtk_text_grab_focus;
|
||||
widget_class->style_updated = gtk_text_style_updated;
|
||||
widget_class->drag_begin = gtk_text_drag_begin;
|
||||
widget_class->drag_end = gtk_text_drag_end;
|
||||
widget_class->direction_changed = gtk_text_direction_changed;
|
||||
widget_class->state_flags_changed = gtk_text_state_flags_changed;
|
||||
widget_class->root = gtk_text_root;
|
||||
@@ -740,8 +730,6 @@ gtk_text_class_init (GtkTextClass *class)
|
||||
widget_class->drag_motion = gtk_text_drag_motion;
|
||||
widget_class->drag_leave = gtk_text_drag_leave;
|
||||
widget_class->drag_data_received = gtk_text_drag_data_received;
|
||||
widget_class->drag_data_get = gtk_text_drag_data_get;
|
||||
widget_class->drag_data_delete = gtk_text_drag_data_delete;
|
||||
|
||||
class->move_cursor = gtk_text_move_cursor;
|
||||
class->insert_at_cursor = gtk_text_insert_at_cursor;
|
||||
@@ -2801,6 +2789,12 @@ gtk_text_motion_controller_motion (GtkEventControllerMotion *controller,
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
drag_end (GtkText *self)
|
||||
{
|
||||
g_object_set_data (G_OBJECT (self), "drag-source", NULL);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_drag_gesture_update (GtkGestureDrag *gesture,
|
||||
double offset_x,
|
||||
@@ -2837,23 +2831,38 @@ gtk_text_drag_gesture_update (GtkGestureDrag *gesture,
|
||||
{
|
||||
int *ranges;
|
||||
int n_ranges;
|
||||
GdkContentFormats *target_list = gdk_content_formats_new (NULL, 0);
|
||||
guint actions = priv->editable ? GDK_ACTION_COPY | GDK_ACTION_MOVE : GDK_ACTION_COPY;
|
||||
|
||||
target_list = gtk_content_formats_add_text_targets (target_list);
|
||||
char *text;
|
||||
GdkPaintable *paintable;
|
||||
GtkDragSource *source;
|
||||
|
||||
text = _gtk_text_get_selected_text (self);
|
||||
gtk_text_get_pixel_ranges (self, &ranges, &n_ranges);
|
||||
|
||||
gtk_drag_begin (widget,
|
||||
gdk_event_get_device ((GdkEvent*) event),
|
||||
target_list, actions,
|
||||
priv->drag_start_x + ranges[0],
|
||||
priv->drag_start_y);
|
||||
paintable = gtk_text_util_create_drag_icon (widget, text, -1);
|
||||
|
||||
source = gtk_drag_source_new (priv->selection_content,
|
||||
priv->editable ? GDK_ACTION_COPY | GDK_ACTION_MOVE
|
||||
: GDK_ACTION_COPY);
|
||||
gtk_drag_source_set_icon (source,
|
||||
paintable,
|
||||
priv->drag_start_x - ranges[0],
|
||||
priv->drag_start_y);
|
||||
g_signal_connect_swapped (source, "drag-data-delete",
|
||||
G_CALLBACK (gtk_text_delete_selection), self);
|
||||
g_signal_connect_swapped (source, "drag-end",
|
||||
G_CALLBACK (drag_end), self);
|
||||
g_object_set_data_full (G_OBJECT (self), "drag-source", source, g_object_unref);
|
||||
|
||||
gtk_drag_source_drag_begin (source,
|
||||
widget,
|
||||
gdk_event_get_device ((GdkEvent*) event),
|
||||
priv->drag_start_x + ranges[0],
|
||||
priv->drag_start_y);
|
||||
g_object_unref (paintable);
|
||||
g_free (ranges);
|
||||
g_free (text);
|
||||
|
||||
priv->in_drag = FALSE;
|
||||
|
||||
gdk_content_formats_unref (target_list);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -6094,41 +6103,6 @@ gtk_text_selection_bubble_popup_set (GtkText *self)
|
||||
g_source_set_name_by_id (priv->selection_bubble_timeout_id, "[gtk] gtk_text_selection_bubble_popup_cb");
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag)
|
||||
{
|
||||
GtkText *self = GTK_TEXT (widget);
|
||||
GtkTextPrivate *priv = gtk_text_get_instance_private (self);
|
||||
char *text;
|
||||
|
||||
text = _gtk_text_get_selected_text (self);
|
||||
|
||||
if (self)
|
||||
{
|
||||
int *ranges, n_ranges;
|
||||
GdkPaintable *paintable;
|
||||
|
||||
paintable = gtk_text_util_create_drag_icon (widget, text, -1);
|
||||
gtk_text_get_pixel_ranges (self, &ranges, &n_ranges);
|
||||
|
||||
gtk_drag_set_icon_paintable (drag,
|
||||
paintable,
|
||||
priv->drag_start_x - ranges[0],
|
||||
priv->drag_start_y);
|
||||
|
||||
g_free (ranges);
|
||||
g_object_unref (paintable);
|
||||
g_free (text);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_drag_end (GtkWidget *widget,
|
||||
GdkDrag *drag)
|
||||
{
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_drag_leave (GtkWidget *widget,
|
||||
GdkDrop *drop)
|
||||
@@ -6218,14 +6192,17 @@ static GdkDragAction
|
||||
gtk_text_get_action (GtkText *self,
|
||||
GdkDrop *drop)
|
||||
{
|
||||
GtkWidget *widget = GTK_WIDGET (self);
|
||||
GdkDrag *drag = gdk_drop_get_drag (drop);
|
||||
GtkWidget *source_widget = gtk_drag_get_source_widget (drag);
|
||||
GtkDragSource *source;
|
||||
GtkDragSource *source1;
|
||||
GdkDragAction actions;
|
||||
|
||||
actions = gdk_drop_get_actions (drop);
|
||||
|
||||
if (source_widget == widget &&
|
||||
source = drag ? gtk_drag_get_source (drag) : NULL;
|
||||
source1 = (GtkDragSource*)g_object_get_data (G_OBJECT (self), "drag-source");
|
||||
|
||||
if (source && source == source1 &&
|
||||
actions & GDK_ACTION_MOVE)
|
||||
return GDK_ACTION_MOVE;
|
||||
|
||||
@@ -6286,36 +6263,6 @@ gtk_text_drag_data_received (GtkWidget *widget,
|
||||
g_free (str);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data)
|
||||
{
|
||||
GtkText *self = GTK_TEXT (widget);
|
||||
GtkTextPrivate *priv = gtk_text_get_instance_private (self);
|
||||
|
||||
if (priv->selection_bound != priv->current_pos)
|
||||
{
|
||||
char *str = gtk_text_get_display_text (self, priv->selection_bound, priv->current_pos);
|
||||
|
||||
gtk_selection_data_set_text (selection_data, str, -1);
|
||||
|
||||
g_free (str);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_drag_data_delete (GtkWidget *widget,
|
||||
GdkDrag *drag)
|
||||
{
|
||||
GtkText *self = GTK_TEXT (widget);
|
||||
GtkTextPrivate *priv = gtk_text_get_instance_private (self);
|
||||
|
||||
if (priv->editable &&
|
||||
priv->selection_bound != priv->current_pos)
|
||||
gtk_text_delete_selection (self);
|
||||
}
|
||||
|
||||
/* We display the cursor when
|
||||
*
|
||||
* - the selection is empty, AND
|
||||
|
||||
@@ -4078,6 +4078,13 @@ cut_or_copy (GtkTextBuffer *buffer,
|
||||
}
|
||||
}
|
||||
|
||||
GdkContentProvider *
|
||||
gtk_text_buffer_get_selection_content (GtkTextBuffer *buffer)
|
||||
{
|
||||
return gtk_text_buffer_content_new (buffer);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* gtk_text_buffer_cut_clipboard:
|
||||
* @buffer: a #GtkTextBuffer
|
||||
|
||||
@@ -453,6 +453,10 @@ gboolean gtk_text_buffer_delete_selection (GtkTextBuffer *buffer,
|
||||
gboolean interactive,
|
||||
gboolean default_editable);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
GdkContentProvider *
|
||||
gtk_text_buffer_get_selection_content (GtkTextBuffer *buffer);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
gboolean gtk_text_buffer_get_can_undo (GtkTextBuffer *buffer);
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
|
||||
+38
-107
@@ -418,17 +418,6 @@ static gboolean get_middle_click_paste (GtkTextView *text_view);
|
||||
|
||||
static GtkTextBuffer* gtk_text_view_create_buffer (GtkTextView *text_view);
|
||||
|
||||
/* Source side drag signals */
|
||||
static void gtk_text_view_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
static void gtk_text_view_drag_end (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
static void gtk_text_view_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data);
|
||||
static void gtk_text_view_drag_data_delete (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
|
||||
/* Target side drag signals */
|
||||
static void gtk_text_view_drag_leave (GtkWidget *widget,
|
||||
GdkDrop *drop);
|
||||
@@ -712,10 +701,6 @@ gtk_text_view_class_init (GtkTextViewClass *klass)
|
||||
widget_class->size_allocate = gtk_text_view_size_allocate;
|
||||
widget_class->snapshot = gtk_text_view_snapshot;
|
||||
widget_class->focus = gtk_text_view_focus;
|
||||
widget_class->drag_begin = gtk_text_view_drag_begin;
|
||||
widget_class->drag_end = gtk_text_view_drag_end;
|
||||
widget_class->drag_data_get = gtk_text_view_drag_data_get;
|
||||
widget_class->drag_data_delete = gtk_text_view_drag_data_delete;
|
||||
|
||||
widget_class->drag_leave = gtk_text_view_drag_leave;
|
||||
widget_class->drag_motion = gtk_text_view_drag_motion;
|
||||
@@ -6698,8 +6683,7 @@ gtk_text_view_copy_clipboard (GtkTextView *text_view)
|
||||
{
|
||||
GdkClipboard *clipboard = gtk_widget_get_clipboard (GTK_WIDGET (text_view));
|
||||
|
||||
gtk_text_buffer_copy_clipboard (get_buffer (text_view),
|
||||
clipboard);
|
||||
gtk_text_buffer_copy_clipboard (get_buffer (text_view), clipboard);
|
||||
|
||||
/* on copy do not scroll, we are already onscreen */
|
||||
}
|
||||
@@ -7691,30 +7675,15 @@ gtk_text_view_im_context_filter_keypress (GtkTextView *text_view,
|
||||
*/
|
||||
|
||||
static void
|
||||
drag_begin_cb (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer data)
|
||||
gtk_text_view_drag_data_delete (GtkTextView *text_view)
|
||||
{
|
||||
GtkTextView *text_view = GTK_TEXT_VIEW (widget);
|
||||
GtkTextBuffer *buffer = gtk_text_view_get_buffer (text_view);
|
||||
GtkTextIter start;
|
||||
GtkTextIter end;
|
||||
GdkPaintable *paintable = NULL;
|
||||
gtk_text_buffer_delete_selection (text_view->priv->buffer, TRUE, text_view->priv->editable);
|
||||
}
|
||||
|
||||
g_signal_handlers_disconnect_by_func (widget, drag_begin_cb, NULL);
|
||||
|
||||
if (gtk_text_buffer_get_selection_bounds (buffer, &start, &end))
|
||||
paintable = gtk_text_util_create_rich_drag_icon (widget, buffer, &start, &end);
|
||||
|
||||
if (paintable)
|
||||
{
|
||||
gtk_drag_set_icon_paintable (drag, paintable, 0, 0);
|
||||
g_object_unref (paintable);
|
||||
}
|
||||
else
|
||||
{
|
||||
gtk_drag_set_icon_default (drag);
|
||||
}
|
||||
static void
|
||||
drag_end (GtkTextView *self)
|
||||
{
|
||||
g_object_set_data (G_OBJECT (self), "drag-source", NULL);
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -7724,78 +7693,36 @@ gtk_text_view_start_selection_dnd (GtkTextView *text_view,
|
||||
gint x,
|
||||
gint y)
|
||||
{
|
||||
GdkContentFormats *formats;
|
||||
|
||||
formats = gdk_content_formats_new_for_gtype (GTK_TYPE_TEXT_BUFFER);
|
||||
|
||||
g_signal_connect (text_view, "drag-begin",
|
||||
G_CALLBACK (drag_begin_cb), NULL);
|
||||
gtk_drag_begin (GTK_WIDGET (text_view),
|
||||
gdk_event_get_device (event),
|
||||
formats,
|
||||
GDK_ACTION_COPY | GDK_ACTION_MOVE,
|
||||
x, y);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_view_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag)
|
||||
{
|
||||
/* do nothing */
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_view_drag_end (GtkWidget *widget,
|
||||
GdkDrag *drag)
|
||||
{
|
||||
GtkTextView *text_view;
|
||||
|
||||
text_view = GTK_TEXT_VIEW (widget);
|
||||
text_view->priv->dnd_x = text_view->priv->dnd_y = -1;
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_view_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data)
|
||||
{
|
||||
GtkTextView *text_view = GTK_TEXT_VIEW (widget);
|
||||
GtkWidget *widget = GTK_WIDGET (text_view);
|
||||
GtkTextBuffer *buffer = gtk_text_view_get_buffer (text_view);
|
||||
GtkDragSource *source;
|
||||
GdkContentProvider *content;
|
||||
GtkTextIter start, end;
|
||||
GdkDragAction actions;
|
||||
GdkDevice *device;
|
||||
|
||||
if (gtk_selection_data_get_target (selection_data) == g_intern_static_string ("GTK_TEXT_BUFFER_CONTENTS"))
|
||||
{
|
||||
gtk_selection_data_set (selection_data,
|
||||
g_intern_static_string ("GTK_TEXT_BUFFER_CONTENTS"),
|
||||
8, /* bytes */
|
||||
(void*)&buffer,
|
||||
sizeof (buffer));
|
||||
}
|
||||
if (text_view->priv->editable)
|
||||
actions = GDK_ACTION_COPY | GDK_ACTION_MOVE;
|
||||
else
|
||||
actions = GDK_ACTION_COPY;
|
||||
content = gtk_text_buffer_get_selection_content (buffer);
|
||||
source = gtk_drag_source_new (content, actions);
|
||||
g_object_unref (content);
|
||||
if (gtk_text_buffer_get_selection_bounds (buffer, &start, &end))
|
||||
{
|
||||
GtkTextIter start;
|
||||
GtkTextIter end;
|
||||
gchar *str = NULL;
|
||||
|
||||
if (gtk_text_buffer_get_selection_bounds (buffer, &start, &end))
|
||||
{
|
||||
/* Extract the selected text */
|
||||
str = gtk_text_iter_get_visible_text (&start, &end);
|
||||
}
|
||||
|
||||
if (str)
|
||||
{
|
||||
gtk_selection_data_set_text (selection_data, str, -1);
|
||||
g_free (str);
|
||||
}
|
||||
GdkPaintable *paintable;
|
||||
paintable = gtk_text_util_create_rich_drag_icon (widget, buffer, &start, &end);
|
||||
gtk_drag_source_set_icon (source, paintable, 0, 0);
|
||||
g_object_unref (paintable);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_view_drag_data_delete (GtkWidget *widget,
|
||||
GdkDrag *drag)
|
||||
{
|
||||
gtk_text_buffer_delete_selection (GTK_TEXT_VIEW (widget)->priv->buffer,
|
||||
TRUE, GTK_TEXT_VIEW (widget)->priv->editable);
|
||||
g_signal_connect_swapped (source, "drag-data-delete",
|
||||
G_CALLBACK (gtk_text_view_drag_data_delete), text_view);
|
||||
g_signal_connect_swapped (source, "drag-end",
|
||||
G_CALLBACK (drag_end), text_view);
|
||||
|
||||
device = gdk_event_get_device (event);
|
||||
gtk_drag_source_drag_begin (source, widget, device, x, y);
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -7969,12 +7896,16 @@ gtk_text_view_get_action (GtkWidget *textview,
|
||||
GdkDrop *drop)
|
||||
{
|
||||
GdkDrag *drag = gdk_drop_get_drag (drop);
|
||||
GtkWidget *source_widget = gtk_drag_get_source_widget (drag);
|
||||
GtkDragSource *source;
|
||||
GtkDragSource *source1;
|
||||
GdkDragAction actions;
|
||||
|
||||
actions = gdk_drop_get_actions (drop);
|
||||
|
||||
if (source_widget == textview &&
|
||||
source = drag ? gtk_drag_get_source (drag) : NULL;
|
||||
source1 = (GtkDragSource*)g_object_get_data (G_OBJECT (textview), "drag-source");
|
||||
|
||||
if (source && source == source1 &&
|
||||
actions & GDK_ACTION_MOVE)
|
||||
return GDK_ACTION_MOVE;
|
||||
|
||||
|
||||
+68
-62
@@ -64,6 +64,7 @@
|
||||
#include "gtkwindowgroup.h"
|
||||
#include "gtknative.h"
|
||||
#include "gtkpopover.h"
|
||||
#include "gtkselectionprivate.h"
|
||||
|
||||
#include "a11y/gtktreeviewaccessibleprivate.h"
|
||||
|
||||
@@ -300,8 +301,8 @@ struct _GtkTreeViewChild
|
||||
typedef struct _TreeViewDragInfo TreeViewDragInfo;
|
||||
struct _TreeViewDragInfo
|
||||
{
|
||||
GtkDragSource *source;
|
||||
GdkModifierType start_button_mask;
|
||||
GdkDragAction source_actions;
|
||||
|
||||
guint source_set : 1;
|
||||
guint dest_set : 1;
|
||||
@@ -674,15 +675,14 @@ static void gtk_tree_view_forall (GtkContainer *container,
|
||||
gpointer callback_data);
|
||||
|
||||
/* Source side drag signals */
|
||||
static void gtk_tree_view_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
static void gtk_tree_view_drag_end (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
static void gtk_tree_view_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data);
|
||||
static void gtk_tree_view_drag_data_delete (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
static void gtk_tree_view_drag_begin (GtkDragSource *source,
|
||||
GtkWidget *widget);
|
||||
static void gtk_tree_view_drag_end (GtkDragSource *source,
|
||||
GtkWidget *widget);
|
||||
static GBytes *gtk_tree_view_drag_data_get (const char *mimetype,
|
||||
gpointer data);
|
||||
static void gtk_tree_view_drag_data_delete (GtkDragSource *source,
|
||||
GtkWidget *widget);
|
||||
|
||||
/* Target side drag signals */
|
||||
static void gtk_tree_view_drag_leave (GtkWidget *widget,
|
||||
@@ -1016,10 +1016,6 @@ gtk_tree_view_class_init (GtkTreeViewClass *class)
|
||||
widget_class->measure = gtk_tree_view_measure;
|
||||
widget_class->size_allocate = gtk_tree_view_size_allocate;
|
||||
widget_class->snapshot = gtk_tree_view_snapshot;
|
||||
widget_class->drag_begin = gtk_tree_view_drag_begin;
|
||||
widget_class->drag_end = gtk_tree_view_drag_end;
|
||||
widget_class->drag_data_get = gtk_tree_view_drag_data_get;
|
||||
widget_class->drag_data_delete = gtk_tree_view_drag_data_delete;
|
||||
widget_class->drag_leave = gtk_tree_view_drag_leave;
|
||||
widget_class->drag_motion = gtk_tree_view_drag_motion;
|
||||
widget_class->drag_drop = gtk_tree_view_drag_drop;
|
||||
@@ -6622,21 +6618,21 @@ _gtk_tree_view_column_autosize (GtkTreeView *tree_view,
|
||||
/* Drag-and-drop */
|
||||
|
||||
static void
|
||||
set_source_row (GdkDrag *drag,
|
||||
set_source_row (GtkDragSource *source,
|
||||
GtkTreeModel *model,
|
||||
GtkTreePath *source_row)
|
||||
{
|
||||
g_object_set_data_full (G_OBJECT (drag),
|
||||
g_object_set_data_full (G_OBJECT (source),
|
||||
I_("gtk-tree-view-source-row"),
|
||||
source_row ? gtk_tree_row_reference_new (model, source_row) : NULL,
|
||||
(GDestroyNotify) (source_row ? gtk_tree_row_reference_free : NULL));
|
||||
}
|
||||
|
||||
static GtkTreePath*
|
||||
get_source_row (GdkDrag *drag)
|
||||
get_source_row (GtkDragSource *source)
|
||||
{
|
||||
GtkTreeRowReference *ref =
|
||||
g_object_get_data (G_OBJECT (drag), "gtk-tree-view-source-row");
|
||||
g_object_get_data (G_OBJECT (source), "gtk-tree-view-source-row");
|
||||
|
||||
if (ref)
|
||||
return gtk_tree_row_reference_get_path (ref);
|
||||
@@ -6749,6 +6745,8 @@ get_info (GtkTreeView *tree_view)
|
||||
static void
|
||||
destroy_info (TreeViewDragInfo *di)
|
||||
{
|
||||
g_clear_object (&di->source);
|
||||
|
||||
g_slice_free (TreeViewDragInfo, di);
|
||||
}
|
||||
|
||||
@@ -7058,7 +7056,6 @@ gtk_tree_view_maybe_begin_dragging_row (GtkTreeView *tree_view)
|
||||
{
|
||||
GtkWidget *widget = GTK_WIDGET (tree_view);
|
||||
gdouble start_x, start_y, offset_x, offset_y;
|
||||
GdkDrag *drag;
|
||||
TreeViewDragInfo *di;
|
||||
GtkTreePath *path = NULL;
|
||||
gint button;
|
||||
@@ -7115,13 +7112,12 @@ gtk_tree_view_maybe_begin_dragging_row (GtkTreeView *tree_view)
|
||||
gtk_gesture_set_state (GTK_GESTURE (tree_view->drag_gesture),
|
||||
GTK_EVENT_SEQUENCE_CLAIMED);
|
||||
|
||||
drag = gtk_drag_begin (widget,
|
||||
gtk_gesture_get_device (GTK_GESTURE (tree_view->drag_gesture)),
|
||||
gtk_drag_source_get_target_list (widget),
|
||||
di->source_actions,
|
||||
start_x, start_y);
|
||||
gtk_drag_source_drag_begin (di->source,
|
||||
widget,
|
||||
gtk_gesture_get_device (GTK_GESTURE (tree_view->drag_gesture)),
|
||||
start_x, start_y);
|
||||
|
||||
set_source_row (drag, model, path);
|
||||
set_source_row (di->source, model, path);
|
||||
|
||||
out:
|
||||
if (path)
|
||||
@@ -7132,8 +7128,8 @@ gtk_tree_view_maybe_begin_dragging_row (GtkTreeView *tree_view)
|
||||
|
||||
|
||||
static void
|
||||
gtk_tree_view_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag)
|
||||
gtk_tree_view_drag_begin (GtkDragSource *source,
|
||||
GtkWidget *widget)
|
||||
{
|
||||
GtkTreeView *tree_view;
|
||||
GtkTreePath *path = NULL;
|
||||
@@ -7168,15 +7164,15 @@ gtk_tree_view_drag_begin (GtkWidget *widget,
|
||||
|
||||
row_pix = gtk_tree_view_create_row_drag_icon (tree_view, path);
|
||||
|
||||
gtk_drag_set_icon_paintable (drag, row_pix, tree_view->press_start_x + 1, 1);
|
||||
gtk_drag_source_set_icon (source, row_pix, tree_view->press_start_x + 1, 1);
|
||||
|
||||
g_object_unref (row_pix);
|
||||
gtk_tree_path_free (path);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_tree_view_drag_end (GtkWidget *widget,
|
||||
GdkDrag *drag)
|
||||
gtk_tree_view_drag_end (GtkDragSource *sourc,
|
||||
GtkWidget *widget)
|
||||
{
|
||||
GtkTreeView *tree_view = GTK_TREE_VIEW (widget);
|
||||
|
||||
@@ -7185,32 +7181,32 @@ gtk_tree_view_drag_end (GtkWidget *widget,
|
||||
}
|
||||
|
||||
/* Default signal implementations for the drag signals */
|
||||
static void
|
||||
gtk_tree_view_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data)
|
||||
static GBytes *
|
||||
gtk_tree_view_drag_data_get (const char *mime_type,
|
||||
gpointer data)
|
||||
{
|
||||
GtkTreeView *tree_view;
|
||||
GtkTreeView *tree_view = data;
|
||||
GtkTreeModel *model;
|
||||
TreeViewDragInfo *di;
|
||||
GtkTreePath *source_row;
|
||||
GtkSelectionData sdata = { 0, };
|
||||
|
||||
tree_view = GTK_TREE_VIEW (widget);
|
||||
sdata.target = g_intern_string (mime_type);
|
||||
|
||||
model = gtk_tree_view_get_model (tree_view);
|
||||
|
||||
if (model == NULL)
|
||||
return;
|
||||
return NULL;
|
||||
|
||||
di = get_info (GTK_TREE_VIEW (widget));
|
||||
di = get_info (tree_view);
|
||||
|
||||
if (di == NULL)
|
||||
return;
|
||||
return NULL;
|
||||
|
||||
source_row = get_source_row (drag);
|
||||
source_row = get_source_row (di->source);
|
||||
|
||||
if (source_row == NULL)
|
||||
return;
|
||||
return NULL;
|
||||
|
||||
/* We can implement the GTK_TREE_MODEL_ROW target generically for
|
||||
* any model; for DragSource models there are some other targets
|
||||
@@ -7220,25 +7216,26 @@ gtk_tree_view_drag_data_get (GtkWidget *widget,
|
||||
if (GTK_IS_TREE_DRAG_SOURCE (model) &&
|
||||
gtk_tree_drag_source_drag_data_get (GTK_TREE_DRAG_SOURCE (model),
|
||||
source_row,
|
||||
selection_data))
|
||||
&sdata))
|
||||
goto done;
|
||||
|
||||
/* If drag_data_get does nothing, try providing row data. */
|
||||
if (gtk_selection_data_get_target (selection_data) == g_intern_static_string ("GTK_TREE_MODEL_ROW"))
|
||||
if (mime_type == g_intern_static_string ("GTK_TREE_MODEL_ROW"))
|
||||
{
|
||||
gtk_tree_set_row_drag_data (selection_data,
|
||||
model,
|
||||
source_row);
|
||||
gtk_tree_set_row_drag_data (&sdata, model, source_row);
|
||||
}
|
||||
|
||||
done:
|
||||
gtk_tree_path_free (source_row);
|
||||
|
||||
return g_bytes_new_take ((gpointer)gtk_selection_data_get_data (&sdata),
|
||||
gtk_selection_data_get_length (&sdata));
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
gtk_tree_view_drag_data_delete (GtkWidget *widget,
|
||||
GdkDrag *drag)
|
||||
gtk_tree_view_drag_data_delete (GtkDragSource *source,
|
||||
GtkWidget *widget)
|
||||
{
|
||||
TreeViewDragInfo *di;
|
||||
GtkTreeModel *model;
|
||||
@@ -7256,7 +7253,7 @@ gtk_tree_view_drag_data_delete (GtkWidget *widget,
|
||||
if (di == NULL)
|
||||
return;
|
||||
|
||||
source_row = get_source_row (drag);
|
||||
source_row = get_source_row (source);
|
||||
|
||||
if (source_row == NULL)
|
||||
return;
|
||||
@@ -7265,7 +7262,7 @@ gtk_tree_view_drag_data_delete (GtkWidget *widget,
|
||||
|
||||
gtk_tree_path_free (source_row);
|
||||
|
||||
set_source_row (drag, NULL, NULL);
|
||||
set_source_row (source, NULL, NULL);
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -7419,16 +7416,20 @@ gtk_tree_view_drag_drop (GtkWidget *widget,
|
||||
}
|
||||
|
||||
static GdkDragAction
|
||||
gtk_tree_view_get_action (GtkWidget *treeview,
|
||||
gtk_tree_view_get_action (GtkWidget *widget,
|
||||
GdkDrop *drop)
|
||||
{
|
||||
GtkTreeView *tree_view = GTK_TREE_VIEW (widget);
|
||||
TreeViewDragInfo *di;
|
||||
GdkDrag *drag = gdk_drop_get_drag (drop);
|
||||
GtkWidget *source_widget = gtk_drag_get_source_widget (drag);
|
||||
GtkDragSource *source = drag ? gtk_drag_get_source (drag) : NULL;
|
||||
GdkDragAction actions;
|
||||
|
||||
di = get_info (tree_view);
|
||||
|
||||
actions = gdk_drop_get_actions (drop);
|
||||
|
||||
if (source_widget == treeview &&
|
||||
if (di && source && di->source == source &&
|
||||
actions & GDK_ACTION_MOVE)
|
||||
return GDK_ACTION_MOVE;
|
||||
|
||||
@@ -12915,29 +12916,34 @@ unset_reorderable (GtkTreeView *tree_view)
|
||||
*
|
||||
* Turns @tree_view into a drag source for automatic DND. Calling this
|
||||
* method sets #GtkTreeView:reorderable to %FALSE.
|
||||
*
|
||||
* Returns: (transfer none): the #GtkDragSource that has been attached to @tree_view
|
||||
**/
|
||||
void
|
||||
GtkDragSource *
|
||||
gtk_tree_view_enable_model_drag_source (GtkTreeView *tree_view,
|
||||
GdkModifierType start_button_mask,
|
||||
GdkContentFormats *formats,
|
||||
GdkDragAction actions)
|
||||
{
|
||||
TreeViewDragInfo *di;
|
||||
GdkContentProvider *content;
|
||||
|
||||
g_return_if_fail (GTK_IS_TREE_VIEW (tree_view));
|
||||
|
||||
gtk_drag_source_set (GTK_WIDGET (tree_view),
|
||||
0,
|
||||
formats,
|
||||
actions);
|
||||
g_return_val_if_fail (GTK_IS_TREE_VIEW (tree_view), NULL);
|
||||
|
||||
di = ensure_info (tree_view);
|
||||
|
||||
content = gdk_content_provider_new_with_formats (formats, gtk_tree_view_drag_data_get, tree_view);
|
||||
di->source = gtk_drag_source_new (content, actions);
|
||||
g_object_unref (content);
|
||||
g_signal_connect (di->source, "drag-begin", G_CALLBACK (gtk_tree_view_drag_begin), tree_view);
|
||||
g_signal_connect (di->source, "drag-end", G_CALLBACK (gtk_tree_view_drag_end), tree_view);
|
||||
g_signal_connect (di->source, "drag-data-delete", G_CALLBACK (gtk_tree_view_drag_data_delete), tree_view);
|
||||
di->start_button_mask = start_button_mask;
|
||||
di->source_actions = actions;
|
||||
di->source_set = TRUE;
|
||||
|
||||
unset_reorderable (tree_view);
|
||||
|
||||
return di->source;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -12991,7 +12997,7 @@ gtk_tree_view_unset_rows_drag_source (GtkTreeView *tree_view)
|
||||
{
|
||||
if (di->source_set)
|
||||
{
|
||||
gtk_drag_source_unset (GTK_WIDGET (tree_view));
|
||||
g_clear_object (&di->source);
|
||||
di->source_set = FALSE;
|
||||
}
|
||||
|
||||
|
||||
+2
-1
@@ -27,6 +27,7 @@
|
||||
#include <gtk/gtktreeviewcolumn.h>
|
||||
#include <gtk/gtkdnd.h>
|
||||
#include <gtk/gtkentry.h>
|
||||
#include <gtk/gtkdragsource.h>
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
@@ -314,7 +315,7 @@ gboolean gtk_tree_view_is_blank_at_pos (GtkTreeView
|
||||
|
||||
/* Drag-and-Drop support */
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_tree_view_enable_model_drag_source (GtkTreeView *tree_view,
|
||||
GtkDragSource * gtk_tree_view_enable_model_drag_source (GtkTreeView *tree_view,
|
||||
GdkModifierType start_button_mask,
|
||||
GdkContentFormats *formats,
|
||||
GdkDragAction actions);
|
||||
|
||||
-129
@@ -518,13 +518,9 @@ enum {
|
||||
MNEMONIC_ACTIVATE,
|
||||
MOVE_FOCUS,
|
||||
KEYNAV_FAILED,
|
||||
DRAG_BEGIN,
|
||||
DRAG_END,
|
||||
DRAG_DATA_DELETE,
|
||||
DRAG_LEAVE,
|
||||
DRAG_MOTION,
|
||||
DRAG_DROP,
|
||||
DRAG_DATA_GET,
|
||||
DRAG_DATA_RECEIVED,
|
||||
POPUP_MENU,
|
||||
ACCEL_CLOSURES_CHANGED,
|
||||
@@ -920,13 +916,6 @@ gtk_widget_class_init (GtkWidgetClass *klass)
|
||||
klass->focus = gtk_widget_real_focus;
|
||||
klass->move_focus = gtk_widget_real_move_focus;
|
||||
klass->keynav_failed = gtk_widget_real_keynav_failed;
|
||||
klass->drag_begin = NULL;
|
||||
klass->drag_end = NULL;
|
||||
klass->drag_data_delete = NULL;
|
||||
klass->drag_leave = NULL;
|
||||
klass->drag_motion = NULL;
|
||||
klass->drag_drop = NULL;
|
||||
klass->drag_data_received = NULL;
|
||||
klass->can_activate_accel = gtk_widget_real_can_activate_accel;
|
||||
klass->query_tooltip = gtk_widget_real_query_tooltip;
|
||||
klass->style_updated = gtk_widget_real_style_updated;
|
||||
@@ -1684,96 +1673,6 @@ gtk_widget_class_init (GtkWidgetClass *klass)
|
||||
G_TYPE_NONE, 1,
|
||||
GDK_TYPE_DROP);
|
||||
|
||||
/**
|
||||
* GtkWidget::drag-begin:
|
||||
* @widget: the object which received the signal
|
||||
* @context: the drag context
|
||||
*
|
||||
* The ::drag-begin signal is emitted on the drag source when a drag is
|
||||
* started. A typical reason to connect to this signal is to set up a
|
||||
* custom drag icon with e.g. gtk_drag_source_set_icon_paintable().
|
||||
*
|
||||
* Note that some widgets set up a drag icon in the default handler of
|
||||
* this signal, so you may have to use g_signal_connect_after() to
|
||||
* override what the default handler did.
|
||||
*/
|
||||
widget_signals[DRAG_BEGIN] =
|
||||
g_signal_new (I_("drag-begin"),
|
||||
G_TYPE_FROM_CLASS (klass),
|
||||
G_SIGNAL_RUN_LAST,
|
||||
G_STRUCT_OFFSET (GtkWidgetClass, drag_begin),
|
||||
NULL, NULL,
|
||||
NULL,
|
||||
G_TYPE_NONE, 1,
|
||||
GDK_TYPE_DRAG);
|
||||
|
||||
/**
|
||||
* GtkWidget::drag-end:
|
||||
* @widget: the object which received the signal
|
||||
* @context: the drag context
|
||||
*
|
||||
* The ::drag-end signal is emitted on the drag source when a drag is
|
||||
* finished. A typical reason to connect to this signal is to undo
|
||||
* things done in #GtkWidget::drag-begin.
|
||||
*/
|
||||
widget_signals[DRAG_END] =
|
||||
g_signal_new (I_("drag-end"),
|
||||
G_TYPE_FROM_CLASS (klass),
|
||||
G_SIGNAL_RUN_LAST,
|
||||
G_STRUCT_OFFSET (GtkWidgetClass, drag_end),
|
||||
NULL, NULL,
|
||||
NULL,
|
||||
G_TYPE_NONE, 1,
|
||||
GDK_TYPE_DRAG);
|
||||
|
||||
/**
|
||||
* GtkWidget::drag-data-delete:
|
||||
* @widget: the object which received the signal
|
||||
* @context: the drag context
|
||||
*
|
||||
* The ::drag-data-delete signal is emitted on the drag source when a drag
|
||||
* with the action %GDK_ACTION_MOVE is successfully completed. The signal
|
||||
* handler is responsible for deleting the data that has been dropped. What
|
||||
* "delete" means depends on the context of the drag operation.
|
||||
*/
|
||||
widget_signals[DRAG_DATA_DELETE] =
|
||||
g_signal_new (I_("drag-data-delete"),
|
||||
G_TYPE_FROM_CLASS (klass),
|
||||
G_SIGNAL_RUN_LAST,
|
||||
G_STRUCT_OFFSET (GtkWidgetClass, drag_data_delete),
|
||||
NULL, NULL,
|
||||
NULL,
|
||||
G_TYPE_NONE, 1,
|
||||
GDK_TYPE_DRAG);
|
||||
|
||||
/**
|
||||
* GtkWidget::drag-failed:
|
||||
* @widget: the object which received the signal
|
||||
* @context: the drag context
|
||||
* @result: the result of the drag operation
|
||||
*
|
||||
* The ::drag-failed signal is emitted on the drag source when a drag has
|
||||
* failed. The signal handler may hook custom code to handle a failed DnD
|
||||
* operation based on the type of error, it returns %TRUE is the failure has
|
||||
* been already handled (not showing the default "drag operation failed"
|
||||
* animation), otherwise it returns %FALSE.
|
||||
*
|
||||
* Returns: %TRUE if the failed drag operation has been already handled.
|
||||
*/
|
||||
widget_signals[DRAG_FAILED] =
|
||||
g_signal_new (I_("drag-failed"),
|
||||
G_TYPE_FROM_CLASS (klass),
|
||||
G_SIGNAL_RUN_LAST,
|
||||
G_STRUCT_OFFSET (GtkWidgetClass, drag_failed),
|
||||
_gtk_boolean_handled_accumulator, NULL,
|
||||
_gtk_marshal_BOOLEAN__OBJECT_ENUM,
|
||||
G_TYPE_BOOLEAN, 2,
|
||||
GDK_TYPE_DRAG,
|
||||
GTK_TYPE_DRAG_RESULT);
|
||||
g_signal_set_va_marshaller (widget_signals[DRAG_FAILED],
|
||||
G_TYPE_FROM_CLASS (klass),
|
||||
_gtk_marshal_BOOLEAN__OBJECT_ENUMv);
|
||||
|
||||
/**
|
||||
* GtkWidget::drag-motion:
|
||||
* @widget: the object which received the signal
|
||||
@@ -1913,34 +1812,6 @@ gtk_widget_class_init (GtkWidgetClass *klass)
|
||||
G_TYPE_FROM_CLASS (klass),
|
||||
_gtk_marshal_BOOLEAN__OBJECT_INT_INTv);
|
||||
|
||||
/**
|
||||
* GtkWidget::drag-data-get:
|
||||
* @widget: the object which received the signal
|
||||
* @context: the drag context
|
||||
* @data: the #GtkSelectionData to be filled with the dragged data
|
||||
* @info: the info that has been registered with the target in the
|
||||
* #GtkTargetList
|
||||
*
|
||||
* The ::drag-data-get signal is emitted on the drag source when the drop
|
||||
* site requests the data which is dragged. It is the responsibility of
|
||||
* the signal handler to fill @data with the data in the format which
|
||||
* is indicated by @info. See gtk_selection_data_set() and
|
||||
* gtk_selection_data_set_text().
|
||||
*/
|
||||
widget_signals[DRAG_DATA_GET] =
|
||||
g_signal_new (I_("drag-data-get"),
|
||||
G_TYPE_FROM_CLASS (klass),
|
||||
G_SIGNAL_RUN_LAST,
|
||||
G_STRUCT_OFFSET (GtkWidgetClass, drag_data_get),
|
||||
NULL, NULL,
|
||||
_gtk_marshal_VOID__OBJECT_BOXED,
|
||||
G_TYPE_NONE, 2,
|
||||
GDK_TYPE_DRAG,
|
||||
GTK_TYPE_SELECTION_DATA | G_SIGNAL_TYPE_STATIC_SCOPE);
|
||||
g_signal_set_va_marshaller (widget_signals[DRAG_DATA_GET],
|
||||
G_TYPE_FROM_CLASS (klass),
|
||||
_gtk_marshal_VOID__OBJECT_BOXEDv);
|
||||
|
||||
/**
|
||||
* GtkWidget::drag-data-received:
|
||||
* @widget: the object which received the signal
|
||||
|
||||
@@ -187,14 +187,6 @@ struct _GtkWidget
|
||||
* @focus:
|
||||
* @move_focus: Signal emitted when a change of focus is requested
|
||||
* @keynav_failed: Signal emitted if keyboard navigation fails.
|
||||
* @drag_begin: Signal emitted on the drag source when a drag is
|
||||
* started.
|
||||
* @drag_end: Signal emitted on the drag source when a drag is
|
||||
* finished.
|
||||
* @drag_data_get: Signal emitted on the drag source when the drop
|
||||
* site requests the data which is dragged.
|
||||
* @drag_data_delete: Signal emitted on the drag source when a drag
|
||||
* with the action %GDK_ACTION_MOVE is successfully completed.
|
||||
* @drag_leave: Signal emitted on the drop site when the cursor leaves
|
||||
* the widget.
|
||||
* @drag_motion: signal emitted on the drop site when the user moves
|
||||
@@ -203,8 +195,6 @@ struct _GtkWidget
|
||||
* data onto the widget.
|
||||
* @drag_data_received: Signal emitted on the drop site when the
|
||||
* dragged data has been received.
|
||||
* @drag_failed: Signal emitted on the drag source when a drag has
|
||||
* failed.
|
||||
* @popup_menu: Signal emitted whenever a widget should pop up a
|
||||
* context menu.
|
||||
* @get_accessible: Returns the accessible object that describes the
|
||||
@@ -276,17 +266,6 @@ struct _GtkWidgetClass
|
||||
gboolean (* keynav_failed) (GtkWidget *widget,
|
||||
GtkDirectionType direction);
|
||||
|
||||
/* Source side drag signals */
|
||||
void (* drag_begin) (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
void (* drag_end) (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
void (* drag_data_get) (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data);
|
||||
void (* drag_data_delete) (GtkWidget *widget,
|
||||
GdkDrag *drag);
|
||||
|
||||
/* Target side drag signals */
|
||||
void (* drag_leave) (GtkWidget *widget,
|
||||
GdkDrop *drop);
|
||||
@@ -301,9 +280,6 @@ struct _GtkWidgetClass
|
||||
void (* drag_data_received) (GtkWidget *widget,
|
||||
GdkDrop *drop,
|
||||
GtkSelectionData *selection_data);
|
||||
gboolean (* drag_failed) (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkDragResult result);
|
||||
|
||||
/* Signals used only for keybindings */
|
||||
gboolean (* popup_menu) (GtkWidget *widget);
|
||||
|
||||
@@ -158,9 +158,7 @@
|
||||
</child>
|
||||
<signal name="drag-data-received" handler="file_list_drag_data_received_cb" swapped="no"/>
|
||||
<signal name="drag-drop" handler="file_list_drag_drop_cb" swapped="no"/>
|
||||
<signal name="drag-begin" handler="file_list_drag_begin_cb" swapped="no"/>
|
||||
<signal name="drag-motion" handler="file_list_drag_motion_cb" swapped="no"/>
|
||||
<signal name="drag-end" handler="file_list_drag_end_cb" swapped="no"/>
|
||||
<signal name="popup-menu" handler="list_popup_menu_cb" swapped="no"/>
|
||||
<signal name="query-tooltip" handler="file_list_query_tooltip_cb" swapped="no"/>
|
||||
<signal name="row-activated" handler="list_row_activated" swapped="no"/>
|
||||
|
||||
@@ -53,7 +53,6 @@ gtk_tests = [
|
||||
['testiconview-keynav'],
|
||||
['testicontheme'],
|
||||
['testinfobar'],
|
||||
['testimage'],
|
||||
['testkineticscrolling'],
|
||||
['testlist'],
|
||||
['testlist2'],
|
||||
|
||||
+11
-32
@@ -313,8 +313,6 @@ target_drag_motion (GtkWidget *widget,
|
||||
gint x,
|
||||
gint y)
|
||||
{
|
||||
GtkWidget *source_widget;
|
||||
GdkDrag *drag;
|
||||
char *s;
|
||||
|
||||
if (!have_drag)
|
||||
@@ -323,12 +321,6 @@ target_drag_motion (GtkWidget *widget,
|
||||
gtk_image_set_from_pixbuf (GTK_IMAGE (widget), trashcan_open);
|
||||
}
|
||||
|
||||
drag = gdk_drop_get_drag (drop);
|
||||
source_widget = drag ? gtk_drag_get_source_widget (drag) : NULL;
|
||||
g_print ("motion, source %s\n", source_widget ?
|
||||
G_OBJECT_TYPE_NAME (source_widget) :
|
||||
"NULL");
|
||||
|
||||
s = gdk_content_formats_to_string (gdk_drop_get_formats (drop));
|
||||
g_print ("%s\n", s);
|
||||
|
||||
@@ -416,20 +408,6 @@ label_drag_data_received (GtkWidget *widget,
|
||||
gdk_drop_finish (drop, 0);
|
||||
}
|
||||
|
||||
void
|
||||
source_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data,
|
||||
gpointer data)
|
||||
{
|
||||
if (gtk_selection_data_get_target (selection_data) == g_intern_static_string ("application/x-rootwindow-drop"))
|
||||
g_print ("I was dropped on the rootwin\n");
|
||||
else
|
||||
gtk_selection_data_set (selection_data,
|
||||
gtk_selection_data_get_target (selection_data),
|
||||
8, (guchar *) "I'm Data!", 9);
|
||||
}
|
||||
|
||||
/* The following is a rather elaborate example demonstrating/testing
|
||||
* changing of the window hierarchy during a drag - in this case,
|
||||
* via a "spring-loaded" popup window.
|
||||
@@ -564,7 +542,6 @@ popsite_leave (GtkWidget *widget,
|
||||
|
||||
void
|
||||
source_drag_data_delete (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer data)
|
||||
{
|
||||
g_print ("Delete the data!\n");
|
||||
@@ -587,6 +564,9 @@ main (int argc, char **argv)
|
||||
GtkWidget *button;
|
||||
GdkPixbuf *drag_icon;
|
||||
GdkTexture *texture;
|
||||
GdkContentProvider *content;
|
||||
GValue value = G_VALUE_INIT;
|
||||
GtkDragSource *source;
|
||||
GdkContentFormats *targets;
|
||||
|
||||
test_init ();
|
||||
@@ -661,12 +641,13 @@ main (int argc, char **argv)
|
||||
|
||||
button = gtk_button_new_with_label ("Drag Here\n");
|
||||
|
||||
targets = gdk_content_formats_new (target_table, n_targets);
|
||||
gtk_drag_source_set (button, GDK_BUTTON1_MASK | GDK_BUTTON3_MASK,
|
||||
targets,
|
||||
GDK_ACTION_COPY | GDK_ACTION_MOVE);
|
||||
gtk_drag_source_set_icon_paintable (button, GDK_PAINTABLE (texture));
|
||||
gdk_content_formats_unref (targets);
|
||||
g_value_init (&value, G_TYPE_STRING);
|
||||
g_value_set_string (&value, "I'm data!");
|
||||
content = gdk_content_provider_new_for_value (&value);
|
||||
g_value_unset (&value);
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_COPY | GDK_ACTION_MOVE);
|
||||
gtk_drag_source_attach (source, button, GDK_BUTTON1_MASK | GDK_BUTTON3_MASK);
|
||||
gtk_drag_source_set_icon (source, GDK_PAINTABLE (texture), 0, 0);
|
||||
|
||||
g_object_unref (texture);
|
||||
|
||||
@@ -674,9 +655,7 @@ main (int argc, char **argv)
|
||||
gtk_widget_set_vexpand (button, TRUE);
|
||||
gtk_grid_attach (GTK_GRID (grid), button, 0, 1, 1, 1);
|
||||
|
||||
g_signal_connect (button, "drag-data-get",
|
||||
G_CALLBACK (source_drag_data_get), NULL);
|
||||
g_signal_connect (button, "drag-data-delete",
|
||||
g_signal_connect (source, "drag-data-delete",
|
||||
G_CALLBACK (source_drag_data_delete), NULL);
|
||||
|
||||
gtk_widget_show (window);
|
||||
|
||||
+142
-202
@@ -37,114 +37,12 @@ enum {
|
||||
BOTTOM_RIGHT
|
||||
};
|
||||
|
||||
static void
|
||||
image_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer data)
|
||||
{
|
||||
GdkPaintable *paintable;
|
||||
gint hotspot;
|
||||
gint hot_x, hot_y;
|
||||
gint size;
|
||||
|
||||
paintable = get_image_paintable (GTK_IMAGE (data), &size);
|
||||
hotspot = GPOINTER_TO_INT (g_object_get_data (G_OBJECT (data), "hotspot"));
|
||||
switch (hotspot)
|
||||
{
|
||||
default:
|
||||
case TOP_LEFT:
|
||||
hot_x = 0;
|
||||
hot_y = 0;
|
||||
break;
|
||||
case CENTER:
|
||||
hot_x = size / 2;
|
||||
hot_y = size / 2;
|
||||
break;
|
||||
case BOTTOM_RIGHT:
|
||||
hot_x = size;
|
||||
hot_y = size;
|
||||
break;
|
||||
}
|
||||
gtk_drag_set_icon_paintable (drag, paintable, hot_x, hot_y);
|
||||
g_object_unref (paintable);
|
||||
}
|
||||
|
||||
static void
|
||||
drag_widget_destroyed (GtkWidget *image, gpointer data)
|
||||
{
|
||||
GtkWidget *widget = data;
|
||||
|
||||
g_print ("drag widget destroyed\n");
|
||||
g_object_unref (image);
|
||||
g_object_set_data (G_OBJECT (widget), "drag widget", NULL);
|
||||
}
|
||||
|
||||
static void
|
||||
window_drag_end (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer data)
|
||||
{
|
||||
GtkWidget *window = data;
|
||||
|
||||
gtk_widget_destroy (window);
|
||||
g_signal_handlers_disconnect_by_func (widget, window_drag_end, data);
|
||||
}
|
||||
|
||||
static void
|
||||
window_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer data)
|
||||
{
|
||||
GdkPaintable *paintable;
|
||||
GtkWidget *image;
|
||||
int hotspot;
|
||||
int size;
|
||||
|
||||
hotspot = GPOINTER_TO_INT (g_object_get_data (G_OBJECT (data), "hotspot"));
|
||||
|
||||
image = g_object_get_data (G_OBJECT (widget), "drag widget");
|
||||
if (image == NULL)
|
||||
{
|
||||
g_print ("creating new drag widget\n");
|
||||
paintable = get_image_paintable (GTK_IMAGE (data), &size);
|
||||
image = gtk_image_new_from_paintable (paintable);
|
||||
g_object_unref (paintable);
|
||||
g_object_ref (image);
|
||||
g_object_set_data (G_OBJECT (widget), "drag widget", image);
|
||||
g_signal_connect (image, "destroy", G_CALLBACK (drag_widget_destroyed), widget);
|
||||
}
|
||||
else
|
||||
g_print ("reusing drag widget\n");
|
||||
|
||||
gtk_drag_set_icon_widget (drag, image, 0, 0);
|
||||
|
||||
if (hotspot == CENTER)
|
||||
g_signal_connect (widget, "drag-end", G_CALLBACK (window_drag_end), image);
|
||||
}
|
||||
|
||||
static void
|
||||
update_source_target_list (GtkWidget *image)
|
||||
{
|
||||
GdkContentFormats *target_list;
|
||||
|
||||
target_list = gdk_content_formats_new (NULL, 0);
|
||||
|
||||
target_list = gtk_content_formats_add_image_targets (target_list, FALSE);
|
||||
if (gtk_image_get_storage_type (GTK_IMAGE (image)) == GTK_IMAGE_ICON_NAME)
|
||||
target_list = gtk_content_formats_add_text_targets (target_list);
|
||||
|
||||
gtk_drag_source_set_target_list (image, target_list);
|
||||
|
||||
gdk_content_formats_unref (target_list);
|
||||
}
|
||||
|
||||
static void
|
||||
update_dest_target_list (GtkWidget *image)
|
||||
{
|
||||
GdkContentFormats *target_list;
|
||||
|
||||
target_list = gdk_content_formats_new (NULL, 0);
|
||||
|
||||
target_list = gtk_content_formats_add_image_targets (target_list, FALSE);
|
||||
target_list = gtk_content_formats_add_text_targets (target_list);
|
||||
|
||||
@@ -191,149 +89,191 @@ image_drag_data_received (GtkWidget *widget,
|
||||
GtkSelectionData *selection_data,
|
||||
gpointer data)
|
||||
{
|
||||
GdkTexture *texture;
|
||||
gchar *text;
|
||||
|
||||
if (gtk_selection_data_get_length (selection_data) == 0)
|
||||
return;
|
||||
|
||||
if (gtk_selection_data_targets_include_image (selection_data, FALSE))
|
||||
texture = gtk_selection_data_get_texture (selection_data);
|
||||
if (texture)
|
||||
{
|
||||
GdkTexture *texture;
|
||||
|
||||
texture = gtk_selection_data_get_texture (selection_data);
|
||||
gtk_image_set_from_paintable (GTK_IMAGE (data), GDK_PAINTABLE (texture));
|
||||
|
||||
gtk_image_set_from_paintable (GTK_IMAGE (widget), GDK_PAINTABLE (texture));
|
||||
g_object_unref (texture);
|
||||
return;
|
||||
}
|
||||
else if (gtk_selection_data_targets_include_text (selection_data))
|
||||
|
||||
text = (gchar *)gtk_selection_data_get_text (selection_data);
|
||||
if (text)
|
||||
{
|
||||
text = (gchar *)gtk_selection_data_get_text (selection_data);
|
||||
gtk_image_set_from_icon_name (GTK_IMAGE (data), text);
|
||||
gtk_image_set_from_icon_name (GTK_IMAGE (widget), text);
|
||||
g_free (text);
|
||||
}
|
||||
else
|
||||
{
|
||||
g_assert_not_reached ();
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
update_source_icon (GtkDragSource *source,
|
||||
const char *icon_name,
|
||||
int hotspot)
|
||||
{
|
||||
GdkPaintable *paintable;
|
||||
int hot_x, hot_y;
|
||||
int size = 48;
|
||||
|
||||
paintable = gtk_icon_theme_load_icon (gtk_icon_theme_get_default (),
|
||||
icon_name, size, 0, NULL);
|
||||
switch (hotspot)
|
||||
{
|
||||
default:
|
||||
case TOP_LEFT:
|
||||
hot_x = 0;
|
||||
hot_y = 0;
|
||||
break;
|
||||
case CENTER:
|
||||
hot_x = size / 2;
|
||||
hot_y = size / 2;
|
||||
break;
|
||||
case BOTTOM_RIGHT:
|
||||
hot_x = size;
|
||||
hot_y = size;
|
||||
break;
|
||||
}
|
||||
gtk_drag_source_set_icon (source, paintable, hot_x, hot_y);
|
||||
g_object_unref (paintable);
|
||||
}
|
||||
|
||||
static GBytes *
|
||||
get_data (const char *mimetype,
|
||||
gpointer data)
|
||||
{
|
||||
GtkWidget *image = data;
|
||||
GdkContentFormats *formats;
|
||||
gboolean want_text;
|
||||
|
||||
formats = gdk_content_formats_new (NULL, 0);
|
||||
formats = gtk_content_formats_add_text_targets (formats);
|
||||
want_text = gdk_content_formats_contain_mime_type (formats, mimetype);
|
||||
gdk_content_formats_unref (formats);
|
||||
|
||||
g_print ("get data called for %s\n", mimetype);
|
||||
if (want_text)
|
||||
{
|
||||
const char *text = gtk_image_get_icon_name (GTK_IMAGE (image));
|
||||
|
||||
return g_bytes_new (text, strlen (text) + 1);
|
||||
}
|
||||
else if (strcmp (mimetype, "image/png") == 0)
|
||||
{
|
||||
int size;
|
||||
GdkPaintable *paintable = get_image_paintable (GTK_IMAGE (image), &size);
|
||||
if (GDK_IS_TEXTURE (paintable))
|
||||
{
|
||||
char *name = g_strdup ("drag-data-XXXXXX");
|
||||
int fd;
|
||||
char *data;
|
||||
gsize size;
|
||||
|
||||
// FIXME: this is horrible
|
||||
|
||||
fd = g_mkstemp (name);
|
||||
close (fd);
|
||||
|
||||
gdk_texture_save_to_png (GDK_TEXTURE (paintable), name);
|
||||
|
||||
g_file_get_contents (name, &data, &size, NULL);
|
||||
g_free (name);
|
||||
|
||||
return g_bytes_new_take (data, size);
|
||||
}
|
||||
|
||||
g_clear_object (&paintable);
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void
|
||||
drag_begin (GtkDragSource *source)
|
||||
{
|
||||
g_print ("drag begin\n");
|
||||
}
|
||||
|
||||
static void
|
||||
drag_end (GtkDragSource *source)
|
||||
{
|
||||
g_print ("drag end\n");
|
||||
}
|
||||
|
||||
static gboolean
|
||||
drag_failed (GtkDragSource *source, GdkDragCancelReason reason)
|
||||
{
|
||||
g_print ("drag failed: %d\n", reason);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
GtkWidget *
|
||||
make_image (const gchar *icon_name, int hotspot)
|
||||
{
|
||||
GtkWidget *image;
|
||||
GtkDragSource *source;
|
||||
GdkContentFormats *formats;
|
||||
GdkContentProvider *content;
|
||||
|
||||
image = gtk_image_new_from_icon_name (icon_name);
|
||||
gtk_image_set_icon_size (GTK_IMAGE (image), GTK_ICON_SIZE_LARGE);
|
||||
|
||||
gtk_drag_source_set (image, GDK_BUTTON1_MASK, NULL, GDK_ACTION_COPY);
|
||||
update_source_target_list (image);
|
||||
formats = gdk_content_formats_new (NULL, 0);
|
||||
formats = gtk_content_formats_add_image_targets (formats, FALSE);
|
||||
formats = gtk_content_formats_add_text_targets (formats);
|
||||
|
||||
g_object_set_data (G_OBJECT (image), "hotspot", GINT_TO_POINTER (hotspot));
|
||||
content = gdk_content_provider_new_with_formats (formats, get_data, image);
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_COPY);
|
||||
g_object_unref (content);
|
||||
gdk_content_formats_unref (formats);
|
||||
update_source_icon (source, icon_name, hotspot);
|
||||
|
||||
g_signal_connect (image, "drag-begin", G_CALLBACK (image_drag_begin), image);
|
||||
g_signal_connect (image, "drag-data-get", G_CALLBACK (image_drag_data_get), image);
|
||||
g_signal_connect (source, "drag-begin", G_CALLBACK (drag_begin), NULL);
|
||||
g_signal_connect (source, "drag-end", G_CALLBACK (drag_end), NULL);
|
||||
g_signal_connect (source, "drag-failed", G_CALLBACK (drag_failed), NULL);
|
||||
gtk_drag_source_attach (source, image, GDK_BUTTON1_MASK);
|
||||
|
||||
gtk_drag_dest_set (image, GTK_DEST_DEFAULT_ALL, NULL, GDK_ACTION_COPY);
|
||||
g_signal_connect (image, "drag-data-received", G_CALLBACK (image_drag_data_received), image);
|
||||
update_dest_target_list (image);
|
||||
|
||||
return image;
|
||||
}
|
||||
|
||||
GtkWidget *
|
||||
make_image2 (const gchar *icon_name, int hotspot)
|
||||
{
|
||||
GtkWidget *image;
|
||||
|
||||
image = gtk_image_new_from_icon_name (icon_name);
|
||||
gtk_image_set_icon_size (GTK_IMAGE (image), GTK_ICON_SIZE_LARGE);
|
||||
|
||||
gtk_drag_source_set (image, GDK_BUTTON1_MASK, NULL, GDK_ACTION_COPY);
|
||||
update_source_target_list (image);
|
||||
|
||||
g_object_set_data (G_OBJECT (image), "hotspot", GINT_TO_POINTER (hotspot));
|
||||
|
||||
g_signal_connect (image, "drag-begin", G_CALLBACK (window_drag_begin), image);
|
||||
g_signal_connect (image, "drag-data-get", G_CALLBACK (image_drag_data_get), image);
|
||||
|
||||
gtk_drag_dest_set (image, GTK_DEST_DEFAULT_ALL, NULL, GDK_ACTION_COPY);
|
||||
g_signal_connect (image, "drag-data-received", G_CALLBACK (image_drag_data_received), image);
|
||||
g_signal_connect (image, "drag-data-received", G_CALLBACK (image_drag_data_received), NULL);
|
||||
update_dest_target_list (image);
|
||||
|
||||
return image;
|
||||
}
|
||||
|
||||
static void
|
||||
spinner_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer data)
|
||||
spinner_drag_begin (GtkDragSource *source,
|
||||
GtkWidget *widget)
|
||||
{
|
||||
GtkWidget *spinner;
|
||||
GdkPaintable *paintable;
|
||||
|
||||
g_print ("GtkWidget::drag-begin\n");
|
||||
spinner = g_object_new (GTK_TYPE_SPINNER,
|
||||
"visible", TRUE,
|
||||
"active", TRUE,
|
||||
NULL);
|
||||
gtk_drag_set_icon_widget (drag, spinner, 0, 0);
|
||||
g_object_set_data (G_OBJECT (drag), "spinner", spinner);
|
||||
}
|
||||
|
||||
static void
|
||||
spinner_drag_end (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer data)
|
||||
{
|
||||
GtkWidget *spinner;
|
||||
|
||||
g_print ("GtkWidget::drag-end\n");
|
||||
spinner = g_object_get_data (G_OBJECT (drag), "spinner");
|
||||
gtk_widget_destroy (spinner);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
spinner_drag_failed (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkDragResult result,
|
||||
gpointer data)
|
||||
{
|
||||
GTypeClass *class;
|
||||
GEnumValue *value;
|
||||
|
||||
class = g_type_class_ref (GTK_TYPE_DRAG_RESULT);
|
||||
value = g_enum_get_value (G_ENUM_CLASS (class), result);
|
||||
g_print ("GtkWidget::drag-failed %s\n", value->value_nick);
|
||||
g_type_class_unref (class);
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
void
|
||||
spinner_drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data,
|
||||
gpointer data)
|
||||
{
|
||||
g_print ("GtkWidget::drag-data-get\n");
|
||||
gtk_selection_data_set_text (selection_data, "ACTIVE", -1);
|
||||
paintable = gtk_widget_paintable_new (widget);
|
||||
gtk_drag_source_set_icon (source, paintable, 0, 0);
|
||||
g_object_unref (paintable);
|
||||
}
|
||||
|
||||
static GtkWidget *
|
||||
make_spinner (void)
|
||||
{
|
||||
GtkWidget *spinner;
|
||||
GtkDragSource *source;
|
||||
GdkContentProvider *content;
|
||||
GValue value = G_VALUE_INIT;
|
||||
|
||||
spinner = gtk_spinner_new ();
|
||||
gtk_spinner_start (GTK_SPINNER (spinner));
|
||||
|
||||
gtk_drag_source_set (spinner, GDK_BUTTON1_MASK, NULL, GDK_ACTION_COPY);
|
||||
gtk_drag_source_add_text_targets (spinner);
|
||||
g_value_init (&value, G_TYPE_STRING);
|
||||
g_value_set_string (&value, "ACTIVE");
|
||||
content = gdk_content_provider_new_for_value (&value);
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_COPY);
|
||||
g_signal_connect (source, "drag-begin", G_CALLBACK (spinner_drag_begin), spinner);
|
||||
gtk_drag_source_attach (source, spinner, GDK_BUTTON1_MASK);
|
||||
|
||||
g_signal_connect (spinner, "drag-begin", G_CALLBACK (spinner_drag_begin), spinner);
|
||||
g_signal_connect (spinner, "drag-end", G_CALLBACK (spinner_drag_end), spinner);
|
||||
g_signal_connect (spinner, "drag-failed", G_CALLBACK (spinner_drag_failed), spinner);
|
||||
g_signal_connect (spinner, "drag-data-get", G_CALLBACK (spinner_drag_data_get), spinner);
|
||||
g_object_unref (content);
|
||||
g_value_unset (&value);
|
||||
|
||||
return spinner;
|
||||
}
|
||||
@@ -367,9 +307,9 @@ main (int argc, char *Argv[])
|
||||
gtk_grid_attach (GTK_GRID (grid), make_spinner (), 0, 2, 1, 1);
|
||||
gtk_grid_attach (GTK_GRID (grid), make_image ("weather-clear", CENTER), 1, 2, 1, 1);
|
||||
|
||||
gtk_grid_attach (GTK_GRID (grid), make_image2 ("dialog-question", TOP_LEFT), 0, 3, 1, 1);
|
||||
gtk_grid_attach (GTK_GRID (grid), make_image ("dialog-question", TOP_LEFT), 0, 3, 1, 1);
|
||||
|
||||
gtk_grid_attach (GTK_GRID (grid), make_image2 ("dialog-information", CENTER), 1, 3, 1, 1);
|
||||
gtk_grid_attach (GTK_GRID (grid), make_image ("dialog-information", CENTER), 1, 3, 1, 1);
|
||||
|
||||
gtk_widget_show (window);
|
||||
gtk_main ();
|
||||
|
||||
+9
-48
@@ -8,45 +8,6 @@ clear_pressed (GtkEntry *entry, gint icon, gpointer data)
|
||||
gtk_editable_set_text (GTK_EDITABLE (entry), "");
|
||||
}
|
||||
|
||||
static void
|
||||
drag_begin_cb (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer user_data)
|
||||
{
|
||||
gint pos;
|
||||
|
||||
pos = gtk_entry_get_current_icon_drag_source (GTK_ENTRY (widget));
|
||||
if (pos != -1)
|
||||
gtk_drag_set_icon_name (drag, "dialog-information", 2, 2);
|
||||
}
|
||||
|
||||
static void
|
||||
drag_data_get_cb (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *data,
|
||||
gpointer user_data)
|
||||
{
|
||||
gint pos;
|
||||
|
||||
pos = gtk_entry_get_current_icon_drag_source (GTK_ENTRY (widget));
|
||||
|
||||
if (pos == GTK_ENTRY_ICON_PRIMARY)
|
||||
{
|
||||
gint start, end;
|
||||
|
||||
if (gtk_editable_get_selection_bounds (GTK_EDITABLE (widget), &start, &end))
|
||||
{
|
||||
gchar *str;
|
||||
|
||||
str = gtk_editable_get_chars (GTK_EDITABLE (widget), start, end);
|
||||
gtk_selection_data_set_text (data, str, -1);
|
||||
g_free (str);
|
||||
}
|
||||
else
|
||||
gtk_selection_data_set_text (data, "XXX", -1);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
set_blank (GtkWidget *button,
|
||||
GtkEntry *entry)
|
||||
@@ -127,7 +88,8 @@ main (int argc, char **argv)
|
||||
GtkWidget *button3;
|
||||
GtkWidget *button4;
|
||||
GIcon *icon;
|
||||
GdkContentFormats *tlist;
|
||||
GdkContentProvider *content;
|
||||
GValue value = G_VALUE_INIT;
|
||||
|
||||
gtk_init ();
|
||||
|
||||
@@ -189,16 +151,15 @@ main (int argc, char **argv)
|
||||
gtk_entry_set_icon_tooltip_text (GTK_ENTRY (entry),
|
||||
GTK_ENTRY_ICON_PRIMARY,
|
||||
"Save a file");
|
||||
tlist = gdk_content_formats_new (NULL, 0);
|
||||
tlist = gtk_content_formats_add_text_targets (tlist);
|
||||
|
||||
g_value_init (&value, G_TYPE_STRING);
|
||||
g_value_set_string (&value, "Amazing");
|
||||
content = gdk_content_provider_new_for_value (&value);
|
||||
g_value_unset (&value);
|
||||
gtk_entry_set_icon_drag_source (GTK_ENTRY (entry),
|
||||
GTK_ENTRY_ICON_PRIMARY,
|
||||
tlist, GDK_ACTION_COPY);
|
||||
g_signal_connect_after (entry, "drag-begin",
|
||||
G_CALLBACK (drag_begin_cb), NULL);
|
||||
g_signal_connect (entry, "drag-data-get",
|
||||
G_CALLBACK (drag_data_get_cb), NULL);
|
||||
gdk_content_formats_unref (tlist);
|
||||
content, GDK_ACTION_COPY);
|
||||
g_object_unref (content);
|
||||
|
||||
/*
|
||||
* Search - Uses a helper function
|
||||
|
||||
@@ -1,178 +0,0 @@
|
||||
/* testimage.c
|
||||
* Copyright (C) 2004 Red Hat, Inc.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include <gtk/gtk.h>
|
||||
#include <gio/gio.h>
|
||||
|
||||
static void
|
||||
drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer data)
|
||||
{
|
||||
GtkWidget *image = GTK_WIDGET (data);
|
||||
GdkPaintable *paintable;
|
||||
|
||||
paintable = gtk_image_get_paintable (GTK_IMAGE (image));
|
||||
gtk_drag_set_icon_paintable (drag, paintable, -2, -2);
|
||||
}
|
||||
|
||||
void
|
||||
drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data,
|
||||
gpointer data)
|
||||
{
|
||||
GtkWidget *image = GTK_WIDGET (data);
|
||||
GdkPaintable *paintable;
|
||||
|
||||
paintable = gtk_image_get_paintable (GTK_IMAGE (image));
|
||||
if (GDK_IS_TEXTURE (paintable))
|
||||
gtk_selection_data_set_texture (selection_data, GDK_TEXTURE (paintable));
|
||||
}
|
||||
|
||||
static void
|
||||
drag_data_received (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data,
|
||||
guint info,
|
||||
guint32 time,
|
||||
gpointer data)
|
||||
{
|
||||
GtkWidget *image = GTK_WIDGET (data);
|
||||
GdkTexture *texture;
|
||||
|
||||
if (gtk_selection_data_get_length (selection_data) < 0)
|
||||
return;
|
||||
|
||||
texture = gtk_selection_data_get_texture (selection_data);
|
||||
gtk_image_set_from_paintable (GTK_IMAGE (image), GDK_PAINTABLE (texture));
|
||||
|
||||
g_object_unref (texture);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
idle_func (gpointer data)
|
||||
{
|
||||
g_print ("keep me busy\n");
|
||||
|
||||
return G_SOURCE_CONTINUE;
|
||||
}
|
||||
|
||||
int
|
||||
main (int argc, char **argv)
|
||||
{
|
||||
GtkWidget *window, *grid;
|
||||
GtkWidget *label, *image;
|
||||
GtkIconTheme *theme;
|
||||
GdkPaintable *paintable;
|
||||
gchar *icon_name = "help-browser";
|
||||
gchar *anim_filename = NULL;
|
||||
GtkIconInfo *icon_info;
|
||||
GIcon *icon;
|
||||
GFile *file;
|
||||
|
||||
gtk_init ();
|
||||
|
||||
if (argc > 1)
|
||||
icon_name = argv[1];
|
||||
|
||||
if (argc > 2)
|
||||
anim_filename = argv[2];
|
||||
|
||||
window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
|
||||
|
||||
grid = gtk_grid_new ();
|
||||
gtk_grid_set_row_spacing (GTK_GRID (grid), 10);
|
||||
gtk_grid_set_column_spacing (GTK_GRID (grid), 10);
|
||||
gtk_container_add (GTK_CONTAINER (window), grid);
|
||||
|
||||
label = gtk_label_new ("symbolic size");
|
||||
gtk_grid_attach (GTK_GRID (grid), label, 1, 0, 1, 1);
|
||||
label = gtk_label_new ("fixed size");
|
||||
gtk_grid_attach (GTK_GRID (grid), label, 2, 0, 1, 1);
|
||||
|
||||
label = gtk_label_new ("GTK_IMAGE_PIXBUF");
|
||||
gtk_grid_attach (GTK_GRID (grid), label, 0, 1, 1, 1);
|
||||
|
||||
theme = gtk_icon_theme_get_default ();
|
||||
icon_info = gtk_icon_theme_lookup_icon_for_scale (theme, icon_name, 48, gtk_widget_get_scale_factor (window), GTK_ICON_LOOKUP_GENERIC_FALLBACK);
|
||||
paintable = gtk_icon_info_load_icon (icon_info, NULL);
|
||||
g_object_unref (icon_info);
|
||||
image = gtk_image_new_from_paintable (paintable);
|
||||
g_object_unref (paintable);
|
||||
gtk_grid_attach (GTK_GRID (grid), image, 2, 1, 1, 1);
|
||||
|
||||
gtk_drag_source_set (image, GDK_BUTTON1_MASK,
|
||||
NULL,
|
||||
GDK_ACTION_COPY);
|
||||
gtk_drag_source_add_image_targets (image);
|
||||
g_signal_connect (image, "drag_begin", G_CALLBACK (drag_begin), image);
|
||||
g_signal_connect (image, "drag_data_get", G_CALLBACK (drag_data_get), image);
|
||||
|
||||
gtk_drag_dest_set (image,
|
||||
GTK_DEST_DEFAULT_MOTION |
|
||||
GTK_DEST_DEFAULT_HIGHLIGHT |
|
||||
GTK_DEST_DEFAULT_DROP,
|
||||
NULL, GDK_ACTION_COPY);
|
||||
gtk_drag_dest_add_image_targets (image);
|
||||
g_signal_connect (image, "drag_data_received",
|
||||
G_CALLBACK (drag_data_received), image);
|
||||
|
||||
label = gtk_label_new ("GTK_IMAGE_ICON_NAME");
|
||||
gtk_grid_attach (GTK_GRID (grid), label, 0, 4, 1, 1);
|
||||
image = gtk_image_new_from_icon_name (icon_name);
|
||||
gtk_image_set_icon_size (GTK_IMAGE (image), GTK_ICON_SIZE_LARGE);
|
||||
gtk_grid_attach (GTK_GRID (grid), image, 1, 4, 1, 1);
|
||||
image = gtk_image_new_from_icon_name (icon_name);
|
||||
gtk_image_set_icon_size (GTK_IMAGE (image), GTK_ICON_SIZE_LARGE);
|
||||
gtk_image_set_pixel_size (GTK_IMAGE (image), 30);
|
||||
gtk_grid_attach (GTK_GRID (grid), image, 2, 4, 1, 1);
|
||||
|
||||
label = gtk_label_new ("GTK_IMAGE_GICON");
|
||||
gtk_grid_attach (GTK_GRID (grid), label, 0, 5, 1, 1);
|
||||
icon = g_themed_icon_new_with_default_fallbacks ("folder-remote");
|
||||
image = gtk_image_new_from_gicon (icon);
|
||||
gtk_image_set_icon_size (GTK_IMAGE (image), GTK_ICON_SIZE_LARGE);
|
||||
g_object_unref (icon);
|
||||
gtk_grid_attach (GTK_GRID (grid), image, 1, 5, 1, 1);
|
||||
file = g_file_new_for_path ("apple-red.png");
|
||||
icon = g_file_icon_new (file);
|
||||
image = gtk_image_new_from_gicon (icon);
|
||||
gtk_image_set_icon_size (GTK_IMAGE (image), GTK_ICON_SIZE_LARGE);
|
||||
g_object_unref (icon);
|
||||
gtk_image_set_pixel_size (GTK_IMAGE (image), 30);
|
||||
gtk_grid_attach (GTK_GRID (grid), image, 2, 5, 1, 1);
|
||||
|
||||
if (anim_filename)
|
||||
{
|
||||
label = gtk_label_new ("GTK_IMAGE_ANIMATION (from file)");
|
||||
gtk_grid_attach (GTK_GRID (grid), label, 0, 6, 1, 1);
|
||||
image = gtk_image_new_from_file (anim_filename);
|
||||
gtk_image_set_pixel_size (GTK_IMAGE (image), 30);
|
||||
gtk_grid_attach (GTK_GRID (grid), image, 2, 6, 1, 1);
|
||||
|
||||
/* produce high load */
|
||||
g_idle_add_full (G_PRIORITY_DEFAULT,
|
||||
idle_func, NULL, NULL);
|
||||
}
|
||||
|
||||
gtk_widget_show (window);
|
||||
|
||||
gtk_main ();
|
||||
|
||||
return 0;
|
||||
}
|
||||
+12
-23
@@ -5,9 +5,8 @@ static const char *entries[] = {
|
||||
};
|
||||
|
||||
static void
|
||||
drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer data)
|
||||
drag_begin (GtkDragSource *source,
|
||||
GtkWidget *widget)
|
||||
{
|
||||
GtkWidget *row;
|
||||
GtkAllocation alloc;
|
||||
@@ -19,26 +18,11 @@ drag_begin (GtkWidget *widget,
|
||||
|
||||
paintable = gtk_widget_paintable_new (row);
|
||||
gtk_widget_translate_coordinates (widget, row, 0, 0, &x, &y);
|
||||
gtk_drag_set_icon_paintable (drag, paintable, -x, -y);
|
||||
gtk_drag_source_set_icon (source, paintable, -x, -y);
|
||||
|
||||
g_object_unref (paintable);
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
drag_data_get (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
GtkSelectionData *selection_data,
|
||||
gpointer data)
|
||||
{
|
||||
gtk_selection_data_set (selection_data,
|
||||
g_intern_static_string ("GTK_LIST_BOX_ROW"),
|
||||
32,
|
||||
(const guchar *)&widget,
|
||||
sizeof (gpointer));
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
drag_data_received (GtkWidget *widget,
|
||||
GdkDrop *drop,
|
||||
@@ -69,7 +53,10 @@ static GtkWidget *
|
||||
create_row (const gchar *text)
|
||||
{
|
||||
GtkWidget *row, *box, *label, *image;
|
||||
GBytes *bytes;
|
||||
GdkContentProvider *content;
|
||||
GdkContentFormats *targets;
|
||||
GtkDragSource *source;
|
||||
|
||||
row = gtk_list_box_row_new ();
|
||||
image = gtk_image_new_from_icon_name ("open-menu-symbolic");
|
||||
@@ -81,11 +68,13 @@ create_row (const gchar *text)
|
||||
gtk_container_add (GTK_CONTAINER (box), label);
|
||||
gtk_container_add (GTK_CONTAINER (box), image);
|
||||
|
||||
targets = gdk_content_formats_new (entries, 1);
|
||||
bytes = g_bytes_new (&row, sizeof (gpointer));
|
||||
content = gdk_content_provider_new_for_bytes ("GTK_LIST_BOX_ROW", bytes);
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_MOVE);
|
||||
g_signal_connect (source, "drag-begin", G_CALLBACK (drag_begin), image);
|
||||
gtk_drag_source_attach (source, image, GDK_BUTTON1_MASK);
|
||||
|
||||
gtk_drag_source_set (image, GDK_BUTTON1_MASK, targets, GDK_ACTION_MOVE);
|
||||
g_signal_connect (image, "drag-begin", G_CALLBACK (drag_begin), NULL);
|
||||
g_signal_connect (image, "drag-data-get", G_CALLBACK (drag_data_get), NULL);
|
||||
targets = gdk_content_formats_new (entries, 1);
|
||||
|
||||
gtk_drag_dest_set (row, GTK_DEST_DEFAULT_ALL, targets, GDK_ACTION_MOVE);
|
||||
g_signal_connect (row, "drag-data-received", G_CALLBACK (drag_data_received), NULL);
|
||||
|
||||
@@ -90,21 +90,6 @@ on_page_reordered (GtkNotebook *notebook, GtkWidget *child, guint page_num, gpoi
|
||||
g_print ("page %d reordered\n", page_num);
|
||||
}
|
||||
|
||||
static void
|
||||
on_notebook_drag_begin (GtkWidget *widget,
|
||||
GdkDrag *drag,
|
||||
gpointer data)
|
||||
{
|
||||
guint page_num;
|
||||
|
||||
page_num = gtk_notebook_get_current_page (GTK_NOTEBOOK (widget));
|
||||
|
||||
if (page_num > 2)
|
||||
gtk_drag_set_icon_name (drag,
|
||||
(page_num % 2) ? "help-browser" : "process-stop",
|
||||
0, 0);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
remove_in_idle (gpointer data)
|
||||
{
|
||||
@@ -186,8 +171,6 @@ create_notebook (gchar **labels,
|
||||
|
||||
g_signal_connect (GTK_NOTEBOOK (notebook), "page-reordered",
|
||||
G_CALLBACK (on_page_reordered), NULL);
|
||||
g_signal_connect_after (G_OBJECT (notebook), "drag-begin",
|
||||
G_CALLBACK (on_notebook_drag_begin), NULL);
|
||||
return notebook;
|
||||
}
|
||||
|
||||
@@ -233,8 +216,6 @@ create_notebook_non_dragable_content (gchar **labels,
|
||||
|
||||
g_signal_connect (GTK_NOTEBOOK (notebook), "page-reordered",
|
||||
G_CALLBACK (on_page_reordered), NULL);
|
||||
g_signal_connect_after (G_OBJECT (notebook), "drag-begin",
|
||||
G_CALLBACK (on_notebook_drag_begin), NULL);
|
||||
return notebook;
|
||||
}
|
||||
|
||||
@@ -271,8 +252,6 @@ create_notebook_with_notebooks (gchar **labels,
|
||||
|
||||
g_signal_connect (GTK_NOTEBOOK (notebook), "page-reordered",
|
||||
G_CALLBACK (on_page_reordered), NULL);
|
||||
g_signal_connect_after (G_OBJECT (notebook), "drag-begin",
|
||||
G_CALLBACK (on_notebook_drag_begin), NULL);
|
||||
return notebook;
|
||||
}
|
||||
|
||||
|
||||
+6
-3
@@ -389,6 +389,8 @@ main (gint argc, gchar **argv)
|
||||
GtkWidget *hbox, *hbox1, *hbox2, *checkbox, *option_menu, *menu;
|
||||
gint i;
|
||||
GdkContentFormats *targets;
|
||||
GdkContentProvider *content;
|
||||
GtkDragSource *source;
|
||||
static const gchar *toolbar_styles[] = { "icons", "text", "both (vertical)",
|
||||
"both (horizontal)" };
|
||||
GtkToolItem *item;
|
||||
@@ -616,9 +618,10 @@ main (gint argc, gchar **argv)
|
||||
gtk_container_add (GTK_CONTAINER (hbox), checkbox);
|
||||
|
||||
targets = gdk_content_formats_new (target_table, G_N_ELEMENTS (target_table));
|
||||
gtk_drag_source_set (button, GDK_BUTTON1_MASK,
|
||||
targets,
|
||||
GDK_ACTION_MOVE);
|
||||
content = gdk_content_provider_new_for_bytes (target_table[0], g_bytes_new ("", 1));
|
||||
source = gtk_drag_source_new (content, GDK_ACTION_MOVE);
|
||||
g_object_unref (content);
|
||||
gtk_drag_source_attach (source, button, GDK_BUTTON1_MASK);
|
||||
gtk_drag_dest_set (toolbar, GTK_DEST_DEFAULT_DROP,
|
||||
targets,
|
||||
GDK_ACTION_MOVE);
|
||||
|
||||
Reference in New Issue
Block a user