앱 위젯에서 구분선 리사이즈 안되는 문제 수정

This commit is contained in:
Macbook
2026-06-14 17:54:26 +09:00
parent 7f5e7b22d2
commit ead2ba6b3a
9 changed files with 229 additions and 65 deletions
@@ -5,7 +5,7 @@ import {
FLOATING_WIDGET_CELL_MIN_W,
FLOATING_WIDGET_GRID_GAP,
} from '../types/floatingWidget';
import { bindWindowDrag, isPrimaryPointerButton } from '../utils/pointerDrag';
import { isPrimaryPointerButton } from '../utils/pointerDrag';
type SplitAxis = 'col' | 'row';
@@ -15,6 +15,7 @@ interface Options {
getColFr: () => number[];
getRowFr: () => number[];
getBodySize: () => { width: number; height: number };
onSplitEnd?: () => void;
}
export function useFloatingWidgetGridSplit({
@@ -23,18 +24,12 @@ export function useFloatingWidgetGridSplit({
getColFr,
getRowFr,
getBodySize,
onSplitEnd,
}: Options) {
const unbindDragRef = useRef<(() => void) | null>(null);
const endDrag = useCallback(() => {
unbindDragRef.current?.();
unbindDragRef.current = null;
document.body.style.cursor = '';
document.body.style.userSelect = '';
}, []);
const activeDragRef = useRef<(() => void) | null>(null);
useEffect(() => () => {
unbindDragRef.current?.();
activeDragRef.current?.();
document.body.style.cursor = '';
document.body.style.userSelect = '';
}, []);
@@ -60,43 +55,67 @@ export function useFloatingWidgetGridSplit({
const startY = e.clientY;
const startColFr = [...getColFr()];
const startRowFr = [...getRowFr()];
const startSize = getBodySize();
document.body.style.cursor = axis === 'col' ? 'col-resize' : 'row-resize';
document.body.style.userSelect = 'none';
unbindDragRef.current?.();
unbindDragRef.current = bindWindowDrag(
(xy) => {
if (axis === 'col') {
const delta = xy.x - startX;
onColFrChange(adjustAdjacentGridFr(
startColFr,
index,
delta,
startSize.width,
FLOATING_WIDGET_GRID_GAP,
FLOATING_WIDGET_CELL_MIN_W,
));
return;
}
const delta = xy.y - startY;
onRowFrChange(adjustAdjacentGridFr(
startRowFr,
activeDragRef.current?.();
const onMove = (ev: PointerEvent) => {
const size = getBodySize();
if (axis === 'col') {
if (size.width <= 0) return;
const delta = ev.clientX - startX;
onColFrChange(adjustAdjacentGridFr(
startColFr,
index,
delta,
startSize.height,
size.width,
FLOATING_WIDGET_GRID_GAP,
FLOATING_WIDGET_CELL_MIN_H,
FLOATING_WIDGET_CELL_MIN_W,
));
},
() => {
handle.classList.remove('fw-grid-splitter--active');
endDrag();
},
{ preventTouchScroll: true },
);
}, [endDrag, getBodySize, getColFr, getRowFr, onColFrChange, onRowFrChange]);
return;
}
if (size.height <= 0) return;
const delta = ev.clientY - startY;
onRowFrChange(adjustAdjacentGridFr(
startRowFr,
index,
delta,
size.height,
FLOATING_WIDGET_GRID_GAP,
FLOATING_WIDGET_CELL_MIN_H,
));
};
const onUp = (ev: PointerEvent) => {
handle.classList.remove('fw-grid-splitter--active');
document.body.style.cursor = '';
document.body.style.userSelect = '';
try {
if (handle.hasPointerCapture(ev.pointerId)) {
handle.releasePointerCapture(ev.pointerId);
}
} catch {
/* ignore */
}
document.removeEventListener('pointermove', onMove, true);
document.removeEventListener('pointerup', onUp, true);
document.removeEventListener('pointercancel', onUp, true);
activeDragRef.current = null;
onSplitEnd?.();
};
document.addEventListener('pointermove', onMove, { capture: true });
document.addEventListener('pointerup', onUp, { capture: true });
document.addEventListener('pointercancel', onUp, { capture: true });
activeDragRef.current = () => {
document.removeEventListener('pointermove', onMove, true);
document.removeEventListener('pointerup', onUp, true);
document.removeEventListener('pointercancel', onUp, true);
};
}, [getBodySize, getColFr, getRowFr, onColFrChange, onRowFrChange, onSplitEnd]);
const onColSplitPointerDown = useCallback(
(index: number) => (e: React.PointerEvent) => startSplit(e, 'col', index),