PDA

View Full Version : (OnKeyPress) Is arrow key pressed?



NecroDOME
23-01-2007, 09:41 PM
Hi there,

I'm trying to grab some keyboard input trough OnKeyPress but it's not returning an event when I press my arrow keys.
I need those keys with the repeat delay and repeat rate from windows. Just like pressing the 'A', the A appears on screen, a short pause and then it just 'AAAAAAAAAAAAAA' (and so on)... you get the point...

I do NOT want to use OnKeyDown or OnKeyUp!!

(grabbing from a basic form in Turbo Delphi)

Thnx

czar
23-01-2007, 10:07 PM
Are you not able to use keydown in this fashion?

Set a variable to indicate which arrow went do and reset on keyup.

MyKey = key


That way in your time loop you respond say every 75 ms if the arrow key is still down.



if TimeGetTime > TimeToRespondgagain then
begin
if MyKey = vk_left then do_my_stuff;
TimeToRespondgagain := TimeGetTime + 75;

end;



The arrow keys are not sent as a message to the keypress method

Nitrogen
23-01-2007, 10:15 PM
Or....

Just use the raw windows messages:


unit Unit1;

interface

uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs;

type
TForm1 = class(TForm)
private
{ Private declarations }
public
procedure WMKeyDown(var Message : TWMKeyDown); message WM_KEYDOWN;
{ Public declarations }
end;

var
Form1: TForm1;

implementation

{$R *.dfm}

{ TForm1 }

procedure TForm1.WMKeyDown(var Message: TWMKeyDown);
begin
if message.CharCode = VK_LEFT then
form1.Left := form1.Left- 2;
if message.CharCode = VK_RIGHT then
form1.Left := form1.Left+ 2;
if message.CharCode = VK_UP then
form1.top := form1.top- 2;
if message.CharCode = VK_DOWN then
form1.top := form1.top+ 2;

end;

end.


Works quite well. With a delay and repeats.

czar
23-01-2007, 10:18 PM
Only other thing I can think is write a keyboard hook

NecroDOME
23-01-2007, 10:57 PM
it's working, but not really as I expected... now it's only grabs 'ABC' and not 'abc' (upper case only). I need it for some text input. WM_CHAR doesn't return the arrow keys and WM_KEYDOWN doesn't return the lower case chars. And it makes % and & from arrow chars.

jdarling
24-01-2007, 02:08 PM
it's working, but not really as I expected... now it's only grabs 'ABC' and not 'abc' (upper case only). I need it for some text input. WM_CHAR doesn't return the arrow keys and WM_KEYDOWN doesn't return the lower case chars. And it makes % and & from arrow chars.

Test for VK_SHIFT being down as well, then case as appropriate. Of course, you can also split your code into two areas, one in the standard windows handler, and the other in the standard OnKeyDown. The following code may help you out as well:

// IsKeyDown
//
function IsKeyDown(c : Char) : Boolean;
var
vk : Integer;
begin
// '$FF' filters out translators like Shift, Ctrl, Alt
vk:=VkKeyScan(c) and $FF;
if vk<>$FF then
Result:=(GetAsyncKeyState(vk)<0>0);
if Result then vLastWheelDelta:=0;
end;
VK_MOUSEWHEELDOWN : begin
Result:=(vLastWheelDelta<0);
if Result then vLastWheelDelta:=0;
end;
else
Result:=(GetAsyncKeyState(vk)<0);
end;
end;

This is taken from GLScene, but its not dependent upon GLScene.

NecroDOME
25-01-2007, 12:28 PM
Thanx, I try it as soon as I get home!

NecroDOME
26-01-2007, 01:28 AM
Is there a function that can convert virtual keys (VK) to chars ? I still don't recieve lower case chars from KeyDown...

Traveler
26-01-2007, 08:45 AM
Continuing on Nitrogens code, you could do something like


if &#40;message.CharCode in &#91;ord&#40;'A'&#41;.. ord&#40;'Z'&#41;&#93;&#41; or &#40;message.CharCode = vk_space&#41; then
yourText &#58;= yourText + lowercase&#40;chr&#40;message.CharCode&#41;&#41;

NecroDOME
26-01-2007, 12:33 PM
I got it working. I used Nitrogen raw windows messages for arrows and special keys and a OnFormKeyPress for catch chars.