src/video/win32/SDL_win32clipboard.c
author Sam Lantinga
Tue, 20 Jul 2010 00:57:01 -0700
changeset 4559 f8c3870af5a2
parent 4504 9faebccfefb3
child 4569 e1664f94f026
permissions -rw-r--r--
Fixed X11 error when running under window managers that don't support the _NET_SUPPORTING_WM_CHECK protocol.
     1 /*
     2     SDL - Simple DirectMedia Layer
     3     Copyright (C) 1997-2010 Sam Lantinga
     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.1 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 Free Software
    17     Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
    18 
    19     Sam Lantinga
    20     slouken@libsdl.org
    21 */
    22 #include "SDL_config.h"
    23 
    24 #include "SDL_win32video.h"
    25 #include "SDL_win32window.h"
    26 #include "../../events/SDL_clipboardevents_c.h"
    27 
    28 
    29 #ifdef UNICODE
    30 #define TEXT_FORMAT  CF_UNICODETEXT
    31 #else
    32 #define TEXT_FORMAT  CF_TEXT
    33 #endif
    34 
    35 
    36 /* Get any application owned window handle for clipboard association */
    37 static HWND
    38 GetWindowHandle(_THIS)
    39 {
    40     SDL_VideoDisplay *display;
    41     SDL_Window *window;
    42 
    43     display = _this->displays;
    44     if (display) {
    45         window = display->windows;
    46         if (window) {
    47             return ((SDL_WindowData *) window->driverdata)->hwnd;
    48         }
    49     }
    50     return NULL;
    51 }
    52 
    53 int
    54 WIN_SetClipboardText(_THIS, const char *text)
    55 {
    56     SDL_VideoData *data = (SDL_VideoData *) _this->driverdata;
    57     int result = 0;
    58 
    59     if (OpenClipboard(GetWindowHandle(_this))) {
    60         HANDLE hMem;
    61         LPTSTR tstr;
    62         SIZE_T i, size;
    63 
    64         /* Convert the text from UTF-8 to Windows Unicode */
    65         tstr = WIN_UTF8ToString(text);
    66         if (!tstr) {
    67             return -1;
    68         }
    69 
    70         /* Find out the size of the data */
    71         for (size = 0, i = 0; tstr[i]; ++i, ++size) {
    72             if (tstr[i] == '\n' && (i == 0 || tstr[i-1] != '\r')) {
    73                 /* We're going to insert a carriage return */
    74                 ++size;
    75             }
    76         }
    77         size = (size+1)*sizeof(*tstr);
    78 
    79         /* Save the data to the clipboard */
    80         hMem = GlobalAlloc(GMEM_MOVEABLE, size);
    81         if (hMem) {
    82             LPTSTR dst = (LPTSTR)GlobalLock(hMem);
    83             /* Copy the text over, adding carriage returns as necessary */
    84             for (i = 0; tstr[i]; ++i) {
    85                 if (tstr[i] == '\n' && (i == 0 || tstr[i-1] != '\r')) {
    86                     *dst++ = '\r';
    87                 }
    88                 *dst++ = tstr[i];
    89             }
    90             *dst = 0;
    91             GlobalUnlock(hMem);
    92 
    93             EmptyClipboard();
    94             if (!SetClipboardData(TEXT_FORMAT, hMem)) {
    95                 WIN_SetError("Couldn't set clipboard data");
    96                 result = -1;
    97             }
    98             data->clipboard_count = GetClipboardSequenceNumber();
    99         }
   100         SDL_free(tstr);
   101 
   102         CloseClipboard();
   103     } else {
   104         WIN_SetError("Couldn't open clipboard");
   105         result = -1;
   106     }
   107     return result;
   108 }
   109 
   110 char *
   111 WIN_GetClipboardText(_THIS)
   112 {
   113     char *text;
   114 
   115     text = NULL;
   116     if (IsClipboardFormatAvailable(TEXT_FORMAT) &&
   117         OpenClipboard(GetWindowHandle(_this))) {
   118         HANDLE hMem;
   119         LPTSTR tstr;
   120 
   121         hMem = GetClipboardData(TEXT_FORMAT);
   122         if (hMem) {
   123             tstr = (LPTSTR)GlobalLock(hMem);
   124             text = WIN_StringToUTF8(tstr);
   125             GlobalUnlock(hMem);
   126         } else {
   127             WIN_SetError("Couldn't get clipboard data");
   128         }
   129         CloseClipboard();
   130     }
   131     if (!text) {
   132         text = SDL_strdup("");
   133     }
   134     return text;
   135 }
   136 
   137 SDL_bool
   138 WIN_HasClipboardText(_THIS)
   139 {
   140     if (IsClipboardFormatAvailable(TEXT_FORMAT)) {
   141         return SDL_TRUE;
   142     } else {
   143         return SDL_FALSE;
   144     }
   145 }
   146 
   147 void
   148 WIN_CheckClipboardUpdate(struct SDL_VideoData * data)
   149 {
   150     DWORD count;
   151 
   152     count = GetClipboardSequenceNumber();
   153     if (count != data->clipboard_count) {
   154         if (data->clipboard_count) {
   155             SDL_SendClipboardUpdate();
   156         }
   157         data->clipboard_count = count;
   158     }
   159 }
   160 
   161 /* vi: set ts=4 sw=4 expandtab: */