-
- {{i18nKey: `${i18nPrefix}.icons.searchBar.search`}}
-
+
+
+
diff --git a/packages/docs/.storybook/preview.tsx b/packages/docs/.storybook/preview.tsx
index 8beeffcd9..33a979a0e 100644
--- a/packages/docs/.storybook/preview.tsx
+++ b/packages/docs/.storybook/preview.tsx
@@ -2,7 +2,8 @@ import "@focus4/styling/lib/focus4.styling.css";
import "@focus4/toolbox/lib/focus4.toolbox.css";
import "./preview.css";
-import {translation} from "@focus4/forms";
+import {translation as collections} from "@focus4/collections";
+import {translation as forms} from "@focus4/forms";
import {colorScheme, initColorScheme} from "@focus4/styling";
import {DocsContainer as BaseContainer} from "@storybook/blocks";
import type {Preview} from "@storybook/react";
@@ -19,7 +20,9 @@ initColorScheme(true);
i18next.init({
lng: "fr",
- resources: {fr: {translation: {focus: {...translation.fr, icons: translation.icons}}}},
+ resources: {
+ fr: {translation: {focus: {...collections.fr, ...forms.fr, icons: {...collections.icons, ...forms.icons}}}}
+ },
nsSeparator: "đ€·ââïž"
});
@@ -30,12 +33,7 @@ function DocsContainer(props) {
export default {
parameters: {
- actions: {argTypesRegex: "^on[A-Z].*"},
controls: {
- matchers: {
- color: /(background|color)$/i,
- date: /Date$/i
- },
sort: "requiredFirst"
},
docs: {
@@ -48,6 +46,7 @@ export default {
"Les bases",
"ModÚle métier",
"Composants",
+ ["Composants de base", "@focus4âtoolbox", "@focus4âforms"],
"Routage",
"Mise en page",
"Listes et recherche",
diff --git a/packages/docs/components/components.mdx b/packages/docs/components/components.mdx
new file mode 100644
index 000000000..182bb297b
--- /dev/null
+++ b/packages/docs/components/components.mdx
@@ -0,0 +1,24 @@
+import {Meta} from "@storybook/blocks";
+
+
+
+# Composants de base
+
+Focus met à disposition une série de composants de base qui implémentent [Material Design 3](https://m3.material.io/components) (avec quelques adaptations).
+
+Ces composants cherchent à couvrir les besoins les plus standards d'une application, tout en offrant un niveau de personnalisation élevé pour couvrir un
+maximum de cas.
+
+- Le module `@focus4/toolbox` contient les versions de base de ces composants, qui sont directement repris de la spécification Material Design.
+- Le module `@focus4/forms` contient :
+ - Quelques "surcharges" de ces composants pour pouvoir s'interfacer directement avec un formulaire (`Input` pour `TextField` et `Select` pour
+ `Dropdown` par exemple)
+ - Des composants un peu plus avancés qui combinent des composants de base pour réaliser des saisies plus complexes (comme `InputDate` ou
+ `SelectChips`), ou simplifier des cas d'usage courants (comme `BooleanRadio` ou `SelectCheckbox`). Ces composants n'existent pas en tant que
+ tels dans la spécification Material Design.
+ - Les composants d'affichage pour les formulaires (`Display`, `Label` et `Panel`)
+
+**Un composant de saisie d'un domaine pour un champ doit venir du module `@focus4/forms`**, car il doit respecter le contrat d'interface correspondant du
+domaine (`BaseInputProps` / `BaseSelectProps` / `BaseAutocompleteProps`). Si vous voulez construire votre propre composant de saisie, vous pouvez
+reproduire ce que font les composants de `@focus4/forms`, en particulier la gestion du `type`, du `onChange`, de l'`error` et du `supportingText`. Ce
+mĂ©canisme a vocation Ă ĂȘtre amĂ©liorĂ© dans le futur, et est suivi par l'[issue #192](https://github.com/klee-contrib/focus4/issues/192) sur Github.
diff --git a/packages/docs/components/forms/AutocompleteChips.stories.tsx b/packages/docs/components/forms/AutocompleteChips.stories.tsx
index d0ef7f81a..fa864de4c 100644
--- a/packages/docs/components/forms/AutocompleteChips.stories.tsx
+++ b/packages/docs/components/forms/AutocompleteChips.stories.tsx
@@ -7,6 +7,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...AutocompleteChipsMeta,
title: "Composants/@focus4âforms/AutocompleteChips",
+ tags: ["autodocs"],
args: {type: "string"}
} as Meta
;
diff --git a/packages/docs/components/forms/AutocompleteSearch.stories.tsx b/packages/docs/components/forms/AutocompleteSearch.stories.tsx
index 013b14087..2b3e85015 100644
--- a/packages/docs/components/forms/AutocompleteSearch.stories.tsx
+++ b/packages/docs/components/forms/AutocompleteSearch.stories.tsx
@@ -7,6 +7,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...AutocompleteSearchMeta,
title: "Composants/@focus4âforms/AutocompleteSearch",
+ tags: ["autodocs"],
args: {type: "string"}
} as Meta;
diff --git a/packages/docs/components/forms/BooleanRadio.stories.tsx b/packages/docs/components/forms/BooleanRadio.stories.tsx
index 26c56f508..6165053fb 100644
--- a/packages/docs/components/forms/BooleanRadio.stories.tsx
+++ b/packages/docs/components/forms/BooleanRadio.stories.tsx
@@ -7,6 +7,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...BooleanRadioMeta,
title: "Composants/@focus4âforms/BooleanRadio",
+ tags: ["autodocs"],
args: {type: "boolean"}
} as Meta;
diff --git a/packages/docs/components/forms/Display.stories.tsx b/packages/docs/components/forms/Display.stories.tsx
index 2a420f20a..507d1af8f 100644
--- a/packages/docs/components/forms/Display.stories.tsx
+++ b/packages/docs/components/forms/Display.stories.tsx
@@ -7,6 +7,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...DisplayMeta,
title: "Composants/@focus4âforms/Display",
+ tags: ["autodocs"],
args: {type: "string", value: "Valeur"}
} as Meta;
diff --git a/packages/docs/components/forms/Input.stories.tsx b/packages/docs/components/forms/Input.stories.tsx
index 13ec97b25..48a07371e 100644
--- a/packages/docs/components/forms/Input.stories.tsx
+++ b/packages/docs/components/forms/Input.stories.tsx
@@ -7,6 +7,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...InputMeta,
title: "Composants/@focus4âforms/Input",
+ tags: ["autodocs"],
args: {type: "string"}
} as Meta;
diff --git a/packages/docs/components/forms/InputDate.stories.tsx b/packages/docs/components/forms/InputDate.stories.tsx
index 038e8f569..bf7c515fb 100644
--- a/packages/docs/components/forms/InputDate.stories.tsx
+++ b/packages/docs/components/forms/InputDate.stories.tsx
@@ -7,6 +7,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...InputDateMeta,
title: "Composants/@focus4âforms/InputDate",
+ tags: ["autodocs"],
args: {type: "string"}
} as Meta;
diff --git a/packages/docs/components/forms/Label.stories.tsx b/packages/docs/components/forms/Label.stories.tsx
index a810353a5..b2198d0e4 100644
--- a/packages/docs/components/forms/Label.stories.tsx
+++ b/packages/docs/components/forms/Label.stories.tsx
@@ -7,6 +7,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...LabelMeta,
title: "Composants/@focus4âforms/Label",
+ tags: ["autodocs"],
args: {label: "Label"}
} as Meta;
diff --git a/packages/docs/components/forms/Panel.stories.tsx b/packages/docs/components/forms/Panel.stories.tsx
index f1a3aa0c7..a56e85121 100644
--- a/packages/docs/components/forms/Panel.stories.tsx
+++ b/packages/docs/components/forms/Panel.stories.tsx
@@ -6,7 +6,8 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...PanelMeta,
- title: "Composants/@focus4âforms/Panel"
+ title: "Composants/@focus4âforms/Panel",
+ tags: ["autodocs"]
} as Meta;
export const Showcase: StoryObj = {};
diff --git a/packages/docs/components/forms/PanelButtons.stories.tsx b/packages/docs/components/forms/PanelButtons.stories.tsx
index b3ddefc74..e61d29a71 100644
--- a/packages/docs/components/forms/PanelButtons.stories.tsx
+++ b/packages/docs/components/forms/PanelButtons.stories.tsx
@@ -6,7 +6,8 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...PanelButtonsMeta,
- title: "Composants/@focus4âforms/PanelButtons"
+ title: "Composants/@focus4âforms/PanelButtons",
+ tags: ["autodocs"]
} as Meta;
export const Showcase: StoryObj = {};
diff --git a/packages/docs/components/forms/Select.stories.tsx b/packages/docs/components/forms/Select.stories.tsx
index ca125c5a3..0b245b047 100644
--- a/packages/docs/components/forms/Select.stories.tsx
+++ b/packages/docs/components/forms/Select.stories.tsx
@@ -8,6 +8,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...SelectMeta,
title: "Composants/@focus4âforms/Select",
+ tags: ["autodocs"],
args: {
type: "string",
values: makeReferenceList([
diff --git a/packages/docs/components/forms/SelectAutocomplete.stories.tsx b/packages/docs/components/forms/SelectAutocomplete.stories.tsx
index 88dab0b1f..610b4b3d7 100644
--- a/packages/docs/components/forms/SelectAutocomplete.stories.tsx
+++ b/packages/docs/components/forms/SelectAutocomplete.stories.tsx
@@ -8,6 +8,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...SelectAutocompleteMeta,
title: "Composants/@focus4âforms/SelectAutocomplete",
+ tags: ["autodocs"],
args: {
type: "string-array",
values: makeReferenceList([
diff --git a/packages/docs/components/forms/SelectCheckbox.stories.tsx b/packages/docs/components/forms/SelectCheckbox.stories.tsx
index adf9d2b56..e9ccc00f3 100644
--- a/packages/docs/components/forms/SelectCheckbox.stories.tsx
+++ b/packages/docs/components/forms/SelectCheckbox.stories.tsx
@@ -8,6 +8,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...SelectCheckboxMeta,
title: "Composants/@focus4âforms/SelectCheckbox",
+ tags: ["autodocs"],
args: {
type: "string-array",
values: makeReferenceList([
diff --git a/packages/docs/components/forms/SelectChips.stories.tsx b/packages/docs/components/forms/SelectChips.stories.tsx
index c6f4ae6aa..d86b01f25 100644
--- a/packages/docs/components/forms/SelectChips.stories.tsx
+++ b/packages/docs/components/forms/SelectChips.stories.tsx
@@ -8,6 +8,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...SelectChipsMeta,
title: "Composants/@focus4âforms/SelectChips",
+ tags: ["autodocs"],
args: {
type: "string-array",
values: makeReferenceList([
diff --git a/packages/docs/components/forms/SelectRadio.stories.tsx b/packages/docs/components/forms/SelectRadio.stories.tsx
index 527403f79..a74ac74fc 100644
--- a/packages/docs/components/forms/SelectRadio.stories.tsx
+++ b/packages/docs/components/forms/SelectRadio.stories.tsx
@@ -8,6 +8,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...SelectRadioMeta,
title: "Composants/@focus4âforms/SelectRadio",
+ tags: ["autodocs"],
args: {
type: "string",
values: makeReferenceList([
diff --git a/packages/docs/components/toolbox/Autocomplete.stories.tsx b/packages/docs/components/toolbox/Autocomplete.stories.tsx
index aad38c676..cf295b127 100644
--- a/packages/docs/components/toolbox/Autocomplete.stories.tsx
+++ b/packages/docs/components/toolbox/Autocomplete.stories.tsx
@@ -1,3 +1,5 @@
+import {useState} from "react";
+
import {Autocomplete} from "@focus4/toolbox";
import {AutocompleteMeta} from "./metas/autocomplete";
@@ -7,6 +9,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...AutocompleteMeta,
title: "Composants/@focus4âtoolbox/Autocomplete",
+ tags: ["autodocs"],
args: {
values: [
{key: "1", label: "Option 1"},
@@ -15,4 +18,28 @@ export default {
}
} as Meta;
-export const Showcase: StoryObj = {};
+export const Showcase: StoryObj = {
+ render(props) {
+ const [selected, setSelected] = useState();
+ const [selected2, setSelected2] = useState();
+ return (
+
+
setSelected(undefined)}}
+ value={selected}
+ {...props}
+ onChange={setSelected}
+ />
+
+
+
+ );
+ }
+};
diff --git a/packages/docs/components/toolbox/Button.stories.tsx b/packages/docs/components/toolbox/Button.stories.tsx
index 92dd53d4d..0d664a99b 100644
--- a/packages/docs/components/toolbox/Button.stories.tsx
+++ b/packages/docs/components/toolbox/Button.stories.tsx
@@ -6,6 +6,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...ButtonMeta,
title: "Composants/@focus4âtoolbox/Button",
+ tags: ["autodocs"],
args: {
label: "Button"
}
diff --git a/packages/docs/components/toolbox/Calendar.stories.tsx b/packages/docs/components/toolbox/Calendar.stories.tsx
index 7a82e986b..4f787f18f 100644
--- a/packages/docs/components/toolbox/Calendar.stories.tsx
+++ b/packages/docs/components/toolbox/Calendar.stories.tsx
@@ -8,7 +8,8 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...CalendarMeta,
- title: "Composants/@focus4âtoolbox/Calendar"
+ title: "Composants/@focus4âtoolbox/Calendar",
+ tags: ["autodocs"]
} as Meta;
export const Showcase: StoryObj = {
diff --git a/packages/docs/components/toolbox/Checkbox.stories.tsx b/packages/docs/components/toolbox/Checkbox.stories.tsx
index 2831013ca..fee462dfb 100644
--- a/packages/docs/components/toolbox/Checkbox.stories.tsx
+++ b/packages/docs/components/toolbox/Checkbox.stories.tsx
@@ -8,7 +8,8 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...CheckboxMeta,
- title: "Composants/@focus4âtoolbox/Checkbox"
+ title: "Composants/@focus4âtoolbox/Checkbox",
+ tags: ["autodocs"]
} as Meta;
export const Showcase: StoryObj = {
diff --git a/packages/docs/components/toolbox/Chip.stories.tsx b/packages/docs/components/toolbox/Chip.stories.tsx
index 0467abd40..22c1acf91 100644
--- a/packages/docs/components/toolbox/Chip.stories.tsx
+++ b/packages/docs/components/toolbox/Chip.stories.tsx
@@ -7,6 +7,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...ChipMeta,
title: "Composants/@focus4âtoolbox/Chip",
+ tags: ["autodocs"],
args: {
label: "Chip"
}
diff --git a/packages/docs/components/toolbox/CircularProgressIndicator.stories.tsx b/packages/docs/components/toolbox/CircularProgressIndicator.stories.tsx
index def91f5cb..c695469a5 100644
--- a/packages/docs/components/toolbox/CircularProgressIndicator.stories.tsx
+++ b/packages/docs/components/toolbox/CircularProgressIndicator.stories.tsx
@@ -7,6 +7,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...CircularProgressIndicatorMeta,
title: "Composants/@focus4âtoolbox/CircularProgressIndicator",
+ tags: ["autodocs"],
args: {
value: 55
}
diff --git a/packages/docs/components/toolbox/Dropdown.stories.tsx b/packages/docs/components/toolbox/Dropdown.stories.tsx
index 36f91eec7..d7b2c9596 100644
--- a/packages/docs/components/toolbox/Dropdown.stories.tsx
+++ b/packages/docs/components/toolbox/Dropdown.stories.tsx
@@ -9,6 +9,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...DropdownMeta,
title: "Composants/@focus4âtoolbox/Dropdown",
+ tags: ["autodocs"],
args: {
values: [
{key: "1", label: "Option 1"},
diff --git a/packages/docs/components/toolbox/FloatingActionButton.stories.tsx b/packages/docs/components/toolbox/FloatingActionButton.stories.tsx
index 82d7813be..85e5153b5 100644
--- a/packages/docs/components/toolbox/FloatingActionButton.stories.tsx
+++ b/packages/docs/components/toolbox/FloatingActionButton.stories.tsx
@@ -9,6 +9,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...FloatingActionButtonMeta,
title: "Composants/@focus4âtoolbox/FloatingActionButton",
+ tags: ["autodocs"],
args: {
icon: "add",
label: "Ajouter"
diff --git a/packages/docs/components/toolbox/FontIcon.stories.tsx b/packages/docs/components/toolbox/FontIcon.stories.tsx
index fa2d64d10..840b76562 100644
--- a/packages/docs/components/toolbox/FontIcon.stories.tsx
+++ b/packages/docs/components/toolbox/FontIcon.stories.tsx
@@ -7,7 +7,26 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...FontIconMeta,
title: "Composants/@focus4âtoolbox/FontIcon",
- args: {children: "add"}
+ tags: ["autodocs"],
+ args: {
+ children: "lightbulb"
+ }
} as Meta;
-export const Showcase: StoryObj = {};
+export const Showcase: StoryObj = {
+ render(props) {
+ return (
+
+ );
+ }
+};
diff --git a/packages/docs/components/toolbox/IconButton.stories.tsx b/packages/docs/components/toolbox/IconButton.stories.tsx
index 170418c84..cc5c1635b 100644
--- a/packages/docs/components/toolbox/IconButton.stories.tsx
+++ b/packages/docs/components/toolbox/IconButton.stories.tsx
@@ -7,6 +7,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...IconButtonMeta,
title: "Composants/@focus4âtoolbox/IconButton",
+ tags: ["autodocs"],
args: {
icon: "add"
}
diff --git a/packages/docs/components/toolbox/LinearProgressIndicator.stories.tsx b/packages/docs/components/toolbox/LinearProgressIndicator.stories.tsx
index 114c9f7a5..4b1cbe23e 100644
--- a/packages/docs/components/toolbox/LinearProgressIndicator.stories.tsx
+++ b/packages/docs/components/toolbox/LinearProgressIndicator.stories.tsx
@@ -7,6 +7,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...LinearProgressIndicatorMeta,
title: "Composants/@focus4âtoolbox/LinearProgressIndicator",
+ tags: ["autodocs"],
args: {
value: 55
}
diff --git a/packages/docs/components/toolbox/Menu.mdx b/packages/docs/components/toolbox/Menu.mdx
new file mode 100644
index 000000000..1b9b52673
--- /dev/null
+++ b/packages/docs/components/toolbox/Menu.mdx
@@ -0,0 +1,18 @@
+import {Meta, Description, Title, Controls, Canvas} from "@storybook/blocks";
+
+import MenuStories, {Showcase} from "./Menu.stories";
+import MenuItemStories, {Showcase as MenuItem} from "./MenuItem.stories";
+
+
+
+
+
+
+
+
+
+
+{MenuItemStories.title.split("/")[2]}
+{MenuItemStories.parameters.docs.description.component}
+
+
diff --git a/packages/docs/components/toolbox/Menu.stories.tsx b/packages/docs/components/toolbox/Menu.stories.tsx
index c92b7d16a..52a2403da 100644
--- a/packages/docs/components/toolbox/Menu.stories.tsx
+++ b/packages/docs/components/toolbox/Menu.stories.tsx
@@ -1,4 +1,4 @@
-import {IconButton, Menu, MenuItem, useMenu} from "@focus4/toolbox";
+import {Button, IconButton, Menu, MenuItem, useMenu} from "@focus4/toolbox";
import {MenuMeta} from "./metas/menu";
@@ -12,13 +12,24 @@ export default {
export const Showcase: StoryObj = {
render() {
const menu = useMenu();
+ const menu2 = useMenu();
return (
-
-
-
-
-
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
);
}
diff --git a/packages/docs/components/toolbox/MenuItem.stories.tsx b/packages/docs/components/toolbox/MenuItem.stories.tsx
index c6de4c2e5..0c42268b4 100644
--- a/packages/docs/components/toolbox/MenuItem.stories.tsx
+++ b/packages/docs/components/toolbox/MenuItem.stories.tsx
@@ -6,8 +6,7 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...MenuItemMeta,
- title: "Composants/@focus4âtoolbox/MenuItem",
- args: {caption: "Action"}
+ title: "Composants/@focus4âtoolbox/MenuItem"
} as Meta
;
export const Showcase: StoryObj = {};
diff --git a/packages/docs/components/toolbox/RadioButton.mdx b/packages/docs/components/toolbox/RadioButton.mdx
new file mode 100644
index 000000000..4b1d3b8f9
--- /dev/null
+++ b/packages/docs/components/toolbox/RadioButton.mdx
@@ -0,0 +1,18 @@
+import {Meta, Description, Title, Controls, Canvas} from "@storybook/blocks";
+
+import RadioButtonStories, {Showcase} from "./RadioButton.stories";
+import RadioGroupStories, {Showcase as RadioGroup} from "./RadioGroup.stories";
+
+
+
+
+
+
+
+
+
+
+{RadioGroupStories.title.split("/")[2]}
+{RadioGroupStories.parameters.docs.description.component}
+
+
diff --git a/packages/docs/components/toolbox/RadioButton.stories.tsx b/packages/docs/components/toolbox/RadioButton.stories.tsx
index 4267817cf..b5f0f50e8 100644
--- a/packages/docs/components/toolbox/RadioButton.stories.tsx
+++ b/packages/docs/components/toolbox/RadioButton.stories.tsx
@@ -1,4 +1,6 @@
-import {RadioButton} from "@focus4/toolbox";
+import {useState} from "react";
+
+import {RadioButton, RadioGroup} from "@focus4/toolbox";
import {RadioButtonMeta} from "./metas/radio-button";
@@ -9,4 +11,15 @@ export default {
title: "Composants/@focus4âtoolbox/RadioButton"
} as Meta;
-export const Showcase: StoryObj = {};
+export const Showcase: StoryObj> = {
+ render(props) {
+ const [value, setValue] = useState();
+ return (
+
+
+
+
+
+ );
+ }
+};
diff --git a/packages/docs/components/toolbox/Ripple.stories.tsx b/packages/docs/components/toolbox/Ripple.stories.tsx
index 9b0ca2491..5ded9a7e2 100644
--- a/packages/docs/components/toolbox/Ripple.stories.tsx
+++ b/packages/docs/components/toolbox/Ripple.stories.tsx
@@ -6,14 +6,24 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...RippleMeta,
- title: "Composants/@focus4âtoolbox/Ripple"
+ title: "Composants/@focus4âtoolbox/Ripple",
+ tags: ["autodocs"]
} as Meta;
export const Showcase: StoryObj = {
render(props) {
return (
- Test
+
+ Test
+
);
}
diff --git a/packages/docs/components/toolbox/Slider.stories.tsx b/packages/docs/components/toolbox/Slider.stories.tsx
index 6e2371f89..aa7faf555 100644
--- a/packages/docs/components/toolbox/Slider.stories.tsx
+++ b/packages/docs/components/toolbox/Slider.stories.tsx
@@ -1,3 +1,5 @@
+import {useState} from "react";
+
import {Slider} from "@focus4/toolbox";
import {SliderMeta} from "./metas/slider";
@@ -6,7 +8,19 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...SliderMeta,
- title: "Composants/@focus4âtoolbox/Slider"
+ title: "Composants/@focus4âtoolbox/Slider",
+ tags: ["autodocs"]
} as Meta;
-export const Showcase: StoryObj = {};
+export const Showcase: StoryObj> = {
+ render(props) {
+ const [selected, setSelected] = useState(23);
+ const [selected2, setSelected2] = useState(45);
+ return (
+
+
+
+
+ );
+ }
+};
diff --git a/packages/docs/components/toolbox/Snackbar.stories.tsx b/packages/docs/components/toolbox/Snackbar.stories.tsx
index 59f680792..7994a6865 100644
--- a/packages/docs/components/toolbox/Snackbar.stories.tsx
+++ b/packages/docs/components/toolbox/Snackbar.stories.tsx
@@ -7,7 +7,15 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...SnackbarMeta,
title: "Composants/@focus4âtoolbox/Snackbar",
- args: {active: true, message: "Salut"}
+ tags: ["autodocs"],
+ args: {
+ active: true,
+ message: "Salut",
+ close: () => {
+ /* */
+ },
+ action: {label: "Action"}
+ }
} as Meta;
export const Showcase: StoryObj = {};
diff --git a/packages/docs/components/toolbox/Switch.stories.tsx b/packages/docs/components/toolbox/Switch.stories.tsx
index a965be0d0..8015330b6 100644
--- a/packages/docs/components/toolbox/Switch.stories.tsx
+++ b/packages/docs/components/toolbox/Switch.stories.tsx
@@ -8,7 +8,8 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...SwitchMeta,
- title: "Composants/@focus4âtoolbox/Switch"
+ title: "Composants/@focus4âtoolbox/Switch",
+ tags: ["autodocs"]
} as Meta;
export const Showcase: StoryObj = {
diff --git a/packages/docs/components/toolbox/Tabs.mdx b/packages/docs/components/toolbox/Tabs.mdx
new file mode 100644
index 000000000..e7e05b8c6
--- /dev/null
+++ b/packages/docs/components/toolbox/Tabs.mdx
@@ -0,0 +1,18 @@
+import {Meta, Description, Title, Controls, Canvas} from "@storybook/blocks";
+
+import TabsStories, {Showcase} from "./Tabs.stories";
+import TabStories, {Showcase as Tab} from "./Tab.stories";
+
+
+
+
+
+
+
+
+
+
+{TabStories.title.split("/")[2]}
+{TabStories.parameters.docs.description.component}
+
+
diff --git a/packages/docs/components/toolbox/Tabs.stories.tsx b/packages/docs/components/toolbox/Tabs.stories.tsx
index ba614fb7b..3f7de0e5f 100644
--- a/packages/docs/components/toolbox/Tabs.stories.tsx
+++ b/packages/docs/components/toolbox/Tabs.stories.tsx
@@ -1,4 +1,6 @@
-import {Tabs} from "@focus4/toolbox";
+import {useState} from "react";
+
+import {Tab, Tabs} from "@focus4/toolbox";
import {TabsMeta} from "./metas/tabs";
@@ -9,4 +11,43 @@ export default {
title: "Composants/@focus4âtoolbox/Tabs"
} as Meta;
-export const Showcase: StoryObj = {};
+export const Showcase: StoryObj = {
+ render(props) {
+ const [tab1, setTab1] = useState(0);
+ const [tab2, setTab2] = useState(0);
+
+ return (
+
+
+
+
+
+
+
+
+
+ Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut
+ labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco
+ laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in
+ voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat
+ cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.
+
+
+
+
+ Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut
+ labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco
+ laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit
+
+
+
+
+ Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut
+ labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco
+
+
+
+
+ );
+ }
+};
diff --git a/packages/docs/components/toolbox/TextField.stories.tsx b/packages/docs/components/toolbox/TextField.stories.tsx
index b84dba686..aab377de2 100644
--- a/packages/docs/components/toolbox/TextField.stories.tsx
+++ b/packages/docs/components/toolbox/TextField.stories.tsx
@@ -6,7 +6,8 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...TextFieldMeta,
- title: "Composants/@focus4âtoolbox/TextField"
+ title: "Composants/@focus4âtoolbox/TextField",
+ tags: ["autodocs"]
} as Meta;
export const Showcase: StoryObj = {
diff --git a/packages/docs/components/toolbox/Tooltip.stories.tsx b/packages/docs/components/toolbox/Tooltip.stories.tsx
index ee5f717bd..b5a76c89a 100644
--- a/packages/docs/components/toolbox/Tooltip.stories.tsx
+++ b/packages/docs/components/toolbox/Tooltip.stories.tsx
@@ -7,15 +7,18 @@ import type {Meta, StoryObj} from "@storybook/react";
export default {
...TooltipMeta,
title: "Composants/@focus4âtoolbox/Tooltip",
+ tags: ["autodocs"],
args: {tooltip: "Tooltip"}
} as Meta;
export const Showcase: StoryObj = {
render(props) {
return (
-
- Test
-
+
);
}
};
diff --git a/packages/forms/src/components/label.tsx b/packages/forms/src/components/label.tsx
index 377bb7a0d..d7602f84d 100644
--- a/packages/forms/src/components/label.tsx
+++ b/packages/forms/src/components/label.tsx
@@ -60,9 +60,11 @@ export function Label({
onClick={onTooltipClick}
/>
) : (
-
- {{i18nKey: `${i18nPrefix}.icons.label.tooltip`}}
-
+
)}
) : null}
diff --git a/packages/layout/src/menu/item.tsx b/packages/layout/src/menu/item.tsx
index 1fa570f26..35d20ae60 100644
--- a/packages/layout/src/menu/item.tsx
+++ b/packages/layout/src/menu/item.tsx
@@ -115,7 +115,7 @@ export function MainMenuItem({
{createElement(
element,
props,
- icon ? {icon} : null,
+ icon ? : null,
label ? {label}
: null
)}
diff --git a/packages/toolbox/src/components/autocomplete.tsx b/packages/toolbox/src/components/autocomplete.tsx
index 10f12b12f..1242769ca 100644
--- a/packages/toolbox/src/components/autocomplete.tsx
+++ b/packages/toolbox/src/components/autocomplete.tsx
@@ -78,7 +78,12 @@ const defaultGetKey = (x: any) => x.key;
const defaultGetLabel = (x: any) => x.label;
/**
- * Champ de saisie en autocomplétion à partir d'une **liste de valeurs possibles en entrée**.
+ * Un Autocomplete combine un champ texte en autocomplétion avec un menu déroulant, pour effectuer une sélection parmi une **liste de valeurs disponibles en entrée**.
+ *
+ * - Le filtrage des valeurs s'effecue dans le composant selon plusieurs modes de correspondance.
+ * - Toutes les options du champ texte sont disponibles.
+ * - Peut ĂȘtre utilisĂ© comme un champ de recherche rapide.
+ * - Peut afficher des suggestions complémentaires.
*/
export const Autocomplete = forwardRef(function Autocomplete(
{
diff --git a/packages/toolbox/src/components/button.tsx b/packages/toolbox/src/components/button.tsx
index 5bae9acc2..7968ae331 100644
--- a/packages/toolbox/src/components/button.tsx
+++ b/packages/toolbox/src/components/button.tsx
@@ -126,7 +126,7 @@ export function Button({
{createElement(
element,
props,
- icon ? {icon} : null,
+ icon ? : null,
{label ?? "\xa0"}
)}
diff --git a/packages/toolbox/src/components/chip.tsx b/packages/toolbox/src/components/chip.tsx
index d76b96fa9..9e00130f1 100644
--- a/packages/toolbox/src/components/chip.tsx
+++ b/packages/toolbox/src/components/chip.tsx
@@ -117,7 +117,7 @@ export function Chip({
{createElement(
element,
props,
- icon ? {icon} : null,
+ icon ? : null,
onDeleteClick ? (
{icon} : null,
+ icon ? : null,
{
alt?: string;
/** Classe CSS Ă poser sur le composant racine. */
className?: string;
- /** IcĂŽne Ă afficher. */
- children: Icon;
- /** Styles inline */
+ /**
+ * Nom de l'icÎne à afficher. Ne sera pas posé en enfant du si la classe CSS de l'icÎne est un template de `{name}`.
+ *
+ * Ignoré si `iconI18nKey` est renseigné.
+ */
+ children?: string;
+ /**
+ * DĂ©finition d'icĂŽne mixte, peut ĂȘtre utilisĂ© Ă la place de `children` / `iconClassName` / `iconI18nKey`.
+ *
+ * N'a pas la priorité sur ces définitions-là .
+ */
+ icon?: Icon;
+ /**
+ * Classe CSS de l'icĂŽne, pour retrouver la police associĂ©e. Peut ĂȘtre utilisĂ©e comme template du nom de l'icĂŽne (en y remplaçant `{name}`).
+ *
+ * Ignoré si `iconI18nKey` est renseigné.
+ */
+ iconClassName?: string;
+ /**
+ * Clé i18n pour retrouver l'icÎne. Doit correspondre à un objet `{name, className?}`.
+ *
+ * Remplace `children` et `iconClassName`.
+ */
+ iconI18nKey?: string;
+ /** Styles inline. */
style?: CSSProperties;
}
/**
- * Affiche une icĂŽne. Prend une `Icon` comme enfant.
+ * Affiche une icÎne. Une icÎne est définie par son nom et sa classe CSS, qui servira à retrouver la police d'icÎne associée.
+ *
+ * Une icÎne définie avec seulement un nom utilisera la classe CSS définie dans `config.defaultIconClassName` (par défaut : `"material-icons"`).
+ *
+ * La classe CSS sera interprétée comme un template du nom si elle contient `{name}` dans sa définition.
+ * Dans ce cas, le `name` ne sera pas posé en enfant du `` qui définira l'icÎne.
+ *
+ * Une icĂŽne peut Ă©galement ĂȘtre dĂ©finie via une clĂ© i18n, qui devra pointer vers un objet `{name, className?}` reprĂ©sentant l'icĂŽne.
*/
export function FontIcon({
+ icon,
alt = "",
className = "",
- children,
+ children = typeof icon === "string" ? icon : typeof icon === "object" && "name" in icon ? icon.name : undefined,
+ iconClassName = typeof icon === "object" && "className" in icon ? icon.className : config.defaultIconClassName,
+ iconI18nKey = typeof icon === "object" && "i18nKey" in icon ? icon.i18nKey : undefined,
onPointerDown,
onPointerEnter,
onPointerLeave,
onPointerUp,
style
}: FontIconProps) {
- let inputClassName = config.defaultIconClassName;
- let inputName;
-
- if (typeof children === "string") {
- inputName = children;
- } else if ("name" in children) {
- inputName = children.name;
- if (children.className) {
- inputClassName = children.className;
+ if (iconI18nKey) {
+ const nameKey = `${iconI18nKey}.name`;
+ const i18nName = i18next.t(nameKey);
+ if (i18nName !== nameKey) {
+ children = i18nName;
}
- } else {
- inputName = i18next.t(`${children.i18nKey}.name`);
- const classNameKey = `${children.i18nKey}.className`;
+ const classNameKey = `${iconI18nKey}.className`;
const i18nClassName = i18next.t(classNameKey);
if (i18nClassName !== classNameKey) {
- inputClassName = i18nClassName;
+ iconClassName = i18nClassName;
}
}
let baseClassName;
let name;
- if (inputClassName.includes("{name}")) {
- baseClassName = inputClassName.replaceAll("{name}", inputName);
+ if (iconClassName.includes("{name}")) {
+ baseClassName = iconClassName.replaceAll("{name}", children ?? "");
} else {
- baseClassName = inputClassName;
- name = inputName;
+ baseClassName = iconClassName;
+ name = children;
}
return (
diff --git a/packages/toolbox/src/components/icon-button.tsx b/packages/toolbox/src/components/icon-button.tsx
index cf3b1fcb3..c71d603a6 100644
--- a/packages/toolbox/src/components/icon-button.tsx
+++ b/packages/toolbox/src/components/icon-button.tsx
@@ -117,7 +117,7 @@ export function IconButton({
onPointerLeave={handlePointerLeave}
onPointerUp={handlePointerUp}
>
- {createElement(element, props, {icon} )}
+ {createElement(element, props, )}
);
}
diff --git a/packages/toolbox/src/components/menu.tsx b/packages/toolbox/src/components/menu.tsx
index 58c2123bb..f3306515f 100644
--- a/packages/toolbox/src/components/menu.tsx
+++ b/packages/toolbox/src/components/menu.tsx
@@ -134,7 +134,7 @@ export interface MenuItemProps extends PointerEvents {
}
/**
- * Item de Menu a utiliser dans un `Menu`.
+ * Composant générique à inclure dans un `Menu`, comprenant un libellé et d'éventuelles icÎnes à l'avant et l'arriÚre.
*/
export function MenuItem({
caption,
@@ -157,9 +157,9 @@ export function MenuItem({
onPointerUp={onPointerUp}
>
- {iconLeft ? {iconLeft} : null}
+ {iconLeft ? : null}
{caption}
- {iconRight ? {iconRight} : null}
+ {iconRight ? : null}
);
@@ -179,7 +179,13 @@ export function useMenu(): MenuControls<
}
/**
- * Menu déroulant. Peut s'attacher à un élément parent. A utiliser avec `useMenu()`.
+ * Un menu permet d'afficher une zone temporaire pour afficher une liste de valeurs qu'un utilisateur peut sélectionner.
+ * Il doit s'attacher à un élément parent comme un `Button` ou un `TextField`.
+ *
+ * Le hook `useMenu()` permet de créer les éléments nécessaires pour l'attacher et contrÎler son affichage.
+ *
+ * L'élément générique d'un menu est le `MenuItem`, mais il est possible d'y mettre toute sorte de composant à l'intérieur.
+ * L'`Autocomplete`, le `Dropdown` ou encore l'`InputDate` utilisent un `Menu` pour afficher leurs listes de sélection/le calendrier.
*/
export function Menu({
active,
diff --git a/packages/toolbox/src/components/radio.tsx b/packages/toolbox/src/components/radio.tsx
index 06d1c55d7..d8cdb6bc1 100644
--- a/packages/toolbox/src/components/radio.tsx
+++ b/packages/toolbox/src/components/radio.tsx
@@ -40,7 +40,9 @@ export interface RadioButtonProps extends PointerEvents {
}
/**
- * A utiliser dans un RadioGroup.
+ * Un bouton radio permet aux utilisateurs de choisir une option parmi un ensemble de valeurs.
+ *
+ * Un ensemble de `RadioButton` doit ĂȘtre contenu dans un `RadioGroup`.
*/
export function RadioButton({
className = "",
@@ -121,7 +123,10 @@ export interface RadioGroupProps {
}
/**
- * A utiliser avec RadioButton pour faire des radios. Les composants [`BooleanRadio`](components/forms.md#booleanradio) et [`SelectRadio`](components/forms.md#selectradio) en sont des implémentations pour les usages les plus courants.
+ * Conteneur pour un ensemble de `RadioButton`, permettant de former un champ de saisie unique.
+ *
+ * Les composants `BooleanRadio` et `SelectRadio` sont des implémentations de plus haut niveau qui couvrent la plupart des cas d'utilisation
+ * et sont à privilégier par rapport à l'usage direct d'un `RadioGroup` et de `RadioButton`.
*/
export function RadioGroup({className = "", children, disabled = false, onChange, value}: RadioGroupProps) {
const ctx = useMemo(() => ({disabled, onChange, value}), [disabled, onChange, value]);
diff --git a/packages/toolbox/src/components/ripple.tsx b/packages/toolbox/src/components/ripple.tsx
index 5ac194d6d..5dc572cc6 100644
--- a/packages/toolbox/src/components/ripple.tsx
+++ b/packages/toolbox/src/components/ripple.tsx
@@ -22,7 +22,9 @@ export interface RippleProps extends Pointe
}
/**
- * Pose un Ripple au clic sur le composant/élément enfant.
+ * Le `Ripple` est un composant à poser autour d'un autre élément pour y ajouter un effet "ripple" lors du clic.
+ *
+ * Tous les composants qui attendent un clic d'un utilisateur dans leur action principale en sont munis.
*/
export function Ripple({
centered,
diff --git a/packages/toolbox/src/components/slider.tsx b/packages/toolbox/src/components/slider.tsx
index 9d5daae97..75a7e669d 100644
--- a/packages/toolbox/src/components/slider.tsx
+++ b/packages/toolbox/src/components/slider.tsx
@@ -34,7 +34,13 @@ export interface SliderProps extends PointerEvents {
value: number;
}
-/** Slider. */
+/**
+ * Un slider permet à un utilisateur de choisir une valeur numérique dans un intervalle donné.
+ *
+ * - Le pas du slider peut ĂȘtre configurĂ©.
+ * - Peut indiquer la valeur précise lors l'interaction.
+ * - Peut afficher un indicateur Ă chaque pas sur le slider.
+ */
export function Slider({
className,
disabled = false,
diff --git a/packages/toolbox/src/components/snackbar.tsx b/packages/toolbox/src/components/snackbar.tsx
index 416fab2f4..6149441be 100644
--- a/packages/toolbox/src/components/snackbar.tsx
+++ b/packages/toolbox/src/components/snackbar.tsx
@@ -31,7 +31,12 @@ export interface SnackbarProps {
}
/**
- * Le composant pour afficher des toasts utilisé par le [`MessageCenter`](basics/messages.md).
+ * Une snackbar affiche un message court Ă un utilisateur en bas de l'Ă©cran pour le notifier du status d'une action dans l'application.
+ *
+ * Elle est posée par défaut par le `MessageCenter` du `Layout`.
+ *
+ * - 4 types de messages : succĂšs, erreur, avertissement ou information
+ * - Peut inclure une action.
*/
export function Snackbar({active, action, className, close, level, message, onClose, theme: pTheme}: SnackbarProps) {
const theme = useTheme("snackbar", snackbarCss, pTheme);
diff --git a/packages/toolbox/src/components/switch.tsx b/packages/toolbox/src/components/switch.tsx
index 7e9198a4d..359838002 100644
--- a/packages/toolbox/src/components/switch.tsx
+++ b/packages/toolbox/src/components/switch.tsx
@@ -99,8 +99,8 @@ export function Switch({
{value !== undefined ? (
<>
- {iconOn ? {iconOn} : null}
- {iconOff ? {iconOff} : null}
+ {iconOn ? : null}
+ {iconOff ? : null}
>
) : null}
diff --git a/packages/toolbox/src/components/tabs.tsx b/packages/toolbox/src/components/tabs.tsx
index 7b0e4c349..afaf5ae24 100644
--- a/packages/toolbox/src/components/tabs.tsx
+++ b/packages/toolbox/src/components/tabs.tsx
@@ -50,7 +50,9 @@ export interface TabsProps {
}
/**
- * Un Tab, Ă utiliser dans Tabs.
+ * DĂ©finit un tab Ă inclure dans une instance de `Tabs`.
+ *
+ * Peut inclure le contenu du tab en enfant ou peut ĂȘtre simplement utilisĂ© pour le titre.
*/
export function Tab({
active = false,
@@ -96,14 +98,19 @@ export function Tab({
role="tab"
tabIndex={disabled ? undefined : 0}
>
- {icon ? {icon} : null}
+ {icon ? : null}
{label ? {label} : null}
);
}
-/** Permet de poser un systĂšme de tabs avec Tab. */
+/**
+ * Les tabs permettent d'organiser du contenu à travers différents écrans ou vues.
+ *
+ * - 2 types : primaires et secondaires
+ * - Les tabs peuvent inclure le contenu ou simplement servir de barre de titres. Le changement de tab animera le contenu s'il est inclus.
+ */
export function Tabs({children, className = "", index = 0, onChange, secondary, theme: pTheme}: TabsProps) {
const theme = useTheme("tabs", tabsCss, pTheme);
const navigationNode = useRef(null);
diff --git a/packages/toolbox/src/components/text-field.tsx b/packages/toolbox/src/components/text-field.tsx
index 11a1022c8..322d507e1 100644
--- a/packages/toolbox/src/components/text-field.tsx
+++ b/packages/toolbox/src/components/text-field.tsx
@@ -132,6 +132,10 @@ export interface TextFieldProps extends PointerEvents
{icon ? (
- {icon}
+
) : null}
{label ? (
@@ -376,7 +380,7 @@ export const TextField = forwardRef(function TextField(
/>
) : (
- {t.icon}
+
);
if (t.tooltip) {
diff --git a/packages/toolbox/src/components/tooltip.tsx b/packages/toolbox/src/components/tooltip.tsx
index 1b6feb182..6f70c3a0c 100644
--- a/packages/toolbox/src/components/tooltip.tsx
+++ b/packages/toolbox/src/components/tooltip.tsx
@@ -22,7 +22,7 @@ export interface TooltipProps extends Point
}
/**
- * Pose une tooltip autour de l'Ă©lement enfant qui s'activera au survol.
+ * Une tooltip permet d'afficher un bref libellé ou message à un utilisateur au survol.
*/
export function Tooltip({
children,