@tsiky/components-r19 1.0.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 (287) hide show
  1. package/.prettierignore +4 -0
  2. package/.prettierrc +9 -0
  3. package/.storybook/main.ts +17 -0
  4. package/.storybook/preview.ts +21 -0
  5. package/.storybook/vitest.setup.ts +7 -0
  6. package/README.md +69 -0
  7. package/chart.ts +1 -0
  8. package/eslint.config.js +40 -0
  9. package/index.html +13 -0
  10. package/index.ts +33 -0
  11. package/package.json +63 -0
  12. package/public/vite.svg +1 -0
  13. package/src/App.css +42 -0
  14. package/src/App.tsx +12 -0
  15. package/src/assets/accessibility.png +0 -0
  16. package/src/assets/accessibility.svg +1 -0
  17. package/src/assets/addon-library.png +0 -0
  18. package/src/assets/assets.png +0 -0
  19. package/src/assets/avif-test-image.avif +0 -0
  20. package/src/assets/context.png +0 -0
  21. package/src/assets/discord.svg +1 -0
  22. package/src/assets/docs.png +0 -0
  23. package/src/assets/figma-plugin.png +0 -0
  24. package/src/assets/github.svg +1 -0
  25. package/src/assets/react.svg +1 -0
  26. package/src/assets/share.png +0 -0
  27. package/src/assets/styling.png +0 -0
  28. package/src/assets/testing.png +0 -0
  29. package/src/assets/theming.png +0 -0
  30. package/src/assets/tutorials.svg +1 -0
  31. package/src/assets/youtube.svg +1 -0
  32. package/src/components/AddItemModal/AddItemModal.module.css +72 -0
  33. package/src/components/AddItemModal/AddItemModal.tsx +82 -0
  34. package/src/components/AddItemModal/index.ts +1 -0
  35. package/src/components/Alert/Alert.css +54 -0
  36. package/src/components/Alert/Alert.stories.tsx +82 -0
  37. package/src/components/Alert/Alert.tsx +85 -0
  38. package/src/components/Alert/AlertContext.tsx +200 -0
  39. package/src/components/Alert/AlertModels.ts +34 -0
  40. package/src/components/Alert/index.ts +3 -0
  41. package/src/components/AnnouncementPanel/FlexRowContainer.css +17 -0
  42. package/src/components/AnnouncementPanel/FlexRowContainer.stories.tsx +329 -0
  43. package/src/components/AnnouncementPanel/FlexRowContainer.tsx +24 -0
  44. package/src/components/AnnouncementPanel/ListBox/CounterListBox.css +56 -0
  45. package/src/components/AnnouncementPanel/ListBox/CounterListBox.stories.tsx +292 -0
  46. package/src/components/AnnouncementPanel/ListBox/CounterListBox.tsx +106 -0
  47. package/src/components/AnnouncementPanel/ListBox/SimpleListBox.css +57 -0
  48. package/src/components/AnnouncementPanel/ListBox/SimpleListBox.stories.tsx +189 -0
  49. package/src/components/AnnouncementPanel/ListBox/SimpleListBox.tsx +138 -0
  50. package/src/components/AnnouncementPanel/ListBox/TrendListBox.css +61 -0
  51. package/src/components/AnnouncementPanel/ListBox/TrendListBox.stories.tsx +257 -0
  52. package/src/components/AnnouncementPanel/ListBox/TrendListBox.tsx +90 -0
  53. package/src/components/AnnouncementPanel/ListBox/index.ts +3 -0
  54. package/src/components/AnnouncementPanel/ListContentContainer.css +23 -0
  55. package/src/components/AnnouncementPanel/ListContentContainer.stories.tsx +212 -0
  56. package/src/components/AnnouncementPanel/ListContentContainer.tsx +33 -0
  57. package/src/components/AnnouncementPanel/index.ts +3 -0
  58. package/src/components/BandChart/index.tsx +282 -0
  59. package/src/components/Button/Button.module.css +165 -0
  60. package/src/components/Button/Button.stories.ts +132 -0
  61. package/src/components/Button/Button.tsx +55 -0
  62. package/src/components/Button/button.css +29 -0
  63. package/src/components/Button/index.ts +2 -0
  64. package/src/components/ChartContainer/ChartContainer.css +116 -0
  65. package/src/components/ChartContainer/ChartContainer.stories.tsx +159 -0
  66. package/src/components/ChartContainer/ChartContainer.tsx +155 -0
  67. package/src/components/ChartContainer/index.ts +1 -0
  68. package/src/components/Charts/area-chart-admission/AreaChartAdmission.stories.tsx +65 -0
  69. package/src/components/Charts/area-chart-admission/AreaChartAdmission.tsx +89 -0
  70. package/src/components/Charts/area-chart-admission/content.json +48 -0
  71. package/src/components/Charts/area-chart-hospitalisation/AreaChartHospitalisation.stories.tsx +141 -0
  72. package/src/components/Charts/area-chart-hospitalisation/AreaChartHospitalisation.tsx +262 -0
  73. package/src/components/Charts/area-chart-hospitalisation/content.json +55 -0
  74. package/src/components/Charts/bar-chart/BarChart.stories.tsx +50 -0
  75. package/src/components/Charts/bar-chart/BarChart.tsx +132 -0
  76. package/src/components/Charts/bar-chart/content.json +15 -0
  77. package/src/components/Charts/boxplot-chart/BoxPlotChart.stories.tsx +63 -0
  78. package/src/components/Charts/boxplot-chart/BoxPlotChart.tsx +114 -0
  79. package/src/components/Charts/boxplot-chart/boxUtils.ts +22 -0
  80. package/src/components/Charts/boxplot-chart/content.json +11 -0
  81. package/src/components/Charts/mixed-chart/MixedChart.stories.tsx +83 -0
  82. package/src/components/Charts/mixed-chart/MixedChart.tsx +625 -0
  83. package/src/components/Charts/mixed-chart/content.json +34 -0
  84. package/src/components/Charts/sankey-adaptation/sankey.tsx +70 -0
  85. package/src/components/Charts/sankey-chart/SankeyChart.stories.tsx +69 -0
  86. package/src/components/Charts/sankey-chart/SankeyChart.tsx +155 -0
  87. package/src/components/Charts/sankey-chart/content.json +15 -0
  88. package/src/components/Charts/stacked-column/StackedColumn.stories.tsx +72 -0
  89. package/src/components/Charts/stacked-column/StackedColumn.tsx +406 -0
  90. package/src/components/Charts/stacked-column/content.json +37 -0
  91. package/src/components/Charts/stacked-column-one-hundred-percent/StackedColumnOneHundredPercent.stories.tsx +43 -0
  92. package/src/components/Charts/stacked-column-one-hundred-percent/StackedColumnOneHundredPercent.tsx +75 -0
  93. package/src/components/Charts/stacked-column-one-hundred-percent/content.json +6 -0
  94. package/src/components/CircularProgress/CircularProgress.css +79 -0
  95. package/src/components/CircularProgress/CircularProgress.stories.tsx +251 -0
  96. package/src/components/CircularProgress/CircularProgress.tsx +101 -0
  97. package/src/components/CircularProgress/index.ts +2 -0
  98. package/src/components/Configure.mdx +369 -0
  99. package/src/components/DayStatCard/DayStatCard.css +50 -0
  100. package/src/components/DayStatCard/DayStatCard.stories.tsx +273 -0
  101. package/src/components/DayStatCard/DayStatCard.tsx +69 -0
  102. package/src/components/DayStatCard/index.ts +2 -0
  103. package/src/components/DraggableSwitcher/DraggableSwitcherButton.tsx +58 -0
  104. package/src/components/DraggableSwitcher/context/useDraggableSwitcher.tsx +45 -0
  105. package/src/components/DraggableSwitcher/index.ts +2 -0
  106. package/src/components/DropdownMenu/DropdownMenu.css +100 -0
  107. package/src/components/DropdownMenu/DropdownMenu.stories.tsx +174 -0
  108. package/src/components/DropdownMenu/DropdownMenu.tsx +106 -0
  109. package/src/components/DropdownMenu/index.ts +1 -0
  110. package/src/components/DynamicForm/DynamicFom.stories.ts +773 -0
  111. package/src/components/DynamicForm/DynamicForm.module.css +468 -0
  112. package/src/components/DynamicForm/DynamicForm.tsx +224 -0
  113. package/src/components/DynamicForm/index.ts +3 -0
  114. package/src/components/DynamicForm/tools/form-metadata.ts +82 -0
  115. package/src/components/DynamicForm/tools/validation.ts +168 -0
  116. package/src/components/DynamicInput/DynamicInput.module.css +126 -0
  117. package/src/components/DynamicInput/DynamicInput.stories.ts +350 -0
  118. package/src/components/DynamicInput/DynamicInput.tsx +144 -0
  119. package/src/components/DynamicInput/index.ts +2 -0
  120. package/src/components/DynamicInput/input/CheckboxInput.tsx +41 -0
  121. package/src/components/DynamicInput/input/ColorInput.tsx +46 -0
  122. package/src/components/DynamicInput/input/DateInput.tsx +57 -0
  123. package/src/components/DynamicInput/input/FileInput.tsx +174 -0
  124. package/src/components/DynamicInput/input/InputWrapper.tsx +26 -0
  125. package/src/components/DynamicInput/input/RadioInput.tsx +46 -0
  126. package/src/components/DynamicInput/input/RangeInput.tsx +46 -0
  127. package/src/components/DynamicInput/input/SelectInput.tsx +75 -0
  128. package/src/components/DynamicInput/input/TextInput.tsx +101 -0
  129. package/src/components/DynamicInput/input/TextareaInput.tsx +47 -0
  130. package/src/components/DynamicInput/input/assets/ColorInput.module.css +48 -0
  131. package/src/components/DynamicInput/input/assets/DateInput.module.css +83 -0
  132. package/src/components/DynamicInput/input/assets/FileInput.module.css +133 -0
  133. package/src/components/DynamicInput/input/assets/RangeInput.module.css +169 -0
  134. package/src/components/DynamicInput/input/assets/SelectInput.module.css +95 -0
  135. package/src/components/DynamicInput/input/index.ts +10 -0
  136. package/src/components/DynamicTable/AdvancedFilters.tsx +196 -0
  137. package/src/components/DynamicTable/ColumnSorter.tsx +185 -0
  138. package/src/components/DynamicTable/Pagination.tsx +115 -0
  139. package/src/components/DynamicTable/TableBody.tsx +42 -0
  140. package/src/components/DynamicTable/TableCell.tsx +30 -0
  141. package/src/components/DynamicTable/TableHeader.tsx +34 -0
  142. package/src/components/DynamicTable/TableRow.tsx +56 -0
  143. package/src/components/DynamicTable/TableauDynamic.stories.ts +1014 -0
  144. package/src/components/DynamicTable/TableauDynamique.module.css +1287 -0
  145. package/src/components/DynamicTable/TableauDynamique.tsx +154 -0
  146. package/src/components/DynamicTable/filters/BooleanFilter.tsx +30 -0
  147. package/src/components/DynamicTable/filters/DateFilter.tsx +28 -0
  148. package/src/components/DynamicTable/filters/DateRangeFilter.tsx +51 -0
  149. package/src/components/DynamicTable/filters/FilterRenderer.tsx +117 -0
  150. package/src/components/DynamicTable/filters/MultiSelectFilter.tsx +59 -0
  151. package/src/components/DynamicTable/filters/NumberFilter.tsx +37 -0
  152. package/src/components/DynamicTable/filters/OperatorFilter.tsx +64 -0
  153. package/src/components/DynamicTable/filters/SelectFilter.tsx +69 -0
  154. package/src/components/DynamicTable/filters/TextFilter.tsx +39 -0
  155. package/src/components/DynamicTable/filters/index.ts +9 -0
  156. package/src/components/DynamicTable/hooks/index.ts +2 -0
  157. package/src/components/DynamicTable/hooks/useAsyncActions.ts +36 -0
  158. package/src/components/DynamicTable/hooks/useFilters.ts +142 -0
  159. package/src/components/DynamicTable/hooks/useTableData.ts +216 -0
  160. package/src/components/DynamicTable/index.ts +11 -0
  161. package/src/components/DynamicTable/tools/filterTypes.ts +118 -0
  162. package/src/components/DynamicTable/tools/index.ts +3 -0
  163. package/src/components/DynamicTable/tools/tableConfig.ts +96 -0
  164. package/src/components/DynamicTable/tools/tableTypes.ts +63 -0
  165. package/src/components/EntryControl/EntryControl.module.css +218 -0
  166. package/src/components/EntryControl/EntryControl.stories.tsx +71 -0
  167. package/src/components/EntryControl/EntryControl.tsx +117 -0
  168. package/src/components/EntryControl/index.ts +2 -0
  169. package/src/components/Grid/Grid.stories.tsx +94 -0
  170. package/src/components/Grid/Grid.tsx +214 -0
  171. package/src/components/Grid/grid.css +285 -0
  172. package/src/components/Grid/index.ts +2 -0
  173. package/src/components/Header/Header.stories.tsx +164 -0
  174. package/src/components/Header/Header.tsx +59 -0
  175. package/src/components/Header/header.css +31 -0
  176. package/src/components/Header/index.ts +1 -0
  177. package/src/components/IconText/IconText..stories.tsx +135 -0
  178. package/src/components/IconText/IconText.css +43 -0
  179. package/src/components/IconText/IconText.tsx +43 -0
  180. package/src/components/IconText/index.ts +1 -0
  181. package/src/components/LanguageSelector/LanguageSelector.css +31 -0
  182. package/src/components/LanguageSelector/LanguageSelector.stories.tsx +38 -0
  183. package/src/components/LanguageSelector/LanguageSelector.tsx +37 -0
  184. package/src/components/LanguageSelector/index.ts +1 -0
  185. package/src/components/Logo/Logo.css +89 -0
  186. package/src/components/Logo/Logo.stories.tsx +79 -0
  187. package/src/components/Logo/Logo.tsx +22 -0
  188. package/src/components/Logo/index.ts +2 -0
  189. package/src/components/MetricsPanel/MetricsItem.tsx +128 -0
  190. package/src/components/MetricsPanel/MetricsPanel.module.css +636 -0
  191. package/src/components/MetricsPanel/MetricsPanel.stories.tsx +692 -0
  192. package/src/components/MetricsPanel/MetricsPanel.tsx +282 -0
  193. package/src/components/MetricsPanel/PanelHeader.tsx +19 -0
  194. package/src/components/MetricsPanel/SummaryCard.tsx +61 -0
  195. package/src/components/MetricsPanel/index.ts +4 -0
  196. package/src/components/MetricsPanel/renderers/CompactRenderer.tsx +125 -0
  197. package/src/components/MetricsPanel/renderers/ImageCard.tsx +62 -0
  198. package/src/components/MetricsPanel/renderers/PertinenceCard.tsx +55 -0
  199. package/src/components/MetricsPanel/tools/MetricsPanelTypes.ts +62 -0
  200. package/src/components/MetricsPanel/tools/chooseDefaultRender.ts +50 -0
  201. package/src/components/MetricsPanel/tools/colorUtils.ts +39 -0
  202. package/src/components/MetricsPanel/tools/index.ts +2 -0
  203. package/src/components/ModuleHeader/ModuleHeader.css +37 -0
  204. package/src/components/ModuleHeader/ModuleHeader.stories.tsx +37 -0
  205. package/src/components/ModuleHeader/ModuleHeader.tsx +42 -0
  206. package/src/components/ModuleHeader/index.ts +1 -0
  207. package/src/components/ModuleSideBar/ModuleSideBar.css +227 -0
  208. package/src/components/ModuleSideBar/ModuleSideBar.stories.tsx +40 -0
  209. package/src/components/ModuleSideBar/ModuleSideBar.tsx +155 -0
  210. package/src/components/ModuleSideBar/index.ts +1 -0
  211. package/src/components/NavBar/NavBar.css +58 -0
  212. package/src/components/NavBar/NavBar.stories.tsx +169 -0
  213. package/src/components/NavBar/NavBar.tsx +100 -0
  214. package/src/components/NavBar/NavContext.tsx +30 -0
  215. package/src/components/NavBar/index.ts +2 -0
  216. package/src/components/NavItem/NavItem.css +29 -0
  217. package/src/components/NavItem/NavItem.tsx +58 -0
  218. package/src/components/NavItem/index.ts +1 -0
  219. package/src/components/Page/Dashboard.tsx +93 -0
  220. package/src/components/Page/Page.stories.ts +33 -0
  221. package/src/components/Page/Page.tsx +73 -0
  222. package/src/components/Page/page.css +81 -0
  223. package/src/components/PerformanceCard/PerformanceCard.module.css +232 -0
  224. package/src/components/PerformanceCard/PerformanceCard.stories.tsx +441 -0
  225. package/src/components/PerformanceCard/PerformanceCard.tsx +198 -0
  226. package/src/components/PerformanceCard/defaultHistogramRenderer.tsx +32 -0
  227. package/src/components/PerformanceCard/tools/types.ts +50 -0
  228. package/src/components/PerformanceCard/tools/usePerformanceCard.ts +93 -0
  229. package/src/components/PeriodRange/PeriodRange.module.css +158 -0
  230. package/src/components/PeriodRange/PeriodRange.stories.tsx +66 -0
  231. package/src/components/PeriodRange/PeriodRange.tsx +130 -0
  232. package/src/components/PeriodSelect/PeriodSelect.module.css +65 -0
  233. package/src/components/PeriodSelect/PeriodSelect.stories.tsx +40 -0
  234. package/src/components/PeriodSelect/PeriodSelect.tsx +42 -0
  235. package/src/components/PeriodSelect/index.ts +1 -0
  236. package/src/components/ScrollableHorizontale/ScrollableHorizontale.css +40 -0
  237. package/src/components/ScrollableHorizontale/ScrollableHorizontale.stories.tsx +133 -0
  238. package/src/components/ScrollableHorizontale/ScrollableHorizontale.tsx +29 -0
  239. package/src/components/ScrollableHorizontale/index.ts +1 -0
  240. package/src/components/SearchBar/SearchBar.css +40 -0
  241. package/src/components/SearchBar/SearchBar.stories.tsx +36 -0
  242. package/src/components/SearchBar/SearchBar.tsx +30 -0
  243. package/src/components/SearchBar/index.ts +1 -0
  244. package/src/components/SectionTitle/SectionTitle.css +21 -0
  245. package/src/components/SectionTitle/SectionTitle.stories.tsx +39 -0
  246. package/src/components/SectionTitle/SectionTitle.tsx +18 -0
  247. package/src/components/SideComponent/PatientEditor.tsx +64 -0
  248. package/src/components/SideComponent/SideComponent.css +179 -0
  249. package/src/components/SideComponent/SideComponent.stories.tsx +547 -0
  250. package/src/components/SideComponent/SideComponent.tsx +243 -0
  251. package/src/components/SideComponent/hooks/useBodyScrollLock.ts +15 -0
  252. package/src/components/SideComponent/index.ts +2 -0
  253. package/src/components/SideComponent/portal.ts +11 -0
  254. package/src/components/SubNavBar/SubNavBar.tsx +41 -0
  255. package/src/components/SubNavBar/index.ts +1 -0
  256. package/src/components/Switcher/Switcher.css +65 -0
  257. package/src/components/Switcher/Switcher.stories.tsx +153 -0
  258. package/src/components/Switcher/Switcher.tsx +83 -0
  259. package/src/components/Switcher/index.ts +1 -0
  260. package/src/components/Title/Title.stories.tsx +18 -0
  261. package/src/components/Title/Title.tsx +26 -0
  262. package/src/components/Title/index.ts +1 -0
  263. package/src/components/TranslationKey/TranslationKey.css +272 -0
  264. package/src/components/TranslationKey/TranslationKey.stories.tsx +50 -0
  265. package/src/components/TranslationKey/TranslationKey.tsx +245 -0
  266. package/src/components/TranslationKey/index.ts +1 -0
  267. package/src/components/TrendItem/TrendItem.css +36 -0
  268. package/src/components/TrendItem/TrendItem.stories.tsx +276 -0
  269. package/src/components/TrendItem/TrendItem.tsx +46 -0
  270. package/src/components/TrendItem/index.ts +1 -0
  271. package/src/components/TrendList/TrendList.css +16 -0
  272. package/src/components/TrendList/TrendList.stories.tsx +337 -0
  273. package/src/components/TrendList/TrendList.tsx +45 -0
  274. package/src/components/TrendList/index.ts +1 -0
  275. package/src/components/theme/ThemeSwitcherButton.tsx +64 -0
  276. package/src/components/theme/context/ThemeContext.tsx +61 -0
  277. package/src/components/theme/context/index.ts +2 -0
  278. package/src/components/theme/context/useThemeSwitcher.ts +18 -0
  279. package/src/components/theme/index.ts +1 -0
  280. package/src/index.css +68 -0
  281. package/src/main.tsx +10 -0
  282. package/src/vite-env.d.ts +1 -0
  283. package/tsconfig.app.json +27 -0
  284. package/tsconfig.json +4 -0
  285. package/tsconfig.node.json +25 -0
  286. package/vite.config.ts +43 -0
  287. package/vitest.shims.d.ts +1 -0
@@ -0,0 +1,773 @@
1
+ /* DynamicForm.stories.tsx */
2
+ import React, { useState } from 'react';
3
+ // eslint-disable-next-line storybook/no-renderer-packages
4
+ import type { Meta, StoryObj } from '@storybook/react';
5
+ import { DynamicForm } from './DynamicForm';
6
+ import type { FormSchema } from './tools/form-metadata';
7
+
8
+ const meta: Meta<typeof DynamicForm> = {
9
+ title: 'Components/DynamicForm',
10
+ component: DynamicForm,
11
+ parameters: {
12
+ layout: 'padded',
13
+ },
14
+ tags: ['autodocs'],
15
+ argTypes: {
16
+ submitLabel: {
17
+ control: 'text',
18
+ description: 'Texte personnalisé pour le bouton de soumission',
19
+ },
20
+ submitIcon: {
21
+ control: 'text',
22
+ description: 'Nom de l\'icône lucide-react (ex: "Send", "Check", "Save")',
23
+ },
24
+ submitIconPosition: {
25
+ control: { type: 'inline-radio', options: ['left', 'right'] },
26
+ description: "Position de l'icône sur le bouton (left | right)",
27
+ },
28
+ },
29
+ };
30
+
31
+ export default meta;
32
+ type Story = StoryObj<typeof DynamicForm>;
33
+
34
+ // Helper pour créer des schémas de formulaire
35
+ const createSchema = (overrides: Partial<FormSchema>): FormSchema => ({
36
+ title: 'Formulaire Dynamique',
37
+ description: 'Un formulaire générique avec validation',
38
+ submitText: 'Soumettre',
39
+ fields: [],
40
+ ...overrides,
41
+ });
42
+
43
+ // Wrapper component pour gérer l'état et les soumissions
44
+ const DynamicFormWrapper: React.FC<{
45
+ schema: FormSchema;
46
+ initialData?: Record<string, unknown>;
47
+ submitLabel?: string;
48
+ submitIcon?: string;
49
+ submitIconPosition?: 'left' | 'right';
50
+ onCancel?: () => void;
51
+ cancelLabel?: string;
52
+ cancelIcon?: string;
53
+ }> = (args) => {
54
+ const [submittedData, setSubmittedData] = useState<Record<string, unknown> | null>(null);
55
+
56
+ const handleSubmit = (data: Record<string, unknown>) => {
57
+ // Dans la story on log et on affiche les données soumises
58
+ // Replacez par votre logique (API call, etc.) dans l'app réelle
59
+
60
+ console.log('Données soumises:', data);
61
+ setSubmittedData(data);
62
+ return Promise.resolve();
63
+ };
64
+
65
+ return React.createElement(
66
+ 'div',
67
+ { style: { maxWidth: '900px', margin: '0 auto' } },
68
+ React.createElement(DynamicForm, {
69
+ schema: args.schema,
70
+ initialData: args.initialData,
71
+ onSubmit: handleSubmit,
72
+ submitLabel: args.submitLabel,
73
+ submitIcon: args.submitIcon,
74
+ submitIconPosition: args.submitIconPosition,
75
+ onCancel: args.onCancel,
76
+ cancelLabel: args.cancelLabel,
77
+ cancelIcon: args.cancelIcon,
78
+ }),
79
+ submittedData &&
80
+ React.createElement(
81
+ 'div',
82
+ { style: { marginTop: '2rem', padding: '1rem', background: '#f8f9fa', borderRadius: 8 } },
83
+ React.createElement('h3', null, 'Données soumises:'),
84
+ React.createElement('pre', null, JSON.stringify(submittedData, null, 2))
85
+ )
86
+ );
87
+ };
88
+
89
+ /* ===========================
90
+ STORIES SANS GRID (STACK)
91
+ =========================== */
92
+
93
+ /** Contact simple (avec icône Send à gauche) */
94
+ export const ContactForm: Story = {
95
+ render: () =>
96
+ React.createElement(DynamicFormWrapper, {
97
+ schema: createSchema({
98
+ title: 'Formulaire de Contact',
99
+ description: 'Entrez vos informations pour nous contacter',
100
+ fields: [
101
+ {
102
+ type: 'text',
103
+ name: 'firstName',
104
+ label: 'Prénom',
105
+ required: true,
106
+ placeholder: 'Votre prénom',
107
+ gridCol: 12,
108
+ disabled: undefined,
109
+ },
110
+ {
111
+ type: 'text',
112
+ name: 'lastName',
113
+ label: 'Nom',
114
+ required: true,
115
+ placeholder: 'Votre nom',
116
+ gridCol: 12,
117
+ disabled: undefined,
118
+ },
119
+ {
120
+ type: 'email',
121
+ name: 'email',
122
+ label: 'Email',
123
+ required: true,
124
+ placeholder: 'votre@email.com',
125
+ gridCol: 12,
126
+ disabled: undefined,
127
+ },
128
+ {
129
+ type: 'textarea',
130
+ name: 'message',
131
+ label: 'Message',
132
+ required: true,
133
+ placeholder: 'Votre message...',
134
+ gridCol: 12,
135
+ disabled: undefined,
136
+ },
137
+ ],
138
+ }),
139
+ submitLabel: 'Envoyer',
140
+ submitIcon: 'Send',
141
+ submitIconPosition: 'left',
142
+ }),
143
+ parameters: {
144
+ docs: {
145
+ source: {
146
+ code: `<DynamicForm
147
+ schema={createSchema({
148
+ title: 'Formulaire de Contact',
149
+ fields: [
150
+ { type: 'text', name: 'firstName', label: 'Prénom', required: true },
151
+ { type: 'text', name: 'lastName', label: 'Nom', required: true },
152
+ { type: 'email', name: 'email', label: 'Email', required: true },
153
+ { type: 'textarea', name: 'message', label: 'Message', required: true },
154
+ ],
155
+ })}
156
+ submitLabel="Envoyer"
157
+ submitIcon="Send"
158
+ submitIconPosition="left"
159
+ />`,
160
+ },
161
+ },
162
+ },
163
+ };
164
+
165
+ /** Inscription (sans icône) */
166
+ export const RegistrationForm: Story = {
167
+ render: () =>
168
+ React.createElement(DynamicFormWrapper, {
169
+ schema: createSchema({
170
+ title: 'Inscription',
171
+ description: 'Créez votre compte',
172
+ fields: [
173
+ {
174
+ type: 'text',
175
+ name: 'username',
176
+ label: "Nom d'utilisateur",
177
+ required: true,
178
+ placeholder: 'Choisissez un nom utilisateur',
179
+ validation: { minLength: 3 },
180
+ gridCol: 12,
181
+ disabled: undefined,
182
+ },
183
+ {
184
+ type: 'password',
185
+ name: 'password',
186
+ label: 'Mot de passe',
187
+ required: true,
188
+ placeholder: 'Créez un mot de passe',
189
+ validation: { minLength: 6 },
190
+ attributes: { showPasswordToggle: true },
191
+ gridCol: 12,
192
+ disabled: undefined,
193
+ },
194
+ {
195
+ type: 'select',
196
+ name: 'gender',
197
+ label: 'Genre',
198
+ options: [
199
+ { value: '', label: 'Sélectionnez' },
200
+ { value: 'male', label: 'Homme' },
201
+ { value: 'female', label: 'Femme' },
202
+ { value: 'other', label: 'Autre' },
203
+ ],
204
+ gridCol: 12,
205
+ disabled: undefined,
206
+ },
207
+ {
208
+ type: 'date',
209
+ name: 'birthdate',
210
+ label: 'Date de naissance',
211
+ gridCol: 12,
212
+ disabled: undefined,
213
+ },
214
+ {
215
+ type: 'checkbox',
216
+ name: 'newsletter',
217
+ label: "S'abonner à la newsletter",
218
+ gridCol: 12,
219
+ disabled: undefined,
220
+ },
221
+ ],
222
+ }),
223
+ }),
224
+ parameters: {
225
+ docs: {
226
+ source: {
227
+ code: `<DynamicForm
228
+ schema={createSchema({
229
+ title: 'Inscription',
230
+ fields: [
231
+ { type: 'text', name: 'username', label: "Nom d'utilisateur", required: true },
232
+ { type: 'password', name: 'password', label: 'Mot de passe', required: true, attributes: { showPasswordToggle: true } },
233
+ { type: 'select', name: 'gender', label: 'Genre', options: [{ value:'', label:'Sélectionnez' }, { value:'male', label:'Homme' }] },
234
+ { type: 'date', name: 'birthdate', label: 'Date de naissance' },
235
+ { type: 'checkbox', name: 'newsletter', label: "S'abonner à la newsletter" },
236
+ ]
237
+ })}
238
+ />`,
239
+ },
240
+ },
241
+ },
242
+ };
243
+
244
+ /* ===========================
245
+ STORIES AVEC GRID
246
+ =========================== */
247
+
248
+ /** Grid simple 2 colonnes (avec icône Check à droite) */
249
+ export const GridTwoColumns: Story = {
250
+ render: () =>
251
+ React.createElement(DynamicFormWrapper, {
252
+ schema: createSchema({
253
+ title: 'Formulaire (Grid 2 colonnes)',
254
+ description: 'Exemple avec layout grid et 2 colonnes par ligne.',
255
+ layout: 'grid',
256
+ columns: 12,
257
+ fields: [
258
+ {
259
+ type: 'text',
260
+ name: 'firstName',
261
+ label: 'Prénom',
262
+ gridCol: 6,
263
+ placeholder: 'Prénom',
264
+ disabled: undefined,
265
+ },
266
+ {
267
+ type: 'text',
268
+ name: 'lastName',
269
+ label: 'Nom',
270
+ gridCol: 6,
271
+ placeholder: 'Nom',
272
+ disabled: undefined,
273
+ },
274
+ {
275
+ type: 'email',
276
+ name: 'email',
277
+ label: 'Email',
278
+ gridCol: 6,
279
+ placeholder: 'email@example.com',
280
+ disabled: undefined,
281
+ },
282
+ {
283
+ type: 'text',
284
+ name: 'phone',
285
+ label: 'Téléphone',
286
+ gridCol: 6,
287
+ placeholder: '+33 ...',
288
+ disabled: undefined,
289
+ },
290
+ {
291
+ type: 'select',
292
+ name: 'country',
293
+ label: 'Pays',
294
+ gridCol: 4,
295
+ options: [
296
+ { value: '', label: 'Sélectionner' },
297
+ { value: 'fr', label: 'France' },
298
+ { value: 'mg', label: 'Madagascar' },
299
+ ],
300
+ disabled: undefined,
301
+ },
302
+ {
303
+ type: 'date',
304
+ name: 'start',
305
+ label: 'Date de début',
306
+ gridCol: 4,
307
+ disabled: undefined,
308
+ },
309
+ {
310
+ type: 'date',
311
+ name: 'end',
312
+ label: 'Date de fin',
313
+ gridCol: 4,
314
+ disabled: undefined,
315
+ },
316
+ ],
317
+ }),
318
+ submitLabel: 'Terminer',
319
+ submitIcon: 'Check',
320
+ submitIconPosition: 'right',
321
+ }),
322
+ parameters: {
323
+ docs: {
324
+ source: {
325
+ code: `<DynamicForm
326
+ schema={createSchema({
327
+ title: 'Formulaire (Grid 2 colonnes)',
328
+ layout: 'grid',
329
+ columns: 12,
330
+ fields: [
331
+ { type: 'text', name: 'firstName', gridCol: 6 },
332
+ { type: 'text', name: 'lastName', gridCol: 6 },
333
+ { type: 'email', name: 'email', gridCol: 6 },
334
+ { type: 'text', name: 'phone', gridCol: 6 },
335
+ { type: 'select', name: 'country', gridCol: 4, options: [{ value:'', label:'Sélectionner' }, { value:'fr', label:'France' }] },
336
+ { type: 'date', name: 'start', gridCol: 4 },
337
+ { type: 'date', name: 'end', gridCol: 4 },
338
+ ],
339
+ })}
340
+ submitLabel="Terminer"
341
+ submitIcon="Check"
342
+ submitIconPosition="right"
343
+ />`,
344
+ },
345
+ },
346
+ },
347
+ };
348
+
349
+ /** Grid mixte — sans icône (ex. champs larges + petits) */
350
+ export const GridMixed: Story = {
351
+ render: () =>
352
+ React.createElement(DynamicFormWrapper, {
353
+ schema: createSchema({
354
+ title: 'Formulaire (Grid mixte)',
355
+ description: 'Exemple mélangeant champs pleine largeur et colonnes partagées.',
356
+ layout: 'grid',
357
+ columns: 12,
358
+ fields: [
359
+ {
360
+ type: 'section',
361
+ name: 'sec_personal',
362
+ label: 'Informations personnelles',
363
+ disabled: undefined,
364
+ },
365
+ {
366
+ type: 'text',
367
+ name: 'company',
368
+ label: 'Entreprise',
369
+ gridCol: 12,
370
+ placeholder: 'Nom de l’entreprise',
371
+ disabled: undefined,
372
+ },
373
+ {
374
+ type: 'text',
375
+ name: 'jobTitle',
376
+ label: 'Poste',
377
+ gridCol: 6,
378
+ placeholder: 'Poste',
379
+ disabled: undefined,
380
+ },
381
+ {
382
+ type: 'number',
383
+ name: 'teamSize',
384
+ label: 'Taille de l’équipe',
385
+ gridCol: 6,
386
+ placeholder: 'Nombre',
387
+ disabled: undefined,
388
+ },
389
+
390
+ {
391
+ type: 'section',
392
+ name: 'sec_address',
393
+ label: 'Adresse',
394
+ disabled: undefined,
395
+ },
396
+ {
397
+ type: 'text',
398
+ name: 'street',
399
+ label: 'Rue',
400
+ gridCol: 8,
401
+ placeholder: 'Rue et numéro',
402
+ disabled: undefined,
403
+ },
404
+ {
405
+ type: 'text',
406
+ name: 'zip',
407
+ label: 'Code postal',
408
+ gridCol: 4,
409
+ placeholder: 'Code postal',
410
+ disabled: undefined,
411
+ },
412
+
413
+ {
414
+ type: 'section',
415
+ name: 'sec_notes',
416
+ label: 'Notes',
417
+ disabled: undefined,
418
+ },
419
+ {
420
+ type: 'textarea',
421
+ name: 'notes',
422
+ label: 'Notes',
423
+ gridCol: 12,
424
+ placeholder: 'Informations supplémentaires...',
425
+ disabled: undefined,
426
+ },
427
+ ],
428
+ }),
429
+ // pas d'icône
430
+ }),
431
+ parameters: {
432
+ docs: {
433
+ source: {
434
+ code: `<DynamicForm
435
+ schema={createSchema({
436
+ title: 'Formulaire (Grid mixte)',
437
+ layout: 'grid',
438
+ columns: 12,
439
+ fields: [
440
+ { type: 'section', name: 'sec_personal', label: 'Informations personnelles' },
441
+ { type: 'text', name: 'company', gridCol: 12 },
442
+ { type: 'text', name: 'jobTitle', gridCol: 6 },
443
+ { type: 'number', name: 'teamSize', gridCol: 6 },
444
+ { type: 'section', name: 'sec_address', label: 'Adresse' },
445
+ { type: 'text', name: 'street', gridCol: 8 },
446
+ { type: 'text', name: 'zip', gridCol: 4 },
447
+ { type: 'section', name: 'sec_notes', label: 'Notes' },
448
+ { type: 'textarea', name: 'notes', gridCol: 12 },
449
+ ]
450
+ })}
451
+ />`,
452
+ },
453
+ },
454
+ },
455
+ };
456
+
457
+ /** Account Settings — avec icône Save (à gauche) */
458
+ export const AccountSettings: Story = {
459
+ render: () =>
460
+ React.createElement(DynamicFormWrapper, {
461
+ schema: createSchema({
462
+ title: 'Informations du compte',
463
+ description: '',
464
+ submitText: 'Valider',
465
+ layout: 'grid',
466
+ columns: 12,
467
+ fields: [
468
+ {
469
+ type: 'section',
470
+ name: 'sec_account',
471
+ label: 'Informations du compte',
472
+ disabled: undefined,
473
+ },
474
+ {
475
+ type: 'email',
476
+ name: 'email',
477
+ label: 'Adresse e-mail',
478
+ placeholder: 'tsiky@appy.solutions',
479
+ required: true,
480
+ gridCol: 12,
481
+ disabled: true,
482
+ attributes: { icon: 'Mail', iconPosition: 'prefix' },
483
+ },
484
+
485
+ {
486
+ type: 'section',
487
+ name: 'sec_password',
488
+ label: 'Changer le mot de passe',
489
+ disabled: undefined,
490
+ },
491
+ {
492
+ type: 'password',
493
+ name: 'password',
494
+ label: 'Entrez Votre Nouveau mot de passe',
495
+ placeholder: 'Mot de passe',
496
+ gridCol: 6,
497
+ validation: { minLength: 6 },
498
+ attributes: { icon: 'Lock', showPasswordToggle: true },
499
+ disabled: undefined,
500
+ },
501
+ {
502
+ type: 'password',
503
+ name: 'confirmPassword',
504
+ label: 'Confirmer nouveau mot de passe',
505
+ placeholder: 'Confirmer nouveau mot de passe',
506
+ gridCol: 6,
507
+ attributes: { icon: 'Lock' },
508
+ disabled: undefined,
509
+ },
510
+
511
+ {
512
+ type: 'section',
513
+ name: 'sec_pref',
514
+ label: 'Préférences',
515
+ disabled: undefined,
516
+ },
517
+ {
518
+ type: 'select',
519
+ name: 'defaultScreen',
520
+ label: 'Ecran par défaut',
521
+ placeholder: 'Sélectionnez un écran par défaut',
522
+ gridCol: 6,
523
+ options: [
524
+ { value: 'dashboard', label: 'Tableau de bord' },
525
+ { value: 'films', label: 'Films' },
526
+ ],
527
+ attributes: { icon: 'Monitor' },
528
+ disabled: undefined,
529
+ },
530
+ {
531
+ type: 'select',
532
+ name: 'language',
533
+ label: 'Langue',
534
+ placeholder: 'Français',
535
+ gridCol: 6,
536
+ options: [
537
+ { value: 'fr', label: 'Français' },
538
+ { value: 'en', label: 'English' },
539
+ ],
540
+ attributes: { icon: 'Globe' },
541
+ disabled: undefined,
542
+ },
543
+ ],
544
+ }),
545
+ initialData: { email: 'tsiky@appy.solutions' },
546
+ submitLabel: 'Valider',
547
+ submitIcon: 'Save',
548
+ submitIconPosition: 'left',
549
+ onCancel: () => console.log('Retour'),
550
+ cancelLabel: 'Retour',
551
+ cancelIcon: 'ChevronLeft',
552
+ }),
553
+ parameters: {
554
+ docs: {
555
+ source: {
556
+ code: `<DynamicForm
557
+ schema={createSchema({
558
+ title: 'Informations du compte',
559
+ layout: 'grid',
560
+ columns: 12,
561
+ fields: [
562
+ { type: 'email', name: 'email', gridCol: 12, disabled: true, attributes: { icon: 'Mail' } },
563
+ { type: 'password', name: 'password', gridCol: 6, attributes: { icon: 'Lock', showPasswordToggle: true } },
564
+ { type: 'password', name: 'confirmPassword', gridCol: 6, attributes: { icon: 'Lock' } },
565
+ { type: 'select', name: 'defaultScreen', gridCol: 6, attributes: { icon: 'Monitor' } },
566
+ { type: 'select', name: 'language', gridCol: 6, attributes: { icon: 'Globe' } },
567
+ ]
568
+ })}
569
+ initialData={{ email: 'tsiky@appy.solutions' }}
570
+ submitLabel="Valider"
571
+ submitIcon="Save"
572
+ submitIconPosition="left"
573
+ onCancel={() => {}}
574
+ cancelLabel="Retour"
575
+ cancelIcon="ChevronLeft"
576
+ />`,
577
+ },
578
+ },
579
+ },
580
+ };
581
+
582
+ /* ===========================
583
+ STORIES UTILES / DIVERS
584
+ =========================== */
585
+
586
+ /** WithInitialData: montre l'édition avec valeurs initiales (sans icône) */
587
+ export const WithInitialData: Story = {
588
+ render: () =>
589
+ React.createElement(DynamicFormWrapper, {
590
+ initialData: {
591
+ firstName: 'Jean',
592
+ lastName: 'Dupont',
593
+ email: 'jean.dupont@example.com',
594
+ newsletter: true,
595
+ },
596
+ schema: createSchema({
597
+ title: 'Modification de profil',
598
+ fields: [
599
+ {
600
+ type: 'text',
601
+ name: 'firstName',
602
+ label: 'Prénom',
603
+ required: true,
604
+ gridCol: 6,
605
+ disabled: undefined,
606
+ },
607
+ {
608
+ type: 'text',
609
+ name: 'lastName',
610
+ label: 'Nom',
611
+ required: true,
612
+ gridCol: 6,
613
+ disabled: undefined,
614
+ },
615
+ {
616
+ type: 'email',
617
+ name: 'email',
618
+ label: 'Email',
619
+ required: true,
620
+ gridCol: 12,
621
+ disabled: undefined,
622
+ },
623
+ {
624
+ type: 'checkbox',
625
+ name: 'newsletter',
626
+ label: 'Recevoir les newsletters',
627
+ gridCol: 12,
628
+ disabled: undefined,
629
+ },
630
+ ],
631
+ }),
632
+ }),
633
+ parameters: {
634
+ docs: {
635
+ source: {
636
+ code: `<DynamicForm
637
+ schema={createSchema({
638
+ title: 'Modification de profil',
639
+ fields: [
640
+ { type: 'text', name: 'firstName', gridCol: 6 },
641
+ { type: 'text', name: 'lastName', gridCol: 6 },
642
+ { type: 'email', name: 'email', gridCol: 12 },
643
+ { type: 'checkbox', name: 'newsletter', gridCol: 12 },
644
+ ],
645
+ })}
646
+ initialData={{ firstName: 'Jean', lastName: 'Dupont', email: 'jean.dupont@example.com' }}
647
+ />`,
648
+ },
649
+ },
650
+ },
651
+ };
652
+
653
+ /** AllFieldTypes: montrer tous les types (avec icône Paperclip à droite) */
654
+ export const AllFieldTypes: Story = {
655
+ render: () =>
656
+ React.createElement(DynamicFormWrapper, {
657
+ schema: createSchema({
658
+ title: 'Tous les Types de Champs',
659
+ description: 'Démonstration de tous les types de champs disponibles',
660
+ fields: [
661
+ {
662
+ type: 'text',
663
+ name: 'textField',
664
+ label: 'Texte',
665
+ placeholder: 'Champ texte simple',
666
+ disabled: undefined,
667
+ },
668
+ {
669
+ type: 'textarea',
670
+ name: 'textareaField',
671
+ label: 'Zone de texte',
672
+ placeholder: 'Texte long...',
673
+ disabled: undefined,
674
+ },
675
+ {
676
+ type: 'email',
677
+ name: 'emailField',
678
+ label: 'Email',
679
+ placeholder: 'email@example.com',
680
+ disabled: undefined,
681
+ },
682
+ {
683
+ type: 'password',
684
+ name: 'passwordField',
685
+ label: 'Mot de passe',
686
+ disabled: undefined,
687
+ },
688
+ {
689
+ type: 'number',
690
+ name: 'numberField',
691
+ label: 'Nombre',
692
+ placeholder: '0',
693
+ disabled: undefined,
694
+ },
695
+ {
696
+ type: 'select',
697
+ name: 'selectField',
698
+ label: 'Sélection',
699
+ options: [
700
+ { value: '', label: 'Sélectionner' },
701
+ { value: 'opt1', label: 'Option 1' },
702
+ { value: 'opt2', label: 'Option 2' },
703
+ ],
704
+ disabled: undefined,
705
+ },
706
+ {
707
+ type: 'checkbox',
708
+ name: 'checkboxField',
709
+ label: 'Case à cocher',
710
+ disabled: undefined,
711
+ },
712
+ {
713
+ type: 'radio',
714
+ name: 'radioField',
715
+ label: 'Boutons radio',
716
+ options: [
717
+ { value: 'radio1', label: 'Choix 1' },
718
+ { value: 'radio2', label: 'Choix 2' },
719
+ ],
720
+ disabled: undefined,
721
+ },
722
+ {
723
+ type: 'date',
724
+ name: 'dateField',
725
+ label: 'Date',
726
+ disabled: undefined,
727
+ },
728
+ {
729
+ type: 'datetime-local',
730
+ name: 'datetimeField',
731
+ label: 'Date et Heure',
732
+ disabled: undefined,
733
+ },
734
+ {
735
+ type: 'file',
736
+ name: 'fileField',
737
+ label: 'Fichier',
738
+ disabled: undefined,
739
+ },
740
+ ],
741
+ }),
742
+ submitLabel: 'Envoyer fichiers',
743
+ submitIcon: 'Paperclip',
744
+ submitIconPosition: 'right',
745
+ }),
746
+ parameters: {
747
+ docs: {
748
+ source: {
749
+ code: `<DynamicForm
750
+ schema={createSchema({
751
+ title: 'Tous les Types de Champs',
752
+ fields: [
753
+ { type: 'text', name: 'textField' },
754
+ { type: 'textarea', name: 'textareaField' },
755
+ { type: 'email', name: 'emailField' },
756
+ { type: 'password', name: 'passwordField' },
757
+ { type: 'number', name: 'numberField' },
758
+ { type: 'select', name: 'selectField', options: [{ value:'', label:'Sélectionner' }, { value:'opt1', label:'Option 1' }] },
759
+ { type: 'checkbox', name: 'checkboxField' },
760
+ { type: 'radio', name: 'radioField', options: [{ value:'radio1', label:'Choix 1' }] },
761
+ { type: 'date', name: 'dateField' },
762
+ { type: 'datetime-local', name: 'datetimeField' },
763
+ { type: 'file', name: 'fileField' },
764
+ ],
765
+ })}
766
+ submitLabel="Envoyer fichiers"
767
+ submitIcon="Paperclip"
768
+ submitIconPosition="right"
769
+ />`,
770
+ },
771
+ },
772
+ },
773
+ };