Files
ewsdr/doc/ANDROMEDA.md
T
ew8bakandClaude Opus 4.8 2d7290e44d feat(cat): Andromeda/G2 front panel support (serial, LED indicators)
Bidirectional Apache Labs Andromeda/G2 front-panel protocol on top of CAT.
Panel logic lives in dedicated units; existing files get only thin hooks.

New units:
- AndromedaMap.pas   — data only: action enums + default button/encoder
  layout tables and LED (ZZZI) numbers (mirroring the Thetis defaults)
- AndromedaPanel.pas — TAndromedaPanel: inbound panel events -> controller
  actions (marshalled via Invoke), state subscription -> ZZZI push via SendProc

Hooks:
- CATEngine: parse ZZZD/ZZZU/ZZZE/ZZZP/ZZZS into generic TCATContext callbacks
- CATAdapter: creates the panel, routes engine callbacks to it, supplies the
  SendProc to the Andromeda port, AddStateListener, ZZZS handshake
- CATSerial: Andromeda flag in port config + HasAndromeda/SendToAndromeda
- RadioController: AddStateListener (multicast, does not steal MainForm's
  OnStateChanged)
- Settings/SettingsForm/MainForm: CATSerialAndromeda[0..3] + persistence + checkbox

First version: serial transport, hardcoded default mapping, LED indicators
(MOX/Tune/CTUN/VFO A-B/Split/NB/NR/SNB/ANF/Squelch). Doc: doc/ANDROMEDA.md.

TODO: default button mapping does not match the physical panel (hardcoded) —
to be fixed later; also ZZMF/LCD text, TCP G2V2 transport, configurable mapping.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-26 11:40:10 +03:00

12 KiB
Raw Blame History

Поддержка передней панели Andromeda / G2 в EWSDR

Ветка разработки: feature/cat-commands-expansion. Дата последнего обновления: 2026-06-26.

Документ описывает поддержку аппаратной передней панели Apache Labs Andromeda / ANAN-G2 (поворотные энкодеры, кнопки, LED-индикаторы, LCD). За эталон протокола взят Thetis (Andromeda/Andromeda.cs, CAT/CATCommands.cs).

См. также CAT_STATUS.md — общий статус CAT-подсистемы.


1. Что такое Andromeda и чем отличается от обычного CAT

Andromeda — это не отдельный набор команд, а двунаправленный протокол панели поверх CAT-фрейминга. В отличие от обычного CAT (реактивный «запрос → ответ»), панель требует, чтобы хост сам инициативно отправлял обновления подсветки.

            ZZZD/ZZZU/ZZZE/ZZZP/ZZZS  (панель → хост: ввод)
   ┌─────────┐  ───────────────────────────►  ┌──────────┐
   │ Панель  │                                 │  EWSDR   │
   │ G2 /    │  ◄───────────────────────────   │  (хост)  │
   │Andromeda│        ZZZI / ZZMF / ZZZS;       └──────────┘
   └─────────┘  (хост → панель: подсветка, LCD, рукопожатие)
Направление Команды Назначение
Панель → хост ZZZS<v> панель сообщает версию HW/SW (рукопожатие)
ZZZU<nn> / ZZZD<nn> энкодер VFO повёрнут вверх/вниз на nn шагов
ZZZE<eees> энкодер #ee повёрнут (01–20 = +шаг, 5170 = −шаг)
ZZZP<bbs> кнопка #bb: s=1 нажата, 2 long-press, 0 отпущена
Хост → панель ZZZI<nn><s> LED-индикатор #nn (0019) вкл (1)/выкл (0)
ZZMF<30 цифр> текст мультифункц. энкодера на LCD (пока не реализован)
ZZZS; запрос версии у панели

2. Архитектура реализации

Логика панели вынесена в отдельные юниты; в существующих файлах — только тонкие хуки. Зависимости однонаправленные, без циклов.

                       ┌────────────────────┐
   serial-порт ──────► │ TCATEngine          │  разбор ZZZ* → generic callbacks
   (Andromeda)         │ (CATEngine.pas)     │  (OnPanelVfoStep/Encoder/Button/Version)
                       └─────────┬──────────┘
                                 │ callbacks
                       ┌─────────▼──────────┐    создаёт/связывает
                       │ TCATAdapter         │ ◄───────────────────┐
                       │ (CATAdapter.pas)    │                     │
                       └─────────┬──────────┘                     │
              SendProc (ZZZI/ZZZS;) │   ▲ AddStateListener         │
              на Andromeda-порт     ▼   │ (push индикаторов)        │
                       ┌────────────────────┐         ┌────────────┴───────┐
                       │ TAndromedaPanel     │ ───────►│ TRadioController   │
                       │ (AndromedaPanel.pas)│  Invoke │ (ядро)             │
                       │  использует ▼       │ действия└────────────────────┘
                       │ AndromedaMap.pas    │  (таблицы раскладки — только данные)
                       └────────────────────┘
Файл Роль
AndromedaMap.pas Только данные: enum'ы TAndButton / TAndEncoder / TAndIndicator, дефолтные таблицы раскладки кнопок/энкодеров и номера LED (ZZZI). Без логики и зависимостей.
AndromedaPanel.pas TAndromedaPanel — «мозг»: входящие события → действия контроллера (свой маршалинг через FController.Invoke); подписка на состояние контроллера → построение ZZZI → отправка через callback SendProc. Зависит только от RadioController + AndromedaMap.
CATEngine.pas Разбор входящих ZZZD/ZZZU/ZZZE/ZZZP/ZZZS в 4 generic-callback'а TCATContext. Движок остаётся чистым парсером, про Andromeda «не знает».
CATAdapter.pas Тонкий клей: создаёт панель, маршрутизирует callback'и движка в неё, даёт SendProc на Andromeda-порт, регистрирует панель как слушателя состояния, инициирует рукопожатие.
CATSerial.pas Флаг Andromeda в конфиге порта + HasAndromeda / SendToAndromeda.
RadioController.pas AddStateListener — multicast-наблюдатель состояния (push не «ворует» единственный OnStateChanged, занятый MainForm).
Settings.pas / SettingsForm.pas / MainForm.pas Поле CATSerialAndromeda[0..3], персист, чекбокс на каждом serial-порту.

Потоки

  • Входящие хэндлеры (HandleVfoStep/Encoder/Button/Version) зовутся из потока CAT-транспорта и маршалят действия в поток контроллера через FController.Invoke (GUI = TThread.Synchronize).
  • Слушатель состояния и SendProc работают из потока, вызвавшего Changed(); отправка в порт потокобезопасна (serial SendStr под своим локом).

3. Раскладка по умолчанию (AndromedaMap.pas)

Раскладка зашита в коде (первая версия). Правится в AndromedaMap.pas.

Кнопки (ZZZP, индекс 0-based после разбора)

# Действие # Действие
0 MOX 9 SNB
1 Tune (TUN) 10 Split (TX VFO-B)
2 Band Up 11 VFO Swap (актив. A/B)
3 Band Down 12 CTUN
4 Mode Up 13 Mute
5 Mode Down 14 CTCSS
6 NB 15 Squelch on/off
7 NR 16 Filter Up
8 ANF 17 Filter Down

Энкодеры (ZZZE, индекс 0-based)

# Параметр Шаг
0 AF Gain (громкость) ±1
1 AGC-T ±1 dB
2 Drive (мощность) ±1 %
3 Squelch level ±1
4 Filter width ±50 Гц (AND_BW_STEP_HZ)
VFO энкодер VFO (ZZZU/ZZZD) ±10 Гц/шаг (AND_VFO_STEP_HZ)

Индикаторы (ZZZI, номера зеркалят дефолт Thetis)

LED # Индикатор LED # Индикатор
1 MOX 12 Split
2 ATU Ready (нет в ewsdr) 13 NB
3 Tune 14 NR
6 Shift (нет) 15 SNB
7 CTUN 16 ANF
8/9 RIT/XIT (нет) 17 Squelch
10 VFO A/B
11 VFO Lock (нет)

Драйвятся реально: MOX, Tune, CTUN, VFO A/B, Split, NB, NR, SNB, ANF, Squelch. Остальные слоты дефолтной таблицы Thetis (ATU/Shift/RIT/XIT/VFOLock) в ewsdr функций не имеют и не зажигаются.


4. Как включить

  1. Подключить панель как обычный serial CAT-порт (USB).
  2. Settings → CAT → выбрать нужный Serial Port, поставить Enable и параметры порта (скорость и т.д. — как требует панель).
  3. Поставить галку «Andromeda / G2 front panel» на этом порту.
  4. При применении настроек EWSDR пошлёт ZZZS;; панель ответит версией — после этого включается push индикаторов и панель управляет радио.

Только один порт может быть Andromeda-портом (первый помеченный).

Настройки сохраняются ключами cat_serial_androm_N / ser_androm_N (N = 0..3) в JSON-конфиге.


5. Что сделано / что осталось

Сделано (первая версия)

  • Транспорт: serial (USB CAT).
  • Вход: ZZZD/ZZZU (VFO), ZZZE (энкодеры), ZZZP (кнопки), ZZZS (рукопожатие).
  • Выход: ZZZI — LED-индикаторы (push от OnStateChanged, дедуп повторов).
  • Раскладка — зашитый дефолт.
  • UI-чекбокс на каждый serial-порт + персист.

Осталось / возможные улучшения

Задача Заметки
ZZMF — текст на LCD мультифункц. энкодера кодировка: 15 ASCII-символов парами цифр (код−32)
TCP-транспорт (G2 V2 panel) сейчас только serial; нужен режим в CATTcp
Настраиваемая раскладка сейчас зашита; вынести в конфиг/UI (как AndromedaEditForm в Thetis)
Long-press кнопок принимается (ZZZP state=2), но действий пока нет — обрабатывается только нажатие (state=1)
Индикаторы RIT/XIT/PureSignal/Diversity/ATU нет соответствующих функций в TRadioController
Мультифункц. энкодер (aeMulti) назначение не задано

6. Точки расширения (чек-лист)

  • Добавить действие кнопки/энкодера: новый элемент в TAndButton/TAndEncoder (AndromedaMap.pas) + ветка в TAndromedaPanel.SyncButton/SyncEncoder (AndromedaPanel.pas) + правка таблицы AND_BUTTON_MAP/AND_ENCODER_MAP.
  • Добавить индикатор: элемент TAndIndicator + номер в AND_INDICATOR_NUM + push в SyncAllIndicators и в OnControllerState (по нужному rf*-полю).
  • Изменить раскладку: только AndromedaMap.pas (таблицы-константы).
  • Сверяться с форматами Thetis: Andromeda/Andromeda.cs (логика панели, EIndicatorActions/EButtonBarActions/EEncoderActions) и CAT/CATCommands.cs (ZZZ*).