input

package
v0.1.0-preview.2 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Oct 16, 2026 License: MIT Imports: 5 Imported by: 0

Documentation

Overview

Package input adapts keyboard state into debounced gameplay and UI input.

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

This section is empty.

Types

type KeySample

type KeySample struct {
	Held    [ebiten.KeyMax + 1]bool
	Pressed [ebiten.KeyMax + 1]bool
}

KeySample is one detached physical-key snapshot. Pressed is an edge, not a repeat or an ordering claim about keys pressed between application updates.

func (KeySample) HasModifiers

func (s KeySample) HasModifiers() bool

HasModifiers distinguishes plain command input from reserved shortcuts.

type Keyboard

type Keyboard struct {
	// contains filtered or unexported fields
}

Keyboard tracks key consumption, repeat timing, and release gates across input owners.

func NewKeyboard

func NewKeyboard(millisecondDelayBetweenKeyPresses int) *Keyboard

NewKeyboard creates a keyboard using physical key state and the default adapter clock.

func NewKeyboardWithKeyStateSource

func NewKeyboardWithKeyStateSource(
	millisecondDelayBetweenKeyPresses int,
	keyPressed func(ebiten.Key) bool,
) *Keyboard

NewKeyboardWithKeyStateSource constructs a keyboard backed by a caller-owned key-state source. It supports deterministic input adapters and tests without changing the keyboard's release-debouncing behavior.

func (*Keyboard) CaptureKeySample

func (k *Keyboard) CaptureKeySample() KeySample

CaptureKeySample samples once before advancing input owners. Readers still receive their ordinary input; sampling alone consumes nothing.

func (*Keyboard) ClearFrameConsumption

func (k *Keyboard) ClearFrameConsumption()

ClearFrameConsumption cleans up released keys from consumption tracking Should be called once per frame by the main game loop at the START of Update() Only clears keys that are no longer physically pressed

func (*Keyboard) ConsumePressEdge

func (k *Keyboard) ConsumePressEdge(sample KeySample, key ebiten.Key) bool

ConsumePressEdge accepts an already captured fresh press without inheriting movement cadence. Ownership/transition gates still apply.

func (*Keyboard) ForceLastKeyPressed

func (k *Keyboard) ForceLastKeyPressed(key ebiten.Key)

ForceLastKeyPressed changes the repeat key identity without changing its timestamp.

func (*Keyboard) GetAlphaNumericPressed

func (k *Keyboard) GetAlphaNumericPressed() (*ebiten.Key, string)

GetAlphaNumericPressed returns a pressed alphanumeric key and its display text.

func (*Keyboard) GetArrowKeyAsDirection

func (k *Keyboard) GetArrowKeyAsDirection() references.Direction

GetArrowKeyAsDirection returns the pressed arrow key as a Direction enum Returns references.NoneDirection if no arrow key is pressed Priority ordering: Down > Up > Right > Left

func (*Keyboard) GetBoundKeyPressed

func (k *Keyboard) GetBoundKeyPressed(boundKeys *[]ebiten.Key) *ebiten.Key

GetBoundKeyPressed returns the first pressed bound key without consuming it.

func (*Keyboard) GetKeyLetter

func (k *Keyboard) GetKeyLetter(key ebiten.Key) string

GetKeyLetter formats alphanumeric keys, including numeric keypad digits.

func (*Keyboard) GetMsSinceLastKeyPress

func (k *Keyboard) GetMsSinceLastKeyPress() int

GetMsSinceLastKeyPress returns elapsed adapter milliseconds since the last accepted key.

func (*Keyboard) GetPressedArrowKey

func (k *Keyboard) GetPressedArrowKey() *ebiten.Key

GetPressedArrowKey returns the currently pressed arrow key, or nil if none pressed Uses priority ordering to determine which key to return when multiple are pressed: Down (highest priority) > Up > Right > Left (lowest priority) This matches the priority used in original game movement logic

func (*Keyboard) GetPressedKey

func (k *Keyboard) GetPressedKey() *semantic_input.Key

GetPressedKey returns the currently pressed key, prioritizing arrow keys Returns nil if no key is pressed Priority: Arrow keys (Down > Up > Right > Left) > Alpha (A-Z) > Numeric (0-9) > Control keys

Used by event queue WhileAwaitingInput() to detect which key stopped sailing Matches original Ultima V key detection priority for automatic sailing

Returns a framework-independent semantic key for use by core packages.

func (*Keyboard) HasUnprotectedHeldKey

func (k *Keyboard) HasUnprotectedHeldKey() bool

HasUnprotectedHeldKey is a workflow-release query, not an acknowledgement query. Rejected presses remain physically held for raw any-key waits.

func (*Keyboard) IsAnyKeyPressed

func (k *Keyboard) IsAnyKeyPressed() bool

IsAnyKeyPressed checks if any key is currently pressed

func (*Keyboard) IsBoundKeyPressed

func (k *Keyboard) IsBoundKeyPressed(boundKeys *[]ebiten.Key) bool

IsBoundKeyPressed reports whether a bound key is pressed and available to its owner.

func (*Keyboard) IsKeyHeld

func (k *Keyboard) IsKeyHeld(key ebiten.Key) bool

IsKeyHeld reads key state through the same adapter used for modifiers and registered keys. Suspended polling masks it; it never consumes a key.

func (*Keyboard) IsKeyPressedAndRegister

func (k *Keyboard) IsKeyPressedAndRegister(key ebiten.Key) bool

IsKeyPressedAndRegister is a convenience method combining key press detection with debouncing Returns true if the key is pressed AND the debounce time has elapsed Simplifies the common pattern: if IsKeyPressed && TryToRegisterKeyPress

func (*Keyboard) IsKeyPressedAndRegisterRepeatable

func (k *Keyboard) IsKeyPressedAndRegisterRepeatable(key ebiten.Key) bool

IsKeyPressedAndRegisterRepeatable combines injected/simulated key detection with movement-style repeat registration.

func (*Keyboard) IsKeyPressedGetKey

func (k *Keyboard) IsKeyPressedGetKey(key ebiten.Key) *ebiten.Key

IsKeyPressedGetKey returns the key when physically pressed, without consuming it.

func (*Keyboard) IsModifierComboPressed

func (k *Keyboard) IsModifierComboPressed(modifier Modifier, key ebiten.Key) bool

IsModifierComboPressed checks if a modifier+key combination is currently pressed Returns true only if both the modifier and the specific key are pressed

func (*Keyboard) IsModifierPressed

func (k *Keyboard) IsModifierPressed(modifier Modifier) bool

IsModifierPressed checks if a modifier key is currently pressed

func (*Keyboard) IsNumberKeyPressedAndRegister

func (k *Keyboard) IsNumberKeyPressedAndRegister() int

IsNumberKeyPressedAndRegister checks if any number key (0-9) is pressed. Returns the digit (0-9) if pressed and registered, or -1 if no number key is pressed. This simplifies the common pattern of checking all number keys in sequence.

func (*Keyboard) IsSuppressedUntilRelease

func (k *Keyboard) IsSuppressedUntilRelease(key ebiten.Key) bool

IsSuppressedUntilRelease is separate from normal one-shot consumption, which repeatable movement is allowed to bypass.

func (*Keyboard) IsTextKeyPressedAndRegister

func (k *Keyboard) IsTextKeyPressedAndRegister(key ebiten.Key) bool

IsTextKeyPressedAndRegister accepts each released-and-pressed text key without the movement repeat delay. Transition and held-key consumption still apply.

func (*Keyboard) IsWaitingForRelease

func (k *Keyboard) IsWaitingForRelease() bool

IsWaitingForRelease returns true if keyboard is waiting for keys to be released Useful for UI feedback (e.g., showing "Release keys..." message)

func (*Keyboard) PrepareForTransition

func (k *Keyboard) PrepareForTransition(postAcceptDelayMs int)

PrepareForTransition records currently pressed keys for release debouncing Use this when transitioning to a new UI state (e.g., dialog dismissal, KeyWait) to prevent key bleeding from the previous input

func (*Keyboard) ResetReleaseDebouncing

func (k *Keyboard) ResetReleaseDebouncing()

ResetReleaseDebouncing clears all release debounce state Use when closing dialog or resetting UI

func (*Keyboard) SetAllowKeyPressImmediately

func (k *Keyboard) SetAllowKeyPressImmediately()

SetAllowKeyPressImmediately bypasses repeat delay after transition and release gates pass.

func (*Keyboard) SetElapsedMillisecondsSource

func (k *Keyboard) SetElapsedMillisecondsSource(source func() int64)

SetElapsedMillisecondsSource injects the adapter's elapsed clock. Configure it before accepting input; switching clocks resets timing, but not release gates.

func (*Keyboard) SetForceWaitAnyKey

func (k *Keyboard) SetForceWaitAnyKey(ms int)

SetForceWaitAnyKey gates key acceptance for the supplied milliseconds.

func (*Keyboard) SetLastKeyPressedNow

func (k *Keyboard) SetLastKeyPressedNow()

SetLastKeyPressedNow restarts repeat timing at the current adapter time.

func (*Keyboard) SetLastKeyPressedNowPlusMs

func (k *Keyboard) SetLastKeyPressedNowPlusMs(ms int)

SetLastKeyPressedNowPlusMs postpones repeat timing by the supplied milliseconds.

func (*Keyboard) SimulateKeyPress

func (k *Keyboard) SimulateKeyPress(key ebiten.Key)

SimulateKeyPress simulates a key press for testing purposes This bypasses the normal key press timing restrictions

func (*Keyboard) SuppressUntilRelease

func (k *Keyboard) SuppressUntilRelease(key ebiten.Key)

SuppressUntilRelease rejects this physical press even in repeatable movement. It deliberately survives ResetReleaseDebouncing and command cancellation.

func (*Keyboard) SuspendInputPolling

func (k *Keyboard) SuspendInputPolling() func()

SuspendInputPolling masks input while an owner advances non-input work, for example while its application window lacks focus. Synthetic input is discarded, not replayed later. Restore once; physical holds remain blocked until release.

func (*Keyboard) TryAcceptKey

func (k *Keyboard) TryAcceptKey(key ebiten.Key) bool

TryAcceptKey combines time-based and state-based release debouncing Returns true if the key should be processed, false if it should be ignored

This method implements two-phase checking: Phase 1 (State-based): If PrepareForTransition was called, wait for key release Phase 2 (Time-based): Standard repeat delay checking

func (*Keyboard) TryToRegisterKeyPress

func (k *Keyboard) TryToRegisterKeyPress(key ebiten.Key) bool

TryToRegisterKeyPress registers a keypress if it is allowed according to the time passed since the previous key press AND if the key hasn't been consumed already while held

func (*Keyboard) TryToRegisterRepeatableKeyPress

func (k *Keyboard) TryToRegisterRepeatableKeyPress(key ebiten.Key) bool

TryToRegisterRepeatableKeyPress registers a keypress that can repeat while held (e.g., movement keys). Returns true if keypress is allowed according to time-based debouncing and transition state. Unlike TryToRegisterKeyPress, this DOES NOT use release-based consumption, allowing continuous input while the key is held down. Use this for movement/navigation keys that should repeat when held.

func (*Keyboard) TryToRegisterRepeatableKeyPressWithRate

func (k *Keyboard) TryToRegisterRepeatableKeyPressWithRate(key ebiten.Key, rate RepeatRate) bool

TryToRegisterRepeatableKeyPressWithRate is like TryToRegisterRepeatableKeyPress but uses a custom repeat rate instead of the default keyboard delay. Use RepeatRateSlow, RepeatRateMedium, or RepeatRateFast for common presets.

type ListNavigation

type ListNavigation struct {
	// contains filtered or unexported fields
}

ListNavigation resolves UI chords before consuming their physical keys. Its zero value is ready to use. Poll once per focused Update; Reset on focus loss or a change of input mode. Timing advances in update ticks, never wall time.

func (*ListNavigation) BlockUntilRelease

func (n *ListNavigation) BlockUntilRelease(pressed func(ebiten.Key) bool)

BlockUntilRelease prevents a hold crossing a modal focus boundary.

func (*ListNavigation) Poll

func (n *ListNavigation) Poll(k *Keyboard, keys ...ebiten.Key) (*ebiten.Key, bool)

Poll returns a normalized navigation key when movement is due. owned remains true during throttled holds, so text input cannot consume/reset navigation. By default Up, Down, PageUp and PageDown are read. Explicit keys allow readers to include Home/End and menus to include Left/Right. Shift+Up/Down always maps to PageUp/PageDown; callers without paging deliberately ignore those intents.

func (*ListNavigation) PollWithKeyState

func (n *ListNavigation) PollWithKeyState(
	keyboard *Keyboard, pressed func(ebiten.Key) bool, keys ...ebiten.Key,
) (*ebiten.Key, bool)

PollWithKeyState supports widgets whose existing physical-input adapter also owns their release gates. Production widgets normally use Poll.

func (*ListNavigation) Reset

func (n *ListNavigation) Reset()

Reset discards a previous hold, for example when a nested modal takes focus.

type Modifier

type Modifier int

Modifier represents keyboard modifiers (Ctrl, Shift, Alt, Meta/Command).

const (
	ModifierCtrl Modifier = iota
	ModifierShift
	ModifierAlt
	ModifierMeta
)

Modifier values identify the supported keyboard modifier families.

type RepeatRate

type RepeatRate int

RepeatRate defines keyboard repeat speed presets in milliseconds

const (
	RepeatRateSlow   RepeatRate = 200 // Slow repeat rate (200ms between repeats)
	RepeatRateMedium RepeatRate = 120 // Medium repeat rate (120ms between repeats)
	RepeatRateFast   RepeatRate = 120 // Legacy fast preset (120ms, same as Medium); UI lists use ListNavigation.
)

Repeat-rate presets control the delay between accepted held-key repeats.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL