Gnoblin

Input and interaction

gnoblin.input.devices() returns read-only records from the native input-device snapshot. It takes no arguments and is available in runtime event callbacks after startup. The read raises a Lua error if its snapshot is unavailable.

Input-device records expose these fields:

Field Type and values
id, name, device_type Strings. The input:N ID remains stable for this session only.
seat Optional string; absent when Mutter provides no seat name.
vendor_id, product_id Optional integers.
capabilities Array of capability names.
revision Integer state revision.

Subscribe to these events to track device changes in the native runtime:

  • gnoblin.input.device-added contains device.
  • gnoblin.input.device-removed contains device_id and the last device record in last.

gnoblin.input.devices() refreshes before either callback runs. Device IDs last only for the current compositor session. Records do not expose device paths or enabled.

The current Mutter backend does not expose a safe enabled-state getter, so records omit enabled.

gnoblin.input.sources() returns configured XKB layouts and variants and configured IBus engine IDs. XKB entries are checked against the installed XKB registry. IBus records use the engine ID for both name and short_name. Gnoblin does not need an IBus library to list or select them. The IBus service must be running for selection; otherwise the operation fails with unavailable.

The list comes only from input_sources.sources in Gnoblin's Lua config. If that setting is absent, the list is empty and Gnoblin leaves Mutter's current keymap in place. Gnoblin does not read the saved GNOME input-source list.

Mutter loads at most four layouts into one keymap at a time. Gnoblin switches the active group of four when you select a listed source outside that group.

gnoblin.input.current_source() returns the current configured XKB source or the current configured IBus engine, or nil when the active source is unknown or is not configured in Gnoblin.

Each listed source is an InputSource object, one for each type and ID. Every read of one source returns the same object, and the compositor's events update it. source:select() requests that source and returns an operation handle.

  • For an XKB source, the operation completes after Mutter confirms the keymap change. It changes the seat's keyboard layout.
  • For an IBus engine, Gnoblin calls org.freedesktop.IBus.SetGlobalEngine over the session bus and completes when IBus accepts the request. It changes the session's global input method.

An InputSource has alive, which is false once the source has left the list. source:watch("current", fn) follows its selection. source:on(signal, fn) takes these signals:

  • changed, with the list of changed fields.
  • selected, when the source becomes the current one.
  • closed, when the source leaves the configured list.
Lua
for _, source in ipairs(gnoblin.input.sources()) do
    source:on("selected", function() print("now typing", source.name) end)
end

Set input_sources.per_window to:

  • true to remember and restore the last selected source for each focused window. A window without a saved source inherits the source active at its first focus.
  • false or omit it (the default) to share the selected source across windows.

Subscribe to gnoblin.input.source-changed for confirmed current-source changes and gnoblin.input.sources-changed when the configured source list changes. The current-source event has available = false and no source when Mutter's current keymap is external or unknown.

gnoblin.input.orientation_lock() returns an immutable OrientationLock record with boolean available and locked, string orientation, source, and integer revision. source is system when the system setting applies, config when input.orientation_lock supplies a boolean, and runtime while a runtime override is active.

The orientation field is normal, bottom-up, left-up, right-up, or undefined. The last value means no orientation is available.

Change the lock with an override:

  • gnoblin.settings.override("input.orientation_lock", true) locks the current orientation.
  • gnoblin.settings.override("input.orientation_lock", false) unlocks orientation.
  • override:revoke() ends the override.

The call returns an Override and does not write the config file. After the override ends, Gnoblin restores the configured boolean if one is set or follows the system setting otherwise. A newer override replaces an older one.

On config reload, Gnoblin applies a boolean input.orientation_lock value and ends every override. When the value is omitted or set to "inherit", Gnoblin follows the system setting. Subscribe to gnoblin.input.orientation-lock-changed to receive the updated record, plus these event fields:

  • name identifies the event.
  • sequence orders events.
  • time is monotonic.

The socket method names and arguments are documented in the compositor bridge.

device_type is "pointer", "keyboard", "extension", "joystick", "tablet", "touchpad", "touchscreen", "pen", "eraser", "cursor", "pad", or "unknown". Capabilities are zero or more of "pointer", "keyboard", "touchpad", "touch", "tablet_tool", "tablet_pad", "trackball", and "trackpoint".

Input handlers

Handle local pointer, keyboard and gesture events with gnoblin.input.on(match, callback). See input handlers. To start a program from a handler, use gnoblin.process.spawn.

Insert text into the focused Wayland client

See text insertion.

Pointer and keyboard snapping

See window snapping.

Tablet-pad help

Subscribe to gnoblin.input.pad-help-requested to show help for a tablet pad whose configured button action is "help". Lua listeners receive the event directly. See Lua events for callback behavior.

The event contains:

  • device: the current gnoblin.input.devices() record for the pad;
  • monitor_id and output_names: optional stable target-monitor identity;
  • buttons: zero-based button numbers with optional localized action labels and optional mode_group values;
  • mode_groups: group numbers, each group's mode_count, and its switch_buttons;
  • features: zero-based rings, strips, and dials with optional labels for clockwise, counterclockwise, up, or down actions;
  • edition_mode: whether the request is for editing; button help sends false.

The event provides labels when available, but no image or popup. Draw and dismiss the overlay in your shell. Each help press sends a new event; without a listener, no overlay appears.

Lua method Arguments Successful result
gnoblin.input.devices() None Physical input-device records
gnoblin.input.sources() None Configured InputSource objects
gnoblin.input.current_source() None Current InputSource, or nil
source:select() None Operation returning the selected source
gnoblin.input.orientation_lock() None Immutable OrientationLock record
gnoblin.input.grab(options?) timeout A live Grab, see Keyboard grabs

The socket operation input.select takes a source's type and id. In Lua it is source:select().

Esc

Try