mirror of
https://github.com/legop3/MultiRoombaRover.git
synced 2026-09-16 01:21:20 -04:00
slop
This commit is contained in:
@@ -178,6 +178,9 @@ kinect:
|
||||
captureCooldownMs: 10000
|
||||
|
||||
balanceBoard:
|
||||
# After enabling this feature, rerun install_server.sh. The installer then
|
||||
# configures BlueZ's Wii-compatible HID mode, persistent hid-wiimote loading,
|
||||
# and the restricted evdev permission automatically.
|
||||
enabled: false
|
||||
# A load must reach this weight before stability timing begins. Keeping the
|
||||
# threshold above sensor drift prevents an empty board from capturing itself.
|
||||
|
||||
@@ -17,6 +17,8 @@ SNAPSHOT_DIR="/var/lib/rover-snapshots"
|
||||
REPLAY_SEGMENT_DIR="/var/lib/replay-segments"
|
||||
KINECT_UDEV_RULE="/etc/udev/rules.d/99-kinect-world.rules"
|
||||
BALANCE_BOARD_UDEV_RULE="/etc/udev/rules.d/99-multirover-balance-board.rules"
|
||||
BALANCE_BOARD_MODULES_LOAD="/etc/modules-load.d/multirover-balance-board.conf"
|
||||
BLUEZ_INPUT_CONFIG="/etc/bluetooth/input.conf"
|
||||
|
||||
if [[ $EUID -ne 0 ]]; then
|
||||
echo "This installer must be run with sudo/root." >&2
|
||||
@@ -139,6 +141,7 @@ dnf install -y \
|
||||
libfreenect-devel \
|
||||
libusb1-devel \
|
||||
bluez \
|
||||
crudini \
|
||||
libcap >/dev/null
|
||||
NODE_BIN="$(command -v node)"
|
||||
|
||||
@@ -201,6 +204,52 @@ if [[ ! -f "$CONFIG_PATH" ]]; then
|
||||
echo "Copied config.example.yaml to config.yaml; edit it before exposing the service."
|
||||
fi
|
||||
|
||||
# Use the same YAML library as the server instead of approximating nested YAML
|
||||
# with grep. This makes system configuration follow the exact explicit boolean
|
||||
# feature flag that the running Node service will use.
|
||||
BALANCE_BOARD_ENABLED=$(SERVER_DIR="$SERVER_DIR" CONFIG_PATH="$CONFIG_PATH" "$NODE_BIN" <<'NODE'
|
||||
const fs = require('fs');
|
||||
const path = require('path');
|
||||
const yaml = require(path.join(process.env.SERVER_DIR, 'node_modules', 'js-yaml'));
|
||||
const config = yaml.load(fs.readFileSync(process.env.CONFIG_PATH, 'utf8')) || {};
|
||||
process.stdout.write(config.balanceBoard?.enabled === true ? 'true' : 'false');
|
||||
NODE
|
||||
)
|
||||
|
||||
if [[ "$BALANCE_BOARD_ENABLED" == "true" ]]; then
|
||||
echo " Configuring BlueZ for the Wii Balance Board"
|
||||
if ! modinfo hid-wiimote >/dev/null 2>&1; then
|
||||
echo "The running kernel does not provide hid-wiimote; install a Fedora kernel with that module before enabling balanceBoard." >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
install -d -m 0755 /etc/bluetooth /etc/modules-load.d
|
||||
touch "$BLUEZ_INPUT_CONFIG"
|
||||
chmod 0644 "$BLUEZ_INPUT_CONFIG"
|
||||
# Modern BlueZ defaults Classic HID devices to userspace UHID and enforces a
|
||||
# security mode that breaks the Wii family's unusual legacy HID handshake.
|
||||
# crudini changes only these two keys, preserving every unrelated Bluetooth
|
||||
# input option an operator may already have configured on the server.
|
||||
crudini --set "$BLUEZ_INPUT_CONFIG" General UserspaceHID false
|
||||
crudini --set "$BLUEZ_INPUT_CONFIG" General ClassicBondedOnly false
|
||||
|
||||
# The service consumes the calibrated evdev axes created specifically by the
|
||||
# kernel hid-wiimote driver. Load it now and on every future boot so the brief
|
||||
# board wake window is never lost waiting for manual module setup.
|
||||
cat > "$BALANCE_BOARD_MODULES_LOAD" <<'EOF'
|
||||
# MultiRoombaRover Wii Balance Board support.
|
||||
hid-wiimote
|
||||
EOF
|
||||
chmod 0644 "$BALANCE_BOARD_MODULES_LOAD"
|
||||
modprobe hid-wiimote
|
||||
|
||||
# BlueZ reads input.conf only at daemon startup. Restart it during the
|
||||
# installer, before multirover is restarted below, so the new HID mode is
|
||||
# guaranteed to be active without requiring a reboot or another command.
|
||||
systemctl enable --now bluetooth.service
|
||||
systemctl restart bluetooth.service
|
||||
fi
|
||||
|
||||
tmpdir=$(mktemp -d)
|
||||
trap 'rm -rf "$tmpdir"' EXIT
|
||||
|
||||
@@ -295,8 +344,8 @@ EOF
|
||||
cat > "$MULTIROVER_SERVICE" <<EOF
|
||||
[Unit]
|
||||
Description=Multi-Roomba Rover control server
|
||||
After=network-online.target mediamtx.service
|
||||
Wants=network-online.target
|
||||
After=network-online.target mediamtx.service bluetooth.service
|
||||
Wants=network-online.target bluetooth.service
|
||||
|
||||
[Service]
|
||||
User=$TARGET_USER
|
||||
@@ -333,5 +382,9 @@ echo
|
||||
echo "Update $CONFIG_PATH to set admins, lockdown settings, and media parameters."
|
||||
echo "Kinect/libfreenect packages and udev permissions were installed."
|
||||
echo "If a Kinect is already plugged in, unplug/replug its USB/power before testing so the new udev rule applies."
|
||||
echo "Wii Balance Board Bluetooth support and the restricted input rule were installed."
|
||||
echo "Enable balanceBoard in config.yaml, then press the red Sync button once to commission it."
|
||||
if [[ "$BALANCE_BOARD_ENABLED" == "true" ]]; then
|
||||
echo "Wii Balance Board BlueZ compatibility, kernel driver, bridge, and restricted input rule were installed."
|
||||
echo "Press the red Sync button once to commission it; later wakes use the front power button."
|
||||
else
|
||||
echo "Wii Balance Board bridge and restricted input rule were installed but system Bluetooth compatibility was left unchanged because balanceBoard is disabled."
|
||||
fi
|
||||
|
||||
@@ -7,19 +7,28 @@ Balance Board input device.
|
||||
|
||||
## Commissioning on the real server
|
||||
|
||||
1. Run `sudo ./install_server.sh` from the `server` directory.
|
||||
2. Set `balanceBoard.enabled: true` in `server/config.yaml` and restart
|
||||
`multirover.service`.
|
||||
3. Open the Activities tab. While it says **Pairing setup**, press the red Sync
|
||||
button under the board's battery cover.
|
||||
4. Wait for the card to change to **Sleeping** or **Ready**. BlueZ retains the
|
||||
bond and the service also stores the selected board address in
|
||||
1. Set `balanceBoard.enabled: true` in `server/config.yaml`.
|
||||
2. Run `sudo ./install_server.sh` from the `server` directory. The installer
|
||||
configures BlueZ's Wii-compatible kernel HID mode, loads `hid-wiimote` now
|
||||
and at boot, and restarts Bluetooth and the rover server automatically.
|
||||
3. Open the Activities tab. When it says **Waiting for red Sync**, press the red
|
||||
Sync button under the board's battery cover.
|
||||
4. Wait for the card to report a paired bond and then **Ready**. BlueZ retains
|
||||
the bond and the service also stores the selected board address in
|
||||
`server/data/balance-board.json`.
|
||||
5. For ordinary use, press only the front power button. The board should connect
|
||||
to the server without another Sync operation.
|
||||
|
||||
The bridge intentionally uses short Bluetooth Classic discovery windows only
|
||||
while no board is commissioned. It stops scanning after a successful bond.
|
||||
The bridge keeps Bluetooth Classic discovery active while no board is
|
||||
commissioned and stops scanning after a successful bond. Once commissioned, it
|
||||
actively retries the saved address while disconnected so a front-button wake is
|
||||
caught even when the adapter does not accept the board's incoming reconnect.
|
||||
|
||||
Wii-family HID compatibility requires `UserspaceHID=false` and
|
||||
`ClassicBondedOnly=false` in BlueZ's `input.conf`. The installer applies only
|
||||
those two keys with an INI-aware tool and preserves unrelated Bluetooth input
|
||||
settings. The latter relaxes BlueZ's global Classic HID bonding restriction;
|
||||
this is limited to servers where Balance Board support is explicitly enabled.
|
||||
|
||||
## Physical station
|
||||
|
||||
|
||||
@@ -418,7 +418,23 @@ std::string command_error_summary(const std::string& raw, const std::string& fal
|
||||
std::string summary;
|
||||
summary.reserve(std::min<std::size_t>(raw.size(), 400));
|
||||
bool previous_was_space = false;
|
||||
int ansi_state = 0;
|
||||
for (unsigned char ch : raw) {
|
||||
// bluetoothctl emits terminal color CSI sequences even when its output is
|
||||
// captured by a pipe. Drop the entire ESC ... final-byte sequence so the UI
|
||||
// never exposes fragments such as `[[0;93mCHG[0m]` as hardware diagnostics.
|
||||
if (ch == 0x1b) {
|
||||
ansi_state = 1;
|
||||
continue;
|
||||
}
|
||||
if (ansi_state == 1) {
|
||||
ansi_state = ch == '[' ? 2 : 0;
|
||||
continue;
|
||||
}
|
||||
if (ansi_state == 2) {
|
||||
if (ch >= 0x40 && ch <= 0x7e) ansi_state = 0;
|
||||
continue;
|
||||
}
|
||||
const bool is_space = ch == ' ' || ch == '\t' || ch == '\n' || ch == '\r';
|
||||
if (is_space) {
|
||||
if (!summary.empty() && !previous_was_space) summary.push_back(' ');
|
||||
|
||||
Reference in New Issue
Block a user