Skip to content

Input

Learn how to handle player input from keyboard, mouse, and gamepads in your Brine2D games.


Quick Start

using Brine2D.Input;

public class GameScene : Scene
{
    protected override void OnUpdate(GameTime gameTime)
    {
        var speed = 200f * (float)gameTime.DeltaTime;

        // Keyboard
        if (Input.IsKeyDown(Key.W)) _position.Y -= speed;
        if (Input.IsKeyDown(Key.S)) _position.Y += speed;
        if (Input.IsKeyDown(Key.A)) _position.X -= speed;
        if (Input.IsKeyDown(Key.D)) _position.X += speed;

        // Mouse
        if (Input.IsMouseButtonPressed(MouseButton.Left))
            Logger.LogInformation("Clicked at {Pos}", Input.MousePosition);

        // Gamepad
        if (Input.IsGamepadButtonPressed(GamepadButton.A))
            Logger.LogInformation("Gamepad A pressed");
    }
}

Topics

Getting Started

Guide Description Difficulty
Keyboard Handle keyboard input ⭐ Beginner
Mouse Mouse position, clicks, and scroll wheel ⭐ Beginner

Advanced

Guide Description Difficulty
Gamepad Support Controller/gamepad input ⭐⭐ Intermediate
Input Actions Rebindable logical actions with multiple bindings ⭐⭐ Intermediate
Input Layers Priority-based input routing for UI ⭐⭐⭐ Advanced

Key Concepts

The Input Framework Property

Input is an IInputContext available on every Scene from OnLoadAsync onwards -- no constructor injection needed:

public class GameScene : Scene
{
    protected override void OnUpdate(GameTime gameTime)
    {
        if (Input.IsKeyDown(Key.W))
            _position.Y -= 200f * (float)gameTime.DeltaTime;
    }
}

Keyboard

if (Input.IsKeyDown(Key.W))      MoveUp();          // Held (continuous)
if (Input.IsKeyPressed(Key.Space)) Jump();           // Just pressed (one-shot)
if (Input.IsKeyReleased(Key.E))  ReleaseCharge();   // Just released
if (Input.IsAnyKeyPressed())     StartGame();        // Any key this frame

Full guide: Keyboard


Mouse

var pos    = Input.MousePosition;        // Vector2, screen coordinates
var delta  = Input.MouseDelta;           // Frame-to-frame movement
var scroll = Input.ScrollWheelDelta;     // float, positive = up
var hscroll = Input.ScrollWheelDeltaX;  // float, horizontal scroll

if (Input.IsMouseButtonPressed(MouseButton.Left))
    SpawnAt(pos);

Input.IsCursorVisible   = false;  // Hide OS cursor
Input.IsRelativeMouseMode = true; // Capture mouse for FPS cameras

Full guide: Mouse


Gamepad

if (Input.IsGamepadConnected())
{
    if (Input.IsGamepadButtonPressed(GamepadButton.A)) Jump();

    // Sticks return Vector2 with radial deadzone already applied (default 0.15)
    var stick = Input.GetGamepadLeftStick();
    _position += stick * speed * deltaTime;

    var trigger = Input.GetGamepadTrigger(GamepadAxis.RightTrigger);

    Input.RumbleGamepad(0.5f, 0.8f, TimeSpan.FromMilliseconds(200));
}

Full guide: Gamepad Support


Input Actions (Rebindable)

var jumpAction = new InputAction("Jump",
    new KeyBinding(Key.Space),
    new GamepadButtonBinding(GamepadButton.A));

if (jumpAction.IsPressed(Input)) Jump();

Full guide: Input Actions


Input Layers (UI Priority)

_inputLayerManager.RegisterLayer(myUiLayer);

protected override void OnUpdate(GameTime gameTime)
{
    _inputLayerManager.ProcessInput();

    if (!_inputLayerManager.KeyboardConsumed) HandleGameKeyboard();
    if (!_inputLayerManager.MouseConsumed)    HandleGameMouse();
    if (!_inputLayerManager.GamepadConsumed)  HandleGameGamepad();
}

Full guide: Input Layers


Best Practices

✅ DO

  1. Use the Input framework property in scenes
  2. Poll input in OnUpdate() only
  3. Use deltaTime for movement -- frame-rate independent
  4. Use IsKeyPressed() for one-shot actions -- jump, shoot, toggle
  5. Use IsKeyDown() for continuous actions -- movement, sprint
protected override void OnUpdate(GameTime gameTime)
{
    if (Input.IsKeyDown(Key.W))
        _position.Y -= _speed * (float)gameTime.DeltaTime;

    if (Input.IsKeyPressed(Key.Space))
        Jump();
}

❌ DON'T

  1. Don't poll input in OnRender() -- wrong lifecycle method
  2. Don't forget deltaTime -- movement will be FPS-dependent
  3. Don't use IsKeyPressed() for movement -- will be choppy
// Bad pattern
protected override void OnRender(GameTime gameTime)
{
    if (Input.IsKeyDown(Key.W))
        _position.Y -= _speed; // No deltaTime and wrong lifecycle!
}

Troubleshooting

Input Not Responding

  1. Check you are in OnUpdate, not OnRender
  2. Click the game window -- input only works when focused

Movement Too Fast or Slow

// Wrong -- FPS dependent
_position.Y -= 5;

// Correct -- 200 pixels per second regardless of frame rate
_position.Y -= 200f * (float)gameTime.DeltaTime;

Gamepad Not Detected

if (!Input.IsGamepadConnected())
{
    Logger.LogWarning("No gamepad connected");
    return;
}