λκ΅°κ° κ²°κ΅ λ¬Όμ΄ λ³΄λ €κ³ νμ΄μ! μλ‘μ΄ νν¬ APIκ° μ¬κΈ°μ λμμ΄ λ μ μμ΅λλ€. λλΆλΆμ APIλ HOCλ₯Ό νν¬μ μ§μ 맀ννμ¬ κ±°μ λμΌνκ² μ μ§ν μ μλ€κ³ μκ°ν©λλ€.
connectDragSource
λ° connectDropTarget
μ useRef
κ°μ μ λ¬νλ κ²μΌλ‘ λ체 ν μ μλμ§ κΆκΈν©λλ€. κ°λ₯νλ€λ©΄ νμ€ν 물건μ κΉ¨λνκ² λ§λ€ μ μμ΅λλ€!
μ΄ λΌμ΄λΈλ¬λ¦¬μμ νν¬ μ¬μ©μ μμνκΈ°λ₯Ό κΈ°λ€λ¦΄ μ μμ΅λλ€. μ νμ΄ μνμ λν΄ λ² μ΄νΉ λ μλ§μ λ§μ΄κ·Έλ μ΄μ λΆκΈ°λ₯Ό μ€μ ν μ μμ΅λλ€.
λλμ΄ APIκ° μ΄λ»κ² 보μΌμ§ μκ°νκΈ° μν΄ μ€ν / νν¬μ λΈλμΉμμ λκ³ μμ΅λλ€. BoardSquare κ΅¬μ± μμλ λ€μκ³Ό κ°μ΅λλ€.
const dropTarget = createDropTarget(ItemTypes.KNIGHT, {
canDrop: (props: BoardSquareProps) => canMoveKnight(props.x, props.y),
drop: (props: BoardSquareProps) => moveKnight(props.x, props.y),
})
const BoardSquare = ({ x, y, children }) => {
const black = (x + y) % 2 === 1
const [connectDropTarget, isOver, canDrop] = useDnd(
dropTarget,
connect => connect.dropTarget,
(connect, monitor) => !!monitor.isOver,
(connect, monitor) => !!monitor.canDrop,
)
return connectDropTarget(
<div>
<Square black={black}>{children}</Square>
{isOver && !canDrop && <Overlay color={'red'} />}
{!isOver && canDrop && <Overlay color={'yellow'} />}
{isOver && canDrop && <Overlay color={'green'} />}
</div>,
)
}
κ·Έλμ μ¬κΈ°μ μμ΄λμ΄λ createDropTarget
κ° λλκ·Έ / λλ‘ νλͺ©μ λν λ
Όλ¦¬μ μ§μ, ID λ° μμΈ‘μ μ€μ νκ³ useDnd νν¬κ°μ΄λ₯Ό DnD μμ€ν
μ μ°κ²°νκ³ μνμ μμ§νλ€λ κ²μ
λλ€.
μ΄κ²μ λ¨μ§ ν보 λμμΈμ μ€μΌμΉ ν κ²μ λλ€. μ€μ λ‘ κ΅¬νλμ§λ μμμ΅λλ€.
@darthtrevino μ΄λ€ μ§μ μμ μμ
νκ³ μμ΅λκΉ? refsλ₯Ό μ¬μ©νμ¬ connectDropTarget
λͺ¨λ μ κ±° ν μ μλμ§ κΆκΈν©λλ€. λλ λΉμ μ μ§μ μμ μλνλλ‘ ν μ μλμ§λ³΄κ³ μΆμ΅λλ€!
const dropTarget = createDropTarget(ItemTypes.KNIGHT, {
canDrop: (props: BoardSquareProps) => canMoveKnight(props.x, props.y),
drop: (props: BoardSquareProps) => moveKnight(props.x, props.y),
})
const BoardSquare = ({ x, y, children }) => {
const dropTargetElement = useRef(null);
const black = (x + y) % 2 === 1
const [isOver, canDrop] = useDnd(
dropTargetElement,
dropTarget,
...
)
return (
<div ref={dropTargetElement}>
<Square black={black}>{children}</Square>
{isOver && !canDrop && <Overlay color={'red'} />}
{!isOver && canDrop && <Overlay color={'yellow'} />}
{isOver && canDrop && <Overlay color={'green'} />}
</div>
)
}
@ jacobp100 μ°Έμ‘°κ° μ 곡λκ³ νν¬ μ체μμ λ°νλλ μ μ¬ν νν¬ κΈ°λ° API (μ const [isOver, canDrop, ref] = useDnd(...)
), μλΉ κ΅¬μ± μμκ° JSX νΈλ¦¬μ λ°°μΉ ν μ€λΉκ° λ κ² κ°μ΅λλ€.)
κ·Έκ² ν¨κ³Όκ° μλ€κ³ μκ°ν©λλ€. μ¬λ¬ νν¬μμ refλ₯Ό μ¬μ©νλ κ²μ΄ λ μ΄λ ΅μ§λ§ μ¬λ¬ refλ₯Ό λ¨μΌ refλ‘ κ²°ν©νλ 무μΈκ°λ₯Ό μμ±νλ κ²μ λ§μ μλ μμ΅λλ€. μ΄κ²μ μ΄λ€ λμκ΄ μ΄μμ΅λκΉ?
μ΄κ²μ λν 컨벀μ μ΄ λ¬΄μμΈμ§ λ΄μΌ ν κ² κ°μμ!
μ¬λ¬ νν¬μμ refλ₯Ό μ¬μ©νλ κ²μ΄ λ μ΄λ ΅μ§λ§ μ¬λ¬ refλ₯Ό λ¨μΌ refλ‘ κ²°ν©νλ κ²μ μμ±νλ κ²μ λ§μ μλ μμ΅λλ€.
μ°Έ, μ°Έ :-)
μ΄κ²μ μ΄λ€ λμκ΄ μ΄μμ΅λκΉ?
λ€μ μ°Ύμ μμλ κ² κ°μ΅λλ€ atm :-/-μ§λ 2 μ£Ό λμ νν¬μ λν λ§μ μ€ν ...
https://github.com/beizhedenglong/react-hooks-lib κ° μμ΅λλ€.
const { hovered, bind } = useHover(); return <div {...bind}>{hovered ? 'yes' : 'no'}</div>;
bind
μ μ¬νμ΄ ν¬ν¨λμ΄ μλ€λ λ»μΈκ°μ?
[νΈμ§ : μλμ, λ¬Όλ‘ { onMouseEnter, onMouseLeave }
λ§ ν¬ν¨ν©λλ€ ...]
νμ§λ§ λ€λ₯Έ APIκ° νν¬μμ λ°λ‘ μ°Έμ‘°λ₯Ό λ°ννλ κ²μ λ³Έ κΈ°μ΅μ΄ μμ΅λλ€.
κ·Έλ€μ§ λ§μ§ μκ³ νμ¬ κ±΄λ¬Όμ΄ μλλ° μ κ°μλ μ§μ μ experiment/hooks
μ¬κΈ°μμ λ°λ³΅ν©λλ€.
const dropTarget = createDropTarget(ItemTypes.KNIGHT, {
canDrop: props => canMoveKnight(props.x, props.y),
drop: props => moveKnight(props.x, props.y),
})
const BoardSquare = ({ x, y, children }) => {
const black = (x + y) % 2 === 1
const ref = useRef(null)
const [isOver, canDrop] = useDnd(
connect => connect(ref, dropTarget),
monitor => monitor.isOver,
monitor => monitor.canDrop,
)
return (
<div ref={ref}>
<Square black={black}>{children}</Square>
{isOver && !canDrop && <Overlay color={'red'} />}
{!isOver && canDrop && <Overlay color={'yellow'} />}
{isOver && canDrop && <Overlay color={'green'} />}
</div>,
)
}
μ΄κ²μ΄ dragSource λ° dropTarget μ°κ²°μ΄ μλνλ λ°©μμ λλ€. refλ₯Ό 첫 λ²μ§Έ μΈμλ‘ μ¬μ©νλ©΄ λλ¨Έμ§ μΈμκ° μ¬λ¬ dnd κ°λ μ μ°κ²°ν μ μμ΅λλ€.
const dropTarget = createDropTarget(ItemTypes.CARD, {
canDrop: () => false
hover(props, monitor) {
/**/
},
})
const dragSource = createDragSource(ItemTypes.CARD, {
beginDrag: props => /*...*/,
endDrag: (props, monitor) => /*...*/
})
function Card({ text }) {
const ref = useRef(null)
const [isDragging] = useDnd(
connect => connect(ref, dropTarget, dragSource),
monitor => monitor.isDragging,
)
const opacity = isDragging ? 0 : 1
return (
<div ref={ref} style={{ ...style, opacity }}>
{text}
</div>
)
}
λ°λΌμ useDndλ λ€μκ³Ό κ°μ΅λλ€.
export type DndConcept = DragSource | DropTarget
export type ConnectorFunction = (connector: Connector /*new type*/) => void
export type CollectorFunction<T> = (monitor: DragDropMonitor) => T
export function useDnd(
connector: ConnectorFunction,
...collectors: CollectorFunction[]
): any[] {
const dragDropManager = useDragDropManager()
// magic
return collectedProperties
}
export function useDragDropManager(): DragDropManager {
return useContext(DragDropContextType)
}
connect
λ° monitor
μ κ²½ μ°μ§ μμλ€λ©΄ μ΄λ¨κΉμ?
const Test = props => {
const ref = useRef(null);
const { isDragging } = useDragSource(ref, ItemTypes.CARD, {
canDrag: props.enabled,
beginDrag: () => ({ id: props.id }),
});
return <div ref={ref} style={{ color: isDragging ? 'red' : 'black' }} />
}
μ°κ²°μ μ κ±° ν μ μλ€κ³ μκ°νμ§λ§ λͺ¨λν°μ λν΄μλ μ λͺ¨λ₯΄κ² μ΅λλ€. isDragging
κ·Έλμ μλ§λ useDragSource(ref, <type>, <spec>, <collect>)
. κ·Έκ²μ λ§μ λ
Όμμ΄λ©°, λ κ°μ λ±λ±ν λ¬Όμ²΄κ° λλν λΆμ΄μλ κ²μ΄ μ΄μ ν μ μμ΅λλ€.
κ·Έλλ λͺ¨λν°μμ λͺ¨λ μνμ λ°ν ν μ μμ΅λκΉ?
μ΄μ©λ©΄,μ΄ λ¬Έμ κ° μμΈμ΄ μ μΌν λ°©λ²μ΄λΌκ³ μκ° : https://github.com/react-dnd/react-dnd/blob/84db06edcb94ab3dbb37e8fe89fcad55b1ad07ce/packages/react-dnd/src/interfaces.ts#L117
IIRC, DragSourceMonitor, DropTragetMonitor λ° DragLayerMonitorλ λͺ¨λ DragDropMonitor ν΄λμ€μ μν©λλ€. κ·Έλμ λλ μ°λ¦¬κ° μ΄λ¦ μΆ©λμ λΆλͺ ν κ²μ΄λΌκ³ μκ°νμ§ μμ§λ§ λλ κ·Έκ²μ λ€μ νμΈνκ³ μΆμ΅λλ€.
@yched κ·Έλ₯ μ΄κ²κ³Ό ν μ κ°μ§κ³ λλ€κ° μ°λ¦¬κ° μ°Έμ‘°λ₯Ό μ λ¬ν΄μΌνλ€λ κ²μ μμ μ±μ΅λλ€. 무μΈκ°κ° μμ€μ νκ² λͺ¨λ μΈ κ²½μ°λ₯Όλ³΄μμμ€.
const Test = () => {
const ref = useRef(null)
const source = useDragSource(ref, β¦props)
const target = useDragTarget(ref, β¦props)
return <div ref={ref}>β¦</div>
}
@ jacobp100 μ€μ λ‘ μλ―Έκ° μμ΅λλ€.
μ’μμ, μμ΄λμ΄
const Test = (props) => {
const ref = useRef(null)
const sourceMonitor = useDragSource(ref, 'item' {
beginDrag: () => ({ id: props.id })
})
const targetMonitor = useDropTarget(ref, ['item'] {
drop: () => alert(targetMonitor.getItem().id)
})
const { isDragging } = useMonitorSubscription(targetMonitor, () => ({
isDragging: targetMonitor.isDragging()
})
return <div ref={ref}>β¦</div>
}
λλκ·Έ μμ€ λ° λμμ λν μ¬μμ μ΄λ―Έ μ‘μΈμ€ κΆνμ΄ μμΌλ―λ‘ λ§€κ° λ³μλ₯Ό μμ νμ§ μμ΅λλ€.
useMonitorSubscription
λ κ°μ²΄μ λν΄ μμ λλ±μ μννμ¬ μ
λ°μ΄νΈλ₯Ό μ€μΌ μ μμ΅λλ€.
λλ μ¬κΈ°λ₯Ό μ²μ μ΄ν΄ 보μλ€. ν μ€νΈλ μμ§λ§ μ²΄μ€ μμ λ νν¬μ ν¨κ» μλν©λλ€. λ΄κ° μνλ κ²μ 보μ¬μ€ κ²μ λλ€!
λλ useDragSource(ref, <type>, <spec>, <collect>)
λ₯Ό κ°λ κ²μ΄ μ λ§ νλ₯νκ² μλνκ³ λ§μ API λ³κ²½μ κ°μ Έ μ€μ§ μλ μ μμ΄λΌκ³ μκ°ν©λλ€. μ μΌν μ°¨μ΄μ μ hocμμ hookμΌλ‘ λ³κ²½νλ€λ κ²μ
λλ€.
λν λ κ°μ λ±λ±ν 물체λ₯Ό λλν λλ κ²μ μ΄μ μλ κ·Έλ κ²ν΄μΌνκΈ° λλ¬Έμ λ΄ μκ°μλ ν° λ¬Έμ κ° μλλλ€.
const DragDrop = () => {
const ref = useRef(null);
const dragSource = {
beginDrag() {
return props;
}
};
const collectSource = monitor => {
return {
isDragging: monitor.isDragging()
};
};
const { isDragging } = useDragSource(ref, "Item", dragSource, collectSource);
const dropTarget = {
drop() {
return undefined;
}
};
const collectTarget = monitor => {
return {
isOver: monitor.isOver()
};
};
const { isOver } = useDropTarget(ref, "Item", dropTarget, collectTarget);
return <div ref={ref}>Drag me</div>;
};
μ’μ μ μ λ€λ₯Έ νν¬μ κ°λ μ¬μ©ν μ μλ€λ κ²μ λλ€.
const Drag = () => {
const ref = useRef(null);
const context = useContext(Context)
const dragSource = {
beginDrag() {
context.setDragItem(props)
return props;
},
endDrag() {
context.setDragItem(null)
}
};
const collectSource = monitor => {
return {
isDragging: monitor.isDragging()
};
};
const { isDragging } = useDragSource(ref, "Item", dragSource, collectSource);
return <div ref={ref}>Drag me</div>;
};
μ’μ μ₯μ μ€ νλλ beginDrag μΈμμμ propsμ κ΅¬μ± μμλ₯Ό μ κ±° ν μ μλ€λ κ²μ λλ€. κ·Έλ¦¬κ³ λ€λ₯Έ λͺ¨λ ν¨μλ μ΄λ―Έ λ²μμμ μ‘μΈμ€ ν μ μμΌλ―λ‘ μλ½ν©λλ€.
^ λ°©κΈ λ§μ§λ§ λκΈμ μ
λ°μ΄νΈνμ¬ collectSource
κ° λͺ¨λν°μμ ν¨μλ‘ μ λ¬λμ§ μμμ 보μ¬μ£Όμμ΅λλ€. λ°©κΈ μ€μ½νμμ μ½μμ΅λλ€.
@ jacobp100 μκ² μ΅λλ€ . λμκ² μ§λ¬Έμ λͺ¨λν°μμ λ°μ΄ν°λ₯Ό μμ§νκΈ° μν΄ λ€λ₯Έ νν¬κ° νμνμ§ μλλ©΄ useDragSource λ° useDropTargetμμλ ꡬνν μ μλμ§ μ¬λΆμ λλ€.
λ¬Όκ±΄μ΄ HOC μμ λ, μ΄μ¨λ μ°κ²° 물건μ μ°κ²°ν΄μΌνλ κ³³μ μλ―Έκ°μμμ΅λλ€.
νμ§λ§ μ΄μ λ λ μ΄μ μ΄λ€μ μ°κ²°νκΈ°μν κΈ°μ μ μꡬ μ¬νμ΄ μμΌλ―λ‘ λ³λλ‘ λμμ΅λλ€.
κ·Έλ¬λ©΄ λ μμ λ‘κ² μ¬μ©ν μ μμ΅λλ€. νλ μ΄μμ νμ κ΅¬μ± μμκ° λͺ¨λν° λ³κ²½ μ¬νμ μλ΅ ν μ μμ§λ§ λκΈ° μμλ κ΅¬μ± μμλ μλλλ€. λν λͺ¨λν° κ΅¬λ μ μ¬μ©νμ§ μλ κ²½μ° ν΄λΉ νν¬κ° νΈλ¦¬ νλ€λ¦΄ μ μλ€λ μΆκ° 보λμ€κ° μμ΅λλ€.
μ¦, μ΄κ²μ μ΄κΈ° μ΄μμ λλ€! κ·Έκ²μ΄ ν©μλΌλ©΄ λλ κ·Έκ²μ λ³κ²½νλ κ²μ λ°λνμ§ μμ΅λλ€!
μ’μ μ£Όμ₯μ λλ€. λ΄κ° 보λ μ μΌν λ¬Έμ λ μ¬μ©μκ° λͺ¨λν°λ₯Ό μ§μ νΈμΆ ν λ νΌλμ€λ¬μνκ³ μ μ λλ‘ μλνμ§ μλμ§ κΆκΈν΄ ν μ μλ€λ κ²μ λλ€.
const Test = (props) => {
const ref = useRef(null)
const sourceMonitor = useDragSource(ref, 'item', {
beginDrag: () => ({ id: props.id })
})
const targetMonitor = useDropTarget(ref, ['item'], {
drop: () => alert(targetMonitor.getItem().id)
})
const { isDragging } = useMonitor(targetMonitor, () => ({
isDragging: targetMonitor.isDragging()
})
return <div ref={ref}>{sourceMonitor.isDragging() ? 'Dragging' : 'Drag me'}</div>
}
μλ§λ useMonitor
νν¬ μΈλΆμμ ν¨μλ₯Ό νΈμΆ ν λ λ¬Έμ λ° κ²½κ³ λ‘ ν΄κ²°ν μ μμ΅λλ€.
μ€μ λ‘ μλν©λλ€! 100 % κ΄μ¬μ΄μλ κ² μ€ νλμ
λλ€. useMonitor
μ μ½λ°±μ λ³κ²½ κ°μ§μ λ°ν κ° λͺ¨λμ μ¬μ©λ©λλ€. React coreμ νμ¬ νν¬μ μλ°°λλ κ²μ²λΌ λκ»΄μ§λλ€.
μλ§λ μ΄μ κ°μ κ²μ΄ λ μ μλ ν κ²μ λλ€.
const Test = (props) => {
...
useMonitorUpdates(targetMonitor, () => [targetMonitor.isDragging()]);
return <div ref={ref}>{sourceMonitor.isDragging() ? 'Dragging' : 'Drag me'}</div>
}
μ΄ μμμΌλ‘ λ²κ·Έλ₯Ό λμ νλ κ²μ΄ ν¨μ¬ λ μ½μ΅λλ€.
λ°μ λ° λ΄λΆμ λν΄ 100 % νμ νμ§λ μμ§λ§ λͺ¨λν°κ° μκΈ° λλ¬Έμ λ§μ°μ€κ° μμ§μΌ λλ§λ€ κ΅¬μ± μμλ₯Ό λ λλ§ ν νμκ° μμ΅λκΉ?
λ°λΌμ useMonitorSubscriptionμ μ κ±°νκ³ render ν¨μμ monitor.isDragging()
λ§ μμΌλ©΄ μ΄μ μμ
μ΄ μ€μ§λ©λκΉ?
λ°λΌμ μ¬λ°λ₯΄κ² μλνμ§ μμ΅λκΉ?
const Test = (props) => {
const ref = useRef(null)
const sourceMonitor = useDragSource(ref, 'item', {
beginDrag: () => ({ id: props.id })
})
return <div ref={ref}>{sourceMonitor.isDragging() ? 'Dragging' : 'Drag me'}</div>
}
λͺ¨λν°μλ κ°μ΄ μ
λ°μ΄νΈ λ λλ§λ€ 리μ€λμκ² μ리λ subscribe
λ©μλκ° μμ΅λλ€. λ°λΌμ μ»΄ν¬λνΈκ° μ
λ°μ΄νΈμκΈ°λ₯Ό μ μ μλλ‘ _something_μ μνν΄μΌν©λλ€.
μ΄μ κ²μλ¬Όμμ νμ₯νμ¬ λ³κ²½ κ°μ§ μ΅μ νλ₯Ό μ ν κΈ°λ₯μΌλ‘ λ§λ€λ©΄ λ€μκ³Ό κ°μ΄ κ°λ¨ ν μ μμ΅λλ€.
const Test = (props) => {
...
useMonitorUpdates(sourceMonitor);
return <div ref={ref}>{sourceMonitor.isDragging() ? 'Dragging' : 'Drag me'}</div>
}
λͺ κ°μ§ μμ΄λμ΄.
첫째, νν¬κ° Ref
ꡬνμ λ°ννλλ‘νμ¬ ref
μΈμλ₯Ό μ νμ μΌλ‘ λ§λ€ μ μμ΅λκΉ?
const dragSource = useDragSource('item', spec);
return <div ref={dragSource}/>
// or if you want to use a ref
const ref = useRef();
const dragSource = useDragSource('item', dragSourceSpec)(ref);
const dropTarget = useDropTarget('item', dropTargetSpec)(ref);
λμ§Έ, useMonitorUpdates
μμ λ€λ₯Έ νν¬λ₯Ό νΈμΆνλλ‘ λ§λλ λμ λ€μμ μν ν μ μλμ§ κΆκΈν©λλ€.
const dragSource = useDragSource('item', spec);
const { isDragging } = dragSource.subscribe(() => ({
isDragging: targetMonitor.isDragging()
}));
ν보 APIκ° μμΌλ―λ‘ μ§κΈμμ΄ νλͺ©μ λ«κ² μ΅λλ€. μλ‘μ΄ λ¬Έμ μ λν΄ μμ λ‘κ² μ견μ λ§νμμμ€. κ°μ¬!
νν¬ APIμ λμμΈ κ²°ν¨μ΄μλ κ² κ°μ΅λλ€ : https://github.com/Swizec/useDimensions/issues/3
ν₯λ―Έ λ‘κΈ° λλ¬Έμ λμμ νμ¬ ν΄λμ€ κΈ°λ° APIμμνλ κ²μ²λΌ μ°κ²° ν¨μλ₯Ό μ¬μ©νλ κ²μ λλ€.
const Box = ({ name }) => {
const [{ isDragging }, dragSource] = useDrag({
item: { name, type: ItemTypes.BOX },
end: (dropResult?: { name: string }) => {
if (dropResult) {
alert(`You dropped ${item.name} into ${dropResult.name}!`)
}
},
collect: monitor => ({
isDragging: monitor.isDragging(),
}),
})
const opacity = isDragging ? 0.4 : 1
return (
<div ref={node => dragSource(node)} style={{ ...style, opacity }}>
{name}
</div>
)
}
λ°λΌμ μΌλ°μ μΌλ‘ APIλ λ€μκ³Ό κ°μ΅λλ€.
const [props, connectDragSource, connectDragPreview] = useDrag(spec)
const [props, connectDropTarget] = useDrop(spec)
컀λ₯ν° κΈ°λ₯μ μꡬνλ κ²μμ λ²μ΄λκ³ μΆμμ§λ§ APIκ° μμΌλ©΄ APIκ° μμλλ©΄ ν μ μμ΅λλ€.
κ·Έλλ κ·Έ λ¬Έμ λ₯Ό μ½μμ λ APIλ λΉμ·νμ§λ§ DOM λ Έλλ₯Ό μΈ‘μ νκΈ° μν΄ λ μ΄μμ ν¨κ³Όλ₯Ό μ¬μ©νκ³ μλ€λ λ¬Έμ κ° μλ€κ³ μκ°ν©λλ€. μ¬κΈ°μλ μ€μ λ‘ λ μ΄μμ ν¨κ³Όλ₯Ό μ¬μ©νμ§ μκ³ dnd-coreμ DOM λ Έλλ₯Ό λ±λ‘ν©λλ€.
@gaearon , μ°λ¦¬κ° μ μν νν¬ APIλ useDimensions APIμ λ§€μ° μ μ¬ν©λλ€. νΉμ ννκ° λ° ν¨ν΄ (μ : let [props, ref] = useCustomHook(config)
)μ
λκΉ, μλλ©΄ λΌμ΄λΈλ¬λ¦¬κ° ν΄κ²°νλ €κ³ νλ λ¬Έμ μ νΉμ΄νκ°μ?
@darthtrevino useDragSource νν¬λ₯Ό μ¬μ©νκ³ μ°Έμ‘°λ₯Ό νμ κ΅¬μ± μμμ μ λ¬νλ©΄ νμ κ΅¬μ± μμκ° λ€μ λ λλ§λλ κ²½μ° dnd-coreμ λ±λ‘ λ dom λ Έλλ₯Ό μ λ°μ΄νΈνμ§ μμ΅λλ€.
function Parent() {
const ref = useRef();
const dragSource = useDragSource(ref, ...);
return <Child connect={ref} />;
}
function Child({ connect }) {
const [open, setOpen] = useState(false);
function toggle() {
setOpen(!open);
}
return (
<Fragment>
<button onClick={toggle}>Toggle</button>
{open ? <div ref={connect} /> : null}
</Fragment>
);
}
Yech. μ΄λ² μ£Ό λ§μ νλ° μ¬λΆλ₯Ό μ¦λͺ νκΈ° μν΄ ν μ€νΈ μΌμ΄μ€λ₯Ό λ§λ€ μ μλμ§ μ΄ν΄ λ³΄κ² μ΅λλ€.
νλ°νλ©΄ 컀λ₯ν° κΈ°λ₯μ μ¬μ©νλ κ²μ΄ λ체μ λλ€.
λͺ¨λ κ²μ μ¬λ°λ₯΄κ² μννλ€λ©΄ μ¬κΈ°μμ μ¬ν ν μμμμ΅λλ€ : https://codesandbox.io/s/xj7k9x4vp4
Kaboom, μ’μ μΌ, κ°μ¬ν©λλ€ @ k15a . 곧 μ°κ²° ν¨μλ₯Ό μ¬μ©νλλ‘ νν¬ APIλ₯Ό μ λ°μ΄νΈνκ³ μμ λ₯Ό ν μ€νΈ μΌμ΄μ€λ‘ ν¬ν¨νκ² μ΅λλ€.
κ·Έλμ μ΄μ ―λ°€μ 컀λ₯ν° ν¨μλ₯Ό μ¬μ©νκΈ° μν΄ νν¬ APIλ₯Ό μ¬ μμ νλ λ° λ§μ μκ°μ 보λμ΅λλ€. API λμμΈμ κ΄ν ν, λλ μ λ§ μ«μ΄ν©λλ€.
λ΄ λ€μ μκ°μ ref-object λμ callback-refλ₯Ό λ°ν ν μ μλ€λ κ²μ λλ€. μ΄λ₯Ό ν΅ν΄ μ°Έμ‘°λ‘ μ§μ μ¬μ©νκ±°λ μ°Έμ‘°λ₯Ό μ λ¬ν μμλ μ μ°μ±μ μ 곡ν©λλ€.
μ§μ μ¬μ© :
let [props, dragSource] = useDrag({spec}) // dragSource result is a function
return <div ref={dragSource} {...props}>hey</div>
체μΈ
let [dragProps, dragSource] = useDrag({spec})
let [dropProps, dropTarget] = useDrag({spec})
return <div ref={node => dragSource(dropTarget(node))}>hey</div>
μ°Έμ‘° κ°μ²΄ μ¬μ©
let ref = useRef(null)
let [dragProps, dragSource] = useDrag({spec})
let [dropProps, dropTarget] = useDrag({spec})
dragSource(dropTarget(ref))
return <div ref={ref}>hey</div>
λμκ²λ κ΅¬μ± μμ λλ νμ μμκ° μ
λ°μ΄νΈλλ©΄ useLayoutEffect
κ° μ€νλμ΄μΌνλ κ²μ²λΌ λκ»΄μ§λλ€. λ§μ½ κ·Έλ λ€λ©΄ μ°λ¦¬λ κ·Έκ²μ μ¬μ©ν μ μμ΅λλ€.
λ°μ μ μ₯μμ ν°μΌμ λ§λ€μμ΅λλ€ . μ견μ μ£ΌμκΈ° λ°λλλ€.
let [dragProps, dragSource] = useDrag({spec})
let [dropProps, dropTarget] = useDrag({spec})
return <div ref={node => dragSource(dropTarget(node))}>hey</div>
맀 λ λλ§λ§λ€ refλ₯Ό νΈμΆνλ κ²μ²λΌ μ΄κ²μ΄ μΌλ§λ μ μλνλμ§ λͺ¨λ₯΄κ² μ΅λλ€. λ°λΌμ λ λλ§ ν λλ§λ€ μ°κ²°νκ³ μ°κ²° ν΄μ ν΄μΌν©λλ€.
λν κ·Έλ κ²νλ κ²μ΄ λ«μ§ μμκΉμ
node => {
dragSource(node)
dropTarget(node)
}
λκ°μ μΌμ΄μΌ
λ°λΌμ μ΄μ μ견μ μ½κ² μ€λͺ νκΈ° μν΄ # 1280μ APIκ° μ²μ μκ°νλ κ²λ³΄λ€ λ λμμ§ κ²μ λλ€. μ¬κΈ° λλ κ±°κΈ°μ μμ λ‘κ² μ견μ λ§νμμμ€.