Files
ds-galo/openspec/changes/archive/2026-10-24-photo-effects-editing/tasks.md
T
iu cb9433666a chore(openspec): архивировать photo-effects-editing и обновить photos
Изменение применено к основной спеке photos: эффекты, виньетка, зерно,
живой предпросмотр, свёрнутые секции панели и редактирование из просмотрщика.
Change перемещён в archive.
2026-10-24 22:58:07 +03:00

11 KiB
Raw Blame History

Tasks

1. Модель правок и нормализация (Go)

  • 1.1 Добавить EffectsParams, VignetteParams, GrainParams и поле EditParams.Effects в backend/internal/photos/edit.go, включая режимы виньетки и hex-цвет — проверить cd backend && go build ./internal/photos/
  • 1.2 Реализовать нормализацию: диапазоны, дефолты midpoint 50 / feather 50 / size 25 / roughness 50, неизвестный режим → light, валидный hex-цвет; обновить IsEmpty/JSON так, чтобы дефолты без силы не считались правкой — проверить cd backend && go test ./internal/photos/ -run TestEffectsParams -v
  • 1.3 Проверить обратную совместимость: {} и старые параметры только со светом/цветом читаются как пустые эффекты и рендерятся без изменений — проверить cd backend && go test ./internal/photos/ -run TestEditParamsLegacy -v

2. Пространственный рендер (Go)

  • 2.1 Добавить хелпер яркости и разделимый box-blur со скользящим окном (O(n) от радиуса, параллельно по строкам) — проверить cd backend && go test ./internal/photos/ -run TestBoxBlur -v и бенчмарк на 4000×3000
  • 2.2 Реализовать текстуру и чёткость как unsharp mask по яркости с ограничением дельты и весами по тонам (радиусы — доли min(width,height)) — проверить тест, что локальная дисперсия растёт при положительных и падает при отрицательных значениях
  • 2.3 Реализовать «Убрать дымку» через dark channel prior: атмосферный свет и карта пропускания на уменьшенной копии, интерполяция на полный кадр, положительные и отрицательные значения — проверить тест на синтетическом «задымлённом» изображении: контраст и насыщенность растут
  • 2.4 Реализовать виньетку: нормализованная геометрия (midpoint, feather, roundness), режимы «Свет»/«Цвет»/«Закарасить», защита светов — проверить тест: края темнеют/светлеют, центр не меняется, цветные режимы меняют оттенок краёв
  • 2.5 Реализовать зерно: PRNG с seed от photo.id, размер и шероховатость, аддитивный шум в яркость — проверить тест: два рендера с одинаковыми параметрами дают идентичные пиксели, сила 0 не меняет кадр
  • 2.6 Встроить эффекты в decodeAndAdjust в порядке свет → цвет → дымка → текстура → чёткость → виньетка → зерно, с пропуском пустых проходов — проверить cd backend && go test ./internal/photos/ -v и бенчмарк полного рендера
  • 2.7 Добавить e2e-сценарий: сохранение правки с эффектами, фоновый рендер edit_*, сброс, повторный рендер с тем же зерном — проверить cd backend && go test ./internal/e2e/ -run TestEffectsEdit -v

3. Клиентская модель и CPU-фолбэк (TypeScript)

  • 3.1 Добавить EffectsParams и дефолты в frontend/src/lib/edit.ts, обновить readEditParams/normalizeEditParams/isEmptyEditParams — проверить cd frontend && npm run test (edit.test.ts) и npm run check
  • 3.2 Реализовать CPU-применение виньетки и зерна (по образцу applyColorToPixels), seed и геометрия — как на сервере; тесты на затемнение краёв и детерминированность шума — проверить cd frontend && npm run test
  • 3.3 Убедиться, что гистограмма по-прежнему считается только по свету и цвету (без пространственных эффектов) — проверить npm run check и отсутствие изменений в расчёте histogram

4. WebGL-предпросмотр

  • 4.1 Перевести frontend/src/lib/webgl-preview.ts на много­проходную схему: свет/цвет в FBO-текстуру вместо экрана, два ping-pong FBO — проверить компиляцию/линковку шейдеров и npm run build
  • 4.2 Добавить проход яркости и разделимое box-размытие: малое разрешение для чёткости, несколько тапов для текстуры; включать проход только при ненулевых значениях — проверить, что текстура и чёткость видны в превью и не ломают свет/цвет
  • 4.3 Добавить предварительный расчёт дымки на CPU (атмосферный свет + карта пропускания по базовому превью) и передачу её текстурой в финальный проход — проверить, что ползунок дымки меняет превью
  • 4.4 Добавить в финальный проход виньетку (три режима) и зерно (хеш-шум) с параметрами из liveParams.effects — проверить визуально смену режимов и силы
  • 4.5 Подключить эффекты в Viewer.svelte для GL-пути и CPU-фолбэка: при previewLow снижать качество размытия, после паузы — полное; в CPU-фолбэке применять только виньетку и зерно — проверить, что интерфейс не блокируется при перетаскивании
  • 4.6 Проверить деградацию без WebGL: пространственные эффекты появляются после серверного рендера, а виньетка/зерно видны сразу — проверить ручным сценарием с отключённым WebGL2

5. UI: раздел «Эффекты»

  • 5.1 Добавить сворачиваемую секцию «Эффекты» в PhotoEditPanel.svelte со слайдерами текстуры, чёткости и дымки (EditSlider) — проверить открытие/сворачивание и изменение превью
  • 5.2 Добавить вкладки виньетки «Свет»/«Цвет»/«Закарасить», ползунки силы/средней точки/растушёвки/округлости/светов и свотч цвета для цветных режимов — проверить сохранение режима и цвета в параметрах
  • 5.3 Добавить ползунки зерна (сила, размер, шероховатость) — проверить, что сила 0 не добавляет правку
  • 5.4 Подключить эффекты к существующему сохранению (scheduleSave/photosApi.edit), переключению фото и глобальному сбросу — проверить PATCH /api/photos/:id/edit с effects, сброс очищает параметры и edit_*, переключение фото не теряет несохранённые эффекты
  • 5.5 Проверить сборку и типы: cd frontend && npm run check && npm run build

6. Интеграционная проверка

  • 6.1 Ручной прогон матрицы: только эффекты; эффекты вместе со светом/цветом; сброс; правка во время переключения фото; фото без effects; копия фото не наследует эффекты; видео отклоняется — проверить в запущенном инстансе
  • 6.2 Замерить время фонового рендера полноразмерного фото с включёнными текстурой/чёткостью/дымкой и сравнить с текущим рендером света/цвета — проверить по логам воркера и бенчмарку
  • 6.3 Прогнать общие проверки репозитория: make test, фронтенд-тесты npm run test и сборку make build

7. Свёрнутые секции редактора

  • 7.1 Добавить frontend/src/lib/editor-sections.ts (дефолты, чтение/запись localStorage, нормализация) и тесты — проверить cd frontend && npm run test (editor-sections.test.ts)
  • 7.2 Сделать все сворачиваемые секции PhotoEditPanel.svelte свёрнутыми по умолчанию и подключить сохранение состояния — проверить npm run check
  • 7.3 Проверить в Chrome: по умолчанию всё свёрнуто, развёрнутое состояние переживает перезагрузку и смену фото — сценарий с CDP, без ошибок в консоли

8. Вкладка редактирования только в просмотрщике

  • 8.1 Скрыть вкладку «Редактирование» в режиме сетки через activeTab в PhotoPanel.svelte — проверить cd frontend && npm run check
  • 8.2 Проверить в Chrome: в сетке доступна только «Сведения», в просмотрщике — «Редактирование», после возврата в сетку вкладка снова скрыта — CDP-сценарий, без ошибок в консоли

Workflow follow-up

  • Архивировать изменение после удовлетворения требований ревью проекта.
  • Проверить архивированный результат: дельта-спека photos применена к основной спеке.