@a11ypros/a11y-ui-components 1.0.1 → 1.0.2

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 (217) hide show
  1. package/README.md +182 -157
  2. package/dist/components/Button/Button.d.ts +37 -0
  3. package/dist/components/Button/Button.d.ts.map +1 -0
  4. package/dist/components/Button/Button.js +52 -0
  5. package/dist/components/Button/index.d.ts +3 -0
  6. package/dist/components/Button/index.d.ts.map +1 -0
  7. package/dist/components/Button/index.js +1 -0
  8. package/dist/components/DataTable/DataTable.d.ts +71 -0
  9. package/dist/components/DataTable/DataTable.d.ts.map +1 -0
  10. package/dist/components/DataTable/DataTable.js +122 -0
  11. package/dist/components/DataTable/index.d.ts +3 -0
  12. package/dist/components/DataTable/index.d.ts.map +1 -0
  13. package/dist/components/DataTable/index.js +1 -0
  14. package/dist/components/Form/Checkbox.d.ts +36 -0
  15. package/dist/components/Form/Checkbox.d.ts.map +1 -0
  16. package/dist/components/Form/Checkbox.js +39 -0
  17. package/dist/components/Form/Fieldset.d.ts +33 -0
  18. package/dist/components/Form/Fieldset.d.ts.map +1 -0
  19. package/dist/components/Form/Fieldset.js +34 -0
  20. package/dist/components/Form/Input.d.ts +37 -0
  21. package/dist/components/Form/Input.d.ts.map +1 -0
  22. package/dist/components/Form/Input.js +41 -0
  23. package/dist/components/Form/Label.d.ts +30 -0
  24. package/dist/components/Form/Label.d.ts.map +1 -0
  25. package/dist/components/Form/Label.js +30 -0
  26. package/dist/components/Form/Radio.d.ts +53 -0
  27. package/dist/components/Form/Radio.d.ts.map +1 -0
  28. package/dist/components/Form/Radio.js +39 -0
  29. package/dist/components/Form/Select.d.ts +51 -0
  30. package/dist/components/Form/Select.d.ts.map +1 -0
  31. package/dist/components/Form/Select.js +49 -0
  32. package/dist/components/Form/Textarea.d.ts +44 -0
  33. package/dist/components/Form/Textarea.d.ts.map +1 -0
  34. package/dist/components/Form/Textarea.js +43 -0
  35. package/dist/components/Form/index.d.ts +8 -0
  36. package/dist/components/Form/index.d.ts.map +1 -0
  37. package/dist/components/Form/index.js +7 -0
  38. package/dist/components/Link/Link.d.ts +34 -0
  39. package/dist/components/Link/Link.d.ts.map +1 -0
  40. package/dist/components/Link/Link.js +48 -0
  41. package/dist/components/Link/index.d.ts +3 -0
  42. package/dist/components/Link/index.d.ts.map +1 -0
  43. package/dist/components/Link/index.js +1 -0
  44. package/dist/components/Modal/Modal.d.ts +64 -0
  45. package/dist/components/Modal/Modal.d.ts.map +1 -0
  46. package/dist/components/Modal/Modal.js +108 -0
  47. package/dist/components/Modal/index.d.ts +3 -0
  48. package/dist/components/Modal/index.d.ts.map +1 -0
  49. package/dist/components/Modal/index.js +1 -0
  50. package/dist/components/Tabs/Tabs.d.ts +63 -0
  51. package/dist/components/Tabs/Tabs.d.ts.map +1 -0
  52. package/dist/components/Tabs/Tabs.js +134 -0
  53. package/dist/components/Tabs/index.d.ts +3 -0
  54. package/dist/components/Tabs/index.d.ts.map +1 -0
  55. package/dist/components/Tabs/index.js +1 -0
  56. package/dist/components/Toast/Toast.d.ts +59 -0
  57. package/dist/components/Toast/Toast.d.ts.map +1 -0
  58. package/dist/components/Toast/Toast.js +91 -0
  59. package/dist/components/Toast/ToastProvider.d.ts +22 -0
  60. package/dist/components/Toast/ToastProvider.d.ts.map +1 -0
  61. package/dist/components/Toast/ToastProvider.js +33 -0
  62. package/dist/components/Toast/index.d.ts +5 -0
  63. package/dist/components/Toast/index.d.ts.map +1 -0
  64. package/dist/components/Toast/index.js +2 -0
  65. package/dist/hooks/useAriaLive.d.ts +9 -0
  66. package/dist/hooks/useAriaLive.d.ts.map +1 -0
  67. package/dist/hooks/useAriaLive.js +39 -0
  68. package/dist/hooks/useFocusReturn.d.ts +9 -0
  69. package/dist/hooks/useFocusReturn.d.ts.map +1 -0
  70. package/dist/hooks/useFocusReturn.js +33 -0
  71. package/dist/hooks/useFocusTrap.d.ts +9 -0
  72. package/dist/hooks/useFocusTrap.d.ts.map +1 -0
  73. package/dist/hooks/useFocusTrap.js +68 -0
  74. package/dist/index.d.ts +22 -0
  75. package/dist/index.d.ts.map +1 -0
  76. package/{packages/design-system/src/index.ts → dist/index.js} +0 -4
  77. package/dist/styles/index.d.ts +3 -0
  78. package/dist/styles/index.d.ts.map +1 -0
  79. package/dist/styles/index.js +1 -0
  80. package/dist/tokens/breakpoints.d.ts +25 -0
  81. package/dist/tokens/breakpoints.d.ts.map +1 -0
  82. package/dist/tokens/breakpoints.js +23 -0
  83. package/dist/tokens/colors.d.ts +81 -0
  84. package/dist/tokens/colors.d.ts.map +1 -0
  85. package/dist/tokens/colors.js +86 -0
  86. package/dist/tokens/index.d.ts +6 -0
  87. package/dist/tokens/index.d.ts.map +1 -0
  88. package/dist/tokens/index.js +5 -0
  89. package/dist/tokens/motion.d.ts +30 -0
  90. package/dist/tokens/motion.d.ts.map +1 -0
  91. package/dist/tokens/motion.js +34 -0
  92. package/dist/tokens/spacing.d.ts +22 -0
  93. package/dist/tokens/spacing.d.ts.map +1 -0
  94. package/dist/tokens/spacing.js +20 -0
  95. package/dist/tokens/theme.d.ts +159 -0
  96. package/dist/tokens/theme.d.ts.map +1 -0
  97. package/dist/tokens/theme.js +15 -0
  98. package/dist/tokens/typography.d.ts +45 -0
  99. package/dist/tokens/typography.d.ts.map +1 -0
  100. package/dist/tokens/typography.js +56 -0
  101. package/dist/utils/aria.d.ts +60 -0
  102. package/dist/utils/aria.d.ts.map +1 -0
  103. package/dist/utils/aria.js +86 -0
  104. package/dist/utils/focus.d.ts +30 -0
  105. package/dist/utils/focus.d.ts.map +1 -0
  106. package/dist/utils/focus.js +80 -0
  107. package/dist/utils/index.d.ts +4 -0
  108. package/dist/utils/index.d.ts.map +1 -0
  109. package/dist/utils/index.js +3 -0
  110. package/dist/utils/keyboard.d.ts +38 -0
  111. package/dist/utils/keyboard.d.ts.map +1 -0
  112. package/dist/utils/keyboard.js +59 -0
  113. package/package.json +58 -31
  114. package/.storybook/custom.css +0 -69
  115. package/.storybook/main.ts +0 -46
  116. package/.storybook/manager.ts +0 -26
  117. package/.storybook/package.json +0 -6
  118. package/.storybook/preview.tsx +0 -31
  119. package/.storybook/public/logo.png +0 -0
  120. package/.storybook/vite.config.ts +0 -24
  121. package/.storybook/welcome.mdx +0 -97
  122. package/DEPLOYMENT.md +0 -154
  123. package/apps/web/app/(docs)/audit/audit.css +0 -269
  124. package/apps/web/app/(docs)/audit/page.tsx +0 -271
  125. package/apps/web/app/(docs)/components/button/page.tsx +0 -49
  126. package/apps/web/app/(docs)/components/form/page.tsx +0 -92
  127. package/apps/web/app/(docs)/components/link/page.tsx +0 -31
  128. package/apps/web/app/(docs)/components/modal/page.tsx +0 -41
  129. package/apps/web/app/(docs)/components/page.tsx +0 -37
  130. package/apps/web/app/(docs)/components/table/page.tsx +0 -54
  131. package/apps/web/app/(docs)/components/tabs/page.tsx +0 -61
  132. package/apps/web/app/(docs)/components/toast/page.tsx +0 -51
  133. package/apps/web/app/api/audit/route.ts +0 -128
  134. package/apps/web/app/favicon.ico +0 -0
  135. package/apps/web/app/layout.tsx +0 -20
  136. package/apps/web/app/page.tsx +0 -17
  137. package/apps/web/app/styles/globals.css +0 -5
  138. package/apps/web/next-env.d.ts +0 -5
  139. package/apps/web/next.config.js +0 -21
  140. package/apps/web/package.json +0 -28
  141. package/apps/web/public/_headers +0 -17
  142. package/apps/web/public/_redirects +0 -31
  143. package/apps/web/public/logo.png +0 -0
  144. package/apps/web/tsconfig.json +0 -29
  145. package/netlify/functions/audit.ts +0 -163
  146. package/netlify.toml +0 -37
  147. package/packages/design-system/README.md +0 -252
  148. package/packages/design-system/package.json +0 -68
  149. package/packages/design-system/scripts/copy-css.js +0 -63
  150. package/packages/design-system/src/components/Button/Button.stories.tsx +0 -228
  151. package/packages/design-system/src/components/Button/Button.tsx +0 -137
  152. package/packages/design-system/src/components/Button/index.ts +0 -3
  153. package/packages/design-system/src/components/DataTable/DataTable.stories.tsx +0 -211
  154. package/packages/design-system/src/components/DataTable/DataTable.tsx +0 -293
  155. package/packages/design-system/src/components/DataTable/index.ts +0 -3
  156. package/packages/design-system/src/components/Form/Checkbox.stories.tsx +0 -252
  157. package/packages/design-system/src/components/Form/Checkbox.tsx +0 -114
  158. package/packages/design-system/src/components/Form/Fieldset.stories.tsx +0 -210
  159. package/packages/design-system/src/components/Form/Fieldset.tsx +0 -71
  160. package/packages/design-system/src/components/Form/Input.stories.tsx +0 -164
  161. package/packages/design-system/src/components/Form/Input.tsx +0 -113
  162. package/packages/design-system/src/components/Form/Label.tsx +0 -56
  163. package/packages/design-system/src/components/Form/Radio.stories.tsx +0 -265
  164. package/packages/design-system/src/components/Form/Radio.tsx +0 -147
  165. package/packages/design-system/src/components/Form/Select.stories.tsx +0 -295
  166. package/packages/design-system/src/components/Form/Select.tsx +0 -160
  167. package/packages/design-system/src/components/Form/Textarea.stories.tsx +0 -253
  168. package/packages/design-system/src/components/Form/Textarea.tsx +0 -145
  169. package/packages/design-system/src/components/Form/index.ts +0 -8
  170. package/packages/design-system/src/components/Link/Link.stories.tsx +0 -128
  171. package/packages/design-system/src/components/Link/Link.tsx +0 -117
  172. package/packages/design-system/src/components/Link/index.ts +0 -3
  173. package/packages/design-system/src/components/Modal/Modal.stories.tsx +0 -165
  174. package/packages/design-system/src/components/Modal/Modal.tsx +0 -202
  175. package/packages/design-system/src/components/Modal/index.ts +0 -3
  176. package/packages/design-system/src/components/Tabs/Tabs.stories.tsx +0 -213
  177. package/packages/design-system/src/components/Tabs/Tabs.tsx +0 -248
  178. package/packages/design-system/src/components/Tabs/index.ts +0 -3
  179. package/packages/design-system/src/components/Toast/Toast.stories.tsx +0 -153
  180. package/packages/design-system/src/components/Toast/Toast.tsx +0 -175
  181. package/packages/design-system/src/components/Toast/ToastProvider.tsx +0 -73
  182. package/packages/design-system/src/components/Toast/index.ts +0 -5
  183. package/packages/design-system/src/hooks/useAriaLive.ts +0 -51
  184. package/packages/design-system/src/hooks/useFocusReturn.ts +0 -40
  185. package/packages/design-system/src/hooks/useFocusTrap.ts +0 -82
  186. package/packages/design-system/src/styles/index.ts +0 -3
  187. package/packages/design-system/src/tokens/breakpoints.ts +0 -28
  188. package/packages/design-system/src/tokens/colors.ts +0 -98
  189. package/packages/design-system/src/tokens/index.ts +0 -6
  190. package/packages/design-system/src/tokens/motion.ts +0 -41
  191. package/packages/design-system/src/tokens/spacing.ts +0 -24
  192. package/packages/design-system/src/tokens/theme.ts +0 -19
  193. package/packages/design-system/src/tokens/typography.ts +0 -64
  194. package/packages/design-system/src/utils/aria.ts +0 -108
  195. package/packages/design-system/src/utils/focus.ts +0 -87
  196. package/packages/design-system/src/utils/index.ts +0 -4
  197. package/packages/design-system/src/utils/keyboard.ts +0 -77
  198. package/packages/design-system/tsconfig.json +0 -17
  199. package/public/logo.png +0 -0
  200. package/scripts/fix-storybook-paths.js +0 -53
  201. package/tsconfig.json +0 -20
  202. /package/{packages/design-system/src → dist}/components/Button/Button.css +0 -0
  203. /package/{packages/design-system/src → dist}/components/DataTable/DataTable.css +0 -0
  204. /package/{packages/design-system/src → dist}/components/Form/Checkbox.css +0 -0
  205. /package/{packages/design-system/src → dist}/components/Form/Fieldset.css +0 -0
  206. /package/{packages/design-system/src → dist}/components/Form/Input.css +0 -0
  207. /package/{packages/design-system/src → dist}/components/Form/Label.css +0 -0
  208. /package/{packages/design-system/src → dist}/components/Form/Radio.css +0 -0
  209. /package/{packages/design-system/src → dist}/components/Form/Select.css +0 -0
  210. /package/{packages/design-system/src → dist}/components/Form/Textarea.css +0 -0
  211. /package/{packages/design-system/src → dist}/components/Link/Link.css +0 -0
  212. /package/{packages/design-system/src → dist}/components/Modal/Modal.css +0 -0
  213. /package/{packages/design-system/src → dist}/components/Tabs/Tabs.css +0 -0
  214. /package/{packages/design-system/src → dist}/components/Toast/Toast.css +0 -0
  215. /package/{packages/design-system/src → dist}/components/Toast/ToastProvider.css +0 -0
  216. /package/{packages/design-system/src → dist}/styles/components.css +0 -0
  217. /package/{packages/design-system/src → dist}/styles/global.css +0 -0
@@ -1,31 +0,0 @@
1
- # Storybook redirects - must be in public/ to be included in build
2
- # IMPORTANT: Order matters! More specific rules must come first
3
-
4
- # Storybook JSON files (must come before catch-all)
5
- # Storybook may request these from root
6
- /index.json /storybook-static/index.json 200
7
- /project.json /storybook-static/project.json 200
8
-
9
- # Storybook iframe.html - must come before other Storybook rules
10
- # Storybook loads components in an iframe with query parameters
11
- /iframe.html /storybook-static/iframe.html 200
12
- /storybook/iframe.html /storybook-static/iframe.html 200
13
-
14
- # Storybook root path
15
- /storybook /storybook-static/index.html 200
16
-
17
- # Storybook sub-paths (JS files, assets, etc.)
18
- # This catches /storybook/sb-manager/runtime.js → /storybook-static/sb-manager/runtime.js
19
- /storybook/* /storybook-static/:splat 200
20
-
21
- # Netlify Function for audit API
22
- /api/audit /.netlify/functions/audit 200
23
-
24
- # Storybook static files (ensures they're served correctly)
25
- /storybook-static/* /storybook-static/:splat 200
26
-
27
- # Next.js SPA fallback (must be last)
28
- # Note: This will catch everything else, including Storybook query params
29
- # But Storybook iframe.html should be handled above
30
- /* /index.html 200
31
-
Binary file
@@ -1,29 +0,0 @@
1
- {
2
- "extends": "../../tsconfig.json",
3
- "compilerOptions": {
4
- "target": "ES2017",
5
- "lib": ["dom", "dom.iterable", "esnext"],
6
- "allowJs": true,
7
- "skipLibCheck": true,
8
- "strict": true,
9
- "noEmit": true,
10
- "esModuleInterop": true,
11
- "module": "esnext",
12
- "moduleResolution": "bundler",
13
- "resolveJsonModule": true,
14
- "isolatedModules": true,
15
- "jsx": "preserve",
16
- "incremental": true,
17
- "plugins": [
18
- {
19
- "name": "next"
20
- }
21
- ],
22
- "paths": {
23
- "@a11ypros/a11y-ui-components": ["../../packages/design-system/src"]
24
- }
25
- },
26
- "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"],
27
- "exclude": ["node_modules"]
28
- }
29
-
@@ -1,163 +0,0 @@
1
- import { Handler } from '@netlify/functions'
2
- import Anthropic from '@anthropic-ai/sdk'
3
-
4
- const anthropic = new Anthropic({
5
- apiKey: process.env.ANTHROPIC_API_KEY || '',
6
- })
7
-
8
- interface AuditIssue {
9
- wcagSC: string // WCAG Success Criterion (e.g., "1.3.1", "2.4.7")
10
- severity: 'error' | 'warning' | 'info'
11
- message: string
12
- suggestion: string
13
- codeSuggestion?: string
14
- }
15
-
16
- interface AuditResponse {
17
- issues: AuditIssue[]
18
- summary: string
19
- }
20
-
21
- const WCAG_PROMPT = `You are an accessibility expert reviewing JSX/React code for WCAG 2.1 and 2.2 compliance.
22
-
23
- Analyze the provided JSX code snippet and identify accessibility issues. For each issue:
24
- 1. Map it to the specific WCAG Success Criterion (SC) number (e.g., "1.3.1", "2.4.7", "4.1.2")
25
- 2. Determine severity: "error" (violates WCAG), "warning" (may cause issues), or "info" (best practice)
26
- 3. Provide a clear message explaining the issue
27
- 4. Suggest how to fix it
28
- 5. If applicable, provide corrected code
29
-
30
- Focus on:
31
- - Semantic HTML (1.3.1)
32
- - Keyboard accessibility (2.1.1, 2.1.2)
33
- - Focus management (2.4.7)
34
- - ARIA usage (4.1.2, 4.1.3)
35
- - Color contrast (1.4.3)
36
- - Form labels (2.5.3)
37
- - Status messages (4.1.3)
38
-
39
- Return your response as a JSON object with this structure:
40
- {
41
- "issues": [
42
- {
43
- "wcagSC": "2.4.7",
44
- "severity": "error",
45
- "message": "Button lacks visible focus indicator",
46
- "suggestion": "Add focus-visible styles with 2px outline",
47
- "codeSuggestion": "button:focus-visible { outline: 2px solid #0ea5e9; }"
48
- }
49
- ],
50
- "summary": "Found 3 issues: 2 errors, 1 warning"
51
- }
52
-
53
- Only return valid JSON, no markdown formatting.`
54
-
55
- export const handler: Handler = async (event, context) => {
56
- // Handle CORS
57
- const headers = {
58
- 'Content-Type': 'application/json',
59
- 'Access-Control-Allow-Origin': '*',
60
- 'Access-Control-Allow-Headers': 'Content-Type',
61
- 'Access-Control-Allow-Methods': 'POST, OPTIONS',
62
- }
63
-
64
- // Handle preflight requests
65
- if (event.httpMethod === 'OPTIONS') {
66
- return {
67
- statusCode: 200,
68
- headers,
69
- body: '',
70
- }
71
- }
72
-
73
- // Only allow POST requests
74
- if (event.httpMethod !== 'POST') {
75
- return {
76
- statusCode: 405,
77
- headers,
78
- body: JSON.stringify({ error: 'Method not allowed' }),
79
- }
80
- }
81
-
82
- try {
83
- const { code } = JSON.parse(event.body || '{}')
84
-
85
- if (!code || typeof code !== 'string') {
86
- return {
87
- statusCode: 400,
88
- headers,
89
- body: JSON.stringify({ error: 'Code snippet is required' }),
90
- }
91
- }
92
-
93
- if (!process.env.ANTHROPIC_API_KEY) {
94
- return {
95
- statusCode: 500,
96
- headers,
97
- body: JSON.stringify({
98
- error: 'ANTHROPIC_API_KEY environment variable is not set',
99
- }),
100
- }
101
- }
102
-
103
- const message = await anthropic.messages.create({
104
- model: 'claude-sonnet-4-20250514',
105
- max_tokens: 4096,
106
- messages: [
107
- {
108
- role: 'user',
109
- content: `${WCAG_PROMPT}\n\nCode to review:\n\`\`\`jsx\n${code}\n\`\`\``,
110
- },
111
- ],
112
- })
113
-
114
- const content = message.content[0]
115
- if (content.type !== 'text') {
116
- throw new Error('Unexpected response type from Anthropic')
117
- }
118
-
119
- // Parse the JSON response
120
- let auditResult: AuditResponse
121
- try {
122
- // Extract JSON from the response (handle markdown code blocks if present)
123
- let jsonText = content.text.trim()
124
- if (jsonText.startsWith('```')) {
125
- jsonText = jsonText.replace(/^```(?:json)?\n/, '').replace(/\n```$/, '')
126
- }
127
- auditResult = JSON.parse(jsonText)
128
- } catch (parseError) {
129
- // If parsing fails, try to extract JSON from the text
130
- const jsonMatch = content.text.match(/\{[\s\S]*\}/)
131
- if (jsonMatch) {
132
- auditResult = JSON.parse(jsonMatch[0])
133
- } else {
134
- throw new Error('Failed to parse audit response as JSON')
135
- }
136
- }
137
-
138
- // Validate response structure
139
- if (!auditResult.issues || !Array.isArray(auditResult.issues)) {
140
- auditResult = {
141
- issues: [],
142
- summary: 'No issues found or invalid response format',
143
- }
144
- }
145
-
146
- return {
147
- statusCode: 200,
148
- headers,
149
- body: JSON.stringify(auditResult),
150
- }
151
- } catch (error) {
152
- console.error('Audit API error:', error)
153
- return {
154
- statusCode: 500,
155
- headers,
156
- body: JSON.stringify({
157
- error: 'Failed to perform accessibility audit',
158
- message: error instanceof Error ? error.message : 'Unknown error',
159
- }),
160
- }
161
- }
162
- }
163
-
package/netlify.toml DELETED
@@ -1,37 +0,0 @@
1
- # Netlify configuration for ui.a11ypros.com
2
-
3
- [build]
4
- # Base directory for the build
5
- base = "."
6
- # Install dependencies, build Storybook, then build Next.js app
7
- # Note: Move API route temporarily since static export can't handle it (we use Netlify Functions)
8
- command = "mv apps/web/app/api apps/web/app/api.disabled 2>/dev/null || true && yarn install && yarn build-storybook && yarn workspace @apps/web build && test -d apps/web/out && echo 'Build successful' || (echo 'Build failed' && exit 1) && mv apps/web/app/api.disabled apps/web/app/api 2>/dev/null || true"
9
- # Publish directory - Next.js static export (includes Storybook in public/)
10
- publish = "apps/web/out"
11
-
12
- # Environment variables (set these in Netlify dashboard)
13
- # [build.environment]
14
- # NODE_VERSION = "18"
15
- # ANTHROPIC_API_KEY = "your_key_here"
16
-
17
- # Redirect rules are now in apps/web/public/_redirects
18
- # The _redirects file takes precedence and is included in the build output
19
- # This keeps redirects in sync with the built files
20
-
21
- # Headers for Storybook - VERY permissive CSP to allow eval
22
- # netlify.toml headers work with netlify serve, _headers file may not
23
- # Storybook requires 'unsafe-eval' in script-src - this is the most permissive CSP that works
24
- [[headers]]
25
- for = "/storybook-static/*"
26
- [headers.values]
27
- Content-Security-Policy = "default-src 'self' 'unsafe-inline' data: blob: http: https: ws: wss:; script-src 'self' 'unsafe-inline' 'unsafe-eval' data: blob: http: https:; style-src 'self' 'unsafe-inline' data: http: https:; img-src 'self' data: blob: http: https:; font-src 'self' data: http: https:; connect-src 'self' ws: wss: blob: http: https:; worker-src 'self' blob: http: https:; frame-src 'self' http: https:; frame-ancestors 'self';"
28
-
29
- [[headers]]
30
- for = "/storybook"
31
- [headers.values]
32
- Content-Security-Policy = "default-src 'self' 'unsafe-inline' data: blob: http: https: ws: wss:; script-src 'self' 'unsafe-inline' 'unsafe-eval' data: blob: http: https:; style-src 'self' 'unsafe-inline' data: http: https:; img-src 'self' data: blob: http: https:; font-src 'self' data: http: https:; connect-src 'self' ws: wss: blob: http: https:; worker-src 'self' blob: http: https:; frame-src 'self' http: https:; frame-ancestors 'self';"
33
-
34
- [[headers]]
35
- for = "/storybook/*"
36
- [headers.values]
37
- Content-Security-Policy = "default-src 'self' 'unsafe-inline' data: blob: http: https: ws: wss:; script-src 'self' 'unsafe-inline' 'unsafe-eval' data: blob: http: https:; style-src 'self' 'unsafe-inline' data: http: https:; img-src 'self' data: blob: http: https:; font-src 'self' data: http: https:; connect-src 'self' ws: wss: blob: http: https:; worker-src 'self' blob: http: https:; frame-src 'self' http: https:; frame-ancestors 'self';"
@@ -1,252 +0,0 @@
1
- # @a11ypros/a11y-ui-components
2
-
3
- An accessibility-first React UI component library built with WCAG 2.1/2.2 Level AA compliance. Every component has been carefully crafted by a certified WAS (Web Accessibility Specialist) to ensure your applications are usable by everyone, regardless of their abilities or the assistive technologies they use.
4
-
5
- ## Features
6
-
7
- - ✅ **WCAG 2.1/2.2 Level AA Compliant** - Built with accessibility as a core requirement
8
- - ✅ **TypeScript** - Full TypeScript support with type definitions included
9
- - ✅ **Tree-shakeable** - ES modules with side-effect-free exports for optimal bundle sizes
10
- - ✅ **Keyboard Navigation** - Full keyboard support for all interactive components
11
- - ✅ **Screen Reader Friendly** - Proper ARIA labels and semantic HTML
12
- - ✅ **Focus Management** - Built-in focus trap and focus return utilities
13
- - ✅ **Modern React** - Built for React 18+ with hooks and modern patterns
14
-
15
- ## Installation
16
-
17
- ```bash
18
- npm install @a11ypros/a11y-ui-components
19
- ```
20
-
21
- or
22
-
23
- ```bash
24
- yarn add @a11ypros/a11y-ui-components
25
- ```
26
-
27
- ## Peer Dependencies
28
-
29
- This package requires React 18+ and React DOM 18+:
30
-
31
- ```bash
32
- npm install react react-dom
33
- ```
34
-
35
- ## Quick Start
36
-
37
- ### 1. Import CSS
38
-
39
- Import the global styles in your application entry point:
40
-
41
- ```tsx
42
- // In your main CSS file or entry point
43
- import '@a11ypros/a11y-ui-components/styles';
44
- ```
45
-
46
- Or import component-specific styles:
47
-
48
- ```tsx
49
- import '@a11ypros/a11y-ui-components/styles/components';
50
- ```
51
-
52
- ### 2. Import and Use Components
53
-
54
- ```tsx
55
- import { Button, Input, Modal } from '@a11ypros/a11y-ui-components';
56
-
57
- function App() {
58
- return (
59
- <div>
60
- <Button>Click me</Button>
61
- <Input label="Email" type="email" />
62
- <Modal isOpen={true} onClose={() => {}}>
63
- <p>Modal content</p>
64
- </Modal>
65
- </div>
66
- );
67
- }
68
- ```
69
-
70
- ## Available Components
71
-
72
- ### Form Components
73
- - **Input** - Accessible text input with label and error handling
74
- - **Textarea** - Multi-line text input
75
- - **Select** - Dropdown select with keyboard navigation
76
- - **Checkbox** - Accessible checkbox with proper labeling
77
- - **Radio** - Radio button group with fieldset support
78
- - **Label** - Accessible form label component
79
- - **Fieldset** - Form fieldset for grouping related inputs
80
-
81
- ### UI Components
82
- - **Button** - Accessible button with multiple variants
83
- - **Link** - Accessible link component
84
- - **Modal** - Accessible modal dialog with focus trap
85
- - **Tabs** - Keyboard-navigable tab component
86
- - **DataTable** - Accessible data table with sorting
87
- - **Toast** - Accessible toast notification system
88
- - **ToastProvider** - Context provider for toast notifications
89
-
90
- ### Hooks
91
- - **useFocusTrap** - Trap focus within a container
92
- - **useFocusReturn** - Return focus to previous element
93
- - **useAriaLive** - Manage ARIA live regions for announcements
94
-
95
- ### Utilities
96
- - **aria** - ARIA attribute utilities
97
- - **keyboard** - Keyboard event utilities
98
- - **focus** - Focus management utilities
99
-
100
- ### Design Tokens
101
- - **colors** - Color palette and theme tokens
102
- - **typography** - Typography scale and font tokens
103
- - **spacing** - Spacing scale tokens
104
- - **breakpoints** - Responsive breakpoint tokens
105
- - **motion** - Animation and transition tokens
106
-
107
- ## Documentation
108
-
109
- 📚 **[View Full Documentation & Storybook](https://ui.a11ypros.com/storybook)**
110
-
111
- Browse all components, see live examples, and explore accessibility features in our interactive Storybook documentation.
112
-
113
- ## Usage Examples
114
-
115
- ### Form with Validation
116
-
117
- ```tsx
118
- import { Input, Button, Label } from '@a11ypros/a11y-ui-components';
119
-
120
- function LoginForm() {
121
- const [email, setEmail] = useState('');
122
- const [error, setError] = useState('');
123
-
124
- return (
125
- <form>
126
- <Input
127
- label="Email"
128
- type="email"
129
- value={email}
130
- onChange={(e) => setEmail(e.target.value)}
131
- error={error}
132
- required
133
- />
134
- <Button type="submit">Sign In</Button>
135
- </form>
136
- );
137
- }
138
- ```
139
-
140
- ### Modal Dialog
141
-
142
- ```tsx
143
- import { Modal, Button } from '@a11ypros/a11y-ui-components';
144
- import { useState } from 'react';
145
-
146
- function App() {
147
- const [isOpen, setIsOpen] = useState(false);
148
-
149
- return (
150
- <>
151
- <Button onClick={() => setIsOpen(true)}>Open Modal</Button>
152
- <Modal
153
- isOpen={isOpen}
154
- onClose={() => setIsOpen(false)}
155
- title="Confirm Action"
156
- >
157
- <p>Are you sure you want to proceed?</p>
158
- <Button onClick={() => setIsOpen(false)}>Confirm</Button>
159
- </Modal>
160
- </>
161
- );
162
- }
163
- ```
164
-
165
- ### Toast Notifications
166
-
167
- ```tsx
168
- import { ToastProvider, useToast, Button } from '@a11ypros/a11y-ui-components';
169
-
170
- function App() {
171
- return (
172
- <ToastProvider>
173
- <MyComponent />
174
- </ToastProvider>
175
- );
176
- }
177
-
178
- function MyComponent() {
179
- const { addToast } = useToast();
180
-
181
- return (
182
- <Button
183
- onClick={() =>
184
- addToast({
185
- message: 'Action completed successfully!',
186
- type: 'success',
187
- })
188
- }
189
- >
190
- Show Toast
191
- </Button>
192
- );
193
- }
194
- ```
195
-
196
- ## Important Note on Accessibility
197
-
198
- > **Note**: While these components are built with accessibility in mind and meet WCAG 2.1/2.2 Level AA standards, **simply using these components does not guarantee an accessible application**. These components are foundational building blocks that must be used properly within the larger consuming application with accessibility in mind.
199
-
200
- To ensure your application is truly accessible, consider:
201
-
202
- - **Proper Implementation**: Use components according to their documented patterns and accessibility guidelines
203
- - **Application-Level Considerations**: Ensure proper page structure, heading hierarchy, and landmark regions
204
- - **Content Accessibility**: Write clear, descriptive text and provide alternative text for images
205
- - **Testing**: Regularly test your application with keyboard navigation and screen readers
206
- - **User Experience**: Consider the full user journey and how components work together
207
-
208
- ## Internationalization (i18n)
209
-
210
- Currently, all screen reader text and ARIA labels are provided in English. Full i18n support is a high-priority feature coming soon to ensure global accessibility.
211
-
212
- ## Tree Shaking
213
-
214
- This package is fully tree-shakeable. Import only what you need:
215
-
216
- ```tsx
217
- // ✅ Good - tree-shakeable
218
- import { Button } from '@a11ypros/a11y-ui-components';
219
-
220
- // ✅ Also good - import specific utilities
221
- import { useFocusTrap } from '@a11ypros/a11y-ui-components';
222
- ```
223
-
224
- ## TypeScript Support
225
-
226
- Full TypeScript definitions are included. No need to install `@types` packages.
227
-
228
- ```tsx
229
- import { Button, ButtonProps } from '@a11ypros/a11y-ui-components';
230
-
231
- const props: ButtonProps = {
232
- variant: 'primary',
233
- size: 'medium',
234
- children: 'Click me',
235
- };
236
- ```
237
-
238
- ## Contributing
239
-
240
- Contributions are welcome! Please see our [GitHub repository](https://github.com/ryan0122/a11ypros-components) for contribution guidelines.
241
-
242
- ## License
243
-
244
- MIT © [A11y Pros](https://a11ypros.com)
245
-
246
- ## Links
247
-
248
- - 📦 [npm package](https://www.npmjs.com/package/@a11ypros/a11y-ui-components)
249
- - 📚 [Documentation & Storybook](https://ui.a11ypros.com/storybook)
250
- - 🐛 [Issue Tracker](https://github.com/ryan0122/a11ypros-components/issues)
251
- - 💻 [Source Code](https://github.com/ryan0122/a11ypros-components)
252
-
@@ -1,68 +0,0 @@
1
- {
2
- "name": "@a11ypros/a11y-ui-components",
3
- "version": "1.0.0",
4
- "description": "An accessibility-first React UI component library built with WCAG 2.1/2.2 compliance",
5
- "keywords": [
6
- "react",
7
- "accessibility",
8
- "a11y",
9
- "wcag",
10
- "design-system",
11
- "components",
12
- "typescript"
13
- ],
14
- "author": "Ryan Mack <ryan@a11ypros.com>",
15
- "license": "MIT",
16
- "type": "module",
17
- "main": "./dist/index.js",
18
- "types": "./dist/index.d.ts",
19
- "module": "./dist/index.js",
20
- "sideEffects": false,
21
- "files": [
22
- "dist",
23
- "README.md"
24
- ],
25
- "exports": {
26
- ".": {
27
- "types": "./dist/index.d.ts",
28
- "import": "./dist/index.js"
29
- },
30
- "./styles": {
31
- "import": "./dist/styles/global.css"
32
- },
33
- "./styles/components": {
34
- "import": "./dist/styles/components.css"
35
- },
36
- "./package.json": "./package.json"
37
- },
38
- "repository": {
39
- "type": "git",
40
- "url": "https://github.com/ryan0122/a11ypros-components.git",
41
- "directory": "packages/design-system"
42
- },
43
- "scripts": {
44
- "build": "tsc && node scripts/copy-css.js",
45
- "prepublishOnly": "npm run build",
46
- "storybook": "cd ../.. && npm run storybook",
47
- "build-storybook": "cd ../.. && npm run build-storybook"
48
- },
49
- "peerDependencies": {
50
- "react": "^18.0.0",
51
- "react-dom": "^18.0.0"
52
- },
53
- "devDependencies": {
54
- "@storybook/addon-a11y": "^7.6.17",
55
- "@storybook/addon-docs": "^7.6.17",
56
- "@storybook/addon-essentials": "^7.6.17",
57
- "@storybook/addon-interactions": "^7.6.17",
58
- "@storybook/addon-links": "^7.6.17",
59
- "@storybook/blocks": "^7.6.17",
60
- "@storybook/react": "^7.6.17",
61
- "@storybook/react-webpack5": "^7.6.17",
62
- "@storybook/test": "^7.6.17",
63
- "@types/react": "^18.2.48",
64
- "@types/react-dom": "^18.2.18",
65
- "typescript": "^5.3.3"
66
- }
67
- }
68
-
@@ -1,63 +0,0 @@
1
- #!/usr/bin/env node
2
-
3
- import { cpSync, mkdirSync, existsSync } from 'fs'
4
- import { join, dirname } from 'path'
5
- import { fileURLToPath } from 'url'
6
-
7
- const __filename = fileURLToPath(import.meta.url)
8
- const __dirname = dirname(__filename)
9
- const srcDir = join(__dirname, '../src')
10
- const distDir = join(__dirname, '../dist')
11
-
12
- // Create dist/styles directory
13
- const stylesDistDir = join(distDir, 'styles')
14
- if (!existsSync(stylesDistDir)) {
15
- mkdirSync(stylesDistDir, { recursive: true })
16
- }
17
-
18
- // Copy global.css and components.css to dist/styles/
19
- const stylesToCopy = ['global.css', 'components.css']
20
- stylesToCopy.forEach(file => {
21
- const srcFile = join(srcDir, 'styles', file)
22
- const destFile = join(stylesDistDir, file)
23
- if (existsSync(srcFile)) {
24
- cpSync(srcFile, destFile)
25
- console.log(`Copied ${file} to dist/styles/`)
26
- }
27
- })
28
-
29
- // Copy component CSS files maintaining directory structure
30
- // This is needed because components.css uses relative imports
31
- import { readdirSync } from 'fs'
32
-
33
- const componentsDir = join(srcDir, 'components')
34
- const componentsDistDir = join(distDir, 'components')
35
-
36
- function copyComponentCSS(dir, distBase) {
37
- const entries = readdirSync(dir, { withFileTypes: true })
38
-
39
- entries.forEach(entry => {
40
- const srcPath = join(dir, entry.name)
41
- const distPath = join(distBase, entry.name)
42
-
43
- if (entry.isDirectory()) {
44
- if (!existsSync(distPath)) {
45
- mkdirSync(distPath, { recursive: true })
46
- }
47
- copyComponentCSS(srcPath, distPath)
48
- } else if (entry.isFile() && entry.name.endsWith('.css')) {
49
- cpSync(srcPath, distPath)
50
- console.log(`Copied ${entry.name} to ${distPath.replace(process.cwd(), '.')}`)
51
- }
52
- })
53
- }
54
-
55
- if (existsSync(componentsDir)) {
56
- if (!existsSync(componentsDistDir)) {
57
- mkdirSync(componentsDistDir, { recursive: true })
58
- }
59
- copyComponentCSS(componentsDir, componentsDistDir)
60
- }
61
-
62
- console.log('CSS files copied successfully!')
63
-