mirror of
https://gitlab.winehq.org/wine/wine.git
synced 2024-11-21 17:09:06 -07:00
user32: Retrieve available clipboard formats from the server.
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
parent
79f90e4e41
commit
c69b4995c5
7 changed files with 186 additions and 26 deletions
|
@ -836,11 +836,17 @@ done:
|
|||
*/
|
||||
INT WINAPI CountClipboardFormats(void)
|
||||
{
|
||||
INT count;
|
||||
INT count = 0;
|
||||
|
||||
USER_Driver->pUpdateClipboard();
|
||||
|
||||
count = USER_Driver->pCountClipboardFormats();
|
||||
SERVER_START_REQ( get_clipboard_formats )
|
||||
{
|
||||
wine_server_call( req );
|
||||
count = reply->count;
|
||||
}
|
||||
SERVER_END_REQ;
|
||||
|
||||
TRACE("returning %d\n", count);
|
||||
return count;
|
||||
}
|
||||
|
@ -853,14 +859,17 @@ UINT WINAPI EnumClipboardFormats( UINT format )
|
|||
{
|
||||
UINT ret = 0;
|
||||
|
||||
if (!(get_clipboard_flags() & CB_OPEN))
|
||||
SERVER_START_REQ( enum_clipboard_formats )
|
||||
{
|
||||
WARN("Clipboard not opened by calling task.\n");
|
||||
SetLastError(ERROR_CLIPBOARD_NOT_OPEN);
|
||||
return 0;
|
||||
req->previous = format;
|
||||
if (!wine_server_call_err( req ))
|
||||
{
|
||||
ret = reply->format;
|
||||
SetLastError( ERROR_SUCCESS );
|
||||
}
|
||||
}
|
||||
SetLastError( 0 );
|
||||
ret = USER_Driver->pEnumClipboardFormats( format );
|
||||
SERVER_END_REQ;
|
||||
|
||||
TRACE( "%s -> %s\n", debugstr_format( format ), debugstr_format( ret ));
|
||||
return ret;
|
||||
}
|
||||
|
@ -871,11 +880,18 @@ UINT WINAPI EnumClipboardFormats( UINT format )
|
|||
*/
|
||||
BOOL WINAPI IsClipboardFormatAvailable( UINT format )
|
||||
{
|
||||
BOOL ret;
|
||||
BOOL ret = FALSE;
|
||||
|
||||
if (!format) return FALSE;
|
||||
|
||||
USER_Driver->pUpdateClipboard();
|
||||
|
||||
ret = USER_Driver->pIsClipboardFormatAvailable( format );
|
||||
SERVER_START_REQ( get_clipboard_formats )
|
||||
{
|
||||
req->format = format;
|
||||
if (!wine_server_call_err( req )) ret = (reply->count > 0);
|
||||
}
|
||||
SERVER_END_REQ;
|
||||
TRACE( "%s -> %u\n", debugstr_format( format ), ret );
|
||||
return ret;
|
||||
}
|
||||
|
@ -886,28 +902,27 @@ BOOL WINAPI IsClipboardFormatAvailable( UINT format )
|
|||
*/
|
||||
BOOL WINAPI GetUpdatedClipboardFormats( UINT *formats, UINT size, UINT *out_size )
|
||||
{
|
||||
UINT i = 0, cf = 0;
|
||||
BOOL ret;
|
||||
|
||||
if (!out_size)
|
||||
{
|
||||
SetLastError( ERROR_NOACCESS );
|
||||
return FALSE;
|
||||
}
|
||||
if (!(*out_size = CountClipboardFormats())) return TRUE; /* nothing else to do */
|
||||
|
||||
if (!formats)
|
||||
USER_Driver->pUpdateClipboard();
|
||||
|
||||
SERVER_START_REQ( get_clipboard_formats )
|
||||
{
|
||||
SetLastError( ERROR_NOACCESS );
|
||||
return FALSE;
|
||||
if (formats) wine_server_set_reply( req, formats, size * sizeof(*formats) );
|
||||
ret = !wine_server_call_err( req );
|
||||
*out_size = reply->count;
|
||||
}
|
||||
if (size < *out_size)
|
||||
{
|
||||
SetLastError( ERROR_INSUFFICIENT_BUFFER );
|
||||
return FALSE;
|
||||
}
|
||||
/* FIXME: format list could change in the meantime */
|
||||
while ((cf = USER_Driver->pEnumClipboardFormats( cf ))) formats[i++] = cf;
|
||||
return TRUE;
|
||||
SERVER_END_REQ;
|
||||
|
||||
TRACE( "%p %u returning %u formats, ret %u\n", formats, size, *out_size, ret );
|
||||
if (!ret && !formats && *out_size) SetLastError( ERROR_NOACCESS );
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -105,7 +105,6 @@ static void set_clipboard_data_process( int arg )
|
|||
SetLastError( 0xdeadbeef );
|
||||
if (arg)
|
||||
{
|
||||
todo_wine_if( arg == 1 || arg == 3 )
|
||||
ok( IsClipboardFormatAvailable( CF_WAVE ), "process %u: CF_WAVE not available\n", arg );
|
||||
ret = SetClipboardData( CF_WAVE, GlobalAlloc( GMEM_DDESHARE | GMEM_ZEROINIT, 100 ));
|
||||
ok( ret != 0, "process %u: SetClipboardData failed err %u\n", arg, GetLastError() );
|
||||
|
@ -321,7 +320,7 @@ static void test_ClipboardOwner(void)
|
|||
ok(!GetClipboardOwner() && GetLastError() == 0xdeadbeef, "clipboard should not be owned\n");
|
||||
ok(!GetClipboardViewer() && GetLastError() == 0xdeadbeef, "viewer still exists\n");
|
||||
ok(!GetOpenClipboardWindow() && GetLastError() == 0xdeadbeef, "clipboard should not be open\n");
|
||||
todo_wine ok( !IsClipboardFormatAvailable( CF_WAVE ), "CF_WAVE available\n" );
|
||||
ok( !IsClipboardFormatAvailable( CF_WAVE ), "CF_WAVE available\n" );
|
||||
|
||||
SetLastError( 0xdeadbeef );
|
||||
ret = CloseClipboard();
|
||||
|
|
|
@ -4540,6 +4540,35 @@ struct set_clipboard_data_reply
|
|||
|
||||
|
||||
|
||||
struct get_clipboard_formats_request
|
||||
{
|
||||
struct request_header __header;
|
||||
unsigned int format;
|
||||
};
|
||||
struct get_clipboard_formats_reply
|
||||
{
|
||||
struct reply_header __header;
|
||||
unsigned int count;
|
||||
/* VARARG(formats,uints); */
|
||||
char __pad_12[4];
|
||||
};
|
||||
|
||||
|
||||
|
||||
struct enum_clipboard_formats_request
|
||||
{
|
||||
struct request_header __header;
|
||||
unsigned int previous;
|
||||
};
|
||||
struct enum_clipboard_formats_reply
|
||||
{
|
||||
struct reply_header __header;
|
||||
unsigned int format;
|
||||
char __pad_12[4];
|
||||
};
|
||||
|
||||
|
||||
|
||||
struct release_clipboard_request
|
||||
{
|
||||
struct request_header __header;
|
||||
|
@ -5743,6 +5772,8 @@ enum request
|
|||
REQ_set_clipboard_info,
|
||||
REQ_empty_clipboard,
|
||||
REQ_set_clipboard_data,
|
||||
REQ_get_clipboard_formats,
|
||||
REQ_enum_clipboard_formats,
|
||||
REQ_release_clipboard,
|
||||
REQ_get_clipboard_info,
|
||||
REQ_set_clipboard_viewer,
|
||||
|
@ -6031,6 +6062,8 @@ union generic_request
|
|||
struct set_clipboard_info_request set_clipboard_info_request;
|
||||
struct empty_clipboard_request empty_clipboard_request;
|
||||
struct set_clipboard_data_request set_clipboard_data_request;
|
||||
struct get_clipboard_formats_request get_clipboard_formats_request;
|
||||
struct enum_clipboard_formats_request enum_clipboard_formats_request;
|
||||
struct release_clipboard_request release_clipboard_request;
|
||||
struct get_clipboard_info_request get_clipboard_info_request;
|
||||
struct set_clipboard_viewer_request set_clipboard_viewer_request;
|
||||
|
@ -6317,6 +6350,8 @@ union generic_reply
|
|||
struct set_clipboard_info_reply set_clipboard_info_reply;
|
||||
struct empty_clipboard_reply empty_clipboard_reply;
|
||||
struct set_clipboard_data_reply set_clipboard_data_reply;
|
||||
struct get_clipboard_formats_reply get_clipboard_formats_reply;
|
||||
struct enum_clipboard_formats_reply enum_clipboard_formats_reply;
|
||||
struct release_clipboard_reply release_clipboard_reply;
|
||||
struct get_clipboard_info_reply get_clipboard_info_reply;
|
||||
struct set_clipboard_viewer_reply set_clipboard_viewer_reply;
|
||||
|
@ -6381,6 +6416,6 @@ union generic_reply
|
|||
struct terminate_job_reply terminate_job_reply;
|
||||
};
|
||||
|
||||
#define SERVER_PROTOCOL_VERSION 518
|
||||
#define SERVER_PROTOCOL_VERSION 519
|
||||
|
||||
#endif /* __WINE_WINE_SERVER_PROTOCOL_H */
|
||||
|
|
|
@ -411,6 +411,61 @@ DECL_HANDLER(set_clipboard_data)
|
|||
}
|
||||
|
||||
|
||||
/* retrieve a list of available formats */
|
||||
DECL_HANDLER(get_clipboard_formats)
|
||||
{
|
||||
struct clipboard *clipboard = get_process_clipboard();
|
||||
|
||||
if (!clipboard) return;
|
||||
|
||||
if (!req->format)
|
||||
{
|
||||
struct clip_format *format;
|
||||
unsigned int i = 0, *ptr;
|
||||
data_size_t size = clipboard->format_count * sizeof(unsigned int);
|
||||
|
||||
reply->count = clipboard->format_count;
|
||||
if (size <= get_reply_max_size())
|
||||
{
|
||||
if ((ptr = mem_alloc( size )))
|
||||
{
|
||||
LIST_FOR_EACH_ENTRY( format, &clipboard->formats, struct clip_format, entry )
|
||||
ptr[i++] = format->id;
|
||||
assert( i == clipboard->format_count );
|
||||
set_reply_data_ptr( ptr, size );
|
||||
}
|
||||
}
|
||||
else set_error( STATUS_BUFFER_TOO_SMALL );
|
||||
}
|
||||
else reply->count = (get_format( clipboard, req->format ) != NULL); /* query a single format */
|
||||
}
|
||||
|
||||
|
||||
/* retrieve the next available format */
|
||||
DECL_HANDLER(enum_clipboard_formats)
|
||||
{
|
||||
struct list *ptr;
|
||||
struct clipboard *clipboard = get_process_clipboard();
|
||||
|
||||
if (!clipboard) return;
|
||||
|
||||
if (clipboard->open_thread != current)
|
||||
{
|
||||
set_win32_error( ERROR_CLIPBOARD_NOT_OPEN );
|
||||
return;
|
||||
}
|
||||
|
||||
ptr = list_head( &clipboard->formats );
|
||||
if (req->previous)
|
||||
{
|
||||
while (ptr && LIST_ENTRY( ptr, struct clip_format, entry )->id != req->previous)
|
||||
ptr = list_next( &clipboard->formats, ptr );
|
||||
if (ptr) ptr = list_next( &clipboard->formats, ptr );
|
||||
}
|
||||
if (ptr) reply->format = LIST_ENTRY( ptr, struct clip_format, entry )->id;
|
||||
}
|
||||
|
||||
|
||||
/* empty the clipboard and grab ownership */
|
||||
DECL_HANDLER(empty_clipboard)
|
||||
{
|
||||
|
|
|
@ -3206,6 +3206,23 @@ enum caret_state
|
|||
@END
|
||||
|
||||
|
||||
/* Retrieve a list of available formats */
|
||||
@REQ(get_clipboard_formats)
|
||||
unsigned int format; /* specific format to query, return all if 0 */
|
||||
@REPLY
|
||||
unsigned int count; /* count of available formats */
|
||||
VARARG(formats,uints); /* array of available formats */
|
||||
@END
|
||||
|
||||
|
||||
/* Retrieve the next available format */
|
||||
@REQ(enum_clipboard_formats)
|
||||
unsigned int previous; /* previous format, or first if 0 */
|
||||
@REPLY
|
||||
unsigned int format; /* next format */
|
||||
@END
|
||||
|
||||
|
||||
/* Release ownership of the clipboard */
|
||||
@REQ(release_clipboard)
|
||||
user_handle_t owner; /* clipboard owner to release */
|
||||
|
|
|
@ -331,6 +331,8 @@ DECL_HANDLER(close_clipboard);
|
|||
DECL_HANDLER(set_clipboard_info);
|
||||
DECL_HANDLER(empty_clipboard);
|
||||
DECL_HANDLER(set_clipboard_data);
|
||||
DECL_HANDLER(get_clipboard_formats);
|
||||
DECL_HANDLER(enum_clipboard_formats);
|
||||
DECL_HANDLER(release_clipboard);
|
||||
DECL_HANDLER(get_clipboard_info);
|
||||
DECL_HANDLER(set_clipboard_viewer);
|
||||
|
@ -618,6 +620,8 @@ static const req_handler req_handlers[REQ_NB_REQUESTS] =
|
|||
(req_handler)req_set_clipboard_info,
|
||||
(req_handler)req_empty_clipboard,
|
||||
(req_handler)req_set_clipboard_data,
|
||||
(req_handler)req_get_clipboard_formats,
|
||||
(req_handler)req_enum_clipboard_formats,
|
||||
(req_handler)req_release_clipboard,
|
||||
(req_handler)req_get_clipboard_info,
|
||||
(req_handler)req_set_clipboard_viewer,
|
||||
|
@ -2046,6 +2050,14 @@ C_ASSERT( sizeof(struct set_clipboard_info_reply) == 32 );
|
|||
C_ASSERT( sizeof(struct empty_clipboard_request) == 16 );
|
||||
C_ASSERT( FIELD_OFFSET(struct set_clipboard_data_request, format) == 12 );
|
||||
C_ASSERT( sizeof(struct set_clipboard_data_request) == 16 );
|
||||
C_ASSERT( FIELD_OFFSET(struct get_clipboard_formats_request, format) == 12 );
|
||||
C_ASSERT( sizeof(struct get_clipboard_formats_request) == 16 );
|
||||
C_ASSERT( FIELD_OFFSET(struct get_clipboard_formats_reply, count) == 8 );
|
||||
C_ASSERT( sizeof(struct get_clipboard_formats_reply) == 16 );
|
||||
C_ASSERT( FIELD_OFFSET(struct enum_clipboard_formats_request, previous) == 12 );
|
||||
C_ASSERT( sizeof(struct enum_clipboard_formats_request) == 16 );
|
||||
C_ASSERT( FIELD_OFFSET(struct enum_clipboard_formats_reply, format) == 8 );
|
||||
C_ASSERT( sizeof(struct enum_clipboard_formats_reply) == 16 );
|
||||
C_ASSERT( FIELD_OFFSET(struct release_clipboard_request, owner) == 12 );
|
||||
C_ASSERT( sizeof(struct release_clipboard_request) == 16 );
|
||||
C_ASSERT( FIELD_OFFSET(struct release_clipboard_reply, viewer) == 8 );
|
||||
|
|
|
@ -3779,6 +3779,27 @@ static void dump_set_clipboard_data_request( const struct set_clipboard_data_req
|
|||
dump_varargs_bytes( ", data=", cur_size );
|
||||
}
|
||||
|
||||
static void dump_get_clipboard_formats_request( const struct get_clipboard_formats_request *req )
|
||||
{
|
||||
fprintf( stderr, " format=%08x", req->format );
|
||||
}
|
||||
|
||||
static void dump_get_clipboard_formats_reply( const struct get_clipboard_formats_reply *req )
|
||||
{
|
||||
fprintf( stderr, " count=%08x", req->count );
|
||||
dump_varargs_uints( ", formats=", cur_size );
|
||||
}
|
||||
|
||||
static void dump_enum_clipboard_formats_request( const struct enum_clipboard_formats_request *req )
|
||||
{
|
||||
fprintf( stderr, " previous=%08x", req->previous );
|
||||
}
|
||||
|
||||
static void dump_enum_clipboard_formats_reply( const struct enum_clipboard_formats_reply *req )
|
||||
{
|
||||
fprintf( stderr, " format=%08x", req->format );
|
||||
}
|
||||
|
||||
static void dump_release_clipboard_request( const struct release_clipboard_request *req )
|
||||
{
|
||||
fprintf( stderr, " owner=%08x", req->owner );
|
||||
|
@ -4652,6 +4673,8 @@ static const dump_func req_dumpers[REQ_NB_REQUESTS] = {
|
|||
(dump_func)dump_set_clipboard_info_request,
|
||||
(dump_func)dump_empty_clipboard_request,
|
||||
(dump_func)dump_set_clipboard_data_request,
|
||||
(dump_func)dump_get_clipboard_formats_request,
|
||||
(dump_func)dump_enum_clipboard_formats_request,
|
||||
(dump_func)dump_release_clipboard_request,
|
||||
(dump_func)dump_get_clipboard_info_request,
|
||||
(dump_func)dump_set_clipboard_viewer_request,
|
||||
|
@ -4936,6 +4959,8 @@ static const dump_func reply_dumpers[REQ_NB_REQUESTS] = {
|
|||
(dump_func)dump_set_clipboard_info_reply,
|
||||
NULL,
|
||||
NULL,
|
||||
(dump_func)dump_get_clipboard_formats_reply,
|
||||
(dump_func)dump_enum_clipboard_formats_reply,
|
||||
(dump_func)dump_release_clipboard_reply,
|
||||
(dump_func)dump_get_clipboard_info_reply,
|
||||
(dump_func)dump_set_clipboard_viewer_reply,
|
||||
|
@ -5220,6 +5245,8 @@ static const char * const req_names[REQ_NB_REQUESTS] = {
|
|||
"set_clipboard_info",
|
||||
"empty_clipboard",
|
||||
"set_clipboard_data",
|
||||
"get_clipboard_formats",
|
||||
"enum_clipboard_formats",
|
||||
"release_clipboard",
|
||||
"get_clipboard_info",
|
||||
"set_clipboard_viewer",
|
||||
|
|
Loading…
Reference in a new issue