diff --git a/.storybook/main.ts b/.storybook/main.ts index 233c8d4d..28f0f002 100644 --- a/.storybook/main.ts +++ b/.storybook/main.ts @@ -6,9 +6,18 @@ const config: StorybookConfig = { stories: [ "../stories/Getting-started.mdx", "../stories/**/*.mdx", - "../packages/{tailwind-formio,react-formio}/src/**/*.mdx", - "../packages/{tailwind-formio,react-formio}/src/**/*.stories.@(js|jsx|ts|tsx)", - "../packages/{tailwind-formio,react-formio}/src/**/*.story.@(js|jsx|ts|tsx)" + { + titlePrefix: "Styling", + directory: "../packages/tailwind-formio" + }, + { + titlePrefix: "Molecules", + directory: "../packages/react-formio/src/molecules" + }, + { + titlePrefix: "Organisms", + directory: "../packages/react-formio/src/organisms" + } ], addons: [ @@ -18,7 +27,6 @@ const config: StorybookConfig = { "@storybook/addon-essentials", "@storybook/addon-mdx-gfm", "@storybook/addon-links", - "@storybook/addon-interactions", "@chromatic-com/storybook", "storybook-addon-mock" ], diff --git a/packages/react-formio-container/src/views/form.routes.tsx b/packages/react-formio-container/src/views/form.routes.tsx index 79fc6b01..8cbd5218 100644 --- a/packages/react-formio-container/src/views/form.routes.tsx +++ b/packages/react-formio-container/src/views/form.routes.tsx @@ -1,4 +1,4 @@ -import type { TabsItemProps } from "@tsed/react-formio"; +import type { TabsItemProps } from "@tsed/react-formio/molecules/tabs/Tabs"; import { AuthState, checkRoleFormAccess, FormType } from "@tsed/react-formio-stores"; import { ComponentType } from "react"; diff --git a/packages/react-formio-container/src/views/form.view.tsx b/packages/react-formio-container/src/views/form.view.tsx index cf3acd1d..6a0cc988 100644 --- a/packages/react-formio-container/src/views/form.view.tsx +++ b/packages/react-formio-container/src/views/form.view.tsx @@ -1,4 +1,7 @@ -import { Alert, Loader, RemoveModal, Tabs } from "@tsed/react-formio"; +import { Alert } from "@tsed/react-formio/molecules/alert/Alert"; +import { Loader } from "@tsed/react-formio/molecules/loader/Loader"; +import { Tabs } from "@tsed/react-formio/molecules/tabs/Tabs"; +import { RemoveModal } from "@tsed/react-formio/organisms/modal/RemoveModal"; import { Route, Switch, useParams } from "react-router"; import { useForm } from "../hooks/useForm.hook"; @@ -13,7 +16,7 @@ function FormComponent({ className, ...props }: ReturnType) { return (
- +
diff --git a/packages/react-formio-container/src/views/formAccess.view.tsx b/packages/react-formio-container/src/views/formAccess.view.tsx index 9631469f..9cf1319e 100644 --- a/packages/react-formio-container/src/views/formAccess.view.tsx +++ b/packages/react-formio-container/src/views/formAccess.view.tsx @@ -1,4 +1,4 @@ -import { FormAccess } from "@tsed/react-formio"; +import { FormAccess } from "@tsed/react-formio/organisms/form/access/FormAccess"; import { useForm } from "../hooks/useForm.hook"; diff --git a/packages/react-formio-container/src/views/formAction.view.tsx b/packages/react-formio-container/src/views/formAction.view.tsx index 68708b7d..d2f5d1c1 100644 --- a/packages/react-formio-container/src/views/formAction.view.tsx +++ b/packages/react-formio-container/src/views/formAction.view.tsx @@ -1,4 +1,7 @@ -import { FormAction, iconClass, RemoveModal, useTooltip } from "@tsed/react-formio"; +import { useTooltip } from "@tsed/react-formio/hooks/useTooltip"; +import { FormAction } from "@tsed/react-formio/organisms/form/action/FormAction"; +import { RemoveModal } from "@tsed/react-formio/organisms/modal/RemoveModal"; +import { iconClass } from "@tsed/react-formio/utils/iconClass"; import classnames from "classnames"; import { useParams } from "react-router"; diff --git a/packages/react-formio-container/src/views/formActions.view.tsx b/packages/react-formio-container/src/views/formActions.view.tsx index 06a4d294..07f710be 100644 --- a/packages/react-formio-container/src/views/formActions.view.tsx +++ b/packages/react-formio-container/src/views/formActions.view.tsx @@ -1,4 +1,4 @@ -import { ActionsTable } from "@tsed/react-formio"; +import { ActionsTable } from "@tsed/react-formio/organisms/table/actions/ActionsTable"; import { Route, Switch } from "react-router"; import { useActions, UseActionsProps } from "../hooks/useActions.hook"; diff --git a/packages/react-formio-container/src/views/formEdit.view.tsx b/packages/react-formio-container/src/views/formEdit.view.tsx index c4bba2f0..12a581f8 100644 --- a/packages/react-formio-container/src/views/formEdit.view.tsx +++ b/packages/react-formio-container/src/views/formEdit.view.tsx @@ -1,4 +1,4 @@ -import { FormEdit } from "@tsed/react-formio"; +import { FormEdit } from "@tsed/react-formio/organisms/form/builder/FormEdit"; import classnames from "classnames"; import { useForm } from "../hooks/useForm.hook"; diff --git a/packages/react-formio-container/src/views/formExport.view.tsx b/packages/react-formio-container/src/views/formExport.view.tsx index e41644e7..963a4ffd 100644 --- a/packages/react-formio-container/src/views/formExport.view.tsx +++ b/packages/react-formio-container/src/views/formExport.view.tsx @@ -1,4 +1,5 @@ -import { Card, iconClass } from "@tsed/react-formio"; +import { Card } from "@tsed/react-formio/molecules/card/Card"; +import { iconClass } from "@tsed/react-formio/utils/iconClass"; import { UseFormProps } from "../hooks/useForm.hook"; import { useFormExport } from "../hooks/useFormExport"; diff --git a/packages/react-formio-container/src/views/formPreview.view.tsx b/packages/react-formio-container/src/views/formPreview.view.tsx index be4f0dde..f0d93c6a 100644 --- a/packages/react-formio-container/src/views/formPreview.view.tsx +++ b/packages/react-formio-container/src/views/formPreview.view.tsx @@ -1,4 +1,6 @@ -import { Card, Form } from "@tsed/react-formio"; +import type { FormType } from "@tsed/react-formio"; +import { Card } from "@tsed/react-formio/molecules/card/Card"; +import { Form } from "@tsed/react-formio/organisms/form/Form"; import { useForm } from "../hooks"; @@ -6,7 +8,7 @@ export function FormPreviewView({ form, i18n }: ReturnType) { return (
-
+
); diff --git a/packages/react-formio-container/src/views/formSettings.view.tsx b/packages/react-formio-container/src/views/formSettings.view.tsx index b22ca86a..4cff583c 100644 --- a/packages/react-formio-container/src/views/formSettings.view.tsx +++ b/packages/react-formio-container/src/views/formSettings.view.tsx @@ -1,4 +1,4 @@ -import { FormSettings } from "@tsed/react-formio"; +import { FormSettings } from "@tsed/react-formio/organisms/form/settings/FormSettings"; import { useForm } from "../hooks/useForm.hook"; diff --git a/packages/react-formio-container/src/views/forms.view.tsx b/packages/react-formio-container/src/views/forms.view.tsx index e5b281d0..7fc4085c 100644 --- a/packages/react-formio-container/src/views/forms.view.tsx +++ b/packages/react-formio-container/src/views/forms.view.tsx @@ -1,4 +1,5 @@ -import { Alert, FormsTable } from "@tsed/react-formio"; +import { Alert } from "@tsed/react-formio/molecules/alert/Alert"; +import { FormsTable } from "@tsed/react-formio/organisms/table/forms/FormsTable"; import { useForms, UseFormsProps } from "../hooks/useForms.hook"; @@ -39,7 +40,7 @@ export function FormsComponent({ return (
- + ) {
- + {submissionAction === "delete" && ( { - return ; -}; - -Sandbox.args = { - error: "error placeholder" -}; diff --git a/packages/react-formio/src/components/form-control/formControl.stories.tsx b/packages/react-formio/src/components/form-control/formControl.stories.tsx deleted file mode 100644 index 31dda9a0..00000000 --- a/packages/react-formio/src/components/form-control/formControl.stories.tsx +++ /dev/null @@ -1,63 +0,0 @@ -import { iconClass } from "../../utils/iconClass"; -import { FormControl } from "./formControl.component"; - -export default { - title: "@tsed/react-formio/FormControl", - component: FormControl, - argTypes: { - label: { - control: { - type: "text" - } - }, - name: { - control: { - type: "text" - } - }, - children: { - control: { - type: HTMLElement || HTMLCollection - } - } - }, - parameters: {} -}; - -export const Sandbox = (args: any) => { - return ; -}; - -Sandbox.args = { - label: "Label", - children: -}; - -export const WithPrefix = (args: any) => { - return ; -}; - -WithPrefix.args = { - label: "Label", - children: , - prefix: -}; - -export const WithSuffix = (args: any) => { - return ; -}; - -WithSuffix.args = { - label: "Label", - children: , - suffix: -}; - -export const WithDescription = (args: any) => { - return ; -}; - -WithDescription.args = { - label: "Label", - children: -}; diff --git a/packages/react-formio/src/components/index.ts b/packages/react-formio/src/components/index.ts deleted file mode 100644 index f0e82ae9..00000000 --- a/packages/react-formio/src/components/index.ts +++ /dev/null @@ -1,25 +0,0 @@ -export * from "./actions-table/actionsTable.component"; -export * from "./alert/alert.component"; -export * from "./card/card.component"; -export * from "./form/form.component"; -export * from "./form/useForm.hook"; -export * from "./form-access/formAccess.component"; -export * from "./form-action/formAction.component"; -export * from "./form-builder/formBuilder.component"; -export * from "./form-control/formControl.component"; -export * from "./form-edit/formCtas.component"; -export * from "./form-edit/formEdit.component"; -export * from "./form-edit/formParameters.component"; -export * from "./form-edit/useFormEdit.hook"; -export * from "./form-settings/formSettings.component"; -export * from "./forms-table/formsTable.component"; -export * from "./input-tags/inputTags.component"; -export * from "./input-text/inputText.component"; -export * from "./loader/loader.component"; -export * from "./modal/modal.component"; -export * from "./modal/removeModal.component"; -export * from "./pagination/pagination.component"; -export * from "./select/select.component"; -export * from "./submissions-table/submissionsTable.component"; -export * from "./table"; -export * from "./tabs/tabs.component"; diff --git a/packages/react-formio/src/components/input-tags/inputTags.stories.tsx b/packages/react-formio/src/components/input-tags/inputTags.stories.tsx deleted file mode 100644 index ef0b7f18..00000000 --- a/packages/react-formio/src/components/input-tags/inputTags.stories.tsx +++ /dev/null @@ -1,97 +0,0 @@ -import { useState } from "react"; - -import { iconClass } from "../../utils/iconClass"; -import { InputTags } from "./inputTags.component"; - -const useValue = (args: any) => { - const [value, setValue] = useState(args.value); - - return { - ...args, - value, - onChange(name: string, value: any) { - setValue(value); - args.onChange(name, value); - } - }; -}; - -export default { - title: "@tsed/react-formio/InputTags", - component: InputTags, - argTypes: { - label: { - control: { - type: "text" - } - }, - name: { - control: { - type: "text" - } - }, - value: { - control: { - type: "object" - } - }, - size: { - control: { - type: "select", - options: ["sm", "normal"] - } - }, - placeholder: { - control: { - type: "text" - } - }, - choices: { - control: { - type: "object" - } - }, - description: { - control: { - type: "text" - } - } - }, - parameters: {} -}; - -export const Sandbox = (args: any) => { - return ; -}; - -Sandbox.args = { - name: "name", - label: "Label", - value: ["test"], - size: "", - placeholder: "Placeholder" -}; - -export const WithPrefix = (args: any) => { - return } {...useValue(args)} />; -}; - -WithPrefix.args = { - label: "Label", - value: [], - name: "name", - size: "", - placeholder: "Placeholder" -}; - -export const WithSuffix = (args: any) => { - return } {...useValue(args)} />; -}; - -WithSuffix.args = { - label: "Label", - value: [], - name: "name", - size: "", - placeholder: "Placeholder" -}; diff --git a/packages/react-formio/src/components/loader/loader.stories.tsx b/packages/react-formio/src/components/loader/loader.stories.tsx deleted file mode 100644 index 29768d82..00000000 --- a/packages/react-formio/src/components/loader/loader.stories.tsx +++ /dev/null @@ -1,16 +0,0 @@ -import { Loader } from "./loader.component"; - -export default { - title: "@tsed/react-formio/Loader", - component: Loader, - argTypes: {}, - parameters: {} -}; - -export const Sandbox = (args: any) => { - return ; -}; - -Sandbox.args = { - isActive: true -}; diff --git a/packages/react-formio/src/components/modal/modal.stories.tsx b/packages/react-formio/src/components/modal/modal.stories.tsx deleted file mode 100644 index 3eb42df8..00000000 --- a/packages/react-formio/src/components/modal/modal.stories.tsx +++ /dev/null @@ -1,190 +0,0 @@ -import { Modal, ModalProps, useModal } from "./modal.component"; -import { RemoveModal, RemoveModalProps } from "./removeModal.component"; - -export default { - title: "@tsed/react-formio/Modal", - component: Modal, - argTypes: { - onSubmit: { - title: { - control: { - type: "text" - } - }, - control: { - action: "onSubmit" - } - } - }, - parameters: {} -}; - -export const Sandbox = (args: ModalProps) => { - const modal = useModal(); - - return ( -
-
- -
- -
- Hello body -
-
-
- ); -}; - -Sandbox.args = {}; - -export const WithTitle = (args: ModalProps) => { - const modal = useModal(); - - return ( -
-
- -
- -
- Hello body -
-
-
- ); -}; - -WithTitle.args = { - title: "Modal title" -}; - -export const WithFooter = (args: ModalProps) => { - const modal = useModal(); - - function ModalFooter({ closeModal, onSubmit }: any) { - return ( -
- - - -
- ); - } - - return ( -
-
- -
- -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
- Hello body -
-
-
-
- ); -}; - -WithFooter.args = { - title: "Modal title" -}; - -export const WithRemoveModal = (args: RemoveModalProps) => { - const modal = useModal(); - - return ( -
-
- -
- f} - show={modal.show} - onSubmit={modal.closeModal} - onClose={modal.closeModal} - closeModal={modal.closeModal} - /> -
- ); -}; - -WithRemoveModal.args = { - valueToCompare: "value", - itemType: "form" -}; diff --git a/packages/react-formio/src/components/pagination/pagination.stories.tsx b/packages/react-formio/src/components/pagination/pagination.stories.tsx deleted file mode 100644 index a042d69b..00000000 --- a/packages/react-formio/src/components/pagination/pagination.stories.tsx +++ /dev/null @@ -1,40 +0,0 @@ -import { useEffect, useState } from "react"; - -import { Pagination } from "./pagination.component"; - -export default { - title: "@tsed/react-formio/Pagination", - component: Pagination, - - parameters: {} -}; - -export const Sandbox = (args: any) => { - const [currentPageIndex, setPageIndex] = useState(args.pageIndex); - - useEffect(() => { - args.gotoPage && args.gotoPage(currentPageIndex); - }, [currentPageIndex]); - - return ( -
- -
- ); -}; - -Sandbox.args = { - pageSizes: [10, 25, 50, 100], - pageCount: 50, - pageIndex: 1 - // gotoPage, - // canPreviousPage, - // previousPage, - // nextPage, - // canNextPage, - // pageCount, - // pageIndex, - // pageOptions, - // pageSize, - // setPageSize, -}; diff --git a/packages/react-formio/src/components/select/select.stories.tsx b/packages/react-formio/src/components/select/select.stories.tsx deleted file mode 100644 index 6488e8f7..00000000 --- a/packages/react-formio/src/components/select/select.stories.tsx +++ /dev/null @@ -1,173 +0,0 @@ -import { useState } from "react"; - -import { iconClass } from "../../utils/iconClass"; -import { Select } from "./select.component"; - -const choices = [ - { label: "label1", value: "value1" }, - { label: "label2", value: "value2" } -]; - -const useValue = (args: any) => { - const [value, setValue] = useState(args.value); - - return { - ...args, - value, - onChange(name: string, value: any) { - setValue(value); - args.onChange(name, value); - } - }; -}; - -export default { - title: "@tsed/react-formio/Select", - component: Select, - argTypes: { - label: { - control: { - type: "text" - } - }, - name: { - control: { - type: "text" - } - }, - value: { - control: { - type: "select", - options: choices - } - }, - size: { - control: { - type: "select", - options: ["sm", "normal"] - } - }, - layout: { - control: { - type: "select", - options: ["html5", "choicesjs"] - } - }, - placeholder: { - control: { - type: "text" - } - }, - choices: { - control: { - type: "object" - } - } - }, - parameters: {} -}; - -export const Sandbox = (args: any) => { - return ; -}; - -Choicesjs.args = { - label: "Label", - value: "", - size: "", - layout: "choicesjs", - placeholder: "Placeholder", - choices -}; - -export const ChoicesjsPrefix = (args: any) => { - return } {...useValue(args)} />; -}; - -WithPrefix.args = { - label: "Label", - value: "", - size: "", - placeholder: "Placeholder", - choices -}; - -export const WithSuffix = (args: any) => { - return ; -}; - -TypeMultiple.args = { - label: "Label", - name: "name", - value: [], - size: "", - multiple: true, - placeholder: "Placeholder", - description: "Select multiple values", - choices -}; - -export const ChoicesjsMultiple = (args: any) => { - return } {...useValue(args)} />; -}; - -Sizing.args = { - label: "Label", - value: "", - size: "sm", - placeholder: "Placeholder", - description: "Use dollars!", - choices -}; diff --git a/packages/react-formio/src/components/table/index.ts b/packages/react-formio/src/components/table/index.ts deleted file mode 100644 index 07ac65e8..00000000 --- a/packages/react-formio/src/components/table/index.ts +++ /dev/null @@ -1,15 +0,0 @@ -export * from "./components/defaultArrowSort.component"; -export * from "./components/defaultCell.component"; -export * from "./components/defaultCellHeader.component"; -export * from "./components/defaultCellHeader.component"; -export * from "./components/defaultCellOperations.component"; -export * from "./components/defaultOperationButton.component"; -export * from "./filters/defaultColumnFilter.component"; -export * from "./filters/selectColumnFilter.component"; -export * from "./filters/sliderColumnFilter.component"; -export * from "./hooks/useCustomTable.hook"; -export * from "./hooks/useOperations.hook"; -export * from "./table.component"; -export * from "./utils/getPageNumbers"; -export * from "./utils/mapFormToColumns"; -export * from "./utils/swapElements"; diff --git a/packages/react-formio/src/components/tabs/tabs.component.stories.tsx b/packages/react-formio/src/components/tabs/tabs.component.stories.tsx deleted file mode 100644 index d8d24e39..00000000 --- a/packages/react-formio/src/components/tabs/tabs.component.stories.tsx +++ /dev/null @@ -1,127 +0,0 @@ -import { useState } from "react"; - -import { Tabs } from "./tabs.component"; - -const useTabs = (args: any) => { - const [current, onClick] = useState(args.value); - - return { - ...args, - current, - onClick - }; -}; - -export default { - title: "@tsed/react-formio/Tabs", - component: Tabs, - argTypes: {}, - parameters: {} -}; - -export const Sandbox = (args: any) => { - const tabs = useTabs(args); - - return ( -
- f}> -
{tabs?.current?.action}
-
-
- ); -}; - -Sandbox.args = { - items: [ - { - action: "back", - exact: true, - icon: "chevron-left", - back: true - }, - { - action: "edit", - exact: true, - icon: "edit", - label: "Edit" - }, - { - action: "submissions", - exact: false, - icon: "data", - label: "Data" - }, - { - action: "preview", - exact: true, - icon: "test-tube", - label: "Preview" - }, - { - action: "actions", - exact: false, - icon: "paper-plane", - label: "Actions" - }, - { - action: "access", - exact: true, - icon: "lock", - label: "Access" - }, - { - action: "export", - exact: true, - icon: "download", - label: "Export" - }, - { - action: "delete", - exact: true, - icon: "trash", - label: "Delete", - roles: ["administrator", "owner"] - } - ] -}; - -function AddButton({ onCreate }: any) { - return ( -
- -
- ); -} - -function HeaderChildren() { - return
test
; -} - -export const WithCloseable = (args: any) => { - args.value = args.value === undefined ? 0 : args.value; - const tabs = useTabs(args); - - return ( -
- f} AddButton={AddButton} HeaderChildren={HeaderChildren}> -
{tabs?.current?.action}
-
-
- ); -}; - -WithCloseable.args = { - reverse: true, - items: [ - { - exact: true, - action: 0, - label: "Test (0)" - }, - { - exact: true, - action: 1, - label: "Test (1)" - } - ] -}; diff --git a/packages/react-formio/src/index.ts b/packages/react-formio/src/index.ts index 5e599435..3741b252 100644 --- a/packages/react-formio/src/index.ts +++ b/packages/react-formio/src/index.ts @@ -2,6 +2,7 @@ import Webform from "formiojs/Webform"; import WebformBuilder from "formiojs/WebformBuilder"; import Wizard from "formiojs/Wizard"; import WizardBuilder from "formiojs/WizardBuilder"; + export { Webform, WebformBuilder, @@ -10,10 +11,5 @@ export { // editFormUtils, }; -export * from "./components"; -export * from "./hooks/useTooltip"; export * from "./interfaces"; -export * from "./utils/iconClass"; -export * from "./utils/mapPagination"; -export * from "./utils/stopPropagationWrapper"; export { Components, Formio, Templates, Utils } from "formiojs"; diff --git a/packages/react-formio/src/interfaces/Operation.ts b/packages/react-formio/src/interfaces/Operation.ts index cca02eb2..b3fc2223 100644 --- a/packages/react-formio/src/interfaces/Operation.ts +++ b/packages/react-formio/src/interfaces/Operation.ts @@ -1,6 +1,6 @@ import React from "react"; -import { OperationButtonProps } from "../components/table/components/defaultOperationButton.component"; +import type { OperationButtonProps } from "../molecules/table"; export type PermissionsResolver = (data: Data, ctx: any) => void; export type OnClickOperation = (data: Data, operation: Operation) => void; diff --git a/packages/react-formio/src/components/__fixtures__/form-actions.json b/packages/react-formio/src/molecules/__fixtures__/form-actions.json similarity index 100% rename from packages/react-formio/src/components/__fixtures__/form-actions.json rename to packages/react-formio/src/molecules/__fixtures__/form-actions.json diff --git a/packages/react-formio/src/components/__fixtures__/form-firstname.fixture.json b/packages/react-formio/src/molecules/__fixtures__/form-firstname.fixture.json similarity index 100% rename from packages/react-formio/src/components/__fixtures__/form-firstname.fixture.json rename to packages/react-formio/src/molecules/__fixtures__/form-firstname.fixture.json diff --git a/packages/react-formio/src/components/__fixtures__/form-schema.json b/packages/react-formio/src/molecules/__fixtures__/form-schema.json similarity index 100% rename from packages/react-formio/src/components/__fixtures__/form-schema.json rename to packages/react-formio/src/molecules/__fixtures__/form-schema.json diff --git a/packages/react-formio/src/components/__fixtures__/form-submissions.json b/packages/react-formio/src/molecules/__fixtures__/form-submissions.json similarity index 100% rename from packages/react-formio/src/components/__fixtures__/form-submissions.json rename to packages/react-formio/src/molecules/__fixtures__/form-submissions.json diff --git a/packages/react-formio/src/components/__fixtures__/form-wizard.fixture.json b/packages/react-formio/src/molecules/__fixtures__/form-wizard.fixture.json similarity index 100% rename from packages/react-formio/src/components/__fixtures__/form-wizard.fixture.json rename to packages/react-formio/src/molecules/__fixtures__/form-wizard.fixture.json diff --git a/packages/react-formio/src/components/__fixtures__/form.fixture.json b/packages/react-formio/src/molecules/__fixtures__/form.fixture.json similarity index 100% rename from packages/react-formio/src/components/__fixtures__/form.fixture.json rename to packages/react-formio/src/molecules/__fixtures__/form.fixture.json diff --git a/packages/react-formio/src/molecules/__fixtures__/useValue.hook.ts b/packages/react-formio/src/molecules/__fixtures__/useValue.hook.ts new file mode 100644 index 00000000..96443ad5 --- /dev/null +++ b/packages/react-formio/src/molecules/__fixtures__/useValue.hook.ts @@ -0,0 +1,14 @@ +import { useState } from "react"; + +export const useValue = (args: any) => { + const [value, setValue] = useState(args.value); + + return { + ...args, + value, + onChange(name: string, value: any) { + setValue(value); + args.onChange(name, value); + } + }; +}; diff --git a/packages/react-formio/src/components/alert/alert.component.spec.tsx b/packages/react-formio/src/molecules/alert/Alert.spec.tsx similarity index 83% rename from packages/react-formio/src/components/alert/alert.component.spec.tsx rename to packages/react-formio/src/molecules/alert/Alert.spec.tsx index 5bbe512f..0011876f 100644 --- a/packages/react-formio/src/components/alert/alert.component.spec.tsx +++ b/packages/react-formio/src/molecules/alert/Alert.spec.tsx @@ -1,18 +1,16 @@ import { render, screen } from "@testing-library/react"; -import { Sandbox } from "./alert.stories"; +import { Alert } from "./Alert"; -describe("Alert component", () => { - it("should NOT display the alert component when no error is received.", () => { - const { container } = render(); - - expect(container).toBeEmptyDOMElement(); - }); +const args = { + error: "error placeholder" +}; +describe("Alert component", () => { it("should display an error when the error is in string format", () => { const error = "error in string format"; - render(); + render(); const alert = screen.getByRole("alert") as HTMLDivElement; @@ -24,7 +22,7 @@ describe("Alert component", () => { it("should display error(s) when the error is an array", () => { const arrayOfErrors = ["first error", "second error", "third error"]; const joinedErrors = arrayOfErrors.map((error) => error).join(""); - render(); + render(); const alert = screen.getByRole("alert") as HTMLDivElement; @@ -41,7 +39,7 @@ describe("Alert component", () => { { name: "third error", path: "/path", message: "message" } ] }; - render(); + render(); const alert = screen.getByRole("alert") as HTMLDivElement; @@ -52,7 +50,7 @@ describe("Alert component", () => { it("should display an error message when the error is a standard error", () => { const standardError = { message: "first error" }; - render(); + render(); const alert = screen.getByRole("alert") as HTMLDivElement; @@ -63,7 +61,7 @@ describe("Alert component", () => { it("should display error(s) message(s) when the error is a joi validation error", () => { const joiValidationError = { name: "ValidationError", details: [{ message: "message 1" }, { message: "message 2" }] }; - render(); + render(); const alert = screen.getByRole("alert") as HTMLDivElement; @@ -76,7 +74,7 @@ describe("Alert component", () => { it("should display a custom error message that asks to reload the form when a conflict error occurs in a form", () => { const error = { _id: "some id", display: "some value" }; const messageReturned = "Another user has saved this form already. Please reload and re-apply your changes."; - render(); + render(); const alert = screen.getByRole("alert") as HTMLDivElement; @@ -87,7 +85,7 @@ describe("Alert component", () => { it("should display an error message by default when the error format does not match any of the conditions of the formatError() handler", () => { const messageError: string = "An error occurred. See console logs for details."; - render(); + render(); const alert = screen.getByRole("alert") as HTMLDivElement; diff --git a/packages/react-formio/src/molecules/alert/Alert.stories.tsx b/packages/react-formio/src/molecules/alert/Alert.stories.tsx new file mode 100644 index 00000000..03ca06ef --- /dev/null +++ b/packages/react-formio/src/molecules/alert/Alert.stories.tsx @@ -0,0 +1,39 @@ +import { Alert } from "./Alert"; + +/** + * Alerts display brief messages for the user without interrupting their use of the app. + * + * ```tsx + * import {Alert} from "@tsed/react-formio/molecules/alert/Alert"; + * + * + * Message + * + * ``` + */ +export default { + title: "Alert", + component: Alert, + argTypes: { + message: { + control: { + type: "text" + } + }, + type: { + control: { + type: "select", + options: ["primary", "secondary", "success", "danger", "warning", "info", "light", "dark"] + } + } + }, + parameters: {}, + tags: ["autodocs"] +}; + +export const Sandbox = { + args: { + type: "danger", + message: "error placeholder" + } +}; diff --git a/packages/react-formio/src/components/alert/alert.component.tsx b/packages/react-formio/src/molecules/alert/Alert.tsx similarity index 86% rename from packages/react-formio/src/components/alert/alert.component.tsx rename to packages/react-formio/src/molecules/alert/Alert.tsx index 9f3d3d09..edfc833e 100644 --- a/packages/react-formio/src/components/alert/alert.component.tsx +++ b/packages/react-formio/src/molecules/alert/Alert.tsx @@ -1,4 +1,10 @@ +import { PropsWithChildren } from "react"; + function formatError(error: any): any { + if (!error || (Array.isArray(error) && !error.length)) { + return ""; + } + if (typeof error === "string") { return error; } @@ -42,18 +48,15 @@ function formatError(error: any): any { } export interface AlertProps { - error?: any | any[]; + message?: string | any | string[]; type?: string; } -export function Alert({ error, type = "danger" }: AlertProps) { - if (!error || (Array.isArray(error) && !error.length)) { - return null; - } - +export function Alert({ children, message, type = "danger" }: PropsWithChildren) { return (
- {formatError(error)} + {formatError(message)} + {children}
); } diff --git a/packages/react-formio/src/components/card/card.component.spec.tsx b/packages/react-formio/src/molecules/card/Card.spec.tsx similarity index 74% rename from packages/react-formio/src/components/card/card.component.spec.tsx rename to packages/react-formio/src/molecules/card/Card.spec.tsx index 198d42ac..e8a7ad0a 100644 --- a/packages/react-formio/src/components/card/card.component.spec.tsx +++ b/packages/react-formio/src/molecules/card/Card.spec.tsx @@ -1,10 +1,11 @@ import { render, screen } from "@testing-library/react"; -import { Sandbox } from "./card.stories"; +import { Card } from "./Card"; +import { Sandbox } from "./Card.stories"; describe("Card", () => { it("should render the card component", () => { - render(); + render(); const title = screen.getByRole("heading"); const body = screen.getByRole("article"); diff --git a/packages/react-formio/src/components/card/card.stories.tsx b/packages/react-formio/src/molecules/card/Card.stories.tsx similarity index 52% rename from packages/react-formio/src/components/card/card.stories.tsx rename to packages/react-formio/src/molecules/card/Card.stories.tsx index b397a43c..30fdf516 100644 --- a/packages/react-formio/src/components/card/card.stories.tsx +++ b/packages/react-formio/src/molecules/card/Card.stories.tsx @@ -1,7 +1,14 @@ -import { Card } from "./card.component"; +import { Card } from "./Card"; +/** + * Cards contain content and actions about a single subject. + * + * ```ts + * import {Card} from "@tsed/react-formio/molecules/card/Card"; + * ``` + */ export default { - title: "@tsed/react-formio/Card", + title: "Card", component: Card, argTypes: {}, parameters: {} diff --git a/packages/react-formio/src/components/card/card.component.tsx b/packages/react-formio/src/molecules/card/Card.tsx similarity index 100% rename from packages/react-formio/src/components/card/card.component.tsx rename to packages/react-formio/src/molecules/card/Card.tsx diff --git a/packages/react-formio/src/components/form-control/formControl.component.spec.tsx b/packages/react-formio/src/molecules/forms/form-control/FormControl.spec.tsx similarity index 81% rename from packages/react-formio/src/components/form-control/formControl.component.spec.tsx rename to packages/react-formio/src/molecules/forms/form-control/FormControl.spec.tsx index 02fc0b35..fcb1ece5 100644 --- a/packages/react-formio/src/components/form-control/formControl.component.spec.tsx +++ b/packages/react-formio/src/molecules/forms/form-control/FormControl.spec.tsx @@ -1,11 +1,12 @@ import { render, screen } from "@testing-library/react"; -import { iconClass } from "../../utils/iconClass"; -import { Sandbox, WithDescription, WithPrefix, WithSuffix } from "./formControl.stories"; +import { iconClass } from "../../../utils/iconClass"; +import { FormControl } from "./FormControl"; +import { Sandbox } from "./FormControl.stories"; describe("form-control", () => { it("should display form control component", () => { - render(); + render(); const formGroup = screen.getByTestId("form-group-test") as HTMLFormElement; @@ -14,7 +15,7 @@ describe("form-control", () => { it("should NOT display form-control component without a name attribute defined", () => { const name = ""; - render(); + render(); const formGroup = screen.queryByTestId(`form-group-${name}`) as HTMLFormElement; @@ -22,7 +23,7 @@ describe("form-control", () => { }); it("should display form-control component with className 'field-required' when the props 'required' is set to true", () => { - render(); + render(); const formGroup = screen.getByTestId("form-group-test") as HTMLFormElement; const formControlLabel = screen.getByTestId(`form-control-label`) as HTMLLabelElement; @@ -35,7 +36,7 @@ describe("form-control", () => { it("should display prefix", () => { const fontAwsomeCalendarIcon = "fa fa-calendar"; const prefix = () as JSX.Element; - render(); + render(); const formGroup = screen.getByTestId("form-group-testPrefix") as HTMLFormElement; const formControlPrefix = screen.getByTestId("form-control-prefix") as HTMLSpanElement; @@ -49,7 +50,7 @@ describe("form-control", () => { it("should display suffix", () => { const fontAwsomeCalendarIcon = "fa fa-calendar"; const suffix = () as JSX.Element; - render(); + render(); const formGroup = screen.getByTestId("form-group-testSuffix") as HTMLFormElement; const formControlSuffix = screen.getByTestId("form-control-suffix") as HTMLSpanElement; @@ -62,7 +63,7 @@ describe("form-control", () => { it("should display description", () => { const description = "test description"; - render(); + render(); const formGroup = screen.getByTestId("form-group-testDescription") as HTMLFormElement; const formControlDescription = screen.getByTestId("form-control-description") as HTMLDivElement; diff --git a/packages/react-formio/src/molecules/forms/form-control/FormControl.stories.tsx b/packages/react-formio/src/molecules/forms/form-control/FormControl.stories.tsx new file mode 100644 index 00000000..b457bb34 --- /dev/null +++ b/packages/react-formio/src/molecules/forms/form-control/FormControl.stories.tsx @@ -0,0 +1,64 @@ +import { Meta, StoryObj } from "@storybook/react"; + +import { iconClass } from "../../../utils/iconClass"; +import { FormControl } from "./FormControl"; +/** + * ```tsx + * import {FormControl} from "@tsed/react-formio/molecules/forms/form-control/FormControl"; + * ``` + */ +export default { + title: "forms/FormControl", + component: FormControl, + argTypes: { + label: { + control: { + type: "text" + } + }, + name: { + control: { + type: "text" + } + }, + children: { + control: { + type: "object" + } + } + }, + parameters: {}, + tags: ["autodocs"] +} satisfies Meta; + +type Story = StoryObj; + +export const Sandbox: Story = { + args: { + label: "Label", + children: "[TEXTFIELD]" + } +}; + +export const Usage: Story = { + args: { + label: "Label", + children: "[TEXTFIELD]", + prefix: + } +}; + +export const WithSuffix: Story = { + args: { + label: "Label", + children: "[TEXTFIELD]", + suffix: + } +}; + +export const WithDescription: Story = { + args: { + label: "Label", + children: "[TEXTFIELD]" + } +}; diff --git a/packages/react-formio/src/components/form-control/formControl.component.tsx b/packages/react-formio/src/molecules/forms/form-control/FormControl.tsx similarity index 100% rename from packages/react-formio/src/components/form-control/formControl.component.tsx rename to packages/react-formio/src/molecules/forms/form-control/FormControl.tsx diff --git a/packages/react-formio/src/molecules/forms/input-tags/InputTags.stories.tsx b/packages/react-formio/src/molecules/forms/input-tags/InputTags.stories.tsx new file mode 100644 index 00000000..68955998 --- /dev/null +++ b/packages/react-formio/src/molecules/forms/input-tags/InputTags.stories.tsx @@ -0,0 +1,95 @@ +import type { Meta, StoryObj } from "@storybook/react"; + +import { iconClass } from "../../../utils/iconClass"; +import { useValue } from "../../__fixtures__/useValue.hook"; +import { InputTags } from "./InputTags"; + +/** + * ```tsx + * import {InputTags} from "@tsed/react-formio/molecules/forms/input-tags/InputTags"; + * ``` + */ +export default { + title: "forms/InputTags", + component: InputTags, + argTypes: { + label: { + control: { + type: "text" + } + }, + name: { + control: { + type: "text" + } + }, + value: { + control: { + type: "object" + } + }, + size: { + control: { + type: "select", + options: ["sm", "normal"] + } + }, + placeholder: { + control: { + type: "text" + } + }, + choices: { + control: { + type: "object" + } + }, + description: { + control: { + type: "text" + } + } + }, + parameters: {}, + tags: ["autodocs"] +} satisfies Meta; + +type Story = StoryObj; + +export const Usage: Story = { + args: { + name: "name", + label: "Label", + value: ["test"], + size: "", + placeholder: "Placeholder" + } +}; + +export const WithPrefix: Story = { + render(args) { + // eslint-disable-next-line react-hooks/rules-of-hooks + return } {...useValue(args)} />; + }, + args: { + label: "Label", + value: [], + name: "name", + size: "", + placeholder: "Placeholder" + } +}; + +export const WithSuffix: Story = { + render(args) { + // eslint-disable-next-line react-hooks/rules-of-hooks + return } {...useValue(args)} />; + }, + args: { + label: "Label", + value: [], + name: "name", + size: "", + placeholder: "Placeholder" + } +}; diff --git a/packages/react-formio/src/components/input-tags/inputTags.component.tsx b/packages/react-formio/src/molecules/forms/input-tags/InputTags.tsx similarity index 94% rename from packages/react-formio/src/components/input-tags/inputTags.component.tsx rename to packages/react-formio/src/molecules/forms/input-tags/InputTags.tsx index 6d27e315..bcd2f4eb 100644 --- a/packages/react-formio/src/components/input-tags/inputTags.component.tsx +++ b/packages/react-formio/src/molecules/forms/input-tags/InputTags.tsx @@ -2,7 +2,7 @@ import Choices from "@formio/choices.js"; import uniq from "lodash/uniq"; import { useEffect, useRef } from "react"; -import { FormControl, FormControlProps } from "../form-control/formControl.component"; +import { FormControl, FormControlProps } from "../form-control/FormControl"; export interface InputTagsProps extends Omit { value?: T; diff --git a/packages/react-formio/src/components/input-text/inputText.component.spec.tsx b/packages/react-formio/src/molecules/forms/input-text/InputText.spec.tsx similarity index 95% rename from packages/react-formio/src/components/input-text/inputText.component.spec.tsx rename to packages/react-formio/src/molecules/forms/input-text/InputText.spec.tsx index 7644493c..b9e8c86c 100644 --- a/packages/react-formio/src/components/input-text/inputText.component.spec.tsx +++ b/packages/react-formio/src/molecules/forms/input-text/InputText.spec.tsx @@ -1,7 +1,7 @@ import { fireEvent, render, screen } from "@testing-library/react"; -import { InputText } from "./inputText.component"; -import { Usage } from "./inputText.stories"; +import { InputText } from "./InputText"; +import { Usage } from "./InputText.stories"; describe("input-text", () => { it("should display the input-text component", () => { diff --git a/packages/react-formio/src/components/input-text/inputText.stories.tsx b/packages/react-formio/src/molecules/forms/input-text/InputText.stories.tsx similarity index 90% rename from packages/react-formio/src/components/input-text/inputText.stories.tsx rename to packages/react-formio/src/molecules/forms/input-text/InputText.stories.tsx index c0c88bb5..31e4a431 100644 --- a/packages/react-formio/src/components/input-text/inputText.stories.tsx +++ b/packages/react-formio/src/molecules/forms/input-text/InputText.stories.tsx @@ -1,27 +1,20 @@ import type { Meta, StoryObj } from "@storybook/react"; import { expect, userEvent, within } from "@storybook/test"; -import { useState } from "react"; -import { iconClass } from "../../utils/iconClass"; -import { InputText } from "./inputText.component"; +import { iconClass } from "../../../utils/iconClass"; +import { useValue } from "../../__fixtures__/useValue.hook"; +import { InputText } from "./InputText"; const delay = (ms: number) => new Promise((resolve) => setTimeout(resolve, ms)); - -const useValue = (args: any) => { - const [value, setValue] = useState(args.value); - - return { - ...args, - value, - onChange(name: string, value: any) { - setValue(value); - args.onChange(name, value); - } - }; -}; - +/** + * Text Fields let users enter and edit text. + * + * ```tsx + * import {InputTags} from "@tsed/react-formio/molecules/forms/input-text/InputText"; + * ``` + */ export default { - title: "@tsed/react-formio/InputText", + title: "forms/InputText", component: InputText, argTypes: { label: { diff --git a/packages/react-formio/src/components/input-text/inputText.component.tsx b/packages/react-formio/src/molecules/forms/input-text/InputText.tsx similarity index 91% rename from packages/react-formio/src/components/input-text/inputText.component.tsx rename to packages/react-formio/src/molecules/forms/input-text/InputText.tsx index 2534ff51..ea7b6fbf 100644 --- a/packages/react-formio/src/components/input-text/inputText.component.tsx +++ b/packages/react-formio/src/molecules/forms/input-text/InputText.tsx @@ -2,8 +2,8 @@ import classnames from "classnames"; import { useEffect, useState } from "react"; import { useDebouncedCallback } from "use-debounce"; -import { getEventValue } from "../../utils/getEventValue"; -import { FormControl, FormControlProps } from "../form-control/formControl.component"; +import { getEventValue } from "../../../utils/getEventValue"; +import { FormControl, FormControlProps } from "../form-control/FormControl"; export interface InputTextProps extends FormControlProps { type?: string; diff --git a/packages/react-formio/src/components/select/select.component.spec.tsx b/packages/react-formio/src/molecules/forms/select/Select.spec.tsx similarity index 73% rename from packages/react-formio/src/components/select/select.component.spec.tsx rename to packages/react-formio/src/molecules/forms/select/Select.spec.tsx index d6b4e2dc..71c55392 100644 --- a/packages/react-formio/src/components/select/select.component.spec.tsx +++ b/packages/react-formio/src/molecules/forms/select/Select.spec.tsx @@ -1,17 +1,22 @@ import { fireEvent, render, screen } from "@testing-library/react"; -import { Choicesjs, Sandbox } from "./select.stories"; +import { Select } from "./Select"; +import { Choicesjs, Usage } from "./Select.stories"; +const choices = [ + { label: "label1", value: "value1" }, + { label: "label2", value: "value2" } +]; describe("Select", () => { describe("select component Usage version", () => { it("should render the select component", () => { - render(); + render(); const select = screen.getByTestId("select_test-sandbox"); expect(select).toBeInTheDocument(); expect(select).toHaveClass("form-control-small"); @@ -25,7 +30,7 @@ describe("Select", () => { const placeHolderTest = "Placeholder test"; - render(); + render(); const option = screen.getByRole("option", { name: placeHolderTest }) as HTMLOptionElement; expect(option.selected).toBeTruthy(); @@ -53,15 +58,12 @@ describe("Select", () => { const placeHolderTest = "Placeholder test"; const onChange = vi.fn(); - render(); + render(); expect(screen.getByRole("option", { name: "test1" })).toBeInTheDocument(); }); diff --git a/packages/react-formio/src/molecules/forms/select/Select.stories.tsx b/packages/react-formio/src/molecules/forms/select/Select.stories.tsx new file mode 100644 index 00000000..9ee076bf --- /dev/null +++ b/packages/react-formio/src/molecules/forms/select/Select.stories.tsx @@ -0,0 +1,167 @@ +import { Meta, StoryObj } from "@storybook/react"; + +import { iconClass } from "../../../utils/iconClass"; +import { useValue } from "../../__fixtures__/useValue.hook"; +import { Select } from "./Select"; + +const choices = [ + { label: "label1", value: "value1" }, + { label: "label2", value: "value2" } +]; + +/** + * Select components are used for collecting user provided information from a list of options. + * + * ```tsx + * import {Select} from "@tsed/react-formio/molecules/forms/select/Select"; + * ``` + */ +export default { + title: "forms/Select", + component: Select, + argTypes: { + label: { + control: { + type: "text" + } + }, + name: { + control: { + type: "text" + } + }, + value: { + control: { + type: "select", + options: choices + } + }, + size: { + control: { + type: "select", + options: ["sm", "normal"] + } + }, + layout: { + control: { + type: "select", + options: ["html5", "choicesjs"] + } + }, + placeholder: { + control: { + type: "text" + } + }, + choices: { + control: { + type: "object" + } + } + }, + parameters: {}, + render(args: any) { + // eslint-disable-next-line react-hooks/rules-of-hooks + return