src/video/x11/SDL_x11events.c
changeset 111 53e3d8ba4321
parent 88 71774090f286
child 161 eb6b76a95f2d
     1.1 --- a/src/video/x11/SDL_x11events.c	Sat Jul 14 19:11:26 2001 +0000
     1.2 +++ b/src/video/x11/SDL_x11events.c	Sat Jul 14 20:37:24 2001 +0000
     1.3 @@ -843,6 +843,10 @@
     1.4  	KeyCode xcode[SDLK_LAST];
     1.5  	Uint8 new_kstate[SDLK_LAST];
     1.6  	Uint8 *kstate = SDL_GetKeyState(NULL);
     1.7 +	SDLMod modstate;
     1.8 +	Window junk_window;
     1.9 +	int x, y;
    1.10 +	unsigned int mask;
    1.11  
    1.12  	/* The first time the window is mapped, we initialize key state */
    1.13  	if ( ! key_vec ) {
    1.14 @@ -850,11 +854,31 @@
    1.15  		XQueryKeymap(display, keys_return);
    1.16  		gen_event = 0;
    1.17  	} else {
    1.18 +#if 1 /* We no longer generate key down events, just update state */
    1.19 +		gen_event = 0;
    1.20 +#else
    1.21  		gen_event = 1;
    1.22 +#endif
    1.23  	}
    1.24  
    1.25 -	/* Zero the new state and generate it */
    1.26 -	memset(new_kstate, 0, sizeof(new_kstate));
    1.27 +	/* Get the keyboard modifier state */
    1.28 +	modstate = 0;
    1.29 +	get_modifier_masks(display);
    1.30 +	if ( XQueryPointer(display, DefaultRootWindow(display),
    1.31 +		&junk_window, &junk_window, &x, &y, &x, &y, &mask) ) {
    1.32 +		if ( mask & LockMask ) {
    1.33 +			modstate |= KMOD_CAPS;
    1.34 +		}
    1.35 +		if ( mask & mode_switch_mask ) {
    1.36 +			modstate |= KMOD_MODE;
    1.37 +		}
    1.38 +		if ( mask & num_mask ) {
    1.39 +			modstate |= KMOD_NUM;
    1.40 +		}
    1.41 +	}
    1.42 +
    1.43 +	/* Zero the new keyboard state and generate it */
    1.44 +	memset(new_kstate, SDL_RELEASED, sizeof(new_kstate));
    1.45  	/*
    1.46  	 * An obvious optimisation is to check entire longwords at a time in
    1.47  	 * both loops, but we can't be sure the arrays are aligned so it's not
    1.48 @@ -869,17 +893,47 @@
    1.49  				SDL_keysym sk;
    1.50  				KeyCode kc = i << 3 | j;
    1.51  				X11_TranslateKey(display, NULL, kc, &sk);
    1.52 -				new_kstate[sk.sym] = 1;
    1.53 +				new_kstate[sk.sym] = SDL_PRESSED;
    1.54  				xcode[sk.sym] = kc;
    1.55  			}
    1.56  		}
    1.57  	}
    1.58  	for(i = SDLK_FIRST+1; i < SDLK_LAST; i++) {
    1.59 -		int st;
    1.60 -		SDL_keysym sk;
    1.61 +		int state = new_kstate[i];
    1.62  
    1.63 -		if(kstate[i] == new_kstate[i])
    1.64 +		if ( state == SDL_PRESSED ) {
    1.65 +			switch (i) {
    1.66 +				case SDLK_LSHIFT:
    1.67 +					modstate |= KMOD_LSHIFT;
    1.68 +					break;
    1.69 +				case SDLK_RSHIFT:
    1.70 +					modstate |= KMOD_RSHIFT;
    1.71 +					break;
    1.72 +				case SDLK_LCTRL:
    1.73 +					modstate |= KMOD_LCTRL;
    1.74 +					break;
    1.75 +				case SDLK_RCTRL:
    1.76 +					modstate |= KMOD_RCTRL;
    1.77 +					break;
    1.78 +				case SDLK_LALT:
    1.79 +					modstate |= KMOD_LALT;
    1.80 +					break;
    1.81 +				case SDLK_RALT:
    1.82 +					modstate |= KMOD_RALT;
    1.83 +					break;
    1.84 +				case SDLK_LMETA:
    1.85 +					modstate |= KMOD_LMETA;
    1.86 +					break;
    1.87 +				case SDLK_RMETA:
    1.88 +					modstate |= KMOD_RMETA;
    1.89 +					break;
    1.90 +				default:
    1.91 +					break;
    1.92 +			}
    1.93 +		}
    1.94 +		if ( kstate[i] == state )
    1.95  			continue;
    1.96 +
    1.97  		/*
    1.98  		 * Send a fake keyboard event correcting the difference between
    1.99  		 * SDL's keyboard state and the actual. Note that there is no
   1.100 @@ -887,16 +941,31 @@
   1.101  		 * keys are released when focus is lost only keypresses should
   1.102  		 * be sent here
   1.103  		 */
   1.104 -		st = new_kstate[i] ? SDL_PRESSED : SDL_RELEASED;
   1.105 -		memset(&sk, 0, sizeof(sk));
   1.106 -		sk.sym = i;
   1.107 -		sk.scancode = xcode[i];		/* only valid for key press */
   1.108  		if ( gen_event ) {
   1.109 -			SDL_PrivateKeyboard(st, &sk);
   1.110 +			SDL_keysym sk;
   1.111 +			memset(&sk, 0, sizeof(sk));
   1.112 +			sk.sym = i;
   1.113 +			sk.scancode = xcode[i];	/* only valid for key press */
   1.114 +			SDL_PrivateKeyboard(state, &sk);
   1.115  		} else {
   1.116 -			kstate[i] = new_kstate[i];
   1.117 +			kstate[i] = state;
   1.118  		}
   1.119  	}
   1.120 +
   1.121 +	/* Hack - set toggle key state */
   1.122 +	if ( modstate & KMOD_CAPS ) {
   1.123 +		kstate[SDLK_CAPSLOCK] = SDL_PRESSED;
   1.124 +	} else {
   1.125 +		kstate[SDLK_CAPSLOCK] = SDL_RELEASED;
   1.126 +	}
   1.127 +	if ( modstate & KMOD_NUM ) {
   1.128 +		kstate[SDLK_NUMLOCK] = SDL_PRESSED;
   1.129 +	} else {
   1.130 +		kstate[SDLK_NUMLOCK] = SDL_RELEASED;
   1.131 +	}
   1.132 +
   1.133 +	/* Set the final modifier state */
   1.134 +	SDL_SetModState(modstate);
   1.135  }
   1.136  
   1.137  void X11_InitOSKeymap(_THIS)