This is an old revision of the document!


Input Polling / Input Controller

One of the basic features a game needs is the control of inputs. And it is not done with just checking which key is pressed or where the mouse is. Most games need much more than just reacting on clicks.

Imagine a combat game, where you allow users to have key-combos for special attacks and animations.

Therefor we provide the easy to use TGorillaInputController component to access keyboard, mouse and gamepad feedbacks. Also in combination!

HotKey

A HotKey is a combination of inputs that are simultanously active. Each HotKey can manage inputs from keyboard, mouse and/or gamepad. An input is a hardware message:

  • For keyboards, inputs are the pressed keys
  • For mouse, inputs are pressed mouse buttons
  • For gamepad, inputs are pressed gamepad buttons

You can define up to 4 inputs per device. Which means you can handle up to 12 simultanously active input messages.

In case you define an input in two different HotKeys, the system will detect the more important Hotkey. The importance is defined by the number of set inputs.

If a HotKey was detected, the controller will call the OnTriggered event and/or an attached TAction instance.

You are allowed to setup your HotKeys at design- and at runtime.

DesignTime

Because HotKeys were implemented by the TCollection component of Delphi, you can setup your combinations at design time.

  1. Drag a TGorillaInputController component onto your form and doubleclick the “HotKeys” property.
  2. In the Delphi Collection-Editor you can now add a new TGorillaHotKeyItem.
  3. Type in a unique name to identify your hotkey, create a OnTriggered event or attach a TAction component to it.
  4. In the next step we should add the input combination by double clicking the “Combinations” property.
  5. Here we can now add a new TGorillaHotKeyInputItem.
  6. In the item select the “Kind” of device.
  7. and add the message input code
  8. Repeat it for any further inputs you wish to combine.

Runtime

uses
  Gorilla.Controller.Input,
  Gorilla.Controller.Input.Consts;
 
procedure TForm1.DoOnHotKey(const AItem : TGorillaHotKeyItem; const ACurrentInput : TGorillaHotKeyRaw);
begin
  DebugOutput(Format('>>> HotKey: %s <<< === %s', [AItem.DisplayName, ACurrentInput.ToString()]));
end;
 
var 
  FInput : TGorillaInputController;
  LHotKey : TGorillaHotKeyItem;
 
  [...]
 
  FInput := TGorillaInputController.Create(Self);
 
  LHotKey := FInput.AddHotKey('TEST1');
  LHotKey.OnTriggered := DoOnHotKey;
  LHotKey.AddInput(TGorillaInputDeviceType.Keyboard, Ord(GORILLA_INPUT_KEY_ALT));
  LHotKey.AddInput(TGorillaInputDeviceType.Keyboard, Ord(GORILLA_INPUT_KEY_C));
  LHotKey.AddInput(TGorillaInputDeviceType.Keyboard, Ord(GORILLA_INPUT_KEY_RETURN));

Persistent Messages

Besides the HotKey settings the component supports persistent/continuously messages. A persistent message is a continuously notified message from the system and not a temporary message like a click or key-press.

Supported persistent messages are:

Message-Code Description
GORILLA_INPUT_MOUSE_POSITION latest mouse position
GORILLA_INPUT_GAMEPAD_TRIGGERS gamepad trigger values
GORILLA_INPUT_GAMEPAD_THUMBSTICK_POS_LEFT gamepad left thumbstick position
GORILLA_INPUT_GAMEPAD_THUMBSTICK_POS_RIGHT gamepad right thumbstick position

You can request those messages at runtime, like in the following code:

var LMPos  : TPoint;
    LMsg   : TGorillaInputMessage;
begin
  // request latest mouse position
  if FInput.GetPersistentMessage(TGorillaInputDeviceType.Mouse, GORILLA_INPUT_MOUSE_POSITION, LMsg) then
  begin
    LMPos := LMsg.Data.AsType<TPoint>();
  end
  else LMPos := TPoint.Zero;
 
  // show mouse position in form caption
  Self.Caption := Format('Gorilla 3D - Mouse: [%d;%d]', [LMPos.X, LMPos.Y]);

Input-Codes

All available InputCodes are defined in the Gorilla.Controller.Input.Consts unit.

Keyboard

Constant Value
GORILLA_INPUT_KEY_A'A'
GORILLA_INPUT_KEY_B'B'
GORILLA_INPUT_KEY_C 'C'
GORILLA_INPUT_KEY_D'D'
GORILLA_INPUT_KEY_E'E'
GORILLA_INPUT_KEY_F'F'
GORILLA_INPUT_KEY_G'G'
GORILLA_INPUT_KEY_H'H'
GORILLA_INPUT_KEY_I'I'
GORILLA_INPUT_KEY_J'J'
GORILLA_INPUT_KEY_K'K'
GORILLA_INPUT_KEY_L'L'
GORILLA_INPUT_KEY_M'M'
GORILLA_INPUT_KEY_N'N'
GORILLA_INPUT_KEY_O'O'
GORILLA_INPUT_KEY_P'P'
GORILLA_INPUT_KEY_Q'Q'
GORILLA_INPUT_KEY_R'R'
GORILLA_INPUT_KEY_S'S'
GORILLA_INPUT_KEY_T'T'
GORILLA_INPUT_KEY_U'U'
GORILLA_INPUT_KEY_V'V'
GORILLA_INPUT_KEY_W'W'
GORILLA_INPUT_KEY_X'X'
GORILLA_INPUT_KEY_Y'Y'
GORILLA_INPUT_KEY_Z'Z'
GORILLA_INPUT_KEY_0'0'
GORILLA_INPUT_KEY_1'1'
GORILLA_INPUT_KEY_2'2'
GORILLA_INPUT_KEY_3'3'
GORILLA_INPUT_KEY_4'4'
GORILLA_INPUT_KEY_5'5'
GORILLA_INPUT_KEY_6'6'
GORILLA_INPUT_KEY_7'7'
GORILLA_INPUT_KEY_8'8'
GORILLA_INPUT_KEY_9'9'
GORILLA_INPUT_KEY_ARROW_LEFT#37
GORILLA_INPUT_KEY_ARROW_UP#38
GORILLA_INPUT_KEY_ARROW_RIGHT#39
GORILLA_INPUT_KEY_ARROW_DOWN#40
GORILLA_INPUT_KEY_SPACE' '
GORILLA_INPUT_KEY_PLUS'+'
GORILLA_INPUT_KEY_MINUS'-'
GORILLA_INPUT_KEY_DOT'.'
GORILLA_INPUT_KEY_COMMA','
GORILLA_INPUT_KEY_HASH'#'
GORILLA_INPUT_KEY_DIV'/'
GORILLA_INPUT_KEY_STAR'*'
GORILLA_INPUT_KEY_EXCL'!'
GORILLA_INPUT_KEY_QUOTE'“'
GORILLA_INPUT_KEY_PARA'§'
GORILLA_INPUT_KEY_DOLLAR'$'
GORILLA_INPUT_KEY_EURO'€'
GORILLA_INPUT_KEY_AT'@'
GORILLA_INPUT_KEY_PERCENT'%'
GORILLA_INPUT_KEY_AND'&'
GORILLA_INPUT_KEY_BACKSLASH'\'
GORILLA_INPUT_KEY_BRACKETOPEN'('
GORILLA_INPUT_KEY_BRACKETCLOSE')'
GORILLA_INPUT_KEY_EQUAL'='
GORILLA_INPUT_KEY_QUESTION'?'
GORILLA_INPUT_KEY_TILDE'~'
GORILLA_INPUT_KEY_UNDERSCORE'_'
GORILLA_INPUT_KEY_SEMICOLON';'
GORILLA_INPUT_KEY_COLON':'
GORILLA_INPUT_KEY_BAR''
GORILLA_INPUT_KEY_TAGOPEN'<'
GORILLA_INPUT_KEY_TAGCLOSE'>'
GORILLA_INPUT_KEY_SHIFT_BACKSPACE#8
GORILLA_INPUT_KEY_SHIFT_TAB#9
GORILLA_INPUT_KEY_LINEFEED#$0A
GORILLA_INPUT_KEY_RETURN#$0D
GORILLA_INPUT_KEY_ESCAPE#$1B
GORILLA_INPUT_KEY_DELETE#$7F
GORILLA_INPUT_KEY_SHIFT_CAPS#20
GORILLA_INPUT_KEY_SHIFT_LEFT#160
GORILLA_INPUT_KEY_SHIFT_RIGHT#161
GORILLA_INPUT_KEY_CTRL_LEFT#162
GORILLA_INPUT_KEY_CTRL_RIGHT#163
GORILLA_INPUT_KEY_ALT#164
GORILLA_INPUT_KEY_ALTGR#165

Mouse

Constant Value
GORILLA_INPUT_MOUSE_POSITION0
GORILLA_INPUT_MOUSE_LBUTTON1
GORILLA_INPUT_MOUSE_LBUTTON_DBLCLK2
GORILLA_INPUT_MOUSE_RBUTTON3
GORILLA_INPUT_MOUSE_RBUTTON_DBLCLK4
GORILLA_INPUT_MOUSE_MBUTTON5
GORILLA_INPUT_MOUSE_MBUTTON_DBLCLK6
GORILLA_INPUT_MOUSE_XBUTTON7
GORILLA_INPUT_MOUSE_XBUTTON_DBLCLK8
GORILLA_INPUT_MOUSE_WHEEL9

GamePad

Constant Value
GORILLA_INPUT_GAMEPAD_CONNECTED$1000
GORILLA_INPUT_GAMEPAD_DISCONNECTED$1001
GORILLA_INPUT_GAMEPAD_DPAD_UP0
GORILLA_INPUT_GAMEPAD_DPAD_DOWN1
GORILLA_INPUT_GAMEPAD_DPAD_LEFT2
GORILLA_INPUT_GAMEPAD_DPAD_RIGHT3
GORILLA_INPUT_GAMEPAD_START_BUTTON4
GORILLA_INPUT_GAMEPAD_MODEBUTTON5
GORILLA_INPUT_GAMEPAD_BACKBUTTON6
GORILLA_INPUT_GAMEPAD_THUMBSTICK_LEFT7
GORILLA_INPUT_GAMEPAD_THUMBSTICK_RIGHT8
GORILLA_INPUT_GAMEPAD_SHOULDER_LEFT9
GORILLA_INPUT_GAMEPAD_SHOULDER_RIGHT10
GORILLA_INPUT_GAMEPAD_BUTTON_A11
GORILLA_INPUT_GAMEPAD_BUTTON_B12
GORILLA_INPUT_GAMEPAD_BUTTON_X13
GORILLA_INPUT_GAMEPAD_BUTTON_Y14
GORILLA_INPUT_GAMEPAD_TRIGGERS$100
GORILLA_INPUT_GAMEPAD_THUMBSTICK_POS_LEFT$200
GORILLA_INPUT_GAMEPAD_THUMBSTICK_POS_RIGHT$201

Sequences

HotKeys are a nice feature, but only work for simultaneous inputs.

Imagine you build a combat game, where attacks or defences are represented by input-combos. For example a user needs to press Button A, then Button B and then Button X to do roundhouse kick. Therefor sequences come in place. Sequences are a descriptive plan of hotkeys, where the order is important.

So Sequence #1

Button A + Button B + Button X

is not the same like

Button B + Button A + Button X

DesignTime

Runtime

procedure TForm1.DoOnSequence(const ASequence : TGorillaInputSequenceItem);
begin
  DebugOutput(Format('>>> Sequence: %s <<<', [ASequence.DisplayName]));
end;
 
[...]
 
var LSequence: TGorillaInputSequenceItem;
    LSeq1HK1, LSeq1HK2, LSeq1HK3 : TGorillaHotKeyItem;
 
  [...]
 
  // create hotkey #1
  LSeq1HK1 := FInput.AddHotKey('STRIDE LEFT');
  LSeq1HK1.AddInput(TGorillaInputDeviceType.Keyboard, Ord(GORILLA_INPUT_KEY_A));
 
  // create hotkey #2
  LSeq1HK2 := FInput.AddHotKey('FORWARD');
  LSeq1HK2.AddInput(TGorillaInputDeviceType.Keyboard, Ord(GORILLA_INPUT_KEY_W));
 
  // create hotkey #3
  LSeq1HK3 := FInput.AddHotKey('STRIDE RIGHT');
  LSeq1HK3.AddInput(TGorillaInputDeviceType.Keyboard, Ord(GORILLA_INPUT_KEY_D));
 
  // create the sequence and add the relevant hotkeys
  LSequence := FInput.AddSequence('TEST SEQUENCE', [LSeq1HK1, LSeq1HK2, LSeq1HK3]);
  LSequence.OnTriggered := DoOnSequence;