- категория connection теперь только жизненный цикл соединения; INIT/PING/keepalive
переклассифицированы в ETCP/SOCKET/KEEPALIVE/REALITY/ROUTING, удалены дубли
- settingsdialog: устранён дубль my_node_name в конфиге (двухпроходная запись + только при изменении)
- storagesettingspage: канонические ключи storage_total_size/storage_unit_size с суффиксом M/G
- audiodevicesettingspage: compressor_max_gain_db min 0→1
- etcp_connections: %s-баг в логе TCP link (addr → sockaddr_storage_to_str)
- docs/sample: [chatserver], актуализированы ключи хранилища
- node_conn_direct_close: immediate conn cleanup when links are down
(graceful fin_wait on a down conn left a lingering entry, so re-open
in Phase3 stuck in 'pending' with no timer and scan never continued)
- tcp_link_close_cb: skip etcp_link_close if conn was already closed
synchronously during etcp_on_link_down cascade (fixes use-after-free)
Полностью убрана фича периодического обмена CSV-метриками с Ed25519-подписью:
- ETCP_SECTION_METRICS и парсинг/верификация секции
- struct etcp_metrics, etcp_metrics_add_*/start/stop и снапшот-таймер
- мёртвый API on_metrics_rcvd/metrics_user_ptr (никто не подписан)
- link->remote_ed25519_pubkey (заполнялся только на клиенте → верификация на сервере всегда падала)
- stats_dir в UTUN_INSTANCE
Общий sc_stream_sign_* (деривация Ed25519 из X25519) и INIT-передача обоих ключей сохранены.
- chatgui: просмотрщик изображений (ImageViewerWindow) с зумом/поворотом
- chatgui: отправка картинок как image с определением разрешения и типа
- chatgui: у видео-пузыря строка info (res·size·bitrate) и бейдж только длительность
- chatgui: контекстное меню медиа (сохранить в файл/скачать)
- chatgui-android: большие emoji-only сообщения, битрейт/разрешение у видео
- chatgui-android: сохранение неактивных интерфейсов как закомментированные секции
- chatgui-android: отправка картинок по расширению (jpg/png/gif/bmp/webp)
- photo_sender: content-type и расширение по типу файла
- C-слой: video_sender (content_type video/mp4, media_video=0 без FFmpeg)
- chat_msg_submit: duration/width/height для метаданных видео в теле сообщения
- JNI: nativeVideoSend + NativeLib/Repository/ViewModel
- VideoRecordScreen: CameraX VideoCapture, 4 пресета качества (разрешение+битрейт),
выбор камеры (селфи/широкая/обычная/макро/теле по фокусу), тумблер подсветки,
запись/пауза/отправить, лимит 60с
- InputBar: единая кнопка — короткий тап переключает voice/video, удержание — запись
- режим камеры/микрофона сохраняется в ViewModel
Сервер (пассивная сторона) на UP шлёт общий RESYNC, клиент по нему
заново анонсирует группы (JOIN_GROUP), которые ему положены по конфигу.
Чинит потерю маршрутов при одностороннем флэпе, когда клиент не замечает
разрыв и не перешлёт JOIN_GROUP повторно.
- main.cpp: на Linux принудительно QT_QPA_PLATFORM=xcb (если не задан) — на Wayland
композитор владеет позицией окна, на XWayland ручной move/resize работает полностью
- videoplayer_window: вернуть ручной move + ручной resize с пропорцией (один путь,
без платформозависимого нативного startSystemMove/Resize)
- окно: startSystemMove/startSystemResize вместо ручного move/setGeometry
(Wayland игнорирует позицию окна) — драг и resize за левый/верхний край работают
- пропорции: снэп к videoAspect после нативного resize (дебаунс 150мс)
- перемотка: backpressure по m_buffered (декод не убегает вперёд и воркер живёт
для seek), seek через av_seek_frame(-1, us), пропуск кадров с AV_NOPTS_VALUE
- SeekSlider: клик по шкале = прыжок к позиции
- крестик закрытия справа вверху; курсор контролов — стрелка
- test_video_engine: проверка seek
- m_render WA_TransparentForMouseEvents — события мыши напрямую в окно (drag работает)
- открытие: видео влезает — натуральный размер по центру; больше экрана — fullscreen
- resize мышью за 4 края и 4 угла, пропорции сохраняются (якорь = противоположный край)
- нижний край доступен через eventFilter на панели контролов (пустые поля пропагируют)
- сброс fullscreen при повторном playFile
- presentTick: кадры всегда по мастер-часам, завершение только когда очередь пуста
- clockMs: по окончании аудио часы в конец (хвостовые кадры не теряются)
- fallback на системные часы, если аудио-устройство недоступно
- tests/test_video_engine: smoke-тест FFmpeg-декодера (opened/frames/seek)