@workday/canvas-kit-docs 16.0.9 → 16.0.11

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,8 +1,5 @@
1
- import {
2
- ExampleCodeBlock,
3
- Specifications,
4
- SymbolDoc,
5
- } from '@workday/canvas-kit-docs';
1
+ import {ExampleCodeBlock, Specifications, SymbolDoc} from '@workday/canvas-kit-docs';
2
+
6
3
  import Basic from './examples/Basic';
7
4
  import Disabled from './examples/Disabled';
8
5
  import Grow from './examples/Grow';
@@ -66,8 +63,6 @@ the width of its container.
66
63
 
67
64
  <ExampleCodeBlock code={Grow} />
68
65
 
69
- The `grow` prop may also be applied directly to the Text Input if Form Field is not being used.
70
-
71
66
  ### Label Position Horizontal
72
67
 
73
68
  Set the `orientation` prop of the Form Field to designate the position of the label relative to the
@@ -77,8 +72,8 @@ input component. By default, the orientation will be set to `vertical`.
77
72
 
78
73
  ### Required
79
74
 
80
- Set the `required` prop of the wrapping Form Field to `true` to indicate that the field is required.
81
- Labels for required fields are suffixed by a red asterisk.
75
+ Set the `isRequired` prop of the wrapping Form Field to `true` to indicate that the field is
76
+ required. Labels for required fields are suffixed by a red asterisk.
82
77
 
83
78
  <ExampleCodeBlock code={Required} />
84
79
 
@@ -97,11 +92,16 @@ something else, be sure to set the `width` property of `InputGroup.InnerStart` o
97
92
  `InputGroup.InnerEnd` to match the intended width of the element. Do not use the `cs` prop or any
98
93
  method to change width. The `width` prop is used to correctly position other inner elements.
99
94
 
95
+ Do **not** use `FormField.Input as={InputGroup}` — that breaks label association. Render
96
+ `FormField.Field as={InputGroup}`, hoist the input `id` from the Form Field model, and set it on
97
+ `InputGroup.Input` (see the Icons example).
98
+
100
99
  <ExampleCodeBlock code={Icons} />
101
100
 
102
- > **Accessibility Note**: In this example, the mail icon is decorative and hidden from screen
103
- > readers. If icons are used for conveying meaning in addition to the label text, a text alternative
104
- > must be provided for screen readers.
101
+ > **Accessibility Note**: Canvas Kit icons are already hidden from assistive technology their SVG
102
+ > markup sets `role="presentation"` and `focusable="false"` so decorative icons like the mail icon
103
+ > in this example need no extra attributes. If an icon conveys meaning beyond the label text,
104
+ > provide that meaning as text for screen readers.
105
105
 
106
106
  ### Error States
107
107
 
@@ -112,33 +112,192 @@ accessibility guidance.
112
112
 
113
113
  ## Accessibility
114
114
 
115
- `TextInput` should be used with [Form Field](/components/inputs/form-field/) to ensure proper
116
- labeling, error handling, and help text association. See
117
- [FormField's accessibility documentation](/components/inputs/form-field/#accessibility) for
118
- comprehensive guidance on form accessibility best practices.
119
-
120
- ### Autocomplete Attribute
121
-
122
- - Add appropriate `autoComplete` values to indicate the input's purpose (e.g., `"email"`, `"name"`,
123
- `"street-address"`, `"tel"`). Read more about
124
- [Identify Input Purpose](https://www.w3.org/WAI/WCAG22/Understanding/identify-input-purpose.html).
125
- - Autocomplete enables browser autofill and helps assistive technologies understand the field's
126
- purpose, benefiting users with cognitive disabilities and motor impairments.
127
- - Autocomplete also helps password managers identify the correct fields.
115
+ The primary accessibility goal for `TextInput` is to give every user a visible, persistent label and
116
+ clear instructions, and to ensure assistive technology users can identify the single-line field and
117
+ hear hints, errors, required state, and input purpose when the control receives focus. Use
118
+ `TextInput` for single-line values (names, emails, short answers). For multiple lines or paragraphs
119
+ of text, use [TextArea](/components/inputs/text-area/) instead.
120
+
121
+ ### Minimum Accessible Structure
122
+
123
+ Build on the Basic example: label first, then the input inside `FormField.Field`. This order matches
124
+ the DOM reading sequence and ensures the label's `htmlFor` targets the `<input>` before hint text
125
+ follows the control.
126
+
127
+ ```tsx
128
+ import {FormField} from '@workday/canvas-kit-react/form-field';
129
+ import {TextInput} from '@workday/canvas-kit-react/text-input';
130
+
131
+ <FormField>
132
+ <FormField.Label>Email</FormField.Label>
133
+ <FormField.Field>
134
+ <FormField.Input as={TextInput} />
135
+ <FormField.Hint>We'll never share your email.</FormField.Hint>
136
+ </FormField.Field>
137
+ </FormField>;
138
+ ```
128
139
 
129
- ### Input Type for Mobile Keyboards
140
+ Every `TextInput` requires **`FormField`**, a visible **`FormField.Label`**, and
141
+ **`FormField.Input as={TextInput}`** so the control has a programmatically determinable name,
142
+ relationships, and instructions. See
143
+ [FormField's accessibility documentation](/components/inputs/form-field/#accessibility) for shared
144
+ form-field guidance. Include **`FormField.Hint`** for instructions or validation
145
+ messages—`FormField` associates that text with the input through `aria-describedby`.
146
+
147
+ ### Built-in Behaviors
148
+
149
+ Canvas Kit applies these automatically when you compose `TextInput` with `FormField` subcomponents
150
+ (and `InputGroup`, when used). **Do not duplicate them** in consuming code.
151
+
152
+ **ARIA and DOM** (_applied by subcomponents_):
153
+
154
+ - **`TextInput`**: Renders a native `<input type="text">` by default. Screen readers identify it as
155
+ a single-line text input.
156
+ - **`TextInput` `disabled`**: Maps to the native `disabled` attribute; disabled fields are removed
157
+ from the tab order.
158
+ - **`InputGroup.ClearButton`**: Sets `role="presentation"` and `tabIndex={-1}` so the control is not
159
+ in the tab order and is not exposed as an operable button to screen readers. Clearing is available
160
+ via native keyboard editing in the input.
161
+ - **`InputGroup.Input`**: Always ensures a `placeholder` attribute exists (empty string when unset)
162
+ so `:placeholder-shown` styling for the clear button works correctly.
163
+ - **Canvas Kit icons** (for example `SystemIcon` inside `InputGroup`): SVG markup includes
164
+ `role="presentation"` and `focusable="false"`, which removes the implied `img` role. Decorative
165
+ icons need no `aria-hidden`.
166
+
167
+ **Keyboard** (_standard `TextInput` behavior_):
168
+
169
+ `TextInput` uses native `<input>` keyboard behavior (tab order, label activation, and text-editing
170
+ shortcuts). Do not add custom key handlers that prevent standard text editing.
171
+
172
+ **`InputGroup.ClearButton`** is intentionally not keyboard-focusable; users clear the value with
173
+ standard input editing keys.
174
+
175
+ **Screen reader expectations** (_when built-in behaviors are used as intended_):
176
+
177
+ - On focus, assistive technology announces the field label and, when applicable: required state,
178
+ invalid state (`error="error"`), and hint or error text via `aria-describedby`.
179
+ - The current value or "blank" is announced when the input receives focus.
180
+ - The Caution state is visual only — `aria-invalid` is **not** set for `error="caution"`.
181
+ - Disabled inputs may be announced as unavailable and are skipped in the tab order.
182
+ - **`InputGroup.ClearButton`** is not announced as a separate operable control.
183
+ - Icons rendered inside **`InputGroup.InnerStart`** or **`InputGroup.InnerEnd`** are not announced,
184
+ because their SVG markup uses `role="presentation"`.
185
+
186
+ For rendered label, input, and hint association markup, see the DOM examples in
187
+ [FormField's Built-in Behaviors](/components/inputs/form-field/#built-in-behaviors). `TextInput`
188
+ renders a native `<input>` (see FormField examples).
189
+
190
+ ### Accessibility Requirements
191
+
192
+ Required in application code for an accessible `TextInput`. Rows marked _(conditional)_ apply only
193
+ when the situation matches—otherwise omit.
194
+
195
+ **If no design spec is provided:** use a visible `FormField.Label`, wrap the control with
196
+ `FormField.Input as={TextInput}`, omit `isHidden`, omit a custom `id` unless testing or composition
197
+ requires it, omit a `ref` unless programmatic focus is required, and omit `InputGroup` unless icons
198
+ or a clear control are part of the design.
199
+
200
+ **Programmatic focus** _(conditional — omit by default)_:
201
+
202
+ Use a ref when the product needs to move focus to the input after an action (for example, focusing
203
+ the field after a validation error, or a control that focuses the input). Do not attach a `ref` or
204
+ call `focus()` unless the design or developer asks for it. See [Ref Forwarding](#ref-forwarding)
205
+ under Usage for a complete Storybook example.
206
+
207
+ ```tsx
208
+ const Example = () => {
209
+ const ref = React.useRef<HTMLInputElement>(null);
210
+
211
+ const handleClick = () => {
212
+ ref.current?.focus();
213
+ };
214
+
215
+ return (
216
+ <>
217
+ <FormField>
218
+ <FormField.Label>Email</FormField.Label>
219
+ <FormField.Field>
220
+ <FormField.Input as={TextInput} ref={ref} />
221
+ </FormField.Field>
222
+ </FormField>
223
+ <PrimaryButton onClick={handleClick}>Focus Text Input</PrimaryButton>
224
+ </>
225
+ );
226
+ };
227
+ ```
130
228
 
131
- `TextInput` defaults to `<input type="text">`, but for better mobile keyboard support, use more
132
- specific `type` attributes (like `"email"`, `"tel"`, `"url"`, or `"search"`) as needed.
229
+ **`InputGroup` with icons** _(conditional)_:
133
230
 
134
- ### Screen Reader Experience
231
+ When the design includes start/end icons or a clear control, compose `InputGroup` as
232
+ `FormField.Field` (not as `FormField.Input`) and wire the input `id` from the Form Field model:
135
233
 
136
- When properly implemented with `FormField`, screen readers will announce:
234
+ ```tsx
235
+ import {
236
+ FormField,
237
+ useFormFieldInput,
238
+ useFormFieldModel,
239
+ } from '@workday/canvas-kit-react/form-field';
240
+ import {SystemIcon} from '@workday/canvas-kit-react/icon';
241
+ import {InputGroup} from '@workday/canvas-kit-react/text-input';
242
+ import {mailIcon} from '@workday/canvas-system-icons-web';
243
+
244
+ const model = useFormFieldModel();
245
+ const {id: formFieldInputId} = useFormFieldInput(model);
246
+
247
+ <FormField model={model}>
248
+ <FormField.Label>Email</FormField.Label>
249
+ <FormField.Field as={InputGroup}>
250
+ <InputGroup.InnerStart>
251
+ <SystemIcon icon={mailIcon} />
252
+ </InputGroup.InnerStart>
253
+ <InputGroup.Input id={formFieldInputId} autoComplete="email" />
254
+ <InputGroup.InnerEnd>
255
+ <InputGroup.ClearButton />
256
+ </InputGroup.InnerEnd>
257
+ </FormField.Field>
258
+ </FormField>;
259
+ ```
137
260
 
138
- - The label text when the input receives focus.
139
- - Required, disabled, or read-only status.
140
- - Help text and error messages (via `aria-describedby`).
141
- - The current value or "blank" if empty.
261
+ | Requirement | How to satisfy |
262
+ | ------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
263
+ | Input wiring | **`FormField.Input as={TextInput}`** wrapping every `TextInput` instance. See [FormField accessibility](/components/inputs/form-field/#accessibility) for label, hint, error, and required wiring |
264
+ | Autocomplete _(conditional)_ | `autoComplete` on **`FormField.Input`** (or **`InputGroup.Input`**) with an appropriate token (e.g. `"email"`, `"name"`, `"street-address"`, `"tel"`). See [Identify Input Purpose](https://www.w3.org/WAI/WCAG22/Understanding/identify-input-purpose.html) |
265
+ | Input `type` _(conditional)_ | More specific `type` than `"text"` (e.g. `"email"`, `"tel"`, `"url"`, `"search"`) when a specialized mobile keyboard improves entry |
266
+ | Icons / clear control _(conditional)_ | **`FormField.Field as={InputGroup}`** + **`InputGroup.Input`** with hoisted `id` (see **`InputGroup` with icons** above). Decorative icons need no extra attributes; when an icon conveys meaning beyond the label, convey that meaning as text |
267
+ | Programmatic focus _(conditional)_ | `ref` on **`FormField.Input`** and call `focus()` when moving focus to the field after an action—omit by default (see **Programmatic focus** above) |
268
+
269
+ **Summary for code generation:**
270
+
271
+ - **REQUIRED:** visible label, `FormField.Input as={TextInput}` wiring
272
+ - **CONDITIONAL:** `autoComplete`, specialized `type`, `InputGroup` icon/clear composition with
273
+ hoisted `id`, programmatic focus via `ref`. See
274
+ [FormField accessibility](/components/inputs/form-field/#accessibility) for shared FormField
275
+ conditionals (hint/error, required, disabled, placeholder, stable `id`).
276
+
277
+ ### Anti-Patterns
278
+
279
+ Do **not** generate code that does the following (see **Accessibility Requirements** above for what
280
+ to supply instead):
281
+
282
+ - **Unlabeled text inputs**: Do not use `TextInput` without `FormField` and `FormField.Label` (see
283
+ **Minimum accessible structure**). For shared FormField anti-patterns (manual ARIA wiring,
284
+ placeholder-only labels, color-only errors, broken ID references), see
285
+ [FormField Anti-Patterns](/components/inputs/form-field/#anti-patterns).
286
+ - **Multi-line content in `TextInput`**: Do not use `TextInput` when the user needs to enter
287
+ paragraphs or multi-line text; use [TextArea](/components/inputs/text-area/) instead.
288
+ - **`FormField.Input as={InputGroup}`**: Do not put `InputGroup` on `FormField.Input` — that breaks
289
+ label association. Use **`FormField.Field as={InputGroup}`**, hoist `id` from
290
+ `useFormFieldInput(model)`, and pass it to **`InputGroup.Input`** (see **`InputGroup` with icons**
291
+ in Accessibility Requirements and [Icons](#icons) under Usage).
292
+ - **Re-wiring `ClearButton` a11y**: Do not override `InputGroup.ClearButton`'s `role` or `tabIndex`
293
+ to make it a focusable, announced button — Canvas Kit intentionally keeps clearing on the input.
294
+ - **Redundant `aria-hidden` on icons**: Do not add `aria-hidden` to Canvas Kit icons — their SVG
295
+ markup already sets `role="presentation"` and `focusable="false"`.
296
+ - **Meaningful icons without a text alternative**: Do not rely on an icon inside `InputGroup` to
297
+ convey information beyond the label; because icons are presentational, that meaning must come from
298
+ text such as **`FormField.Label`** or **`FormField.Hint`**.
299
+ - **Programmatic focus by default**: Do not attach a `ref` or call `focus()` on the input unless the
300
+ design or developer asks for it (see **Programmatic focus** in Accessibility Requirements).
142
301
 
143
302
  ## Component API
144
303
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@workday/canvas-kit-docs",
3
- "version": "16.0.9",
3
+ "version": "16.0.11",
4
4
  "description": "Documentation components of Canvas Kit components",
5
5
  "author": "Workday, Inc. (https://www.workday.com)",
6
6
  "license": "Apache-2.0",
@@ -47,10 +47,10 @@
47
47
  "@stackblitz/sdk": "^1.11.0",
48
48
  "@storybook/csf": "0.0.1",
49
49
  "@workday/canvas-expressive-icons-web": "1.0.2",
50
- "@workday/canvas-kit-labs-react": "^16.0.9",
51
- "@workday/canvas-kit-preview-react": "^16.0.9",
52
- "@workday/canvas-kit-react": "^16.0.9",
53
- "@workday/canvas-kit-styling": "^16.0.9",
50
+ "@workday/canvas-kit-labs-react": "^16.0.11",
51
+ "@workday/canvas-kit-preview-react": "^16.0.11",
52
+ "@workday/canvas-kit-react": "^16.0.11",
53
+ "@workday/canvas-kit-styling": "^16.0.11",
54
54
  "@workday/canvas-system-icons-web": "^5.0.3",
55
55
  "@workday/canvas-tokens-web": "^4.4.0",
56
56
  "markdown-to-jsx": "^7.2.0",
@@ -63,5 +63,5 @@
63
63
  "mkdirp": "^1.0.3",
64
64
  "typescript": "5.0"
65
65
  },
66
- "gitHead": "83ec5bdb4736eabff2829149a705ed07f00af83f"
66
+ "gitHead": "c24d68b9e1fa5a1e5af583d3240bf64c369d5037"
67
67
  }