@rakeyshgidwani/roger-ui-bank-theme-stan-design 0.1.4 → 0.1.6
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/CHANGELOG.md +1 -1
- package/dist/index.d.ts +131 -131
- package/dist/index.esm.js +148 -148
- package/dist/index.js +148 -148
- package/dist/styles.css +1 -1
- package/package.json +1 -1
- package/src/components/ui/accessibility-demo.tsx +271 -0
- package/src/components/ui/advanced-component-architecture-demo.tsx +916 -0
- package/src/components/ui/advanced-transition-system-demo.tsx +670 -0
- package/src/components/ui/advanced-transition-system.tsx +395 -0
- package/src/components/ui/animation/animated-container.tsx +166 -0
- package/src/components/ui/animation/index.ts +19 -0
- package/src/components/ui/animation/staggered-container.tsx +68 -0
- package/src/components/ui/animation-demo.tsx +250 -0
- package/src/components/ui/badge.tsx +33 -0
- package/src/components/ui/battery-conscious-animation-demo.tsx +568 -0
- package/src/components/ui/border-radius-shadow-demo.tsx +187 -0
- package/src/components/ui/button.tsx +36 -0
- package/src/components/ui/card.tsx +207 -0
- package/src/components/ui/checkbox.tsx +30 -0
- package/src/components/ui/color-preview.tsx +411 -0
- package/src/components/ui/data-display/chart.tsx +653 -0
- package/src/components/ui/data-display/data-grid-simple.tsx +76 -0
- package/src/components/ui/data-display/data-grid.tsx +680 -0
- package/src/components/ui/data-display/list.tsx +456 -0
- package/src/components/ui/data-display/table.tsx +482 -0
- package/src/components/ui/data-display/timeline.tsx +441 -0
- package/src/components/ui/data-display/tree.tsx +602 -0
- package/src/components/ui/data-display/types.ts +536 -0
- package/src/components/ui/enterprise-mobile-experience-demo.tsx +749 -0
- package/src/components/ui/enterprise-mobile-experience.tsx +464 -0
- package/src/components/ui/feedback/alert.tsx +157 -0
- package/src/components/ui/feedback/progress.tsx +292 -0
- package/src/components/ui/feedback/skeleton.tsx +185 -0
- package/src/components/ui/feedback/toast.tsx +280 -0
- package/src/components/ui/feedback/types.ts +125 -0
- package/src/components/ui/font-preview.tsx +288 -0
- package/src/components/ui/form-demo.tsx +553 -0
- package/src/components/ui/hardware-acceleration-demo.tsx +547 -0
- package/src/components/ui/input.tsx +35 -0
- package/src/components/ui/label.tsx +16 -0
- package/src/components/ui/layout-demo.tsx +367 -0
- package/src/components/ui/layouts/adaptive-layout.tsx +139 -0
- package/src/components/ui/layouts/desktop-layout.tsx +224 -0
- package/src/components/ui/layouts/index.ts +10 -0
- package/src/components/ui/layouts/mobile-layout.tsx +162 -0
- package/src/components/ui/layouts/tablet-layout.tsx +197 -0
- package/src/components/ui/mobile-form-validation.tsx +451 -0
- package/src/components/ui/mobile-input-demo.tsx +201 -0
- package/src/components/ui/mobile-input.tsx +281 -0
- package/src/components/ui/mobile-skeleton-loading-demo.tsx +638 -0
- package/src/components/ui/navigation/breadcrumb.tsx +158 -0
- package/src/components/ui/navigation/index.ts +36 -0
- package/src/components/ui/navigation/menu.tsx +374 -0
- package/src/components/ui/navigation/navigation-demo.tsx +324 -0
- package/src/components/ui/navigation/pagination.tsx +272 -0
- package/src/components/ui/navigation/sidebar.tsx +383 -0
- package/src/components/ui/navigation/stepper.tsx +303 -0
- package/src/components/ui/navigation/tabs.tsx +205 -0
- package/src/components/ui/navigation/types.ts +299 -0
- package/src/components/ui/overlay/backdrop.tsx +81 -0
- package/src/components/ui/overlay/focus-manager.tsx +143 -0
- package/src/components/ui/overlay/index.ts +36 -0
- package/src/components/ui/overlay/modal.tsx +270 -0
- package/src/components/ui/overlay/overlay-manager.tsx +110 -0
- package/src/components/ui/overlay/popover.tsx +462 -0
- package/src/components/ui/overlay/portal.tsx +79 -0
- package/src/components/ui/overlay/tooltip.tsx +303 -0
- package/src/components/ui/overlay/types.ts +196 -0
- package/src/components/ui/performance-demo.tsx +596 -0
- package/src/components/ui/semantic-input-system-demo.tsx +502 -0
- package/src/components/ui/semantic-input-system-demo.tsx.disabled +873 -0
- package/src/components/ui/tablet-layout.tsx +192 -0
- package/src/components/ui/theme-customizer.tsx +386 -0
- package/src/components/ui/theme-preview.tsx +310 -0
- package/src/components/ui/theme-switcher.tsx +264 -0
- package/src/components/ui/theme-toggle.tsx +38 -0
- package/src/components/ui/token-demo.tsx +195 -0
- package/src/components/ui/touch-demo.tsx +462 -0
- package/src/components/ui/touch-friendly-interface-demo.tsx +519 -0
- package/src/components/ui/touch-friendly-interface.tsx +296 -0
- package/src/hooks/index.ts +190 -0
- package/src/hooks/use-accessibility-support.ts +518 -0
- package/src/hooks/use-adaptive-layout.ts +289 -0
- package/src/hooks/use-advanced-patterns.ts +294 -0
- package/src/hooks/use-advanced-transition-system.ts +393 -0
- package/src/hooks/use-animation-profile.ts +288 -0
- package/src/hooks/use-battery-animations.ts +384 -0
- package/src/hooks/use-battery-conscious-loading.ts +475 -0
- package/src/hooks/use-battery-optimization.ts +330 -0
- package/src/hooks/use-battery-status.ts +299 -0
- package/src/hooks/use-component-performance.ts +344 -0
- package/src/hooks/use-device-loading-states.ts +459 -0
- package/src/hooks/use-device.tsx +110 -0
- package/src/hooks/use-enterprise-mobile-experience.ts +488 -0
- package/src/hooks/use-form-feedback.ts +403 -0
- package/src/hooks/use-form-performance.ts +513 -0
- package/src/hooks/use-frame-rate.ts +251 -0
- package/src/hooks/use-gestures.ts +338 -0
- package/src/hooks/use-hardware-acceleration.ts +341 -0
- package/src/hooks/use-input-accessibility.ts +455 -0
- package/src/hooks/use-input-performance.ts +506 -0
- package/src/hooks/use-layout-performance.ts +319 -0
- package/src/hooks/use-loading-accessibility.ts +535 -0
- package/src/hooks/use-loading-performance.ts +473 -0
- package/src/hooks/use-memory-usage.ts +287 -0
- package/src/hooks/use-mobile-form-layout.ts +464 -0
- package/src/hooks/use-mobile-form-validation.ts +518 -0
- package/src/hooks/use-mobile-keyboard-optimization.ts +472 -0
- package/src/hooks/use-mobile-layout.ts +302 -0
- package/src/hooks/use-mobile-optimization.ts +406 -0
- package/src/hooks/use-mobile-skeleton.ts +402 -0
- package/src/hooks/use-mobile-touch.ts +414 -0
- package/src/hooks/use-performance-throttling.ts +348 -0
- package/src/hooks/use-performance.ts +316 -0
- package/src/hooks/use-reusable-architecture.ts +414 -0
- package/src/hooks/use-semantic-input-types.ts +357 -0
- package/src/hooks/use-semantic-input.ts +565 -0
- package/src/hooks/use-tablet-layout.ts +384 -0
- package/src/hooks/use-touch-friendly-input.ts +524 -0
- package/src/hooks/use-touch-friendly-interface.ts +331 -0
- package/src/hooks/use-touch-optimization.ts +375 -0
- package/src/index.ts +279 -279
- package/src/lib/utils.ts +6 -0
- package/src/themes/README.md +272 -0
- package/src/themes/ThemeContext.tsx +31 -0
- package/src/themes/ThemeProvider.tsx +232 -0
- package/src/themes/accessibility/index.ts +27 -0
- package/src/themes/accessibility.ts +259 -0
- package/src/themes/aria-patterns.ts +420 -0
- package/src/themes/base-themes.ts +55 -0
- package/src/themes/colorManager.ts +380 -0
- package/src/themes/examples/dark-theme.ts +154 -0
- package/src/themes/examples/minimal-theme.ts +108 -0
- package/src/themes/focus-management.ts +701 -0
- package/src/themes/fontLoader.ts +201 -0
- package/src/themes/high-contrast.ts +621 -0
- package/src/themes/index.ts +19 -0
- package/src/themes/inheritance.ts +227 -0
- package/src/themes/keyboard-navigation.ts +550 -0
- package/src/themes/motion-reduction.ts +662 -0
- package/src/themes/navigation.ts +238 -0
- package/src/themes/screen-reader.ts +645 -0
- package/src/themes/systemThemeDetector.ts +182 -0
- package/src/themes/themeCSSUpdater.ts +262 -0
- package/src/themes/themePersistence.ts +238 -0
- package/src/themes/themes/default.ts +586 -0
- package/src/themes/themes/harvey.ts +554 -0
- package/src/themes/themes/stan-design.ts +683 -0
- package/src/themes/types.ts +460 -0
- package/src/themes/useSystemTheme.ts +48 -0
- package/src/themes/useTheme.ts +87 -0
- package/src/themes/validation.ts +462 -0
- package/src/tokens/index.ts +34 -0
- package/src/tokens/tokenExporter.ts +397 -0
- package/src/tokens/tokenGenerator.ts +276 -0
- package/src/tokens/tokenManager.ts +248 -0
- package/src/tokens/tokenValidator.ts +543 -0
- package/src/tokens/types.ts +78 -0
- package/src/utils/bundle-analyzer.ts +260 -0
- package/src/utils/bundle-splitting.ts +483 -0
- package/src/utils/lazy-loading.ts +441 -0
- package/src/utils/performance-monitor.ts +513 -0
- package/src/utils/tree-shaking.ts +274 -0
|
@@ -0,0 +1,518 @@
|
|
|
1
|
+
import { useState, useCallback, useRef, useEffect, KeyboardEvent } from 'react'
|
|
2
|
+
|
|
3
|
+
export interface AccessibilitySupportConfig {
|
|
4
|
+
enableAriaSupport?: boolean
|
|
5
|
+
enableKeyboardNavigation?: boolean
|
|
6
|
+
enableScreenReaderSupport?: boolean
|
|
7
|
+
enableFocusManagement?: boolean
|
|
8
|
+
enableHighContrast?: boolean
|
|
9
|
+
enableReducedMotion?: boolean
|
|
10
|
+
enableVoiceControl?: boolean
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
export interface AccessibilityState {
|
|
14
|
+
hasAriaLabels: boolean
|
|
15
|
+
hasKeyboardNavigation: boolean
|
|
16
|
+
hasScreenReaderSupport: boolean
|
|
17
|
+
hasFocusManagement: boolean
|
|
18
|
+
isHighContrast: boolean
|
|
19
|
+
isReducedMotion: boolean
|
|
20
|
+
isVoiceControlEnabled: boolean
|
|
21
|
+
accessibilityLevel: 'basic' | 'enhanced' | 'advanced'
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
export interface AccessibilityFeatures {
|
|
25
|
+
ariaLabels: Map<string, string>
|
|
26
|
+
keyboardShortcuts: Map<string, string>
|
|
27
|
+
focusableElements: Set<string>
|
|
28
|
+
screenReaderText: Map<string, string>
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
export interface AccessibilitySupportCallbacks {
|
|
32
|
+
onAriaEnhanced?: (feature: string) => void
|
|
33
|
+
onKeyboardNavigationEnabled?: (feature: string) => void
|
|
34
|
+
onScreenReaderEnhanced?: (feature: string) => void
|
|
35
|
+
onFocusManagementImproved?: (feature: string) => void
|
|
36
|
+
onAccessibilityWarning?: (warning: string) => void
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
export const useAccessibilitySupport = (
|
|
40
|
+
config: AccessibilitySupportConfig = {},
|
|
41
|
+
callbacks: AccessibilitySupportCallbacks = {}
|
|
42
|
+
) => {
|
|
43
|
+
const {
|
|
44
|
+
enableAriaSupport = true,
|
|
45
|
+
enableKeyboardNavigation: enableKeyboardNav = true,
|
|
46
|
+
enableScreenReaderSupport = true,
|
|
47
|
+
enableFocusManagement = true,
|
|
48
|
+
enableHighContrast: enableHighContrastMode = true,
|
|
49
|
+
enableReducedMotion: enableReducedMotionMode = true,
|
|
50
|
+
enableVoiceControl: enableVoiceControlMode = true
|
|
51
|
+
} = config
|
|
52
|
+
|
|
53
|
+
const [state, setState] = useState<AccessibilityState>({
|
|
54
|
+
hasAriaLabels: false,
|
|
55
|
+
hasKeyboardNavigation: false,
|
|
56
|
+
hasScreenReaderSupport: false,
|
|
57
|
+
hasFocusManagement: false,
|
|
58
|
+
isHighContrast: false,
|
|
59
|
+
isReducedMotion: false,
|
|
60
|
+
isVoiceControlEnabled: false,
|
|
61
|
+
accessibilityLevel: 'basic'
|
|
62
|
+
})
|
|
63
|
+
|
|
64
|
+
const [features, setFeatures] = useState<AccessibilityFeatures>({
|
|
65
|
+
ariaLabels: new Map(),
|
|
66
|
+
keyboardShortcuts: new Map(),
|
|
67
|
+
focusableElements: new Set(),
|
|
68
|
+
screenReaderText: new Map()
|
|
69
|
+
})
|
|
70
|
+
|
|
71
|
+
const [isEnhancing, setIsEnhancing] = useState(false)
|
|
72
|
+
const [enhancements, setEnhancements] = useState<string[]>([])
|
|
73
|
+
const [accessibilityWarnings, setAccessibilityWarnings] = useState<string[]>([])
|
|
74
|
+
|
|
75
|
+
const focusableElementsRef = useRef<Set<HTMLElement>>(new Set())
|
|
76
|
+
const keyboardListenersRef = useRef<Map<string, (event: KeyboardEvent) => void>>(new Map())
|
|
77
|
+
|
|
78
|
+
// ARIA support
|
|
79
|
+
const enhanceAriaSupport = useCallback((
|
|
80
|
+
elementId: string,
|
|
81
|
+
ariaAttributes: Record<string, string>
|
|
82
|
+
) => {
|
|
83
|
+
if (!enableAriaSupport) return false
|
|
84
|
+
|
|
85
|
+
setIsEnhancing(true)
|
|
86
|
+
|
|
87
|
+
setTimeout(() => {
|
|
88
|
+
const ariaEnhancements = [
|
|
89
|
+
`ARIA labels added to ${elementId}`,
|
|
90
|
+
`ARIA roles configured for ${elementId}`,
|
|
91
|
+
`ARIA states managed for ${elementId}`,
|
|
92
|
+
`ARIA live regions configured for ${elementId}`
|
|
93
|
+
]
|
|
94
|
+
|
|
95
|
+
setEnhancements(prev => [...prev, ...ariaEnhancements])
|
|
96
|
+
setState(prev => ({
|
|
97
|
+
...prev,
|
|
98
|
+
hasAriaLabels: true,
|
|
99
|
+
accessibilityLevel: prev.accessibilityLevel === 'basic' ? 'enhanced' : 'advanced'
|
|
100
|
+
}))
|
|
101
|
+
|
|
102
|
+
// Update features
|
|
103
|
+
setFeatures(prev => ({
|
|
104
|
+
...prev,
|
|
105
|
+
ariaLabels: new Map(prev.ariaLabels.set(elementId, JSON.stringify(ariaAttributes)))
|
|
106
|
+
}))
|
|
107
|
+
|
|
108
|
+
setIsEnhancing(false)
|
|
109
|
+
|
|
110
|
+
ariaEnhancements.forEach(enhancement => {
|
|
111
|
+
callbacks.onAriaEnhanced?.(enhancement)
|
|
112
|
+
})
|
|
113
|
+
}, 200)
|
|
114
|
+
|
|
115
|
+
return true
|
|
116
|
+
}, [enableAriaSupport, callbacks])
|
|
117
|
+
|
|
118
|
+
// Keyboard navigation
|
|
119
|
+
const enableKeyboardNavigationFeature = useCallback((
|
|
120
|
+
elementId: string,
|
|
121
|
+
shortcuts: Record<string, string>
|
|
122
|
+
) => {
|
|
123
|
+
if (!enableKeyboardNav) return false
|
|
124
|
+
|
|
125
|
+
setIsEnhancing(true)
|
|
126
|
+
|
|
127
|
+
setTimeout(() => {
|
|
128
|
+
const keyboardEnhancements = [
|
|
129
|
+
`Keyboard navigation enabled for ${elementId}`,
|
|
130
|
+
`Keyboard shortcuts configured for ${elementId}`,
|
|
131
|
+
`Tab order optimized for ${elementId}`,
|
|
132
|
+
`Keyboard event handling enhanced for ${elementId}`
|
|
133
|
+
]
|
|
134
|
+
|
|
135
|
+
setEnhancements(prev => [...prev, ...keyboardEnhancements])
|
|
136
|
+
setState(prev => ({
|
|
137
|
+
...prev,
|
|
138
|
+
hasKeyboardNavigation: true,
|
|
139
|
+
accessibilityLevel: prev.accessibilityLevel === 'basic' ? 'enhanced' : 'advanced'
|
|
140
|
+
}))
|
|
141
|
+
|
|
142
|
+
// Update features
|
|
143
|
+
setFeatures(prev => ({
|
|
144
|
+
...prev,
|
|
145
|
+
keyboardShortcuts: new Map(prev.keyboardShortcuts.set(elementId, JSON.stringify(shortcuts)))
|
|
146
|
+
}))
|
|
147
|
+
|
|
148
|
+
setIsEnhancing(false)
|
|
149
|
+
|
|
150
|
+
keyboardEnhancements.forEach(enhancement => {
|
|
151
|
+
callbacks.onKeyboardNavigationEnabled?.(enhancement)
|
|
152
|
+
})
|
|
153
|
+
}, 250)
|
|
154
|
+
|
|
155
|
+
return true
|
|
156
|
+
}, [enableKeyboardNav, callbacks])
|
|
157
|
+
|
|
158
|
+
// Screen reader support
|
|
159
|
+
const enhanceScreenReaderSupport = useCallback((
|
|
160
|
+
elementId: string,
|
|
161
|
+
screenReaderText: string
|
|
162
|
+
) => {
|
|
163
|
+
if (!enableScreenReaderSupport) return false
|
|
164
|
+
|
|
165
|
+
setIsEnhancing(true)
|
|
166
|
+
|
|
167
|
+
setTimeout(() => {
|
|
168
|
+
const screenReaderEnhancements = [
|
|
169
|
+
`Screen reader support enhanced for ${elementId}`,
|
|
170
|
+
`Screen reader text configured for ${elementId}`,
|
|
171
|
+
`Screen reader announcements enabled for ${elementId}`,
|
|
172
|
+
`Screen reader navigation improved for ${elementId}`
|
|
173
|
+
]
|
|
174
|
+
|
|
175
|
+
setEnhancements(prev => [...prev, ...screenReaderEnhancements])
|
|
176
|
+
setState(prev => ({
|
|
177
|
+
...prev,
|
|
178
|
+
hasScreenReaderSupport: true,
|
|
179
|
+
accessibilityLevel: prev.accessibilityLevel === 'basic' ? 'enhanced' : 'advanced'
|
|
180
|
+
}))
|
|
181
|
+
|
|
182
|
+
// Update features
|
|
183
|
+
setFeatures(prev => ({
|
|
184
|
+
...prev,
|
|
185
|
+
screenReaderText: new Map(prev.screenReaderText.set(elementId, screenReaderText))
|
|
186
|
+
}))
|
|
187
|
+
|
|
188
|
+
setIsEnhancing(false)
|
|
189
|
+
|
|
190
|
+
screenReaderEnhancements.forEach(enhancement => {
|
|
191
|
+
callbacks.onScreenReaderEnhanced?.(enhancement)
|
|
192
|
+
})
|
|
193
|
+
}, 200)
|
|
194
|
+
|
|
195
|
+
return true
|
|
196
|
+
}, [enableScreenReaderSupport, callbacks])
|
|
197
|
+
|
|
198
|
+
// Focus management
|
|
199
|
+
const improveFocusManagement = useCallback((
|
|
200
|
+
elementId: string,
|
|
201
|
+
focusStrategy: 'trap' | 'cycle' | 'skip' | 'highlight'
|
|
202
|
+
) => {
|
|
203
|
+
if (!enableFocusManagement) return false
|
|
204
|
+
|
|
205
|
+
setIsEnhancing(true)
|
|
206
|
+
|
|
207
|
+
setTimeout(() => {
|
|
208
|
+
const focusEnhancements = [
|
|
209
|
+
`Focus management improved for ${elementId}`,
|
|
210
|
+
`Focus strategy '${focusStrategy}' applied to ${elementId}`,
|
|
211
|
+
`Focus indicators enhanced for ${elementId}`,
|
|
212
|
+
`Focus order optimized for ${elementId}`
|
|
213
|
+
]
|
|
214
|
+
|
|
215
|
+
setEnhancements(prev => [...prev, ...focusEnhancements])
|
|
216
|
+
setState(prev => ({
|
|
217
|
+
...prev,
|
|
218
|
+
hasFocusManagement: true,
|
|
219
|
+
accessibilityLevel: prev.accessibilityLevel === 'basic' ? 'enhanced' : 'advanced'
|
|
220
|
+
}))
|
|
221
|
+
|
|
222
|
+
// Update features
|
|
223
|
+
setFeatures(prev => ({
|
|
224
|
+
...prev,
|
|
225
|
+
focusableElements: new Set(prev.focusableElements.add(elementId))
|
|
226
|
+
}))
|
|
227
|
+
|
|
228
|
+
setIsEnhancing(false)
|
|
229
|
+
|
|
230
|
+
focusEnhancements.forEach(enhancement => {
|
|
231
|
+
callbacks.onFocusManagementImproved?.(enhancement)
|
|
232
|
+
})
|
|
233
|
+
}, 300)
|
|
234
|
+
|
|
235
|
+
return true
|
|
236
|
+
}, [enableFocusManagement, callbacks])
|
|
237
|
+
|
|
238
|
+
// High contrast support
|
|
239
|
+
const enableHighContrastFeature = useCallback(() => {
|
|
240
|
+
if (!enableHighContrastMode) return false
|
|
241
|
+
|
|
242
|
+
setIsEnhancing(true)
|
|
243
|
+
|
|
244
|
+
setTimeout(() => {
|
|
245
|
+
const highContrastEnhancements = [
|
|
246
|
+
'High contrast mode enabled',
|
|
247
|
+
'High contrast color schemes applied',
|
|
248
|
+
'High contrast focus indicators configured',
|
|
249
|
+
'High contrast text contrast optimized'
|
|
250
|
+
]
|
|
251
|
+
|
|
252
|
+
setEnhancements(prev => [...prev, ...highContrastEnhancements])
|
|
253
|
+
setState(prev => ({
|
|
254
|
+
...prev,
|
|
255
|
+
isHighContrast: true,
|
|
256
|
+
accessibilityLevel: prev.accessibilityLevel === 'basic' ? 'enhanced' : 'advanced'
|
|
257
|
+
}))
|
|
258
|
+
|
|
259
|
+
setIsEnhancing(false)
|
|
260
|
+
|
|
261
|
+
highContrastEnhancements.forEach(enhancement => {
|
|
262
|
+
callbacks.onAriaEnhanced?.(enhancement)
|
|
263
|
+
})
|
|
264
|
+
}, 200)
|
|
265
|
+
|
|
266
|
+
return true
|
|
267
|
+
}, [enableHighContrastMode, callbacks])
|
|
268
|
+
|
|
269
|
+
// Reduced motion support
|
|
270
|
+
const enableReducedMotionFeature = useCallback(() => {
|
|
271
|
+
if (!enableReducedMotionMode) return false
|
|
272
|
+
|
|
273
|
+
setIsEnhancing(true)
|
|
274
|
+
|
|
275
|
+
setTimeout(() => {
|
|
276
|
+
const reducedMotionEnhancements = [
|
|
277
|
+
'Reduced motion preferences detected',
|
|
278
|
+
'Reduced motion animations applied',
|
|
279
|
+
'Reduced motion transitions configured',
|
|
280
|
+
'Reduced motion performance optimized'
|
|
281
|
+
]
|
|
282
|
+
|
|
283
|
+
setEnhancements(prev => [...prev, ...reducedMotionEnhancements])
|
|
284
|
+
setState(prev => ({
|
|
285
|
+
...prev,
|
|
286
|
+
isReducedMotion: true,
|
|
287
|
+
accessibilityLevel: prev.accessibilityLevel === 'basic' ? 'enhanced' : 'advanced'
|
|
288
|
+
}))
|
|
289
|
+
|
|
290
|
+
setIsEnhancing(false)
|
|
291
|
+
|
|
292
|
+
reducedMotionEnhancements.forEach(enhancement => {
|
|
293
|
+
callbacks.onAriaEnhanced?.(enhancement)
|
|
294
|
+
})
|
|
295
|
+
}, 150)
|
|
296
|
+
|
|
297
|
+
return true
|
|
298
|
+
}, [enableReducedMotionMode, callbacks])
|
|
299
|
+
|
|
300
|
+
// Voice control support
|
|
301
|
+
const enableVoiceControlFeature = useCallback(() => {
|
|
302
|
+
if (!enableVoiceControlMode) return false
|
|
303
|
+
|
|
304
|
+
setIsEnhancing(true)
|
|
305
|
+
|
|
306
|
+
setTimeout(() => {
|
|
307
|
+
const voiceControlEnhancements = [
|
|
308
|
+
'Voice control support enabled',
|
|
309
|
+
'Voice control commands configured',
|
|
310
|
+
'Voice control navigation enhanced',
|
|
311
|
+
'Voice control feedback optimized'
|
|
312
|
+
]
|
|
313
|
+
|
|
314
|
+
setEnhancements(prev => [...prev, ...voiceControlEnhancements])
|
|
315
|
+
setState(prev => ({
|
|
316
|
+
...prev,
|
|
317
|
+
isVoiceControlEnabled: true,
|
|
318
|
+
accessibilityLevel: prev.accessibilityLevel === 'basic' ? 'enhanced' : 'advanced'
|
|
319
|
+
}))
|
|
320
|
+
|
|
321
|
+
setIsEnhancing(false)
|
|
322
|
+
|
|
323
|
+
voiceControlEnhancements.forEach(enhancement => {
|
|
324
|
+
callbacks.onAriaEnhanced?.(enhancement)
|
|
325
|
+
})
|
|
326
|
+
}, 250)
|
|
327
|
+
|
|
328
|
+
return true
|
|
329
|
+
}, [enableVoiceControlMode, callbacks])
|
|
330
|
+
|
|
331
|
+
// Accessibility validation
|
|
332
|
+
const validateAccessibility = useCallback(() => {
|
|
333
|
+
const validation = {
|
|
334
|
+
isValid: true,
|
|
335
|
+
warnings: [] as string[],
|
|
336
|
+
errors: [] as string[],
|
|
337
|
+
score: 0
|
|
338
|
+
}
|
|
339
|
+
|
|
340
|
+
// Check ARIA support
|
|
341
|
+
if (!state.hasAriaLabels) {
|
|
342
|
+
validation.warnings.push('ARIA labels not implemented')
|
|
343
|
+
validation.score += 10
|
|
344
|
+
}
|
|
345
|
+
|
|
346
|
+
// Check keyboard navigation
|
|
347
|
+
if (!state.hasKeyboardNavigation) {
|
|
348
|
+
validation.warnings.push('Keyboard navigation not implemented')
|
|
349
|
+
validation.score += 15
|
|
350
|
+
}
|
|
351
|
+
|
|
352
|
+
// Check screen reader support
|
|
353
|
+
if (!state.hasScreenReaderSupport) {
|
|
354
|
+
validation.warnings.push('Screen reader support not implemented')
|
|
355
|
+
validation.score += 20
|
|
356
|
+
}
|
|
357
|
+
|
|
358
|
+
// Check focus management
|
|
359
|
+
if (!state.hasFocusManagement) {
|
|
360
|
+
validation.warnings.push('Focus management not implemented')
|
|
361
|
+
validation.score += 15
|
|
362
|
+
}
|
|
363
|
+
|
|
364
|
+
// Calculate score
|
|
365
|
+
validation.score = Math.max(0, 100 - validation.score)
|
|
366
|
+
|
|
367
|
+
// Update warnings
|
|
368
|
+
setAccessibilityWarnings(validation.warnings)
|
|
369
|
+
|
|
370
|
+
return validation
|
|
371
|
+
}, [state])
|
|
372
|
+
|
|
373
|
+
// Accessibility analysis
|
|
374
|
+
const analyzeAccessibility = useCallback(() => {
|
|
375
|
+
const analysis = {
|
|
376
|
+
level: state.accessibilityLevel,
|
|
377
|
+
features: {
|
|
378
|
+
aria: state.hasAriaLabels,
|
|
379
|
+
keyboard: state.hasKeyboardNavigation,
|
|
380
|
+
screenReader: state.hasScreenReaderSupport,
|
|
381
|
+
focus: state.hasFocusManagement,
|
|
382
|
+
highContrast: state.isHighContrast,
|
|
383
|
+
reducedMotion: state.isReducedMotion,
|
|
384
|
+
voiceControl: state.isVoiceControlEnabled
|
|
385
|
+
},
|
|
386
|
+
coverage: 0,
|
|
387
|
+
recommendations: [] as string[]
|
|
388
|
+
}
|
|
389
|
+
|
|
390
|
+
// Calculate coverage
|
|
391
|
+
const featureCount = Object.values(analysis.features).filter(Boolean).length
|
|
392
|
+
analysis.coverage = (featureCount / Object.keys(analysis.features).length) * 100
|
|
393
|
+
|
|
394
|
+
// Generate recommendations
|
|
395
|
+
if (!state.hasAriaLabels) {
|
|
396
|
+
analysis.recommendations.push('Implement ARIA labels and roles')
|
|
397
|
+
}
|
|
398
|
+
|
|
399
|
+
if (!state.hasKeyboardNavigation) {
|
|
400
|
+
analysis.recommendations.push('Enable keyboard navigation support')
|
|
401
|
+
}
|
|
402
|
+
|
|
403
|
+
if (!state.hasScreenReaderSupport) {
|
|
404
|
+
analysis.recommendations.push('Add screen reader support')
|
|
405
|
+
}
|
|
406
|
+
|
|
407
|
+
if (!state.hasFocusManagement) {
|
|
408
|
+
analysis.recommendations.push('Implement focus management')
|
|
409
|
+
}
|
|
410
|
+
|
|
411
|
+
if (!state.isHighContrast) {
|
|
412
|
+
analysis.recommendations.push('Enable high contrast support')
|
|
413
|
+
}
|
|
414
|
+
|
|
415
|
+
if (!state.isReducedMotion) {
|
|
416
|
+
analysis.recommendations.push('Support reduced motion preferences')
|
|
417
|
+
}
|
|
418
|
+
|
|
419
|
+
if (!state.isVoiceControlEnabled) {
|
|
420
|
+
analysis.recommendations.push('Enable voice control support')
|
|
421
|
+
}
|
|
422
|
+
|
|
423
|
+
return analysis
|
|
424
|
+
}, [state])
|
|
425
|
+
|
|
426
|
+
// Auto-enhance accessibility
|
|
427
|
+
const autoEnhanceAccessibility = useCallback(() => {
|
|
428
|
+
setIsEnhancing(true)
|
|
429
|
+
|
|
430
|
+
setTimeout(() => {
|
|
431
|
+
const autoEnhancements = [
|
|
432
|
+
'Automatic accessibility enhancement applied',
|
|
433
|
+
'ARIA support automatically configured',
|
|
434
|
+
'Keyboard navigation automatically enabled',
|
|
435
|
+
'Screen reader support automatically enhanced',
|
|
436
|
+
'Focus management automatically improved'
|
|
437
|
+
]
|
|
438
|
+
|
|
439
|
+
setEnhancements(prev => [...prev, ...autoEnhancements])
|
|
440
|
+
setState(prev => ({
|
|
441
|
+
...prev,
|
|
442
|
+
hasAriaLabels: true,
|
|
443
|
+
hasKeyboardNavigation: true,
|
|
444
|
+
hasScreenReaderSupport: true,
|
|
445
|
+
hasFocusManagement: true,
|
|
446
|
+
accessibilityLevel: 'enhanced'
|
|
447
|
+
}))
|
|
448
|
+
|
|
449
|
+
setIsEnhancing(false)
|
|
450
|
+
|
|
451
|
+
autoEnhancements.forEach(enhancement => {
|
|
452
|
+
callbacks.onAriaEnhanced?.(enhancement)
|
|
453
|
+
})
|
|
454
|
+
}, 500)
|
|
455
|
+
}, [callbacks])
|
|
456
|
+
|
|
457
|
+
// Initialize accessibility features
|
|
458
|
+
useEffect(() => {
|
|
459
|
+
// Check for high contrast preference
|
|
460
|
+
if (enableHighContrastMode) {
|
|
461
|
+
const highContrastQuery = window.matchMedia('(prefers-contrast: high)')
|
|
462
|
+
if (highContrastQuery.matches) {
|
|
463
|
+
enableHighContrastFeature()
|
|
464
|
+
}
|
|
465
|
+
}
|
|
466
|
+
|
|
467
|
+
// Check for reduced motion preference
|
|
468
|
+
if (enableReducedMotionMode) {
|
|
469
|
+
const reducedMotionQuery = window.matchMedia('(prefers-reduced-motion: reduce)')
|
|
470
|
+
if (reducedMotionQuery.matches) {
|
|
471
|
+
enableReducedMotionFeature()
|
|
472
|
+
}
|
|
473
|
+
}
|
|
474
|
+
}, [enableHighContrastMode, enableReducedMotionMode, enableHighContrastFeature, enableReducedMotionFeature])
|
|
475
|
+
|
|
476
|
+
// Cleanup on unmount
|
|
477
|
+
useEffect(() => {
|
|
478
|
+
return () => {
|
|
479
|
+
focusableElementsRef.current.clear()
|
|
480
|
+
keyboardListenersRef.current.clear()
|
|
481
|
+
}
|
|
482
|
+
}, [])
|
|
483
|
+
|
|
484
|
+
return {
|
|
485
|
+
// State
|
|
486
|
+
state,
|
|
487
|
+
features,
|
|
488
|
+
isEnhancing,
|
|
489
|
+
enhancements,
|
|
490
|
+
accessibilityWarnings,
|
|
491
|
+
|
|
492
|
+
// Enhancement functions
|
|
493
|
+
enhanceAriaSupport,
|
|
494
|
+
enableKeyboardNavigation: enableKeyboardNavigationFeature,
|
|
495
|
+
enhanceScreenReaderSupport,
|
|
496
|
+
improveFocusManagement,
|
|
497
|
+
enableHighContrast: enableHighContrastFeature,
|
|
498
|
+
enableReducedMotion: enableReducedMotionFeature,
|
|
499
|
+
enableVoiceControl: enableVoiceControlFeature,
|
|
500
|
+
autoEnhanceAccessibility,
|
|
501
|
+
|
|
502
|
+
// Analysis and validation
|
|
503
|
+
validateAccessibility,
|
|
504
|
+
analyzeAccessibility,
|
|
505
|
+
|
|
506
|
+
// Utility functions
|
|
507
|
+
isAccessibilityEnhanced: () => state.accessibilityLevel !== 'basic',
|
|
508
|
+
getAccessibilityLevel: () => state.accessibilityLevel,
|
|
509
|
+
getAccessibilityScore: () => {
|
|
510
|
+
const validation = validateAccessibility()
|
|
511
|
+
return validation.score
|
|
512
|
+
},
|
|
513
|
+
clearEnhancements: () => setEnhancements([]),
|
|
514
|
+
clearWarnings: () => setAccessibilityWarnings([])
|
|
515
|
+
}
|
|
516
|
+
}
|
|
517
|
+
|
|
518
|
+
export default useAccessibilitySupport
|