@app-studio/web 0.9.17 → 0.9.19
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/components/AuthGuard/index.d.ts +1 -1
- package/dist/utils/request.d.ts +2 -2
- package/dist/web.cjs.development.js +41 -46
- package/dist/web.cjs.development.js.map +1 -1
- package/dist/web.cjs.production.min.js +1 -1
- package/dist/web.cjs.production.min.js.map +1 -1
- package/dist/web.esm.js +43 -48
- package/dist/web.esm.js.map +1 -1
- package/dist/web.umd.development.js +45 -45
- package/dist/web.umd.development.js.map +1 -1
- package/dist/web.umd.production.min.js +1 -1
- package/dist/web.umd.production.min.js.map +1 -1
- package/docs/README.md +52 -0
- package/docs/adk-components.md +316 -0
- package/docs/adk-quick-start.md +294 -0
- package/docs/api-integration.md +801 -0
- package/docs/api-reference/README.md +103 -0
- package/docs/api-reference/data-display/flow.md +220 -0
- package/docs/api-reference/data-display/tree.md +210 -0
- package/docs/api-reference/form/chat-input.md +210 -0
- package/docs/api-reference/utility/button.md +145 -0
- package/docs/api-reference/utility/title.md +301 -0
- package/docs/app-studio.md +302 -0
- package/docs/component-development/guide.md +546 -0
- package/docs/contributing/documentation.md +153 -0
- package/docs/conventions.md +536 -0
- package/docs/design-system/theming.md +299 -0
- package/docs/documentation-system.md +143 -0
- package/docs/getting-started/component-usage.md +211 -0
- package/docs/getting-started/introduction.md +114 -0
- package/docs/guide.md +550 -0
- package/docs/integration-guide.md +449 -0
- package/docs/tutorials/README.md +51 -0
- package/docs/tutorials/basic/creating-a-simple-form.md +566 -0
- package/package.json +3 -2
|
@@ -0,0 +1,546 @@
|
|
|
1
|
+
# Component Development Guide
|
|
2
|
+
|
|
3
|
+
This guide provides a comprehensive overview of how to build components for the `@src/components/` directory, following the established patterns and best practices in the codebase.
|
|
4
|
+
|
|
5
|
+
## Table of Contents
|
|
6
|
+
|
|
7
|
+
1. [Component Architecture](#component-architecture)
|
|
8
|
+
2. [File Structure](#file-structure)
|
|
9
|
+
3. [Component Creation Process](#component-creation-process)
|
|
10
|
+
4. [Styling Approach](#styling-approach)
|
|
11
|
+
5. [State Management](#state-management)
|
|
12
|
+
6. [Accessibility Considerations](#accessibility-considerations)
|
|
13
|
+
7. [Examples and Documentation](#examples-and-documentation)
|
|
14
|
+
8. [Utility Scripts](#utility-scripts)
|
|
15
|
+
9. [Component Integration](#component-integration)
|
|
16
|
+
10. [Best Practices](#best-practices)
|
|
17
|
+
|
|
18
|
+
## Component Architecture
|
|
19
|
+
|
|
20
|
+
Components in this library follow a clear separation of concerns with a structured architecture:
|
|
21
|
+
|
|
22
|
+
- **Main Component File**: Orchestrates state and view, exports the public API
|
|
23
|
+
- **Props**: Defines the component's API and TypeScript interfaces
|
|
24
|
+
- **State**: Manages component-specific state through custom hooks
|
|
25
|
+
- **View**: Handles the presentational aspects of the component
|
|
26
|
+
- **Style**: Contains style constants, mappings, and theme definitions
|
|
27
|
+
- **Types**: Defines TypeScript types and enums for the component
|
|
28
|
+
|
|
29
|
+
This architecture promotes maintainability, reusability, and clear separation between logic and presentation.
|
|
30
|
+
|
|
31
|
+
## File Structure
|
|
32
|
+
|
|
33
|
+
Each component follows a consistent file structure:
|
|
34
|
+
|
|
35
|
+
```
|
|
36
|
+
ComponentName/
|
|
37
|
+
├── ComponentName.tsx # Main component file (exports public API)
|
|
38
|
+
├── ComponentName/ # Inner folder for core files
|
|
39
|
+
│ ├── ComponentName.props.ts # Props interface definitions
|
|
40
|
+
│ ├── ComponentName.state.ts # Custom state hook
|
|
41
|
+
│ ├── ComponentName.view.tsx # Presentational component
|
|
42
|
+
│ ├── ComponentName.style.ts # Style constants and theme mappings
|
|
43
|
+
│ └── ComponentName.type.ts # TypeScript type definitions
|
|
44
|
+
└── examples/ # Usage examples
|
|
45
|
+
├── default.tsx # Default usage example
|
|
46
|
+
├── variant.tsx # Variant-specific example
|
|
47
|
+
├── size.tsx # Size-specific example
|
|
48
|
+
└── index.ts # Exports all examples
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
## Component Creation Process
|
|
52
|
+
|
|
53
|
+
### 1. Plan Your Component
|
|
54
|
+
|
|
55
|
+
Before writing code, define:
|
|
56
|
+
- The component's purpose and functionality
|
|
57
|
+
- Required props and their types
|
|
58
|
+
- State management needs
|
|
59
|
+
- Visual variants (size, shape, color, etc.)
|
|
60
|
+
- Accessibility requirements
|
|
61
|
+
|
|
62
|
+
### 2. Create Component Structure
|
|
63
|
+
|
|
64
|
+
Use the provided script to scaffold the component structure:
|
|
65
|
+
|
|
66
|
+
```bash
|
|
67
|
+
npm run create-structure -- ComponentName
|
|
68
|
+
```
|
|
69
|
+
|
|
70
|
+
This creates the basic file structure with placeholder content.
|
|
71
|
+
|
|
72
|
+
### 3. Define Types and Props
|
|
73
|
+
|
|
74
|
+
In `ComponentName.type.ts`:
|
|
75
|
+
```typescript
|
|
76
|
+
export type Size = 'xs' | 'sm' | 'md' | 'lg' | 'xl';
|
|
77
|
+
export type Variant = 'default' | 'primary' | 'secondary';
|
|
78
|
+
export type Shape = 'sharp' | 'rounded' | 'pillShaped';
|
|
79
|
+
|
|
80
|
+
export interface ComponentNameStyles {
|
|
81
|
+
container?: ViewProps;
|
|
82
|
+
label?: ViewProps;
|
|
83
|
+
icon?: ViewProps;
|
|
84
|
+
// Add other style override points as needed
|
|
85
|
+
}
|
|
86
|
+
```
|
|
87
|
+
|
|
88
|
+
In `ComponentName.props.ts`:
|
|
89
|
+
```typescript
|
|
90
|
+
import { ViewProps } from 'app-studio';
|
|
91
|
+
import { Size, Variant, Shape, ComponentNameStyles } from './ComponentName.type';
|
|
92
|
+
|
|
93
|
+
export interface ComponentNameProps extends ViewProps {
|
|
94
|
+
/**
|
|
95
|
+
* Size variant of the component
|
|
96
|
+
* @default 'md'
|
|
97
|
+
*/
|
|
98
|
+
size?: Size;
|
|
99
|
+
|
|
100
|
+
/**
|
|
101
|
+
* Visual style variant
|
|
102
|
+
* @default 'default'
|
|
103
|
+
*/
|
|
104
|
+
variant?: Variant;
|
|
105
|
+
|
|
106
|
+
/**
|
|
107
|
+
* Shape of the component
|
|
108
|
+
* @default 'rounded'
|
|
109
|
+
*/
|
|
110
|
+
shape?: Shape;
|
|
111
|
+
|
|
112
|
+
/**
|
|
113
|
+
* Whether the component is disabled
|
|
114
|
+
* @default false
|
|
115
|
+
*/
|
|
116
|
+
isDisabled?: boolean;
|
|
117
|
+
|
|
118
|
+
/**
|
|
119
|
+
* Custom styles for different parts of the component
|
|
120
|
+
*/
|
|
121
|
+
views?: ComponentNameStyles;
|
|
122
|
+
|
|
123
|
+
/**
|
|
124
|
+
* Optional theme mode override ('light' or 'dark')
|
|
125
|
+
* If not provided, the component will use the theme mode from context
|
|
126
|
+
*/
|
|
127
|
+
themeMode?: 'light' | 'dark';
|
|
128
|
+
|
|
129
|
+
// Add other props as needed
|
|
130
|
+
}
|
|
131
|
+
```
|
|
132
|
+
|
|
133
|
+
### 4. Implement State Management
|
|
134
|
+
|
|
135
|
+
In `ComponentName.state.ts`:
|
|
136
|
+
```typescript
|
|
137
|
+
import { useState, useCallback } from 'react';
|
|
138
|
+
|
|
139
|
+
export interface ComponentNameStateProps {
|
|
140
|
+
// Add any props needed for state initialization
|
|
141
|
+
defaultValue?: string;
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
export const useComponentNameState = (props: ComponentNameStateProps = {}) => {
|
|
145
|
+
const { defaultValue = '' } = props;
|
|
146
|
+
|
|
147
|
+
const [value, setValue] = useState(defaultValue);
|
|
148
|
+
const [isHovered, setIsHovered] = useState(false);
|
|
149
|
+
const [isFocused, setIsFocused] = useState(false);
|
|
150
|
+
|
|
151
|
+
const handleHover = useCallback((isHovering: boolean) => {
|
|
152
|
+
setIsHovered(isHovering);
|
|
153
|
+
}, []);
|
|
154
|
+
|
|
155
|
+
const handleFocus = useCallback((isFocusing: boolean) => {
|
|
156
|
+
setIsFocused(isFocusing);
|
|
157
|
+
}, []);
|
|
158
|
+
|
|
159
|
+
return {
|
|
160
|
+
value,
|
|
161
|
+
setValue,
|
|
162
|
+
isHovered,
|
|
163
|
+
isFocused,
|
|
164
|
+
handleHover,
|
|
165
|
+
handleFocus
|
|
166
|
+
};
|
|
167
|
+
};
|
|
168
|
+
```
|
|
169
|
+
|
|
170
|
+
### 5. Create Style Definitions
|
|
171
|
+
|
|
172
|
+
In `ComponentName.style.ts`:
|
|
173
|
+
```typescript
|
|
174
|
+
import { ViewProps } from 'app-studio';
|
|
175
|
+
import { Size, Variant, Shape } from './ComponentName.type';
|
|
176
|
+
|
|
177
|
+
// Size mappings
|
|
178
|
+
export const ComponentNameSizes: Record<Size, ViewProps> = {
|
|
179
|
+
xs: { padding: '4px 8px', fontSize: 12 },
|
|
180
|
+
sm: { padding: '6px 12px', fontSize: 14 },
|
|
181
|
+
md: { padding: '8px 16px', fontSize: 16 },
|
|
182
|
+
lg: { padding: '10px 20px', fontSize: 18 },
|
|
183
|
+
xl: { padding: '12px 24px', fontSize: 20 },
|
|
184
|
+
};
|
|
185
|
+
|
|
186
|
+
// Shape mappings
|
|
187
|
+
export const ComponentNameShapes: Record<Shape, ViewProps> = {
|
|
188
|
+
sharp: { borderRadius: 0 },
|
|
189
|
+
rounded: { borderRadius: 4 },
|
|
190
|
+
pillShaped: { borderRadius: 9999 },
|
|
191
|
+
};
|
|
192
|
+
|
|
193
|
+
// Get variant styles based on theme mode
|
|
194
|
+
export const getComponentNameVariants = (themeMode: 'light' | 'dark') => {
|
|
195
|
+
const isDark = themeMode === 'dark';
|
|
196
|
+
|
|
197
|
+
return {
|
|
198
|
+
default: {
|
|
199
|
+
backgroundColor: isDark ? 'color.gray.800' : 'color.gray.100',
|
|
200
|
+
color: isDark ? 'color.gray.100' : 'color.gray.800',
|
|
201
|
+
borderColor: isDark ? 'color.gray.700' : 'color.gray.300',
|
|
202
|
+
},
|
|
203
|
+
primary: {
|
|
204
|
+
backgroundColor: 'theme.primary',
|
|
205
|
+
color: 'color.white',
|
|
206
|
+
borderColor: 'theme.primary',
|
|
207
|
+
},
|
|
208
|
+
secondary: {
|
|
209
|
+
backgroundColor: 'theme.secondary',
|
|
210
|
+
color: 'color.white',
|
|
211
|
+
borderColor: 'theme.secondary',
|
|
212
|
+
},
|
|
213
|
+
};
|
|
214
|
+
};
|
|
215
|
+
```
|
|
216
|
+
|
|
217
|
+
### 6. Implement the View Component
|
|
218
|
+
|
|
219
|
+
In `ComponentName.view.tsx`:
|
|
220
|
+
```typescript
|
|
221
|
+
import React from 'react';
|
|
222
|
+
import { View, Horizontal, Vertical, useTheme } from 'app-studio';
|
|
223
|
+
import { ComponentNameProps } from './ComponentName.props';
|
|
224
|
+
import {
|
|
225
|
+
ComponentNameSizes,
|
|
226
|
+
ComponentNameShapes,
|
|
227
|
+
getComponentNameVariants
|
|
228
|
+
} from './ComponentName.style';
|
|
229
|
+
|
|
230
|
+
export const ComponentNameView: React.FC<ComponentNameProps> = ({
|
|
231
|
+
size = 'md',
|
|
232
|
+
variant = 'default',
|
|
233
|
+
shape = 'rounded',
|
|
234
|
+
isDisabled = false,
|
|
235
|
+
children,
|
|
236
|
+
views = {},
|
|
237
|
+
themeMode: elementMode,
|
|
238
|
+
...props
|
|
239
|
+
}) => {
|
|
240
|
+
// Access theme context
|
|
241
|
+
const { themeMode } = useTheme();
|
|
242
|
+
const currentThemeMode = elementMode || themeMode;
|
|
243
|
+
|
|
244
|
+
// Get styles based on props
|
|
245
|
+
const sizeStyles = ComponentNameSizes[size];
|
|
246
|
+
const shapeStyles = ComponentNameShapes[shape];
|
|
247
|
+
const variantStyles = getComponentNameVariants(currentThemeMode)[variant];
|
|
248
|
+
|
|
249
|
+
return (
|
|
250
|
+
<View
|
|
251
|
+
// Base styles
|
|
252
|
+
display="flex"
|
|
253
|
+
alignItems="center"
|
|
254
|
+
justifyContent="center"
|
|
255
|
+
opacity={isDisabled ? 0.5 : 1}
|
|
256
|
+
cursor={isDisabled ? 'not-allowed' : 'pointer'}
|
|
257
|
+
transition="all 0.2s ease"
|
|
258
|
+
|
|
259
|
+
// Variant-specific styles
|
|
260
|
+
{...sizeStyles}
|
|
261
|
+
{...shapeStyles}
|
|
262
|
+
{...variantStyles}
|
|
263
|
+
|
|
264
|
+
// Custom style overrides
|
|
265
|
+
{...views?.container}
|
|
266
|
+
|
|
267
|
+
// Pass through remaining props
|
|
268
|
+
{...props}
|
|
269
|
+
>
|
|
270
|
+
{children}
|
|
271
|
+
</View>
|
|
272
|
+
);
|
|
273
|
+
};
|
|
274
|
+
```
|
|
275
|
+
|
|
276
|
+
### 7. Create the Main Component
|
|
277
|
+
|
|
278
|
+
In `ComponentName.tsx`:
|
|
279
|
+
```typescript
|
|
280
|
+
import React from 'react';
|
|
281
|
+
import { ComponentNameProps } from './ComponentName/ComponentName.props';
|
|
282
|
+
import { useComponentNameState } from './ComponentName/ComponentName.state';
|
|
283
|
+
import { ComponentNameView } from './ComponentName/ComponentName.view';
|
|
284
|
+
|
|
285
|
+
/**
|
|
286
|
+
* ComponentName component description
|
|
287
|
+
*/
|
|
288
|
+
const ComponentNameComponent: React.FC<ComponentNameProps> = (props) => {
|
|
289
|
+
// Initialize component state
|
|
290
|
+
const state = useComponentNameState();
|
|
291
|
+
|
|
292
|
+
// Return the view with state and props
|
|
293
|
+
return <ComponentNameView {...state} {...props} />;
|
|
294
|
+
};
|
|
295
|
+
|
|
296
|
+
export const ComponentName = ComponentNameComponent;
|
|
297
|
+
```
|
|
298
|
+
|
|
299
|
+
### 8. Create Examples
|
|
300
|
+
|
|
301
|
+
In `examples/default.tsx`:
|
|
302
|
+
```typescript
|
|
303
|
+
import React from 'react';
|
|
304
|
+
import { ComponentName } from '../ComponentName';
|
|
305
|
+
|
|
306
|
+
export const DefaultDemo = () => {
|
|
307
|
+
return <ComponentName>Default Example</ComponentName>;
|
|
308
|
+
};
|
|
309
|
+
```
|
|
310
|
+
|
|
311
|
+
In `examples/variant.tsx`:
|
|
312
|
+
```typescript
|
|
313
|
+
import React from 'react';
|
|
314
|
+
import { ComponentName } from '../ComponentName';
|
|
315
|
+
import { Horizontal } from 'app-studio';
|
|
316
|
+
|
|
317
|
+
export const VariantDemo = () => {
|
|
318
|
+
return (
|
|
319
|
+
<Horizontal gap={10}>
|
|
320
|
+
<ComponentName variant="default">Default</ComponentName>
|
|
321
|
+
<ComponentName variant="primary">Primary</ComponentName>
|
|
322
|
+
<ComponentName variant="secondary">Secondary</ComponentName>
|
|
323
|
+
</Horizontal>
|
|
324
|
+
);
|
|
325
|
+
};
|
|
326
|
+
```
|
|
327
|
+
|
|
328
|
+
## Styling Approach
|
|
329
|
+
|
|
330
|
+
Components in this library use a consistent styling approach:
|
|
331
|
+
|
|
332
|
+
### App-Studio Layout Components
|
|
333
|
+
|
|
334
|
+
Use the layout components from `app-studio` for consistent layout:
|
|
335
|
+
- `View`: Base container component
|
|
336
|
+
- `Horizontal`: Horizontal flex container
|
|
337
|
+
- `Vertical`: Vertical flex container
|
|
338
|
+
- `Center`: Centered flex container
|
|
339
|
+
|
|
340
|
+
### Theme Integration
|
|
341
|
+
|
|
342
|
+
Use the theme system via `useTheme` hook:
|
|
343
|
+
```typescript
|
|
344
|
+
const { getColor, themeMode } = useTheme();
|
|
345
|
+
const colorValue = getColor('theme.primary', { themeMode });
|
|
346
|
+
```
|
|
347
|
+
|
|
348
|
+
### Style Customization
|
|
349
|
+
|
|
350
|
+
Allow style customization through the `views` prop:
|
|
351
|
+
```typescript
|
|
352
|
+
<View
|
|
353
|
+
{...defaultStyles}
|
|
354
|
+
{...views?.container}
|
|
355
|
+
{...props}
|
|
356
|
+
>
|
|
357
|
+
<Text {...views?.label}>{label}</Text>
|
|
358
|
+
</View>
|
|
359
|
+
```
|
|
360
|
+
|
|
361
|
+
### Style Constants
|
|
362
|
+
|
|
363
|
+
Define style constants in `.style.ts` files:
|
|
364
|
+
```typescript
|
|
365
|
+
export const ComponentSizes = {
|
|
366
|
+
sm: { height: 30, fontSize: 14 },
|
|
367
|
+
md: { height: 40, fontSize: 16 },
|
|
368
|
+
lg: { height: 50, fontSize: 18 },
|
|
369
|
+
};
|
|
370
|
+
```
|
|
371
|
+
|
|
372
|
+
## State Management
|
|
373
|
+
|
|
374
|
+
### Component-Specific State
|
|
375
|
+
|
|
376
|
+
Use custom hooks for component-specific state:
|
|
377
|
+
```typescript
|
|
378
|
+
export const useComponentState = (initialState = {}) => {
|
|
379
|
+
const [value, setValue] = useState(initialState.value || '');
|
|
380
|
+
const [isOpen, setIsOpen] = useState(initialState.isOpen || false);
|
|
381
|
+
|
|
382
|
+
return { value, setValue, isOpen, setIsOpen };
|
|
383
|
+
};
|
|
384
|
+
```
|
|
385
|
+
|
|
386
|
+
### Global State
|
|
387
|
+
|
|
388
|
+
For components that need global state (like Toast, Modal), use Zustand:
|
|
389
|
+
```typescript
|
|
390
|
+
export const useToastStore = create<ToastState>((set) => ({
|
|
391
|
+
toasts: [],
|
|
392
|
+
addToast: (toast) => set((state) => ({
|
|
393
|
+
toasts: [...state.toasts, toast]
|
|
394
|
+
})),
|
|
395
|
+
removeToast: (id) => set((state) => ({
|
|
396
|
+
toasts: state.toasts.filter(toast => toast.id !== id)
|
|
397
|
+
})),
|
|
398
|
+
}));
|
|
399
|
+
```
|
|
400
|
+
|
|
401
|
+
## Accessibility Considerations
|
|
402
|
+
|
|
403
|
+
Ensure components are accessible:
|
|
404
|
+
|
|
405
|
+
- Use semantic HTML elements
|
|
406
|
+
- Add proper ARIA attributes
|
|
407
|
+
- Support keyboard navigation
|
|
408
|
+
- Ensure sufficient color contrast
|
|
409
|
+
- Provide text alternatives for non-text content
|
|
410
|
+
- Make focus states visible
|
|
411
|
+
|
|
412
|
+
Example:
|
|
413
|
+
```typescript
|
|
414
|
+
<View
|
|
415
|
+
role="button"
|
|
416
|
+
aria-disabled={isDisabled}
|
|
417
|
+
tabIndex={isDisabled ? -1 : 0}
|
|
418
|
+
onKeyDown={(e) => {
|
|
419
|
+
if (e.key === 'Enter' || e.key === ' ') {
|
|
420
|
+
onClick?.();
|
|
421
|
+
}
|
|
422
|
+
}}
|
|
423
|
+
{...props}
|
|
424
|
+
>
|
|
425
|
+
{children}
|
|
426
|
+
</View>
|
|
427
|
+
```
|
|
428
|
+
|
|
429
|
+
## Examples and Documentation
|
|
430
|
+
|
|
431
|
+
### Component Examples
|
|
432
|
+
|
|
433
|
+
Create examples for each significant prop or feature:
|
|
434
|
+
- `default.tsx`: Basic usage
|
|
435
|
+
- `variant.tsx`: Different variants
|
|
436
|
+
- `size.tsx`: Different sizes
|
|
437
|
+
- `isDisabled.tsx`: Disabled state
|
|
438
|
+
|
|
439
|
+
### Example Index
|
|
440
|
+
|
|
441
|
+
Export all examples from `examples/index.ts`:
|
|
442
|
+
```typescript
|
|
443
|
+
export * from './default';
|
|
444
|
+
export * from './variant';
|
|
445
|
+
export * from './size';
|
|
446
|
+
export * from './isDisabled';
|
|
447
|
+
```
|
|
448
|
+
|
|
449
|
+
## Utility Scripts
|
|
450
|
+
|
|
451
|
+
The codebase provides several utility scripts to help with component development:
|
|
452
|
+
|
|
453
|
+
### Create Component Structure
|
|
454
|
+
|
|
455
|
+
```bash
|
|
456
|
+
npm run create-structure -- ComponentName
|
|
457
|
+
```
|
|
458
|
+
|
|
459
|
+
### Create Examples
|
|
460
|
+
|
|
461
|
+
```bash
|
|
462
|
+
npm run create-example -- ComponentName
|
|
463
|
+
```
|
|
464
|
+
|
|
465
|
+
### Create Index Files
|
|
466
|
+
|
|
467
|
+
```bash
|
|
468
|
+
npm run create-indices
|
|
469
|
+
```
|
|
470
|
+
|
|
471
|
+
### Create Component Pages
|
|
472
|
+
|
|
473
|
+
```bash
|
|
474
|
+
npm run create-pages
|
|
475
|
+
```
|
|
476
|
+
|
|
477
|
+
## Component Integration
|
|
478
|
+
|
|
479
|
+
### Compound Components
|
|
480
|
+
|
|
481
|
+
For complex components, use the compound component pattern:
|
|
482
|
+
|
|
483
|
+
```typescript
|
|
484
|
+
const CardComponent: React.FC<CardProps> = (props) => {
|
|
485
|
+
return <CardView {...props} />;
|
|
486
|
+
};
|
|
487
|
+
|
|
488
|
+
export const Card = CardComponent as CardType;
|
|
489
|
+
|
|
490
|
+
// Assign the sub-components to the main component
|
|
491
|
+
Card.Header = CardHeader;
|
|
492
|
+
Card.Content = CardContent;
|
|
493
|
+
Card.Footer = CardFooter;
|
|
494
|
+
```
|
|
495
|
+
|
|
496
|
+
### Context Integration
|
|
497
|
+
|
|
498
|
+
For components that need to share state between sub-components, use React Context:
|
|
499
|
+
|
|
500
|
+
```typescript
|
|
501
|
+
// Create context
|
|
502
|
+
const ComponentContext = createContext<ComponentContextType | undefined>(undefined);
|
|
503
|
+
|
|
504
|
+
// Provider component
|
|
505
|
+
export const ComponentProvider: React.FC<{ children: React.ReactNode }> = ({ children }) => {
|
|
506
|
+
const state = useComponentState();
|
|
507
|
+
return (
|
|
508
|
+
<ComponentContext.Provider value={state}>
|
|
509
|
+
{children}
|
|
510
|
+
</ComponentContext.Provider>
|
|
511
|
+
);
|
|
512
|
+
};
|
|
513
|
+
|
|
514
|
+
// Hook to use the context
|
|
515
|
+
export const useComponentContext = () => {
|
|
516
|
+
const context = useContext(ComponentContext);
|
|
517
|
+
if (!context) {
|
|
518
|
+
throw new Error('useComponentContext must be used within a ComponentProvider');
|
|
519
|
+
}
|
|
520
|
+
return context;
|
|
521
|
+
};
|
|
522
|
+
```
|
|
523
|
+
|
|
524
|
+
## Best Practices
|
|
525
|
+
|
|
526
|
+
### Do's
|
|
527
|
+
|
|
528
|
+
- ✅ Follow the established file structure
|
|
529
|
+
- ✅ Use TypeScript for type safety
|
|
530
|
+
- ✅ Document props with TSDoc comments
|
|
531
|
+
- ✅ Use app-studio layout components
|
|
532
|
+
- ✅ Separate logic from presentation
|
|
533
|
+
- ✅ Make components accessible
|
|
534
|
+
- ✅ Allow style customization via the `views` prop
|
|
535
|
+
- ✅ Use theme variables for colors
|
|
536
|
+
- ✅ Create comprehensive examples
|
|
537
|
+
|
|
538
|
+
### Don'ts
|
|
539
|
+
|
|
540
|
+
- ❌ Use global CSS (except when absolutely necessary)
|
|
541
|
+
- ❌ Mix state logic with presentation
|
|
542
|
+
- ❌ Hardcode colors or sizes
|
|
543
|
+
- ❌ Ignore accessibility
|
|
544
|
+
- ❌ Create overly complex components
|
|
545
|
+
- ❌ Duplicate functionality that exists in other components
|
|
546
|
+
- ❌ Use direct DOM manipulation
|
|
@@ -0,0 +1,153 @@
|
|
|
1
|
+
# Contributing to Documentation
|
|
2
|
+
|
|
3
|
+
This guide explains how to contribute to the documentation for the App Studio Web Component Library.
|
|
4
|
+
|
|
5
|
+
## Documentation Structure
|
|
6
|
+
|
|
7
|
+
The documentation is organized into the following sections:
|
|
8
|
+
|
|
9
|
+
- **Getting Started**: Quick start guides for new users
|
|
10
|
+
- **Component Development**: Guides for building components
|
|
11
|
+
- **Design System**: Information about theming and styling
|
|
12
|
+
- **API Reference**: Detailed API documentation for all components
|
|
13
|
+
- **Tutorials**: Step-by-step tutorials for common tasks
|
|
14
|
+
- **Contributing**: Guidelines for contributing to the library
|
|
15
|
+
|
|
16
|
+
## Documentation Tools
|
|
17
|
+
|
|
18
|
+
The documentation uses the following tools:
|
|
19
|
+
|
|
20
|
+
- **Markdown**: Most documentation is written in Markdown format
|
|
21
|
+
- **MDX**: Component documentation uses MDX for interactive examples
|
|
22
|
+
- **bot-doc**: Automated documentation generation tool
|
|
23
|
+
|
|
24
|
+
## Writing Documentation
|
|
25
|
+
|
|
26
|
+
When writing documentation, follow these guidelines:
|
|
27
|
+
|
|
28
|
+
### General Guidelines
|
|
29
|
+
|
|
30
|
+
- Use clear, concise language
|
|
31
|
+
- Use proper grammar and spelling
|
|
32
|
+
- Use consistent terminology
|
|
33
|
+
- Use headings to organize content
|
|
34
|
+
- Include examples where appropriate
|
|
35
|
+
- Link to related documentation
|
|
36
|
+
|
|
37
|
+
### Markdown Formatting
|
|
38
|
+
|
|
39
|
+
- Use `#` for top-level headings, `##` for second-level headings, etc.
|
|
40
|
+
- Use backticks for inline code: `` `code` ``
|
|
41
|
+
- Use triple backticks for code blocks:
|
|
42
|
+
```
|
|
43
|
+
```jsx
|
|
44
|
+
// Code here
|
|
45
|
+
```
|
|
46
|
+
```
|
|
47
|
+
- Use `*` or `_` for emphasis: *italic* or _italic_
|
|
48
|
+
- Use `**` or `__` for strong emphasis: **bold** or __bold__
|
|
49
|
+
- Use `>` for blockquotes
|
|
50
|
+
- Use `- ` for unordered lists
|
|
51
|
+
- Use `1. ` for ordered lists
|
|
52
|
+
- Use `[text](url)` for links
|
|
53
|
+
- Use `` for images
|
|
54
|
+
|
|
55
|
+
### Component Documentation
|
|
56
|
+
|
|
57
|
+
Component documentation should include:
|
|
58
|
+
|
|
59
|
+
1. **Import** - How to import the component
|
|
60
|
+
2. **Props** - Detailed list of props with types and descriptions
|
|
61
|
+
3. **Examples** - Basic usage examples
|
|
62
|
+
4. **Variants** - Available variants and their usage
|
|
63
|
+
5. **Compound Components** - Sub-components (if applicable)
|
|
64
|
+
6. **Accessibility** - Accessibility features and considerations
|
|
65
|
+
7. **Best Practices** - Recommended usage patterns
|
|
66
|
+
|
|
67
|
+
Example:
|
|
68
|
+
|
|
69
|
+
```mdx
|
|
70
|
+
# Button
|
|
71
|
+
|
|
72
|
+
The Button component is used to trigger an action or event.
|
|
73
|
+
|
|
74
|
+
## Import
|
|
75
|
+
|
|
76
|
+
```jsx
|
|
77
|
+
import { Button } from '@app-studio/web';
|
|
78
|
+
```
|
|
79
|
+
|
|
80
|
+
## Props
|
|
81
|
+
|
|
82
|
+
| Prop | Type | Default | Description |
|
|
83
|
+
| ---- | ---- | ------- | ----------- |
|
|
84
|
+
| variant | 'filled' \| 'outline' \| 'ghost' \| 'link' | 'filled' | The visual style of the button |
|
|
85
|
+
| size | 'xs' \| 'sm' \| 'md' \| 'lg' \| 'xl' | 'md' | The size of the button |
|
|
86
|
+
| isDisabled | boolean | false | Whether the button is disabled |
|
|
87
|
+
| isLoading | boolean | false | Whether the button is in a loading state |
|
|
88
|
+
|
|
89
|
+
## Examples
|
|
90
|
+
|
|
91
|
+
### Basic Button
|
|
92
|
+
|
|
93
|
+
```jsx
|
|
94
|
+
<Button onClick={() => alert('Button clicked!')}>Click Me</Button>
|
|
95
|
+
```
|
|
96
|
+
|
|
97
|
+
### Button Variants
|
|
98
|
+
|
|
99
|
+
```jsx
|
|
100
|
+
<>
|
|
101
|
+
<Button variant="filled">Filled</Button>
|
|
102
|
+
<Button variant="outline">Outline</Button>
|
|
103
|
+
<Button variant="ghost">Ghost</Button>
|
|
104
|
+
<Button variant="link">Link</Button>
|
|
105
|
+
</>
|
|
106
|
+
```
|
|
107
|
+
```
|
|
108
|
+
|
|
109
|
+
## Generating Component Documentation
|
|
110
|
+
|
|
111
|
+
Component documentation is automatically generated using the `bot-doc` tool. To generate documentation for a component:
|
|
112
|
+
|
|
113
|
+
```bash
|
|
114
|
+
npm run bot-doc -- ComponentName src/components/ComponentName
|
|
115
|
+
```
|
|
116
|
+
|
|
117
|
+
To regenerate documentation for all components:
|
|
118
|
+
|
|
119
|
+
```bash
|
|
120
|
+
npm run create-docs
|
|
121
|
+
```
|
|
122
|
+
|
|
123
|
+
## Documentation Review Process
|
|
124
|
+
|
|
125
|
+
Before submitting documentation changes, review your changes for:
|
|
126
|
+
|
|
127
|
+
1. **Accuracy**: Ensure the information is correct
|
|
128
|
+
2. **Completeness**: Ensure all relevant information is included
|
|
129
|
+
3. **Clarity**: Ensure the information is easy to understand
|
|
130
|
+
4. **Consistency**: Ensure the style and terminology are consistent
|
|
131
|
+
5. **Examples**: Ensure examples are clear and work as expected
|
|
132
|
+
|
|
133
|
+
## Submitting Documentation Changes
|
|
134
|
+
|
|
135
|
+
To submit documentation changes:
|
|
136
|
+
|
|
137
|
+
1. Create a branch for your changes
|
|
138
|
+
2. Make your changes
|
|
139
|
+
3. Test your changes locally
|
|
140
|
+
4. Commit your changes with a clear commit message
|
|
141
|
+
5. Push your changes to your branch
|
|
142
|
+
6. Create a pull request
|
|
143
|
+
|
|
144
|
+
## Documentation Best Practices
|
|
145
|
+
|
|
146
|
+
- **Be concise**: Use clear, direct language
|
|
147
|
+
- **Use examples**: Include code examples for complex concepts
|
|
148
|
+
- **Be consistent**: Use consistent terminology and formatting
|
|
149
|
+
- **Link related content**: Add links to related documentation
|
|
150
|
+
- **Update related docs**: When changing one document, update related documents
|
|
151
|
+
- **Test code examples**: Ensure all code examples work as expected
|
|
152
|
+
- **Use proper grammar**: Check spelling and grammar
|
|
153
|
+
- **Use proper formatting**: Use consistent Markdown formatting
|