Compare commits
4 Commits
cba8856c85
...
e1f63108f2
| Author | SHA1 | Date |
|---|---|---|
|
|
e1f63108f2 | |
|
|
2737811e2e | |
|
|
f9b6cfe871 | |
|
|
ded1eb7464 |
|
|
@ -322,7 +322,7 @@ job. Details, payloads and safety rules: [docs/mqtt-api.md](docs/mqtt-api.md).
|
||||||
|
|
||||||
| Command | Does |
|
| Command | Does |
|
||||||
|---|---|
|
|---|---|
|
||||||
| `mode auto` / `mode manual` | sweep the scan grid / stop and take the gimbal by hand (it stays homed and powered) |
|
| `mode auto` / `mode manual` | sweep the scan grid / stop the gimbal where it is and take it by hand (it stays homed and powered) |
|
||||||
| `mode pan <heading> <span> [<pitch>]` | watch one direction: `mode pan 90 30` covers 75°-105°, a picture every 6° |
|
| `mode pan <heading> <span> [<pitch>]` | watch one direction: `mode pan 90 30` covers 75°-105°, a picture every 6° |
|
||||||
| `gimbal home` | find the endstops and centre - needed after every power-up |
|
| `gimbal home` | find the endstops and centre - needed after every power-up |
|
||||||
| `gimbal move <yaw>[,<pitch>]` | point at a **true bearing** (0 = north) and an elevation, in degrees; without a pitch only yaw moves. A yaw-only tower ignores the pitch and refuses pitch-only commands |
|
| `gimbal move <yaw>[,<pitch>]` | point at a **true bearing** (0 = north) and an elevation, in degrees; without a pitch only yaw moves. A yaw-only tower ignores the pitch and refuses pitch-only commands |
|
||||||
|
|
|
||||||
22
deploy.sh
22
deploy.sh
|
|
@ -219,6 +219,26 @@ ssh "$REMOTE_HOST" "mkdir -p '$REMOTE_DIR'"
|
||||||
# build*/ covers every local build tree, not just build/. They are machine-specific
|
# build*/ covers every local build tree, not just build/. They are machine-specific
|
||||||
# and the device regenerates its own build/ remotely, so shipping build-tui/ etc.
|
# and the device regenerates its own build/ remotely, so shipping build-tui/ etc.
|
||||||
# just pushed tens of MB of x86 object files the device can never use.
|
# just pushed tens of MB of x86 object files the device can never use.
|
||||||
|
#
|
||||||
|
# Only what git knows about is copied: the tracked files and new ones not yet
|
||||||
|
# added, as they are in the working tree, so uncommitted work still deploys.
|
||||||
|
# Whatever .gitignore names stays behind - build trees, the editor's cache,
|
||||||
|
# Claude Code worktrees, the 12-bit report's full-size example pictures - which
|
||||||
|
# made a deploy 505 MB, where 7 MB was needed, while the whole folder was
|
||||||
|
# mirrored. The set is staged locally so the rsync below keeps its --delete: a
|
||||||
|
# file git no longer has, or clutter an older deploy left, is removed from the
|
||||||
|
# tower, and the excludes still protect the tower's own files as before.
|
||||||
|
git rev-parse --git-dir >/dev/null 2>&1 || {
|
||||||
|
echo "error: deploy from a git checkout - it decides what is copied" >&2
|
||||||
|
exit 1
|
||||||
|
}
|
||||||
|
STAGE="$(mktemp -d)"
|
||||||
|
trap 'rm -rf "$STAGE"' EXIT
|
||||||
|
chmod 0755 "$STAGE" # rsync gives the tower's project folder these permissions
|
||||||
|
# --ignore-missing-args: a tracked file deleted but not yet committed is listed
|
||||||
|
git ls-files -z --cached --others --exclude-standard |
|
||||||
|
rsync -a --from0 --files-from=- --ignore-missing-args ./ "$STAGE/"
|
||||||
|
|
||||||
echo ">> syncing to $REMOTE_HOST:$REMOTE_DIR"
|
echo ">> syncing to $REMOTE_HOST:$REMOTE_DIR"
|
||||||
rsync -avz --delete \
|
rsync -avz --delete \
|
||||||
--exclude 'build*/' \
|
--exclude 'build*/' \
|
||||||
|
|
@ -235,7 +255,7 @@ rsync -avz --delete \
|
||||||
--exclude 'config/camera_profiles/**/*.xml' \
|
--exclude 'config/camera_profiles/**/*.xml' \
|
||||||
--exclude 'config/camera_profiles/**/*.txt' \
|
--exclude 'config/camera_profiles/**/*.txt' \
|
||||||
--exclude 'images/' \
|
--exclude 'images/' \
|
||||||
./ "$REMOTE_HOST:$REMOTE_DIR/"
|
"$STAGE/" "$REMOTE_HOST:$REMOTE_DIR/"
|
||||||
|
|
||||||
# .git is not synced, so leave the revision beside the tree for the tools that
|
# .git is not synced, so leave the revision beside the tree for the tools that
|
||||||
# run THERE and need to know what they are building (install-tower, flash.sh).
|
# run THERE and need to know what they are building (install-tower, flash.sh).
|
||||||
|
|
|
||||||
|
|
@ -76,7 +76,11 @@ and which mode it starts in are the tower's own `config.ini` `[Startup] home` /
|
||||||
```
|
```
|
||||||
|
|
||||||
It syncs the tree (leaving `.git` behind, and writing the revision into
|
It syncs the tree (leaving `.git` behind, and writing the revision into
|
||||||
`.revision` beside it instead), then configures and builds **on the tower**. The
|
`.revision` beside it instead), then configures and builds **on the tower**. Only
|
||||||
|
files git knows about are synced - tracked ones and new ones not yet added, as
|
||||||
|
they are in the working tree - so nothing `.gitignore` names (build trees, editor
|
||||||
|
caches, `.claude/worktrees/`, the camera bench's example pictures) reaches the
|
||||||
|
tower, and a file left there by an older deploy is removed. The
|
||||||
program already running keeps running the old binary until it is restarted:
|
program already running keeps running the old binary until it is restarted:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
|
|
|
||||||
|
|
@ -1849,6 +1849,7 @@ struct Application::Impl {
|
||||||
if (m == Mode::Manual) camera->stop();
|
if (m == Mode::Manual) camera->stop();
|
||||||
else camera->start();
|
else camera->start();
|
||||||
scheduler->setMode(m, pan);
|
scheduler->setMode(m, pan);
|
||||||
|
if (m == Mode::Manual && was != Mode::Manual) stopScanMove();
|
||||||
if (m == Mode::Pan) {
|
if (m == Mode::Pan) {
|
||||||
const auto& h = scheduler->panHeadingsNow();
|
const auto& h = scheduler->panHeadingsNow();
|
||||||
LOG_INFO << "mode pan: " << panText(pan) << " - " << h.size()
|
LOG_INFO << "mode pan: " << panText(pan) << " - " << h.size()
|
||||||
|
|
@ -1861,6 +1862,22 @@ struct Application::Impl {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Leaving a scan: stop the move it last sent, which the firmware would
|
||||||
|
// otherwise finish - a slow return to the first waypoint can take many
|
||||||
|
// seconds the operator spends waiting for the gimbal to answer. The firmware
|
||||||
|
// ramps the axis down and holds where it comes to rest (it does not resume
|
||||||
|
// the move), and the next MOVE or jog supersedes a stop still ramping down.
|
||||||
|
// Sent whether or not telemetry shows motion, since a MOVE sent this tick
|
||||||
|
// is not in it yet. Never during a homing, which a STOP ends in ERROR.
|
||||||
|
void stopScanMove() {
|
||||||
|
const MotorTelemetry t = motor->telemetry();
|
||||||
|
if (t.yaw.state == AxisState::Homing ||
|
||||||
|
(t.pitch_present && t.pitch.state == AxisState::Homing))
|
||||||
|
return;
|
||||||
|
if (anyLeftoverMove()) LOG_INFO << "stopping the gimbal where it is";
|
||||||
|
motor->sendCommand("STOP ALL");
|
||||||
|
}
|
||||||
|
|
||||||
// A pan the gimbal can actually do: its pitch inside the homed window (not
|
// A pan the gimbal can actually do: its pitch inside the homed window (not
|
||||||
// clamped to it - that would image an elevation nobody asked for), and at
|
// clamped to it - that would image an elevation nobody asked for), and at
|
||||||
// least one of its headings inside the reachable yaw arc.
|
// least one of its headings inside the reachable yaw arc.
|
||||||
|
|
|
||||||
|
|
@ -35,7 +35,7 @@ const std::vector<HelpSection>& helpCatalog() {
|
||||||
"Pitch defaults to 0 (level); a yaw-only tower ignores it. Key p pans",
|
"Pitch defaults to 0 (level); a yaw-only tower ignores it. Key p pans",
|
||||||
"30 deg around the current aim.",
|
"30 deg around the current aim.",
|
||||||
"Example: mode pan 90 30"}},
|
"Example: mode pan 90 30"}},
|
||||||
{"mode manual", "Stop scanning; aim by hand (key m). Cancels a running procedure.", {}},
|
{"mode manual", "Stop scanning, and the gimbal where it is; aim by hand (key m). Cancels a running procedure.", {}},
|
||||||
}},
|
}},
|
||||||
{"Capture", "Images and cameras. Manual mode, homed gimbal.", {
|
{"Capture", "Images and cameras. Manual mode, homed gimbal.", {
|
||||||
{"snapshot", "Take one image now (key Space).", {
|
{"snapshot", "Take one image now (key Space).", {
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue