@lobehub/ui
Version:
Lobe UI is an open-source UI component library for building AIGC web apps
49 lines (48 loc) • 1.66 kB
JavaScript
"use client";
import { useCallback, useEffect, useMemo, useState, useSyncExternalStore } from "react";
//#region src/dashboard/hooks.ts
function useMediaQuery(query) {
const list = useMemo(() => typeof window === "undefined" ? null : window.matchMedia(query), [query]);
const subscribe = useCallback((listener) => {
if (!list) return () => {};
list.addEventListener("change", listener);
return () => list.removeEventListener("change", listener);
}, [list]);
return useSyncExternalStore(subscribe, () => list?.matches ?? false, () => false);
}
/**
* Tablet and below. Matches `responsive.laptop` (max-width 991px), which is
* the width where a fixed console sidebar becomes a drawer.
*/
function useIsCompact() {
return useMediaQuery("(max-width: 991px)");
}
function usePrefersReducedMotion() {
return useMediaQuery("(prefers-reduced-motion: reduce)");
}
/**
* Reads storage after mount so the first render matches the server.
* Omit `key` to keep the value in memory only.
*/
function useLocalStorage(key, defaultValue) {
const [value, setValue] = useState(defaultValue);
useEffect(() => {
if (!key) return;
try {
const raw = window.localStorage.getItem(key);
if (raw !== null) setValue(JSON.parse(raw));
} catch {}
}, [key]);
return [value, useCallback((next) => {
setValue((current) => {
const resolved = typeof next === "function" ? next(current) : next;
if (key) try {
window.localStorage.setItem(key, JSON.stringify(resolved));
} catch {}
return resolved;
});
}, [key])];
}
//#endregion
export { useIsCompact, useLocalStorage, useMediaQuery, usePrefersReducedMotion };
//# sourceMappingURL=hooks.mjs.map