Files
web/packages/design-system/lib/components/Input/Input.stories.tsx
Rasmus Langvad d0546926a9 Merged in fix/3697-prettier-configs (pull request #3396)
fix(SW-3691): Setup one prettier config for whole repo

* Setup prettierrc in root and remove other configs


Approved-by: Joakim Jäderberg
Approved-by: Linus Flood
2026-01-07 12:45:50 +00:00

204 lines
5.3 KiB
TypeScript

import type { Meta, StoryObj } from "@storybook/nextjs-vite"
import { expect } from "storybook/test"
import { Input } from "./Input"
import { TextField } from "react-aria-components"
import { MaterialIcon } from "../Icons/MaterialIcon"
import type { SymbolCodepoints } from "../Icons/MaterialIcon/MaterialSymbol/types"
const meta: Meta<typeof Input> = {
title: "Core Components/Input",
// @ts-expect-error Input does not support this, but wrapping <TextField> does
component: ({ isInvalid, validationState, ...props }) => (
<TextField isInvalid={isInvalid} data-validation-state={validationState}>
<Input {...props} data-validation-state={validationState} />
</TextField>
),
argTypes: {
label: {
control: "text",
description: "The label text displayed for the input field",
table: {
type: { summary: "string" },
},
},
labelPosition: {
control: "select",
options: ["floating", "top"],
description: "Position of the label relative to the input",
table: {
type: { summary: "'floating' | 'top'" },
defaultValue: { summary: "'floating'" },
},
},
placeholder: {
control: "text",
description: "Placeholder text shown when input is empty",
table: {
type: { summary: "string" },
defaultValue: { summary: "undefined" },
},
},
required: {
control: "boolean",
description: "Whether the input is required",
table: {
type: { summary: "boolean" },
defaultValue: { summary: "false" },
},
},
disabled: {
control: "boolean",
description: "Whether the input is disabled",
table: {
type: { summary: "boolean" },
defaultValue: { summary: "false" },
},
},
showClearContentIcon: {
control: "boolean",
description: "Whether the clear content icon is shown",
table: {
type: { summary: "boolean" },
defaultValue: { summary: "false" },
},
},
showLeftIcon: {
control: "boolean",
description: "Whether to show a left icon",
table: {
type: { summary: "boolean" },
defaultValue: { summary: "false" },
},
},
showRightIcon: {
control: "boolean",
description: "Whether to show a right icon",
table: {
type: { summary: "boolean" },
defaultValue: { summary: "false" },
},
},
leftIconName: {
control: "select",
options: [
"calendar_month",
"credit_card",
"email",
"info_circle",
"location_on",
"lock",
"phone",
"search",
"sell",
"visibility",
"visibility_off",
],
description: "Icon name for the left icon",
table: {
type: { summary: "string" },
defaultValue: { summary: "'person'" },
},
},
rightIconName: {
control: "select",
options: [
"calendar_month",
"credit_card",
"email",
"info_circle",
"location_on",
"lock",
"phone",
"search",
"sell",
"visibility",
"visibility_off",
],
description: "Icon name for the right icon",
table: {
type: { summary: "string" },
defaultValue: { summary: "'lock'" },
},
},
showWarning: {
control: "boolean",
description: "Whether to show warning validation state",
table: {
type: { summary: "boolean" },
defaultValue: { summary: "false" },
},
},
// eslint-disable-next-line @typescript-eslint/no-explicit-any
} as any,
}
export default meta
type Story = StoryObj<typeof Input>
export const Default: Story = {
args: {
label: "Label",
name: "foo",
required: false,
showLeftIcon: false,
showRightIcon: false,
leftIconName: "person",
rightIconName: "lock",
showWarning: false,
// eslint-disable-next-line @typescript-eslint/no-explicit-any
} as any,
render: (args) => {
// Extract custom Storybook args
const {
showLeftIcon,
showRightIcon,
leftIconName,
rightIconName,
showWarning,
...inputProps
} = args as typeof args & {
showLeftIcon?: boolean
showRightIcon?: boolean
leftIconName?: string
rightIconName?: string
showWarning?: boolean
}
const validationState = showWarning ? "warning" : undefined
return (
<TextField data-validation-state={validationState}>
<Input
{...inputProps}
data-validation-state={validationState}
leftIcon={
showLeftIcon && leftIconName ? (
<MaterialIcon icon={leftIconName as SymbolCodepoints} />
) : undefined
}
rightIcon={
showRightIcon && rightIconName ? (
<MaterialIcon icon={rightIconName as SymbolCodepoints} />
) : undefined
}
/>
</TextField>
)
},
play: async ({ canvas, userEvent }) => {
const textbox = canvas.getByRole("textbox")
expect(textbox).not.toBeDisabled()
expect(textbox).toHaveValue("")
await userEvent.type(textbox, "Hello World")
expect(textbox).toHaveValue("Hello World")
await userEvent.clear(textbox)
expect(textbox).toHaveValue("")
},
}