@ezpg/app-ui 0.2.0 → 0.4.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 (203) hide show
  1. package/CHANGELOG.md +23 -0
  2. package/lib/module/blocks/brand-profile-card/brand-profile-card.js +2 -2
  3. package/lib/module/blocks/brand-profile-card/brand-profile-card.js.map +1 -1
  4. package/lib/module/blocks/bulk-ship-list/bulk-ship-list.js +1 -1
  5. package/lib/module/blocks/bulk-ship-list/bulk-ship-list.js.map +1 -1
  6. package/lib/module/blocks/claim-row/claim-row.js +6 -5
  7. package/lib/module/blocks/claim-row/claim-row.js.map +1 -1
  8. package/lib/module/blocks/color-swatch-picker/color-swatch-picker.js +1 -1
  9. package/lib/module/blocks/color-swatch-picker/color-swatch-picker.js.map +1 -1
  10. package/lib/module/blocks/copy-variant-picker/copy-variant-picker.js +4 -4
  11. package/lib/module/blocks/copy-variant-picker/copy-variant-picker.js.map +1 -1
  12. package/lib/module/blocks/credit-wallet/credit-wallet.js +1 -1
  13. package/lib/module/blocks/credit-wallet/credit-wallet.js.map +1 -1
  14. package/lib/module/blocks/generation-progress/generation-progress.js +4 -4
  15. package/lib/module/blocks/generation-progress/generation-progress.js.map +1 -1
  16. package/lib/module/blocks/image-grid/image-grid.js +11 -11
  17. package/lib/module/blocks/image-grid/image-grid.js.map +1 -1
  18. package/lib/module/blocks/internal/format.js +4 -0
  19. package/lib/module/blocks/internal/format.js.map +1 -1
  20. package/lib/module/blocks/invoice-row/invoice-row.js +5 -5
  21. package/lib/module/blocks/invoice-row/invoice-row.js.map +1 -1
  22. package/lib/module/blocks/logo-candidate-grid/logo-candidate-grid.js +1 -1
  23. package/lib/module/blocks/logo-candidate-grid/logo-candidate-grid.js.map +1 -1
  24. package/lib/module/blocks/oauth-buttons/oauth-buttons.js +2 -2
  25. package/lib/module/blocks/oauth-buttons/oauth-buttons.js.map +1 -1
  26. package/lib/module/blocks/option-editor/option-editor.js +3 -3
  27. package/lib/module/blocks/option-editor/option-editor.js.map +1 -1
  28. package/lib/module/blocks/order-card/index.js +1 -1
  29. package/lib/module/blocks/order-card/index.js.map +1 -1
  30. package/lib/module/blocks/order-card/order-card.js +31 -9
  31. package/lib/module/blocks/order-card/order-card.js.map +1 -1
  32. package/lib/module/blocks/plan-card/plan-card.js +3 -3
  33. package/lib/module/blocks/plan-card/plan-card.js.map +1 -1
  34. package/lib/module/blocks/product-list-empty/product-list-empty.js +5 -5
  35. package/lib/module/blocks/product-list-empty/product-list-empty.js.map +1 -1
  36. package/lib/module/blocks/review-row/review-row.js +17 -17
  37. package/lib/module/blocks/review-row/review-row.js.map +1 -1
  38. package/lib/module/blocks/sales-chart/sales-chart.js +3 -3
  39. package/lib/module/blocks/sales-chart/sales-chart.js.map +1 -1
  40. package/lib/module/blocks/selection-bar/selection-bar.js +1 -1
  41. package/lib/module/blocks/selection-bar/selection-bar.js.map +1 -1
  42. package/lib/module/blocks/service-state-banner/service-state-banner.js +1 -1
  43. package/lib/module/blocks/service-state-banner/service-state-banner.js.map +1 -1
  44. package/lib/module/blocks/shipping-tracking-row/shipping-tracking-row.js +1 -1
  45. package/lib/module/blocks/shipping-tracking-row/shipping-tracking-row.js.map +1 -1
  46. package/lib/module/blocks/site-preview-frame/site-preview-frame.js +1 -1
  47. package/lib/module/blocks/site-preview-frame/site-preview-frame.js.map +1 -1
  48. package/lib/module/blocks/stat-card/stat-card.js +1 -1
  49. package/lib/module/blocks/stat-card/stat-card.js.map +1 -1
  50. package/lib/module/blocks/step-screen/step-screen.js +18 -14
  51. package/lib/module/blocks/step-screen/step-screen.js.map +1 -1
  52. package/lib/module/blocks/supply-item-card/supply-item-card.js +5 -5
  53. package/lib/module/blocks/supply-item-card/supply-item-card.js.map +1 -1
  54. package/lib/module/components/button/button.js +15 -20
  55. package/lib/module/components/button/button.js.map +1 -1
  56. package/lib/module/components/chip/chip.js +2 -2
  57. package/lib/module/components/chip/chip.js.map +1 -1
  58. package/lib/module/components/dialog/dialog.js +6 -6
  59. package/lib/module/components/dialog/dialog.js.map +1 -1
  60. package/lib/module/components/empty-state/empty-state.js +4 -4
  61. package/lib/module/components/empty-state/empty-state.js.map +1 -1
  62. package/lib/module/components/field/field.js +20 -19
  63. package/lib/module/components/field/field.js.map +1 -1
  64. package/lib/module/components/list-row/index.js.map +1 -1
  65. package/lib/module/components/list-row/list-row.js +38 -10
  66. package/lib/module/components/list-row/list-row.js.map +1 -1
  67. package/lib/module/components/price/price.js +1 -1
  68. package/lib/module/components/price/price.js.map +1 -1
  69. package/lib/module/components/segmented-tabs/segmented-tabs.js +2 -2
  70. package/lib/module/components/segmented-tabs/segmented-tabs.js.map +1 -1
  71. package/lib/module/components/status-badge/status-badge.js +2 -2
  72. package/lib/module/components/status-badge/status-badge.js.map +1 -1
  73. package/lib/module/components/text/text.js +7 -2
  74. package/lib/module/components/text/text.js.map +1 -1
  75. package/lib/module/components/toast/toast.js +5 -5
  76. package/lib/module/components/toast/toast.js.map +1 -1
  77. package/lib/module/index.js +1 -0
  78. package/lib/module/index.js.map +1 -1
  79. package/lib/module/templates/editor-template.js +142 -0
  80. package/lib/module/templates/editor-template.js.map +1 -0
  81. package/lib/module/templates/index.js +9 -0
  82. package/lib/module/templates/index.js.map +1 -0
  83. package/lib/module/templates/list-template.js +98 -0
  84. package/lib/module/templates/list-template.js.map +1 -0
  85. package/lib/module/templates/parts.js +115 -0
  86. package/lib/module/templates/parts.js.map +1 -0
  87. package/lib/module/templates/result-template.js +233 -0
  88. package/lib/module/templates/result-template.js.map +1 -0
  89. package/lib/module/templates/scroll-templates.js +100 -0
  90. package/lib/module/templates/scroll-templates.js.map +1 -0
  91. package/lib/module/templates/system-template.js +64 -0
  92. package/lib/module/templates/system-template.js.map +1 -0
  93. package/lib/module/theme/base.js +141 -0
  94. package/lib/module/theme/base.js.map +1 -0
  95. package/lib/module/theme/contract.js +6 -0
  96. package/lib/module/theme/contract.js.map +1 -0
  97. package/lib/module/theme/tokens.js +18 -114
  98. package/lib/module/theme/tokens.js.map +1 -1
  99. package/lib/typescript/src/blocks/claim-row/claim-row.d.ts.map +1 -1
  100. package/lib/typescript/src/blocks/color-swatch-picker/color-swatch-picker.d.ts.map +1 -1
  101. package/lib/typescript/src/blocks/image-grid/image-grid.d.ts.map +1 -1
  102. package/lib/typescript/src/blocks/internal/format.d.ts +1 -0
  103. package/lib/typescript/src/blocks/internal/format.d.ts.map +1 -1
  104. package/lib/typescript/src/blocks/invoice-row/invoice-row.d.ts.map +1 -1
  105. package/lib/typescript/src/blocks/oauth-buttons/oauth-buttons.d.ts.map +1 -1
  106. package/lib/typescript/src/blocks/order-card/index.d.ts +1 -1
  107. package/lib/typescript/src/blocks/order-card/index.d.ts.map +1 -1
  108. package/lib/typescript/src/blocks/order-card/order-card.d.ts +10 -0
  109. package/lib/typescript/src/blocks/order-card/order-card.d.ts.map +1 -1
  110. package/lib/typescript/src/blocks/product-list-empty/product-list-empty.d.ts.map +1 -1
  111. package/lib/typescript/src/blocks/review-row/review-row.d.ts.map +1 -1
  112. package/lib/typescript/src/blocks/step-screen/step-screen.d.ts +3 -1
  113. package/lib/typescript/src/blocks/step-screen/step-screen.d.ts.map +1 -1
  114. package/lib/typescript/src/components/button/button.d.ts +2 -2
  115. package/lib/typescript/src/components/button/button.d.ts.map +1 -1
  116. package/lib/typescript/src/components/dialog/dialog.d.ts +2 -2
  117. package/lib/typescript/src/components/dialog/dialog.d.ts.map +1 -1
  118. package/lib/typescript/src/components/empty-state/empty-state.d.ts.map +1 -1
  119. package/lib/typescript/src/components/field/field.d.ts.map +1 -1
  120. package/lib/typescript/src/components/list-row/index.d.ts +1 -1
  121. package/lib/typescript/src/components/list-row/index.d.ts.map +1 -1
  122. package/lib/typescript/src/components/list-row/list-row.d.ts +4 -1
  123. package/lib/typescript/src/components/list-row/list-row.d.ts.map +1 -1
  124. package/lib/typescript/src/components/status-badge/status-badge.d.ts +2 -1
  125. package/lib/typescript/src/components/status-badge/status-badge.d.ts.map +1 -1
  126. package/lib/typescript/src/components/text/text.d.ts +1 -1
  127. package/lib/typescript/src/components/text/text.d.ts.map +1 -1
  128. package/lib/typescript/src/components/toast/toast.d.ts +2 -1
  129. package/lib/typescript/src/components/toast/toast.d.ts.map +1 -1
  130. package/lib/typescript/src/index.d.ts +1 -0
  131. package/lib/typescript/src/index.d.ts.map +1 -1
  132. package/lib/typescript/src/templates/editor-template.d.ts +22 -0
  133. package/lib/typescript/src/templates/editor-template.d.ts.map +1 -0
  134. package/lib/typescript/src/templates/index.d.ts +13 -0
  135. package/lib/typescript/src/templates/index.d.ts.map +1 -0
  136. package/lib/typescript/src/templates/list-template.d.ts +27 -0
  137. package/lib/typescript/src/templates/list-template.d.ts.map +1 -0
  138. package/lib/typescript/src/templates/parts.d.ts +27 -0
  139. package/lib/typescript/src/templates/parts.d.ts.map +1 -0
  140. package/lib/typescript/src/templates/result-template.d.ts +21 -0
  141. package/lib/typescript/src/templates/result-template.d.ts.map +1 -0
  142. package/lib/typescript/src/templates/scroll-templates.d.ts +32 -0
  143. package/lib/typescript/src/templates/scroll-templates.d.ts.map +1 -0
  144. package/lib/typescript/src/templates/system-template.d.ts +12 -0
  145. package/lib/typescript/src/templates/system-template.d.ts.map +1 -0
  146. package/lib/typescript/src/theme/base.d.ts +139 -0
  147. package/lib/typescript/src/theme/base.d.ts.map +1 -0
  148. package/lib/typescript/src/theme/contract.d.ts +7 -0
  149. package/lib/typescript/src/theme/contract.d.ts.map +1 -0
  150. package/lib/typescript/src/theme/tokens.d.ts.map +1 -1
  151. package/lib/typescript/src/types/index.d.ts +25 -3
  152. package/lib/typescript/src/types/index.d.ts.map +1 -1
  153. package/package.json +1 -1
  154. package/src/blocks/brand-profile-card/brand-profile-card.tsx +2 -2
  155. package/src/blocks/bulk-ship-list/bulk-ship-list.tsx +1 -1
  156. package/src/blocks/claim-row/claim-row.tsx +12 -3
  157. package/src/blocks/color-swatch-picker/color-swatch-picker.tsx +5 -1
  158. package/src/blocks/copy-variant-picker/copy-variant-picker.tsx +4 -4
  159. package/src/blocks/credit-wallet/credit-wallet.tsx +1 -1
  160. package/src/blocks/generation-progress/generation-progress.tsx +4 -4
  161. package/src/blocks/image-grid/image-grid.tsx +16 -9
  162. package/src/blocks/internal/format.ts +5 -0
  163. package/src/blocks/invoice-row/invoice-row.tsx +8 -4
  164. package/src/blocks/logo-candidate-grid/logo-candidate-grid.tsx +1 -1
  165. package/src/blocks/oauth-buttons/oauth-buttons.tsx +6 -2
  166. package/src/blocks/option-editor/option-editor.tsx +3 -3
  167. package/src/blocks/order-card/index.ts +4 -0
  168. package/src/blocks/order-card/order-card.tsx +50 -6
  169. package/src/blocks/plan-card/plan-card.tsx +3 -3
  170. package/src/blocks/product-list-empty/product-list-empty.tsx +11 -4
  171. package/src/blocks/review-row/review-row.tsx +26 -15
  172. package/src/blocks/sales-chart/sales-chart.tsx +3 -3
  173. package/src/blocks/selection-bar/selection-bar.tsx +1 -1
  174. package/src/blocks/service-state-banner/service-state-banner.tsx +1 -1
  175. package/src/blocks/shipping-tracking-row/shipping-tracking-row.tsx +1 -1
  176. package/src/blocks/site-preview-frame/site-preview-frame.tsx +1 -1
  177. package/src/blocks/stat-card/stat-card.tsx +1 -1
  178. package/src/blocks/step-screen/step-screen.tsx +24 -12
  179. package/src/blocks/supply-item-card/supply-item-card.tsx +5 -5
  180. package/src/components/button/button.tsx +24 -16
  181. package/src/components/chip/chip.tsx +2 -2
  182. package/src/components/dialog/dialog.tsx +7 -7
  183. package/src/components/empty-state/empty-state.tsx +8 -4
  184. package/src/components/field/field.tsx +20 -19
  185. package/src/components/list-row/index.ts +1 -1
  186. package/src/components/list-row/list-row.tsx +35 -8
  187. package/src/components/price/price.tsx +1 -1
  188. package/src/components/segmented-tabs/segmented-tabs.tsx +2 -2
  189. package/src/components/status-badge/status-badge.tsx +4 -4
  190. package/src/components/text/text.tsx +5 -2
  191. package/src/components/toast/toast.tsx +7 -6
  192. package/src/index.tsx +1 -0
  193. package/src/templates/editor-template.tsx +164 -0
  194. package/src/templates/index.ts +26 -0
  195. package/src/templates/list-template.tsx +124 -0
  196. package/src/templates/parts.tsx +138 -0
  197. package/src/templates/result-template.tsx +266 -0
  198. package/src/templates/scroll-templates.tsx +140 -0
  199. package/src/templates/system-template.tsx +70 -0
  200. package/src/theme/base.ts +149 -0
  201. package/src/theme/contract.ts +21 -0
  202. package/src/theme/tokens.ts +30 -81
  203. package/src/types/index.ts +17 -3
@@ -0,0 +1,140 @@
1
+ import type { ReactNode } from 'react';
2
+ import {
3
+ KeyboardAvoidingView,
4
+ RefreshControl,
5
+ ScrollView,
6
+ View,
7
+ } from 'react-native';
8
+ import { useTheme } from '../theme/theme-provider';
9
+ import { makeStyles } from '../utils/styles';
10
+ import {
11
+ BottomBar,
12
+ Notice,
13
+ type TemplateAction,
14
+ type TemplateNotice,
15
+ } from './parts';
16
+
17
+ type ScrollTemplateProps = {
18
+ top?: ReactNode;
19
+ notice?: TemplateNotice;
20
+ primaryAction?: TemplateAction;
21
+ secondaryAction?: TemplateAction;
22
+ refreshing?: boolean;
23
+ onRefresh?: () => void;
24
+ bottomInset?: number;
25
+ children: ReactNode;
26
+ };
27
+
28
+ const useStyles = makeStyles((t) => ({
29
+ root: { flex: 1, backgroundColor: t.colors.background },
30
+ content: { paddingBottom: t.layout.sectionGap },
31
+ top: {
32
+ flexDirection: 'row',
33
+ flexWrap: 'wrap',
34
+ gap: t.layout.itemGap,
35
+ paddingTop: t.space[2],
36
+ paddingHorizontal: t.layout.screenX,
37
+ },
38
+ notice: { paddingTop: t.layout.groupGap },
39
+ }));
40
+
41
+ function ScrollTemplate({
42
+ top,
43
+ notice,
44
+ primaryAction,
45
+ secondaryAction,
46
+ refreshing = false,
47
+ onRefresh,
48
+ bottomInset = 0,
49
+ children,
50
+ }: ScrollTemplateProps) {
51
+ const t = useTheme();
52
+ const s = useStyles();
53
+ return (
54
+ <KeyboardAvoidingView behavior="padding" style={s.root}>
55
+ <ScrollView
56
+ contentContainerStyle={[
57
+ s.content,
58
+ primaryAction
59
+ ? null
60
+ : { paddingBottom: t.layout.sectionGap + bottomInset },
61
+ ]}
62
+ keyboardShouldPersistTaps="handled"
63
+ refreshControl={
64
+ onRefresh ? (
65
+ <RefreshControl refreshing={refreshing} onRefresh={onRefresh} />
66
+ ) : undefined
67
+ }
68
+ >
69
+ {top ? <View style={s.top}>{top}</View> : null}
70
+ {notice ? (
71
+ <View style={s.notice}>
72
+ <Notice notice={notice} />
73
+ </View>
74
+ ) : null}
75
+ {children}
76
+ </ScrollView>
77
+ {primaryAction ? (
78
+ <BottomBar
79
+ primaryAction={primaryAction}
80
+ secondaryAction={secondaryAction}
81
+ bottomInset={bottomInset}
82
+ />
83
+ ) : null}
84
+ </KeyboardAvoidingView>
85
+ );
86
+ }
87
+
88
+ export type DetailTemplateProps = {
89
+ status?: ReactNode;
90
+ notice?: TemplateNotice;
91
+ primaryAction?: TemplateAction;
92
+ secondaryAction?: TemplateAction;
93
+ bottomInset?: number;
94
+ children: ReactNode;
95
+ };
96
+
97
+ export function DetailTemplate({ status, ...rest }: DetailTemplateProps) {
98
+ return <ScrollTemplate top={status} {...rest} />;
99
+ }
100
+
101
+ export type FormTemplateProps = {
102
+ notice?: TemplateNotice;
103
+ saveAction: TemplateAction;
104
+ bottomInset?: number;
105
+ children: ReactNode;
106
+ };
107
+
108
+ export function FormTemplate({ saveAction, ...rest }: FormTemplateProps) {
109
+ return <ScrollTemplate primaryAction={saveAction} {...rest} />;
110
+ }
111
+
112
+ export type MenuTemplateProps = {
113
+ bottomInset?: number;
114
+ children: ReactNode;
115
+ };
116
+
117
+ export function MenuTemplate(props: MenuTemplateProps) {
118
+ return <ScrollTemplate {...props} />;
119
+ }
120
+
121
+ export type DashboardTemplateProps = {
122
+ banner?: ReactNode;
123
+ refreshing?: boolean;
124
+ onRefresh?: () => void;
125
+ bottomInset?: number;
126
+ children: ReactNode;
127
+ };
128
+
129
+ export function DashboardTemplate({
130
+ banner,
131
+ children,
132
+ ...rest
133
+ }: DashboardTemplateProps) {
134
+ return (
135
+ <ScrollTemplate {...rest}>
136
+ {banner}
137
+ {children}
138
+ </ScrollTemplate>
139
+ );
140
+ }
@@ -0,0 +1,70 @@
1
+ import type { ReactNode } from 'react';
2
+ import { View } from 'react-native';
3
+ import { Text } from '../components/text/text';
4
+ import { renderIcon, type IconSlot } from '../internal/icon';
5
+ import { useTheme } from '../theme/theme-provider';
6
+ import { makeStyles } from '../utils/styles';
7
+ import { BottomBar, type TemplateAction } from './parts';
8
+
9
+ export type SystemTemplateProps = {
10
+ icon?: IconSlot;
11
+ title: string;
12
+ primaryAction?: TemplateAction;
13
+ actions?: ReactNode;
14
+ bottomInset?: number;
15
+ };
16
+
17
+ const useStyles = makeStyles((t) => ({
18
+ root: { flex: 1, backgroundColor: t.colors.background },
19
+ center: {
20
+ flex: 1,
21
+ alignItems: 'center',
22
+ justifyContent: 'center',
23
+ gap: t.layout.titleGap,
24
+ paddingHorizontal: t.layout.screenX,
25
+ },
26
+ title: { textAlign: 'center' },
27
+ actions: {
28
+ gap: t.layout.itemGap,
29
+ paddingHorizontal: t.layout.screenX,
30
+ paddingTop: t.layout.footerTop,
31
+ },
32
+ }));
33
+
34
+ export function SystemTemplate({
35
+ icon,
36
+ title,
37
+ primaryAction,
38
+ actions,
39
+ bottomInset = 0,
40
+ }: SystemTemplateProps) {
41
+ const t = useTheme();
42
+ const s = useStyles();
43
+ return (
44
+ <View style={s.root}>
45
+ <View style={s.center}>
46
+ {icon
47
+ ? renderIcon(icon, {
48
+ color: t.colors.foreground,
49
+ size: t.controlSize.lg,
50
+ })
51
+ : null}
52
+ <Text variant="screenTitle" accessibilityRole="header" style={s.title}>
53
+ {title}
54
+ </Text>
55
+ </View>
56
+ {actions ? (
57
+ <View
58
+ style={[
59
+ s.actions,
60
+ { paddingBottom: t.layout.footerBottom + bottomInset },
61
+ ]}
62
+ >
63
+ {actions}
64
+ </View>
65
+ ) : primaryAction ? (
66
+ <BottomBar primaryAction={primaryAction} bottomInset={bottomInset} />
67
+ ) : null}
68
+ </View>
69
+ );
70
+ }
@@ -0,0 +1,149 @@
1
+ export const semantic = {
2
+ light: {
3
+ background: '#ffffff',
4
+ foreground: '#0a0a0a',
5
+ muted: '#f5f5f5',
6
+ mutedForeground: '#525252',
7
+ border: '#e5e5e5',
8
+ input: '#d4d4d4',
9
+ ring: '#a3a3a3',
10
+ primary: '#171717',
11
+ primaryForeground: '#fafafa',
12
+ danger: '#b91c1c',
13
+ dangerForeground: '#ffffff',
14
+ success: '#15803d',
15
+ successForeground: '#ffffff',
16
+ warning: '#f59e0b',
17
+ warningForeground: '#0a0a0a',
18
+ warningText: '#b45309',
19
+ info: '#2563eb',
20
+ infoForeground: '#ffffff',
21
+ },
22
+ dark: {
23
+ background: '#0a0a0a',
24
+ foreground: '#fafafa',
25
+ muted: '#262626',
26
+ mutedForeground: '#a3a3a3',
27
+ border: '#262626',
28
+ input: '#404040',
29
+ ring: '#737373',
30
+ primary: '#fafafa',
31
+ primaryForeground: '#171717',
32
+ danger: '#f87171',
33
+ dangerForeground: '#0a0a0a',
34
+ success: '#4ade80',
35
+ successForeground: '#0a0a0a',
36
+ warning: '#fbbf24',
37
+ warningForeground: '#0a0a0a',
38
+ warningText: '#fbbf24',
39
+ info: '#60a5fa',
40
+ infoForeground: '#0a0a0a',
41
+ },
42
+ } as const;
43
+
44
+ export const space = {
45
+ '0': 0,
46
+ '1': 4,
47
+ '2': 8,
48
+ '3': 12,
49
+ '4': 16,
50
+ '5': 20,
51
+ '6': 24,
52
+ '8': 32,
53
+ '10': 40,
54
+ '12': 48,
55
+ '16': 64,
56
+ } as const;
57
+
58
+ export const radius = {
59
+ sm: 6,
60
+ md: 8,
61
+ lg: 12,
62
+ full: 9999,
63
+ } as const;
64
+
65
+ export const typography = {
66
+ caption: {
67
+ fontSize: 12,
68
+ lineHeight: 16,
69
+ fontWeight: '400',
70
+ },
71
+ label: {
72
+ fontSize: 14,
73
+ lineHeight: 20,
74
+ fontWeight: '400',
75
+ },
76
+ body: {
77
+ fontSize: 15,
78
+ lineHeight: 22,
79
+ fontWeight: '400',
80
+ },
81
+ bodyLg: {
82
+ fontSize: 17,
83
+ lineHeight: 24,
84
+ fontWeight: '400',
85
+ },
86
+ title: {
87
+ fontSize: 20,
88
+ lineHeight: 28,
89
+ fontWeight: '600',
90
+ },
91
+ screenTitle: {
92
+ fontSize: 24,
93
+ lineHeight: 32,
94
+ fontWeight: '700',
95
+ },
96
+ display: {
97
+ fontSize: 28,
98
+ lineHeight: 34,
99
+ fontWeight: '700',
100
+ },
101
+ } as const;
102
+
103
+ export const shadow = {
104
+ sm: '0px 1px 2px rgba(0, 0, 0, 0.08)',
105
+ md: '0px 4px 12px rgba(0, 0, 0, 0.12)',
106
+ } as const;
107
+
108
+ export const motion = {
109
+ duration: 200,
110
+ } as const;
111
+
112
+ export const opacity = {
113
+ pressed: 0.8,
114
+ disabled: 0.5,
115
+ } as const;
116
+
117
+ export const iconSize = {
118
+ sm: 16,
119
+ md: 20,
120
+ } as const;
121
+
122
+ export const touch = {
123
+ ios: 44,
124
+ android: 48,
125
+ } as const;
126
+
127
+ export const layout = {
128
+ screenX: 16,
129
+ screenTop: 24,
130
+ titleGap: 24,
131
+ sectionGap: 32,
132
+ groupGap: 12,
133
+ itemGap: 8,
134
+ footerTop: 12,
135
+ footerBottom: 16,
136
+ } as const;
137
+
138
+ export const controlSize = {
139
+ sm: 44,
140
+ md: 48,
141
+ lg: 52,
142
+ } as const;
143
+
144
+ export const frame = {
145
+ header: 52,
146
+ listRow: 56,
147
+ listRow2: 72,
148
+ listRow3: 88,
149
+ } as const;
@@ -0,0 +1,21 @@
1
+ export const TONES = [
2
+ 'neutral',
3
+ 'info',
4
+ 'success',
5
+ 'warning',
6
+ 'danger',
7
+ 'primary',
8
+ ] as const;
9
+ export type Tone = (typeof TONES)[number];
10
+
11
+ export const BUTTON_VARIANTS = [
12
+ 'primary',
13
+ 'secondary',
14
+ 'outline',
15
+ 'ghost',
16
+ 'danger',
17
+ ] as const;
18
+ export type ButtonVariant = (typeof BUTTON_VARIANTS)[number];
19
+
20
+ export const BUTTON_SIZES = ['sm', 'md', 'lg'] as const;
21
+ export type ButtonSize = (typeof BUTTON_SIZES)[number];
@@ -1,90 +1,39 @@
1
1
  import { Platform } from 'react-native';
2
2
  import type { ColorScheme, ThemeColors, ThemeTokens } from '../types';
3
+ import {
4
+ controlSize,
5
+ frame,
6
+ iconSize,
7
+ layout,
8
+ motion,
9
+ opacity,
10
+ radius,
11
+ semantic,
12
+ shadow,
13
+ space,
14
+ touch,
15
+ typography,
16
+ } from './base';
3
17
 
4
- const neutral = {
5
- 50: '#fafafa',
6
- 100: '#f5f5f5',
7
- 200: '#e5e5e5',
8
- 300: '#d4d4d4',
9
- 400: '#a3a3a3',
10
- 500: '#737373',
11
- 700: '#404040',
12
- 800: '#262626',
13
- 900: '#171717',
14
- 950: '#0a0a0a',
15
- };
16
-
17
- export const colors: Record<ColorScheme, ThemeColors> = {
18
- light: {
19
- background: '#ffffff',
20
- foreground: neutral[950],
21
- muted: neutral[100],
22
- mutedForeground: neutral[500],
23
- border: neutral[200],
24
- input: neutral[300],
25
- ring: neutral[400],
26
- primary: neutral[900],
27
- primaryForeground: neutral[50],
28
- destructive: '#dc2626',
29
- destructiveForeground: '#ffffff',
30
- success: '#15803d',
31
- successForeground: '#ffffff',
32
- warning: '#f59e0b',
33
- warningForeground: neutral[950],
34
- info: '#2563eb',
35
- infoForeground: '#ffffff',
36
- },
37
- dark: {
38
- background: neutral[950],
39
- foreground: neutral[50],
40
- muted: neutral[800],
41
- mutedForeground: neutral[400],
42
- border: neutral[800],
43
- input: neutral[700],
44
- ring: neutral[500],
45
- primary: neutral[50],
46
- primaryForeground: neutral[900],
47
- destructive: '#f87171',
48
- destructiveForeground: neutral[950],
49
- success: '#4ade80',
50
- successForeground: neutral[950],
51
- warning: '#fbbf24',
52
- warningForeground: neutral[950],
53
- info: '#60a5fa',
54
- infoForeground: neutral[950],
55
- },
56
- };
18
+ export const colors: Record<ColorScheme, ThemeColors> = semantic;
57
19
 
58
20
  export const tokens: ThemeTokens = {
59
- space: {
60
- 0: 0,
61
- 1: 4,
62
- 2: 8,
63
- 3: 12,
64
- 4: 16,
65
- 5: 20,
66
- 6: 24,
67
- 8: 32,
68
- 10: 40,
69
- 12: 48,
70
- 16: 64,
71
- },
72
- radius: { sm: 6, md: 8, lg: 12, full: 9999 },
73
- typography: {
74
- caption: { fontSize: 12, lineHeight: 16, fontWeight: '400' },
75
- body: { fontSize: 15, lineHeight: 22, fontWeight: '400' },
76
- bodyLg: { fontSize: 17, lineHeight: 24, fontWeight: '400' },
77
- title: { fontSize: 20, lineHeight: 28, fontWeight: '600' },
78
- display: { fontSize: 28, lineHeight: 34, fontWeight: '700' },
79
- },
21
+ space,
22
+ radius,
23
+ typography,
80
24
  fontFamily: undefined,
81
25
  maxFontScale: 1.3,
82
- shadow: {
83
- sm: '0px 1px 2px rgba(0, 0, 0, 0.08)',
84
- md: '0px 4px 12px rgba(0, 0, 0, 0.12)',
26
+ shadow,
27
+ motion,
28
+ opacity,
29
+ iconSize,
30
+ minTouchSize: Platform.OS === 'ios' ? touch.ios : touch.android,
31
+ layout,
32
+ controlSize,
33
+ headerHeight: frame.header,
34
+ listRow: {
35
+ oneLine: frame.listRow,
36
+ twoLine: frame.listRow2,
37
+ threeLine: frame.listRow3,
85
38
  },
86
- motion: { duration: 200 },
87
- opacity: { pressed: 0.8, disabled: 0.5 },
88
- iconSize: { sm: 16, md: 20 },
89
- minTouchSize: Platform.OS === 'ios' ? 44 : 48,
90
39
  };
@@ -12,18 +12,19 @@ export type ThemeColors = {
12
12
  ring: string;
13
13
  primary: string;
14
14
  primaryForeground: string;
15
- destructive: string;
16
- destructiveForeground: string;
15
+ danger: string;
16
+ dangerForeground: string;
17
17
  success: string;
18
18
  successForeground: string;
19
19
  warning: string;
20
20
  warningForeground: string;
21
+ warningText: string;
21
22
  info: string;
22
23
  infoForeground: string;
23
24
  };
24
25
 
25
26
  export type TypographyVariant =
26
- 'caption' | 'body' | 'bodyLg' | 'title' | 'display';
27
+ 'caption' | 'label' | 'body' | 'bodyLg' | 'title' | 'screenTitle' | 'display';
27
28
 
28
29
  export type TypographyToken = {
29
30
  fontSize: number;
@@ -54,6 +55,19 @@ export type ThemeTokens = {
54
55
  opacity: { pressed: number; disabled: number };
55
56
  iconSize: { sm: number; md: number };
56
57
  minTouchSize: number;
58
+ layout: {
59
+ screenX: number;
60
+ screenTop: number;
61
+ titleGap: number;
62
+ sectionGap: number;
63
+ groupGap: number;
64
+ itemGap: number;
65
+ footerTop: number;
66
+ footerBottom: number;
67
+ };
68
+ controlSize: { sm: number; md: number; lg: number };
69
+ headerHeight: number;
70
+ listRow: { oneLine: number; twoLine: number; threeLine: number };
57
71
  };
58
72
 
59
73
  export type Theme = ThemeTokens & {