panelui-native 0.97.0 → 0.99.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -0
- package/lib/module/components/image-viewer/image-viewer-geometry.js +203 -0
- package/lib/module/components/image-viewer/image-viewer-geometry.js.map +1 -0
- package/lib/module/components/image-viewer/index.js +1100 -0
- package/lib/module/components/image-viewer/index.js.map +1 -0
- package/lib/module/components/stack-card/index.js +1204 -0
- package/lib/module/components/stack-card/index.js.map +1 -0
- package/lib/module/components/stack-card/stack-card-geometry.js +261 -0
- package/lib/module/components/stack-card/stack-card-geometry.js.map +1 -0
- package/lib/module/index.js +2 -0
- package/lib/module/index.js.map +1 -1
- package/lib/module/primitives/scrim.js +65 -1
- package/lib/module/primitives/scrim.js.map +1 -1
- package/lib/typescript/src/components/image-viewer/image-viewer-geometry.d.ts +83 -0
- package/lib/typescript/src/components/image-viewer/image-viewer-geometry.d.ts.map +1 -0
- package/lib/typescript/src/components/image-viewer/index.d.ts +148 -0
- package/lib/typescript/src/components/image-viewer/index.d.ts.map +1 -0
- package/lib/typescript/src/components/stack-card/index.d.ts +472 -0
- package/lib/typescript/src/components/stack-card/index.d.ts.map +1 -0
- package/lib/typescript/src/components/stack-card/stack-card-geometry.d.ts +126 -0
- package/lib/typescript/src/components/stack-card/stack-card-geometry.d.ts.map +1 -0
- package/lib/typescript/src/index.d.ts +2 -0
- package/lib/typescript/src/index.d.ts.map +1 -1
- package/lib/typescript/src/primitives/scrim.d.ts +11 -1
- package/lib/typescript/src/primitives/scrim.d.ts.map +1 -1
- package/package.json +8 -1
- package/src/components/image-viewer/image-viewer-geometry.ts +205 -0
- package/src/components/image-viewer/index.tsx +1329 -0
- package/src/components/stack-card/index.tsx +1423 -0
- package/src/components/stack-card/stack-card-geometry.ts +279 -0
- package/src/index.ts +19 -0
- package/src/primitives/scrim.tsx +96 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"image-viewer-geometry.d.ts","sourceRoot":"","sources":["../../../../../src/components/image-viewer/image-viewer-geometry.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,MAAM,WAAW,IAAI;IACnB,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,IAAK,SAAQ,IAAI;IAChC,CAAC,EAAE,MAAM,CAAC;IACV,CAAC,EAAE,MAAM,CAAC;CACX;AAED,kEAAkE;AAClE,eAAO,MAAM,WAAW,OAAO,CAAC;AAEhC,wBAAgB,KAAK,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,CAGrE;AAED,wBAAgB,IAAI,CAAC,IAAI,EAAE,MAAM,EAAE,EAAE,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,GAAG,MAAM,CAGhE;AAED,wBAAgB,QAAQ,CAAC,IAAI,EAAE,IAAI,EAAE,EAAE,EAAE,IAAI,EAAE,CAAC,EAAE,MAAM,GAAG,IAAI,CAQ9D;AAED;;;GAGG;AACH,wBAAgB,UAAU,CAAC,KAAK,EAAE,IAAI,EAAE,GAAG,EAAE,IAAI,GAAG,IAAI,CASvD;AAED,oEAAoE;AACpE,wBAAgB,SAAS,CAAC,KAAK,EAAE,IAAI,EAAE,GAAG,EAAE,IAAI,GAAG,IAAI,CAItD;AAED;;;;;;GAMG;AACH,wBAAgB,SAAS,CAAC,KAAK,EAAE,IAAI,EAAE,KAAK,EAAE,IAAI,GAAG,IAAI,CAOxD;AAED;;;GAGG;AACH,wBAAgB,UAAU,CAAC,SAAS,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,WAAW,CAAC,EAAE,MAAM,GAAG,MAAM,CAK7F;AAED,yFAAyF;AACzF,wBAAgB,eAAe,CAC7B,KAAK,EAAE,MAAM,EACb,GAAG,EAAE,MAAM,EACX,GAAG,EAAE,MAAM,EACX,SAAS,EAAE,MAAM,EACjB,WAAW,CAAC,EAAE,MAAM,GACnB,MAAM,CAOR;AAED;;;;GAIG;AACH,wBAAgB,QAAQ,CAAC,MAAM,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,MAAM,CAGhF;AAED;;;;;;GAMG;AACH,wBAAgB,gBAAgB,CAC9B,KAAK,EAAE,MAAM,EACb,MAAM,EAAE,MAAM,EACd,SAAS,EAAE,MAAM,EACjB,OAAO,EAAE,MAAM,GACd,MAAM,CAIR;AAED;;;;GAIG;AACH,wBAAgB,QAAQ,CACtB,MAAM,EAAE,MAAM,EACd,QAAQ,EAAE,MAAM,EAChB,OAAO,EAAE,MAAM,EACf,KAAK,EAAE,MAAM,EACb,SAAS,EAAE,MAAM,GAChB,MAAM,CAMR;AAED,sFAAsF;AACtF,eAAO,MAAM,gBAAgB,MAAM,CAAC;AAEpC;;;;;;GAMG;AACH,wBAAgB,aAAa,CAAC,WAAW,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,OAAO,CAK5E;AAED;;;;GAIG;AACH,wBAAgB,QAAQ,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,MAAM,CAInE;AAED,iFAAiF;AACjF,wBAAgB,SAAS,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,MAAM,CAIpE;AAED,uFAAuF;AACvF,wBAAgB,QAAQ,CACtB,EAAE,EAAE,MAAM,EACV,EAAE,EAAE,MAAM,EACV,IAAI,EAAE,IAAI,EACV,KAAK,EAAE,MAAM,EACb,EAAE,EAAE,MAAM,EACV,EAAE,EAAE,MAAM,GACT,OAAO,CAQT"}
|
|
@@ -0,0 +1,148 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* ImageViewer — a picture that opens out of the page to fill the screen.
|
|
3
|
+
*
|
|
4
|
+
* Pressing a trigger lifts its image from where it sits, grows it to the whole
|
|
5
|
+
* picture in the middle of the screen, and blurs the page behind it. From there
|
|
6
|
+
* it can be pinched and double-tapped to zoom, swiped sideways to the next
|
|
7
|
+
* image under the same root, and dragged away to put it back.
|
|
8
|
+
*
|
|
9
|
+
* ```tsx
|
|
10
|
+
* <ImageViewer>
|
|
11
|
+
* {photos.map((photo) => (
|
|
12
|
+
* <ImageViewer.Trigger
|
|
13
|
+
* key={photo.id}
|
|
14
|
+
* source={photo.source}
|
|
15
|
+
* alt={photo.alt}
|
|
16
|
+
* radius={12}
|
|
17
|
+
* className="h-40 flex-1 rounded-xl"
|
|
18
|
+
* />
|
|
19
|
+
* ))}
|
|
20
|
+
* </ImageViewer>
|
|
21
|
+
* ```
|
|
22
|
+
*
|
|
23
|
+
* ## The image travels; nothing appears
|
|
24
|
+
*
|
|
25
|
+
* The viewer never fades a second copy of the picture in over the first. The
|
|
26
|
+
* thumbnail is hidden and the same image is drawn in a frame that starts at the
|
|
27
|
+
* thumbnail's exact rectangle and corner radius and ends at the fitted one. The
|
|
28
|
+
* picture inside that frame is always drawn at the size that *covers* it, so the
|
|
29
|
+
* crop a thumbnail shows opens out into the whole image as the frame grows — and
|
|
30
|
+
* closes back into the crop on the way home. That continuity is the point: the
|
|
31
|
+
* picture on screen is the one that was pressed, not a picture of it.
|
|
32
|
+
*
|
|
33
|
+
* The frame animates its bounds rather than a transform, because a transform
|
|
34
|
+
* cannot change a crop. It is one view with one child, so the layout pass it
|
|
35
|
+
* costs per frame is small.
|
|
36
|
+
*
|
|
37
|
+
* ## Every trigger under one root is a page
|
|
38
|
+
*
|
|
39
|
+
* Triggers register themselves with the root as they mount, in render order or
|
|
40
|
+
* by an explicit `index`. Opening one opens the gallery at its page, and the
|
|
41
|
+
* thumbnail hidden underneath follows the page — close on the third image and it
|
|
42
|
+
* flies back into the third thumbnail.
|
|
43
|
+
*
|
|
44
|
+
* ## One gesture surface, decided at the start
|
|
45
|
+
*
|
|
46
|
+
* Pinching, panning a zoomed image, turning the page and dragging to dismiss all
|
|
47
|
+
* begin as a one- or two-finger drag, and which one it is gets decided the
|
|
48
|
+
* moment it starts: two fingers zoom, one finger on a zoomed image pans it, one
|
|
49
|
+
* finger moving sideways across a gallery turns the page, and anything else
|
|
50
|
+
* drags the image away. Deciding once keeps a drag from changing its mind
|
|
51
|
+
* halfway, which is what makes a viewer feel loose.
|
|
52
|
+
*/
|
|
53
|
+
import { type ReactNode } from 'react';
|
|
54
|
+
import { type ImageSourcePropType, type PressableProps } from 'react-native';
|
|
55
|
+
export interface ImageViewerProps {
|
|
56
|
+
children?: ReactNode;
|
|
57
|
+
/** Controlled open state. */
|
|
58
|
+
open?: boolean;
|
|
59
|
+
/** Initial open state when uncontrolled. */
|
|
60
|
+
defaultOpen?: boolean;
|
|
61
|
+
onOpenChange?: (open: boolean) => void;
|
|
62
|
+
/** Controlled page — which trigger's image is showing, in page order. */
|
|
63
|
+
index?: number;
|
|
64
|
+
/** Initial page when uncontrolled. */
|
|
65
|
+
defaultIndex?: number;
|
|
66
|
+
onIndexChange?: (index: number) => void;
|
|
67
|
+
/**
|
|
68
|
+
* Blur the page behind the picture. Needs the optional `expo-blur`, and dims
|
|
69
|
+
* instead without it. Reduce Transparency draws an opaque backdrop.
|
|
70
|
+
*/
|
|
71
|
+
blur?: boolean;
|
|
72
|
+
/** How far a pinch can zoom in, as a multiple of the fitted size. */
|
|
73
|
+
maxScale?: number;
|
|
74
|
+
/** Where a double tap zooms to, as a multiple of the fitted size. */
|
|
75
|
+
doubleTapScale?: number;
|
|
76
|
+
/** Tick as a drag to dismiss begins. Needs the optional `expo-haptics`. */
|
|
77
|
+
haptics?: boolean;
|
|
78
|
+
/** Draw the close button. Tapping outside the picture and dragging it away still close it. */
|
|
79
|
+
showClose?: boolean;
|
|
80
|
+
/** Read out for the close button. */
|
|
81
|
+
closeLabel?: string;
|
|
82
|
+
/**
|
|
83
|
+
* Space kept between the open picture and the edges of the screen, in points.
|
|
84
|
+
* Measured from the safe area at the top and bottom, and the larger of the
|
|
85
|
+
* two is used for both, so the picture stays centred. `0` fills the screen.
|
|
86
|
+
*/
|
|
87
|
+
inset?: number;
|
|
88
|
+
/**
|
|
89
|
+
* Corner radius of the open picture, in points. The corners stay this size on
|
|
90
|
+
* screen while the picture is zoomed or dragged. `0` squares them.
|
|
91
|
+
*/
|
|
92
|
+
cornerRadius?: number;
|
|
93
|
+
}
|
|
94
|
+
declare function ImageViewerRoot({ children, open, defaultOpen, onOpenChange, index, defaultIndex, onIndexChange, blur, maxScale, doubleTapScale, haptics, showClose, closeLabel, inset, cornerRadius, }: ImageViewerProps): import("react").JSX.Element;
|
|
95
|
+
export interface ImageViewerTriggerProps extends Omit<PressableProps, 'children' | 'style' | 'disabled'> {
|
|
96
|
+
/**
|
|
97
|
+
* Classes on the pressable. Without `children` the image fills it, so give it
|
|
98
|
+
* a size — `h-48 w-full`, `aspect-square flex-1`.
|
|
99
|
+
*/
|
|
100
|
+
className?: string;
|
|
101
|
+
/** The picture. Shown in the page and, until `fullSource` loads, in the viewer. */
|
|
102
|
+
source: ImageSourcePropType;
|
|
103
|
+
/**
|
|
104
|
+
* A larger copy to show once the viewer is open. It loads when the viewer
|
|
105
|
+
* opens and replaces `source` when it arrives, so a feed can carry thumbnails.
|
|
106
|
+
*/
|
|
107
|
+
fullSource?: ImageSourcePropType;
|
|
108
|
+
/** Described for a screen reader, on the trigger and in the viewer. */
|
|
109
|
+
alt?: string;
|
|
110
|
+
/** Shown under the picture while it is open. A string is set as text. */
|
|
111
|
+
caption?: ReactNode;
|
|
112
|
+
/** Page order within the root. Render order when left out. */
|
|
113
|
+
index?: number;
|
|
114
|
+
/**
|
|
115
|
+
* The corner radius the picture has in the page, in points, so the flight
|
|
116
|
+
* starts from the same shape. Match it to the `rounded-*` class you gave the
|
|
117
|
+
* trigger — a class cannot be read back.
|
|
118
|
+
*/
|
|
119
|
+
radius?: number;
|
|
120
|
+
/**
|
|
121
|
+
* The image's own width and height, when known. Saves looking it up, and is
|
|
122
|
+
* the only way the viewer knows the proportions before a remote image loads.
|
|
123
|
+
*/
|
|
124
|
+
width?: number;
|
|
125
|
+
height?: number;
|
|
126
|
+
/** Nothing opens, and the press is not reported. */
|
|
127
|
+
disabled?: boolean;
|
|
128
|
+
/**
|
|
129
|
+
* Draw the picture yourself — a `Post.Media`, a card. It should show `source`
|
|
130
|
+
* cropped to fill, the way the viewer's own flight starts. Left out, the
|
|
131
|
+
* trigger draws `source` to fill its box.
|
|
132
|
+
*/
|
|
133
|
+
children?: ReactNode;
|
|
134
|
+
}
|
|
135
|
+
/**
|
|
136
|
+
* The thing pressed to open the viewer.
|
|
137
|
+
*
|
|
138
|
+
* It registers its picture with the root, so the gallery is simply every
|
|
139
|
+
* trigger under that root. While its picture is out on the screen it is drawn
|
|
140
|
+
* transparent — not removed, so the page does not reflow under the blur and the
|
|
141
|
+
* flight home has somewhere to land.
|
|
142
|
+
*/
|
|
143
|
+
declare function ImageViewerTrigger({ className, source, fullSource, alt, caption, index, radius, width, height, disabled, children, onPress, onLayout, ...props }: ImageViewerTriggerProps): import("react").JSX.Element;
|
|
144
|
+
export declare const ImageViewer: typeof ImageViewerRoot & {
|
|
145
|
+
Trigger: typeof ImageViewerTrigger;
|
|
146
|
+
};
|
|
147
|
+
export {};
|
|
148
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../../src/components/image-viewer/index.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAmDG;AACH,OAAO,EAWL,KAAK,SAAS,EACf,MAAM,OAAO,CAAC;AACf,OAAO,EAOL,KAAK,mBAAmB,EAExB,KAAK,cAAc,EACpB,MAAM,cAAc,CAAC;AAyKtB,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,EAAE,SAAS,CAAC;IACrB,6BAA6B;IAC7B,IAAI,CAAC,EAAE,OAAO,CAAC;IACf,4CAA4C;IAC5C,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,YAAY,CAAC,EAAE,CAAC,IAAI,EAAE,OAAO,KAAK,IAAI,CAAC;IACvC,yEAAyE;IACzE,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,sCAAsC;IACtC,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,aAAa,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IACxC;;;OAGG;IACH,IAAI,CAAC,EAAE,OAAO,CAAC;IACf,qEAAqE;IACrE,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,qEAAqE;IACrE,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,2EAA2E;IAC3E,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,8FAA8F;IAC9F,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,qCAAqC;IACrC,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB;;;;OAIG;IACH,KAAK,CAAC,EAAE,MAAM,CAAC;IACf;;;OAGG;IACH,YAAY,CAAC,EAAE,MAAM,CAAC;CACvB;AAED,iBAAS,eAAe,CAAC,EACvB,QAAQ,EACR,IAAI,EACJ,WAAmB,EACnB,YAAY,EACZ,KAAK,EACL,YAAgB,EAChB,aAAa,EACb,IAAW,EACX,QAAY,EACZ,cAAoB,EACpB,OAAc,EACd,SAAgB,EAChB,UAAoB,EACpB,KAAqB,EACrB,YAAoC,GACrC,EAAE,gBAAgB,+BAuElB;AAMD,MAAM,WAAW,uBACf,SAAQ,IAAI,CAAC,cAAc,EAAE,UAAU,GAAG,OAAO,GAAG,UAAU,CAAC;IAC/D;;;OAGG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,mFAAmF;IACnF,MAAM,EAAE,mBAAmB,CAAC;IAC5B;;;OAGG;IACH,UAAU,CAAC,EAAE,mBAAmB,CAAC;IACjC,uEAAuE;IACvE,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,yEAAyE;IACzE,OAAO,CAAC,EAAE,SAAS,CAAC;IACpB,8DAA8D;IAC9D,KAAK,CAAC,EAAE,MAAM,CAAC;IACf;;;;OAIG;IACH,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB;;;OAGG;IACH,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,oDAAoD;IACpD,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB;;;;OAIG;IACH,QAAQ,CAAC,EAAE,SAAS,CAAC;CACtB;AAmBD;;;;;;;GAOG;AACH,iBAAS,kBAAkB,CAAC,EAC1B,SAAS,EACT,MAAM,EACN,UAAU,EACV,GAAG,EACH,OAAO,EACP,KAAK,EACL,MAAU,EACV,KAAK,EACL,MAAM,EACN,QAAgB,EAChB,QAAQ,EACR,OAAO,EACP,QAAQ,EACR,GAAG,KAAK,EACT,EAAE,uBAAuB,+BAyGzB;AA0vBD,eAAO,MAAM,WAAW;;CAEtB,CAAC"}
|
|
@@ -0,0 +1,472 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* StackCard — a pile of cards, taken one at a time by throwing the top one off.
|
|
3
|
+
*
|
|
4
|
+
* ```tsx
|
|
5
|
+
* <StackCard className="h-[460px]" onSwipe={(direction, index) => decide(people[index], direction)}>
|
|
6
|
+
* <StackCard.Stamp direction="right" color="success">Yes</StackCard.Stamp>
|
|
7
|
+
* <StackCard.Stamp direction="left" color="destructive">No</StackCard.Stamp>
|
|
8
|
+
* {people.map((person) => (
|
|
9
|
+
* <StackCard.Card key={person.id}>
|
|
10
|
+
* <Text>{person.name}</Text>
|
|
11
|
+
* </StackCard.Card>
|
|
12
|
+
* ))}
|
|
13
|
+
* <StackCard.Empty>
|
|
14
|
+
* <Text muted>Nobody left</Text>
|
|
15
|
+
* </StackCard.Empty>
|
|
16
|
+
* </StackCard>
|
|
17
|
+
* ```
|
|
18
|
+
*
|
|
19
|
+
* For a queue of things each answered with one decision and then gone: a
|
|
20
|
+
* review queue, a set of flashcards, an inbox of suggestions. The gesture is
|
|
21
|
+
* the answer, which is what makes it quicker than a list of rows with buttons
|
|
22
|
+
* on them — and what makes it wrong for anything the reader has to compare,
|
|
23
|
+
* skim or come back to. A deck shows one card and hides the rest.
|
|
24
|
+
*
|
|
25
|
+
* For a run of slides the reader browses rather than disposes of, use
|
|
26
|
+
* [Carousel](../carousel); for one row's actions in a list, [Swipe](../swipe).
|
|
27
|
+
*
|
|
28
|
+
* ## The pile is one drag, read by everything
|
|
29
|
+
*
|
|
30
|
+
* The top card's `x` and `y` are the only values a gesture writes, and every
|
|
31
|
+
* other moving part is derived from them: each stamp fades in on how far the
|
|
32
|
+
* drag has carried the card toward its own direction, and the cards behind
|
|
33
|
+
* climb toward the top position on the furthest of those.
|
|
34
|
+
*
|
|
35
|
+
* That derivation is also what makes a dismissal seamless. By the time the top
|
|
36
|
+
* card has been carried far enough to leave, the second card is already
|
|
37
|
+
* exactly where the top card sits — so when the deck advances there is nothing
|
|
38
|
+
* left for it to move, and no frame in which the pile re-arranges itself.
|
|
39
|
+
*
|
|
40
|
+
* ## The deck moves on the UI thread, and React catches up
|
|
41
|
+
*
|
|
42
|
+
* Which card is on top is held twice: as React state, for what is mounted and
|
|
43
|
+
* for the callbacks, and as a shared value, for what is drawn. A throw is
|
|
44
|
+
* handled entirely on the UI thread — the card leaves on the frame the finger
|
|
45
|
+
* lets go, and once it is off the screen the top card, the offset and the fade
|
|
46
|
+
* all move in one step — and only then is the new index requested from React.
|
|
47
|
+
*
|
|
48
|
+
* Nothing on the screen waits for a render, so a busy JavaScript thread cannot
|
|
49
|
+
* stall a throw or leave a frame where the two halves disagree. What React
|
|
50
|
+
* renders afterwards is kept from showing before the UI thread agrees with it:
|
|
51
|
+
* a stamp is only drawn on the card the UI thread has on top.
|
|
52
|
+
*
|
|
53
|
+
* A controlled deck is still the owner's to decide. An owner that declines the
|
|
54
|
+
* new index gets the card back, flown in from the way it went; one that
|
|
55
|
+
* accepts it sees nothing move at all, because it already has.
|
|
56
|
+
*
|
|
57
|
+
* One card behind the pile's stated depth stays mounted so it can fade in as
|
|
58
|
+
* it takes the last visible place, and one card ahead of the top stays mounted
|
|
59
|
+
* so `undo` has something to fly back in. The rest are unmounted, which is
|
|
60
|
+
* what makes a deck of five hundred cost what a deck of five costs.
|
|
61
|
+
*
|
|
62
|
+
* ## A deck is not reachable by a gesture alone
|
|
63
|
+
*
|
|
64
|
+
* A throw is not available to a screen reader, and neither is a card that can
|
|
65
|
+
* only be answered by throwing it. So the top card publishes an accessibility
|
|
66
|
+
* action for every direction the deck accepts, and `StackCard.Action` renders
|
|
67
|
+
* the same decisions as ordinary buttons — which sighted people reach for too,
|
|
68
|
+
* on the card they are not sure about.
|
|
69
|
+
*/
|
|
70
|
+
import { type ReactNode } from 'react';
|
|
71
|
+
import { View, type ViewProps } from 'react-native';
|
|
72
|
+
import { type SharedValue } from 'react-native-reanimated';
|
|
73
|
+
import { type VariantProps } from 'tailwind-variants';
|
|
74
|
+
import { type StackCardDirection } from './stack-card-geometry.js';
|
|
75
|
+
export type { StackCardDirection } from './stack-card-geometry.js';
|
|
76
|
+
/**
|
|
77
|
+
* The deck's state, for a control that lives outside the pile — a counter, a
|
|
78
|
+
* progress bar, a button in a toolbar.
|
|
79
|
+
*
|
|
80
|
+
* `release` is a shared value running 0 to 1 as the top card is carried toward
|
|
81
|
+
* leaving, so something beside the deck can move with the drag rather than
|
|
82
|
+
* starting a second animation next to it.
|
|
83
|
+
*/
|
|
84
|
+
export declare function useStackCard(): {
|
|
85
|
+
/** How many cards have been answered, which is also the top card's index. */
|
|
86
|
+
index: number;
|
|
87
|
+
/** How many cards the deck was given. */
|
|
88
|
+
count: number;
|
|
89
|
+
/** How many are left, the top one included. */
|
|
90
|
+
remaining: number;
|
|
91
|
+
/** Whether there is a card to bring back. */
|
|
92
|
+
canUndo: boolean;
|
|
93
|
+
release: SharedValue<number>;
|
|
94
|
+
send: (direction: StackCardDirection) => void;
|
|
95
|
+
undo: () => void;
|
|
96
|
+
reset: () => void;
|
|
97
|
+
};
|
|
98
|
+
/** How the cards behind the top one are arranged. */
|
|
99
|
+
export type StackCardLayout = 'stack' | 'fan' | 'flat';
|
|
100
|
+
export interface StackCardHandle {
|
|
101
|
+
/** Send the top card away as though it had been thrown that way. */
|
|
102
|
+
swipe: (direction: StackCardDirection) => void;
|
|
103
|
+
/** Bring the last card back, and with it the decision that removed it. */
|
|
104
|
+
undo: () => void;
|
|
105
|
+
/** Put every card back. */
|
|
106
|
+
reset: () => void;
|
|
107
|
+
}
|
|
108
|
+
export interface StackCardProps extends Omit<ViewProps, 'children'> {
|
|
109
|
+
/**
|
|
110
|
+
* A `StackCard.Card` for each card, plus any of `StackCard.Stamp`,
|
|
111
|
+
* `StackCard.Empty` and `StackCard.Actions`, in any order. Anything else is
|
|
112
|
+
* laid out under the pile.
|
|
113
|
+
*/
|
|
114
|
+
children?: ReactNode;
|
|
115
|
+
/**
|
|
116
|
+
* Which card is on top, when the caller holds it. Leave unset to let the
|
|
117
|
+
* deck keep its own. A controlled deck that declines a request stays where
|
|
118
|
+
* it is and the thrown card comes back, so this is also how a decision is
|
|
119
|
+
* confirmed before it is taken.
|
|
120
|
+
*/
|
|
121
|
+
index?: number;
|
|
122
|
+
/** Which card an uncontrolled deck starts on. */
|
|
123
|
+
defaultIndex?: number;
|
|
124
|
+
/** Fires whenever the deck asks to move, with the index it is asking for. */
|
|
125
|
+
onIndexChange?: (index: number) => void;
|
|
126
|
+
/**
|
|
127
|
+
* Fires when a card leaves, with the way it went and the index it was at.
|
|
128
|
+
* It fires before `onIndexChange` asks for the next index. Not called by
|
|
129
|
+
* `undo` — the index going back is what reports that.
|
|
130
|
+
*/
|
|
131
|
+
onSwipe?: (direction: StackCardDirection, index: number) => void;
|
|
132
|
+
/** Fires once when the last card leaves. */
|
|
133
|
+
onEmpty?: () => void;
|
|
134
|
+
/**
|
|
135
|
+
* Which ways a card may be thrown. Left and right by default.
|
|
136
|
+
*
|
|
137
|
+
* A direction left out still follows the finger a little and then comes
|
|
138
|
+
* back, rather than refusing to move at all — a card that does not budge
|
|
139
|
+
* reads as a frozen screen.
|
|
140
|
+
*/
|
|
141
|
+
directions?: readonly StackCardDirection[];
|
|
142
|
+
/**
|
|
143
|
+
* How the cards behind the top one are arranged. `stack` steps them down and
|
|
144
|
+
* back; `fan` turns them alternately, like a hand of cards; `flat` hides them
|
|
145
|
+
* entirely, for full-bleed cards where a peeking edge is only clutter.
|
|
146
|
+
*/
|
|
147
|
+
layout?: StackCardLayout;
|
|
148
|
+
/** How many cards are drawn behind the top one. Two is a pile; five is a mess. */
|
|
149
|
+
depth?: number;
|
|
150
|
+
/**
|
|
151
|
+
* How far a card has to be taken for a release to send it away, as a
|
|
152
|
+
* fraction of the card. Momentum counts toward it, so a flick clears it
|
|
153
|
+
* without travelling.
|
|
154
|
+
*/
|
|
155
|
+
threshold?: number;
|
|
156
|
+
/** Stop the deck taking a gesture, without changing how it looks. */
|
|
157
|
+
disabled?: boolean;
|
|
158
|
+
/** A tick when a drag first reaches the point of no return, and a knock as the card goes. */
|
|
159
|
+
haptics?: boolean;
|
|
160
|
+
/**
|
|
161
|
+
* What a screen reader is offered for each direction, in place of "Swipe
|
|
162
|
+
* left". Name the decision — `{ left: 'Skip', right: 'Save' }`.
|
|
163
|
+
*/
|
|
164
|
+
directionLabels?: Partial<Record<StackCardDirection, string>>;
|
|
165
|
+
/** Classes for the whole control. Give it a height; the pile fills what is left. */
|
|
166
|
+
className?: string;
|
|
167
|
+
/** Classes for the box the cards are laid out in. */
|
|
168
|
+
pileClassName?: string;
|
|
169
|
+
}
|
|
170
|
+
export interface StackCardCardProps extends ViewProps {
|
|
171
|
+
className?: string;
|
|
172
|
+
children?: ReactNode;
|
|
173
|
+
}
|
|
174
|
+
/**
|
|
175
|
+
* A stamp is a filled block of colour with a word on it, turned a few degrees
|
|
176
|
+
* so it reads as pressed onto the card rather than laid out on it.
|
|
177
|
+
*
|
|
178
|
+
* The fill is the status colour at full strength rather than a tint of it: a
|
|
179
|
+
* stamp exists only for the moment it appears, and a six-per-cent wash of the
|
|
180
|
+
* card's own surface is a smudge rather than an answer. The word is carried in
|
|
181
|
+
* white, which is what the status colours are chosen to take — a status's
|
|
182
|
+
* `-foreground` token is its darker text form, meant for a neutral surface,
|
|
183
|
+
* and over the fill it is the same hue twice.
|
|
184
|
+
*
|
|
185
|
+
* It sits in the corner the card is being pulled away from, which is also the
|
|
186
|
+
* corner the thumb is not over.
|
|
187
|
+
*/
|
|
188
|
+
declare const stampVariants: import("tailwind-variants").TVReturnType<{
|
|
189
|
+
color: {
|
|
190
|
+
default: {
|
|
191
|
+
pill: string;
|
|
192
|
+
label: string;
|
|
193
|
+
};
|
|
194
|
+
primary: {
|
|
195
|
+
pill: string;
|
|
196
|
+
label: string;
|
|
197
|
+
};
|
|
198
|
+
success: {
|
|
199
|
+
pill: string;
|
|
200
|
+
label: string;
|
|
201
|
+
};
|
|
202
|
+
warning: {
|
|
203
|
+
pill: string;
|
|
204
|
+
label: string;
|
|
205
|
+
};
|
|
206
|
+
info: {
|
|
207
|
+
pill: string;
|
|
208
|
+
label: string;
|
|
209
|
+
};
|
|
210
|
+
destructive: {
|
|
211
|
+
pill: string;
|
|
212
|
+
label: string;
|
|
213
|
+
};
|
|
214
|
+
};
|
|
215
|
+
direction: {
|
|
216
|
+
left: {
|
|
217
|
+
root: string;
|
|
218
|
+
pill: string;
|
|
219
|
+
};
|
|
220
|
+
right: {
|
|
221
|
+
root: string;
|
|
222
|
+
pill: string;
|
|
223
|
+
};
|
|
224
|
+
up: {
|
|
225
|
+
root: string;
|
|
226
|
+
};
|
|
227
|
+
down: {
|
|
228
|
+
root: string;
|
|
229
|
+
};
|
|
230
|
+
};
|
|
231
|
+
}, {
|
|
232
|
+
root: string;
|
|
233
|
+
pill: string;
|
|
234
|
+
label: string;
|
|
235
|
+
}, undefined, {
|
|
236
|
+
color: {
|
|
237
|
+
default: {
|
|
238
|
+
pill: string;
|
|
239
|
+
label: string;
|
|
240
|
+
};
|
|
241
|
+
primary: {
|
|
242
|
+
pill: string;
|
|
243
|
+
label: string;
|
|
244
|
+
};
|
|
245
|
+
success: {
|
|
246
|
+
pill: string;
|
|
247
|
+
label: string;
|
|
248
|
+
};
|
|
249
|
+
warning: {
|
|
250
|
+
pill: string;
|
|
251
|
+
label: string;
|
|
252
|
+
};
|
|
253
|
+
info: {
|
|
254
|
+
pill: string;
|
|
255
|
+
label: string;
|
|
256
|
+
};
|
|
257
|
+
destructive: {
|
|
258
|
+
pill: string;
|
|
259
|
+
label: string;
|
|
260
|
+
};
|
|
261
|
+
};
|
|
262
|
+
direction: {
|
|
263
|
+
left: {
|
|
264
|
+
root: string;
|
|
265
|
+
pill: string;
|
|
266
|
+
};
|
|
267
|
+
right: {
|
|
268
|
+
root: string;
|
|
269
|
+
pill: string;
|
|
270
|
+
};
|
|
271
|
+
up: {
|
|
272
|
+
root: string;
|
|
273
|
+
};
|
|
274
|
+
down: {
|
|
275
|
+
root: string;
|
|
276
|
+
};
|
|
277
|
+
};
|
|
278
|
+
}, {
|
|
279
|
+
root: string;
|
|
280
|
+
pill: string;
|
|
281
|
+
label: string;
|
|
282
|
+
}, import("tailwind-variants").TVReturnType<{
|
|
283
|
+
color: {
|
|
284
|
+
default: {
|
|
285
|
+
pill: string;
|
|
286
|
+
label: string;
|
|
287
|
+
};
|
|
288
|
+
primary: {
|
|
289
|
+
pill: string;
|
|
290
|
+
label: string;
|
|
291
|
+
};
|
|
292
|
+
success: {
|
|
293
|
+
pill: string;
|
|
294
|
+
label: string;
|
|
295
|
+
};
|
|
296
|
+
warning: {
|
|
297
|
+
pill: string;
|
|
298
|
+
label: string;
|
|
299
|
+
};
|
|
300
|
+
info: {
|
|
301
|
+
pill: string;
|
|
302
|
+
label: string;
|
|
303
|
+
};
|
|
304
|
+
destructive: {
|
|
305
|
+
pill: string;
|
|
306
|
+
label: string;
|
|
307
|
+
};
|
|
308
|
+
};
|
|
309
|
+
direction: {
|
|
310
|
+
left: {
|
|
311
|
+
root: string;
|
|
312
|
+
pill: string;
|
|
313
|
+
};
|
|
314
|
+
right: {
|
|
315
|
+
root: string;
|
|
316
|
+
pill: string;
|
|
317
|
+
};
|
|
318
|
+
up: {
|
|
319
|
+
root: string;
|
|
320
|
+
};
|
|
321
|
+
down: {
|
|
322
|
+
root: string;
|
|
323
|
+
};
|
|
324
|
+
};
|
|
325
|
+
}, {
|
|
326
|
+
root: string;
|
|
327
|
+
pill: string;
|
|
328
|
+
label: string;
|
|
329
|
+
}, undefined, unknown, unknown, undefined>>;
|
|
330
|
+
export type StackCardStampColor = 'default' | 'primary' | 'success' | 'warning' | 'info' | 'destructive';
|
|
331
|
+
export interface StackCardStampProps extends Omit<ViewProps, 'children'>, VariantProps<typeof stampVariants> {
|
|
332
|
+
className?: string;
|
|
333
|
+
/** The word, or anything else to draw on the stamp. */
|
|
334
|
+
children?: ReactNode;
|
|
335
|
+
/** Which direction the stamp answers for. Also where on the card it goes. */
|
|
336
|
+
direction?: StackCardDirection;
|
|
337
|
+
/** Extra classes for the label, when the stamp is given a string. */
|
|
338
|
+
labelClassName?: string;
|
|
339
|
+
}
|
|
340
|
+
export interface StackCardEmptyProps extends ViewProps {
|
|
341
|
+
className?: string;
|
|
342
|
+
children?: ReactNode;
|
|
343
|
+
}
|
|
344
|
+
export interface StackCardActionsProps extends ViewProps {
|
|
345
|
+
className?: string;
|
|
346
|
+
children?: ReactNode;
|
|
347
|
+
}
|
|
348
|
+
declare const actionVariants: import("tailwind-variants").TVReturnType<{
|
|
349
|
+
color: {
|
|
350
|
+
default: {
|
|
351
|
+
root: string;
|
|
352
|
+
};
|
|
353
|
+
primary: {
|
|
354
|
+
root: string;
|
|
355
|
+
};
|
|
356
|
+
success: {
|
|
357
|
+
root: string;
|
|
358
|
+
};
|
|
359
|
+
warning: {
|
|
360
|
+
root: string;
|
|
361
|
+
};
|
|
362
|
+
info: {
|
|
363
|
+
root: string;
|
|
364
|
+
};
|
|
365
|
+
destructive: {
|
|
366
|
+
root: string;
|
|
367
|
+
};
|
|
368
|
+
};
|
|
369
|
+
size: {
|
|
370
|
+
sm: {
|
|
371
|
+
root: string;
|
|
372
|
+
};
|
|
373
|
+
md: {
|
|
374
|
+
root: string;
|
|
375
|
+
};
|
|
376
|
+
lg: {
|
|
377
|
+
root: string;
|
|
378
|
+
};
|
|
379
|
+
};
|
|
380
|
+
}, {
|
|
381
|
+
root: string;
|
|
382
|
+
}, undefined, {
|
|
383
|
+
color: {
|
|
384
|
+
default: {
|
|
385
|
+
root: string;
|
|
386
|
+
};
|
|
387
|
+
primary: {
|
|
388
|
+
root: string;
|
|
389
|
+
};
|
|
390
|
+
success: {
|
|
391
|
+
root: string;
|
|
392
|
+
};
|
|
393
|
+
warning: {
|
|
394
|
+
root: string;
|
|
395
|
+
};
|
|
396
|
+
info: {
|
|
397
|
+
root: string;
|
|
398
|
+
};
|
|
399
|
+
destructive: {
|
|
400
|
+
root: string;
|
|
401
|
+
};
|
|
402
|
+
};
|
|
403
|
+
size: {
|
|
404
|
+
sm: {
|
|
405
|
+
root: string;
|
|
406
|
+
};
|
|
407
|
+
md: {
|
|
408
|
+
root: string;
|
|
409
|
+
};
|
|
410
|
+
lg: {
|
|
411
|
+
root: string;
|
|
412
|
+
};
|
|
413
|
+
};
|
|
414
|
+
}, {
|
|
415
|
+
root: string;
|
|
416
|
+
}, import("tailwind-variants").TVReturnType<{
|
|
417
|
+
color: {
|
|
418
|
+
default: {
|
|
419
|
+
root: string;
|
|
420
|
+
};
|
|
421
|
+
primary: {
|
|
422
|
+
root: string;
|
|
423
|
+
};
|
|
424
|
+
success: {
|
|
425
|
+
root: string;
|
|
426
|
+
};
|
|
427
|
+
warning: {
|
|
428
|
+
root: string;
|
|
429
|
+
};
|
|
430
|
+
info: {
|
|
431
|
+
root: string;
|
|
432
|
+
};
|
|
433
|
+
destructive: {
|
|
434
|
+
root: string;
|
|
435
|
+
};
|
|
436
|
+
};
|
|
437
|
+
size: {
|
|
438
|
+
sm: {
|
|
439
|
+
root: string;
|
|
440
|
+
};
|
|
441
|
+
md: {
|
|
442
|
+
root: string;
|
|
443
|
+
};
|
|
444
|
+
lg: {
|
|
445
|
+
root: string;
|
|
446
|
+
};
|
|
447
|
+
};
|
|
448
|
+
}, {
|
|
449
|
+
root: string;
|
|
450
|
+
}, undefined, unknown, unknown, undefined>>;
|
|
451
|
+
export interface StackCardActionProps extends Omit<ViewProps, 'children'>, VariantProps<typeof actionVariants> {
|
|
452
|
+
className?: string;
|
|
453
|
+
/** What pressing it does: send the top card that way, or bring the last one back. */
|
|
454
|
+
action: StackCardDirection | 'undo';
|
|
455
|
+
/** The glyph. Sized and tinted by the button — pass neither. */
|
|
456
|
+
icon?: ReactNode;
|
|
457
|
+
/**
|
|
458
|
+
* What a screen reader is offered. Falls back to "Undo", or to the plain
|
|
459
|
+
* name of the direction.
|
|
460
|
+
*/
|
|
461
|
+
label?: string;
|
|
462
|
+
/** Run after the deck has been told, for a sound or a log. */
|
|
463
|
+
onPress?: () => void;
|
|
464
|
+
}
|
|
465
|
+
export declare const StackCard: import("react").ForwardRefExoticComponent<StackCardProps & import("react").RefAttributes<StackCardHandle>> & {
|
|
466
|
+
Card: import("react").ForwardRefExoticComponent<StackCardCardProps & import("react").RefAttributes<View>>;
|
|
467
|
+
Stamp: import("react").ForwardRefExoticComponent<StackCardStampProps & import("react").RefAttributes<View>>;
|
|
468
|
+
Empty: import("react").ForwardRefExoticComponent<StackCardEmptyProps & import("react").RefAttributes<View>>;
|
|
469
|
+
Actions: import("react").ForwardRefExoticComponent<StackCardActionsProps & import("react").RefAttributes<View>>;
|
|
470
|
+
Action: import("react").ForwardRefExoticComponent<StackCardActionProps & import("react").RefAttributes<View>>;
|
|
471
|
+
};
|
|
472
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../../src/components/stack-card/index.tsx"],"names":[],"mappings":"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"}
|