vojo/src/app/state/sidebarWidth.ts

31 lines
1.2 KiB
TypeScript

import {
atomWithLocalStorage,
getLocalStorageItem,
setLocalStorageItem,
} from './utils/atomWithLocalStorage';
export const SIDEBAR_WIDTH_KEY = 'vojo_sidebar_width';
// Floor must fit the StreamHeader tabs row in full: 3 segment buttons
// (Личные/Каналы/Роботы — RU is the widest locale) plus the two
// action icons (Plus / Search) plus the row's 8px horizontal padding.
// Measured at ≈378px in RU; 384 gives a few px of breathing room and
// keeps the icon cluster from clipping at the curtain's right edge.
export const SIDEBAR_WIDTH_MIN = 384;
export const SIDEBAR_WIDTH_DEFAULT = 416;
const readSidebarWidth = (key: string): number => {
const raw = getLocalStorageItem<unknown>(key, SIDEBAR_WIDTH_DEFAULT);
const value = typeof raw === 'number' && Number.isFinite(raw) ? raw : SIDEBAR_WIDTH_DEFAULT;
return Math.max(SIDEBAR_WIDTH_MIN, Math.round(value));
};
export const sidebarWidthAtom = atomWithLocalStorage<number>(
SIDEBAR_WIDTH_KEY,
readSidebarWidth,
setLocalStorageItem
);
export const clampSidebarWidth = (px: number, viewportWidth: number): number => {
const max = Math.max(SIDEBAR_WIDTH_MIN, Math.floor(viewportWidth / 3));
return Math.max(SIDEBAR_WIDTH_MIN, Math.min(max, Math.round(px)));
};