server: Maintain the "set since last time" bit for the global keystate.

This commit is contained in:
Alexandre Julliard 2011-02-28 21:43:44 +01:00
parent b9e4b5a28c
commit 22468ec65c
1 changed files with 18 additions and 13 deletions

View File

@ -1106,13 +1106,14 @@ static void set_input_key_state( unsigned char *keystate, unsigned char key, int
if (down) if (down)
{ {
if (!(keystate[key] & 0x80)) keystate[key] ^= 0x01; if (!(keystate[key] & 0x80)) keystate[key] ^= 0x01;
keystate[key] |= 0x80; keystate[key] |= down;
} }
else keystate[key] &= ~0x80; else keystate[key] &= ~0x80;
} }
/* update the input key state for a keyboard message */ /* update the input key state for a keyboard message */
static void update_input_key_state( unsigned char *keystate, const struct message *msg ) static void update_input_key_state( struct desktop *desktop, unsigned char *keystate,
const struct message *msg )
{ {
unsigned char key; unsigned char key;
int down = 0; int down = 0;
@ -1120,25 +1121,25 @@ static void update_input_key_state( unsigned char *keystate, const struct messag
switch (msg->msg) switch (msg->msg)
{ {
case WM_LBUTTONDOWN: case WM_LBUTTONDOWN:
down = 1; down = (keystate == desktop->keystate) ? 0xc0 : 0x80;
/* fall through */ /* fall through */
case WM_LBUTTONUP: case WM_LBUTTONUP:
set_input_key_state( keystate, VK_LBUTTON, down ); set_input_key_state( keystate, VK_LBUTTON, down );
break; break;
case WM_MBUTTONDOWN: case WM_MBUTTONDOWN:
down = 1; down = (keystate == desktop->keystate) ? 0xc0 : 0x80;
/* fall through */ /* fall through */
case WM_MBUTTONUP: case WM_MBUTTONUP:
set_input_key_state( keystate, VK_MBUTTON, down ); set_input_key_state( keystate, VK_MBUTTON, down );
break; break;
case WM_RBUTTONDOWN: case WM_RBUTTONDOWN:
down = 1; down = (keystate == desktop->keystate) ? 0xc0 : 0x80;
/* fall through */ /* fall through */
case WM_RBUTTONUP: case WM_RBUTTONUP:
set_input_key_state( keystate, VK_RBUTTON, down ); set_input_key_state( keystate, VK_RBUTTON, down );
break; break;
case WM_XBUTTONDOWN: case WM_XBUTTONDOWN:
down = 1; down = (keystate == desktop->keystate) ? 0xc0 : 0x80;
/* fall through */ /* fall through */
case WM_XBUTTONUP: case WM_XBUTTONUP:
if (msg->wparam == XBUTTON1) set_input_key_state( keystate, VK_XBUTTON1, down ); if (msg->wparam == XBUTTON1) set_input_key_state( keystate, VK_XBUTTON1, down );
@ -1146,7 +1147,7 @@ static void update_input_key_state( unsigned char *keystate, const struct messag
break; break;
case WM_KEYDOWN: case WM_KEYDOWN:
case WM_SYSKEYDOWN: case WM_SYSKEYDOWN:
down = 1; down = (keystate == desktop->keystate) ? 0xc0 : 0x80;
/* fall through */ /* fall through */
case WM_KEYUP: case WM_KEYUP:
case WM_SYSKEYUP: case WM_SYSKEYUP:
@ -1229,7 +1230,7 @@ static void release_hardware_message( struct msg_queue *queue, unsigned int hw_i
} }
if (remove) if (remove)
{ {
update_input_key_state( input->keystate, msg ); update_input_key_state( input->desktop, input->keystate, msg );
list_remove( &msg->entry ); list_remove( &msg->entry );
free_message( msg ); free_message( msg );
} }
@ -1280,7 +1281,7 @@ static void queue_hardware_message( struct desktop *desktop, struct thread_input
unsigned int msg_code; unsigned int msg_code;
struct hardware_msg_data *data = msg->data; struct hardware_msg_data *data = msg->data;
update_input_key_state( desktop->keystate, msg ); update_input_key_state( desktop, desktop->keystate, msg );
last_input_time = get_tick_count(); last_input_time = get_tick_count();
if (!is_keyboard_msg( msg )) if (!is_keyboard_msg( msg ))
@ -1300,7 +1301,7 @@ static void queue_hardware_message( struct desktop *desktop, struct thread_input
win = find_hardware_message_window( input, msg, &msg_code ); win = find_hardware_message_window( input, msg, &msg_code );
if (!win || !(thread = get_window_thread(win))) if (!win || !(thread = get_window_thread(win)))
{ {
if (input) update_input_key_state( input->keystate, msg ); if (input) update_input_key_state( input->desktop, input->keystate, msg );
free( msg ); free( msg );
return; return;
} }
@ -1390,7 +1391,7 @@ static int get_hardware_message( struct thread *thread, unsigned int hw_id, user
if (!win || !(win_thread = get_window_thread( win ))) if (!win || !(win_thread = get_window_thread( win )))
{ {
/* no window at all, remove it */ /* no window at all, remove it */
update_input_key_state( input->keystate, msg ); update_input_key_state( input->desktop, input->keystate, msg );
list_remove( &msg->entry ); list_remove( &msg->entry );
free_message( msg ); free_message( msg );
continue; continue;
@ -1406,7 +1407,7 @@ static int get_hardware_message( struct thread *thread, unsigned int hw_id, user
else else
{ {
/* for another thread input, drop it */ /* for another thread input, drop it */
update_input_key_state( input->keystate, msg ); update_input_key_state( input->desktop, input->keystate, msg );
list_remove( &msg->entry ); list_remove( &msg->entry );
free_message( msg ); free_message( msg );
} }
@ -2117,7 +2118,11 @@ DECL_HANDLER(get_key_state)
if (!req->tid) /* get global async key state */ if (!req->tid) /* get global async key state */
{ {
if (!(desktop = get_thread_desktop( current, 0 ))) return; if (!(desktop = get_thread_desktop( current, 0 ))) return;
if (req->key >= 0) reply->state = desktop->keystate[req->key & 0xff]; if (req->key >= 0)
{
reply->state = desktop->keystate[req->key & 0xff];
desktop->keystate[req->key & 0xff] &= ~0x40;
}
set_reply_data( desktop->keystate, size ); set_reply_data( desktop->keystate, size );
release_object( desktop ); release_object( desktop );
} }