summaryrefslogtreecommitdiff
path: root/gdk/win32/gdkproperty-win32.c
diff options
context:
space:
mode:
authorTor Lillqvist <tml@novell.com>2005-04-04 00:12:26 +0000
committerTor Lillqvist <tml@src.gnome.org>2005-04-04 00:12:26 +0000
commit0b2ac32cf5d8ed96ebf743cbfc112d7e52928c81 (patch)
tree36a7395abd82e5c8bc1ad3ca0aec863ae0c8bc57 /gdk/win32/gdkproperty-win32.c
parentba433af9fb2419f3429622d40300c7ac3659fd75 (diff)
downloadgdk-pixbuf-0b2ac32cf5d8ed96ebf743cbfc112d7e52928c81.tar.gz
New debugging function, to log a clipboard format name symbolically.
2005-04-04 Tor Lillqvist <tml@novell.com> * gdk/win32/gdkmain.c (_gdk_win32_cf_to_string): New debugging function, to log a clipboard format name symbolically. (_gdk_win32_data_to_string): Also new, to log random data bytes. Implement delayed rendering on Win32, specifically for transfering images through the clipboard from GTK+ apps to other apps (#168173, implementation by Ivan Wong): * gdk/win32/gdkevents-win32.c (gdk_event_translate): Handle WM_RENDERFORMAT. * gdk/win32/gdkprivate-win32.h * gdk/win32/gdkglobals-win32.c: Add _format_atom_table, _delayed_rendering_data and _image_bmp. * gdk/win32/gdkmain-win32.c: Initialize _image_bmp. * gdk/win32/gdkproperty-win32.c (gdk_property_change): Accept formats other than GDK_TARGET_STRING or _utf8_string, and assume they are handled through delayed rendering. * gdk/win32/gdkselection-win32.c (gdk_selection_convert): Return all available formats (including those registered by GTK+ apps) on request_targets. (gdk_selection_property_get): We should append a zero byte like X11 does. (gdk_win32_selection_add_targets): New function, for gtkselection's use. Win32 requires that the clipboard owner registers all valid formats even if the owner wants delayed rendering. (_gdk_win32_selection_convert_to_dib): New function. Convert images to DIB using gdk-pixbuf. * gdk/win32/gdkwin32.h: Declare gdk_win32_selection_add_targets(). * gtk/gtkselection.c (gtk_selection_add_target, gtk_selection_add_targets): Call gdk_win32_selection_add_targets() to register target formats. * gdk/gdk.symbols: Add gdk_win32_selection_add_targets().
Diffstat (limited to 'gdk/win32/gdkproperty-win32.c')
-rw-r--r--gdk/win32/gdkproperty-win32.c354
1 files changed, 188 insertions, 166 deletions
diff --git a/gdk/win32/gdkproperty-win32.c b/gdk/win32/gdkproperty-win32.c
index 5fb34bc5e..145271216 100644
--- a/gdk/win32/gdkproperty-win32.c
+++ b/gdk/win32/gdkproperty-win32.c
@@ -265,7 +265,7 @@ gdk_property_change (GdkWindow *window,
GDK_NOTE (DND,
(prop_name = gdk_atom_name (property),
type_name = gdk_atom_name (type),
- g_print ("gdk_property_change: %p %#x (%s) %#x (%s) %s %d*%d bytes %.10s\n",
+ g_print ("gdk_property_change: %p %#x (%s) %#x (%s) %s %d*%d bytes: %s\n",
GDK_WINDOW_HWND (window),
(guint) property, prop_name,
(guint) type, type_name,
@@ -273,201 +273,221 @@ gdk_property_change (GdkWindow *window,
(mode == GDK_PROP_MODE_PREPEND ? "PREPEND" :
(mode == GDK_PROP_MODE_APPEND ? "APPEND" :
"???"))),
- format, nelements, data),
+ format, nelements,
+ _gdk_win32_data_to_string (data, MIN (10, format*nelements/8))),
g_free (prop_name),
g_free (type_name)));
if (property == _gdk_selection_property
- && ((type == GDK_TARGET_STRING && GetACP () == 1252) ||
- type == _utf8_string)
&& format == 8
&& mode == GDK_PROP_MODE_REPLACE)
{
- if (!OpenClipboard (GDK_WINDOW_HWND (window)))
+ if ((type == GDK_TARGET_STRING && GetACP () == 1252) ||
+ type == _utf8_string)
{
- WIN32_API_FAILED ("OpenClipboard");
- return;
- }
+ if (!OpenClipboard (GDK_WINDOW_HWND (window)))
+ {
+ WIN32_API_FAILED ("OpenClipboard");
+ return;
+ }
- if (type == _utf8_string)
- {
- /* Check if only ASCII */
- for (i = 0; i < nelements; i++)
- if (data[i] >= 0200)
- break;
- }
- else /* if (type == GDK_TARGET_STRING) */
- {
- /* Check that no 0200..0240 chars present, as they
- * differ between ISO-8859-1 and CP1252.
- */
- for (i = 0; i < nelements; i++)
- if (data[i] >= 0200 && data[i] < 0240)
- break;
- }
- nchars = g_utf8_strlen (data, nelements);
+ if (type == _utf8_string)
+ {
+ /* Check if only ASCII */
+ for (i = 0; i < nelements; i++)
+ if (data[i] >= 0200)
+ break;
+ }
+ else /* if (type == GDK_TARGET_STRING) */
+ {
+ /* Check that no 0200..0240 chars present, as they
+ * differ between ISO-8859-1 and CP1252.
+ */
+ for (i = 0; i < nelements; i++)
+ if (data[i] >= 0200 && data[i] < 0240)
+ break;
+ }
+ nchars = g_utf8_strlen (data, nelements);
- if (i == nelements)
- {
- /* If UTF-8 and only ASCII, or if STRING (ISO-8859-1) and
- * system codepage is CP1252, use CF_TEXT and the data as
- * such.
- */
- method = SYSTEM_CODEPAGE;
- size = nelements;
- for (i = 0; i < nelements; i++)
- if (data[i] == '\n')
+ if (i == nelements)
+ {
+ /* If UTF-8 and only ASCII, or if STRING (ISO-8859-1)
+ * and system codepage is CP1252, use CF_TEXT and the
+ * data as such.
+ */
+ method = SYSTEM_CODEPAGE;
+ size = nelements;
+ for (i = 0; i < nelements; i++)
+ if (data[i] == '\n')
+ size++;
size++;
- size++;
- GDK_NOTE (DND, g_print ("... as text: %.40s\n", data));
- }
- else if (G_WIN32_IS_NT_BASED ())
- {
- /* On NT, use CF_UNICODETEXT if any non-system codepage char
- * present.
- */
- method = UNICODE_TEXT;
+ GDK_NOTE (DND, g_print ("... as text: %.40s\n", data));
+ }
+ else if (G_WIN32_IS_NT_BASED ())
+ {
+ /* On NT, use CF_UNICODETEXT if any non-system codepage
+ * char present.
+ */
+ method = UNICODE_TEXT;
- wcptr = g_utf8_to_utf16 (data, nelements, NULL, &wclen, NULL);
+ wcptr = g_utf8_to_utf16 (data, nelements, NULL, &wclen, NULL);
- wclen++; /* Terminating 0 */
- size = wclen * 2;
- GDK_NOTE (DND, g_print ("... as Unicode\n"));
- }
- else if (find_common_locale (data, nelements, nchars, &lcid, &buf, &size))
- {
- /* On Win9x, if all chars are in the default code page of
- * some installed locale, use CF_TEXT and CF_LOCALE.
- */
- method = SINGLE_LOCALE;
- GDK_NOTE (DND, g_print ("... as text in locale %#lx %d bytes\n",
- (gulong) lcid, size));
- }
- else
- {
- /* On Win9x, otherwise use RTF */
+ wclen++; /* Terminating 0 */
+ size = wclen * 2;
+ GDK_NOTE (DND, g_print ("... as Unicode\n"));
+ }
+ else if (find_common_locale (data, nelements, nchars, &lcid, &buf, &size))
+ {
+ /* On Win9x, if all chars are in the default code page
+ * of some installed locale, use CF_TEXT and CF_LOCALE.
+ */
+ method = SINGLE_LOCALE;
+ GDK_NOTE (DND, g_print ("... as text in locale %#lx %d bytes\n",
+ (gulong) lcid, size));
+ }
+ else
+ {
+ /* On Win9x, otherwise use RTF */
+
+ const guchar *p = data;
+
+ method = RICH_TEXT;
+ rtf = g_string_new ("{\\rtf1\\uc0 ");
- const guchar *p = data;
+ while (p < data + nelements)
+ {
+ if (*p == '{' ||
+ *p == '\\' ||
+ *p == '}')
+ {
+ rtf = g_string_append_c (rtf, '\\');
+ rtf = g_string_append_c (rtf, *p);
+ p++;
+ }
+ else if (*p < 0200 && *p >= ' ')
+ {
+ rtf = g_string_append_c (rtf, *p);
+ p++;
+ }
+ else
+ {
+ guchar *q;
+ gint n;
+
+ rtf = g_string_append (rtf, "\\uNNNNN ");
+ rtf->len -= 6; /* five digits and a space */
+ q = rtf->str + rtf->len;
+ n = g_sprintf (q, "%d ", g_utf8_get_char (p));
+ g_assert (n <= 6);
+ rtf->len += n;
+
+ p = g_utf8_next_char (p);
+ }
+ }
+ rtf = g_string_append (rtf, "}");
+ size = rtf->len + 1;
+ GDK_NOTE (DND, g_print ("... as RTF: %.40s\n", rtf->str));
+ }
+
+ if (!(hdata = GlobalAlloc (GMEM_MOVEABLE, size)))
+ {
+ WIN32_API_FAILED ("GlobalAlloc");
+ if (!CloseClipboard ())
+ WIN32_API_FAILED ("CloseClipboard");
+ if (buf != NULL)
+ g_free (buf);
+ if (rtf != NULL)
+ g_string_free (rtf, TRUE);
+ return;
+ }
- method = RICH_TEXT;
- rtf = g_string_new ("{\\rtf1\\uc0 ");
+ ucptr = GlobalLock (hdata);
- while (p < data + nelements)
+ switch (method)
{
- if (*p == '{' ||
- *p == '\\' ||
- *p == '}')
+ case SYSTEM_CODEPAGE:
+ cf = CF_TEXT;
+ for (i = 0; i < nelements; i++)
{
- rtf = g_string_append_c (rtf, '\\');
- rtf = g_string_append_c (rtf, *p);
- p++;
+ if (data[i] == '\n')
+ *ucptr++ = '\r';
+ *ucptr++ = data[i];
}
- else if (*p < 0200 && *p >= ' ')
+ *ucptr++ = '\0';
+ break;
+
+ case UNICODE_TEXT:
+ cf = CF_UNICODETEXT;
+ memmove (ucptr, wcptr, size);
+ g_free (wcptr);
+ break;
+
+ case SINGLE_LOCALE:
+ cf = CF_TEXT;
+ memmove (ucptr, buf, size);
+ g_free (buf);
+
+ /* Set the CF_LOCALE clipboard data, too */
+ if (!(hlcid = GlobalAlloc (GMEM_MOVEABLE, sizeof (LCID))))
+ WIN32_API_FAILED ("GlobalAlloc"), ok = FALSE;
+ if (ok)
{
- rtf = g_string_append_c (rtf, *p);
- p++;
+ lcidptr = GlobalLock (hlcid);
+ *lcidptr = lcid;
+ GlobalUnlock (hlcid);
+ if (!SetClipboardData (CF_LOCALE, hlcid))
+ WIN32_API_FAILED ("SetClipboardData (CF_LOCALE)"), ok = FALSE;
}
+ break;
+
+ case RICH_TEXT:
+ cf = _cf_rtf;
+ memmove (ucptr, rtf->str, size);
+ g_string_free (rtf, TRUE);
+
+ /* Set the UTF8_STRING clipboard data, too, for other
+ * GTK+ apps to use (won't bother reading RTF).
+ */
+ if (!(hutf8 = GlobalAlloc (GMEM_MOVEABLE, nelements)))
+ WIN32_API_FAILED ("GlobalAlloc");
else
{
- guchar *q;
- gint n;
-
- rtf = g_string_append (rtf, "\\uNNNNN ");
- rtf->len -= 6; /* five digits and a space */
- q = rtf->str + rtf->len;
- n = g_sprintf (q, "%d ", g_utf8_get_char (p));
- g_assert (n <= 6);
- rtf->len += n;
-
- p = g_utf8_next_char (p);
+ guchar *utf8ptr = GlobalLock (hutf8);
+ memmove (utf8ptr, data, nelements);
+ GlobalUnlock (hutf8);
+ if (!SetClipboardData (_cf_utf8_string, hutf8))
+ WIN32_API_FAILED ("SetClipboardData (UTF8_STRING)");
}
+ break;
+
+ default:
+ g_assert_not_reached ();
}
- rtf = g_string_append (rtf, "}");
- size = rtf->len + 1;
- GDK_NOTE (DND, g_print ("... as RTF: %.40s\n", rtf->str));
- }
-
- if (!(hdata = GlobalAlloc (GMEM_MOVEABLE, size)))
- {
- WIN32_API_FAILED ("GlobalAlloc");
+
+ GlobalUnlock (hdata);
+ if (ok && !SetClipboardData (cf, hdata))
+ WIN32_API_FAILED ("SetClipboardData"), ok = FALSE;
+
if (!CloseClipboard ())
WIN32_API_FAILED ("CloseClipboard");
- if (buf != NULL)
- g_free (buf);
- if (rtf != NULL)
- g_string_free (rtf, TRUE);
- return;
}
-
- ucptr = GlobalLock (hdata);
-
- switch (method)
- {
- case SYSTEM_CODEPAGE:
- cf = CF_TEXT;
- for (i = 0; i < nelements; i++)
- {
- if (data[i] == '\n')
- *ucptr++ = '\r';
- *ucptr++ = data[i];
- }
- *ucptr++ = '\0';
- break;
-
- case UNICODE_TEXT:
- cf = CF_UNICODETEXT;
- memmove (ucptr, wcptr, size);
- g_free (wcptr);
- break;
-
- case SINGLE_LOCALE:
- cf = CF_TEXT;
- memmove (ucptr, buf, size);
- g_free (buf);
-
- /* Set the CF_LOCALE clipboard data, too */
- if (!(hlcid = GlobalAlloc (GMEM_MOVEABLE, sizeof (LCID))))
- WIN32_API_FAILED ("GlobalAlloc"), ok = FALSE;
- if (ok)
- {
- lcidptr = GlobalLock (hlcid);
- *lcidptr = lcid;
- GlobalUnlock (hlcid);
- if (!SetClipboardData (CF_LOCALE, hlcid))
- WIN32_API_FAILED ("SetClipboardData (CF_LOCALE)"), ok = FALSE;
- }
- break;
-
- case RICH_TEXT:
- cf = _cf_rtf;
- memmove (ucptr, rtf->str, size);
- g_string_free (rtf, TRUE);
-
- /* Set the UTF8_STRING clipboard data, too, for other
- * GTK+ apps to use (won't bother reading RTF).
+ else
+ {
+ /* Delayed Rendering. We can't assign hdata to the clipboard
+ * here as type may be "image/png", "image/jpg", etc. In
+ * this case there's a further conversion afterwards.
*/
- if (!(hutf8 = GlobalAlloc (GMEM_MOVEABLE, nelements)))
- WIN32_API_FAILED ("GlobalAlloc");
- else
+ _delayed_rendering_data = NULL;
+ if (!(hdata = GlobalAlloc (GMEM_MOVEABLE, nelements > 0 ? nelements : 1)))
{
- guchar *utf8ptr = GlobalLock (hutf8);
- memmove (utf8ptr, data, nelements);
- GlobalUnlock (hutf8);
- if (!SetClipboardData (_cf_utf8_string, hutf8))
- WIN32_API_FAILED ("SetClipboardData (UTF8_STRING)");
+ WIN32_API_FAILED ("GlobalAlloc");
+ return;
}
- break;
-
- default:
- g_assert_not_reached ();
+ ucptr = GlobalLock (hdata);
+ memcpy (ucptr, data, nelements);
+ GlobalUnlock (hdata);
+ _delayed_rendering_data = hdata;
}
-
- GlobalUnlock (hdata);
- if (ok && !SetClipboardData (cf, hdata))
- WIN32_API_FAILED ("SetClipboardData"), ok = FALSE;
-
- if (!CloseClipboard ())
- WIN32_API_FAILED ("CloseClipboard");
}
else
g_warning ("gdk_property_change: General case not implemented");
@@ -592,13 +612,15 @@ gdk_screen_get_setting (GdkScreen *screen,
ncm.cbSize = sizeof(NONCLIENTMETRICS);
if (SystemParametersInfo (SPI_GETNONCLIENTMETRICS, ncm.cbSize, &ncm, FALSE))
{
- /* Pango finally uses GetDeviceCaps to scale, we use simple approximation here */
+ /* Pango finally uses GetDeviceCaps to scale, we use simple
+ * approximation here.
+ */
int nHeight = (0 > ncm.lfMenuFont.lfHeight ? -3*ncm.lfMenuFont.lfHeight/4 : 10);
if (OUT_STRING_PRECIS == ncm.lfMenuFont.lfOutPrecision)
GDK_NOTE(MISC, g_print("gdk_screen_get_setting(%s) : ignoring bitmap font '%s'\n",
name, ncm.lfMenuFont.lfFaceName));
else if (ncm.lfMenuFont.lfFaceName && strlen(ncm.lfMenuFont.lfFaceName) > 0 &&
- /* avoid issues like those described in bug #135098 */
+ /* Avoid issues like those described in bug #135098 */
g_utf8_validate (ncm.lfMenuFont.lfFaceName, -1, NULL))
{
char* s = g_strdup_printf ("%s %d", ncm.lfMenuFont.lfFaceName, nHeight);