@kanso-labs/react-native-kanso-ui 0.1.0 → 0.2.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.
Files changed (49) hide show
  1. package/dist/button/index.d.ts +24 -2
  2. package/dist/button/index.js.map +1 -1
  3. package/dist/button/pending.js +144 -0
  4. package/dist/button/pending.js.map +1 -0
  5. package/dist/components/button/index.d.ts +1 -1
  6. package/dist/components/button/index.js +154 -112
  7. package/dist/components/button/index.js.map +1 -1
  8. package/dist/components/icon-button/index.d.ts +1 -1
  9. package/dist/components/icon-button/index.js +160 -110
  10. package/dist/components/icon-button/index.js.map +1 -1
  11. package/dist/components/meter/index.d.ts +73 -0
  12. package/dist/components/meter/index.js +179 -0
  13. package/dist/components/meter/index.js.map +1 -0
  14. package/dist/components/number-field/index.js +1 -9
  15. package/dist/components/number-field/index.js.map +1 -1
  16. package/dist/components/progress-indicator/index.d.ts +113 -0
  17. package/dist/components/progress-indicator/index.js +1024 -0
  18. package/dist/components/progress-indicator/index.js.map +1 -0
  19. package/dist/components/snackbar/index.d.ts +120 -0
  20. package/dist/components/snackbar/index.js +540 -0
  21. package/dist/components/snackbar/index.js.map +1 -0
  22. package/dist/glyphs/hidden.js +13 -0
  23. package/dist/glyphs/hidden.js.map +1 -0
  24. package/dist/glyphs/index.js +2 -8
  25. package/dist/glyphs/index.js.map +1 -1
  26. package/dist/i18n/index.js +23 -0
  27. package/dist/i18n/index.js.map +1 -0
  28. package/dist/i18n/messages.js +41 -0
  29. package/dist/i18n/messages.js.map +1 -0
  30. package/dist/index.d.ts +4 -1
  31. package/dist/index.js +6 -3
  32. package/dist/indicator/index.d.ts +15 -0
  33. package/dist/indicator/index.js +256 -0
  34. package/dist/indicator/index.js.map +1 -0
  35. package/dist/indicator/motion.js +86 -0
  36. package/dist/indicator/motion.js.map +1 -0
  37. package/dist/indicator/paths.js +72 -0
  38. package/dist/indicator/paths.js.map +1 -0
  39. package/dist/indicator/styles.js +62 -0
  40. package/dist/indicator/styles.js.map +1 -0
  41. package/dist/number/locale.js +14 -0
  42. package/dist/number/locale.js.map +1 -0
  43. package/dist/overlay/host.js +65 -2
  44. package/dist/overlay/host.js.map +1 -1
  45. package/dist/press/index.js +10 -9
  46. package/dist/press/index.js.map +1 -1
  47. package/dist/theme/resolve.js +1 -1
  48. package/dist/theme/resolve.js.map +1 -1
  49. package/package.json +2 -2
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","names":["ReactNode","Ref","PressableProps","StyleProp","TextStyle","View","ViewStyle","AnimatedStyle","Text","NativeText","StyleSheet","Animated","ButtonLinkForm","ButtonPressForm","ButtonToggleForm","PaletteName","IconStyle","ResolvedTheme","TypeRole","AnimatedPressable","buttonStyles","HEIGHTS","OUTLINE_WIDTHS","PRESSED_CORNERS","toggleState","useButtonAction","useCorner","palettesOf","IconStyleContext","hitSlop","usePressFeedback","useTheme","composeStyles","themedStyles","useTypeRole","ButtonForm","variant","Exclude","ButtonVariant","ButtonProps","Omit","children","disableRipple","icon","isDisabled","ref","shape","ButtonShape","size","ButtonSize","style","ToggleVariant","DISABLED","Readonly","Record","elevated","filled","outlined","text","tonal","ICON_SIZES","lg","md","xl","xs","xxl","ROLES","SQUARE_CORNERS","const","TOGGLE_PALETTES","selected","unselected","styles","create","base","alignItems","flexDirection","justifyContent","maxWidth","flexShrink","label","textAlign","inlinePaddings","spacing","shadowsOf","shadows","elevation1","boxShadow","elevation2","sizesOf","theme","sizing","inline","gap","sm","minHeight","controlLg","paddingHorizontal","paddingVertical","controlSm","controlXl","controlXs","controlXxl","outlinedSizesOf","borderWidth","Button","t0","$","_c","defaultSelected","href","isSelected","onBlur","onChange","onFocus","onHoverIn","onHoverOut","onLayout","onPress","onPressIn","onPressOut","ownHitSlop","props","t1","t2","t3","t4","t5","type","undefined","role","isToggle","t6","action","colors","feedback","color","content","disabled","radii","resting","pill","shaped","pressed","T0","t7","t8","t9","handlers","t10","t11","t12","t13","container","shadowOf","corner","ring","t14","clip","t15","layer","t16","iconStyleOf","t17","t18","hovered","lifted","_c","NativeText"],"sources":["../../../src/components/button/index.tsx"],"sourcesContent":["import type { ReactNode, Ref } from 'react'\nimport type {\n PressableProps,\n StyleProp,\n TextStyle,\n View,\n ViewStyle,\n} from 'react-native'\nimport type { AnimatedStyle } from 'react-native-reanimated'\n\nimport { Text as NativeText, StyleSheet } from 'react-native'\nimport Animated from 'react-native-reanimated'\n\nimport type {\n ButtonLinkForm,\n ButtonPressForm,\n ButtonToggleForm,\n} from '../../button'\nimport type { PaletteName } from '../../button/palettes'\nimport type { IconStyle } from '../../glyphs/icon-style'\nimport type { ResolvedTheme } from '../../theme/scope'\nimport type { TypeRole } from '../../typography/roles'\n\nimport {\n AnimatedPressable,\n buttonStyles,\n HEIGHTS,\n OUTLINE_WIDTHS,\n PRESSED_CORNERS,\n toggleState,\n useButtonAction,\n useCorner,\n} from '../../button'\nimport { palettesOf } from '../../button/palettes'\nimport { IconStyleContext } from '../../glyphs/icon-style'\nimport { hitSlop, usePressFeedback } from '../../press'\nimport { useTheme } from '../../theme/scope'\nimport { composeStyles, themedStyles } from '../../theme/styles'\nimport { useTypeRole } from '../../typography/roles'\n\n// The buttons spec page's five colour styles, five sizes and two shapes, as\n// kanso-ui's Button draws them. The variant carries colour and the size\n// carries geometry, so the two never argue: the padding belongs to the size\n// alone, and a text button is as wide as a filled one at the same size.\n//\n// The colour pairs are the page's: filled on primary, tonal on secondary\n// container, outlined with an outline-variant rule and an on-surface-variant\n// label, text on primary, and elevated on surface container low with a\n// primary label. Elevated is the one variant whose shadow is part of it: it\n// rests at elevation 1, rises to 2 under a pointer and settles back while\n// pressed, where filled and tonal rest flat and lift to 1 under a pointer\n// only. The shadow is the theme's `boxShadow` value, which React Native draws\n// on iOS and Android as React Native Web draws it in a browser.\n//\n// The state layers, the ripple and the focus ring are src/press's, drawn in\n// the label's colour over the container, as on web.\n//\n// **Disabled is the page's colour at an opacity, translucent.** A container\n// is on-surface at the `disabledContainer` opacity, and the label on-surface\n// at `disabledContent`, over whatever the button sits on rather than mixed\n// over the surface role as web's are; src/button/palettes.ts gives the\n// reason. Disabled drops the shadow, since a shadow says a control is there\n// to press.\n//\n// **A toggle is the same button reporting a state.** Given `isSelected`,\n// `defaultSelected` or `onChange` it takes the page's second pair of colour\n// roles for its variant: a filled toggle rests on surface container with an\n// on-surface-variant label and takes primary once selected, a tonal one moves\n// from the secondary container pair to secondary, an elevated one keeps its\n// low surface until it takes primary, and an outlined one swaps its rule for\n// the inverse surface pair. The page gives text no pair, so a text button\n// given those props stays a plain one.\n//\n// **The corner is a shape the button morphs between.** `round` rests as the\n// pill and `square` at the size's square corner: 12dp up to the page's S,\n// 16dp at M and 28dp above. A press tightens either to the size's pressed\n// corner, 8dp, 12dp or 16dp, and a toggle trades its shape for the other\n// once selected. The corner eases through Reanimated, as src/button's\n// `useCorner` sets out.\n//\n// The forms, the toggle's state, what a press does and the corner's ease are\n// src/button's, shared with IconButton.\n\ntype ButtonForm =\n | ButtonLinkForm\n | ButtonPressForm\n | (ButtonToggleForm & {\n /**\n * A toggle takes any variant but `text`, which the page gives no\n * selected colours.\n */\n readonly variant?: Exclude<ButtonVariant, 'text'>\n })\n\ntype ButtonProps = ButtonForm &\n Omit<PressableProps, 'children' | 'disabled' | 'style'> & {\n /** The label. */\n readonly children?: ReactNode\n /**\n * Draws no press ripple. The state layer is unaffected.\n * @default false\n */\n readonly disableRipple?: boolean\n /**\n * An icon before the label, at the page's icon size for the button's\n * size: 20dp at `xs` and `md`, 24dp at `lg`, 32dp at `xl` and 40dp at\n * `xxl`. The slot hands it the label's colour and that size through\n * `useIconStyle()`.\n */\n readonly icon?: ReactNode\n /**\n * Draws the button disabled, and takes no presses.\n * @default false\n */\n readonly isDisabled?: boolean\n readonly ref?: Ref<View>\n /**\n * The corner the button rests at: `round` is the pill, `square` the\n * page's rounded rectangle, 12dp up to `md`, 16dp at `lg` and 28dp above.\n * Either tightens while pressed, and a toggle trades one for the other\n * once selected.\n * @default 'round'\n */\n readonly shape?: ButtonShape\n /**\n * Control height: `xs` 32dp, `md` 40dp, `lg` 56dp, `xl` 96dp, `xxl` 136dp,\n * the buttons spec page's XS, S, M, L and XL, each with its own padding\n * and type role. `md` is the page's default. The height is a floor, so a\n * label that wraps, or that the device's text size enlarges, grows the\n * button rather than running out of it.\n * @default 'md'\n */\n readonly size?: ButtonSize\n readonly style?: StyleProp<ViewStyle>\n /**\n * How much weight the button pulls. `filled` and `tonal` carry a container\n * of their own; `outlined` and `text` sit on the page; `elevated` sits on\n * a low surface and lifts off it with a shadow, for a button that has to\n * separate from a busy background rather than from the page.\n * @default 'filled'\n */\n readonly variant?: ButtonVariant\n }\n\ntype ButtonShape = 'round' | 'square'\n\ntype ButtonSize = 'lg' | 'md' | 'xl' | 'xs' | 'xxl'\n\ntype ButtonVariant = 'elevated' | 'filled' | 'outlined' | 'text' | 'tonal'\n\ntype ToggleVariant = Exclude<ButtonVariant, 'text'>\n\n// The disabled container each variant draws. Filled, tonal and elevated share\n// one, which is the page's single disabled container for all three.\nconst DISABLED: Readonly<Record<ButtonVariant, PaletteName>> = {\n elevated: 'filledDisabled',\n filled: 'filledDisabled',\n outlined: 'outlinedDisabled',\n text: 'textDisabled',\n tonal: 'filledDisabled',\n}\n\n// The icon each size draws, from the page's size token sets. Literals, as on\n// web: they are icon sizes, which the theme has no scale for.\nconst ICON_SIZES: Readonly<Record<ButtonSize, number>> = {\n lg: 24,\n md: 20,\n xl: 32,\n xs: 20,\n xxl: 40,\n}\n\n// The type role each size sets its label in, taken whole: label-large for the\n// two small sizes, then title-medium, headline-small and headline-large.\nconst ROLES: Readonly<Record<ButtonSize, TypeRole>> = {\n lg: 'titleMedium',\n md: 'labelLarge',\n xl: 'headlineSmall',\n xs: 'labelLarge',\n xxl: 'headlineLarge',\n}\n\n// The square corner each size rests at, and a round toggle takes once\n// selected.\nconst SQUARE_CORNERS = {\n lg: 'lg',\n md: 'md',\n xl: 'xl',\n xs: 'md',\n xxl: 'xl',\n} as const satisfies Record<ButtonSize, keyof ResolvedTheme['radii']>\n\n// Which container a toggle draws, selected and not.\nconst TOGGLE_PALETTES: Readonly<\n Record<\n ToggleVariant,\n Readonly<Record<'selected' | 'unselected', PaletteName>>\n >\n> = {\n elevated: { selected: 'elevatedToggleSelected', unselected: 'elevated' },\n filled: { selected: 'filledToggleSelected', unselected: 'filledToggle' },\n outlined: { selected: 'outlinedToggleSelected', unselected: 'outlined' },\n tonal: { selected: 'tonalToggleSelected', unselected: 'tonal' },\n}\n\nconst styles = StyleSheet.create({\n // The label sits in the middle of a button wider than it, one stretched by\n // a column or given a width, as the page draws every button, and a button\n // is never wider than what holds it.\n base: {\n alignItems: 'center',\n flexDirection: 'row',\n justifyContent: 'center',\n maxWidth: '100%',\n },\n icon: {\n alignItems: 'center',\n flexShrink: 0,\n justifyContent: 'center',\n },\n // A label too long for the row wraps, its lines centred, and grows the\n // button with it.\n label: {\n flexShrink: 1,\n textAlign: 'center',\n },\n})\n\n// Each size's inline padding. The two largest are literals: 48 and 64 are not\n// steps of the spacing scale, and the scale should not grow to fit one\n// component. `xs` pads 12 a side, the extra-small token set's leading and\n// trailing space.\nfunction inlinePaddings({\n spacing,\n}: ResolvedTheme): Readonly<Record<ButtonSize, number>> {\n return { lg: spacing.xl, md: spacing.lg, xl: 48, xs: spacing.md, xxl: 64 }\n}\n\nconst shadowsOf = themedStyles(({ shadows }) =>\n StyleSheet.create({\n elevation1: { boxShadow: shadows.elevation1 },\n elevation2: { boxShadow: shadows.elevation2 },\n }),\n)\n\n// The five sizes, from the page's size token sets: the container height, the\n// padding, and the gap before an icon. The height is a floor rather than a\n// fixed size, and the block padding is what keeps a wrapped label off the\n// pill's edge: a step short of a single line's own inset, so a label on one\n// line still draws exactly the page's height.\nconst sizesOf = themedStyles((theme) => {\n const { sizing, spacing } = theme\n const inline = inlinePaddings(theme)\n\n return StyleSheet.create({\n lg: {\n gap: spacing.sm,\n minHeight: sizing.controlLg,\n paddingHorizontal: inline.lg,\n paddingVertical: spacing.md,\n },\n md: {\n gap: spacing.sm,\n minHeight: sizing.controlSm,\n paddingHorizontal: inline.md,\n paddingVertical: spacing.sm,\n },\n xl: {\n gap: spacing.md,\n minHeight: sizing.controlXl,\n paddingHorizontal: inline.xl,\n paddingVertical: spacing.xl,\n },\n xs: {\n gap: spacing.sm,\n minHeight: sizing.controlXs,\n paddingHorizontal: inline.xs,\n paddingVertical: spacing.xs,\n },\n xxl: {\n gap: spacing.lg,\n minHeight: sizing.controlXxl,\n paddingHorizontal: inline.xxl,\n paddingVertical: spacing.xxl,\n },\n })\n})\n\n// The outlined button draws its rule inside the width the other variants\n// take, as the page's buttons do: the padding gives up what the rule takes,\n// so an outlined and a filled button with one label are one width.\nconst outlinedSizesOf = themedStyles((theme) => {\n const inline = inlinePaddings(theme)\n\n function outlined(size: ButtonSize): ViewStyle {\n return {\n borderWidth: OUTLINE_WIDTHS[size],\n paddingHorizontal: inline[size] - OUTLINE_WIDTHS[size],\n }\n }\n\n return StyleSheet.create({\n lg: outlined('lg'),\n md: outlined('md'),\n xl: outlined('xl'),\n xs: outlined('xs'),\n xxl: outlined('xxl'),\n })\n})\n\n/**\n * The design's button, at five emphasis levels and five control heights,\n * round or square, with web's props and values. Given `href` it is a link with\n * the same appearance, and given `isSelected`, `defaultSelected` or\n * `onChange` it is a toggle, which reports its state to a screen reader and\n * draws the page's second pair of colour roles for its variant.\n *\n * ```tsx\n * <Button defaultSelected variant=\"tonal\">\n * Label\n * </Button>\n * ```\n *\n * A column stretches a button across it, as it does any view, and as a flex\n * column does a button on web; a column that should hold its buttons at their\n * labels' width says so with `alignItems`.\n *\n * The two sizes under 48dp tall, `xs` and `md`, take presses over a 48dp\n * target through `hitSlop`, which a `hitSlop` of the call site's own replaces.\n * `style`, `ref` and `testID` land on the `Pressable`.\n */\nfunction Button({\n children,\n defaultSelected,\n disableRipple = false,\n hitSlop: ownHitSlop,\n href,\n icon,\n isDisabled = false,\n isSelected,\n onBlur,\n onChange,\n onFocus,\n onHoverIn,\n onHoverOut,\n onLayout,\n onPress,\n onPressIn,\n onPressOut,\n shape = 'round',\n size = 'md',\n style,\n type,\n variant = 'filled',\n ...props\n}: ButtonProps) {\n const theme = useTheme()\n const role = useTypeRole(ROLES[size])\n\n // The three props that make this a toggle, read as web reads them. The\n // types keep them off a `text` button; the check here keeps a call site\n // that slipped past them a plain button.\n const isToggle =\n variant !== 'text' &&\n (defaultSelected !== undefined ||\n isSelected !== undefined ||\n onChange !== undefined)\n const action = useButtonAction({\n defaultSelected,\n href,\n isSelected,\n isToggle,\n onChange,\n onPress,\n type,\n })\n const colors =\n palettesOf(theme)[\n isDisabled\n ? DISABLED[variant]\n : variant !== 'text' && isToggle\n ? TOGGLE_PALETTES[variant][\n action.selected ? 'selected' : 'unselected'\n ]\n : variant\n ]\n\n const feedback = usePressFeedback({\n color: colors.content,\n disabled: isDisabled,\n disableRipple,\n onBlur,\n onFocus,\n onHoverIn,\n onHoverOut,\n onPressIn,\n onPressOut,\n })\n\n const { radii } = theme\n const resting =\n (shape === 'square') !== action.selected\n ? radii[SQUARE_CORNERS[size]]\n : radii.pill\n const shaped = useCorner(\n feedback.pressed ? radii[PRESSED_CORNERS[size]] : resting,\n onLayout,\n )\n\n return (\n <AnimatedPressable\n role={href === undefined ? 'button' : 'link'}\n {...(isToggle ? toggleState(action.selected) : undefined)}\n {...props}\n {...feedback.handlers}\n disabled={isDisabled}\n hitSlop={ownHitSlop ?? hitSlop(theme.sizing[HEIGHTS[size]])}\n onLayout={shaped.onLayout}\n onPress={action.onPress}\n style={composeStyles<AnimatedStyle<ViewStyle>>(\n styles.base,\n sizesOf(theme)[size],\n variant === 'outlined' ? outlinedSizesOf(theme)[size] : undefined,\n colors.container,\n shadowOf(variant, feedback, isDisabled, theme),\n shaped.corner,\n feedback.ring,\n style,\n )}\n >\n <Animated.View\n style={composeStyles<AnimatedStyle<ViewStyle>>(\n buttonStyles.clip,\n shaped.corner,\n )}\n >\n {feedback.layer}\n </Animated.View>\n {icon === undefined ? null : (\n <IconStyleContext value={iconStyleOf(colors.content, size)}>\n {icon}\n </IconStyleContext>\n )}\n {children === undefined ? null : (\n <NativeText\n style={composeStyles<TextStyle>(role, styles.label, colors.label)}\n >\n {children}\n </NativeText>\n )}\n </AnimatedPressable>\n )\n}\n\nfunction iconStyleOf(color: string, size: ButtonSize): IconStyle {\n return { color, size: ICON_SIZES[size] }\n}\n\n// The shadow a variant draws in its state: elevated rests at 1 and rises to 2\n// under a pointer, filled and tonal rest flat and rise to 1, and a press\n// brings each back to where it rests.\nfunction shadowOf(\n variant: ButtonVariant,\n {\n hovered,\n pressed,\n }: { readonly hovered: boolean; readonly pressed: boolean },\n isDisabled: boolean,\n theme: ResolvedTheme,\n): undefined | ViewStyle {\n const lifted = hovered && !pressed\n\n if (isDisabled) {\n return undefined\n }\n\n if (variant === 'elevated') {\n return shadowsOf(theme)[lifted ? 'elevation2' : 'elevation1']\n }\n\n return (variant === 'filled' || variant === 'tonal') && lifted\n ? shadowsOf(theme).elevation1\n : undefined\n}\n\nexport { Button }\nexport type { ButtonProps, ButtonShape, ButtonSize, ButtonVariant }\n"],"mappings":"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"}
1
+ {"version":3,"file":"index.js","names":["ReactNode","Ref","PressableProps","StyleProp","TextStyle","View","ViewStyle","AnimatedStyle","Text","NativeText","StyleSheet","useWindowDimensions","Animated","ButtonLinkForm","ButtonPressForm","ButtonToggleForm","PaletteName","IconStyle","ResolvedTheme","TypeRole","AnimatedPressable","buttonStyles","HEIGHTS","OUTLINE_WIDTHS","PRESSED_CORNERS","toggleState","useButtonAction","useCorner","palettesOf","BUSY","CONCEALED","PendingContent","PendingRing","pendingStyles","usePending","IconStyleContext","hitSlop","usePressFeedback","useTheme","composeStyles","themedStyles","useTypeRole","ButtonForm","variant","Exclude","ButtonVariant","ButtonProps","Omit","children","disableRipple","icon","isDisabled","ref","shape","ButtonShape","size","ButtonSize","style","ToggleVariant","DISABLED","Readonly","Record","elevated","filled","outlined","text","tonal","ICON_SIZES","lg","md","xl","xs","xxl","ROLES","SQUARE_CORNERS","const","TOGGLE_PALETTES","selected","unselected","styles","create","base","alignItems","flexDirection","justifyContent","maxWidth","flexShrink","label","textAlign","inlinePaddings","spacing","shadowsOf","shadows","elevation1","boxShadow","elevation2","sizesOf","theme","sizing","inline","gap","sm","minHeight","controlLg","paddingHorizontal","paddingVertical","controlSm","controlXl","controlXs","controlXxl","outlinedSizesOf","borderWidth","Button","t0","$","_c","defaultSelected","href","isSelected","onBlur","onChange","onFocus","onHoverIn","onHoverOut","onLayout","onLongPress","onPress","onPressIn","onPressOut","ownHitSlop","pendingLabel","props","t1","t2","t3","t4","t5","t6","type","isPending","undefined","role","fontScale","pending","ringLabel","isToggle","t7","action","colors","feedback","color","content","disabled","radii","resting","pill","shaped","pressed","T0","t8","t9","t10","t11","handlers","t12","t13","t14","t15","t16","container","shadowOf","corner","ring","t17","clip","t18","layer","t19","iconStyleOf","t20","hidden","t21","typography","t22","hovered","lifted","_c","NativeText"],"sources":["../../../src/components/button/index.tsx"],"sourcesContent":["import type { ReactNode, Ref } from 'react'\nimport type {\n PressableProps,\n StyleProp,\n TextStyle,\n View,\n ViewStyle,\n} from 'react-native'\nimport type { AnimatedStyle } from 'react-native-reanimated'\n\nimport {\n Text as NativeText,\n StyleSheet,\n useWindowDimensions,\n} from 'react-native'\nimport Animated from 'react-native-reanimated'\n\nimport type {\n ButtonLinkForm,\n ButtonPressForm,\n ButtonToggleForm,\n} from '../../button'\nimport type { PaletteName } from '../../button/palettes'\nimport type { IconStyle } from '../../glyphs/icon-style'\nimport type { ResolvedTheme } from '../../theme/scope'\nimport type { TypeRole } from '../../typography/roles'\n\nimport {\n AnimatedPressable,\n buttonStyles,\n HEIGHTS,\n OUTLINE_WIDTHS,\n PRESSED_CORNERS,\n toggleState,\n useButtonAction,\n useCorner,\n} from '../../button'\nimport { palettesOf } from '../../button/palettes'\nimport {\n BUSY,\n CONCEALED,\n PendingContent,\n PendingRing,\n pendingStyles,\n usePending,\n} from '../../button/pending'\nimport { IconStyleContext } from '../../glyphs/icon-style'\nimport { hitSlop, usePressFeedback } from '../../press'\nimport { useTheme } from '../../theme/scope'\nimport { composeStyles, themedStyles } from '../../theme/styles'\nimport { useTypeRole } from '../../typography/roles'\n\n// The buttons spec page's five colour styles, five sizes and two shapes, as\n// kanso-ui's Button draws them. The variant carries colour and the size\n// carries geometry, so the two never argue: the padding belongs to the size\n// alone, and a text button is as wide as a filled one at the same size.\n//\n// The colour pairs are the page's: filled on primary, tonal on secondary\n// container, outlined with an outline-variant rule and an on-surface-variant\n// label, text on primary, and elevated on surface container low with a\n// primary label. Elevated is the one variant whose shadow is part of it: it\n// rests at elevation 1, rises to 2 under a pointer and settles back while\n// pressed, where filled and tonal rest flat and lift to 1 under a pointer\n// only. The shadow is the theme's `boxShadow` value, which React Native draws\n// on iOS and Android as React Native Web draws it in a browser.\n//\n// The state layers, the ripple and the focus ring are src/press's, drawn in\n// the label's colour over the container, as on web.\n//\n// **Disabled is the page's colour at an opacity, translucent.** A container\n// is on-surface at the `disabledContainer` opacity, and the label on-surface\n// at `disabledContent`, over whatever the button sits on rather than mixed\n// over the surface role as web's are; src/button/palettes.ts gives the\n// reason. Disabled drops the shadow, since a shadow says a control is there\n// to press.\n//\n// **A toggle is the same button reporting a state.** Given `isSelected`,\n// `defaultSelected` or `onChange` it takes the page's second pair of colour\n// roles for its variant: a filled toggle rests on surface container with an\n// on-surface-variant label and takes primary once selected, a tonal one moves\n// from the secondary container pair to secondary, an elevated one keeps its\n// low surface until it takes primary, and an outlined one swaps its rule for\n// the inverse surface pair. The page gives text no pair, so a text button\n// given those props stays a plain one.\n//\n// **A pending button keeps its place.** Given `isPending` the label and the\n// icon are hidden where they stand, so the button keeps its width, and an\n// indeterminate ring is drawn over them in the label's colour, at the label's\n// type size times the device's text size, which is what web's `1em` reads.\n// The button keeps its focus and its ring and takes no press, so a double tap\n// cannot run the action twice: neither `onPress` nor `onLongPress` is called,\n// and a toggle keeps its state until it clears. It reports itself busy, and\n// src/button's pending.tsx says the change out loud.\n//\n// **The corner is a shape the button morphs between.** `round` rests as the\n// pill and `square` at the size's square corner: 12dp up to the page's S,\n// 16dp at M and 28dp above. A press tightens either to the size's pressed\n// corner, 8dp, 12dp or 16dp, and a toggle trades its shape for the other\n// once selected. The corner eases through Reanimated, as src/button's\n// `useCorner` sets out.\n//\n// The forms, the toggle's state, what a press does and the corner's ease are\n// src/button's, shared with IconButton.\n\ntype ButtonForm =\n | ButtonLinkForm\n | ButtonPressForm\n | (ButtonToggleForm & {\n /**\n * A toggle takes any variant but `text`, which the page gives no\n * selected colours.\n */\n readonly variant?: Exclude<ButtonVariant, 'text'>\n })\n\ntype ButtonProps = ButtonForm &\n Omit<PressableProps, 'children' | 'disabled' | 'style'> & {\n /** The label. */\n readonly children?: ReactNode\n /**\n * Draws no press ripple. The state layer is unaffected.\n * @default false\n */\n readonly disableRipple?: boolean\n /**\n * An icon before the label, at the page's icon size for the button's\n * size: 20dp at `xs` and `md`, 24dp at `lg`, 32dp at `xl` and 40dp at\n * `xxl`. The slot hands it the label's colour and that size through\n * `useIconStyle()`.\n */\n readonly icon?: ReactNode\n /**\n * Draws the button disabled, and takes no presses.\n * @default false\n */\n readonly isDisabled?: boolean\n readonly ref?: Ref<View>\n /**\n * The corner the button rests at: `round` is the pill, `square` the\n * page's rounded rectangle, 12dp up to `md`, 16dp at `lg` and 28dp above.\n * Either tightens while pressed, and a toggle trades one for the other\n * once selected.\n * @default 'round'\n */\n readonly shape?: ButtonShape\n /**\n * Control height: `xs` 32dp, `md` 40dp, `lg` 56dp, `xl` 96dp, `xxl` 136dp,\n * the buttons spec page's XS, S, M, L and XL, each with its own padding\n * and type role. `md` is the page's default. The height is a floor, so a\n * label that wraps, or that the device's text size enlarges, grows the\n * button rather than running out of it.\n * @default 'md'\n */\n readonly size?: ButtonSize\n readonly style?: StyleProp<ViewStyle>\n /**\n * How much weight the button pulls. `filled` and `tonal` carry a container\n * of their own; `outlined` and `text` sit on the page; `elevated` sits on\n * a low surface and lifts off it with a shadow, for a button that has to\n * separate from a busy background rather than from the page.\n * @default 'filled'\n */\n readonly variant?: ButtonVariant\n }\n\ntype ButtonShape = 'round' | 'square'\n\ntype ButtonSize = 'lg' | 'md' | 'xl' | 'xs' | 'xxl'\n\ntype ButtonVariant = 'elevated' | 'filled' | 'outlined' | 'text' | 'tonal'\n\ntype ToggleVariant = Exclude<ButtonVariant, 'text'>\n\n// The disabled container each variant draws. Filled, tonal and elevated share\n// one, which is the page's single disabled container for all three.\nconst DISABLED: Readonly<Record<ButtonVariant, PaletteName>> = {\n elevated: 'filledDisabled',\n filled: 'filledDisabled',\n outlined: 'outlinedDisabled',\n text: 'textDisabled',\n tonal: 'filledDisabled',\n}\n\n// The icon each size draws, from the page's size token sets. Literals, as on\n// web: they are icon sizes, which the theme has no scale for.\nconst ICON_SIZES: Readonly<Record<ButtonSize, number>> = {\n lg: 24,\n md: 20,\n xl: 32,\n xs: 20,\n xxl: 40,\n}\n\n// The type role each size sets its label in, taken whole: label-large for the\n// two small sizes, then title-medium, headline-small and headline-large.\nconst ROLES: Readonly<Record<ButtonSize, TypeRole>> = {\n lg: 'titleMedium',\n md: 'labelLarge',\n xl: 'headlineSmall',\n xs: 'labelLarge',\n xxl: 'headlineLarge',\n}\n\n// The square corner each size rests at, and a round toggle takes once\n// selected.\nconst SQUARE_CORNERS = {\n lg: 'lg',\n md: 'md',\n xl: 'xl',\n xs: 'md',\n xxl: 'xl',\n} as const satisfies Record<ButtonSize, keyof ResolvedTheme['radii']>\n\n// Which container a toggle draws, selected and not.\nconst TOGGLE_PALETTES: Readonly<\n Record<\n ToggleVariant,\n Readonly<Record<'selected' | 'unselected', PaletteName>>\n >\n> = {\n elevated: { selected: 'elevatedToggleSelected', unselected: 'elevated' },\n filled: { selected: 'filledToggleSelected', unselected: 'filledToggle' },\n outlined: { selected: 'outlinedToggleSelected', unselected: 'outlined' },\n tonal: { selected: 'tonalToggleSelected', unselected: 'tonal' },\n}\n\nconst styles = StyleSheet.create({\n // The label sits in the middle of a button wider than it, one stretched by\n // a column or given a width, as the page draws every button, and a button\n // is never wider than what holds it.\n base: {\n alignItems: 'center',\n flexDirection: 'row',\n justifyContent: 'center',\n maxWidth: '100%',\n },\n icon: {\n alignItems: 'center',\n flexShrink: 0,\n justifyContent: 'center',\n },\n // A label too long for the row wraps, its lines centred, and grows the\n // button with it.\n label: {\n flexShrink: 1,\n textAlign: 'center',\n },\n})\n\n// Each size's inline padding. The two largest are literals: 48 and 64 are not\n// steps of the spacing scale, and the scale should not grow to fit one\n// component. `xs` pads 12 a side, the extra-small token set's leading and\n// trailing space.\nfunction inlinePaddings({\n spacing,\n}: ResolvedTheme): Readonly<Record<ButtonSize, number>> {\n return { lg: spacing.xl, md: spacing.lg, xl: 48, xs: spacing.md, xxl: 64 }\n}\n\nconst shadowsOf = themedStyles(({ shadows }) =>\n StyleSheet.create({\n elevation1: { boxShadow: shadows.elevation1 },\n elevation2: { boxShadow: shadows.elevation2 },\n }),\n)\n\n// The five sizes, from the page's size token sets: the container height, the\n// padding, and the gap before an icon. The height is a floor rather than a\n// fixed size, and the block padding is what keeps a wrapped label off the\n// pill's edge: a step short of a single line's own inset, so a label on one\n// line still draws exactly the page's height.\nconst sizesOf = themedStyles((theme) => {\n const { sizing, spacing } = theme\n const inline = inlinePaddings(theme)\n\n return StyleSheet.create({\n lg: {\n gap: spacing.sm,\n minHeight: sizing.controlLg,\n paddingHorizontal: inline.lg,\n paddingVertical: spacing.md,\n },\n md: {\n gap: spacing.sm,\n minHeight: sizing.controlSm,\n paddingHorizontal: inline.md,\n paddingVertical: spacing.sm,\n },\n xl: {\n gap: spacing.md,\n minHeight: sizing.controlXl,\n paddingHorizontal: inline.xl,\n paddingVertical: spacing.xl,\n },\n xs: {\n gap: spacing.sm,\n minHeight: sizing.controlXs,\n paddingHorizontal: inline.xs,\n paddingVertical: spacing.xs,\n },\n xxl: {\n gap: spacing.lg,\n minHeight: sizing.controlXxl,\n paddingHorizontal: inline.xxl,\n paddingVertical: spacing.xxl,\n },\n })\n})\n\n// The outlined button draws its rule inside the width the other variants\n// take, as the page's buttons do: the padding gives up what the rule takes,\n// so an outlined and a filled button with one label are one width.\nconst outlinedSizesOf = themedStyles((theme) => {\n const inline = inlinePaddings(theme)\n\n function outlined(size: ButtonSize): ViewStyle {\n return {\n borderWidth: OUTLINE_WIDTHS[size],\n paddingHorizontal: inline[size] - OUTLINE_WIDTHS[size],\n }\n }\n\n return StyleSheet.create({\n lg: outlined('lg'),\n md: outlined('md'),\n xl: outlined('xl'),\n xs: outlined('xs'),\n xxl: outlined('xxl'),\n })\n})\n\n/**\n * The design's button, at five emphasis levels and five control heights,\n * round or square, with web's props and values. Given `href` it is a link with\n * the same appearance, and given `isSelected`, `defaultSelected` or\n * `onChange` it is a toggle, which reports its state to a screen reader and\n * draws the page's second pair of colour roles for its variant.\n *\n * ```tsx\n * <Button defaultSelected variant=\"tonal\">\n * Label\n * </Button>\n * ```\n *\n * A column stretches a button across it, as it does any view, and as a flex\n * column does a button on web; a column that should hold its buttons at their\n * labels' width says so with `alignItems`.\n *\n * The two sizes under 48dp tall, `xs` and `md`, take presses over a 48dp\n * target through `hitSlop`, which a `hitSlop` of the call site's own replaces.\n * `style`, `ref` and `testID` land on the `Pressable`.\n */\nfunction Button({\n children,\n defaultSelected,\n disableRipple = false,\n hitSlop: ownHitSlop,\n href,\n icon,\n isDisabled = false,\n isPending = false,\n isSelected,\n onBlur,\n onChange,\n onFocus,\n onHoverIn,\n onHoverOut,\n onLayout,\n onLongPress,\n onPress,\n onPressIn,\n onPressOut,\n pendingLabel,\n shape = 'round',\n size = 'md',\n style,\n type,\n variant = 'filled',\n ...props\n}: ButtonProps) {\n const theme = useTheme()\n const role = useTypeRole(ROLES[size])\n const { fontScale } = useWindowDimensions()\n // A link is never pending, as on web, where its props have no such state.\n const pending = href === undefined && isPending\n const ringLabel = usePending(pending, pendingLabel)\n\n // The three props that make this a toggle, read as web reads them. The\n // types keep them off a `text` button; the check here keeps a call site\n // that slipped past them a plain button.\n const isToggle =\n variant !== 'text' &&\n (defaultSelected !== undefined ||\n isSelected !== undefined ||\n onChange !== undefined)\n const action = useButtonAction({\n defaultSelected,\n href,\n isSelected,\n isToggle,\n onChange,\n onPress,\n type,\n })\n const colors =\n palettesOf(theme)[\n isDisabled\n ? DISABLED[variant]\n : variant !== 'text' && isToggle\n ? TOGGLE_PALETTES[variant][\n action.selected ? 'selected' : 'unselected'\n ]\n : variant\n ]\n\n const feedback = usePressFeedback({\n color: colors.content,\n disabled: isDisabled,\n disableRipple,\n onBlur,\n onFocus,\n onHoverIn,\n onHoverOut,\n onPressIn,\n onPressOut,\n pending,\n })\n\n const { radii } = theme\n const resting =\n (shape === 'square') !== action.selected\n ? radii[SQUARE_CORNERS[size]]\n : radii.pill\n const shaped = useCorner(\n feedback.pressed ? radii[PRESSED_CORNERS[size]] : resting,\n onLayout,\n )\n\n return (\n <AnimatedPressable\n role={href === undefined ? 'button' : 'link'}\n {...(isToggle ? toggleState(action.selected) : undefined)}\n {...(pending ? BUSY : undefined)}\n {...props}\n {...feedback.handlers}\n disabled={isDisabled}\n hitSlop={ownHitSlop ?? hitSlop(theme.sizing[HEIGHTS[size]])}\n onLayout={shaped.onLayout}\n onLongPress={pending ? undefined : onLongPress}\n onPress={pending ? undefined : action.onPress}\n style={composeStyles<AnimatedStyle<ViewStyle>>(\n styles.base,\n sizesOf(theme)[size],\n variant === 'outlined' ? outlinedSizesOf(theme)[size] : undefined,\n colors.container,\n shadowOf(variant, feedback, isDisabled, theme),\n shaped.corner,\n feedback.ring,\n style,\n )}\n >\n <Animated.View\n style={composeStyles<AnimatedStyle<ViewStyle>>(\n buttonStyles.clip,\n shaped.corner,\n )}\n >\n {feedback.layer}\n </Animated.View>\n {icon === undefined ? null : (\n <PendingContent isPending={pending}>\n <IconStyleContext value={iconStyleOf(colors.content, size)}>\n {icon}\n </IconStyleContext>\n </PendingContent>\n )}\n {children === undefined ? null : (\n <NativeText\n {...(pending ? CONCEALED : undefined)}\n style={composeStyles<TextStyle>(\n role,\n styles.label,\n colors.label,\n pending ? pendingStyles.hidden : undefined,\n )}\n >\n {children}\n </NativeText>\n )}\n {pending ? (\n <PendingRing\n color={colors.content}\n diameter={theme.typography[`${ROLES[size]}Size`] * fontScale}\n label={ringLabel}\n />\n ) : null}\n </AnimatedPressable>\n )\n}\n\nfunction iconStyleOf(color: string, size: ButtonSize): IconStyle {\n return { color, size: ICON_SIZES[size] }\n}\n\n// The shadow a variant draws in its state: elevated rests at 1 and rises to 2\n// under a pointer, filled and tonal rest flat and rise to 1, and a press\n// brings each back to where it rests.\nfunction shadowOf(\n variant: ButtonVariant,\n {\n hovered,\n pressed,\n }: { readonly hovered: boolean; readonly pressed: boolean },\n isDisabled: boolean,\n theme: ResolvedTheme,\n): undefined | ViewStyle {\n const lifted = hovered && !pressed\n\n if (isDisabled) {\n return undefined\n }\n\n if (variant === 'elevated') {\n return shadowsOf(theme)[lifted ? 'elevation2' : 'elevation1']\n }\n\n return (variant === 'filled' || variant === 'tonal') && lifted\n ? shadowsOf(theme).elevation1\n : undefined\n}\n\nexport { Button }\nexport type { ButtonProps, ButtonShape, ButtonSize, ButtonVariant }\n"],"mappings":"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"}
@@ -62,7 +62,7 @@ type IconButtonVariant = 'filled' | 'outlined' | 'standard' | 'tonal';
62
62
  * through `hitSlop`, which a `hitSlop` of the call site's own replaces.
63
63
  * `style`, `ref` and `testID` land on the `Pressable`.
64
64
  */
65
- declare function IconButton({ children, defaultSelected, disableRipple, hitSlop: ownHitSlop, href, isDisabled, isSelected, onBlur, onChange, onFocus, onHoverIn, onHoverOut, onLayout, onPress, onPressIn, onPressOut, size, style, type, variant, ...props }: IconButtonProps): import("react").JSX.Element;
65
+ declare function IconButton({ children, defaultSelected, disableRipple, hitSlop: ownHitSlop, href, isDisabled, isPending, isSelected, onBlur, onChange, onFocus, onHoverIn, onHoverOut, onLayout, onLongPress, onPress, onPressIn, onPressOut, pendingLabel, size, style, type, variant, ...props }: IconButtonProps): import("react").JSX.Element;
66
66
  //#endregion
67
67
  export { IconButton, type IconButtonProps, type IconButtonSize, type IconButtonVariant };
68
68
  //# sourceMappingURL=index.d.ts.map
@@ -3,6 +3,7 @@ import { useTheme } from "../../theme/scope.js";
3
3
  import { composeStyles, themedStyles } from "../../theme/styles.js";
4
4
  import { AnimatedPressable, HEIGHTS, OUTLINE_WIDTHS, PRESSED_CORNERS, buttonStyles, toggleState, useButtonAction, useCorner } from "../../button/index.js";
5
5
  import { palettesOf } from "../../button/palettes.js";
6
+ import { BUSY, PendingContent, PendingRing, usePending } from "../../button/pending.js";
6
7
  import { hitSlop, usePressFeedback } from "../../press/index.js";
7
8
  import { c } from "react/compiler-runtime";
8
9
  import { StyleSheet } from "react-native";
@@ -87,7 +88,7 @@ const sizesOf = themedStyles(({ sizing }) => {
87
88
  * `style`, `ref` and `testID` land on the `Pressable`.
88
89
  */
89
90
  function IconButton(t0) {
90
- const $ = c(58);
91
+ const $ = c(73);
91
92
  let children;
92
93
  let defaultSelected;
93
94
  let href;
@@ -98,19 +99,22 @@ function IconButton(t0) {
98
99
  let onHoverIn;
99
100
  let onHoverOut;
100
101
  let onLayout;
102
+ let onLongPress;
101
103
  let onPress;
102
104
  let onPressIn;
103
105
  let onPressOut;
104
106
  let ownHitSlop;
107
+ let pendingLabel;
105
108
  let props;
106
109
  let style;
107
110
  let t1;
108
111
  let t2;
109
112
  let t3;
110
113
  let t4;
114
+ let t5;
111
115
  let type;
112
116
  if ($[0] !== t0) {
113
- ({children, defaultSelected, disableRipple: t1, hitSlop: ownHitSlop, href, isDisabled: t2, isSelected, onBlur, onChange, onFocus, onHoverIn, onHoverOut, onLayout, onPress, onPressIn, onPressOut, size: t3, style, type, variant: t4, ...props} = t0);
117
+ ({children, defaultSelected, disableRipple: t1, hitSlop: ownHitSlop, href, isDisabled: t2, isPending: t3, isSelected, onBlur, onChange, onFocus, onHoverIn, onHoverOut, onLayout, onLongPress, onPress, onPressIn, onPressOut, pendingLabel, size: t4, style, type, variant: t5, ...props} = t0);
114
118
  $[0] = t0;
115
119
  $[1] = children;
116
120
  $[2] = defaultSelected;
@@ -122,17 +126,20 @@ function IconButton(t0) {
122
126
  $[8] = onHoverIn;
123
127
  $[9] = onHoverOut;
124
128
  $[10] = onLayout;
125
- $[11] = onPress;
126
- $[12] = onPressIn;
127
- $[13] = onPressOut;
128
- $[14] = ownHitSlop;
129
- $[15] = props;
130
- $[16] = style;
131
- $[17] = t1;
132
- $[18] = t2;
133
- $[19] = t3;
134
- $[20] = t4;
135
- $[21] = type;
129
+ $[11] = onLongPress;
130
+ $[12] = onPress;
131
+ $[13] = onPressIn;
132
+ $[14] = onPressOut;
133
+ $[15] = ownHitSlop;
134
+ $[16] = pendingLabel;
135
+ $[17] = props;
136
+ $[18] = style;
137
+ $[19] = t1;
138
+ $[20] = t2;
139
+ $[21] = t3;
140
+ $[22] = t4;
141
+ $[23] = t5;
142
+ $[24] = type;
136
143
  } else {
137
144
  children = $[1];
138
145
  defaultSelected = $[2];
@@ -144,27 +151,33 @@ function IconButton(t0) {
144
151
  onHoverIn = $[8];
145
152
  onHoverOut = $[9];
146
153
  onLayout = $[10];
147
- onPress = $[11];
148
- onPressIn = $[12];
149
- onPressOut = $[13];
150
- ownHitSlop = $[14];
151
- props = $[15];
152
- style = $[16];
153
- t1 = $[17];
154
- t2 = $[18];
155
- t3 = $[19];
156
- t4 = $[20];
157
- type = $[21];
154
+ onLongPress = $[11];
155
+ onPress = $[12];
156
+ onPressIn = $[13];
157
+ onPressOut = $[14];
158
+ ownHitSlop = $[15];
159
+ pendingLabel = $[16];
160
+ props = $[17];
161
+ style = $[18];
162
+ t1 = $[19];
163
+ t2 = $[20];
164
+ t3 = $[21];
165
+ t4 = $[22];
166
+ t5 = $[23];
167
+ type = $[24];
158
168
  }
159
169
  const disableRipple = t1 === void 0 ? false : t1;
160
170
  const isDisabled = t2 === void 0 ? false : t2;
161
- const size = t3 === void 0 ? "md" : t3;
162
- const variant = t4 === void 0 ? "standard" : t4;
171
+ const isPending = t3 === void 0 ? false : t3;
172
+ const size = t4 === void 0 ? "md" : t4;
173
+ const variant = t5 === void 0 ? "standard" : t5;
163
174
  const theme = useTheme();
175
+ const pending = href === void 0 && isPending;
176
+ const ringLabel = usePending(pending, pendingLabel);
164
177
  const isToggle = defaultSelected !== void 0 || isSelected !== void 0 || onChange !== void 0;
165
- let t5;
166
- if ($[22] !== defaultSelected || $[23] !== href || $[24] !== isSelected || $[25] !== isToggle || $[26] !== onChange || $[27] !== onPress || $[28] !== type) {
167
- t5 = {
178
+ let t6;
179
+ if ($[25] !== defaultSelected || $[26] !== href || $[27] !== isSelected || $[28] !== isToggle || $[29] !== onChange || $[30] !== onPress || $[31] !== type) {
180
+ t6 = {
168
181
  defaultSelected,
169
182
  href,
170
183
  isSelected,
@@ -173,16 +186,16 @@ function IconButton(t0) {
173
186
  onPress,
174
187
  type
175
188
  };
176
- $[22] = defaultSelected;
177
- $[23] = href;
178
- $[24] = isSelected;
179
- $[25] = isToggle;
180
- $[26] = onChange;
181
- $[27] = onPress;
182
- $[28] = type;
183
- $[29] = t5;
184
- } else t5 = $[29];
185
- const action = useButtonAction(t5);
189
+ $[25] = defaultSelected;
190
+ $[26] = href;
191
+ $[27] = isSelected;
192
+ $[28] = isToggle;
193
+ $[29] = onChange;
194
+ $[30] = onPress;
195
+ $[31] = type;
196
+ $[32] = t6;
197
+ } else t6 = $[32];
198
+ const action = useButtonAction(t6);
186
199
  const colors = palettesOf(theme)[isDisabled ? DISABLED[variant] : isToggle ? TOGGLE_PALETTES[variant][action.selected ? "selected" : "unselected"] : variant];
187
200
  const feedback = usePressFeedback({
188
201
  color: colors.content,
@@ -193,89 +206,126 @@ function IconButton(t0) {
193
206
  onHoverIn,
194
207
  onHoverOut,
195
208
  onPressIn,
196
- onPressOut
209
+ onPressOut,
210
+ pending
197
211
  });
198
212
  const { radii, sizing } = theme;
199
213
  const edge = sizing[HEIGHTS[size]];
200
214
  const shaped = useCorner(feedback.pressed || action.selected ? radii[PRESSED_CORNERS[size]] : radii.pill, onLayout);
201
215
  const T0 = AnimatedPressable;
202
- const t6 = href === void 0 ? "button" : "link";
203
- let t7;
204
- if ($[30] !== action.selected || $[31] !== isToggle) {
205
- t7 = isToggle ? toggleState(action.selected) : void 0;
206
- $[30] = action.selected;
207
- $[31] = isToggle;
208
- $[32] = t7;
209
- } else t7 = $[32];
210
- const t8 = feedback.handlers;
211
- let t9;
212
- if ($[33] !== edge || $[34] !== ownHitSlop) {
213
- t9 = ownHitSlop ?? hitSlop(edge, edge);
214
- $[33] = edge;
215
- $[34] = ownHitSlop;
216
- $[35] = t9;
217
- } else t9 = $[35];
218
- const t10 = shaped.onLayout;
219
- const t11 = action.onPress;
220
- const t12 = composeStyles(styles.base, sizesOf(theme)[size], variant === "outlined" ? outlineWidths[size] : void 0, colors.container, shaped.corner, feedback.ring, style);
221
- let t13;
222
- if ($[36] !== shaped.corner) {
223
- t13 = composeStyles(buttonStyles.clip, shaped.corner);
224
- $[36] = shaped.corner;
225
- $[37] = t13;
226
- } else t13 = $[37];
227
- let t14;
228
- if ($[38] !== feedback.layer || $[39] !== t13) {
229
- t14 = /* @__PURE__ */ jsx(Animated.View, {
230
- style: t13,
216
+ const t7 = href === void 0 ? "button" : "link";
217
+ let t8;
218
+ if ($[33] !== action || $[34] !== isToggle) {
219
+ t8 = isToggle ? toggleState(action.selected) : void 0;
220
+ $[33] = action;
221
+ $[34] = isToggle;
222
+ $[35] = t8;
223
+ } else t8 = $[35];
224
+ const t9 = pending ? BUSY : void 0;
225
+ const t10 = feedback.handlers;
226
+ let t11;
227
+ if ($[36] !== edge || $[37] !== ownHitSlop) {
228
+ t11 = ownHitSlop ?? hitSlop(edge, edge);
229
+ $[36] = edge;
230
+ $[37] = ownHitSlop;
231
+ $[38] = t11;
232
+ } else t11 = $[38];
233
+ const t12 = shaped.onLayout;
234
+ const t13 = pending ? void 0 : onLongPress;
235
+ const t14 = pending ? void 0 : action.onPress;
236
+ const t15 = composeStyles(styles.base, sizesOf(theme)[size], variant === "outlined" ? outlineWidths[size] : void 0, colors.container, shaped.corner, feedback.ring, style);
237
+ let t16;
238
+ if ($[39] !== shaped.corner) {
239
+ t16 = composeStyles(buttonStyles.clip, shaped.corner);
240
+ $[39] = shaped.corner;
241
+ $[40] = t16;
242
+ } else t16 = $[40];
243
+ let t17;
244
+ if ($[41] !== feedback.layer || $[42] !== t16) {
245
+ t17 = /* @__PURE__ */ jsx(Animated.View, {
246
+ style: t16,
231
247
  children: feedback.layer
232
248
  });
233
- $[38] = feedback.layer;
234
- $[39] = t13;
235
- $[40] = t14;
236
- } else t14 = $[40];
237
- const T1 = IconStyleContext;
238
- const t15 = iconStyleOf(colors.content, size);
239
- let t16;
240
- if ($[41] !== T1 || $[42] !== children || $[43] !== t15) {
241
- t16 = /* @__PURE__ */ jsx(T1, {
242
- value: t15,
249
+ $[41] = feedback.layer;
250
+ $[42] = t16;
251
+ $[43] = t17;
252
+ } else t17 = $[43];
253
+ const T1 = PendingContent;
254
+ const T2 = IconStyleContext;
255
+ const t18 = iconStyleOf(colors.content, size);
256
+ let t19;
257
+ if ($[44] !== T2 || $[45] !== children || $[46] !== t18) {
258
+ t19 = /* @__PURE__ */ jsx(T2, {
259
+ value: t18,
243
260
  children
244
261
  });
245
- $[41] = T1;
246
- $[42] = children;
247
- $[43] = t15;
248
- $[44] = t16;
249
- } else t16 = $[44];
250
- let t17;
251
- if ($[45] !== T0 || $[46] !== action.onPress || $[47] !== feedback.handlers || $[48] !== isDisabled || $[49] !== props || $[50] !== shaped.onLayout || $[51] !== t12 || $[52] !== t14 || $[53] !== t16 || $[54] !== t6 || $[55] !== t7 || $[56] !== t9) {
252
- t17 = /* @__PURE__ */ jsxs(T0, {
253
- role: t6,
254
- ...t7,
255
- ...props,
262
+ $[44] = T2;
263
+ $[45] = children;
264
+ $[46] = t18;
265
+ $[47] = t19;
266
+ } else t19 = $[47];
267
+ let t20;
268
+ if ($[48] !== T1 || $[49] !== pending || $[50] !== t19) {
269
+ t20 = /* @__PURE__ */ jsx(T1, {
270
+ isPending: pending,
271
+ children: t19
272
+ });
273
+ $[48] = T1;
274
+ $[49] = pending;
275
+ $[50] = t19;
276
+ $[51] = t20;
277
+ } else t20 = $[51];
278
+ let t21;
279
+ if ($[52] !== colors || $[53] !== pending || $[54] !== ringLabel || $[55] !== size) {
280
+ t21 = pending ? /* @__PURE__ */ jsx(PendingRing, {
281
+ color: colors.content,
282
+ diameter: ICON_SIZES[size],
283
+ label: ringLabel
284
+ }) : null;
285
+ $[52] = colors;
286
+ $[53] = pending;
287
+ $[54] = ringLabel;
288
+ $[55] = size;
289
+ $[56] = t21;
290
+ } else t21 = $[56];
291
+ let t22;
292
+ if ($[57] !== T0 || $[58] !== feedback.handlers || $[59] !== isDisabled || $[60] !== props || $[61] !== shaped.onLayout || $[62] !== t11 || $[63] !== t13 || $[64] !== t14 || $[65] !== t15 || $[66] !== t17 || $[67] !== t20 || $[68] !== t21 || $[69] !== t7 || $[70] !== t8 || $[71] !== t9) {
293
+ t22 = /* @__PURE__ */ jsxs(T0, {
294
+ role: t7,
256
295
  ...t8,
296
+ ...t9,
297
+ ...props,
298
+ ...t10,
257
299
  disabled: isDisabled,
258
- hitSlop: t9,
259
- onLayout: t10,
260
- onPress: t11,
261
- style: t12,
262
- children: [t14, t16]
300
+ hitSlop: t11,
301
+ onLayout: t12,
302
+ onLongPress: t13,
303
+ onPress: t14,
304
+ style: t15,
305
+ children: [
306
+ t17,
307
+ t20,
308
+ t21
309
+ ]
263
310
  });
264
- $[45] = T0;
265
- $[46] = action.onPress;
266
- $[47] = feedback.handlers;
267
- $[48] = isDisabled;
268
- $[49] = props;
269
- $[50] = shaped.onLayout;
270
- $[51] = t12;
271
- $[52] = t14;
272
- $[53] = t16;
273
- $[54] = t6;
274
- $[55] = t7;
275
- $[56] = t9;
276
- $[57] = t17;
277
- } else t17 = $[57];
278
- return t17;
311
+ $[57] = T0;
312
+ $[58] = feedback.handlers;
313
+ $[59] = isDisabled;
314
+ $[60] = props;
315
+ $[61] = shaped.onLayout;
316
+ $[62] = t11;
317
+ $[63] = t13;
318
+ $[64] = t14;
319
+ $[65] = t15;
320
+ $[66] = t17;
321
+ $[67] = t20;
322
+ $[68] = t21;
323
+ $[69] = t7;
324
+ $[70] = t8;
325
+ $[71] = t9;
326
+ $[72] = t22;
327
+ } else t22 = $[72];
328
+ return t22;
279
329
  }
280
330
  function iconStyleOf(color, size) {
281
331
  return {
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","names":["ReactNode","Ref","PressableProps","StyleProp","View","ViewStyle","AnimatedStyle","StyleSheet","Animated","ButtonLinkForm","ButtonPressForm","ButtonToggleForm","PaletteName","IconStyle","AnimatedPressable","buttonStyles","HEIGHTS","OUTLINE_WIDTHS","PRESSED_CORNERS","toggleState","useButtonAction","useCorner","palettesOf","IconStyleContext","hitSlop","usePressFeedback","useTheme","composeStyles","themedStyles","IconButtonProps","Omit","children","disableRipple","isDisabled","ref","size","IconButtonSize","style","variant","IconButtonVariant","DISABLED","Readonly","Record","filled","outlined","standard","tonal","ICON_SIZES","lg","md","xl","xs","xxl","TOGGLE_PALETTES","selected","unselected","styles","create","base","alignItems","flexShrink","justifyContent","outlineWidths","borderWidth","sizesOf","sizing","square","edge","height","width","IconButton","t0","$","_c","defaultSelected","href","isSelected","onBlur","onChange","onFocus","onHoverIn","onHoverOut","onLayout","onPress","onPressIn","onPressOut","ownHitSlop","props","t1","t2","t3","t4","type","undefined","theme","isToggle","t5","action","colors","feedback","color","content","disabled","radii","shaped","pressed","pill","T0","t6","t7","t8","handlers","t9","t10","t11","t12","container","corner","ring","t13","clip","t14","layer","T1","t15","iconStyleOf","t16","t17","_c"],"sources":["../../../src/components/icon-button/index.tsx"],"sourcesContent":["import type { ReactNode, Ref } from 'react'\nimport type { PressableProps, StyleProp, View, ViewStyle } from 'react-native'\nimport type { AnimatedStyle } from 'react-native-reanimated'\n\nimport { StyleSheet } from 'react-native'\nimport Animated from 'react-native-reanimated'\n\nimport type {\n ButtonLinkForm,\n ButtonPressForm,\n ButtonToggleForm,\n} from '../../button'\nimport type { PaletteName } from '../../button/palettes'\nimport type { IconStyle } from '../../glyphs/icon-style'\n\nimport {\n AnimatedPressable,\n buttonStyles,\n HEIGHTS,\n OUTLINE_WIDTHS,\n PRESSED_CORNERS,\n toggleState,\n useButtonAction,\n useCorner,\n} from '../../button'\nimport { palettesOf } from '../../button/palettes'\nimport { IconStyleContext } from '../../glyphs/icon-style'\nimport { hitSlop, usePressFeedback } from '../../press'\nimport { useTheme } from '../../theme/scope'\nimport { composeStyles, themedStyles } from '../../theme/styles'\n\n// The icon buttons spec page's four styles at its five sizes, as kanso-ui's\n// IconButton draws them: Button's chrome around a single icon. The pairs are\n// the page's: filled on primary, tonal on secondary container, outlined with\n// an outline-variant rule and an on-surface-variant icon, and standard,\n// transparent, with the same icon over whatever it sits on. Disabled is\n// Button's, on-surface at the two disabled opacities, and a standard button\n// takes the text button's colour since neither has a container.\n//\n// The sizes are the page's XS to XL at Button's five heights, so the two line\n// up in a row: a square of 32, 40, 56, 96 or 136dp holding an icon of 20, 24,\n// 24, 32 or 40dp. The two middle sizes share one icon, and the container\n// alone grows between them. The two smallest take presses over a 48dp target\n// through `hitSlop`, which is the page's floor for them.\n//\n// **A toggle is the same button reporting a state.** Given `isSelected`,\n// `defaultSelected` or `onChange` it takes the page's second pair of colour\n// roles for its variant: a filled toggle rests on surface container with an\n// on-surface-variant icon and takes primary once selected, a tonal one moves\n// from the secondary container pair to secondary, a standard one stays\n// transparent while its icon moves to primary, and an outlined one swaps its\n// rule for the inverse surface pair. So a selected filled toggle looks like a\n// plain filled button, and an unselected one does not.\n//\n// **The corner morphs from a circle to a rounded square.** A press tightens\n// it to the size's pressed corner, 8dp for the two small sizes, 12dp at\n// `lg` and 16dp at the two large, and a selected toggle rests there, which is\n// the page's round-to-square morph. It eases as Button's does.\n//\n// The forms, the toggle's state, what a press does and the corner's ease are\n// src/button's, shared with Button.\n\ntype IconButtonProps = (ButtonLinkForm | ButtonPressForm | ButtonToggleForm) &\n Omit<PressableProps, 'aria-label' | 'children' | 'disabled' | 'style'> & {\n /**\n * What the button does, in words. Required rather than optional: an icon\n * on its own has no accessible name, so without this the control\n * announces nothing at all.\n */\n readonly 'aria-label': string\n /**\n * The icon. The button hands it its colour and the page's icon size for\n * the button's size through `useIconStyle()`.\n */\n readonly children?: ReactNode\n /**\n * Draws no press ripple. The state layer is unaffected.\n * @default false\n */\n readonly disableRipple?: boolean\n /**\n * Draws the button disabled, and takes no presses.\n * @default false\n */\n readonly isDisabled?: boolean\n readonly ref?: Ref<View>\n /**\n * Control size: `xs` 32dp, `md` 40dp, `lg` 56dp, `xl` 96dp, `xxl` 136dp,\n * the icon buttons spec page's XS to XL, and the same heights `Button`\n * uses, so the two line up beside each other in a row. The icon is 20dp,\n * 24dp, 24dp, 32dp and 40dp in turn.\n * @default 'md'\n */\n readonly size?: IconButtonSize\n readonly style?: StyleProp<ViewStyle>\n /**\n * `standard` is transparent and tints what it sits on; `outlined` is\n * transparent with a rule around it; `filled` and `tonal` carry a\n * container of their own.\n * @default 'standard'\n */\n readonly variant?: IconButtonVariant\n }\n\ntype IconButtonSize = 'lg' | 'md' | 'xl' | 'xs' | 'xxl'\n\ntype IconButtonVariant = 'filled' | 'outlined' | 'standard' | 'tonal'\n\n// The disabled container each variant draws. Filled and tonal share the\n// page's one disabled container, and standard draws the text button's\n// colour, which is the icon alone.\nconst DISABLED: Readonly<Record<IconButtonVariant, PaletteName>> = {\n filled: 'filledDisabled',\n outlined: 'outlinedDisabled',\n standard: 'textDisabled',\n tonal: 'filledDisabled',\n}\n\n// The icon each size holds, from the page's size token sets. Literals, as on\n// web: they are icon sizes, which the theme has no scale for.\nconst ICON_SIZES: Readonly<Record<IconButtonSize, number>> = {\n lg: 24,\n md: 24,\n xl: 32,\n xs: 20,\n xxl: 40,\n}\n\n// Which container a toggle draws, selected and not. An unselected outlined,\n// standard or tonal toggle is the plain button of that variant.\nconst TOGGLE_PALETTES: Readonly<\n Record<\n IconButtonVariant,\n Readonly<Record<'selected' | 'unselected', PaletteName>>\n >\n> = {\n filled: { selected: 'filledToggleSelected', unselected: 'filledToggle' },\n outlined: { selected: 'outlinedToggleSelected', unselected: 'outlined' },\n standard: { selected: 'standardToggleSelected', unselected: 'standard' },\n tonal: { selected: 'tonalToggleSelected', unselected: 'tonal' },\n}\n\nconst styles = StyleSheet.create({\n // The icon sits in the middle of a square that a row never squeezes.\n base: {\n alignItems: 'center',\n flexShrink: 0,\n justifyContent: 'center',\n },\n})\n\n// The outlined rule's width at each size, Button's.\nconst outlineWidths = StyleSheet.create({\n lg: { borderWidth: OUTLINE_WIDTHS.lg },\n md: { borderWidth: OUTLINE_WIDTHS.md },\n xl: { borderWidth: OUTLINE_WIDTHS.xl },\n xs: { borderWidth: OUTLINE_WIDTHS.xs },\n xxl: { borderWidth: OUTLINE_WIDTHS.xxl },\n})\n\n// Square, so one control height sets both edges.\nconst sizesOf = themedStyles(({ sizing }) => {\n function square(size: IconButtonSize): ViewStyle {\n const edge = sizing[HEIGHTS[size]]\n\n return { height: edge, width: edge }\n }\n\n return StyleSheet.create({\n lg: square('lg'),\n md: square('md'),\n xl: square('xl'),\n xs: square('xs'),\n xxl: square('xxl'),\n })\n})\n\n/**\n * A button that is an icon, at five control heights, with web's props and\n * values. Given `href` it is a link with the same appearance, and given\n * `isSelected`, `defaultSelected` or `onChange` it is a toggle, which reports\n * its state to a screen reader and draws the page's second pair of colour\n * roles for its variant. The three forms are exclusive, so a toggle given\n * `href` does not compile.\n *\n * ```tsx\n * <IconButton aria-label=\"Label\" defaultSelected variant=\"tonal\">\n * <Icon />\n * </IconButton>\n * ```\n *\n * The two sizes under 48dp, `xs` and `md`, take presses over a 48dp target\n * through `hitSlop`, which a `hitSlop` of the call site's own replaces.\n * `style`, `ref` and `testID` land on the `Pressable`.\n */\nfunction IconButton({\n children,\n defaultSelected,\n disableRipple = false,\n hitSlop: ownHitSlop,\n href,\n isDisabled = false,\n isSelected,\n onBlur,\n onChange,\n onFocus,\n onHoverIn,\n onHoverOut,\n onLayout,\n onPress,\n onPressIn,\n onPressOut,\n size = 'md',\n style,\n type,\n variant = 'standard',\n ...props\n}: IconButtonProps) {\n const theme = useTheme()\n\n // The three props that make this a toggle, read as web reads them.\n const isToggle =\n defaultSelected !== undefined ||\n isSelected !== undefined ||\n onChange !== undefined\n const action = useButtonAction({\n defaultSelected,\n href,\n isSelected,\n isToggle,\n onChange,\n onPress,\n type,\n })\n const colors =\n palettesOf(theme)[\n isDisabled\n ? DISABLED[variant]\n : isToggle\n ? TOGGLE_PALETTES[variant][\n action.selected ? 'selected' : 'unselected'\n ]\n : variant\n ]\n\n const feedback = usePressFeedback({\n color: colors.content,\n disabled: isDisabled,\n disableRipple,\n onBlur,\n onFocus,\n onHoverIn,\n onHoverOut,\n onPressIn,\n onPressOut,\n })\n\n const { radii, sizing } = theme\n const edge = sizing[HEIGHTS[size]]\n const shaped = useCorner(\n feedback.pressed || action.selected\n ? radii[PRESSED_CORNERS[size]]\n : radii.pill,\n onLayout,\n )\n\n return (\n <AnimatedPressable\n role={href === undefined ? 'button' : 'link'}\n {...(isToggle ? toggleState(action.selected) : undefined)}\n {...props}\n {...feedback.handlers}\n disabled={isDisabled}\n hitSlop={ownHitSlop ?? hitSlop(edge, edge)}\n onLayout={shaped.onLayout}\n onPress={action.onPress}\n style={composeStyles<AnimatedStyle<ViewStyle>>(\n styles.base,\n sizesOf(theme)[size],\n variant === 'outlined' ? outlineWidths[size] : undefined,\n colors.container,\n shaped.corner,\n feedback.ring,\n style,\n )}\n >\n <Animated.View\n style={composeStyles<AnimatedStyle<ViewStyle>>(\n buttonStyles.clip,\n shaped.corner,\n )}\n >\n {feedback.layer}\n </Animated.View>\n <IconStyleContext value={iconStyleOf(colors.content, size)}>\n {children}\n </IconStyleContext>\n </AnimatedPressable>\n )\n}\n\nfunction iconStyleOf(color: string, size: IconButtonSize): IconStyle {\n return { color, size: ICON_SIZES[size] }\n}\n\nexport { IconButton }\nexport type { IconButtonProps, IconButtonSize, IconButtonVariant }\n"],"mappings":"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"}
1
+ {"version":3,"file":"index.js","names":["ReactNode","Ref","PressableProps","StyleProp","View","ViewStyle","AnimatedStyle","StyleSheet","Animated","ButtonLinkForm","ButtonPressForm","ButtonToggleForm","PaletteName","IconStyle","AnimatedPressable","buttonStyles","HEIGHTS","OUTLINE_WIDTHS","PRESSED_CORNERS","toggleState","useButtonAction","useCorner","palettesOf","BUSY","PendingContent","PendingRing","usePending","IconStyleContext","hitSlop","usePressFeedback","useTheme","composeStyles","themedStyles","IconButtonProps","Omit","children","disableRipple","isDisabled","ref","size","IconButtonSize","style","variant","IconButtonVariant","DISABLED","Readonly","Record","filled","outlined","standard","tonal","ICON_SIZES","lg","md","xl","xs","xxl","TOGGLE_PALETTES","selected","unselected","styles","create","base","alignItems","flexShrink","justifyContent","outlineWidths","borderWidth","sizesOf","sizing","square","edge","height","width","IconButton","t0","$","_c","defaultSelected","href","isSelected","onBlur","onChange","onFocus","onHoverIn","onHoverOut","onLayout","onLongPress","onPress","onPressIn","onPressOut","ownHitSlop","pendingLabel","props","t1","t2","t3","t4","t5","type","isPending","undefined","theme","pending","ringLabel","isToggle","t6","action","colors","feedback","color","content","disabled","radii","shaped","pressed","pill","T0","t7","t8","t9","t10","handlers","t11","t12","t13","t14","t15","container","corner","ring","t16","clip","t17","layer","T1","T2","t18","iconStyleOf","t19","t20","t21","t22","_c"],"sources":["../../../src/components/icon-button/index.tsx"],"sourcesContent":["import type { ReactNode, Ref } from 'react'\nimport type { PressableProps, StyleProp, View, ViewStyle } from 'react-native'\nimport type { AnimatedStyle } from 'react-native-reanimated'\n\nimport { StyleSheet } from 'react-native'\nimport Animated from 'react-native-reanimated'\n\nimport type {\n ButtonLinkForm,\n ButtonPressForm,\n ButtonToggleForm,\n} from '../../button'\nimport type { PaletteName } from '../../button/palettes'\nimport type { IconStyle } from '../../glyphs/icon-style'\n\nimport {\n AnimatedPressable,\n buttonStyles,\n HEIGHTS,\n OUTLINE_WIDTHS,\n PRESSED_CORNERS,\n toggleState,\n useButtonAction,\n useCorner,\n} from '../../button'\nimport { palettesOf } from '../../button/palettes'\nimport {\n BUSY,\n PendingContent,\n PendingRing,\n usePending,\n} from '../../button/pending'\nimport { IconStyleContext } from '../../glyphs/icon-style'\nimport { hitSlop, usePressFeedback } from '../../press'\nimport { useTheme } from '../../theme/scope'\nimport { composeStyles, themedStyles } from '../../theme/styles'\n\n// The icon buttons spec page's four styles at its five sizes, as kanso-ui's\n// IconButton draws them: Button's chrome around a single icon. The pairs are\n// the page's: filled on primary, tonal on secondary container, outlined with\n// an outline-variant rule and an on-surface-variant icon, and standard,\n// transparent, with the same icon over whatever it sits on. Disabled is\n// Button's, on-surface at the two disabled opacities, and a standard button\n// takes the text button's colour since neither has a container.\n//\n// The sizes are the page's XS to XL at Button's five heights, so the two line\n// up in a row: a square of 32, 40, 56, 96 or 136dp holding an icon of 20, 24,\n// 24, 32 or 40dp. The two middle sizes share one icon, and the container\n// alone grows between them. The two smallest take presses over a 48dp target\n// through `hitSlop`, which is the page's floor for them.\n//\n// **A toggle is the same button reporting a state.** Given `isSelected`,\n// `defaultSelected` or `onChange` it takes the page's second pair of colour\n// roles for its variant: a filled toggle rests on surface container with an\n// on-surface-variant icon and takes primary once selected, a tonal one moves\n// from the secondary container pair to secondary, a standard one stays\n// transparent while its icon moves to primary, and an outlined one swaps its\n// rule for the inverse surface pair. So a selected filled toggle looks like a\n// plain filled button, and an unselected one does not.\n//\n// **A pending button keeps its place**, as Button's does: the icon is hidden\n// where it stands and an indeterminate ring is drawn over it, in the icon's\n// colour and at the icon's size, which is what web's `1em` reads there. The\n// button keeps its focus and its ring, reports itself busy and takes no\n// press until it clears, and src/button's pending.tsx says the change out\n// loud.\n//\n// **The corner morphs from a circle to a rounded square.** A press tightens\n// it to the size's pressed corner, 8dp for the two small sizes, 12dp at\n// `lg` and 16dp at the two large, and a selected toggle rests there, which is\n// the page's round-to-square morph. It eases as Button's does.\n//\n// The forms, the toggle's state, what a press does and the corner's ease are\n// src/button's, shared with Button.\n\ntype IconButtonProps = (ButtonLinkForm | ButtonPressForm | ButtonToggleForm) &\n Omit<PressableProps, 'aria-label' | 'children' | 'disabled' | 'style'> & {\n /**\n * What the button does, in words. Required rather than optional: an icon\n * on its own has no accessible name, so without this the control\n * announces nothing at all.\n */\n readonly 'aria-label': string\n /**\n * The icon. The button hands it its colour and the page's icon size for\n * the button's size through `useIconStyle()`.\n */\n readonly children?: ReactNode\n /**\n * Draws no press ripple. The state layer is unaffected.\n * @default false\n */\n readonly disableRipple?: boolean\n /**\n * Draws the button disabled, and takes no presses.\n * @default false\n */\n readonly isDisabled?: boolean\n readonly ref?: Ref<View>\n /**\n * Control size: `xs` 32dp, `md` 40dp, `lg` 56dp, `xl` 96dp, `xxl` 136dp,\n * the icon buttons spec page's XS to XL, and the same heights `Button`\n * uses, so the two line up beside each other in a row. The icon is 20dp,\n * 24dp, 24dp, 32dp and 40dp in turn.\n * @default 'md'\n */\n readonly size?: IconButtonSize\n readonly style?: StyleProp<ViewStyle>\n /**\n * `standard` is transparent and tints what it sits on; `outlined` is\n * transparent with a rule around it; `filled` and `tonal` carry a\n * container of their own.\n * @default 'standard'\n */\n readonly variant?: IconButtonVariant\n }\n\ntype IconButtonSize = 'lg' | 'md' | 'xl' | 'xs' | 'xxl'\n\ntype IconButtonVariant = 'filled' | 'outlined' | 'standard' | 'tonal'\n\n// The disabled container each variant draws. Filled and tonal share the\n// page's one disabled container, and standard draws the text button's\n// colour, which is the icon alone.\nconst DISABLED: Readonly<Record<IconButtonVariant, PaletteName>> = {\n filled: 'filledDisabled',\n outlined: 'outlinedDisabled',\n standard: 'textDisabled',\n tonal: 'filledDisabled',\n}\n\n// The icon each size holds, from the page's size token sets. Literals, as on\n// web: they are icon sizes, which the theme has no scale for.\nconst ICON_SIZES: Readonly<Record<IconButtonSize, number>> = {\n lg: 24,\n md: 24,\n xl: 32,\n xs: 20,\n xxl: 40,\n}\n\n// Which container a toggle draws, selected and not. An unselected outlined,\n// standard or tonal toggle is the plain button of that variant.\nconst TOGGLE_PALETTES: Readonly<\n Record<\n IconButtonVariant,\n Readonly<Record<'selected' | 'unselected', PaletteName>>\n >\n> = {\n filled: { selected: 'filledToggleSelected', unselected: 'filledToggle' },\n outlined: { selected: 'outlinedToggleSelected', unselected: 'outlined' },\n standard: { selected: 'standardToggleSelected', unselected: 'standard' },\n tonal: { selected: 'tonalToggleSelected', unselected: 'tonal' },\n}\n\nconst styles = StyleSheet.create({\n // The icon sits in the middle of a square that a row never squeezes.\n base: {\n alignItems: 'center',\n flexShrink: 0,\n justifyContent: 'center',\n },\n})\n\n// The outlined rule's width at each size, Button's.\nconst outlineWidths = StyleSheet.create({\n lg: { borderWidth: OUTLINE_WIDTHS.lg },\n md: { borderWidth: OUTLINE_WIDTHS.md },\n xl: { borderWidth: OUTLINE_WIDTHS.xl },\n xs: { borderWidth: OUTLINE_WIDTHS.xs },\n xxl: { borderWidth: OUTLINE_WIDTHS.xxl },\n})\n\n// Square, so one control height sets both edges.\nconst sizesOf = themedStyles(({ sizing }) => {\n function square(size: IconButtonSize): ViewStyle {\n const edge = sizing[HEIGHTS[size]]\n\n return { height: edge, width: edge }\n }\n\n return StyleSheet.create({\n lg: square('lg'),\n md: square('md'),\n xl: square('xl'),\n xs: square('xs'),\n xxl: square('xxl'),\n })\n})\n\n/**\n * A button that is an icon, at five control heights, with web's props and\n * values. Given `href` it is a link with the same appearance, and given\n * `isSelected`, `defaultSelected` or `onChange` it is a toggle, which reports\n * its state to a screen reader and draws the page's second pair of colour\n * roles for its variant. The three forms are exclusive, so a toggle given\n * `href` does not compile.\n *\n * ```tsx\n * <IconButton aria-label=\"Label\" defaultSelected variant=\"tonal\">\n * <Icon />\n * </IconButton>\n * ```\n *\n * The two sizes under 48dp, `xs` and `md`, take presses over a 48dp target\n * through `hitSlop`, which a `hitSlop` of the call site's own replaces.\n * `style`, `ref` and `testID` land on the `Pressable`.\n */\nfunction IconButton({\n children,\n defaultSelected,\n disableRipple = false,\n hitSlop: ownHitSlop,\n href,\n isDisabled = false,\n isPending = false,\n isSelected,\n onBlur,\n onChange,\n onFocus,\n onHoverIn,\n onHoverOut,\n onLayout,\n onLongPress,\n onPress,\n onPressIn,\n onPressOut,\n pendingLabel,\n size = 'md',\n style,\n type,\n variant = 'standard',\n ...props\n}: IconButtonProps) {\n const theme = useTheme()\n // A link is never pending, as on web, where its props have no such state.\n const pending = href === undefined && isPending\n const ringLabel = usePending(pending, pendingLabel)\n\n // The three props that make this a toggle, read as web reads them.\n const isToggle =\n defaultSelected !== undefined ||\n isSelected !== undefined ||\n onChange !== undefined\n const action = useButtonAction({\n defaultSelected,\n href,\n isSelected,\n isToggle,\n onChange,\n onPress,\n type,\n })\n const colors =\n palettesOf(theme)[\n isDisabled\n ? DISABLED[variant]\n : isToggle\n ? TOGGLE_PALETTES[variant][\n action.selected ? 'selected' : 'unselected'\n ]\n : variant\n ]\n\n const feedback = usePressFeedback({\n color: colors.content,\n disabled: isDisabled,\n disableRipple,\n onBlur,\n onFocus,\n onHoverIn,\n onHoverOut,\n onPressIn,\n onPressOut,\n pending,\n })\n\n const { radii, sizing } = theme\n const edge = sizing[HEIGHTS[size]]\n const shaped = useCorner(\n feedback.pressed || action.selected\n ? radii[PRESSED_CORNERS[size]]\n : radii.pill,\n onLayout,\n )\n\n return (\n <AnimatedPressable\n role={href === undefined ? 'button' : 'link'}\n {...(isToggle ? toggleState(action.selected) : undefined)}\n {...(pending ? BUSY : undefined)}\n {...props}\n {...feedback.handlers}\n disabled={isDisabled}\n hitSlop={ownHitSlop ?? hitSlop(edge, edge)}\n onLayout={shaped.onLayout}\n onLongPress={pending ? undefined : onLongPress}\n onPress={pending ? undefined : action.onPress}\n style={composeStyles<AnimatedStyle<ViewStyle>>(\n styles.base,\n sizesOf(theme)[size],\n variant === 'outlined' ? outlineWidths[size] : undefined,\n colors.container,\n shaped.corner,\n feedback.ring,\n style,\n )}\n >\n <Animated.View\n style={composeStyles<AnimatedStyle<ViewStyle>>(\n buttonStyles.clip,\n shaped.corner,\n )}\n >\n {feedback.layer}\n </Animated.View>\n <PendingContent isPending={pending}>\n <IconStyleContext value={iconStyleOf(colors.content, size)}>\n {children}\n </IconStyleContext>\n </PendingContent>\n {pending ? (\n <PendingRing\n color={colors.content}\n diameter={ICON_SIZES[size]}\n label={ringLabel}\n />\n ) : null}\n </AnimatedPressable>\n )\n}\n\nfunction iconStyleOf(color: string, size: IconButtonSize): IconStyle {\n return { color, size: ICON_SIZES[size] }\n}\n\nexport { IconButton }\nexport type { IconButtonProps, IconButtonSize, IconButtonVariant }\n"],"mappings":";;;;;;;;;;;;AA4HA,MAAM4C,WAA6D;CACjEG,QAAQ;CACRC,UAAU;CACVC,UAAU;CACVC,OAAO;AACT;AAIA,MAAMC,aAAuD;CAC3DC,IAAI;CACJC,IAAI;CACJC,IAAI;CACJC,IAAI;CACJC,KAAK;AACP;AAIA,MAAMC,kBAKF;CACFV,QAAQ;EAAEW,UAAU;EAAwBC,YAAY;CAAe;CACvEX,UAAU;EAAEU,UAAU;EAA0BC,YAAY;CAAW;CACvEV,UAAU;EAAES,UAAU;EAA0BC,YAAY;CAAW;CACvET,OAAO;EAAEQ,UAAU;EAAuBC,YAAY;CAAQ;AAChE;AAEA,MAAMC,SAASrD,WAAWsD,OAAO,EAE/BC,MAAM;CACJC,YAAY;CACZC,YAAY;CACZC,gBAAgB;AAClB,EACF,CAAC;AAGD,MAAMC,gBAAgB3D,WAAWsD,OAAO;CACtCT,IAAI,EAAEe,aAAalD,eAAemC,GAAG;CACrCC,IAAI,EAAEc,aAAalD,eAAeoC,GAAG;CACrCC,IAAI,EAAEa,aAAalD,eAAeqC,GAAG;CACrCC,IAAI,EAAEY,aAAalD,eAAesC,GAAG;CACrCC,KAAK,EAAEW,aAAalD,eAAeuC,IAAI;AACzC,CAAC;AAGD,MAAMY,UAAUpC,cAAc,EAAEqC,aAAa;CAC3C,SAASC,OAAO/B,MAAiC;EAC/C,MAAMgC,OAAOF,OAAOrD,QAAQuB;EAE5B,OAAO;GAAEiC,QAAQD;GAAME,OAAOF;EAAK;CACrC;CAEA,OAAOhE,WAAWsD,OAAO;EACvBT,IAAIkB,OAAO,IAAI;EACfjB,IAAIiB,OAAO,IAAI;EACfhB,IAAIgB,OAAO,IAAI;EACff,IAAIe,OAAO,IAAI;EACfd,KAAKc,OAAO,KAAK;CACnB,CAAC;AACH,CAAC;;;;;;;;;;;;;;;;;;;AAoBD,SAAAI,WAAAC,IAAA;CAAA,MAAAC,IAAAC,EAAA,EAAA;CAAA,IAAA1C;CAAA,IAAA2C;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAApD;CAAA,IAAAqD;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAC;CAAA,IAAAvB,EAAA,OAAAD,IAAA;EAAoB,CAAA,CAAAxC,UAAA2C,iBAAA1C,eAAA0D,IAAAlE,SAAA+D,YAAAZ,MAAA1C,YAAA0D,IAAAK,WAAAJ,IAAAhB,YAAAC,QAAAC,UAAAC,SAAAC,WAAAC,YAAAC,UAAAC,aAAAC,SAAAC,WAAAC,YAAAE,cAAArD,MAAA0D,IAAAxD,OAAA0D,MAAAzD,SAAAwD,IAAA,GAAAL,SAAAlB;EAyBFC,EAAA,KAAAD;EAAAC,EAAA,KAAAzC;EAAAyC,EAAA,KAAAE;EAAAF,EAAA,KAAAG;EAAAH,EAAA,KAAAI;EAAAJ,EAAA,KAAAK;EAAAL,EAAA,KAAAM;EAAAN,EAAA,KAAAO;EAAAP,EAAA,KAAAQ;EAAAR,EAAA,KAAAS;EAAAT,EAAA,MAAAU;EAAAV,EAAA,MAAAW;EAAAX,EAAA,MAAAY;EAAAZ,EAAA,MAAAa;EAAAb,EAAA,MAAAc;EAAAd,EAAA,MAAAe;EAAAf,EAAA,MAAAgB;EAAAhB,EAAA,MAAAiB;EAAAjB,EAAA,MAAAnC;EAAAmC,EAAA,MAAAkB;EAAAlB,EAAA,MAAAmB;EAAAnB,EAAA,MAAAoB;EAAApB,EAAA,MAAAqB;EAAArB,EAAA,MAAAsB;EAAAtB,EAAA,MAAAuB;CAAA,OAAA;EAAAhE,WAAAyC,EAAA;EAAAE,kBAAAF,EAAA;EAAAG,OAAAH,EAAA;EAAAI,aAAAJ,EAAA;EAAAK,SAAAL,EAAA;EAAAM,WAAAN,EAAA;EAAAO,UAAAP,EAAA;EAAAQ,YAAAR,EAAA;EAAAS,aAAAT,EAAA;EAAAU,WAAAV,EAAA;EAAAW,cAAAX,EAAA;EAAAY,UAAAZ,EAAA;EAAAa,YAAAb,EAAA;EAAAc,aAAAd,EAAA;EAAAe,aAAAf,EAAA;EAAAgB,eAAAhB,EAAA;EAAAiB,QAAAjB,EAAA;EAAAnC,QAAAmC,EAAA;EAAAkB,KAAAlB,EAAA;EAAAmB,KAAAnB,EAAA;EAAAoB,KAAApB,EAAA;EAAAqB,KAAArB,EAAA;EAAAsB,KAAAtB,EAAA;EAAAuB,OAAAvB,EAAA;CAAA;CAtBhB,MAAAxC,gBAAA0D,OAAAO,KAAAA,IAAA,QAAAP;CAGA,MAAAzD,aAAA0D,OAAAM,KAAAA,IAAA,QAAAN;CACA,MAAAK,YAAAJ,OAAAK,KAAAA,IAAA,QAAAL;CAaA,MAAAzD,OAAA0D,OAAAI,KAAAA,IAAA,OAAAJ;CAGA,MAAAvD,UAAAwD,OAAAG,KAAAA,IAAA,aAAAH;CAGA,MAAAI,QAAcxE,SAAS;CAEvB,MAAAyE,UAAgBxB,SAASsB,KAAAA,KAATD;CAChB,MAAAI,YAAkB9E,WAAW6E,SAASX,YAAY;CAGlD,MAAAa,WACE3B,oBAAoBuB,KAAAA,KACpBrB,eAAeqB,KAAAA,KACfnB,aAAamB,KAAAA;CAAS,IAAAK;CAAA,IAAA9B,EAAA,QAAAE,mBAAAF,EAAA,QAAAG,QAAAH,EAAA,QAAAI,cAAAJ,EAAA,QAAA6B,YAAA7B,EAAA,QAAAM,YAAAN,EAAA,QAAAY,WAAAZ,EAAA,QAAAuB,MAAA;EACOO,KAAA;GAAA5B;GAAAC;GAAAC;GAAAyB;GAAAvB;GAAAM;GAAAW;EAQ/B;EAACvB,EAAA,MAAAE;EAAAF,EAAA,MAAAG;EAAAH,EAAA,MAAAI;EAAAJ,EAAA,MAAA6B;EAAA7B,EAAA,MAAAM;EAAAN,EAAA,MAAAY;EAAAZ,EAAA,MAAAuB;EAAAvB,EAAA,MAAA8B;CAAA,OAAAA,KAAA9B,EAAA;CARD,MAAA+B,SAAevF,gBAAgBsF,EAQ9B;CACD,MAAAE,SACEtF,WAAWgF,KAAK,CAAC,CACfjE,aACIO,SAASF,WACT+D,WACEhD,gBAAgBf,QAAQ,CACtBiE,OAAMjD,WAAN,aAAA,gBAFJhB;CAOR,MAAAmE,WAAiBhF,iBAAiB;EAAAiF,OACzBF,OAAMG;EAAQC,UACX3E;EAAUD;EAAA6C;EAAAE;EAAAC;EAAAC;EAAAI;EAAAC;EAAAa;CAStB,CAAC;CAED,MAAA,EAAAU,OAAA5C,WAA0BiC;CAC1B,MAAA/B,OAAaF,OAAOrD,QAAQuB;CAC5B,MAAA2E,SAAe7F,UACbwF,SAAQM,WAAYR,OAAMjD,WACtBuD,MAAM/F,gBAAgBqB,SACtB0E,MAAKG,MACT9B,QACF;CAGG,MAAA+B,KAAAvG;CACO,MAAAwG,KAAAvC,SAASsB,KAAAA,IAAT,WAAA;CAAsC,IAAAkB;CAAA,IAAA3C,EAAA,QAAA+B,UAAA/B,EAAA,QAAA6B,UAAA;EACvCc,KAAAd,WAAWtF,YAAYwF,OAAMjD,QAAqB,IAAlD2C,KAAAA;EAAmDzB,EAAA,MAAA+B;EAAA/B,EAAA,MAAA6B;EAAA7B,EAAA,MAAA2C;CAAA,OAAAA,KAAA3C,EAAA;CACnD,MAAA4C,KAAAjB,UAAAhF,OAAA8E,KAAAA;CAED,MAAAoB,MAAAZ,SAAQa;CAAS,IAAAC;CAAA,IAAA/C,EAAA,QAAAL,QAAAK,EAAA,QAAAe,YAAA;EAEZgC,MAAAhC,cAAc/D,QAAQ2C,MAAMA,IAAI;EAACK,EAAA,MAAAL;EAAAK,EAAA,MAAAe;EAAAf,EAAA,MAAA+C;CAAA,OAAAA,MAAA/C,EAAA;CAChC,MAAAgD,MAAAV,OAAM5B;CACH,MAAAuC,MAAAtB,UAAAF,KAAAA,IAAAd;CACJ,MAAAuC,MAAAvB,UAAAF,KAAAA,IAAsBM,OAAMnB;CAC9B,MAAAuC,MAAAhG,cACL6B,OAAME,MACNM,QAAQkC,KAAK,CAAC,CAAC/D,OACfG,YAAY,aAAawB,cAAc3B,QAAvC8D,KAAAA,GACAO,OAAMoB,WACNd,OAAMe,QACNpB,SAAQqB,MACRzF,KACF;CAAC,IAAA0F;CAAA,IAAAvD,EAAA,QAAAsC,OAAAe,QAAA;EAGQE,MAAApG,cACLhB,aAAYqH,MACZlB,OAAMe,MACR;EAACrD,EAAA,MAAAsC,OAAAe;EAAArD,EAAA,MAAAuD;CAAA,OAAAA,MAAAvD,EAAA;CAAA,IAAAyD;CAAA,IAAAzD,EAAA,QAAAiC,SAAAyB,SAAA1D,EAAA,QAAAuD,KAAA;EAJHE,MAAA,oBAAA,SAAA,MAAA;GACS,OAAAF;GAKNtB,UAAAA,SAAQyB;EACX,CAAA;EAAgB1D,EAAA,MAAAiC,SAAAyB;EAAA1D,EAAA,MAAAuD;EAAAvD,EAAA,MAAAyD;CAAA,OAAAA,MAAAzD,EAAA;CACf,MAAA2D,KAAA/G;CACE,MAAAgH,KAAA7G;CAAwB,MAAA8G,MAAAC,YAAY9B,OAAMG,SAAUxE,IAAI;CAAC,IAAAoG;CAAA,IAAA/D,EAAA,QAAA4D,MAAA5D,EAAA,QAAAzC,YAAAyC,EAAA,QAAA6D,KAAA;EAA1DE,MAAA,oBAAC,IAAD;GAAyB,OAAAF;GACtBtG;EADc,CAAA;EAEEyC,EAAA,MAAA4D;EAAA5D,EAAA,MAAAzC;EAAAyC,EAAA,MAAA6D;EAAA7D,EAAA,MAAA+D;CAAA,OAAAA,MAAA/D,EAAA;CAAA,IAAAgE;CAAA,IAAAhE,EAAA,QAAA2D,MAAA3D,EAAA,QAAA2B,WAAA3B,EAAA,QAAA+D,KAAA;EAHrBC,MAAA,oBAAC,IAAD;GAA2BrC,WAAAA;GACzBoC,UAAAA;EADa,CAAA;EAIE/D,EAAA,MAAA2D;EAAA3D,EAAA,MAAA2B;EAAA3B,EAAA,MAAA+D;EAAA/D,EAAA,MAAAgE;CAAA,OAAAA,MAAAhE,EAAA;CAAA,IAAAiE;CAAA,IAAAjE,EAAA,QAAAgC,UAAAhC,EAAA,QAAA2B,WAAA3B,EAAA,QAAA4B,aAAA5B,EAAA,QAAArC,MAAA;EAChBsG,MAAAtC,UACC,oBAAC,aAAD;GACS,OAAAK,OAAMG;GACH,UAAA5D,WAAWZ;GACdiE,OAAAA;EAAS,CAAA,IAJnB;EAMO5B,EAAA,MAAAgC;EAAAhC,EAAA,MAAA2B;EAAA3B,EAAA,MAAA4B;EAAA5B,EAAA,MAAArC;EAAAqC,EAAA,MAAAiE;CAAA,OAAAA,MAAAjE,EAAA;CAAA,IAAAkE;CAAA,IAAAlE,EAAA,QAAAyC,MAAAzC,EAAA,QAAAiC,SAAAa,YAAA9C,EAAA,QAAAvC,cAAAuC,EAAA,QAAAiB,SAAAjB,EAAA,QAAAsC,OAAA5B,YAAAV,EAAA,QAAA+C,OAAA/C,EAAA,QAAAiD,OAAAjD,EAAA,QAAAkD,OAAAlD,EAAA,QAAAmD,OAAAnD,EAAA,QAAAyD,OAAAzD,EAAA,QAAAgE,OAAAhE,EAAA,QAAAiE,OAAAjE,EAAA,QAAA0C,MAAA1C,EAAA,QAAA2C,MAAA3C,EAAA,QAAA4C,IAAA;EAxCVsB,MAAA,qBAAC,IAAD;GACQ,MAAAxB;GAAsC,GACvCC;GAAmD,GACnDC;GAA0B,GAC3B3B;GAAK,GACL4B;GACMpF,UAAAA;GACD,SAAAsF;GACC,UAAAC;GACG,aAAAC;GACJ,SAAAC;GACF,OAAAC;GAXT,UAAA;IAqBEM;IAQAO;IAKCC;GAlCe;;EAyCEjE,EAAA,MAAAyC;EAAAzC,EAAA,MAAAiC,SAAAa;EAAA9C,EAAA,MAAAvC;EAAAuC,EAAA,MAAAiB;EAAAjB,EAAA,MAAAsC,OAAA5B;EAAAV,EAAA,MAAA+C;EAAA/C,EAAA,MAAAiD;EAAAjD,EAAA,MAAAkD;EAAAlD,EAAA,MAAAmD;EAAAnD,EAAA,MAAAyD;EAAAzD,EAAA,MAAAgE;EAAAhE,EAAA,MAAAiE;EAAAjE,EAAA,MAAA0C;EAAA1C,EAAA,MAAA2C;EAAA3C,EAAA,MAAA4C;EAAA5C,EAAA,MAAAkE;CAAA,OAAAA,MAAAlE,EAAA;CAAA,OAzCpBkE;AAyCoB;AAIxB,SAASJ,YAAY5B,OAAevE,MAAiC;CACnE,OAAO;EAAEuE;EAAOvE,MAAMY,WAAWZ;CAAM;AACzC"}