Files
prosperon/docs/input.md
John Alanbrook 83b798e365 Add Hugo website and rewrite docs to match current engine
New Hugo site in website/ with prosperon.dev theme (blue/gold/castle
aesthetic), docs sidebar navigation, and content pages. Rewrote all
doc files to align with the actual codebase: compositor+film2d
rendering, use() modules (no global prosperon object), Pit language,
script+JSON entity model. Added entities.md, front matter to all
70+ API docs, and updated API index for current module architecture.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-23 18:09:55 -06:00

3.4 KiB

title, type
title type
Input docs

Input

Prosperon's input system normalizes keyboard, mouse, gamepad, and touch into named actions. You define what actions your game uses, bind them to physical inputs, and the engine routes events to the right place.

Actions

An action is a named game event like "jump", "attack", or "ui_up". Multiple physical inputs can trigger the same action:

var input = use('input')

input.configure({
  action_map: {
    jump: ['space', 'gamepad_a'],
    attack: ['mouse_button_left', 'gamepad_x'],
    move_left: ['a', 'left', 'gamepad_dpleft'],
    move_right: ['d', 'right', 'gamepad_dpright']
  }
})

Default actions are provided for common UI navigation (ui_up, ui_down, ui_left, ui_right, confirm, cancel, menu).

Players and Users

The input system supports multiple players. Each user has:

  • Paired devices (keyboard, specific gamepad, etc.)
  • An action map (bindings can differ per player)
  • A control stack of possessed entities
var p1 = input.player1()

Device Pairing

By default, pairing is 'last_used' — all input goes to player 1, and the active device switches when a button is pressed. For local multiplayer, use 'explicit' pairing where each player is assigned specific devices.

input.configure({
  max_users: 2,
  pairing: 'explicit'
})

Control Stack (Possession)

Players possess entities to route input to them. The control stack is ordered — the topmost entity gets input first.

var p1 = input.player1()

// Take control of the player character
p1.possess(player_entity)

// Push a menu on top — it gets input priority
p1.push(pause_menu)

// Pop the menu — player character gets input again
p1.pop()

The possessed entity must have an on_input method:

var player = {
  on_input: function(action, data) {
    if (action == 'jump' && data.pressed) {
      // jump logic
    }
    if (action == 'move_right') {
      // data.pressed, data.released, data.time
    }
  }
}

Device Detection

The input system tracks what kind of device is active, so you can show appropriate button prompts:

var p1 = input.player1()
var kind = p1.device_kind()  // 'keyboard', 'mouse', 'gamepad'
var type = p1.gamepad_type() // 'xbox', 'playstation', etc.

Get the display name or icon for an action based on the current device:

var icon = p1.get_icon_for_action('jump')
var binding = p1.get_primary_binding('jump')

Emacs-Style Keybindings

For editors or complex hotkey systems, Prosperon supports modifier notation:

Prefix Key
C- Ctrl
M- Alt
S- Super

So C-a means Ctrl+A, C-M-s means Ctrl+Alt+S. Case is preserved — a and A are different bindings.

The emacs module is enabled by default but can be disabled:

input.configure({ emacs: false })

Gestures

Touch gesture recognition is built in:

  • Swipe detection (with configurable distance and time thresholds)
  • Pinch detection
input.configure({
  gestures: true,
  swipe_min_dist: 50,
  swipe_max_time: 0.5
})

Saved Bindings

Player bindings are automatically saved and loaded, so remapped controls persist across sessions.

Raw Events

For debugging or special cases, the raw SDL event can be accessed via the config callback:

core.start({
  input: function(raw_event) {
    // raw SDL event object
  }
})