项目文件夹

文件
wehub-resource-sync 2114b14ee0
Sync main into demo / sync (push) Has been cancelled
chore: import upstream snapshot with attribution
2026-07-13 12:35:26 +08:00

59 行
1.9 KiB
TypeScript

此文件含有模棱两可的 Unicode 字符
此文件含有可能会与其他字符混淆的 Unicode 字符。 如果您是想特意这样的,可以安全地忽略该警告。 使用 Escape 按钮显示他们。
import { useLayoutEffect, useMemo, useRef, useState } from 'react';
import { useDraggableSheet } from './useDraggableSheet';
import { computeMapTabSheetSnaps } from '../utils/mapSheetSnaps';
/**
* 「我 / 贡献」Tab Sheetpeek / **中间档 50% 屏高** / full 顶满;进入时吸附第三档(盖住搜索栏)。
* 中间档与「本地生活脉搏」(约 20%)不同。
*
* 须在**同一次** layout 回调里根据实测容器高度写入 snaps 并 setHeight(full)。
* 若拆成两个 useLayoutEffect,会先按默认 full=700 执行 setHeight 并打标「已初始化」,
* 实测 full(如 h-48)到来后只会 Math.min 卡在 700,导致默认高度低于「顶满」吸附点。
*/
export function useMapTabBottomSheet(containerRef: React.RefObject<HTMLElement | null>) {
const [snaps, setSnaps] = useState({ peek: 72, middle: 160, full: 700 });
const snapArray = useMemo(
() => [snaps.peek, snaps.middle, snaps.full],
[snaps.peek, snaps.middle, snaps.full],
);
const { height, setHeight, isDragging, pointerHandlers } = useDraggableSheet({
snapPoints: snapArray,
initialHeight: snaps.full,
minHeight: 56,
maxHeight: snaps.full,
});
const initialFullAppliedRef = useRef(false);
useLayoutEffect(() => {
const el = containerRef.current;
if (!el) return;
const update = () => {
const h = el.clientHeight;
if (h <= 0) return;
const next = computeMapTabSheetSnaps(h);
setSnaps(next);
if (!initialFullAppliedRef.current) {
setHeight(next.full);
initialFullAppliedRef.current = true;
} else {
setHeight((cur) => Math.min(cur, next.full));
}
};
update();
const ro = new ResizeObserver(update);
ro.observe(el);
return () => ro.disconnect();
}, [setHeight]);
return {
snaps,
sheetHeight: height,
setSheetHeight: setHeight,
isDragging,
pointerHandlers,
};
}