Skip to main content

Dora Node for Teleoperation Input (Keyboard & Joystick)

Project description

hex_dora_node_teleop

Dora nodes for reading teleoperation inputs from keyboard and joystick/gamepad using evdev. Each node maintains an internal state table updated by background threads and outputs the full state at the configured tick rate (recommended 100 Hz).

Nodes

Node Description Inputs Outputs
hex-dora-teleop-keyboard Keyboard letter-key state reader tick state
hex-dora-teleop-joystick Joystick/Gamepad button & axis state reader tick buttons, axes
hex-dora-teleop-test-keyboard Terminal viewer for keyboard state tick, state -
hex-dora-teleop-test-joystick Terminal viewer for joystick state tick, buttons, axes -

Prerequisites

Accessing /dev/input/* requires the current user to be in the input group:

sudo usermod -aG input $USER
# Log out and back in for the change to take effect

Installation

pip install hex_dora_node_teleop

YAML Examples

Keyboard (100 Hz)

nodes:
  - id: teleop_keyboard
    build: pip install hex_dora_node_teleop
    path: hex-dora-teleop-keyboard
    inputs:
      tick: dora/timer/millis/10
    outputs:
      - state
    env:
      NODE_NAME: teleop_keyboard
      DEVICE_PATH: ""  # auto-detect; or set e.g. /dev/input/event0

  - id: test_keyboard
    build: pip install hex_dora_node_teleop
    path: hex-dora-teleop-test-keyboard
    inputs:
      tick: dora/timer/millis/10
      state: teleop_keyboard/state
    env:
      NODE_NAME: test_keyboard

Joystick / Gamepad (100 Hz)

nodes:
  - id: teleop_joystick
    build: pip install hex_dora_node_teleop
    path: hex-dora-teleop-joystick
    inputs:
      tick: dora/timer/millis/10
    outputs:
      - buttons
      - axes
    env:
      NODE_NAME: teleop_joystick
      DEVICE_PATH: ""  # auto-detect; or set e.g. /dev/input/event5

  - id: test_joystick
    build: pip install hex_dora_node_teleop
    path: hex-dora-teleop-test-joystick
    inputs:
      tick: dora/timer/millis/10
      buttons: teleop_joystick/buttons
      axes: teleop_joystick/axes
    env:
      NODE_NAME: test_joystick

Inputs

Teleop Nodes (keyboard / joystick)

Input Type Description
tick dora/timer/millis/* Timer tick to trigger state output (use millis/10 for 100 Hz)

Test Nodes (test-keyboard)

Input Type Description
tick dora/timer/millis/* Timer tick to refresh terminal display
state Arrow UInt8Array Keyboard letter-key state from keyboard node

Test Nodes (test-joystick)

Input Type Description
tick dora/timer/millis/* Timer tick to refresh terminal display
buttons Arrow UInt8Array Button states from joystick node
axes Arrow Float64Array Axis values from joystick node

Outputs

state (keyboard)

Arrow UInt8Array of length 26 — one element per letter key (a–z, in order). 1 = pressed, 0 = released.

state_data: UInt8Array  # pa.array([0, 0, 1, ...], type=pa.uint8())
metadata = {
    "keys": "a,b,c,...,z",         # comma-separated key names
    "primitive": "keyboard_state",
}

buttons (joystick)

Arrow UInt8Array — one element per detected gamepad button. 1 = pressed, 0 = released. Button list is auto-detected from device capabilities.

buttons_data: UInt8Array  # pa.array([0, 1, 0, ...], type=pa.uint8())
metadata = {
    "names": "BTN_SOUTH,BTN_EAST,...",  # comma-separated button names
    "primitive": "joystick_buttons",
}

axes (joystick)

Arrow Float64Array — one element per detected analog axis, normalized to [-1.0, 1.0]. Axis list is auto-detected from device capabilities.

axes_data: Float64Array  # pa.array([-0.5, 0.0, ...], type=pa.float64())
metadata = {
    "names": "ABS_X,ABS_Y,...",    # comma-separated axis names
    "primitive": "joystick_axes",
}

Environment Variables

All Nodes

Variable Type Default Description
NODE_NAME str "" Dora node name passed to Node() constructor; empty = use default

Keyboard Node

Variable Type Default Description
DEVICE_PATH str "" (auto) Specific /dev/input/eventN path; empty = auto-detect all keyboards

Joystick Node

Variable Type Default Description
DEVICE_PATH str "" (auto) Specific /dev/input/eventN path; empty = auto-detect first joystick

Architecture

Both keyboard and joystick nodes follow the same pattern:

  1. Device discovery — enumerate /dev/input/* via evdev.list_devices() and filter by capabilities (letter keys for keyboard, analog axes for joystick).
  2. Background reader thread — a daemon thread continuously reads evdev events and updates an in-memory state table protected by a threading.Lock.
  3. Dora tick loop — on each tick input, the node snapshots the current state table and sends it as an Arrow array output.

This decouples the variable-rate hardware events from the fixed-rate dora output, ensuring consistent 100 Hz state updates regardless of actual input event frequency.

License

This project is licensed under Apache-2.0.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

hex_dora_node_teleop-0.0.1a3.tar.gz (12.0 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

hex_dora_node_teleop-0.0.1a3-py3-none-any.whl (13.5 kB view details)

Uploaded Python 3

File details

Details for the file hex_dora_node_teleop-0.0.1a3.tar.gz.

File metadata

  • Download URL: hex_dora_node_teleop-0.0.1a3.tar.gz
  • Upload date:
  • Size: 12.0 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.10.12

File hashes

Hashes for hex_dora_node_teleop-0.0.1a3.tar.gz
Algorithm Hash digest
SHA256 ff760c1dd3c44277d5ffb9a7e69cc70d020d0bfb410508674043d1822ee2629e
MD5 4b03afa73797fe761fe0fe2ef3933cf8
BLAKE2b-256 8e6a023d30ccd2b0c132195685b5705cedb892ce88303744d87d435cf53926c2

See more details on using hashes here.

File details

Details for the file hex_dora_node_teleop-0.0.1a3-py3-none-any.whl.

File metadata

File hashes

Hashes for hex_dora_node_teleop-0.0.1a3-py3-none-any.whl
Algorithm Hash digest
SHA256 2b31f8775da341c0949e96cbe82f391da9519c6ca0b8270131bd878de1415600
MD5 fa645e718048a44719ab60d5c35b46f3
BLAKE2b-256 4c89deef8355146b9683294953cbd66dc3f3d92a0a1953dec7f590250465f189

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page