0
# Interactions
1
2
Low-level interaction hooks for handling user input across different devices and interaction models. These hooks provide normalized event handling for mouse, touch, keyboard, and screen reader interactions.
3
4
## Capabilities
5
6
### Press
7
8
Provides press interaction handling across mouse, touch, and keyboard.
9
10
```typescript { .api }
11
/**
12
* Provides press interaction handling
13
* @param props - Press configuration
14
* @returns Press result with event handlers
15
*/
16
function usePress(props: PressHookProps): PressResult;
17
18
interface PressHookProps extends PressProps {
19
/** Ref to the target element */
20
ref?: RefObject<Element>;
21
}
22
23
interface PressProps {
24
/** Handler called when press starts */
25
onPressStart?: (e: PressEvent) => void;
26
/** Handler called when press ends */
27
onPressEnd?: (e: PressEvent) => void;
28
/** Handler called when press changes */
29
onPressChange?: (isPressed: boolean) => void;
30
/** Handler called when press is released over target */
31
onPressUp?: (e: PressEvent) => void;
32
/** Handler called when press is completed */
33
onPress?: (e: PressEvent) => void;
34
/** Whether press events are disabled */
35
isDisabled?: boolean;
36
/** Whether to prevent focus on press (mobile) */
37
preventFocusOnPress?: boolean;
38
/** Whether press should cancel when pointer exits */
39
shouldCancelOnPointerExit?: boolean;
40
/** Whether text selection should be allowed during press */
41
allowTextSelectionOnPress?: boolean;
42
}
43
44
interface PressResult {
45
/** Whether the element is currently pressed */
46
isPressed: boolean;
47
/** Props to spread on the target element */
48
pressProps: DOMAttributes<Element>;
49
}
50
51
interface PressEvent {
52
/** Type of press event */
53
type: 'pressstart' | 'pressend' | 'pressup' | 'press';
54
/** Input type that triggered the event */
55
pointerType: 'mouse' | 'pen' | 'touch' | 'keyboard' | 'virtual';
56
/** Target element */
57
target: Element;
58
/** Whether shift key was pressed */
59
shiftKey: boolean;
60
/** Whether ctrl key was pressed */
61
ctrlKey: boolean;
62
/** Whether meta key was pressed */
63
metaKey: boolean;
64
/** Whether alt key was pressed */
65
altKey: boolean;
66
/** X coordinate relative to target */
67
x: number;
68
/** Y coordinate relative to target */
69
y: number;
70
/** Continue propagation */
71
continuePropagation(): void;
72
}
73
```
74
75
### Long Press
76
77
Provides long press interaction handling with customizable delay.
78
79
```typescript { .api }
80
/**
81
* Provides long press interaction handling
82
* @param props - Long press configuration
83
* @returns Long press result with event handlers
84
*/
85
function useLongPress(props: LongPressProps): LongPressResult;
86
87
interface LongPressProps {
88
/** Whether long press is disabled */
89
isDisabled?: boolean;
90
/** Handler called when long press is triggered */
91
onLongPressStart?: (e: LongPressEvent) => void;
92
/** Handler called when long press ends */
93
onLongPressEnd?: (e: LongPressEvent) => void;
94
/** Handler called when long press completes */
95
onLongPress?: (e: LongPressEvent) => void;
96
/** Long press threshold in milliseconds */
97
threshold?: number;
98
/** Accessibility description for long press action */
99
accessibilityDescription?: string;
100
}
101
102
interface LongPressResult {
103
/** Props to spread on the target element */
104
longPressProps: DOMAttributes<Element>;
105
}
106
107
interface LongPressEvent {
108
/** Type of long press event */
109
type: 'longpressstart' | 'longpressend' | 'longpress';
110
/** Input type that triggered the event */
111
pointerType: 'mouse' | 'pen' | 'touch' | 'keyboard' | 'virtual';
112
/** Target element */
113
target: Element;
114
/** Whether shift key was pressed */
115
shiftKey: boolean;
116
/** Whether ctrl key was pressed */
117
ctrlKey: boolean;
118
/** Whether meta key was pressed */
119
metaKey: boolean;
120
/** Whether alt key was pressed */
121
altKey: boolean;
122
}
123
```
124
125
### Hover
126
127
Provides hover interaction handling with proper touch device support.
128
129
```typescript { .api }
130
/**
131
* Provides hover interaction handling
132
* @param props - Hover configuration
133
* @returns Hover result with event handlers
134
*/
135
function useHover(props: HoverProps): HoverResult;
136
137
interface HoverProps {
138
/** Handler called when hover starts */
139
onHoverStart?: (e: HoverEvent) => void;
140
/** Handler called when hover ends */
141
onHoverEnd?: (e: HoverEvent) => void;
142
/** Handler called when hover changes */
143
onHoverChange?: (isHovering: boolean) => void;
144
/** Whether hover is disabled */
145
isDisabled?: boolean;
146
}
147
148
interface HoverResult {
149
/** Props to spread on the target element */
150
hoverProps: DOMAttributes<Element>;
151
/** Whether the element is currently hovered */
152
isHovered: boolean;
153
}
154
155
interface HoverEvent {
156
/** Type of hover event */
157
type: 'hoverstart' | 'hoverend';
158
/** Input type that triggered the event */
159
pointerType: 'mouse' | 'pen';
160
/** Target element */
161
target: Element;
162
}
163
```
164
165
### Focus
166
167
Provides focus event handling with proper event normalization.
168
169
```typescript { .api }
170
/**
171
* Provides focus event handling
172
* @param props - Focus configuration
173
* @returns Focus result with event handlers
174
*/
175
function useFocus(props: FocusProps): FocusResult;
176
177
interface FocusProps {
178
/** Whether focus events are disabled */
179
isDisabled?: boolean;
180
/** Handler called when element receives focus */
181
onFocus?: (e: FocusEvent) => void;
182
/** Handler called when element loses focus */
183
onBlur?: (e: FocusEvent) => void;
184
/** Handler called when focus changes */
185
onFocusChange?: (isFocused: boolean) => void;
186
}
187
188
interface FocusResult {
189
/** Props to spread on the target element */
190
focusProps: DOMAttributes<Element>;
191
}
192
```
193
194
### Focus Visible
195
196
Provides focus-visible state management for keyboard navigation styling.
197
198
```typescript { .api }
199
/**
200
* Provides focus-visible state management
201
* @param props - Focus visible configuration
202
* @returns Focus visible result with state
203
*/
204
function useFocusVisible(props?: FocusVisibleProps): FocusVisibleResult;
205
206
interface FocusVisibleProps {
207
/** Whether focus visible is disabled */
208
isDisabled?: boolean;
209
/** Auto-focus behavior */
210
autoFocus?: boolean;
211
}
212
213
interface FocusVisibleResult {
214
/** Whether focus is visible */
215
isFocusVisible: boolean;
216
}
217
```
218
219
### Focus Within
220
221
Provides focus-within state tracking for container elements.
222
223
```typescript { .api }
224
/**
225
* Provides focus-within state tracking
226
* @param props - Focus within configuration
227
* @returns Focus within result with event handlers
228
*/
229
function useFocusWithin(props: FocusWithinProps): FocusWithinResult;
230
231
interface FocusWithinProps {
232
/** Whether focus within is disabled */
233
isDisabled?: boolean;
234
/** Handler called when focus enters the container */
235
onFocusWithin?: (e: FocusEvent) => void;
236
/** Handler called when focus leaves the container */
237
onBlurWithin?: (e: FocusEvent) => void;
238
/** Handler called when focus within changes */
239
onFocusWithinChange?: (isFocusWithin: boolean) => void;
240
}
241
242
interface FocusWithinResult {
243
/** Props to spread on the container element */
244
focusWithinProps: DOMAttributes<Element>;
245
/** Whether focus is within the container */
246
isFocusWithin: boolean;
247
}
248
```
249
250
### Keyboard
251
252
Provides keyboard event handling with normalized key handling.
253
254
```typescript { .api }
255
/**
256
* Provides keyboard event handling
257
* @param props - Keyboard configuration
258
* @returns Keyboard result with event handlers
259
*/
260
function useKeyboard(props: KeyboardProps): KeyboardResult;
261
262
interface KeyboardProps {
263
/** Whether keyboard events are disabled */
264
isDisabled?: boolean;
265
/** Handler called on key down */
266
onKeyDown?: (e: KeyboardEvent) => void;
267
/** Handler called on key up */
268
onKeyUp?: (e: KeyboardEvent) => void;
269
}
270
271
interface KeyboardResult {
272
/** Props to spread on the target element */
273
keyboardProps: DOMAttributes<Element>;
274
}
275
```
276
277
### Move
278
279
Provides move/drag interaction handling for pointer events.
280
281
```typescript { .api }
282
/**
283
* Provides move/drag interaction handling
284
* @param props - Move configuration
285
* @returns Move result with event handlers
286
*/
287
function useMove(props: MoveEvents): MoveResult;
288
289
interface MoveEvents {
290
/** Handler called when move starts */
291
onMoveStart?: (e: MoveStartEvent) => void;
292
/** Handler called during move */
293
onMove?: (e: MoveMoveEvent) => void;
294
/** Handler called when move ends */
295
onMoveEnd?: (e: MoveEndEvent) => void;
296
}
297
298
interface MoveResult {
299
/** Props to spread on the target element */
300
moveProps: DOMAttributes<Element>;
301
}
302
303
interface MoveStartEvent {
304
/** Type of move event */
305
type: 'movestart';
306
/** Input type */
307
pointerType: 'mouse' | 'pen' | 'touch' | 'keyboard' | 'virtual';
308
/** Whether shift key was pressed */
309
shiftKey: boolean;
310
/** Whether ctrl key was pressed */
311
ctrlKey: boolean;
312
/** Whether meta key was pressed */
313
metaKey: boolean;
314
/** Whether alt key was pressed */
315
altKey: boolean;
316
}
317
318
interface MoveMoveEvent {
319
/** Type of move event */
320
type: 'move';
321
/** Input type */
322
pointerType: 'mouse' | 'pen' | 'touch' | 'keyboard' | 'virtual';
323
/** Delta X movement */
324
deltaX: number;
325
/** Delta Y movement */
326
deltaY: number;
327
/** Whether shift key was pressed */
328
shiftKey: boolean;
329
/** Whether ctrl key was pressed */
330
ctrlKey: boolean;
331
/** Whether meta key was pressed */
332
metaKey: boolean;
333
/** Whether alt key was pressed */
334
altKey: boolean;
335
}
336
337
interface MoveEndEvent {
338
/** Type of move event */
339
type: 'moveend';
340
/** Input type */
341
pointerType: 'mouse' | 'pen' | 'touch' | 'keyboard' | 'virtual';
342
/** Whether shift key was pressed */
343
shiftKey: boolean;
344
/** Whether ctrl key was pressed */
345
ctrlKey: boolean;
346
/** Whether meta key was pressed */
347
metaKey: boolean;
348
/** Whether alt key was pressed */
349
altKey: boolean;
350
}
351
```
352
353
### Interact Outside
354
355
Provides outside interaction detection for dismissing overlays.
356
357
```typescript { .api }
358
/**
359
* Provides outside interaction detection
360
* @param props - Interact outside configuration
361
* @returns Event handlers for outside detection
362
*/
363
function useInteractOutside(props: InteractOutsideProps): void;
364
365
interface InteractOutsideProps {
366
/** Ref to the element to monitor */
367
ref: RefObject<Element>;
368
/** Handler called when interaction occurs outside */
369
onInteractOutside?: (e: InteractOutsideEvent) => void;
370
/** Whether interact outside is disabled */
371
isDisabled?: boolean;
372
/** Handler to determine if interaction should be ignored */
373
onInteractOutsideStart?: (e: InteractOutsideEvent) => void;
374
}
375
376
interface InteractOutsideEvent {
377
/** Type of interaction */
378
type: 'pointerdown' | 'pointerup' | 'focusin' | 'focusout';
379
/** Target element */
380
target: Element;
381
}
382
```
383
384
### Focusable
385
386
Provides focusable element behavior with keyboard and screen reader support.
387
388
```typescript { .api }
389
/**
390
* Provides focusable element behavior
391
* @param props - Focusable configuration
392
* @param ref - Ref to the focusable element
393
* @returns Focusable result with props and state
394
*/
395
function useFocusable(props: FocusableOptions, ref: RefObject<Element>): FocusableAria;
396
397
interface FocusableOptions {
398
/** Whether the element should exclude from tab order */
399
excludeFromTabOrder?: boolean;
400
/** Whether the element is disabled */
401
isDisabled?: boolean;
402
/** Auto-focus behavior */
403
autoFocus?: boolean;
404
}
405
406
interface FocusableAria {
407
/** Props to spread on the focusable element */
408
focusableProps: DOMAttributes<Element>;
409
}
410
```
411
412
### Drag and Drop
413
414
Provides comprehensive drag and drop interaction handling.
415
416
```typescript { .api }
417
/**
418
* Provides drag behavior for elements
419
* @param options - Drag configuration
420
* @returns Drag result with props and state
421
*/
422
function useDrag(options: DragOptions): DragResult;
423
424
/**
425
* Provides drop behavior for elements
426
* @param options - Drop configuration
427
* @returns Drop result with props and state
428
*/
429
function useDrop(options: DropOptions): DropResult;
430
431
/**
432
* Provides draggable collection behavior
433
* @param options - Draggable collection configuration
434
* @returns Collection drag result
435
*/
436
function useDraggableCollection(options: DraggableCollectionOptions): DroppableCollectionResult;
437
438
/**
439
* Provides droppable collection behavior
440
* @param options - Droppable collection configuration
441
* @returns Collection drop result
442
*/
443
function useDroppableCollection(options: DroppableCollectionOptions): DroppableCollectionResult;
444
445
/**
446
* Provides individual draggable item behavior
447
* @param props - Draggable item configuration
448
* @returns Draggable item result
449
*/
450
function useDraggableItem(props: DraggableItemProps, ref: RefObject<Element>): DraggableItemResult;
451
452
/**
453
* Provides individual droppable item behavior
454
* @param options - Droppable item configuration
455
* @param ref - Ref to the droppable element
456
* @returns Droppable item result
457
*/
458
function useDroppableItem(options: DroppableItemOptions, ref: RefObject<Element>): DroppableItemResult;
459
460
/**
461
* Provides drop indicator behavior
462
* @param props - Drop indicator configuration
463
* @param ref - Ref to the indicator element
464
* @returns Drop indicator result
465
*/
466
function useDropIndicator(props: DropIndicatorProps, ref: RefObject<Element>): DropIndicatorAria;
467
468
/**
469
* Component for rendering drag previews
470
* @param props - Drag preview configuration
471
* @returns Drag preview component
472
*/
473
function DragPreview(props: DragPreviewProps): JSX.Element;
474
475
/**
476
* Drop target delegate for list components
477
*/
478
class ListDropTargetDelegate implements DropTargetDelegate {
479
/** Get drop target for a point */
480
getDropTarget(target: DropTarget, types: Set<string>): DropTarget | null;
481
/** Check if drop is allowed */
482
isValidDropTarget(target: DropTarget, types: Set<string>): boolean;
483
}
484
485
/**
486
* Constant for directory drag type
487
*/
488
const DIRECTORY_DRAG_TYPE: string;
489
490
/**
491
* Type guard to check if drop item is a directory
492
* @param item - Drop item to check
493
* @returns Whether item is a directory
494
*/
495
function isDirectoryDropItem(item: DropItem): item is DirectoryDropItem;
496
497
/**
498
* Type guard to check if drop item is a file
499
* @param item - Drop item to check
500
* @returns Whether item is a file
501
*/
502
function isFileDropItem(item: DropItem): item is FileDropItem;
503
504
/**
505
* Type guard to check if drop item is text
506
* @param item - Drop item to check
507
* @returns Whether item is text
508
*/
509
function isTextDropItem(item: DropItem): item is TextDropItem;
510
511
interface DragOptions {
512
/** Handler called when drag starts */
513
onDragStart?: (e: DragStartEvent) => void;
514
/** Handler called during drag */
515
onDragMove?: (e: DragMoveEvent) => void;
516
/** Handler called when drag ends */
517
onDragEnd?: (e: DragEndEvent) => void;
518
/** Get drag data for the operation */
519
getItems: () => DragItem[];
520
/** Preview component */
521
preview?: DragPreviewRenderer;
522
/** Whether drag is disabled */
523
isDisabled?: boolean;
524
}
525
526
interface DragResult {
527
/** Props for the draggable element */
528
dragProps: DOMAttributes<Element>;
529
/** Whether element is currently being dragged */
530
isDragging: boolean;
531
}
532
533
interface DropOptions {
534
/** Ref to the drop target element */
535
ref: RefObject<Element>;
536
/** Handler called when drop occurs */
537
onDrop?: (e: DropEvent) => void;
538
/** Handler called when drag enters */
539
onDropEnter?: (e: DropEnterEvent) => void;
540
/** Handler called when drag exits */
541
onDropExit?: (e: DropExitEvent) => void;
542
/** Handler called during drag over */
543
onDropMove?: (e: DropMoveEvent) => void;
544
/** Get drop operation for items */
545
getDropOperation?: (target: DropTarget, types: Set<string>, allowedOperations: DropOperation[]) => DropOperation;
546
/** Accept drop delegate */
547
acceptedDragTypes?: string[];
548
/** Whether drop is disabled */
549
isDisabled?: boolean;
550
}
551
552
interface DropResult {
553
/** Props for the droppable element */
554
dropProps: DOMAttributes<Element>;
555
/** Whether drag is currently over */
556
isDropTarget: boolean;
557
}
558
```
559
560
### Clipboard
561
562
Provides clipboard operations with proper permissions and fallbacks.
563
564
```typescript { .api }
565
/**
566
* Provides clipboard operations
567
* @param props - Clipboard configuration
568
* @returns Clipboard result with operations
569
*/
570
function useClipboard(props?: ClipboardProps): ClipboardResult;
571
572
interface ClipboardProps {
573
/** Handler called when copy succeeds */
574
onCopy?: () => void;
575
/** Handler called when copy fails */
576
onError?: () => void;
577
}
578
579
interface ClipboardResult {
580
/** Copy text to clipboard */
581
copy(text: string): Promise<void>;
582
/** Copy data items to clipboard */
583
copyItems(items: ClipboardItem[]): Promise<void>;
584
/** Paste from clipboard */
585
paste(): Promise<string>;
586
/** Whether clipboard operations are supported */
587
isSupported: boolean;
588
}
589
```
590
591
### Interaction Components
592
593
```typescript { .api }
594
/**
595
* Component for pressable elements with interaction states
596
*/
597
function Pressable(props: PressableProps): JSX.Element;
598
599
/**
600
* Component for focusable elements with proper semantics
601
*/
602
function Focusable(props: FocusableProps): JSX.Element;
603
604
interface PressableProps extends PressProps {
605
/** Children render prop */
606
children: (states: { isPressed: boolean }) => ReactNode;
607
/** Element type to render */
608
elementType?: React.ElementType;
609
}
610
611
interface FocusableProps extends FocusableOptions {
612
/** Children content */
613
children: ReactNode;
614
/** Element type to render */
615
elementType?: React.ElementType;
616
}
617
```
618
619
## Types
620
621
```typescript { .api }
622
type PointerType = 'mouse' | 'pen' | 'touch' | 'keyboard' | 'virtual';
623
624
interface KeyboardEvent {
625
/** Type of keyboard event */
626
type: 'keydown' | 'keyup';
627
/** Key that was pressed */
628
key: string;
629
/** Key code */
630
code: string;
631
/** Whether shift key was pressed */
632
shiftKey: boolean;
633
/** Whether ctrl key was pressed */
634
ctrlKey: boolean;
635
/** Whether meta key was pressed */
636
metaKey: boolean;
637
/** Whether alt key was pressed */
638
altKey: boolean;
639
/** Repeat count */
640
repeat: boolean;
641
/** Whether event is composing */
642
isComposing: boolean;
643
/** Target element */
644
target: Element;
645
/** Current target element */
646
currentTarget: Element;
647
/** Prevent default behavior */
648
preventDefault(): void;
649
/** Stop propagation */
650
stopPropagation(): void;
651
/** Continue propagation */
652
continuePropagation(): void;
653
}
654
655
interface FocusEvent {
656
/** Type of focus event */
657
type: 'focus' | 'blur' | 'focusin' | 'focusout';
658
/** Target element */
659
target: Element;
660
/** Related target element */
661
relatedTarget: Element | null;
662
}
663
664
type DropOperation = 'copy' | 'link' | 'move' | 'cancel';
665
666
interface DragItem {
667
/** MIME types for the item */
668
[type: string]: string | (() => string);
669
}
670
671
interface DropTarget {
672
/** Type of drop target */
673
type: 'item' | 'folder' | 'root';
674
/** Key of the target */
675
key?: Key;
676
/** Drop position relative to target */
677
dropPosition?: 'before' | 'after' | 'on';
678
}
679
680
interface DragStartEvent {
681
/** Type of event */
682
type: 'dragstart';
683
/** X coordinate */
684
x: number;
685
/** Y coordinate */
686
y: number;
687
}
688
689
interface DragMoveEvent {
690
/** Type of event */
691
type: 'dragmove';
692
/** X coordinate */
693
x: number;
694
/** Y coordinate */
695
y: number;
696
/** Delta X */
697
deltaX: number;
698
/** Delta Y */
699
deltaY: number;
700
}
701
702
interface DragEndEvent {
703
/** Type of event */
704
type: 'dragend';
705
/** X coordinate */
706
x: number;
707
/** Y coordinate */
708
y: number;
709
/** Drop operation performed */
710
dropOperation: DropOperation;
711
/** Whether operation was successful */
712
isInternal: boolean;
713
}
714
715
interface DropEvent {
716
/** Type of event */
717
type: 'drop';
718
/** X coordinate */
719
x: number;
720
/** Y coordinate */
721
y: number;
722
/** Drop operation */
723
dropOperation: DropOperation;
724
/** Dropped items */
725
items: DropItem[];
726
/** Drop target */
727
target: DropTarget;
728
}
729
```