]> Pileus Git - ~andy/gtk/blob - gtk/gtkclipboard.c
5b57f3d2adfa3eb93f666fc939e57400507ea219
[~andy/gtk] / gtk / gtkclipboard.c
1 /* GTK - The GTK+ Toolkit
2  * Copyright (C) 2000 Red Hat, Inc.
3  * Copyright (C) 2004 Nokia Corporation
4  *
5  * This library is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU Lesser General Public
7  * License as published by the Free Software Foundation; either
8  * version 2 of the License, or (at your option) any later version.
9  *
10  * This library is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  * Lesser General Public License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General Public
16  * License along with this library; if not, write to the
17  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18  * Boston, MA 02111-1307, USA.
19  *
20  * Global clipboard abstraction. 
21  */
22
23 #include "config.h"
24 #include <string.h>
25
26 #include "gtkclipboard.h"
27 #include "gtkinvisible.h"
28 #include "gtkmain.h"
29 #include "gtkmarshalers.h"
30 #include "gtktextbufferrichtext.h"
31 #include "gtkintl.h"
32 #include "gtkalias.h"
33
34 #ifdef GDK_WINDOWING_X11
35 #include "x11/gdkx.h"
36 #endif
37
38 #ifdef GDK_WINDOWING_WIN32
39 #include "win32/gdkwin32.h"
40 #endif
41
42 enum {
43   OWNER_CHANGE,
44   LAST_SIGNAL
45 };
46
47 typedef struct _GtkClipboardClass GtkClipboardClass;
48
49 typedef struct _RequestContentsInfo RequestContentsInfo;
50 typedef struct _RequestTextInfo RequestTextInfo;
51 typedef struct _RequestRichTextInfo RequestRichTextInfo;
52 typedef struct _RequestImageInfo RequestImageInfo;
53 typedef struct _RequestURIInfo RequestURIInfo;
54 typedef struct _RequestTargetsInfo RequestTargetsInfo;
55
56 struct _GtkClipboard 
57 {
58   GObject parent_instance;
59
60   GdkAtom selection;
61
62   GtkClipboardGetFunc get_func;
63   GtkClipboardClearFunc clear_func;
64   gpointer user_data;
65   gboolean have_owner;
66
67   guint32 timestamp;
68
69   gboolean have_selection;
70   GdkDisplay *display;
71
72   GdkAtom *cached_targets;
73   gint     n_cached_targets;
74
75   guint      notify_signal_id;
76   gboolean   storing_selection;
77   GMainLoop *store_loop;
78   guint      store_timeout;
79   gint       n_storable_targets;
80   GdkAtom   *storable_targets;
81 };
82
83 struct _GtkClipboardClass
84 {
85   GObjectClass parent_class;
86
87   void (*owner_change) (GtkClipboard        *clipboard,
88                         GdkEventOwnerChange *event);
89 };
90
91 struct _RequestContentsInfo
92 {
93   GtkClipboardReceivedFunc callback;
94   gpointer user_data;
95 };
96
97 struct _RequestTextInfo
98 {
99   GtkClipboardTextReceivedFunc callback;
100   gpointer user_data;
101 };
102
103 struct _RequestRichTextInfo
104 {
105   GtkClipboardRichTextReceivedFunc callback;
106   GdkAtom *atoms;
107   gint     n_atoms;
108   gint     current_atom;
109   gpointer user_data;
110 };
111
112 struct _RequestImageInfo
113 {
114   GtkClipboardImageReceivedFunc callback;
115   gpointer user_data;
116 };
117
118 struct _RequestURIInfo
119 {
120   GtkClipboardURIReceivedFunc callback;
121   gpointer user_data;
122 };
123
124 struct _RequestTargetsInfo
125 {
126   GtkClipboardTargetsReceivedFunc callback;
127   gpointer user_data;
128 };
129
130 static void gtk_clipboard_class_init   (GtkClipboardClass   *class);
131 static void gtk_clipboard_finalize     (GObject             *object);
132 static void gtk_clipboard_owner_change (GtkClipboard        *clipboard,
133                                         GdkEventOwnerChange *event);
134
135 static void          clipboard_unset      (GtkClipboard     *clipboard);
136 static void          selection_received   (GtkWidget        *widget,
137                                            GtkSelectionData *selection_data,
138                                            guint             time);
139 static GtkClipboard *clipboard_peek       (GdkDisplay       *display,
140                                            GdkAtom           selection,
141                                            gboolean          only_if_exists);
142 static GtkWidget *   get_clipboard_widget (GdkDisplay       *display);
143
144
145 enum {
146   TARGET_STRING,
147   TARGET_TEXT,
148   TARGET_COMPOUND_TEXT,
149   TARGET_UTF8_STRING,
150   TARGET_SAVE_TARGETS
151 };
152
153 static const gchar request_contents_key[] = "gtk-request-contents";
154 static GQuark request_contents_key_id = 0;
155
156 static const gchar clipboards_owned_key[] = "gtk-clipboards-owned";
157 static GQuark clipboards_owned_key_id = 0;
158
159 static guint         clipboard_signals[LAST_SIGNAL] = { 0 };
160
161 G_DEFINE_TYPE (GtkClipboard, gtk_clipboard, G_TYPE_OBJECT)
162
163 static void
164 gtk_clipboard_init (GtkClipboard *object)
165 {
166 }
167
168 static void
169 gtk_clipboard_class_init (GtkClipboardClass *class)
170 {
171   GObjectClass *gobject_class = G_OBJECT_CLASS (class);
172
173   gobject_class->finalize = gtk_clipboard_finalize;
174
175   class->owner_change = gtk_clipboard_owner_change;
176
177   /**
178    * GtkClipboard::owner-change:
179    * @clipboard: the #GtkClipboard on which the signal is emitted
180    * @event: the @GdkEventOwnerChange event 
181    *
182    * The ::owner-change signal is emitted when GTK+ receives an
183    * event that indicates that the ownership of the selection 
184    * associated with @clipboard has changed.
185    *
186    * Since: 2.6
187    */ 
188   clipboard_signals[OWNER_CHANGE] =
189     g_signal_new (I_("owner_change"),
190                   G_TYPE_FROM_CLASS (gobject_class),
191                   G_SIGNAL_RUN_FIRST,
192                   G_STRUCT_OFFSET (GtkClipboardClass, owner_change),
193                   NULL, NULL,
194                   _gtk_marshal_VOID__BOXED,
195                   G_TYPE_NONE, 1,
196                   GDK_TYPE_EVENT | G_SIGNAL_TYPE_STATIC_SCOPE);
197 }
198
199 static void
200 gtk_clipboard_finalize (GObject *object)
201 {
202   GtkClipboard *clipboard;
203   GtkWidget *clipboard_widget = NULL;
204   GSList *clipboards = NULL;
205
206   clipboard = GTK_CLIPBOARD (object);
207
208   if (clipboard->display)
209     {
210       clipboards = g_object_get_data (G_OBJECT (clipboard->display), "gtk-clipboard-list");
211
212       if (g_slist_index (clipboards, clipboard) >= 0)
213         g_warning ("GtkClipboard prematurely finalized");
214
215       clipboards = g_slist_remove (clipboards, clipboard);
216
217       g_object_set_data (G_OBJECT (clipboard->display), "gtk-clipboard-list", 
218                          clipboards);
219
220       /* don't use get_clipboard_widget() here because it would create the
221        * widget if it doesn't exist.
222        */
223       clipboard_widget = g_object_get_data (G_OBJECT (clipboard->display),
224                                             "gtk-clipboard-widget");
225     }
226
227   clipboard_unset (clipboard);
228
229   if (clipboard->store_loop && g_main_loop_is_running (clipboard->store_loop))
230     g_main_loop_quit (clipboard->store_loop);
231
232   if (clipboard->store_timeout != 0)
233     g_source_remove (clipboard->store_timeout);
234
235   if (clipboard->notify_signal_id != 0)
236     g_signal_handler_disconnect (clipboard_widget, clipboard->notify_signal_id);
237   
238   g_free (clipboard->storable_targets);
239
240   G_OBJECT_CLASS (gtk_clipboard_parent_class)->finalize (object);
241 }
242
243 static void
244 clipboard_display_closed (GdkDisplay   *display,
245                           gboolean      is_error,
246                           GtkClipboard *clipboard)
247 {
248   GSList *clipboards;
249
250   clipboards = g_object_get_data (G_OBJECT (display), "gtk-clipboard-list");
251   g_object_run_dispose (G_OBJECT (clipboard));
252   clipboards = g_slist_remove (clipboards, clipboard);
253   g_object_set_data (G_OBJECT (display), I_("gtk-clipboard-list"), clipboards);
254   g_object_unref (clipboard);
255 }
256
257 /**
258  * gtk_clipboard_get_for_display:
259  * @display: the display for which the clipboard is to be retrieved or created
260  * @selection: a #GdkAtom which identifies the clipboard
261  *             to use.
262  * 
263  * Returns the clipboard object for the given selection.
264  * Cut/copy/paste menu items and keyboard shortcuts should use
265  * the default clipboard, returned by passing %GDK_SELECTION_CLIPBOARD for @selection.
266  * (%GDK_NONE is supported as a synonym for GDK_SELECTION_CLIPBOARD
267  * for backwards compatibility reasons.)
268  * The currently-selected object or text should be provided on the clipboard
269  * identified by #GDK_SELECTION_PRIMARY. Cut/copy/paste menu items
270  * conceptually copy the contents of the #GDK_SELECTION_PRIMARY clipboard
271  * to the default clipboard, i.e. they copy the selection to what the
272  * user sees as the clipboard.
273  *
274  * (Passing #GDK_NONE is the same as using <literal>gdk_atom_intern
275  * ("CLIPBOARD", FALSE)</literal>. See <ulink
276  * url="http://www.freedesktop.org/Standards/clipboards-spec">
277  * http://www.freedesktop.org/Standards/clipboards-spec</ulink>
278  * for a detailed discussion of the "CLIPBOARD" vs. "PRIMARY"
279  * selections under the X window system. On Win32 the
280  * #GDK_SELECTION_PRIMARY clipboard is essentially ignored.)
281  *
282  * It's possible to have arbitrary named clipboards; if you do invent
283  * new clipboards, you should prefix the selection name with an
284  * underscore (because the ICCCM requires that nonstandard atoms are
285  * underscore-prefixed), and namespace it as well. For example,
286  * if your application called "Foo" has a special-purpose
287  * clipboard, you might call it "_FOO_SPECIAL_CLIPBOARD".
288  * 
289  * Return value: the appropriate clipboard object. If no
290  *             clipboard already exists, a new one will
291  *             be created. Once a clipboard object has
292  *             been created, it is persistent and, since
293  *             it is owned by GTK+, must not be freed or
294  *             unrefd.
295  *
296  * Since: 2.2
297  **/
298 GtkClipboard *
299 gtk_clipboard_get_for_display (GdkDisplay *display, 
300                                GdkAtom     selection)
301 {
302   g_return_val_if_fail (GDK_IS_DISPLAY (display), NULL);
303   g_return_val_if_fail (!display->closed, NULL);
304
305   return clipboard_peek (display, selection, FALSE);
306 }
307
308
309 /**
310  * gtk_clipboard_get():
311  * @selection: a #GdkAtom which identifies the clipboard
312  *             to use.
313  * 
314  * Returns the clipboard object for the given selection.
315  * See gtk_clipboard_get_for_display() for complete details.
316  * 
317  * Return value: the appropriate clipboard object. If no
318  *             clipboard already exists, a new one will
319  *             be created. Once a clipboard object has
320  *             been created, it is persistent and, since
321  *             it is owned by GTK+, must not be freed or
322  *             unrefd.
323  **/
324 GtkClipboard *
325 gtk_clipboard_get (GdkAtom selection)
326 {
327   return gtk_clipboard_get_for_display (gdk_display_get_default (), selection);
328 }
329
330 static void 
331 selection_get_cb (GtkWidget          *widget,
332                   GtkSelectionData   *selection_data,
333                   guint               info,
334                   guint               time)
335 {
336   GtkClipboard *clipboard = gtk_widget_get_clipboard (widget, selection_data->selection);
337
338   if (clipboard && clipboard->get_func)
339     clipboard->get_func (clipboard, selection_data, info, clipboard->user_data);
340 }
341
342 static gboolean
343 selection_clear_event_cb (GtkWidget         *widget,
344                           GdkEventSelection *event)
345 {
346   GtkClipboard *clipboard = gtk_widget_get_clipboard (widget, event->selection);
347
348   if (clipboard)
349     {
350       clipboard_unset (clipboard);
351
352       return TRUE;
353     }
354
355   return FALSE;
356 }
357
358 static GtkWidget *
359 make_clipboard_widget (GdkDisplay *display, 
360                        gboolean    provider)
361 {
362   GtkWidget *widget = gtk_invisible_new_for_screen (gdk_display_get_default_screen (display));
363
364   g_signal_connect (widget, "selection_received",
365                     G_CALLBACK (selection_received), NULL);
366
367   if (provider)
368     {
369       /* We need this for gdk_x11_get_server_time() */
370       gtk_widget_add_events (widget, GDK_PROPERTY_CHANGE_MASK);
371       
372       g_signal_connect (widget, "selection_get",
373                         G_CALLBACK (selection_get_cb), NULL);
374       g_signal_connect (widget, "selection_clear_event",
375                         G_CALLBACK (selection_clear_event_cb), NULL);
376     }
377
378   return widget;
379 }
380
381 static GtkWidget *
382 get_clipboard_widget (GdkDisplay *display)
383 {
384   GtkWidget *clip_widget = g_object_get_data (G_OBJECT (display), "gtk-clipboard-widget");
385   if (!clip_widget)
386     {
387       clip_widget = make_clipboard_widget (display, TRUE);
388       g_object_set_data (G_OBJECT (display), I_("gtk-clipboard-widget"), clip_widget);
389     }
390
391   return clip_widget;
392 }
393
394 /* This function makes a very good guess at what the correct
395  * timestamp for a selection request should be. If there is
396  * a currently processed event, it uses the timestamp for that
397  * event, otherwise it uses the current server time. However,
398  * if the time resulting from that is older than the time used
399  * last time, it uses the time used last time instead.
400  *
401  * In order implement this correctly, we never use CurrentTime,
402  * but actually retrieve the actual timestamp from the server.
403  * This is a little slower but allows us to make the guarantee
404  * that the times used by this application will always ascend
405  * and we won't get selections being rejected just because
406  * we are using a correct timestamp from an event, but used
407  * CurrentTime previously.
408  */
409 static guint32
410 clipboard_get_timestamp (GtkClipboard *clipboard)
411 {
412   GtkWidget *clipboard_widget = get_clipboard_widget (clipboard->display);
413   guint32 timestamp = gtk_get_current_event_time ();
414
415   if (timestamp == GDK_CURRENT_TIME)
416     {
417 #ifdef GDK_WINDOWING_X11
418       timestamp = gdk_x11_get_server_time (clipboard_widget->window);
419 #elif defined GDK_WINDOWING_WIN32
420       timestamp = GetMessageTime ();
421 #endif
422     }
423   else
424     {
425       if (clipboard->timestamp != GDK_CURRENT_TIME)
426         {
427           /* Check to see if clipboard->timestamp is newer than
428            * timestamp, accounting for wraparound.
429            */
430
431           guint32 max = timestamp + 0x80000000;
432
433           if ((max > timestamp &&
434                (clipboard->timestamp > timestamp &&
435                 clipboard->timestamp <= max)) ||
436               (max <= timestamp &&
437                (clipboard->timestamp > timestamp ||
438                 clipboard->timestamp <= max)))
439             {
440               timestamp = clipboard->timestamp;
441             }
442         }
443     }
444
445   clipboard->timestamp = timestamp;
446
447   return timestamp;
448 }
449
450 static void
451 clipboard_owner_destroyed (gpointer data)
452 {
453   GSList *clipboards = data;
454   GSList *tmp_list;
455
456   tmp_list = clipboards;
457   while (tmp_list)
458     {
459       GtkClipboard *clipboard = tmp_list->data;
460
461       clipboard->get_func = NULL;
462       clipboard->clear_func = NULL;
463       clipboard->user_data = NULL;
464       clipboard->have_owner = FALSE;
465
466       gtk_clipboard_clear (clipboard);
467
468       tmp_list = tmp_list->next;
469     }
470   
471   g_slist_free (clipboards);
472 }
473
474 static void
475 clipboard_add_owner_notify (GtkClipboard *clipboard)
476 {
477   if (!clipboards_owned_key_id)
478     clipboards_owned_key_id = g_quark_from_static_string (clipboards_owned_key);
479   
480   if (clipboard->have_owner)
481     g_object_set_qdata_full (clipboard->user_data, clipboards_owned_key_id,
482                              g_slist_prepend (g_object_steal_qdata (clipboard->user_data,
483                                                                     clipboards_owned_key_id),
484                                               clipboard),
485                              clipboard_owner_destroyed);
486 }
487
488 static void
489 clipboard_remove_owner_notify (GtkClipboard *clipboard)
490 {
491   if (clipboard->have_owner)
492      g_object_set_qdata_full (clipboard->user_data, clipboards_owned_key_id,
493                               g_slist_remove (g_object_steal_qdata (clipboard->user_data,
494                                                                     clipboards_owned_key_id),
495                                               clipboard),
496                               clipboard_owner_destroyed);
497 }
498           
499 static gboolean
500 gtk_clipboard_set_contents (GtkClipboard         *clipboard,
501                             const GtkTargetEntry *targets,
502                             guint                 n_targets,
503                             GtkClipboardGetFunc   get_func,
504                             GtkClipboardClearFunc clear_func,
505                             gpointer              user_data,
506                             gboolean              have_owner)
507 {
508   GtkWidget *clipboard_widget = get_clipboard_widget (clipboard->display);
509
510   if (gtk_selection_owner_set_for_display (clipboard->display,
511                                            clipboard_widget,
512                                            clipboard->selection,
513                                            clipboard_get_timestamp (clipboard)))
514     {
515       clipboard->have_selection = TRUE;
516
517       if (!(clipboard->have_owner && have_owner) ||
518           clipboard->user_data != user_data)
519         {
520           clipboard_unset (clipboard);
521
522           if (clipboard->get_func)
523             {
524               /* Calling unset() caused the clipboard contents to be reset!
525                * Avoid leaking and return 
526                */
527               if (!(clipboard->have_owner && have_owner) ||
528                   clipboard->user_data != user_data)
529                 {
530                   (*clear_func) (clipboard, user_data);
531                   return FALSE;
532                 }
533               else
534                 return TRUE;
535             }
536           else
537             {
538               clipboard->user_data = user_data;
539               clipboard->have_owner = have_owner;
540               if (have_owner)
541                 clipboard_add_owner_notify (clipboard);
542             }
543           
544         }
545
546       clipboard->get_func = get_func;
547       clipboard->clear_func = clear_func;
548
549       gtk_selection_clear_targets (clipboard_widget, clipboard->selection);
550       gtk_selection_add_targets (clipboard_widget, clipboard->selection,
551                                  targets, n_targets);
552
553       return TRUE;
554     }
555   else
556     return FALSE;
557 }
558
559 /**
560  * gtk_clipboard_set_with_data:
561  * @clipboard:  a #GtkClipboard
562  * @targets:    array containing information about the available forms for the
563  *              clipboard data
564  * @n_targets:  number of elements in @targets
565  * @get_func:   function to call to get the actual clipboard data
566  * @clear_func: when the clipboard contents are set again, this function will
567  *              be called, and @get_func will not be subsequently called.
568  * @user_data:  user data to pass to @get_func and @clear_func.
569  * 
570  * Virtually sets the contents of the specified clipboard by providing
571  * a list of supported formats for the clipboard data and a function
572  * to call to get the actual data when it is requested.
573  * 
574  * Return value: %TRUE if setting the clipboard data succeeded. If setting
575  *               the clipboard data failed the provided callback functions
576  *               will be ignored.
577  **/
578 gboolean
579 gtk_clipboard_set_with_data (GtkClipboard          *clipboard,
580                              const GtkTargetEntry  *targets,
581                              guint                  n_targets,
582                              GtkClipboardGetFunc    get_func,
583                              GtkClipboardClearFunc  clear_func,
584                              gpointer               user_data)
585 {
586   g_return_val_if_fail (clipboard != NULL, FALSE);
587   g_return_val_if_fail (targets != NULL, FALSE);
588   g_return_val_if_fail (get_func != NULL, FALSE);
589
590   return gtk_clipboard_set_contents (clipboard, targets, n_targets,
591                                      get_func, clear_func, user_data,
592                                      FALSE);
593 }
594
595 /**
596  * gtk_clipboard_set_with_owner:
597  * @clipboard:  a #GtkClipboard
598  * @targets:    array containing information about the available forms for the
599  *              clipboard data
600  * @n_targets:  number of elements in @targets
601  * @get_func:   function to call to get the actual clipboard data
602  * @clear_func: when the clipboard contents are set again, this function will
603  *              be called, and @get_func will not be subsequently called.
604  * @owner:      an object that "owns" the data. This object will be passed
605  *              to the callbacks when called. 
606  * 
607  * Virtually sets the contents of the specified clipboard by providing
608  * a list of supported formats for the clipboard data and a function
609  * to call to get the actual data when it is requested.
610  *
611  * The difference between this function and gtk_clipboard_set_with_data()
612  * is that instead of an generic @user_data pointer, a #GObject is passed
613  * in. 
614  * 
615  * Return value: %TRUE if setting the clipboard data succeeded. If setting
616  *               the clipboard data failed the provided callback functions
617  *               will be ignored.
618  **/
619 gboolean
620 gtk_clipboard_set_with_owner (GtkClipboard          *clipboard,
621                               const GtkTargetEntry  *targets,
622                               guint                  n_targets,
623                               GtkClipboardGetFunc    get_func,
624                               GtkClipboardClearFunc  clear_func,
625                               GObject               *owner)
626 {
627   g_return_val_if_fail (clipboard != NULL, FALSE);
628   g_return_val_if_fail (targets != NULL, FALSE);
629   g_return_val_if_fail (get_func != NULL, FALSE);
630   g_return_val_if_fail (G_IS_OBJECT (owner), FALSE);
631
632   return gtk_clipboard_set_contents (clipboard, targets, n_targets,
633                                      get_func, clear_func, owner,
634                                      TRUE);
635 }
636
637 /**
638  * gtk_clipboard_get_owner:
639  * @clipboard: a #GtkClipboard
640  * 
641  * If the clipboard contents callbacks were set with 
642  * gtk_clipboard_set_with_owner(), and the gtk_clipboard_set_with_data() or 
643  * gtk_clipboard_clear() has not subsequently called, returns the owner set 
644  * by gtk_clipboard_set_with_owner().
645  * 
646  * Return value: the owner of the clipboard, if any; otherwise %NULL.
647  **/
648 GObject *
649 gtk_clipboard_get_owner (GtkClipboard *clipboard)
650 {
651   g_return_val_if_fail (clipboard != NULL, NULL);
652
653   if (clipboard->have_owner)
654     return clipboard->user_data;
655   else
656     return NULL;
657 }
658
659 static void
660 clipboard_unset (GtkClipboard *clipboard)
661 {
662   GtkClipboardClearFunc old_clear_func;
663   gpointer old_data;
664   gboolean old_have_owner;
665   gint old_n_storable_targets;
666   
667   old_clear_func = clipboard->clear_func;
668   old_data = clipboard->user_data;
669   old_have_owner = clipboard->have_owner;
670   old_n_storable_targets = clipboard->n_storable_targets;
671   
672   if (old_have_owner)
673     {
674       clipboard_remove_owner_notify (clipboard);
675       clipboard->have_owner = FALSE;
676     }
677
678   clipboard->n_storable_targets = -1;
679   g_free (clipboard->storable_targets);
680   clipboard->storable_targets = NULL;
681       
682   clipboard->get_func = NULL;
683   clipboard->clear_func = NULL;
684   clipboard->user_data = NULL;
685   
686   if (old_clear_func)
687     old_clear_func (clipboard, old_data);
688
689   /* If we've transferred the clipboard data to the manager,
690    * unref the owner
691    */
692   if (old_have_owner &&
693       old_n_storable_targets != -1)
694     g_object_unref (old_data);
695 }
696
697 /**
698  * gtk_clipboard_clear:
699  * @clipboard:  a #GtkClipboard
700  * 
701  * Clears the contents of the clipboard. Generally this should only
702  * be called between the time you call gtk_clipboard_set_with_owner()
703  * or gtk_clipboard_set_with_data(),
704  * and when the @clear_func you supplied is called. Otherwise, the
705  * clipboard may be owned by someone else.
706  **/
707 void
708 gtk_clipboard_clear (GtkClipboard *clipboard)
709 {
710   g_return_if_fail (clipboard != NULL);
711
712   if (clipboard->have_selection)
713     gtk_selection_owner_set_for_display (clipboard->display, 
714                                          NULL,
715                                          clipboard->selection,
716                                          clipboard_get_timestamp (clipboard));
717 }
718
719 static void 
720 text_get_func (GtkClipboard     *clipboard,
721                GtkSelectionData *selection_data,
722                guint             info,
723                gpointer          data)
724 {
725   gtk_selection_data_set_text (selection_data, data, -1);
726 }
727
728 static void 
729 text_clear_func (GtkClipboard *clipboard,
730                  gpointer      data)
731 {
732   g_free (data);
733 }
734
735
736 /**
737  * gtk_clipboard_set_text:
738  * @clipboard: a #GtkClipboard object
739  * @text:      a UTF-8 string.
740  * @len:       length of @text, in bytes, or -1, in which case
741  *             the length will be determined with <function>strlen()</function>.
742  * 
743  * Sets the contents of the clipboard to the given UTF-8 string. GTK+ will
744  * make a copy of the text and take responsibility for responding
745  * for requests for the text, and for converting the text into
746  * the requested format.
747  **/
748 void 
749 gtk_clipboard_set_text (GtkClipboard *clipboard,
750                         const gchar  *text,
751                         gint          len)
752 {
753   GtkTargetList *list;
754   GtkTargetEntry *targets;
755   gint n_targets;
756
757   g_return_if_fail (clipboard != NULL);
758   g_return_if_fail (text != NULL);
759
760   list = gtk_target_list_new (NULL, 0);
761   gtk_target_list_add_text_targets (list, 0);
762
763   targets = gtk_target_table_new_from_list (list, &n_targets);
764   
765   if (len < 0)
766     len = strlen (text);
767   
768   gtk_clipboard_set_with_data (clipboard, 
769                                targets, n_targets,
770                                text_get_func, text_clear_func,
771                                g_strndup (text, len));
772   gtk_clipboard_set_can_store (clipboard, NULL, 0);
773
774   gtk_target_table_free (targets, n_targets);
775   gtk_target_list_unref (list);
776 }
777
778 static void 
779 pixbuf_get_func (GtkClipboard     *clipboard,
780                  GtkSelectionData *selection_data,
781                  guint             info,
782                  gpointer          data)
783 {
784   gtk_selection_data_set_pixbuf (selection_data, data);
785 }
786
787 static void 
788 pixbuf_clear_func (GtkClipboard *clipboard,
789                    gpointer      data)
790 {
791   g_object_unref (data);
792 }
793
794 /**
795  * gtk_clipboard_set_image:
796  * @clipboard: a #GtkClipboard object
797  * @pixbuf:    a #GdkPixbuf 
798  * 
799  * Sets the contents of the clipboard to the given #GdkPixbuf. 
800  * GTK+ will take responsibility for responding for requests 
801  * for the image, and for converting the image into the 
802  * requested format.
803  * 
804  * Since: 2.6
805  **/
806 void
807 gtk_clipboard_set_image (GtkClipboard *clipboard,
808                           GdkPixbuf    *pixbuf)
809 {
810   GtkTargetList *list;
811   GtkTargetEntry *targets;
812   gint n_targets;
813
814   g_return_if_fail (clipboard != NULL);
815   g_return_if_fail (GDK_IS_PIXBUF (pixbuf));
816
817   list = gtk_target_list_new (NULL, 0);
818   gtk_target_list_add_image_targets (list, 0, TRUE);
819
820   targets = gtk_target_table_new_from_list (list, &n_targets);
821
822   gtk_clipboard_set_with_data (clipboard, 
823                                targets, n_targets,
824                                pixbuf_get_func, pixbuf_clear_func,
825                                g_object_ref (pixbuf));
826   gtk_clipboard_set_can_store (clipboard, NULL, 0);
827
828   gtk_target_table_free (targets, n_targets);
829   gtk_target_list_unref (list);
830 }
831
832 static void
833 set_request_contents_info (GtkWidget           *widget,
834                            RequestContentsInfo *info)
835 {
836   if (!request_contents_key_id)
837     request_contents_key_id = g_quark_from_static_string (request_contents_key);
838
839   g_object_set_qdata (G_OBJECT (widget), request_contents_key_id, info);
840 }
841
842 static RequestContentsInfo *
843 get_request_contents_info (GtkWidget *widget)
844 {
845   if (!request_contents_key_id)
846     return NULL;
847   else
848     return g_object_get_qdata (G_OBJECT (widget), request_contents_key_id);
849 }
850
851 static void 
852 selection_received (GtkWidget            *widget,
853                     GtkSelectionData     *selection_data,
854                     guint                 time)
855 {
856   RequestContentsInfo *request_info = get_request_contents_info (widget);
857   set_request_contents_info (widget, NULL);
858   
859   request_info->callback (gtk_widget_get_clipboard (widget, selection_data->selection), 
860                           selection_data,
861                           request_info->user_data);
862
863   g_free (request_info);
864
865   if (widget != get_clipboard_widget (gtk_widget_get_display (widget)))
866     gtk_widget_destroy (widget);
867 }
868
869 /**
870  * gtk_clipboard_request_contents:
871  * @clipboard: a #GtkClipboard
872  * @target:    an atom representing the form into which the clipboard
873  *             owner should convert the selection.
874  * @callback:  A function to call when the results are received
875  *             (or the retrieval fails). If the retrieval fails
876  *             the length field of @selection_data will be
877  *             negative.
878  * @user_data: user data to pass to @callback
879  * 
880  * Requests the contents of clipboard as the given target.
881  * When the results of the result are later received the supplied callback
882  * will be called.
883  **/
884 void 
885 gtk_clipboard_request_contents (GtkClipboard            *clipboard,
886                                 GdkAtom                  target,
887                                 GtkClipboardReceivedFunc callback,
888                                 gpointer                 user_data)
889 {
890   RequestContentsInfo *info;
891   GtkWidget *widget;
892   GtkWidget *clipboard_widget;
893
894   g_return_if_fail (clipboard != NULL);
895   g_return_if_fail (target != GDK_NONE);
896   g_return_if_fail (callback != NULL);
897   
898   clipboard_widget = get_clipboard_widget (clipboard->display);
899
900   if (get_request_contents_info (clipboard_widget))
901     widget = make_clipboard_widget (clipboard->display, FALSE);
902   else
903     widget = clipboard_widget;
904
905   info = g_new (RequestContentsInfo, 1);
906   info->callback = callback;
907   info->user_data = user_data;
908
909   set_request_contents_info (widget, info);
910
911   gtk_selection_convert (widget, clipboard->selection, target,
912                          clipboard_get_timestamp (clipboard));
913 }
914
915 static void 
916 request_text_received_func (GtkClipboard     *clipboard,
917                             GtkSelectionData *selection_data,
918                             gpointer          data)
919 {
920   RequestTextInfo *info = data;
921   gchar *result = NULL;
922
923   result = (gchar *) gtk_selection_data_get_text (selection_data);
924
925   if (!result)
926     {
927       /* If we asked for UTF8 and didn't get it, try compound_text;
928        * if we asked for compound_text and didn't get it, try string;
929        * If we asked for anything else and didn't get it, give up.
930        */
931       if (selection_data->target == gdk_atom_intern_static_string ("UTF8_STRING"))
932         {
933           gtk_clipboard_request_contents (clipboard,
934                                           gdk_atom_intern_static_string ("COMPOUND_TEXT"), 
935                                           request_text_received_func, info);
936           return;
937         }
938       else if (selection_data->target == gdk_atom_intern_static_string ("COMPOUND_TEXT"))
939         {
940           gtk_clipboard_request_contents (clipboard,
941                                           GDK_TARGET_STRING, 
942                                           request_text_received_func, info);
943           return;
944         }
945     }
946
947   info->callback (clipboard, result, info->user_data);
948   g_free (info);
949   g_free (result);
950 }
951
952 /**
953  * gtk_clipboard_request_text:
954  * @clipboard: a #GtkClipboard
955  * @callback:  a function to call when the text is received,
956  *             or the retrieval fails. (It will always be called
957  *             one way or the other.)
958  * @user_data: user data to pass to @callback.
959  * 
960  * Requests the contents of the clipboard as text. When the text is
961  * later received, it will be converted to UTF-8 if necessary, and
962  * @callback will be called. 
963  *
964  * The @text parameter to @callback will contain the resulting text if
965  * the request succeeded, or %NULL if it failed. This could happen for
966  * various reasons, in particular if the clipboard was empty or if the
967  * contents of the clipboard could not be converted into text form.
968  **/
969 void 
970 gtk_clipboard_request_text (GtkClipboard                *clipboard,
971                             GtkClipboardTextReceivedFunc callback,
972                             gpointer                     user_data)
973 {
974   RequestTextInfo *info;
975   
976   g_return_if_fail (clipboard != NULL);
977   g_return_if_fail (callback != NULL);
978   
979   info = g_new (RequestTextInfo, 1);
980   info->callback = callback;
981   info->user_data = user_data;
982
983   gtk_clipboard_request_contents (clipboard, gdk_atom_intern_static_string ("UTF8_STRING"),
984                                   request_text_received_func,
985                                   info);
986 }
987
988 static void
989 request_rich_text_received_func (GtkClipboard     *clipboard,
990                                  GtkSelectionData *selection_data,
991                                  gpointer          data)
992 {
993   RequestRichTextInfo *info = data;
994   guint8 *result = NULL;
995   gsize length = 0;
996
997   result = selection_data->data;
998   length = selection_data->length;
999
1000   info->current_atom++;
1001
1002   if ((!result || length < 1) && (info->current_atom < info->n_atoms))
1003     {
1004       gtk_clipboard_request_contents (clipboard, info->atoms[info->current_atom],
1005                                       request_rich_text_received_func,
1006                                       info);
1007       return;
1008     }
1009
1010   info->callback (clipboard, selection_data->target, result, length,
1011                   info->user_data);
1012   g_free (info->atoms);
1013   g_free (info);
1014 }
1015
1016 /**
1017  * gtk_clipboard_request_rich_text:
1018  * @clipboard: a #GtkClipboard
1019  * @buffer:    a #GtkTextBuffer
1020  * @callback:  a function to call when the text is received,
1021  *             or the retrieval fails. (It will always be called
1022  *             one way or the other.)
1023  * @user_data: user data to pass to @callback.
1024  *
1025  * Requests the contents of the clipboard as rich text. When the rich
1026  * text is later received, @callback will be called.
1027  *
1028  * The @text parameter to @callback will contain the resulting rich
1029  * text if the request succeeded, or %NULL if it failed. The @length
1030  * parameter will contain @text's length. This function can fail for
1031  * various reasons, in particular if the clipboard was empty or if the
1032  * contents of the clipboard could not be converted into rich text form.
1033  *
1034  * Since: 2.10
1035  **/
1036 void
1037 gtk_clipboard_request_rich_text (GtkClipboard                    *clipboard,
1038                                  GtkTextBuffer                   *buffer,
1039                                  GtkClipboardRichTextReceivedFunc callback,
1040                                  gpointer                         user_data)
1041 {
1042   RequestRichTextInfo *info;
1043
1044   g_return_if_fail (clipboard != NULL);
1045   g_return_if_fail (GTK_IS_TEXT_BUFFER (buffer));
1046   g_return_if_fail (callback != NULL);
1047
1048   info = g_new (RequestRichTextInfo, 1);
1049   info->callback = callback;
1050   info->atoms = NULL;
1051   info->n_atoms = 0;
1052   info->current_atom = 0;
1053   info->user_data = user_data;
1054
1055   info->atoms = gtk_text_buffer_get_deserialize_formats (buffer, &info->n_atoms);
1056
1057   gtk_clipboard_request_contents (clipboard, info->atoms[info->current_atom],
1058                                   request_rich_text_received_func,
1059                                   info);
1060 }
1061
1062 static void 
1063 request_image_received_func (GtkClipboard     *clipboard,
1064                              GtkSelectionData *selection_data,
1065                              gpointer          data)
1066 {
1067   RequestImageInfo *info = data;
1068   GdkPixbuf *result = NULL;
1069
1070   result = gtk_selection_data_get_pixbuf (selection_data);
1071
1072   if (!result)
1073     {
1074       /* If we asked for image/png and didn't get it, try image/jpeg;
1075        * if we asked for image/jpeg and didn't get it, try image/gif;
1076        * if we asked for image/gif and didn't get it, try image/bmp;
1077        * If we asked for anything else and didn't get it, give up.
1078        */
1079       if (selection_data->target == gdk_atom_intern_static_string ("image/png"))
1080         {
1081           gtk_clipboard_request_contents (clipboard,
1082                                           gdk_atom_intern_static_string ("image/jpeg"), 
1083                                           request_image_received_func, info);
1084           return;
1085         }
1086       else if (selection_data->target == gdk_atom_intern_static_string ("image/jpeg"))
1087         {
1088           gtk_clipboard_request_contents (clipboard,
1089                                           gdk_atom_intern_static_string ("image/gif"), 
1090                                           request_image_received_func, info);
1091           return;
1092         }
1093       else if (selection_data->target == gdk_atom_intern_static_string ("image/gif"))
1094         {
1095           gtk_clipboard_request_contents (clipboard,
1096                                           gdk_atom_intern_static_string ("image/bmp"), 
1097                                           request_image_received_func, info);
1098           return;
1099         }
1100     }
1101
1102   info->callback (clipboard, result, info->user_data);
1103   g_free (info);
1104
1105   if (result)
1106     g_object_unref (result);
1107 }
1108
1109 /**
1110  * gtk_clipboard_request_image:
1111  * @clipboard: a #GtkClipboard
1112  * @callback:  a function to call when the image is received,
1113  *             or the retrieval fails. (It will always be called
1114  *             one way or the other.)
1115  * @user_data: user data to pass to @callback.
1116  * 
1117  * Requests the contents of the clipboard as image. When the image is
1118  * later received, it will be converted to a #GdkPixbuf, and
1119  * @callback will be called. 
1120  *
1121  * The @pixbuf parameter to @callback will contain the resulting 
1122  * #GdkPixbuf if the request succeeded, or %NULL if it failed. This 
1123  * could happen for various reasons, in particular if the clipboard 
1124  * was empty or if the contents of the clipboard could not be 
1125  * converted into an image.
1126  *
1127  * Since: 2.6
1128  **/
1129 void 
1130 gtk_clipboard_request_image (GtkClipboard                  *clipboard,
1131                              GtkClipboardImageReceivedFunc  callback,
1132                              gpointer                       user_data)
1133 {
1134   RequestImageInfo *info;
1135   
1136   g_return_if_fail (clipboard != NULL);
1137   g_return_if_fail (callback != NULL);
1138   
1139   info = g_new (RequestImageInfo, 1);
1140   info->callback = callback;
1141   info->user_data = user_data;
1142
1143   gtk_clipboard_request_contents (clipboard, 
1144                                   gdk_atom_intern_static_string ("image/png"),
1145                                   request_image_received_func,
1146                                   info);
1147 }
1148
1149 static void 
1150 request_uris_received_func (GtkClipboard     *clipboard,
1151                             GtkSelectionData *selection_data,
1152                             gpointer          data)
1153 {
1154   RequestURIInfo *info = data;
1155   gchar **uris;
1156
1157   uris = gtk_selection_data_get_uris (selection_data);
1158   info->callback (clipboard, uris, info->user_data);
1159   g_strfreev (uris);
1160
1161   g_slice_free (RequestURIInfo, info);
1162 }
1163
1164 /**
1165  * gtk_clipboard_request_uris:
1166  * @clipboard: a #GtkClipboard
1167  * @callback:  a function to call when the URIs are received,
1168  *             or the retrieval fails. (It will always be called
1169  *             one way or the other.)
1170  * @user_data: user data to pass to @callback.
1171  * 
1172  * Requests the contents of the clipboard as URIs. When the URIs are
1173  * later received @callback will be called.
1174  *
1175  * The @uris parameter to @callback will contain the resulting array of
1176  * URIs if the request succeeded, or %NULL if it failed. This could happen
1177  * for various reasons, in particular if the clipboard was empty or if the
1178  * contents of the clipboard could not be converted into URI form.
1179  *
1180  * Since: 2.14
1181  **/
1182 void 
1183 gtk_clipboard_request_uris (GtkClipboard                *clipboard,
1184                             GtkClipboardURIReceivedFunc  callback,
1185                             gpointer                     user_data)
1186 {
1187   RequestURIInfo *info;
1188   
1189   g_return_if_fail (clipboard != NULL);
1190   g_return_if_fail (callback != NULL);
1191   
1192   info = g_slice_new (RequestURIInfo);
1193   info->callback = callback;
1194   info->user_data = user_data;
1195
1196   gtk_clipboard_request_contents (clipboard, gdk_atom_intern_static_string ("text/uri-list"),
1197                                   request_uris_received_func,
1198                                   info);
1199 }
1200
1201 static void 
1202 request_targets_received_func (GtkClipboard     *clipboard,
1203                                GtkSelectionData *selection_data,
1204                                gpointer          data)
1205 {
1206   RequestTargetsInfo *info = data;
1207   GdkAtom *targets = NULL;
1208   gint n_targets = 0;
1209
1210   gtk_selection_data_get_targets (selection_data, &targets, &n_targets);
1211
1212   info->callback (clipboard, targets, n_targets, info->user_data);
1213
1214   g_free (info);
1215   g_free (targets);
1216 }
1217
1218 /**
1219  * gtk_clipboard_request_targets:
1220  * @clipboard: a #GtkClipboard
1221  * @callback:  a function to call when the targets are received,
1222  *             or the retrieval fails. (It will always be called
1223  *             one way or the other.)
1224  * @user_data: user data to pass to @callback.
1225  * 
1226  * Requests the contents of the clipboard as list of supported targets. 
1227  * When the list is later received, @callback will be called. 
1228  *
1229  * The @targets parameter to @callback will contain the resulting targets if
1230  * the request succeeded, or %NULL if it failed.
1231  *
1232  * Since: 2.4
1233  **/
1234 void 
1235 gtk_clipboard_request_targets (GtkClipboard                *clipboard,
1236                                GtkClipboardTargetsReceivedFunc callback,
1237                                gpointer                     user_data)
1238 {
1239   RequestTargetsInfo *info;
1240   
1241   g_return_if_fail (clipboard != NULL);
1242   g_return_if_fail (callback != NULL);
1243
1244   /* If the display supports change notification we cache targets */
1245   if (gdk_display_supports_selection_notification (gtk_clipboard_get_display (clipboard)) &&
1246       clipboard->n_cached_targets != -1)
1247     {
1248       (* callback) (clipboard, clipboard->cached_targets, clipboard->n_cached_targets, user_data);
1249       return;
1250     }
1251   
1252   info = g_new (RequestTargetsInfo, 1);
1253   info->callback = callback;
1254   info->user_data = user_data;
1255
1256   gtk_clipboard_request_contents (clipboard, gdk_atom_intern_static_string ("TARGETS"),
1257                                   request_targets_received_func,
1258                                   info);
1259 }
1260
1261 typedef struct
1262 {
1263   GMainLoop *loop;
1264   gpointer data;
1265   GdkAtom format; /* used by rich text */
1266   gsize length; /* used by rich text */
1267 } WaitResults;
1268
1269 static void 
1270 clipboard_received_func (GtkClipboard     *clipboard,
1271                          GtkSelectionData *selection_data,
1272                          gpointer          data)
1273 {
1274   WaitResults *results = data;
1275
1276   if (selection_data->length >= 0)
1277     results->data = gtk_selection_data_copy (selection_data);
1278   
1279   g_main_loop_quit (results->loop);
1280 }
1281
1282 /**
1283  * gtk_clipboard_wait_for_contents:
1284  * @clipboard: a #GtkClipboard
1285  * @target: an atom representing the form into which the clipboard
1286  *          owner should convert the selection.
1287  * 
1288  * Requests the contents of the clipboard using the given target.
1289  * This function waits for the data to be received using the main 
1290  * loop, so events, timeouts, etc, may be dispatched during the wait.
1291  * 
1292  * Return value: a newly-allocated #GtkSelectionData object or %NULL
1293  *               if retrieving the given target failed. If non-%NULL,
1294  *               this value must be freed with gtk_selection_data_free() 
1295  *               when you are finished with it.
1296  **/
1297 GtkSelectionData *
1298 gtk_clipboard_wait_for_contents (GtkClipboard *clipboard,
1299                                  GdkAtom       target)
1300 {
1301   WaitResults results;
1302
1303   g_return_val_if_fail (clipboard != NULL, NULL);
1304   g_return_val_if_fail (target != GDK_NONE, NULL);
1305   
1306   results.data = NULL;
1307   results.loop = g_main_loop_new (NULL, TRUE);
1308
1309   gtk_clipboard_request_contents (clipboard, target, 
1310                                   clipboard_received_func,
1311                                   &results);
1312
1313   if (g_main_loop_is_running (results.loop))
1314     {
1315       GDK_THREADS_LEAVE ();
1316       g_main_loop_run (results.loop);
1317       GDK_THREADS_ENTER ();
1318     }
1319
1320   g_main_loop_unref (results.loop);
1321
1322   return results.data;
1323 }
1324
1325 static void 
1326 clipboard_text_received_func (GtkClipboard *clipboard,
1327                               const gchar  *text,
1328                               gpointer      data)
1329 {
1330   WaitResults *results = data;
1331
1332   results->data = g_strdup (text);
1333   g_main_loop_quit (results->loop);
1334 }
1335
1336 /**
1337  * gtk_clipboard_wait_for_text:
1338  * @clipboard: a #GtkClipboard
1339  * 
1340  * Requests the contents of the clipboard as text and converts
1341  * the result to UTF-8 if necessary. This function waits for
1342  * the data to be received using the main loop, so events,
1343  * timeouts, etc, may be dispatched during the wait.
1344  * 
1345  * Return value: a newly-allocated UTF-8 string which must
1346  *               be freed with g_free(), or %NULL if retrieving
1347  *               the selection data failed. (This could happen
1348  *               for various reasons, in particular if the
1349  *               clipboard was empty or if the contents of the
1350  *               clipboard could not be converted into text form.)
1351  **/
1352 gchar *
1353 gtk_clipboard_wait_for_text (GtkClipboard *clipboard)
1354 {
1355   WaitResults results;
1356
1357   g_return_val_if_fail (clipboard != NULL, NULL);
1358   
1359   results.data = NULL;
1360   results.loop = g_main_loop_new (NULL, TRUE);
1361
1362   gtk_clipboard_request_text (clipboard,
1363                               clipboard_text_received_func,
1364                               &results);
1365
1366   if (g_main_loop_is_running (results.loop))
1367     {
1368       GDK_THREADS_LEAVE ();
1369       g_main_loop_run (results.loop);
1370       GDK_THREADS_ENTER ();
1371     }
1372
1373   g_main_loop_unref (results.loop);
1374
1375   return results.data;
1376 }
1377
1378 static void
1379 clipboard_rich_text_received_func (GtkClipboard *clipboard,
1380                                    GdkAtom       format,
1381                                    const guint8 *text,
1382                                    gsize         length,
1383                                    gpointer      data)
1384 {
1385   WaitResults *results = data;
1386
1387   results->data = g_memdup (text, length);
1388   results->format = format;
1389   results->length = length;
1390   g_main_loop_quit (results->loop);
1391 }
1392
1393 /**
1394  * gtk_clipboard_wait_for_rich_text:
1395  * @clipboard: a #GtkClipboard
1396  * @buffer: a #GtkTextBuffer
1397  * @format: return location for the format of the returned data
1398  * @length: return location for the length of the returned data
1399  *
1400  * Requests the contents of the clipboard as rich text.  This function
1401  * waits for the data to be received using the main loop, so events,
1402  * timeouts, etc, may be dispatched during the wait.
1403  *
1404  * Return value: a newly-allocated binary block of data which must
1405  *               be freed with g_free(), or %NULL if retrieving
1406  *               the selection data failed. (This could happen
1407  *               for various reasons, in particular if the
1408  *               clipboard was empty or if the contents of the
1409  *               clipboard could not be converted into text form.)
1410  *
1411  * Since: 2.10
1412  **/
1413 guint8 *
1414 gtk_clipboard_wait_for_rich_text (GtkClipboard  *clipboard,
1415                                   GtkTextBuffer *buffer,
1416                                   GdkAtom       *format,
1417                                   gsize         *length)
1418 {
1419   WaitResults results;
1420
1421   g_return_val_if_fail (clipboard != NULL, NULL);
1422   g_return_val_if_fail (GTK_IS_TEXT_BUFFER (buffer), NULL);
1423   g_return_val_if_fail (format != NULL, NULL);
1424   g_return_val_if_fail (length != NULL, NULL);
1425
1426   results.data = NULL;
1427   results.loop = g_main_loop_new (NULL, TRUE);
1428
1429   gtk_clipboard_request_rich_text (clipboard, buffer,
1430                                    clipboard_rich_text_received_func,
1431                                    &results);
1432
1433   if (g_main_loop_is_running (results.loop))
1434     {
1435       GDK_THREADS_LEAVE ();
1436       g_main_loop_run (results.loop);
1437       GDK_THREADS_ENTER ();
1438     }
1439
1440   g_main_loop_unref (results.loop);
1441
1442   *format = results.format;
1443   *length = results.length;
1444
1445   return results.data;
1446 }
1447
1448 static void 
1449 clipboard_image_received_func (GtkClipboard *clipboard,
1450                                GdkPixbuf    *pixbuf,
1451                                gpointer      data)
1452 {
1453   WaitResults *results = data;
1454
1455   if (pixbuf)
1456     results->data = g_object_ref (pixbuf);
1457
1458   g_main_loop_quit (results->loop);
1459 }
1460
1461 /**
1462  * gtk_clipboard_wait_for_image:
1463  * @clipboard: a #GtkClipboard
1464  * 
1465  * Requests the contents of the clipboard as image and converts
1466  * the result to a #GdkPixbuf. This function waits for
1467  * the data to be received using the main loop, so events,
1468  * timeouts, etc, may be dispatched during the wait.
1469  * 
1470  * Return value: a newly-allocated #GdkPixbuf object which must
1471  *               be disposed with g_object_unref(), or %NULL if 
1472  *               retrieving the selection data failed. (This 
1473  *               could happen for various reasons, in particular 
1474  *               if the clipboard was empty or if the contents of 
1475  *               the clipboard could not be converted into an image.)
1476  *
1477  * Since: 2.6
1478  **/
1479 GdkPixbuf *
1480 gtk_clipboard_wait_for_image (GtkClipboard *clipboard)
1481 {
1482   WaitResults results;
1483
1484   g_return_val_if_fail (clipboard != NULL, NULL);
1485   
1486   results.data = NULL;
1487   results.loop = g_main_loop_new (NULL, TRUE);
1488
1489   gtk_clipboard_request_image (clipboard,
1490                                clipboard_image_received_func,
1491                                &results);
1492
1493   if (g_main_loop_is_running (results.loop))
1494     {
1495       GDK_THREADS_LEAVE ();
1496       g_main_loop_run (results.loop);
1497       GDK_THREADS_ENTER ();
1498     }
1499
1500   g_main_loop_unref (results.loop);
1501
1502   return results.data;
1503 }
1504
1505 static void 
1506 clipboard_uris_received_func (GtkClipboard *clipboard,
1507                               gchar       **uris,
1508                               gpointer      data)
1509 {
1510   WaitResults *results = data;
1511
1512   results->data = g_strdupv (uris);
1513   g_main_loop_quit (results->loop);
1514 }
1515
1516 /**
1517  * gtk_clipboard_wait_for_uris:
1518  * @clipboard: a #GtkClipboard
1519  * 
1520  * Requests the contents of the clipboard as URIs. This function waits
1521  * for the data to be received using the main loop, so events,
1522  * timeouts, etc, may be dispatched during the wait.
1523  * 
1524  * Return value: a newly-allocated %NULL-terminated array of strings which must
1525  *               be freed with g_strfreev(), or %NULL if
1526  *               retrieving the selection data failed. (This 
1527  *               could happen for various reasons, in particular 
1528  *               if the clipboard was empty or if the contents of 
1529  *               the clipboard could not be converted into URI form.)
1530  *
1531  * Since: 2.14
1532  **/
1533 gchar **
1534 gtk_clipboard_wait_for_uris (GtkClipboard *clipboard)
1535 {
1536   WaitResults results;
1537
1538   g_return_val_if_fail (clipboard != NULL, NULL);
1539   
1540   results.data = NULL;
1541   results.loop = g_main_loop_new (NULL, TRUE);
1542
1543   gtk_clipboard_request_uris (clipboard,
1544                               clipboard_uris_received_func,
1545                               &results);
1546
1547   if (g_main_loop_is_running (results.loop))
1548     {
1549       GDK_THREADS_LEAVE ();
1550       g_main_loop_run (results.loop);
1551       GDK_THREADS_ENTER ();
1552     }
1553
1554   g_main_loop_unref (results.loop);
1555
1556   return results.data;
1557 }
1558
1559 /**
1560  * gtk_clipboard_get_display:
1561  * @clipboard: a #GtkClipboard
1562  *
1563  * Gets the #GdkDisplay associated with @clipboard
1564  *
1565  * Return value: the #GdkDisplay associated with @clipboard
1566  *
1567  * Since: 2.2
1568  **/
1569 GdkDisplay *
1570 gtk_clipboard_get_display (GtkClipboard *clipboard)
1571 {
1572   g_return_val_if_fail (clipboard != NULL, NULL);
1573
1574   return clipboard->display;
1575 }
1576
1577 /**
1578  * gtk_clipboard_wait_is_text_available:
1579  * @clipboard: a #GtkClipboard
1580  * 
1581  * Test to see if there is text available to be pasted
1582  * This is done by requesting the TARGETS atom and checking
1583  * if it contains any of the supported text targets. This function 
1584  * waits for the data to be received using the main loop, so events, 
1585  * timeouts, etc, may be dispatched during the wait.
1586  *
1587  * This function is a little faster than calling
1588  * gtk_clipboard_wait_for_text() since it doesn't need to retrieve
1589  * the actual text.
1590  * 
1591  * Return value: %TRUE is there is text available, %FALSE otherwise.
1592  **/
1593 gboolean
1594 gtk_clipboard_wait_is_text_available (GtkClipboard *clipboard)
1595 {
1596   GtkSelectionData *data;
1597   gboolean result = FALSE;
1598
1599   data = gtk_clipboard_wait_for_contents (clipboard, gdk_atom_intern_static_string ("TARGETS"));
1600   if (data)
1601     {
1602       result = gtk_selection_data_targets_include_text (data);
1603       gtk_selection_data_free (data);
1604     }
1605
1606   return result;
1607 }
1608
1609 /**
1610  * gtk_clipboard_wait_is_rich_text_available:
1611  * @clipboard: a #GtkClipboard
1612  * @buffer: a #GtkTextBuffer
1613  *
1614  * Test to see if there is rich text available to be pasted
1615  * This is done by requesting the TARGETS atom and checking
1616  * if it contains any of the supported rich text targets. This function
1617  * waits for the data to be received using the main loop, so events,
1618  * timeouts, etc, may be dispatched during the wait.
1619  *
1620  * This function is a little faster than calling
1621  * gtk_clipboard_wait_for_rich_text() since it doesn't need to retrieve
1622  * the actual text.
1623  *
1624  * Return value: %TRUE is there is rich text available, %FALSE otherwise.
1625  *
1626  * Since: 2.10
1627  **/
1628 gboolean
1629 gtk_clipboard_wait_is_rich_text_available (GtkClipboard  *clipboard,
1630                                            GtkTextBuffer *buffer)
1631 {
1632   GtkSelectionData *data;
1633   gboolean result = FALSE;
1634
1635   g_return_val_if_fail (GTK_IS_CLIPBOARD (clipboard), FALSE);
1636   g_return_val_if_fail (GTK_IS_TEXT_BUFFER (buffer), FALSE);
1637
1638   data = gtk_clipboard_wait_for_contents (clipboard, gdk_atom_intern_static_string ("TARGETS"));
1639   if (data)
1640     {
1641       result = gtk_selection_data_targets_include_rich_text (data, buffer);
1642       gtk_selection_data_free (data);
1643     }
1644
1645   return result;
1646 }
1647
1648 /**
1649  * gtk_clipboard_wait_is_image_available:
1650  * @clipboard: a #GtkClipboard
1651  * 
1652  * Test to see if there is an image available to be pasted
1653  * This is done by requesting the TARGETS atom and checking
1654  * if it contains any of the supported image targets. This function 
1655  * waits for the data to be received using the main loop, so events, 
1656  * timeouts, etc, may be dispatched during the wait.
1657  *
1658  * This function is a little faster than calling
1659  * gtk_clipboard_wait_for_image() since it doesn't need to retrieve
1660  * the actual image data.
1661  * 
1662  * Return value: %TRUE is there is an image available, %FALSE otherwise.
1663  *
1664  * Since: 2.6
1665  **/
1666 gboolean
1667 gtk_clipboard_wait_is_image_available (GtkClipboard *clipboard)
1668 {
1669   GtkSelectionData *data;
1670   gboolean result = FALSE;
1671
1672   data = gtk_clipboard_wait_for_contents (clipboard, 
1673                                           gdk_atom_intern_static_string ("TARGETS"));
1674   if (data)
1675     {
1676       result = gtk_selection_data_targets_include_image (data, FALSE);
1677       gtk_selection_data_free (data);
1678     }
1679
1680   return result;
1681 }
1682
1683 /**
1684  * gtk_clipboard_wait_is_uris_available:
1685  * @clipboard: a #GtkClipboard
1686  * 
1687  * Test to see if there is a list of URIs available to be pasted
1688  * This is done by requesting the TARGETS atom and checking
1689  * if it contains the URI targets. This function
1690  * waits for the data to be received using the main loop, so events, 
1691  * timeouts, etc, may be dispatched during the wait.
1692  *
1693  * This function is a little faster than calling
1694  * gtk_clipboard_wait_for_uris() since it doesn't need to retrieve
1695  * the actual URI data.
1696  * 
1697  * Return value: %TRUE is there is an URI list available, %FALSE otherwise.
1698  *
1699  * Since: 2.14
1700  **/
1701 gboolean
1702 gtk_clipboard_wait_is_uris_available (GtkClipboard *clipboard)
1703 {
1704   GtkSelectionData *data;
1705   gboolean result = FALSE;
1706
1707   data = gtk_clipboard_wait_for_contents (clipboard, 
1708                                           gdk_atom_intern_static_string ("TARGETS"));
1709   if (data)
1710     {
1711       result = gtk_selection_data_targets_include_uri (data);
1712       gtk_selection_data_free (data);
1713     }
1714
1715   return result;
1716 }
1717
1718 /**
1719  * gtk_clipboard_wait_for_targets
1720  * @clipboard: a #GtkClipboard
1721  * @targets: location to store an array of targets. The result
1722  *           stored here must be freed with g_free().
1723  * @n_targets: location to store number of items in @targets.
1724  *
1725  * Returns a list of targets that are present on the clipboard, or %NULL
1726  * if there aren't any targets available. The returned list must be 
1727  * freed with g_free().
1728  * This function waits for the data to be received using the main 
1729  * loop, so events, timeouts, etc, may be dispatched during the wait.
1730  *
1731  * Return value: %TRUE if any targets are present on the clipboard,
1732  *               otherwise %FALSE.
1733  *
1734  * Since: 2.4
1735  */
1736 gboolean
1737 gtk_clipboard_wait_for_targets (GtkClipboard  *clipboard, 
1738                                 GdkAtom      **targets,
1739                                 gint          *n_targets)
1740 {
1741   GtkSelectionData *data;
1742   gboolean result = FALSE;
1743   
1744   g_return_val_if_fail (clipboard != NULL, FALSE);
1745
1746   /* If the display supports change notification we cache targets */
1747   if (gdk_display_supports_selection_notification (gtk_clipboard_get_display (clipboard)) &&
1748       clipboard->n_cached_targets != -1)
1749     {
1750       if (n_targets)
1751         *n_targets = clipboard->n_cached_targets;
1752  
1753       if (targets)
1754         *targets = g_memdup (clipboard->cached_targets,
1755                              clipboard->n_cached_targets * sizeof (GdkAtom));
1756
1757        return TRUE;
1758     }
1759   
1760   if (n_targets)
1761     *n_targets = 0;
1762       
1763   if (targets)
1764     *targets = NULL;      
1765
1766   data = gtk_clipboard_wait_for_contents (clipboard, gdk_atom_intern_static_string ("TARGETS"));
1767
1768   if (data)
1769     {
1770       GdkAtom *tmp_targets;
1771       gint tmp_n_targets;
1772        
1773       result = gtk_selection_data_get_targets (data, &tmp_targets, &tmp_n_targets);
1774  
1775       if (gdk_display_supports_selection_notification (gtk_clipboard_get_display (clipboard)))
1776         {
1777           clipboard->n_cached_targets = tmp_n_targets;
1778           clipboard->cached_targets = g_memdup (tmp_targets,
1779                                                 tmp_n_targets * sizeof (GdkAtom));
1780         }
1781  
1782       if (n_targets)
1783         *n_targets = tmp_n_targets;
1784  
1785       if (targets)
1786         *targets = tmp_targets;
1787       else
1788         g_free (tmp_targets);
1789       
1790       gtk_selection_data_free (data);
1791     }
1792
1793   return result;
1794 }
1795
1796 static GtkClipboard *
1797 clipboard_peek (GdkDisplay *display, 
1798                 GdkAtom     selection,
1799                 gboolean    only_if_exists)
1800 {
1801   GtkClipboard *clipboard = NULL;
1802   GSList *clipboards;
1803   GSList *tmp_list;
1804
1805   if (selection == GDK_NONE)
1806     selection = GDK_SELECTION_CLIPBOARD;
1807
1808   clipboards = g_object_get_data (G_OBJECT (display), "gtk-clipboard-list");
1809
1810   tmp_list = clipboards;
1811   while (tmp_list)
1812     {
1813       clipboard = tmp_list->data;
1814       if (clipboard->selection == selection)
1815         break;
1816
1817       tmp_list = tmp_list->next;
1818     }
1819
1820   if (!tmp_list && !only_if_exists)
1821     {
1822       clipboard = g_object_new (GTK_TYPE_CLIPBOARD, NULL);
1823       clipboard->selection = selection;
1824       clipboard->display = display;
1825       clipboard->n_cached_targets = -1;
1826       clipboard->n_storable_targets = -1;
1827       clipboards = g_slist_prepend (clipboards, clipboard);
1828       g_object_set_data (G_OBJECT (display), I_("gtk-clipboard-list"), clipboards);
1829       g_signal_connect (display, "closed",
1830                         G_CALLBACK (clipboard_display_closed), clipboard);
1831       gdk_display_request_selection_notification (display, selection);
1832     }
1833   
1834   return clipboard;
1835 }
1836
1837 static void
1838 gtk_clipboard_owner_change (GtkClipboard        *clipboard,
1839                             GdkEventOwnerChange *event)
1840 {
1841   if (clipboard->n_cached_targets != -1)
1842     {
1843       clipboard->n_cached_targets = -1;
1844       g_free (clipboard->cached_targets);
1845     }
1846 }
1847
1848 /**
1849  * gtk_clipboard_wait_is_target_available:
1850  * @clipboard: a #GtkClipboard
1851  * @target:    A #GdkAtom indicating which target to look for.
1852  *
1853  * Checks if a clipboard supports pasting data of a given type. This
1854  * function can be used to determine if a "Paste" menu item should be
1855  * insensitive or not.
1856  *
1857  * If you want to see if there's text available on the clipboard, use
1858  * gtk_clipboard_wait_is_text_available () instead.
1859  *
1860  * Return value: %TRUE if the target is available, %FALSE otherwise.
1861  *
1862  * Since: 2.6
1863  */
1864 gboolean
1865 gtk_clipboard_wait_is_target_available (GtkClipboard *clipboard,
1866                                         GdkAtom       target)
1867 {
1868   GdkAtom *targets;
1869   gint i, n_targets;
1870   gboolean retval = FALSE;
1871     
1872   if (!gtk_clipboard_wait_for_targets (clipboard, &targets, &n_targets))
1873     return FALSE;
1874
1875   for (i = 0; i < n_targets; i++)
1876     {
1877       if (targets[i] == target)
1878         {
1879           retval = TRUE;
1880           break;
1881         }
1882     }
1883
1884   g_free (targets);
1885   
1886   return retval;
1887 }
1888
1889 /**
1890  * _gtk_clipboard_handle_event:
1891  * @event: a owner change event
1892  * 
1893  * Emits the #GtkClipboard::owner-change signal on the appropriate @clipboard.
1894  *
1895  * Since: 2.6
1896  **/
1897 void 
1898 _gtk_clipboard_handle_event (GdkEventOwnerChange *event)
1899 {
1900   GdkDisplay *display;
1901   GtkClipboard *clipboard;
1902   
1903   display = gdk_drawable_get_display (event->window);
1904   clipboard = clipboard_peek (display, event->selection, TRUE);
1905       
1906   if (clipboard)
1907     g_signal_emit (clipboard, 
1908                    clipboard_signals[OWNER_CHANGE], 0, event, NULL);
1909 }
1910
1911 static gboolean
1912 gtk_clipboard_store_timeout (GtkClipboard *clipboard)
1913 {
1914   g_main_loop_quit (clipboard->store_loop);
1915   
1916   return FALSE;
1917 }
1918
1919 /**
1920  * gtk_clipboard_set_can_store:
1921  * @clipboard: a #GtkClipboard
1922  * @targets: array containing information about which forms should be stored
1923  *           or %NULL to indicate that all forms should be stored.
1924  * @n_targets: number of elements in @targets
1925  *
1926  * Hints that the clipboard data should be stored somewhere when the
1927  * application exits or when gtk_clipboard_store () is called.
1928  *
1929  * This value is reset when the clipboard owner changes.
1930  * Where the clipboard data is stored is platform dependent,
1931  * see gdk_display_store_clipboard () for more information.
1932  * 
1933  * Since: 2.6
1934  */
1935 void
1936 gtk_clipboard_set_can_store (GtkClipboard         *clipboard,
1937                              const GtkTargetEntry *targets,
1938                              gint                  n_targets)
1939 {
1940   GtkWidget *clipboard_widget;
1941   int i;
1942   static const GtkTargetEntry save_targets[] = {
1943     { "SAVE_TARGETS", 0, TARGET_SAVE_TARGETS }
1944   };
1945   
1946   g_return_if_fail (GTK_IS_CLIPBOARD (clipboard));
1947   g_return_if_fail (n_targets >= 0);
1948
1949   if (clipboard->selection != GDK_SELECTION_CLIPBOARD)
1950     return;
1951   
1952   g_free (clipboard->storable_targets);
1953   
1954   clipboard_widget = get_clipboard_widget (clipboard->display);
1955
1956   /* n_storable_targets being -1 means that
1957    * gtk_clipboard_set_can_store hasn't been called since the
1958    * clipboard owner changed. We only want to add SAVE_TARGETS and 
1959    * ref the owner once , so we do that here
1960    */  
1961   if (clipboard->n_storable_targets == -1)
1962     {
1963       gtk_selection_add_targets (clipboard_widget, clipboard->selection,
1964                                  save_targets, 1);
1965
1966       /* Ref the owner so it won't go away */
1967       if (clipboard->have_owner)
1968         g_object_ref (clipboard->user_data);
1969     }
1970   
1971   clipboard->n_storable_targets = n_targets;
1972   clipboard->storable_targets = g_new (GdkAtom, n_targets);
1973   for (i = 0; i < n_targets; i++)
1974     clipboard->storable_targets[i] = gdk_atom_intern (targets[i].target, FALSE);
1975 }
1976
1977 static gboolean
1978 gtk_clipboard_selection_notify (GtkWidget         *widget,
1979                                 GdkEventSelection *event,
1980                                 GtkClipboard      *clipboard)
1981 {
1982   if (event->selection == gdk_atom_intern_static_string ("CLIPBOARD_MANAGER") &&
1983       clipboard->storing_selection)
1984     g_main_loop_quit (clipboard->store_loop);
1985
1986   return FALSE;
1987 }
1988
1989 /**
1990  * gtk_clipboard_store:
1991  * @clipboard: a #GtkClipboard
1992  *
1993  * Stores the current clipboard data somewhere so that it will stay
1994  * around after the application has quit.
1995  *
1996  * Since: 2.6
1997  */
1998 void
1999 gtk_clipboard_store (GtkClipboard *clipboard)
2000 {
2001   GtkWidget *clipboard_widget;
2002
2003   g_return_if_fail (GTK_IS_CLIPBOARD (clipboard));
2004
2005   if (clipboard->n_storable_targets < 0)
2006     return;
2007   
2008   if (!gdk_display_supports_clipboard_persistence (clipboard->display))
2009     return;
2010
2011   g_object_ref (clipboard);
2012
2013   clipboard_widget = get_clipboard_widget (clipboard->display);
2014   clipboard->notify_signal_id = g_signal_connect (clipboard_widget, "selection_notify_event",
2015                                                   G_CALLBACK (gtk_clipboard_selection_notify), clipboard);
2016   
2017   gdk_display_store_clipboard (clipboard->display,
2018                                clipboard_widget->window,
2019                                clipboard_get_timestamp (clipboard),
2020                                clipboard->storable_targets,
2021                                clipboard->n_storable_targets);
2022
2023   clipboard->storing_selection = TRUE;
2024
2025   clipboard->store_loop = g_main_loop_new (NULL, TRUE);
2026   clipboard->store_timeout = g_timeout_add (10000, (GSourceFunc) gtk_clipboard_store_timeout, clipboard);
2027
2028   if (g_main_loop_is_running (clipboard->store_loop))
2029     {
2030       GDK_THREADS_LEAVE ();
2031       g_main_loop_run (clipboard->store_loop);
2032       GDK_THREADS_ENTER ();
2033     }
2034   
2035   g_main_loop_unref (clipboard->store_loop);
2036   clipboard->store_loop = NULL;
2037   
2038   g_source_remove (clipboard->store_timeout);
2039   clipboard->store_timeout = 0;
2040   g_signal_handler_disconnect (clipboard_widget, clipboard->notify_signal_id);
2041   clipboard->notify_signal_id = 0;
2042   
2043   clipboard->storing_selection = FALSE;
2044
2045   g_object_unref (clipboard);
2046 }
2047
2048 /* Stores all clipboard selections on all displays, called from
2049  * gtk_main_quit ().
2050  */
2051 void
2052 _gtk_clipboard_store_all (void)
2053 {
2054   GtkClipboard *clipboard;
2055   GSList *displays, *list;
2056   
2057   displays = gdk_display_manager_list_displays (gdk_display_manager_get ());
2058
2059   list = displays;
2060   while (list)
2061     {
2062       GdkDisplay *display = list->data;
2063
2064       clipboard = clipboard_peek (display, GDK_SELECTION_CLIPBOARD, TRUE);
2065
2066       if (clipboard)
2067         gtk_clipboard_store (clipboard);
2068       
2069       list = list->next;
2070     }
2071   g_slist_free (displays);
2072   
2073 }
2074
2075 #define __GTK_CLIPBOARD_C__
2076 #include "gtkaliasdef.c"