diff --git a/packages/react/src/components/form/CharacterCounter.tsx b/packages/react/src/components/form/CharacterCounter.tsx index b409bf0bf7..36ecd460db 100644 --- a/packages/react/src/components/form/CharacterCounter.tsx +++ b/packages/react/src/components/form/CharacterCounter.tsx @@ -1,7 +1,7 @@ import React from 'react'; import utilityClasses from '../../utils/utility.module.css'; -import { ErrorMessage, Paragraph } from '../Typography'; +import { ErrorMessage } from '../Typography'; export type CharacterLimitProps = Omit< CharacterCounterProps, @@ -10,9 +10,9 @@ export type CharacterLimitProps = Omit< type CharacterCounterProps = { /** The message indicating the remaining character limit. */ - label: (count: number) => string; + label?: (count: number) => string; /** The description of the maximum character limit for screen readers. */ - srLabel: string; + srLabel?: string; /** The maximum allowed character count. */ maxCount: number; /** The current value. */ @@ -23,15 +23,15 @@ type CharacterCounterProps = { size?: 'xsmall' | 'small' | 'medium' | 'large'; }; -// const defaultLabel: CharacterCounterProps['label'] = (count) => -// count > -1 ? `${count} tegn igjen` : `${Math.abs(count)} tegn for mye.`; +const defaultLabel: CharacterCounterProps['label'] = (count) => + count > -1 ? `${count} tegn igjen` : `${Math.abs(count)} tegn for mye.`; -// const defaultSrLabel = (maxCount: number) => -// `Tekstfelt med plass til ${maxCount} tegn.`; +const defaultSrLabel = (maxCount: number) => + `Tekstfelt med plass til ${maxCount} tegn.`; export const CharacterCounter = ({ - label, - srLabel, + label = defaultLabel, + srLabel: propsSrLabel, maxCount, value, id, @@ -39,6 +39,7 @@ export const CharacterCounter = ({ }: CharacterCounterProps): JSX.Element => { const currentCount = maxCount - value.length; const hasExceededLimit = value.length > maxCount; + const srLabel = propsSrLabel ? propsSrLabel : defaultSrLabel(maxCount); return ( <> diff --git a/packages/react/src/components/form/Textfield/Textfield.mdx b/packages/react/src/components/form/Textfield/Textfield.mdx index 7775207e3b..b4718e6517 100644 --- a/packages/react/src/components/form/Textfield/Textfield.mdx +++ b/packages/react/src/components/form/Textfield/Textfield.mdx @@ -10,3 +10,4 @@ import * as TextfieldStories from './Textfield.stories'; + diff --git a/packages/react/src/components/form/Textfield/Textfield.stories.tsx b/packages/react/src/components/form/Textfield/Textfield.stories.tsx index 41c220a41d..77d926dc9b 100644 --- a/packages/react/src/components/form/Textfield/Textfield.stories.tsx +++ b/packages/react/src/components/form/Textfield/Textfield.stories.tsx @@ -1,4 +1,7 @@ -import type { Meta, StoryObj } from '@storybook/react'; +import type { Meta, StoryObj, StoryFn } from '@storybook/react'; +import React, { useState } from 'react'; + +import { Button, Paragraph } from '../..'; import { Textfield } from '.'; @@ -12,28 +15,37 @@ export default { export const Preview: Story = { args: { label: 'Label', - description: 'Description', disabled: false, readOnly: false, - error: 'Annen feilmelding her', - characterLimit: { - label: (count) => - count > -1 ? `${count} tegn igjen` : `${Math.abs(count)} tegn for mye.`, - maxCount: 20, - srLabel: `Tekstfelt med plass til ${20} tegn.`, - }, + description: '', }, }; export const WithCharacterCounter: Story = { args: { label: 'Label', - error: 'Annen feilmelding her', characterLimit: { label: (count) => - count > -1 ? `${count} tegn igjen` : `${Math.abs(count)} tegn for mye.`, - maxCount: 20, - srLabel: `Tekstfelt med plass til ${20} tegn.`, + count > -1 + ? `${count} character Left` + : `${Math.abs(count)} characters to many.`, + maxCount: 5, + srLabel: `Field with room for ${5} characters.`, }, }, }; + +export const Controlled: StoryFn = () => { + const [value, setValue] = useState(); + return ( + <> + Du har skrevet inn: {value} + setValue(e.target.value)} + /> + + + ); +}; diff --git a/packages/react/src/components/form/Textfield/Textfield.tsx b/packages/react/src/components/form/Textfield/Textfield.tsx index a8a1009270..84cda9d1d8 100644 --- a/packages/react/src/components/form/Textfield/Textfield.tsx +++ b/packages/react/src/components/form/Textfield/Textfield.tsx @@ -14,32 +14,51 @@ import classes from './Textfield.module.css'; import utilityClasses from './../../../utils/utility.module.css'; export type TextfieldProps = { + /** Label */ label?: ReactNode; + /** Visually hides `label` and `description` (still available for screen readers) */ + hideLabel?: boolean; + /** Changes field size and paddings */ size?: 'xsmall' | 'small' | 'medium' | 'large'; + /** Prefix for field. */ prefix?: string; + /** Sufix for field. */ sufix?: string; + /** Supported `input` types */ type?: - | 'text' - | 'password' | 'date' | 'datetime-local' | 'email' + | 'file' | 'month' | 'number' + | 'password' | 'search' | 'tel' + | 'text' | 'time' | 'url' | 'week'; /** - * The characterLimit function calculates remaining characters. + * The characterLimit function calculates remaining characters based on `maxCount` + * * Provide a `label` function that takes count as parameter and returns a message. + * * Use `srLabel` to describe `maxCount` for screen readers. + * + * Defaults to Norwegian if no labels are provided. */ characterLimit?: CharacterLimitProps; } & Omit & Omit, 'size'>; +/** Text input field + * + * @example + * ```tsx + * + * ``` + */ export const Textfield = forwardRef( (props, ref) => { const { @@ -49,8 +68,10 @@ export const Textfield = forwardRef( prefix, style, characterLimit, + hideLabel, ...rest } = props; + const { inputProps, descriptionId, @@ -61,7 +82,7 @@ export const Textfield = forwardRef( } = useTextfield(props); const [inputValue, setInputValue] = useState(props.defaultValue); - const characterLimitId = `charactercount-${useId()}`; + const characterLimitId = `textfield-charactercount-${useId()}`; const hasCharacterLimit = characterLimit != null; const describedBy = cn( @@ -83,7 +104,10 @@ export const Textfield = forwardRef( > {label && (