---
layout: ~/layouts/MdxDocLayout.astro
title: "Label"
description: "A label component for form fields with support for required/optional indicators and tooltips."
sourceFile: "components/label"
---

import ComponentExample from "~/components/docs/ComponentExample.astro";
import ComponentSection from "~/components/docs/ComponentSection.astro";
import Heading from "~/components/docs/Heading.astro";
import {
  LabelBasicDemo,
  LabelOptionalFieldDemo,
  LabelWithTooltipDemo,
  LabelReactNodeDemo,
  LabelFormMixedDemo,
  LabelStandaloneDemo,
} from "~/components/demos/LabelDemo";

{/* Hero Demo */}

<ComponentSection>
  <ComponentExample demo="LabelBasicDemo">
    <LabelBasicDemo client:visible />
  </ComponentExample>
</ComponentSection>

{/* Installation */}

<ComponentSection>
  <Heading level={2}>Installation</Heading>
  <Heading level={3}>Barrel</Heading>

```tsx
import { Label } from "@cloudflare/kumo";
```

<Heading level={3}>Granular</Heading>

```tsx
import { Label } from "@cloudflare/kumo/components/label";
```

</ComponentSection>

{/* Usage */}

<ComponentSection>
  <Heading level={2}>Usage</Heading>
  <Heading level={3}>With Form Components (Recommended)</Heading>
  <p>
    Label features are automatically available through form components like `Input`, `Select`, `Checkbox`, and `Switch` via the `required` and `labelTooltip` props.
  </p>

```tsx
import { Input } from "@cloudflare/kumo";

export default function Example() {
  return (
    <>
      {/* Optional field with "(optional)" text */}
      <Input label="Phone" required={false} placeholder="+1 555-0000" />

      {/* With tooltip */}
      <Input
        label="API Key"
        labelTooltip="Find this in your dashboard settings"
      />
    </>
  );
}
```

<Heading level={3}>Standalone Label</Heading>
<p>For custom form layouts, use the `Label` component directly.</p>

```tsx
import { Label } from "@cloudflare/kumo";

export default function Example() {
  return <Label tooltip="This field is mandatory">Username</Label>;
}
```

</ComponentSection>

{/* Examples */}

<ComponentSection>
  <Heading level={2}>Examples</Heading>

<Heading level={3}>Optional Field</Heading>
<p>Shows gray "(optional)" text when `required={false}`.</p>
<ComponentExample demo="LabelOptionalFieldDemo">
  <LabelOptionalFieldDemo client:visible />
</ComponentExample>

<Heading level={3}>With Tooltip</Heading>
<p>Shows an info icon with a tooltip for additional context.</p>
<ComponentExample demo="LabelWithTooltipDemo">
  <LabelWithTooltipDemo client:visible />
</ComponentExample>

<Heading level={3}>ReactNode Label Content</Heading>
<p>Labels support ReactNode content for rich formatting.</p>
<ComponentExample demo="LabelReactNodeDemo">
  <LabelReactNodeDemo client:visible />
</ComponentExample>

<Heading level={3}>Form with Mixed Fields</Heading>
<p>Real-world example showing required and optional fields together.</p>
<ComponentExample demo="LabelFormMixedDemo">
  <LabelFormMixedDemo client:visible />
</ComponentExample>

<Heading level={3}>Standalone Label</Heading>
<p>Use Label directly for custom layouts or non-form contexts.</p>
<ComponentExample demo="LabelStandaloneDemo">
  <LabelStandaloneDemo client:visible />
</ComponentExample>

</ComponentSection>

{/* API Reference */}

<ComponentSection>
  <Heading level={2}>API Reference</Heading>

<Heading level={3}>Label Props</Heading>
<p>Props for the standalone Label component:</p>
<div class="overflow-x-auto">
  <table class="w-full text-sm">
    <thead>
      <tr class="border-b border-kumo-hairline">
        <th class="px-4 py-3 text-left font-semibold">Prop</th>
        <th class="px-4 py-3 text-left font-semibold">Type</th>
        <th class="px-4 py-3 text-left font-semibold">Default</th>
        <th class="px-4 py-3 text-left font-semibold">Description</th>
      </tr>
    </thead>
    <tbody class="text-kumo-strong">
      <tr class="border-b border-kumo-hairline">
        <td class="px-4 py-3 font-mono text-xs">children</td>
        <td class="px-4 py-3 font-mono text-xs">ReactNode</td>
        <td class="px-4 py-3 font-mono text-xs">-</td>
        <td class="px-4 py-3 text-xs">Label content (required)</td>
      </tr>
      <tr class="border-b border-kumo-hairline">
        <td class="px-4 py-3 font-mono text-xs">showOptional</td>
        <td class="px-4 py-3 font-mono text-xs">boolean</td>
        <td class="px-4 py-3 font-mono text-xs">false</td>
        <td class="px-4 py-3 text-xs">
          Shows gray "(optional)" text (only when required is false)
        </td>
      </tr>
      <tr class="border-b border-kumo-hairline">
        <td class="px-4 py-3 font-mono text-xs">tooltip</td>
        <td class="px-4 py-3 font-mono text-xs">ReactNode</td>
        <td class="px-4 py-3 font-mono text-xs">-</td>
        <td class="px-4 py-3 text-xs">Tooltip content shown via info icon</td>
      </tr>
      <tr class="border-b border-kumo-hairline">
        <td class="px-4 py-3 font-mono text-xs">className</td>
        <td class="px-4 py-3 font-mono text-xs">string</td>
        <td class="px-4 py-3 font-mono text-xs">-</td>
        <td class="px-4 py-3 text-xs">Additional CSS classes</td>
      </tr>
    </tbody>
  </table>
</div>

<Heading level={3}>Form Component Label Props</Heading>
<p>
  These props are available on Input, InputArea, Select, Checkbox, Switch,
  SensitiveInput, and Combobox:
</p>
<div class="overflow-x-auto">
  <table class="w-full text-sm">
    <thead>
      <tr class="border-b border-kumo-hairline">
        <th class="px-4 py-3 text-left font-semibold">Prop</th>
        <th class="px-4 py-3 text-left font-semibold">Type</th>
        <th class="px-4 py-3 text-left font-semibold">Default</th>
        <th class="px-4 py-3 text-left font-semibold">Description</th>
      </tr>
    </thead>
    <tbody class="text-kumo-strong">
      <tr class="border-b border-kumo-hairline">
        <td class="px-4 py-3 font-mono text-xs">label</td>
        <td class="px-4 py-3 font-mono text-xs">ReactNode</td>
        <td class="px-4 py-3 font-mono text-xs">-</td>
        <td class="px-4 py-3 text-xs">Label content (enables Field wrapper)</td>
      </tr>
      <tr class="border-b border-kumo-hairline">
        <td class="px-4 py-3 font-mono text-xs">required</td>
        <td class="px-4 py-3 font-mono text-xs">boolean</td>
        <td class="px-4 py-3 font-mono text-xs">-</td>
        <td class="px-4 py-3 text-xs">
          When false: shows "(optional)" text. Also sets HTML required
          attribute.
        </td>
      </tr>
      <tr class="border-b border-kumo-hairline">
        <td class="px-4 py-3 font-mono text-xs">labelTooltip</td>
        <td class="px-4 py-3 font-mono text-xs">ReactNode</td>
        <td class="px-4 py-3 font-mono text-xs">-</td>
        <td class="px-4 py-3 text-xs">
          Tooltip content shown via info icon next to label
        </td>
      </tr>
    </tbody>
  </table>
</div>

</ComponentSection>

{/* Design Guidelines */}

<ComponentSection>
  <Heading level={2}>Design Guidelines</Heading>
  <div class="space-y-4 text-sm">
    <div>
      <h3 class="mb-2 font-semibold">When to Use Optional Indicators</h3>
      <ul class="ml-4 list-disc space-y-1 text-kumo-strong">
        <li>
          Use "(optional)" for optional fields when most fields are required
        </li>
        <li>Be consistent within a form</li>
        <li>Default fields (no indicator) are assumed required by users</li>
      </ul>
    </div>
    <div>
      <h3 class="mb-2 font-semibold">When to Use Tooltips</h3>
      <ul class="ml-4 list-disc space-y-1 text-kumo-strong">
        <li>Provide additional context that doesn't fit in the label</li>
        <li>Explain format requirements or validation rules</li>
        <li>Link to help documentation for complex fields</li>
        <li>Keep tooltip content concise - 1-2 sentences max</li>
      </ul>
    </div>
    <div>
      <h3 class="mb-2 font-semibold">Accessibility</h3>
      <ul class="ml-4 list-disc space-y-1 text-kumo-strong">
        <li>
          Optional indicators are purely visual - use the `required` attribute
          for validation
        </li>
        <li>Tooltips are accessible via keyboard focus on the info icon</li>
        <li>Screen readers will announce tooltip content when focused</li>
      </ul>
    </div>
  </div>
</ComponentSection>
