views:

421

answers:

4

Hello, I'm developing for Windows Mobile in C++, and i'm running into a problem - I added my window class, and in it i handle the keyboard input with my WndProc implementation. The problem is that i'm getting the wrong codes, and identifying keys such as the func key incorrectly. And to make it worse, the values i'm getting (the wParam of the WM_KEYDOWN message) differ between the two phones i have here for testing - who knows what will happen on other phones.

After playing around with it for ages, i found out that if i only create a window from the predefined "EDIT" class, i actually do get the input correctly ( in terms of letters/keys ). So the problem must not be in the phone, but rather the modes of getting messages (a bit of a newbie in win32, excuse me for lack of knowledge). I tried playing around with input modes, but sending a message to my window using EM_NUMBERS and the such, always failed.

So what i would want to do ( though i'm open for suggestions ), is somehow just get the characters from some hidden EDIT window, and forward them to my window. (Though i still need my window to have the focus so it would react correctly to messages different from WM_KEYDOWN and the like)

Is there any way to do this?

This is the 3'rd time i'm asking regarding this issue, i am eternally grateful to everyone who tried to help so far ( though would be even more grateful if i had managed to solve my problem)

Thanks alot!!

Dan

here are some code exercpts :

Class registration :
WNDCLASS wc; wc.style = CS_HREDRAW | CS_VREDRAW;
wc.lpfnWndProc = WndProc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = hInstance;
wc.hIcon = LoadIcon(hInstance, MAKEINTRESOURCE(IDI_ROADMAP));
wc.hCursor = 0;
wc.hbrBackground = (HBRUSH) GetStockObject(WHITE_BRUSH);
wc.lpszMenuName = 0;
wc.lpszClassName = szWindowClass;

window creation
if (width == -1) width = CW_USEDEFAULT;
if (height == -1) height = CW_USEDEFAULT;
RoadMapMainWindow = CreateWindow(g_szWindowClass, szTitle, OVERLAPPEDWINDOW,
CW_USEDEFAULT, CW_USEDEFAULT, width, height, NULL,
NULL, g_hInst, NULL);

MessageLoop
// Main message loop:
while (GetMessage(&msg, NULL, 0, 0))
{ if (!TranslateAccelerator(msg.hwnd, hAccelTable, &msg))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}

WNDPROC excerpt
case WM_KEYDOWN:
{
WORD Code = (WORD)wParam;
int iRepeatTimes = (lParam & 0x0000FFFF);
int iScanCode = (lParam & 0x00FF0000) >> 16;
BOOL bALT_IsDown = (lParam & 0x20000000)? TRUE: FALSE;
BOOL bAlreadyPressed= (lParam & 0x40000000)? TRUE: FALSE;
BOOL bNowReleased = (lParam & 0x80000000)? TRUE: FALSE;
return DefWindowProc(hWnd, message, wParam, lParam);
}

A: 

I've not had any problems like you describe, so I'd really like to see a bare-bones set of code that repros this. It is known that some phones get spurrious user-range messages but these shouldn't be affecting you at the level you're at. The fact that you're getting wrong codes for something so basic indicates to me that you must have something wrong in your window creation or message handling code.

ctacke
i added some code excerpts below
dan
A: 

I added code here before, but now i edited it into the question

dan
these should be in the question itself, not in a separate answer
ctacke
+2  A: 

The wParam of WM_KEYDOWN is a virtual key code that is not really constrained to be an ascii (or unicode) character - its simply a code that uniquely identifies the key on the platform.

If you want the 'text' - you want to wait for the WM_CHAR message - the wParam of WM_CHAR will be the actual character value that the user entered.


More Info - in your application loop - where you call TranslateMessage - it is actually the job of TranslateMessage to spot WM_KEYDOWN messages and synthesize and post the corresponding WM_CHAR messages.


TranslateAccelerator seems to be the only thing that can interfere with posted messages. Of course, sometimes very unusual behaviour can manifest if the windows message proc is (or is not) handing messages to DefWindowProc at the wrong time. Why for example do you have an explicit call to DefWindowProc in your WM_KEYDOWN handler? The easiest way to handle that correctly is to have DefWindowProc as the last thing your window proc does so that all messages, handled and unhandled, go there by default. the exceptional case would be messages where you want to prevent DefWindowProc getting the message (WM_PAINT if you handle it for example).


You also keep mentioning trying to use Edit_SetInputMode - Edit_SetInputMode sends a message to the window: EM_SETINPUTMODE - which is a message only understood by EDIT controls. As you have registered your own window class, 'EM_SETINPUTMODE` is going to do nothing.

Chris Becke
i actually have the also a WM_CHAR code, Problem is that unfortunately, That's exactly the bug - On some keys i get the KEYDOWN message, but that does not get translated properly to the CHAR messages. ( and sometimes it does get translated, but to a different character :( )
dan
If WM_CHAR isn't what you expect, then you have some bigger problem somewhere and these symtoms are indications of something more fundamental.
Chris Becke
SO what can cause WM_KEYDOWN not to be interpereted to WM_CHAR?Can you see anything wrong with my class definition?
dan
By the way - i USUALLY get WM_CHAR, only on some characters i do not...
dan
So if you make a really, really basic app with just one Window and this handler, do you get the proper messages?
ctacke
nope - still get wrong message codes :(
dan
A: 

I am just guessing, but maybe your app is an Ansi app? That could maybe explain that different codepages give you different keycodes. So have you tried to make it all Unicode in the project settings, and define the string constants accordingly? And did you try ctacke's suggestion to make a really basic app?

Adam