anc
Экран записи и проигрыватель: волна, источники, отметки, звук ↔ текст
Запись:
- Время — по записанному звуку, паузы не в счёт (позиция сессии записи,
ms в событиях уровня, position_ms в recorder_status).
- Живая «волна» последней минуты, «Микрофон / Звук компьютера —
слышно / тишина», объём записи; «Остановить и расшифровать».
- «★ Отметить момент»: отметка с подписью (Meeting.markers,
add_marker / set_markers); видна в расшифровке и на проигрывателе.
Проигрыватель (player.ts):
- Полоса внизу экрана записи: играть, ±15 с, скорость до 2×, «волна»
всей встречи (клик и протяжка — перемотка, отметки, текущее место),
«★» — отметить место. Две дорожки записи играют вместе и
подравниваются. Живёт дольше перерисовок экрана — звук не прерывается.
- Звук читается с диска протоколом asset: только из папки записей
(protocol-asset, scope на папку, media-src в CSP); «волна» считается
один раз и кэшируется в peaks.json.
- Время реплики и отметки — кнопка «слушать отсюда», звучащая реплика
подсвечивается; пробел — играть/пауза, ←/→ — 5 с.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
b82e259
2 октября 2026 г.
playback.rs
//! Проигрыватель: что играть и «волна» всей встречи для прокрутки.
//!
//! Звук отдаётся интерфейсу самими файлами записи (протокол `asset:` Tauri):
//! у записи с двумя дорожками — оба WAV, интерфейс играет их вместе. «Волна»
//! — громкость по равным отрезкам всей записи: по ней видно, где говорили,
//! и по ней перематывают. Считается один раз и кладётся рядом
//! (`peaks.json`); двухчасовой mp3 декодируется секунды, WAV читается кусками.
use ;
use WavFile;
use ;
/// Сколько отрезков в «волне»: шире окна программы не бывает.
pub const BUCKETS: usize = 1_600;
/// Громкость отрезков одной дорожки: максимум модуля сэмпла, 0…1.
/// «Волна» записи: по всем дорожкам, из кэша, если он про ту же длину.