Skip to main content
Pre-release

This release is a pre-release and may not be stable for production use.

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 keys
hex-dora-teleop-joystick Joystick/Gamepad button & axis state reader tick buttons, axes
hex-dora-teleop-test-keyboard Terminal viewer for keyboard state tick, keys -
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:
      - keys
    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
      keys: teleop_keyboard/keys
    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
keys 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

keys (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.

Metadata

Release files for hex-dora-node-teleop 0.0.1a4

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for hex-dora-node-teleop 0.0.1a4
File Size Uploaded
hex_dora_node_teleop-0.0.1a4.tar.gz 12.0 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for hex-dora-node-teleop 0.0.1a4
File Interpreter ABI Platform
hex_dora_node_teleop-0.0.1a4-py3-none-any.whl Python 3 none any Details

Total release size: 25.5 kB

Release files / hex_dora_node_teleop-0.0.1a4.tar.gz

Download URL hex_dora_node_teleop-0.0.1a4.tar.gz
Size 12.0 kB
Tags Source
SHA-256 checksum
How to use checksums
d71e4347be199f55d78313f1fb0fd994b6661c71c6036f16fd9c0325a92ddcd1
BLAKE2b-256 checksum
How to use checksums
a4068414323298b26258034c1c56b42a53e42cb21271eb69d722a757feed218b
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/6.2.0 CPython/3.10.12

Release files / hex_dora_node_teleop-0.0.1a4-py3-none-any.whl

Download URL hex_dora_node_teleop-0.0.1a4-py3-none-any.whl
Size 13.5 kB
Tags Python 3
SHA-256 checksum
How to use checksums
709fc534bc16fc5871523f1887968cf137ccfeacb8d2545433c8248369f8773d
BLAKE2b-256 checksum
How to use checksums
2019eb28b3b83c4012559fd81927cbea469fb081bedd33a9aefdbdba56d97b73
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/6.2.0 CPython/3.10.12
Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page