@ankhorage/zora 4.5.0 → 5.0.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 (147) hide show
  1. package/CHANGELOG.md +7 -0
  2. package/README.md +1 -1
  3. package/dist/index.d.ts +0 -12
  4. package/dist/index.d.ts.map +1 -1
  5. package/dist/index.js +0 -6
  6. package/dist/index.js.map +1 -1
  7. package/dist/metadata/componentMeta.d.ts.map +1 -1
  8. package/dist/metadata/componentMeta.js +0 -12
  9. package/dist/metadata/componentMeta.js.map +1 -1
  10. package/dist/registry.d.ts.map +1 -1
  11. package/dist/registry.js +0 -12
  12. package/dist/registry.js.map +1 -1
  13. package/package.json +1 -1
  14. package/src/audit.test.ts +0 -29
  15. package/src/index.ts +0 -23
  16. package/src/interactionPolicy.test.ts +0 -17
  17. package/src/metadata/componentMeta.ts +0 -12
  18. package/src/registry.ts +0 -12
  19. package/src/showcaseCoverage.test.ts +0 -6
  20. package/src/theme/themeScopeStructure.test.ts +0 -4
  21. package/dist/components/drawer/Drawer.d.ts +0 -7
  22. package/dist/components/drawer/Drawer.d.ts.map +0 -1
  23. package/dist/components/drawer/Drawer.js +0 -36
  24. package/dist/components/drawer/Drawer.js.map +0 -1
  25. package/dist/components/drawer/index.d.ts +0 -3
  26. package/dist/components/drawer/index.d.ts.map +0 -1
  27. package/dist/components/drawer/index.js +0 -2
  28. package/dist/components/drawer/index.js.map +0 -1
  29. package/dist/components/drawer/meta.d.ts +0 -9
  30. package/dist/components/drawer/meta.d.ts.map +0 -1
  31. package/dist/components/drawer/meta.js +0 -9
  32. package/dist/components/drawer/meta.js.map +0 -1
  33. package/dist/components/drawer/types.d.ts +0 -10
  34. package/dist/components/drawer/types.d.ts.map +0 -1
  35. package/dist/components/drawer/types.js +0 -2
  36. package/dist/components/drawer/types.js.map +0 -1
  37. package/dist/components/navigation-item/NavigationItem.d.ts +0 -7
  38. package/dist/components/navigation-item/NavigationItem.d.ts.map +0 -1
  39. package/dist/components/navigation-item/NavigationItem.js +0 -21
  40. package/dist/components/navigation-item/NavigationItem.js.map +0 -1
  41. package/dist/components/navigation-item/index.d.ts +0 -3
  42. package/dist/components/navigation-item/index.d.ts.map +0 -1
  43. package/dist/components/navigation-item/index.js +0 -2
  44. package/dist/components/navigation-item/index.js.map +0 -1
  45. package/dist/components/navigation-item/meta.d.ts +0 -9
  46. package/dist/components/navigation-item/meta.d.ts.map +0 -1
  47. package/dist/components/navigation-item/meta.js +0 -9
  48. package/dist/components/navigation-item/meta.js.map +0 -1
  49. package/dist/components/navigation-item/types.d.ts +0 -23
  50. package/dist/components/navigation-item/types.d.ts.map +0 -1
  51. package/dist/components/navigation-item/types.js +0 -2
  52. package/dist/components/navigation-item/types.js.map +0 -1
  53. package/dist/components/navigation-list/NavigationList.d.ts +0 -7
  54. package/dist/components/navigation-list/NavigationList.d.ts.map +0 -1
  55. package/dist/components/navigation-list/NavigationList.js +0 -29
  56. package/dist/components/navigation-list/NavigationList.js.map +0 -1
  57. package/dist/components/navigation-list/index.d.ts +0 -3
  58. package/dist/components/navigation-list/index.d.ts.map +0 -1
  59. package/dist/components/navigation-list/index.js +0 -2
  60. package/dist/components/navigation-list/index.js.map +0 -1
  61. package/dist/components/navigation-list/meta.d.ts +0 -9
  62. package/dist/components/navigation-list/meta.d.ts.map +0 -1
  63. package/dist/components/navigation-list/meta.js +0 -9
  64. package/dist/components/navigation-list/meta.js.map +0 -1
  65. package/dist/components/navigation-list/types.d.ts +0 -15
  66. package/dist/components/navigation-list/types.d.ts.map +0 -1
  67. package/dist/components/navigation-list/types.js +0 -2
  68. package/dist/components/navigation-list/types.js.map +0 -1
  69. package/dist/internal/resolveZoraNavigationItems.d.ts +0 -65
  70. package/dist/internal/resolveZoraNavigationItems.d.ts.map +0 -1
  71. package/dist/internal/resolveZoraNavigationItems.js +0 -56
  72. package/dist/internal/resolveZoraNavigationItems.js.map +0 -1
  73. package/dist/patterns/responsive-panel/ResponsivePanel.d.ts +0 -16
  74. package/dist/patterns/responsive-panel/ResponsivePanel.d.ts.map +0 -1
  75. package/dist/patterns/responsive-panel/ResponsivePanel.js +0 -101
  76. package/dist/patterns/responsive-panel/ResponsivePanel.js.map +0 -1
  77. package/dist/patterns/responsive-panel/index.d.ts +0 -3
  78. package/dist/patterns/responsive-panel/index.d.ts.map +0 -1
  79. package/dist/patterns/responsive-panel/index.js +0 -3
  80. package/dist/patterns/responsive-panel/index.js.map +0 -1
  81. package/dist/patterns/responsive-panel/meta.d.ts +0 -9
  82. package/dist/patterns/responsive-panel/meta.d.ts.map +0 -1
  83. package/dist/patterns/responsive-panel/meta.js +0 -9
  84. package/dist/patterns/responsive-panel/meta.js.map +0 -1
  85. package/dist/patterns/responsive-panel/types.d.ts +0 -23
  86. package/dist/patterns/responsive-panel/types.d.ts.map +0 -1
  87. package/dist/patterns/responsive-panel/types.js +0 -2
  88. package/dist/patterns/responsive-panel/types.js.map +0 -1
  89. package/dist/patterns/zora-drawer-content/ZoraDrawerContent.d.ts +0 -9
  90. package/dist/patterns/zora-drawer-content/ZoraDrawerContent.d.ts.map +0 -1
  91. package/dist/patterns/zora-drawer-content/ZoraDrawerContent.js +0 -31
  92. package/dist/patterns/zora-drawer-content/ZoraDrawerContent.js.map +0 -1
  93. package/dist/patterns/zora-drawer-content/index.d.ts +0 -3
  94. package/dist/patterns/zora-drawer-content/index.d.ts.map +0 -1
  95. package/dist/patterns/zora-drawer-content/index.js +0 -2
  96. package/dist/patterns/zora-drawer-content/index.js.map +0 -1
  97. package/dist/patterns/zora-drawer-content/meta.d.ts +0 -9
  98. package/dist/patterns/zora-drawer-content/meta.d.ts.map +0 -1
  99. package/dist/patterns/zora-drawer-content/meta.js +0 -9
  100. package/dist/patterns/zora-drawer-content/meta.js.map +0 -1
  101. package/dist/patterns/zora-drawer-content/types.d.ts +0 -15
  102. package/dist/patterns/zora-drawer-content/types.d.ts.map +0 -1
  103. package/dist/patterns/zora-drawer-content/types.js +0 -2
  104. package/dist/patterns/zora-drawer-content/types.js.map +0 -1
  105. package/dist/patterns/zora-tab-bar/ZoraTabBar.d.ts +0 -9
  106. package/dist/patterns/zora-tab-bar/ZoraTabBar.d.ts.map +0 -1
  107. package/dist/patterns/zora-tab-bar/ZoraTabBar.js +0 -89
  108. package/dist/patterns/zora-tab-bar/ZoraTabBar.js.map +0 -1
  109. package/dist/patterns/zora-tab-bar/index.d.ts +0 -3
  110. package/dist/patterns/zora-tab-bar/index.d.ts.map +0 -1
  111. package/dist/patterns/zora-tab-bar/index.js +0 -2
  112. package/dist/patterns/zora-tab-bar/index.js.map +0 -1
  113. package/dist/patterns/zora-tab-bar/meta.d.ts +0 -9
  114. package/dist/patterns/zora-tab-bar/meta.d.ts.map +0 -1
  115. package/dist/patterns/zora-tab-bar/meta.js +0 -9
  116. package/dist/patterns/zora-tab-bar/meta.js.map +0 -1
  117. package/dist/patterns/zora-tab-bar/types.d.ts +0 -19
  118. package/dist/patterns/zora-tab-bar/types.d.ts.map +0 -1
  119. package/dist/patterns/zora-tab-bar/types.js +0 -2
  120. package/dist/patterns/zora-tab-bar/types.js.map +0 -1
  121. package/src/components/drawer/Drawer.tsx +0 -59
  122. package/src/components/drawer/index.ts +0 -2
  123. package/src/components/drawer/meta.ts +0 -10
  124. package/src/components/drawer/types.ts +0 -17
  125. package/src/components/navigation-item/NavigationItem.tsx +0 -41
  126. package/src/components/navigation-item/index.ts +0 -6
  127. package/src/components/navigation-item/meta.ts +0 -10
  128. package/src/components/navigation-item/types.ts +0 -26
  129. package/src/components/navigation-list/NavigationList.tsx +0 -68
  130. package/src/components/navigation-list/index.ts +0 -2
  131. package/src/components/navigation-list/meta.ts +0 -10
  132. package/src/components/navigation-list/types.ts +0 -17
  133. package/src/internal/resolveZoraNavigationItems.test.ts +0 -174
  134. package/src/internal/resolveZoraNavigationItems.ts +0 -157
  135. package/src/navigationExports.test.ts +0 -15
  136. package/src/patterns/responsive-panel/ResponsivePanel.tsx +0 -172
  137. package/src/patterns/responsive-panel/index.ts +0 -2
  138. package/src/patterns/responsive-panel/meta.ts +0 -10
  139. package/src/patterns/responsive-panel/types.ts +0 -25
  140. package/src/patterns/zora-drawer-content/ZoraDrawerContent.tsx +0 -60
  141. package/src/patterns/zora-drawer-content/index.ts +0 -2
  142. package/src/patterns/zora-drawer-content/meta.ts +0 -10
  143. package/src/patterns/zora-drawer-content/types.ts +0 -20
  144. package/src/patterns/zora-tab-bar/ZoraTabBar.tsx +0 -157
  145. package/src/patterns/zora-tab-bar/index.ts +0 -2
  146. package/src/patterns/zora-tab-bar/meta.ts +0 -10
  147. package/src/patterns/zora-tab-bar/types.ts +0 -18
@@ -1,89 +0,0 @@
1
- import React from 'react';
2
- import { Pressable, Text as ReactNativeText } from 'react-native';
3
- import { Icon } from '../../components/icon';
4
- import { Box, Surface } from '../../foundation';
5
- import { createTabBarItemPressHandler, resolveNavigationItems, } from '../../internal/resolveZoraNavigationItems';
6
- import { useZoraTheme } from '../../theme/useZoraTheme';
7
- import { withZoraThemeScope } from '../../theme/withZoraThemeScope';
8
- function resolveAccessibilityLabel(label, explicitLabel) {
9
- if (explicitLabel !== undefined) {
10
- return explicitLabel;
11
- }
12
- if (typeof label === 'string') {
13
- return label;
14
- }
15
- if (typeof label === 'number') {
16
- return String(label);
17
- }
18
- return undefined;
19
- }
20
- function ZoraTabBarInner({ themeId: _themeId, mode: _mode, interactionPolicy, state, navigation, descriptors, insets, routeMap, compact = false, chrome = 'raised', testID, }) {
21
- const { theme } = useZoraTheme();
22
- const resolved = resolveNavigationItems({
23
- state,
24
- descriptors,
25
- routeMap,
26
- kind: 'tab',
27
- });
28
- const bottomInset = insets?.bottom ?? 0;
29
- const minHeight = compact ? 56 : 64;
30
- const labelSize = compact ? theme.typography.sizes.xs : theme.typography.sizes.s;
31
- const labelWeight = theme.typography.weights.medium;
32
- const content = (<Box bg="surface" style={{
33
- borderTopColor: theme.semantics.border.default,
34
- borderTopWidth: 1,
35
- flexDirection: 'row',
36
- minHeight: minHeight + bottomInset,
37
- paddingBottom: bottomInset,
38
- }} testID={testID}>
39
- {resolved.map((item) => {
40
- const { active } = item;
41
- const { disabled } = item;
42
- const contentColor = disabled
43
- ? theme.semantics.content.subtle
44
- : active
45
- ? theme.semantics.action.primary.base
46
- : theme.semantics.content.muted;
47
- const backgroundColor = active
48
- ? theme.semantics.action.primary.softBg
49
- : theme.semantics.surface.default;
50
- return (<Pressable accessibilityLabel={resolveAccessibilityLabel(item.label, item.metadata?.accessibilityLabel)} accessibilityRole="tab" accessibilityState={{ selected: active, disabled }} disabled={disabled} key={item.route.key} onPress={interactionPolicy === 'passive'
51
- ? undefined
52
- : createTabBarItemPressHandler({ item, navigation })} style={{
53
- alignItems: 'center',
54
- backgroundColor,
55
- flex: 1,
56
- justifyContent: 'center',
57
- minHeight,
58
- opacity: disabled ? 0.48 : 1,
59
- paddingHorizontal: theme.spacing.s,
60
- paddingVertical: compact ? theme.spacing.xs : theme.spacing.s,
61
- }} testID={item.metadata?.testID ?? (testID ? `${testID}-item-${item.route.key}` : undefined)}>
62
- {item.metadata?.icon ? (<Icon {...item.metadata.icon} color={contentColor} size={compact ? theme.spacing.m : theme.spacing.l}/>) : null}
63
- <ReactNativeText numberOfLines={1} style={{
64
- color: contentColor,
65
- fontSize: labelSize,
66
- fontWeight: labelWeight,
67
- lineHeight: compact ? 16 : 20,
68
- marginTop: item.metadata?.icon ? theme.spacing.xs : 0,
69
- textAlign: 'center',
70
- }}>
71
- {item.label}
72
- </ReactNativeText>
73
- </Pressable>);
74
- })}
75
- </Box>);
76
- if (chrome === 'none') {
77
- return content;
78
- }
79
- return (<Surface interactionPolicy={interactionPolicy} testID={testID ? `${testID}-chrome` : undefined} variant="raised">
80
- {content}
81
- </Surface>);
82
- }
83
- /***
84
- * Bottom tab bar pattern with badge support and active state styling.
85
- *
86
-
87
- */
88
- export const ZoraTabBar = withZoraThemeScope(ZoraTabBarInner);
89
- //# sourceMappingURL=ZoraTabBar.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"ZoraTabBar.js","sourceRoot":"","sources":["../../../src/patterns/zora-tab-bar/ZoraTabBar.tsx"],"names":[],"mappings":"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","sourcesContent":["import React from 'react';\nimport { Pressable, Text as ReactNativeText } from 'react-native';\n\nimport { Icon } from '../../components/icon';\nimport { Box, Surface } from '../../foundation';\nimport {\n createTabBarItemPressHandler,\n resolveNavigationItems,\n} from '../../internal/resolveZoraNavigationItems';\nimport { useZoraTheme } from '../../theme/useZoraTheme';\nimport { withZoraThemeScope } from '../../theme/withZoraThemeScope';\nimport type { ZoraTabBarProps } from './types';\n\nfunction resolveAccessibilityLabel(\n label: React.ReactNode,\n explicitLabel?: string,\n): string | undefined {\n if (explicitLabel !== undefined) {\n return explicitLabel;\n }\n\n if (typeof label === 'string') {\n return label;\n }\n\n if (typeof label === 'number') {\n return String(label);\n }\n\n return undefined;\n}\n\nfunction ZoraTabBarInner({\n themeId: _themeId,\n mode: _mode,\n interactionPolicy,\n state,\n navigation,\n descriptors,\n insets,\n routeMap,\n compact = false,\n chrome = 'raised',\n testID,\n}: ZoraTabBarProps) {\n const { theme } = useZoraTheme();\n const resolved = resolveNavigationItems({\n state,\n descriptors,\n routeMap,\n kind: 'tab',\n });\n\n const bottomInset = insets?.bottom ?? 0;\n const minHeight = compact ? 56 : 64;\n const labelSize = compact ? theme.typography.sizes.xs : theme.typography.sizes.s;\n const labelWeight = theme.typography.weights.medium;\n const content = (\n <Box\n bg=\"surface\"\n style={{\n borderTopColor: theme.semantics.border.default,\n borderTopWidth: 1,\n flexDirection: 'row',\n minHeight: minHeight + bottomInset,\n paddingBottom: bottomInset,\n }}\n testID={testID}\n >\n {resolved.map((item) => {\n const { active } = item;\n const { disabled } = item;\n const contentColor = disabled\n ? theme.semantics.content.subtle\n : active\n ? theme.semantics.action.primary.base\n : theme.semantics.content.muted;\n const backgroundColor = active\n ? theme.semantics.action.primary.softBg\n : theme.semantics.surface.default;\n\n return (\n <Pressable\n accessibilityLabel={resolveAccessibilityLabel(\n item.label,\n item.metadata?.accessibilityLabel,\n )}\n accessibilityRole=\"tab\"\n accessibilityState={{ selected: active, disabled }}\n disabled={disabled}\n key={item.route.key}\n onPress={\n interactionPolicy === 'passive'\n ? undefined\n : createTabBarItemPressHandler({ item, navigation })\n }\n style={{\n alignItems: 'center',\n backgroundColor,\n flex: 1,\n justifyContent: 'center',\n minHeight,\n opacity: disabled ? 0.48 : 1,\n paddingHorizontal: theme.spacing.s,\n paddingVertical: compact ? theme.spacing.xs : theme.spacing.s,\n }}\n testID={\n item.metadata?.testID ?? (testID ? `${testID}-item-${item.route.key}` : undefined)\n }\n >\n {item.metadata?.icon ? (\n <Icon\n {...item.metadata.icon}\n color={contentColor}\n size={compact ? theme.spacing.m : theme.spacing.l}\n />\n ) : null}\n <ReactNativeText\n numberOfLines={1}\n style={{\n color: contentColor,\n fontSize: labelSize,\n fontWeight: labelWeight,\n lineHeight: compact ? 16 : 20,\n marginTop: item.metadata?.icon ? theme.spacing.xs : 0,\n textAlign: 'center',\n }}\n >\n {item.label}\n </ReactNativeText>\n </Pressable>\n );\n })}\n </Box>\n );\n\n if (chrome === 'none') {\n return content;\n }\n\n return (\n <Surface\n interactionPolicy={interactionPolicy}\n testID={testID ? `${testID}-chrome` : undefined}\n variant=\"raised\"\n >\n {content}\n </Surface>\n );\n}\n\n/***\n * Bottom tab bar pattern with badge support and active state styling.\n *\n \n */\nexport const ZoraTabBar = withZoraThemeScope(ZoraTabBarInner);\n"]}
@@ -1,3 +0,0 @@
1
- export type { ZoraTabBarProps } from './types';
2
- export { ZoraTabBar } from './ZoraTabBar';
3
- //# sourceMappingURL=index.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/patterns/zora-tab-bar/index.ts"],"names":[],"mappings":"AAAA,YAAY,EAAE,eAAe,EAAE,MAAM,SAAS,CAAC;AAC/C,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC"}
@@ -1,2 +0,0 @@
1
- export { ZoraTabBar } from './ZoraTabBar';
2
- //# sourceMappingURL=index.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/patterns/zora-tab-bar/index.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC","sourcesContent":["export type { ZoraTabBarProps } from './types';\nexport { ZoraTabBar } from './ZoraTabBar';\n"]}
@@ -1,9 +0,0 @@
1
- export declare const zoraTabBarMeta: {
2
- readonly name: "ZoraTabBar";
3
- readonly category: "pattern";
4
- readonly directManifestNode: false;
5
- readonly allowedChildren: readonly [];
6
- readonly note: "Navigation chrome pattern; not represented as a manifest node in v1.";
7
- readonly props: {};
8
- };
9
- //# sourceMappingURL=meta.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"meta.d.ts","sourceRoot":"","sources":["../../../src/patterns/zora-tab-bar/meta.ts"],"names":[],"mappings":"AAEA,eAAO,MAAM,cAAc;;;;;;;CAOW,CAAC"}
@@ -1,9 +0,0 @@
1
- export const zoraTabBarMeta = {
2
- name: 'ZoraTabBar',
3
- category: 'pattern',
4
- directManifestNode: false,
5
- allowedChildren: [],
6
- note: 'Navigation chrome pattern; not represented as a manifest node in v1.',
7
- props: {},
8
- };
9
- //# sourceMappingURL=meta.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"meta.js","sourceRoot":"","sources":["../../../src/patterns/zora-tab-bar/meta.ts"],"names":[],"mappings":"AAEA,MAAM,CAAC,MAAM,cAAc,GAAG;IAC5B,IAAI,EAAE,YAAY;IAClB,QAAQ,EAAE,SAAS;IACnB,kBAAkB,EAAE,KAAK;IACzB,eAAe,EAAE,EAAE;IACnB,IAAI,EAAE,sEAAsE;IAC5E,KAAK,EAAE,EAAE;CAC2B,CAAC","sourcesContent":["import type { ZoraComponentMeta } from '../../metadata';\n\nexport const zoraTabBarMeta = {\n name: 'ZoraTabBar',\n category: 'pattern',\n directManifestNode: false,\n allowedChildren: [],\n note: 'Navigation chrome pattern; not represented as a manifest node in v1.',\n props: {},\n} as const satisfies ZoraComponentMeta;\n"]}
@@ -1,19 +0,0 @@
1
- import type { ZoraNavigationRouteMap } from '../../components/navigation-list';
2
- import type { ZoraNavigationDescriptors, ZoraNavigationState, ZoraTabBarNavigation } from '../../internal/resolveZoraNavigationItems';
3
- import type { ZoraBaseProps } from '../../theme/ZoraBaseProps';
4
- export interface ZoraTabBarProps extends ZoraBaseProps {
5
- state: ZoraNavigationState;
6
- navigation: ZoraTabBarNavigation;
7
- descriptors?: ZoraNavigationDescriptors | undefined;
8
- insets?: {
9
- top?: number;
10
- bottom?: number;
11
- left?: number;
12
- right?: number;
13
- } | undefined;
14
- routeMap?: ZoraNavigationRouteMap | undefined;
15
- compact?: boolean;
16
- chrome?: 'none' | 'raised';
17
- testID?: string;
18
- }
19
- //# sourceMappingURL=types.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../src/patterns/zora-tab-bar/types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,sBAAsB,EAAE,MAAM,kCAAkC,CAAC;AAC/E,OAAO,KAAK,EACV,yBAAyB,EACzB,mBAAmB,EACnB,oBAAoB,EACrB,MAAM,2CAA2C,CAAC;AACnD,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,2BAA2B,CAAC;AAE/D,MAAM,WAAW,eAAgB,SAAQ,aAAa;IACpD,KAAK,EAAE,mBAAmB,CAAC;IAC3B,UAAU,EAAE,oBAAoB,CAAC;IACjC,WAAW,CAAC,EAAE,yBAAyB,GAAG,SAAS,CAAC;IACpD,MAAM,CAAC,EAAE;QAAE,GAAG,CAAC,EAAE,MAAM,CAAC;QAAC,MAAM,CAAC,EAAE,MAAM,CAAC;QAAC,IAAI,CAAC,EAAE,MAAM,CAAC;QAAC,KAAK,CAAC,EAAE,MAAM,CAAA;KAAE,GAAG,SAAS,CAAC;IACtF,QAAQ,CAAC,EAAE,sBAAsB,GAAG,SAAS,CAAC;IAC9C,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,MAAM,CAAC,EAAE,MAAM,GAAG,QAAQ,CAAC;IAC3B,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB"}
@@ -1,2 +0,0 @@
1
- export {};
2
- //# sourceMappingURL=types.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"types.js","sourceRoot":"","sources":["../../../src/patterns/zora-tab-bar/types.ts"],"names":[],"mappings":"","sourcesContent":["import type { ZoraNavigationRouteMap } from '../../components/navigation-list';\nimport type {\n ZoraNavigationDescriptors,\n ZoraNavigationState,\n ZoraTabBarNavigation,\n} from '../../internal/resolveZoraNavigationItems';\nimport type { ZoraBaseProps } from '../../theme/ZoraBaseProps';\n\nexport interface ZoraTabBarProps extends ZoraBaseProps {\n state: ZoraNavigationState;\n navigation: ZoraTabBarNavigation;\n descriptors?: ZoraNavigationDescriptors | undefined;\n insets?: { top?: number; bottom?: number; left?: number; right?: number } | undefined;\n routeMap?: ZoraNavigationRouteMap | undefined;\n compact?: boolean;\n chrome?: 'none' | 'raised';\n testID?: string;\n}\n"]}
@@ -1,59 +0,0 @@
1
- import { Drawer as SurfaceDrawer } from '@ankhorage/surface';
2
- import React, { useCallback, useEffect, useRef } from 'react';
3
-
4
- import { Box, Stack } from '../../foundation';
5
- import { withZoraThemeScope } from '../../theme/withZoraThemeScope';
6
- import { Heading } from '../heading';
7
- import { Text } from '../text';
8
- import type { DrawerProps } from './types';
9
-
10
- function useStableCallback(callback: (() => void) | undefined): (() => void) | undefined {
11
- const callbackRef = useRef(callback);
12
-
13
- useEffect(() => {
14
- callbackRef.current = callback;
15
- }, [callback]);
16
-
17
- return useCallback(() => {
18
- callbackRef.current?.();
19
- }, []);
20
- }
21
-
22
- function DrawerInner({
23
- themeId: _themeId,
24
- mode: _mode,
25
- children,
26
- title,
27
- description,
28
- footer,
29
- onDismiss,
30
- interactionPolicy,
31
- ...props
32
- }: DrawerProps) {
33
- const hasHeader = title != null || description != null;
34
- const stableOnDismiss = useStableCallback(onDismiss);
35
-
36
- return (
37
- <SurfaceDrawer {...props} onDismiss={stableOnDismiss} interactionPolicy={interactionPolicy}>
38
- <Stack gap="m">
39
- {hasHeader ? (
40
- <Stack gap="xs">
41
- {title ? <Heading level={3}>{title}</Heading> : null}
42
- {description ? (
43
- <Text emphasis="muted" variant="bodySmall">
44
- {description}
45
- </Text>
46
- ) : null}
47
- </Stack>
48
- ) : null}
49
- {children ? <Box flex={1}>{children}</Box> : null}
50
- {footer ? <Box pt="xs">{footer}</Box> : null}
51
- </Stack>
52
- </SurfaceDrawer>
53
- );
54
- }
55
-
56
- /***
57
- * Side panel overlay for navigation, settings, and secondary content.
58
- */
59
- export const Drawer = withZoraThemeScope(DrawerInner);
@@ -1,2 +0,0 @@
1
- export { Drawer } from './Drawer';
2
- export type { DrawerProps } from './types';
@@ -1,10 +0,0 @@
1
- import type { ZoraComponentMeta } from '../../metadata';
2
-
3
- export const drawerMeta = {
4
- name: 'Drawer',
5
- category: 'component',
6
- directManifestNode: false,
7
- allowedChildren: [],
8
- note: 'Shell/navigation component; not represented as a manifest node in v1.',
9
- props: {},
10
- } as const satisfies ZoraComponentMeta;
@@ -1,17 +0,0 @@
1
- import type { DrawerProps as SurfaceDrawerProps } from '@ankhorage/surface';
2
- import type React from 'react';
3
-
4
- import type { ZoraBaseProps } from '../../theme/ZoraBaseProps';
5
-
6
- export interface DrawerProps
7
- extends
8
- ZoraBaseProps,
9
- Pick<
10
- Omit<SurfaceDrawerProps, 'mode' | 'themeId'>,
11
- 'closeOnBackdrop' | 'onDismiss' | 'position' | 'visible'
12
- > {
13
- children?: React.ReactNode;
14
- title?: React.ReactNode;
15
- description?: React.ReactNode;
16
- footer?: React.ReactNode;
17
- }
@@ -1,41 +0,0 @@
1
- import { NavigationItem as SurfaceNavigationItem } from '@ankhorage/surface';
2
- import React from 'react';
3
-
4
- import { withZoraThemeScope } from '../../theme/withZoraThemeScope';
5
- import type { NavigationItemProps } from './types';
6
-
7
- function NavigationItemInner({
8
- themeId: _themeId,
9
- mode: _mode,
10
- route,
11
- metadata,
12
- active = false,
13
- compact = false,
14
- onPress,
15
- testID,
16
- interactionPolicy,
17
- }: NavigationItemProps) {
18
- return (
19
- <SurfaceNavigationItem
20
- compact={compact}
21
- interactionPolicy={interactionPolicy}
22
- item={{
23
- id: route.key,
24
- label: metadata?.label ?? route.name,
25
- icon: metadata?.icon,
26
- badge: metadata?.badge,
27
- active,
28
- disabled: metadata?.disabled,
29
- onPress,
30
- accessibilityLabel: metadata?.accessibilityLabel,
31
- testID: metadata?.testID,
32
- }}
33
- testID={testID}
34
- />
35
- );
36
- }
37
-
38
- /***
39
- * Renders a single navigation entry with active/disabled state support.
40
- */
41
- export const NavigationItem = withZoraThemeScope(NavigationItemInner);
@@ -1,6 +0,0 @@
1
- export { NavigationItem } from './NavigationItem';
2
- export type {
3
- NavigationItemProps,
4
- ZoraNavigationRouteMetadata,
5
- ZoraNavigationRouteState,
6
- } from './types';
@@ -1,10 +0,0 @@
1
- import type { ZoraComponentMeta } from '../../metadata';
2
-
3
- export const navigationItemMeta = {
4
- name: 'NavigationItem',
5
- category: 'component',
6
- directManifestNode: false,
7
- allowedChildren: [],
8
- note: 'Navigation chrome component; not represented as a manifest node in v1.',
9
- props: {},
10
- } as const satisfies ZoraComponentMeta;
@@ -1,26 +0,0 @@
1
- import type { ButtonIconSpec } from '@ankhorage/surface';
2
- import type React from 'react';
3
-
4
- import type { ZoraBaseProps } from '../../theme/ZoraBaseProps';
5
-
6
- export interface ZoraNavigationRouteMetadata {
7
- label?: React.ReactNode;
8
- icon?: ButtonIconSpec;
9
- badge?: React.ReactNode;
10
- disabled?: boolean;
11
- testID?: string;
12
- accessibilityLabel?: string;
13
- }
14
-
15
- export interface ZoraNavigationRouteState {
16
- key: string;
17
- name: string;
18
- }
19
-
20
- export interface NavigationItemProps extends ZoraBaseProps {
21
- route: ZoraNavigationRouteState;
22
- metadata?: ZoraNavigationRouteMetadata;
23
- active?: boolean;
24
- compact?: boolean;
25
- onPress?: () => void;
26
- }
@@ -1,68 +0,0 @@
1
- import {
2
- DrawerNavigation as SurfaceDrawerNavigation,
3
- NavigationList as SurfaceNavigationList,
4
- } from '@ankhorage/surface';
5
- import React from 'react';
6
-
7
- import { withZoraThemeScope } from '../../theme/withZoraThemeScope';
8
- import type { NavigationListProps } from './types';
9
-
10
- function NavigationListInner({
11
- themeId: _themeId,
12
- mode: _mode,
13
- routes,
14
- routeMap,
15
- activeRouteKey,
16
- orientation = 'vertical',
17
- compact = false,
18
- onRoutePress,
19
- header,
20
- footer,
21
- testID,
22
- interactionPolicy,
23
- }: NavigationListProps) {
24
- const items = routes.map((route) => {
25
- const metadata = routeMap?.[route.name];
26
- const active = activeRouteKey ? route.key === activeRouteKey : false;
27
-
28
- return {
29
- id: route.key,
30
- label: metadata?.label ?? route.name,
31
- icon: metadata?.icon,
32
- badge: metadata?.badge,
33
- active,
34
- disabled: metadata?.disabled,
35
- onPress: metadata?.disabled ? undefined : () => onRoutePress?.(route),
36
- accessibilityLabel: metadata?.accessibilityLabel,
37
- testID: metadata?.testID,
38
- };
39
- });
40
-
41
- if (header || footer) {
42
- return (
43
- <SurfaceDrawerNavigation
44
- compact={compact}
45
- footer={footer}
46
- header={header}
47
- interactionPolicy={interactionPolicy}
48
- items={items}
49
- testID={testID}
50
- />
51
- );
52
- }
53
-
54
- return (
55
- <SurfaceNavigationList
56
- compact={compact}
57
- interactionPolicy={interactionPolicy}
58
- items={items}
59
- orientation={orientation}
60
- testID={testID}
61
- />
62
- );
63
- }
64
-
65
- /***
66
- * Renders a navigation list from route metadata with active state mapping.
67
- */
68
- export const NavigationList = withZoraThemeScope(NavigationListInner);
@@ -1,2 +0,0 @@
1
- export { NavigationList } from './NavigationList';
2
- export type { NavigationListProps, ZoraNavigationRouteMap } from './types';
@@ -1,10 +0,0 @@
1
- import type { ZoraComponentMeta } from '../../metadata';
2
-
3
- export const navigationListMeta = {
4
- name: 'NavigationList',
5
- category: 'component',
6
- directManifestNode: false,
7
- allowedChildren: [],
8
- note: 'Navigation chrome component; not represented as a manifest node in v1.',
9
- props: {},
10
- } as const satisfies ZoraComponentMeta;
@@ -1,17 +0,0 @@
1
- import type React from 'react';
2
-
3
- import type { ZoraBaseProps } from '../../theme/ZoraBaseProps';
4
- import type { ZoraNavigationRouteMetadata, ZoraNavigationRouteState } from '../navigation-item';
5
-
6
- export type ZoraNavigationRouteMap = Partial<Record<string, ZoraNavigationRouteMetadata>>;
7
-
8
- export interface NavigationListProps extends ZoraBaseProps {
9
- routes: readonly ZoraNavigationRouteState[];
10
- routeMap?: ZoraNavigationRouteMap;
11
- activeRouteKey?: string;
12
- orientation?: 'vertical' | 'horizontal';
13
- compact?: boolean;
14
- onRoutePress?: (route: ZoraNavigationRouteState) => void;
15
- header?: React.ReactNode;
16
- footer?: React.ReactNode;
17
- }
@@ -1,174 +0,0 @@
1
- import { describe, expect, test } from 'bun:test';
2
- import React from 'react';
3
-
4
- import {
5
- createDrawerItemPressHandler,
6
- createTabBarItemPressHandler,
7
- resolveNavigationItems,
8
- resolveRouteLabel,
9
- type ZoraNavigationDescriptor,
10
- type ZoraNavigationState,
11
- type ZoraResolvedNavigationItem,
12
- type ZoraRouteLabelSource,
13
- } from './resolveZoraNavigationItems';
14
-
15
- describe('resolveRouteLabel', () => {
16
- test('prefers routeMap label over descriptor label', () => {
17
- const descriptor: ZoraNavigationDescriptor = {
18
- options: {
19
- title: 'Home Title',
20
- tabBarLabel: 'Home Tab',
21
- },
22
- };
23
-
24
- const result = resolveRouteLabel({
25
- kind: 'tab',
26
- route: { key: 'k1', name: 'home' },
27
- metadata: { label: 'Home Map' },
28
- descriptor,
29
- });
30
-
31
- const expectedSource: ZoraRouteLabelSource = 'routeMap';
32
- expect(result).toEqual({ label: 'Home Map', source: expectedSource });
33
- });
34
-
35
- test('uses descriptor label/title as fallback for label only', () => {
36
- const descriptor: ZoraNavigationDescriptor = {
37
- options: {
38
- title: 'Settings Title',
39
- tabBarLabel: undefined,
40
- },
41
- };
42
-
43
- const result = resolveRouteLabel({
44
- kind: 'tab',
45
- route: { key: 'k2', name: 'settings' },
46
- metadata: undefined,
47
- descriptor,
48
- });
49
-
50
- expect(result).toEqual({ label: 'Settings Title', source: 'descriptor' });
51
- });
52
-
53
- test('falls back to route name if nothing else provided', () => {
54
- const result = resolveRouteLabel({
55
- kind: 'drawer',
56
- route: { key: 'k3', name: 'profile' },
57
- metadata: undefined,
58
- descriptor: undefined,
59
- });
60
-
61
- expect(result).toEqual({ label: 'profile', source: 'name' });
62
- });
63
-
64
- test('uses descriptor title instead of invoking a callable Expo tab label', () => {
65
- const result = resolveRouteLabel({
66
- route: { key: 'k4', name: 'home' },
67
- metadata: undefined,
68
- descriptor: { options: { tabBarLabel: () => 'callable', title: 'Home title' } },
69
- kind: 'tab',
70
- });
71
-
72
- expect(result).toEqual({ label: 'Home title', source: 'descriptor' });
73
- });
74
- });
75
-
76
- describe('resolveNavigationItems', () => {
77
- test('maps active index + routeMap disabled state without using descriptors for icons/badges', () => {
78
- const state: ZoraNavigationState = {
79
- index: 1,
80
- routes: [
81
- { key: 'r1', name: 'home' },
82
- { key: 'r2', name: 'settings' },
83
- ],
84
- };
85
-
86
- const items = resolveNavigationItems({
87
- state,
88
- kind: 'tab',
89
- descriptors: {
90
- r1: { options: { tabBarLabel: 'Home Opt', title: 'Home Title' } },
91
- r2: { options: { tabBarLabel: 'Settings Opt' } },
92
- },
93
- routeMap: {
94
- settings: { disabled: true, badge: React.createElement('span', null, '3') },
95
- },
96
- });
97
-
98
- expect(items).toHaveLength(2);
99
- expect(items[0]).toMatchObject({ active: false, disabled: false });
100
- expect(items[1]).toMatchObject({ active: true, disabled: true });
101
- expect(items[1]?.metadata?.badge).toBeDefined();
102
- });
103
- });
104
-
105
- describe('press handler helpers', () => {
106
- test('tab press handler is undefined for disabled or active items', () => {
107
- const handlerDisabled = createTabBarItemPressHandler({
108
- item: {
109
- route: { key: 'k1', name: 'home' },
110
- metadata: { disabled: true },
111
- label: 'Home',
112
- active: false,
113
- disabled: true,
114
- },
115
- navigation: { navigate: () => undefined },
116
- });
117
- expect(handlerDisabled).toBeUndefined();
118
-
119
- const handlerActive = createTabBarItemPressHandler({
120
- item: {
121
- route: { key: 'k1', name: 'home' },
122
- metadata: undefined,
123
- label: 'Home',
124
- active: true,
125
- disabled: false,
126
- },
127
- navigation: { navigate: () => undefined },
128
- });
129
- expect(handlerActive).toBeUndefined();
130
- });
131
-
132
- test('tab press handler respects preventDefault', () => {
133
- let navigatedTo: string | null = null;
134
- const handler = createTabBarItemPressHandler({
135
- item: {
136
- route: { key: 'k1', name: 'home' },
137
- metadata: undefined,
138
- label: 'Home',
139
- active: false,
140
- disabled: false,
141
- },
142
- navigation: {
143
- emit: () => ({ defaultPrevented: true }),
144
- navigate: (name) => {
145
- navigatedTo = name;
146
- },
147
- },
148
- });
149
-
150
- expect(handler).toBeDefined();
151
- handler?.();
152
- expect(navigatedTo).toBeNull();
153
- });
154
-
155
- test('drawer press handler navigates and closes drawer', () => {
156
- const calls: string[] = [];
157
- const handler = createDrawerItemPressHandler({
158
- item: {
159
- route: { key: 'k1', name: 'home' },
160
- metadata: undefined,
161
- label: 'Home',
162
- active: false,
163
- disabled: false,
164
- } satisfies ZoraResolvedNavigationItem,
165
- navigation: {
166
- navigate: (name) => calls.push(`navigate:${name}`),
167
- closeDrawer: () => calls.push('close'),
168
- },
169
- });
170
-
171
- handler?.();
172
- expect(calls).toEqual(['navigate:home', 'close']);
173
- });
174
- });