astryx-dracula 0.1.3 → 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 (94) hide show
  1. package/BRAND.md +1 -1
  2. package/README.md +2 -0
  3. package/USAGE.md +13 -0
  4. package/astryx-dracula.js +4 -4
  5. package/astryx.integration.mjs +3 -0
  6. package/package.json +4 -2
  7. package/templates/ai-chat-landing.template.mjs +6 -0
  8. package/templates/ai-chat-landing.tsx +476 -0
  9. package/templates/ai-chat.template.mjs +6 -0
  10. package/templates/ai-chat.tsx +762 -0
  11. package/templates/blank.template.mjs +6 -0
  12. package/templates/blank.tsx +16 -0
  13. package/templates/centered-hero.template.mjs +6 -0
  14. package/templates/centered-hero.tsx +188 -0
  15. package/templates/classic-gallery.template.mjs +6 -0
  16. package/templates/classic-gallery.tsx +181 -0
  17. package/templates/contact-form.template.mjs +6 -0
  18. package/templates/contact-form.tsx +292 -0
  19. package/templates/dashboard-portfolio.template.mjs +6 -0
  20. package/templates/dashboard-portfolio.tsx +800 -0
  21. package/templates/dashboard.template.mjs +6 -0
  22. package/templates/dashboard.tsx +774 -0
  23. package/templates/detail-page.template.mjs +6 -0
  24. package/templates/detail-page.tsx +695 -0
  25. package/templates/documentation-design.template.mjs +6 -0
  26. package/templates/documentation-design.tsx +751 -0
  27. package/templates/documentation-technical.template.mjs +6 -0
  28. package/templates/documentation-technical.tsx +292 -0
  29. package/templates/documentation.template.mjs +6 -0
  30. package/templates/documentation.tsx +347 -0
  31. package/templates/editor.template.mjs +6 -0
  32. package/templates/editor.tsx +959 -0
  33. package/templates/file-explorer.template.mjs +6 -0
  34. package/templates/file-explorer.tsx +577 -0
  35. package/templates/form-two-column.template.mjs +6 -0
  36. package/templates/form-two-column.tsx +314 -0
  37. package/templates/gallery-hero.template.mjs +6 -0
  38. package/templates/gallery-hero.tsx +287 -0
  39. package/templates/ide.template.mjs +6 -0
  40. package/templates/ide.tsx +533 -0
  41. package/templates/incident-console.template.mjs +6 -0
  42. package/templates/incident-console.tsx +584 -0
  43. package/templates/kanban-board.template.mjs +6 -0
  44. package/templates/kanban-board.tsx +746 -0
  45. package/templates/library.template.mjs +6 -0
  46. package/templates/library.tsx +489 -0
  47. package/templates/login-card.template.mjs +6 -0
  48. package/templates/login-card.tsx +200 -0
  49. package/templates/login-split.template.mjs +6 -0
  50. package/templates/login-split.tsx +318 -0
  51. package/templates/login-sso.template.mjs +6 -0
  52. package/templates/login-sso.tsx +277 -0
  53. package/templates/login.template.mjs +6 -0
  54. package/templates/login.tsx +98 -0
  55. package/templates/messaging-shell.template.mjs +6 -0
  56. package/templates/messaging-shell.tsx +675 -0
  57. package/templates/mixed-gallery.template.mjs +6 -0
  58. package/templates/mixed-gallery.tsx +190 -0
  59. package/templates/payment-form.template.mjs +6 -0
  60. package/templates/payment-form.tsx +990 -0
  61. package/templates/product-detail.template.mjs +6 -0
  62. package/templates/product-detail.tsx +366 -0
  63. package/templates/product-gallery.template.mjs +6 -0
  64. package/templates/product-gallery.tsx +173 -0
  65. package/templates/settings-dialog.template.mjs +6 -0
  66. package/templates/settings-dialog.tsx +920 -0
  67. package/templates/settings-sidebar.template.mjs +6 -0
  68. package/templates/settings-sidebar.tsx +952 -0
  69. package/templates/settings.template.mjs +6 -0
  70. package/templates/settings.tsx +235 -0
  71. package/templates/shell-nav.template.mjs +6 -0
  72. package/templates/shell-nav.tsx +306 -0
  73. package/templates/shell-side-nav.template.mjs +6 -0
  74. package/templates/shell-side-nav.tsx +238 -0
  75. package/templates/shell-top-nav.template.mjs +6 -0
  76. package/templates/shell-top-nav.tsx +243 -0
  77. package/templates/side-gallery.template.mjs +6 -0
  78. package/templates/side-gallery.tsx +179 -0
  79. package/templates/table-grouped.template.mjs +6 -0
  80. package/templates/table-grouped.tsx +1174 -0
  81. package/templates/table-page-chart.template.mjs +6 -0
  82. package/templates/table-page-chart.tsx +693 -0
  83. package/templates/table-page-heatmap-status.template.mjs +6 -0
  84. package/templates/table-page-heatmap-status.tsx +547 -0
  85. package/templates/table-page-shoe-store-heatmap.template.mjs +6 -0
  86. package/templates/table-page-shoe-store-heatmap.tsx +1038 -0
  87. package/templates/table-page.template.mjs +6 -0
  88. package/templates/table-page.tsx +445 -0
  89. package/templates/table.template.mjs +6 -0
  90. package/templates/table.tsx +84 -0
  91. package/templates/theme-showcase.template.mjs +6 -0
  92. package/templates/theme-showcase.tsx +1282 -0
  93. package/theme.css +4 -4
  94. package/tokens.css +4 -4
@@ -0,0 +1,292 @@
1
+ // Copyright (c) Meta Platforms, Inc. and affiliates.
2
+
3
+ import {useState} from 'react';
4
+ import {VStack, HStack} from '@astryxdesign/core/Layout';
5
+ import {Center} from '@astryxdesign/core/Center';
6
+ import {Section} from '@astryxdesign/core/Section';
7
+ import {Grid} from '@astryxdesign/core/Grid';
8
+ import {Card} from '@astryxdesign/core/Card';
9
+ import {Button} from '@astryxdesign/core/Button';
10
+ import {Text} from '@astryxdesign/core/Text';
11
+ import {Icon} from '@astryxdesign/core/Icon';
12
+ import {TextInput} from '@astryxdesign/core/TextInput';
13
+ import {Selector} from '@astryxdesign/core/Selector';
14
+ import {CheckboxInput} from '@astryxdesign/core/CheckboxInput';
15
+ import {Link} from '@astryxdesign/core/Link';
16
+ import {Token} from '@astryxdesign/core/Token';
17
+ import {RadioList, RadioListItem} from '@astryxdesign/core/RadioList';
18
+ import {TextArea} from '@astryxdesign/core/TextArea';
19
+ import {Divider} from '@astryxdesign/core/Divider';
20
+ import {Banner} from '@astryxdesign/core/Banner';
21
+ import {Rocket, SlidersHorizontal, Hand} from 'lucide-react';
22
+
23
+ const CAMPAIGN_GOALS = [
24
+ 'Brand Awareness',
25
+ 'Product Sampling',
26
+ 'Product Launch',
27
+ 'Event Promotion',
28
+ 'Retail / In-Store',
29
+ 'Trade Show',
30
+ 'Influencer Activation',
31
+ 'Community Building',
32
+ 'Seasonal Campaign',
33
+ 'Other',
34
+ ];
35
+
36
+ const LAUNCH_OPTIONS = [
37
+ 'Within 30 days',
38
+ '1\u20133 months',
39
+ '3\u20136 months',
40
+ '6\u201312 months',
41
+ '12+ months',
42
+ ];
43
+
44
+ const BUDGET_OPTIONS = [
45
+ 'Under $5K/mo',
46
+ '$5K\u2013$15K/mo',
47
+ '$15K\u2013$50K/mo',
48
+ '$50K\u2013$100K/mo',
49
+ '$100K+/mo',
50
+ ];
51
+
52
+ const WHY_US = [
53
+ {
54
+ icon: Rocket,
55
+ title: 'We ship before sunrise',
56
+ description: 'We cut through the fog and land the work before dawn.',
57
+ },
58
+ {
59
+ icon: SlidersHorizontal,
60
+ title: 'We tune around you',
61
+ description: "Every dial set to what you're trying to summon.",
62
+ },
63
+ {
64
+ icon: Hand,
65
+ title: 'We answer after dark',
66
+ description: 'A dedicated coven that knows your brand and haunts your roadmap.',
67
+ },
68
+ ];
69
+
70
+ /**
71
+ * Contact Form — lead capture form template
72
+ */
73
+ export default function ContactForm() {
74
+ const [fullName, setFullName] = useState('');
75
+ const [email, setEmail] = useState('');
76
+ const [company, setCompany] = useState('');
77
+ const [phone, setPhone] = useState('');
78
+ const [goals, setGoals] = useState<string[]>([]);
79
+ const [timeline, setTimeline] = useState('');
80
+ const [budget, setBudget] = useState('');
81
+ const [message, setMessage] = useState('');
82
+ const [hearAboutUs, setHearAboutUs] = useState('');
83
+ const [isDecider, setIsDecider] = useState(false);
84
+ const [submitted, setSubmitted] = useState(false);
85
+
86
+ const errors = submitted
87
+ ? {
88
+ fullName: !fullName.trim() ? 'Required' : undefined,
89
+ email: !email.trim() ? 'Required' : undefined,
90
+ company: !company.trim() ? 'Required' : undefined,
91
+ phone: !phone.trim() ? 'Required' : undefined,
92
+ goals: goals.length === 0 ? 'Pick at least one' : undefined,
93
+ timeline: !timeline ? 'Required' : undefined,
94
+ budget: !budget ? 'Required' : undefined,
95
+ }
96
+ : {};
97
+
98
+ const toggleGoal = (goal: string) =>
99
+ setGoals(prev =>
100
+ prev.includes(goal) ? prev.filter(g => g !== goal) : [...prev, goal],
101
+ );
102
+
103
+ return (
104
+ <Center axis="horizontal">
105
+ <VStack hAlign="center" width="100%">
106
+ <Section
107
+ maxWidth={800}
108
+ width="100%"
109
+ padding={6}
110
+ paddingBlock={10}
111
+ variant="section">
112
+ <VStack gap={6}>
113
+ {/* Header */}
114
+ <VStack gap={2} hAlign="center" style={{textAlign: 'center'}}>
115
+ <Text type="display-1" weight="bold">
116
+ Let&apos;s brew after dark
117
+ </Text>
118
+ <Text type="body" color="secondary">
119
+ Tell us a bit about what you&apos;re summoning — the coven
120
+ would love to help it take flight.
121
+ </Text>
122
+ </VStack>
123
+
124
+ {/* Why work with us */}
125
+ <VStack gap={5}>
126
+ <Grid columns={{minWidth: 200}} gap={4}>
127
+ {WHY_US.map(item => (
128
+ <Card key={item.title}>
129
+ <VStack gap={3}>
130
+ <Icon icon={item.icon} size="lg" color="accent" />
131
+ <VStack gap={1}>
132
+ <Text type="body" weight="bold">
133
+ {item.title}
134
+ </Text>
135
+ <Text type="supporting" color="secondary">
136
+ {item.description}
137
+ </Text>
138
+ </VStack>
139
+ </VStack>
140
+ </Card>
141
+ ))}
142
+ </Grid>
143
+ </VStack>
144
+
145
+ {/* Your details */}
146
+ <VStack gap={5}>
147
+ <Grid columns={{minWidth: 260}} gap={4}>
148
+ <TextInput
149
+ label="Full Name"
150
+ placeholder="Full Name"
151
+ value={fullName}
152
+ onChange={setFullName}
153
+ status={
154
+ errors.fullName
155
+ ? {type: 'error', message: errors.fullName}
156
+ : undefined
157
+ }
158
+ />
159
+ <TextInput
160
+ label="Email"
161
+ placeholder="you@company.com"
162
+ value={email}
163
+ onChange={setEmail}
164
+ status={
165
+ errors.email
166
+ ? {type: 'error', message: errors.email}
167
+ : undefined
168
+ }
169
+ />
170
+ </Grid>
171
+ <Grid columns={{minWidth: 260}} gap={4}>
172
+ <TextInput
173
+ label="Company"
174
+ placeholder="Company"
175
+ value={company}
176
+ onChange={setCompany}
177
+ status={
178
+ errors.company
179
+ ? {type: 'error', message: errors.company}
180
+ : undefined
181
+ }
182
+ />
183
+ <TextInput
184
+ label="Phone"
185
+ placeholder="Phone number"
186
+ value={phone}
187
+ onChange={setPhone}
188
+ status={
189
+ errors.phone
190
+ ? {type: 'error', message: errors.phone}
191
+ : undefined
192
+ }
193
+ />
194
+ </Grid>
195
+ </VStack>
196
+
197
+ <Divider />
198
+
199
+ {/* Your project */}
200
+ <VStack gap={5}>
201
+ <VStack gap={2}>
202
+ <Text type="label" color="secondary">
203
+ What are you going for?
204
+ </Text>
205
+ <HStack gap={2} wrap="wrap">
206
+ {CAMPAIGN_GOALS.map(goal => (
207
+ <Token
208
+ key={goal}
209
+ label={goal}
210
+ color={goals.includes(goal) ? 'yellow' : 'default'}
211
+ onClick={() => toggleGoal(goal)}
212
+ />
213
+ ))}
214
+ </HStack>
215
+ {errors.goals && <Banner status="error" title={errors.goals} />}
216
+ </VStack>
217
+
218
+ <Selector
219
+ label="When are you thinking?"
220
+ placeholder="When are you thinking of launching?"
221
+ options={LAUNCH_OPTIONS}
222
+ value={timeline}
223
+ onChange={setTimeline}
224
+ status={
225
+ errors.timeline
226
+ ? {type: 'error', message: errors.timeline}
227
+ : undefined
228
+ }
229
+ />
230
+
231
+ <Selector
232
+ label="Ballpark budget?"
233
+ placeholder="What's your rough monthly budget?"
234
+ options={BUDGET_OPTIONS}
235
+ value={budget}
236
+ onChange={setBudget}
237
+ status={
238
+ errors.budget
239
+ ? {type: 'error', message: errors.budget}
240
+ : undefined
241
+ }
242
+ />
243
+
244
+ <RadioList
245
+ label="How did you hear about us?"
246
+ value={hearAboutUs}
247
+ onChange={setHearAboutUs}>
248
+ <RadioListItem label="Social media" value="social" />
249
+ <RadioListItem label="Word of mouth" value="word-of-mouth" />
250
+ <RadioListItem label="Search engine" value="search" />
251
+ <RadioListItem label="Event or conference" value="event" />
252
+ <RadioListItem label="Other" value="other" />
253
+ </RadioList>
254
+
255
+ <TextArea
256
+ label="Anything else?"
257
+ placeholder="Tell us whatever else is on your mind..."
258
+ value={message}
259
+ onChange={setMessage}
260
+ />
261
+
262
+ <CheckboxInput
263
+ label="I'm a budget decision-maker"
264
+ value={isDecider}
265
+ onChange={setIsDecider}
266
+ />
267
+ </VStack>
268
+
269
+ {/* Submit */}
270
+ <VStack gap={3}>
271
+ <Button
272
+ label="Submit"
273
+ variant="primary"
274
+ size="lg"
275
+ onClick={() => setSubmitted(true)}
276
+ />
277
+ <HStack gap={1} hAlign="center">
278
+ <Text type="supporting" color="secondary">
279
+ By submitting you agree to our{' '}
280
+ <Link href="#/templates/contact-form" type="supporting">
281
+ Privacy Policy
282
+ </Link>
283
+ .
284
+ </Text>
285
+ </HStack>
286
+ </VStack>
287
+ </VStack>
288
+ </Section>
289
+ </VStack>
290
+ </Center>
291
+ );
292
+ }
@@ -0,0 +1,6 @@
1
+ export default {
2
+ type: 'page',
3
+ name: 'Portfolio Dashboard',
4
+ description: 'Holdings chart, market cards, and trending table',
5
+ category: 'dashboard',
6
+ };