Prechádzať zdrojové kódy

Win32 shift key handling fix, version 2.

woollybah 7 rokov pred
rodič
commit
4d99d90c3d

+ 5 - 11
polledinput.mod/polledinput.bmx

@@ -13,7 +13,7 @@ ModuleInfo "Copyright: Blitz Research Ltd"
 ModuleInfo "Modserver: BRL"
 
 ModuleInfo "History: 1.03"
-ModuleInfo "History: Improved Win32 KeyDown support."
+ModuleInfo "History: Improved Win32 KeyDown handling."
 ModuleInfo "History: 1.02"
 ModuleInfo "History: Added SetAutoPoll() function."
 ModuleInfo "History: 1.01 Release"
@@ -23,10 +23,6 @@ Import BRL.System
 
 Private
 
-Extern "Win32"
-  Function GetAsyncKeyState:Short(key:Int)="SHORT __stdcall GetAsyncKeyState(int)!"
-End Extern
-
 Global enabled
 Global autoPoll=True
 Global inputSource:Object
@@ -46,10 +42,12 @@ Function Hook:Object( id,data:Object,context:Object )
 	If inputSource And inputSource<>ev.source Return data
 	
 	Select ev.id
-	Case EVENT_KEYDOWN
+	Case EVENT_KEYDOWN, EVENT_KEYREPEAT
 		If Not keyStates[ev.data]
 			keyStates[ev.data]=1
-			keyHits[ev.data]:+1
+			If ev.id <> EVENT_KEYREPEAT
+				keyHits[ev.data]:+1
+			End If
 		EndIf
 	Case EVENT_KEYUP
 		keyStates[ev.data]=0
@@ -156,12 +154,8 @@ about:
 See the #{key codes} module for a list of valid keycodes.
 End Rem
 Function KeyDown( key )
-?win32
-	Return (GetAsyncKeyState(key) & $8000) <> 0
-?Not win32
 	If autoPoll PollSystem
 	Return keyStates[key]
-?
 End Function
 
 Rem

+ 35 - 0
systemdefault.mod/system.win32.c

@@ -10,6 +10,10 @@ typedef struct AsyncOp{
 	int asyncInfo;
 }AsyncOp;
 
+// track shift key state because Windows doesn't report events when the two shift
+// keys are being pressed at the same time, and then one released.
+static int shiftKeyState[2];
+
 static int _usew;
 
 static HHOOK msghook;
@@ -129,11 +133,31 @@ void bbSystemEmitOSEvent( HWND hwnd,UINT msg,WPARAM wp,LPARAM lp,BBObject *sourc
 		if( wp<1 || wp>255 ) return;
 		id=( lp & 0x40000000 ) ? BBEVENT_KEYREPEAT : BBEVENT_KEYDOWN;
 		data=keyCode( wp,lp );
+		
+		switch(data) {
+			case VK_LSHIFT:
+				shiftKeyState[0] = 1;
+				break;
+			case VK_RSHIFT:
+				shiftKeyState[1] = 1;
+				break;
+		}
+		
 		break;
 	case WM_KEYUP:case WM_SYSKEYUP:
 		if( wp<1 || wp>255 ) return;
 		id=BBEVENT_KEYUP;
 		data=keyCode( wp,lp );
+
+		switch(data) {
+			case VK_LSHIFT:
+				shiftKeyState[0] = 0;
+				break;
+			case VK_RSHIFT:
+				shiftKeyState[1] = 0;
+				break;
+		}
+
 		break;
 	case WM_CHAR:case WM_SYSCHAR:
 		id=BBEVENT_KEYCHAR;
@@ -256,6 +280,17 @@ void bbSystemPoll(){
 		TranslateMessage( &msg );
 		DispatchMessage( &msg );
 	}
+
+	// test shift keys current state
+	if (shiftKeyState[0] && !(GetKeyState(VK_LSHIFT) & 0x8000)) {
+		shiftKeyState[0] = 0;
+		bbSystemEmitEvent( BBEVENT_KEYUP,&bbNullObject,VK_LSHIFT,mods,0,0,&bbNullObject );
+	}
+
+	if (shiftKeyState[1] && !(GetKeyState(VK_RSHIFT) & 0x8000)) {
+		shiftKeyState[1] = 0;
+		bbSystemEmitEvent( BBEVENT_KEYUP,&bbNullObject,VK_RSHIFT,mods,0,0,&bbNullObject );
+	}
 }
 
 void bbSystemWait(){