/** * Состояние сворачиваемых секций редактора фото. * * Все секции по умолчанию свёрнуты, а выбор пользователя хранится в браузере * (localStorage), поэтому панель открывается в том же виде после перезагрузки * и переключения фото. Серверные настройки для этого не нужны. */ export const EDITOR_SECTIONS = [ 'light', 'curve', 'color', 'mixer', 'pointColor', 'correction', 'effects' ] as const; export type EditorSection = (typeof EDITOR_SECTIONS)[number]; /** true — секция свёрнута. */ export type SectionCollapse = Record; export const EDITOR_SECTIONS_KEY = 'galo.edit.sections'; /** По умолчанию все секции свёрнуты. */ export function defaultSectionCollapse(): SectionCollapse { return { light: true, curve: true, color: true, mixer: true, pointColor: true, correction: true, effects: true }; } function isRecord(value: unknown): value is Record { return typeof value === 'object' && value !== null && !Array.isArray(value); } /** * Приводит сохранённое значение к полному набору секций: неизвестные ключи * отбрасываются, небулевы значения и отсутствующие ключи получают дефолт. */ export function normalizeSectionCollapse(raw: unknown): SectionCollapse { const defaults = defaultSectionCollapse(); if (!isRecord(raw)) return defaults; const out = defaults; for (const section of EDITOR_SECTIONS) { const value = raw[section]; if (typeof value === 'boolean') out[section] = value; } return out; } type ReadableStorage = Pick; type WritableStorage = Pick; /** Читает состояние секций из браузера; без хранилища — дефолт. */ export function loadSectionCollapse( storage?: ReadableStorage | null ): SectionCollapse { const target = storage === undefined ? browserStorage() : storage; if (!target) return defaultSectionCollapse(); try { const raw = target.getItem(EDITOR_SECTIONS_KEY); if (!raw) return defaultSectionCollapse(); return normalizeSectionCollapse(JSON.parse(raw)); } catch { return defaultSectionCollapse(); } } /** Сохраняет состояние секций в браузере; ошибки хранилища игнорируются. */ export function saveSectionCollapse( state: SectionCollapse, storage?: WritableStorage | null ): void { const target = storage === undefined ? browserStorage() : storage; if (!target) return; try { target.setItem(EDITOR_SECTIONS_KEY, JSON.stringify(state)); } catch { // Приватный режим или переполненное хранилище не должны ломать панель. } } function browserStorage(): Storage | null { return typeof localStorage === 'undefined' ? null : localStorage; }