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 = { title: 'Core Components/Input', // @ts-expect-error Input does not support this, but wrapping does component: ({ isInvalid, validationState, ...props }) => ( ), 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 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 ( ) : undefined } rightIcon={ showRightIcon && rightIconName ? ( ) : undefined } /> ) }, 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('') }, }