# Link

Ein Link dient in erster Linie dazu, den User zu einer anderen Seite zu navigieren. Darüber hinaus kann er auch einen Download starten oder zu einem bestimmten Ankerpunkt auf der Seite führen.

## Overview

# Playground

Verwende `<Link />`, um einen Link darzustellen.

```tsx
import { Link } from "@mittwald/flow-react-components";

<Link href="#">Zum Dashboard</Link>
```

---

# Inline

Links innerhalb des `<Text />` -Tags werden automatisch als Inline Link
gerendert.

```tsx
import {
  Link,
  Text,
} from "@mittwald/flow-react-components";

<Text>
  Sieh dir unser <Link href="#">Onboarding</Link> an, um
  weitere Informationen zu erhalten.
</Text>
```

---

# Color

Zusätzlich zu der Standard-Color, kann der Link in **Light** und **Dark**
dargestellt werden. Light und Dark eignen sich besonders gut für Links auf
farbigen/dekorativen Hintergründen.

```tsx
import { Link } from "@mittwald/flow-react-components";

<Link href="#" color="light">
  Light
</Link>
```

```tsx
import { Link } from "@mittwald/flow-react-components";

<Link href="#" color="dark">
  Dark
</Link>
```

**Light:** Verwende die Light-Color bei dunklen Hintergründen mit einem HSL
Lightness-Wert von weniger als 50.

**Dark:** Verwende die Dark-Color bei hellen, farbigen Hintergründen mit einem
HSL Lightness-Wert von mehr als 50.

---

# Kombiniere mit ...

## Icon

Rechts neben dem Link kann ein `Icon` eingefügt werden.

### Externer Link

Das `IconExternalLink` signalisiert dem User, dass es sich um einen externen
Link handelt – also einen Verweis auf eine andere Domain –, der in einem neuen
Tab geöffnet wird. Das Icon erscheint automatisch neben dem Link, wenn das
Attribut `target="_blank"` gesetzt ist.

```tsx
import { Link } from "@mittwald/flow-react-components";

<Link href="https://mittwald.de" target="_blank">
  Externer Link
</Link>
```

### Download

Das `IconDownload` zeigt an, dass es sich um einen Download-Link handelt. Das
Icon wird automatisch neben dem Link angezeigt, wenn das `download` Property
gesetzt ist.

```tsx
import { Link } from "@mittwald/flow-react-components";

<Link download>Rechnung herunterladen</Link>
```

---

## States

Ein Link hat vier verschiedene States: **Default**, **Hover**, **Pressed** und
**Disabled**.

```tsx
import { Link } from "@mittwald/flow-react-components";

<Link href="#" isDisabled>
  Disabled
</Link>
```


## Develop

# Properties

| Property | Type | Default | Description |
| --- | --- | --- | --- |
| `inline` | `boolean` | - | Whether the link should be styled for being displayed inside a text. |
| `linkComponent` | `ComponentType<Omit<DetailedHTMLProps<AnchorHTMLAttributes<HTMLAnchorElement>, HTMLAnchorElement>, "ref">>` | - | An alternative link component. |
| `color` | `"default" \| "dark" \| "light" \| "dark-static" \| "light-static"` | `"default"` | The color of the link. |
| `slot` | `string` | - | - |
| `whiteSpace` | `WhiteSpace` | - | The whiteSpace css value of the element. |
| `size` | `"s" \| "m"` | `"m"` | The size of the element. |
| `id` | `string` | - | The element's unique identifier. See [MDN](https://developer.mozilla.org/en-US/docs/Web/HTML/Global_attributes/id). |
| `translate` | `"yes" \| "no"` | - | - |
| `style` | `StyleOrFunction<TooltipRenderProps>` | - | The inline [style](https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement/style) for the element. A function may be provided to compute the style based on component state. |
| `render` | `DOMRenderFunction<"div", TooltipRenderProps>` | - | Overrides the default DOM element with a custom render function. This allows rendering existing components with built-in styles and behaviors such as router links, animation libraries, and pre-styled components. Requirements: - You must render the expected element type (e.g. if `<button>` is expected, you cannot render an `<a>`). - Only a single root DOM element can be rendered (no fragments). - You must pass through props and ref to the underlying DOM element, merging with your own prop as appropriate. |
| `dir` | `string` | - | - |
| `lang` | `string` | - | - |
| `hidden` | `boolean` | - | - |
| `inert` | `boolean` | - | - |
| `isDisabled` | `boolean` | - | Whether the link is disabled. |
| `autoFocus` | `boolean` | - | Whether the element should receive focus on render. |
| `rel` | `string` | - | The relationship between the linked resource and the current page. See [MDN](https://developer.mozilla.org/en-US/docs/Web/HTML/Attributes/rel). |
| `target` | `HTMLAttributeAnchorTarget` | - | The target window for the link. See [MDN](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/a#target). |
| `href` | `string` | - | A URL to link to. See [MDN](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/a#href). |
| `hrefLang` | `string` | - | Hints at the human language of the linked URL. See[MDN](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/a#hreflang). |
| `download` | `string \| boolean` | - | Causes the browser to download the linked URL. A string may be provided to suggest a file name. See [MDN](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/a#download). |
| `ping` | `string` | - | A space-separated list of URLs to ping when the link is followed. See [MDN](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/a#ping). |
| `referrerPolicy` | `HTMLAttributeReferrerPolicy` | - | How much of the referrer to send when following the link. See [MDN](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/a#referrerpolicy). |
| `routerOptions` | `undefined` | - | Options for the configured client side router. |
| `children` | `ReactNode` | - | - |
| `wrapWith` | `ReactElement<unknown, string \| JSXElementConstructor<any>>` | - | - |
| `ref` | `Ref<HTMLSpanElement>` | - | Allows getting a ref to the component instance. Once the component unmounts, React will set `ref.current` to `null` (or call the ref with `null` if you passed a callback ref). @see [React Docs](https://react.dev/learn/referencing-values-with-refs#refs-and-the-dom) |
| `key` | `Key` | - | - |
| `className` | `string` | - | The elements class name. |

### Events

| Property | Type | Default | Description |
| --- | --- | --- | --- |
| `onClick` | `((e: MouseEvent<FocusableElement, MouseEvent>) => void)` | - | **Not recommended – use `onPress` instead.** `onClick` is an alias for `onPress` provided for compatibility with other libraries. `onPress` provides additional event details for non-mouse interactions. |
| `onClickCapture` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onAuxClick` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onAuxClickCapture` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onContextMenu` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onContextMenuCapture` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onDoubleClick` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onDoubleClickCapture` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onMouseDown` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onMouseDownCapture` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onMouseEnter` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onMouseLeave` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onMouseMove` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onMouseMoveCapture` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onMouseOut` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onMouseOutCapture` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onMouseOver` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onMouseOverCapture` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onMouseUp` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onMouseUpCapture` | `MouseEventHandler<HTMLDivElement>` | - | - |
| `onTouchCancel` | `TouchEventHandler<HTMLDivElement>` | - | - |
| `onTouchCancelCapture` | `TouchEventHandler<HTMLDivElement>` | - | - |
| `onTouchEnd` | `TouchEventHandler<HTMLDivElement>` | - | - |
| `onTouchEndCapture` | `TouchEventHandler<HTMLDivElement>` | - | - |
| `onTouchMove` | `TouchEventHandler<HTMLDivElement>` | - | - |
| `onTouchMoveCapture` | `TouchEventHandler<HTMLDivElement>` | - | - |
| `onTouchStart` | `TouchEventHandler<HTMLDivElement>` | - | - |
| `onTouchStartCapture` | `TouchEventHandler<HTMLDivElement>` | - | - |
| `onPointerDown` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onPointerDownCapture` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onPointerMove` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onPointerMoveCapture` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onPointerUp` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onPointerUpCapture` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onPointerCancel` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onPointerCancelCapture` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onPointerEnter` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onPointerLeave` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onPointerOver` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onPointerOverCapture` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onPointerOut` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onPointerOutCapture` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onGotPointerCapture` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onGotPointerCaptureCapture` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onLostPointerCapture` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onLostPointerCaptureCapture` | `PointerEventHandler<HTMLDivElement>` | - | - |
| `onScroll` | `UIEventHandler<HTMLDivElement>` | - | - |
| `onScrollCapture` | `UIEventHandler<HTMLDivElement>` | - | - |
| `onWheel` | `WheelEventHandler<HTMLDivElement>` | - | - |
| `onWheelCapture` | `WheelEventHandler<HTMLDivElement>` | - | - |
| `onAnimationStart` | `AnimationEventHandler<HTMLDivElement>` | - | - |
| `onAnimationStartCapture` | `AnimationEventHandler<HTMLDivElement>` | - | - |
| `onAnimationEnd` | `AnimationEventHandler<HTMLDivElement>` | - | - |
| `onAnimationEndCapture` | `AnimationEventHandler<HTMLDivElement>` | - | - |
| `onAnimationIteration` | `AnimationEventHandler<HTMLDivElement>` | - | - |
| `onAnimationIterationCapture` | `AnimationEventHandler<HTMLDivElement>` | - | - |
| `onTransitionCancel` | `TransitionEventHandler<HTMLDivElement>` | - | - |
| `onTransitionCancelCapture` | `TransitionEventHandler<HTMLDivElement>` | - | - |
| `onTransitionEnd` | `TransitionEventHandler<HTMLDivElement>` | - | - |
| `onTransitionEndCapture` | `TransitionEventHandler<HTMLDivElement>` | - | - |
| `onTransitionRun` | `TransitionEventHandler<HTMLDivElement>` | - | - |
| `onTransitionRunCapture` | `TransitionEventHandler<HTMLDivElement>` | - | - |
| `onTransitionStart` | `TransitionEventHandler<HTMLDivElement>` | - | - |
| `onTransitionStartCapture` | `TransitionEventHandler<HTMLDivElement>` | - | - |
| `onFocus` | `((e: FocusEvent<Element, Element>) => void)` | - | Handler that is called when the element receives focus. |
| `onBlur` | `((e: FocusEvent<Element, Element>) => void)` | - | Handler that is called when the element loses focus. |
| `onFocusChange` | `((isFocused: boolean) => void)` | - | Handler that is called when the element's focus status changes. |
| `onKeyDown` | `((e: KeyboardEvent) => void)` | - | Handler that is called when a key is pressed. |
| `onKeyUp` | `((e: KeyboardEvent) => void)` | - | Handler that is called when a key is released. |
| `onPress` | `((e: PressEvent) => void)` | - | Handler that is called when the press is released over the target. |
| `onPressStart` | `((e: PressEvent) => void)` | - | Handler that is called when a press interaction starts. |
| `onPressEnd` | `((e: PressEvent) => void)` | - | Handler that is called when a press interaction ends, either over the target or when the pointer leaves the target. |
| `onPressChange` | `((isPressed: boolean) => void)` | - | Handler that is called when the press state changes. |
| `onPressUp` | `((e: PressEvent) => void)` | - | Handler that is called when a press is released over the target, regardless of whether it started on the target or not. |
| `onHoverStart` | `((e: HoverEvent) => void)` | - | Handler that is called when a hover interaction starts. |
| `onHoverEnd` | `((e: HoverEvent) => void)` | - | Handler that is called when a hover interaction ends. |
| `onHoverChange` | `((isHovering: boolean) => void)` | - | Handler that is called when the hover state changes. |

### Accessibility

| Property | Type | Default | Description |
| --- | --- | --- | --- |
| `aria-current` | `string` | - | - |
| `aria-label` | `string` | - | Defines a string value that labels the current element. |
| `aria-labelledby` | `string` | - | Identifies the element (or elements) that labels the current element. |
| `aria-describedby` | `string` | - | Identifies the element (or elements) that describes the object. |
| `aria-details` | `string` | - | Identifies the element (or elements) that provide a detailed, extended description for the object. |


## Guidelines

# Grundlagen

## Best practices

Achte bei Verwendung eines Links darauf, dass ...

- je nach Umgebung der richtige Link gewählt wird. Ein Inline Link wird
  automatisch in einem Textblock gesetzt. Bei farbigem Hintergrund muss die
  Color Light oder Dark selbst ausgewählt werden.
- Links standardmäßig im gleichen Tab geöffnet werden. User haben dann immer
  noch die Möglichkeit, die Links selbstgesteuert in einem neuen Tab zu öffnen.
- Externe Links sich immer in einem neuen Tab öffnen.
- Links nur als Navigationselement gedacht sind. Links können z. B. keine
  [Modals](/04-components/overlays/modal/overview) öffnen, keine Aktionen
  bestätigen und keine weiteren Informationen aufklappen lassen
  ([Accordion](/04-components/structure/accordion/overview)).
- nicht zu viele Links verwendet werden, um den User nicht durch die Anzahl zu
  verwirren.
- Links entweder einzeln stehen oder in einen Textblock integriert werden
  (Inline Link). Andernfalls ist es für den User schwieriger, den Link zu
  erkennen. Beispielsweise sollte ein Link nicht in der Überschrift stehen.

## Verwendung

Verwende einen Link, um ...

- den User zu einer neuen Seite zu navigieren.
- auf einen Ankerpunkt auf der Seite für eine Information zu scrollen.
- einen Download zu starten.
- eine externe Seite zu öffnen.

## Link vs. Button

Links und [Buttons](/04-components/actions/button/overview) werden häufig
verwechselt. Um die beiden besser unterscheiden zu können, hier ein paar
hilfreiche Anhaltspunkte.

  

**ℹ️ Info**

- zu einer anderen Seite zu navigieren.

    - zu einem Anker auf der Seite zu scrollen.

    - eine externe Seite zu öffnen.

    - einen Download zu starten.

  

**ℹ️ Info**

- eine Aktion auszuführen oder ein Event zu starten, ohne die Seite zu
    verlassen.

    - Formulare zu speichern oder zurückzusetzen.

    - in einem [Modals](/04-components/overlays/modal) oder [OffCanvas](/04-components/overlays/modal) zu navigieren und
    Aktionen auszuwählen.

---

# Anwendung

## Position

Links sind ein zentrales Navigationselement für die User. Daher sollte deren
Platzierung sorgfältig überlegt werden. Beispiele für geeignete Stellen sind:

- In einer [Section](/04-components/structure/section/overview) können Links in
  der oberen rechten Ecke neben der
  [Heading](/04-components/content/heading/overview) platziert werden. Diese
  Position eignet sich besonders für Links, die inhaltlich stark mit der Section
  verbunden sind, und wenn nur ein einzelner Link benötigt wird.
- Im unteren Bereich einer Section oder eines
  [Textblocks](/04-components/content/text/overview) können ein oder mehrere
  Links angezeigt werden. Diese sollten sich auf den vorangehenden Text
  beziehen.
- Inline Links werden direkt im [Text](/04-components/content/text/overview)
  eingefügt.

  

**✅ Do**

Die Section verfügt über einen speziellen Bereich in der Nähe der Heading,
    in dem Links platziert werden können.

```tsx
import {
  Header,
  Heading,
  Link,
  Section,
  Text,
} from "@mittwald/flow-react-components";

<Section>
  <Header>
    <Heading>Heading 2</Heading>
    <Link href="#">Textlink</Link>
  </Header>
  <Text>
    Lorem ipsum dolor sit amet, consectetur adipiscing elit.
  </Text>
</Section>
```

  

**✅ Do**

Links können am Ende einer Section oder eines Textblocks angezeigt werden.

```tsx
import {
  Header,
  Heading,
  Link,
  Section,
  Text,
} from "@mittwald/flow-react-components";

<Section>
  <Header>
    <Heading>Heading 2</Heading>
  </Header>
  <Text>
    Lorem ipsum dolor sit amet, consectetur adipiscing elit.
  </Text>
  <Link href="#">Textlink</Link>
</Section>
```

---

# Inhalt

## Interne und externe Links

Interne Links öffnen sich immer im dem Tab, in dem der User sich gerade
befindet. Der User kann jedoch selbst entscheiden, ob er den Link lieber in
einem neuen Tab öffnen möchte. Externe Links – also Verweise auf eine andere
Domain – öffnen sich hingegen immer in einem neuen Tab. Um das Verhalten dem
User zu verdeutlichen, wird automatisch das `IconExternalLink` angezeigt werden,
wenn `target="_blank"` gesetzt ist.

---

# Writing guidelines

Der **Linktext** ist der wichtigste Bestandteil eines Links. Versuche daher auf
folgendes zu achten:

- Verwende für Links, die auf dieselbe Seite verweisen, immer denselben Text.
  Unterschiedliche Zielseiten sollten unterschiedliche Linktexte haben, um
  Verwirrung zu vermeiden.
- Vermeide generische Formulierungen wie „Klick hier“. Der Linktext sollte klar
  vermitteln, wohin der Link führt oder was dort zu erwarten ist.
- Formuliere Linktexte so präzise wie möglich, damit sofort erkennbar ist, wohin
  der Link führt. Allgemeine Formulierungen wie „Erfahre mehr“ sollten vermieden
  werden, da diese oft überflüssig sind. Falls nötig, ergänze „Erfahre mehr“ mit
  spezifischen Informationen, z. B. „Erfahre mehr über Flow“.
- Wenn ein Link in einem Satz vorkommt, verlinke nur den Teil des Satzes, der
  direkt auf das Ziel hinweist. Der gesamte Satz sollte nicht als Link markiert
  werden. Vermeide es, den Link in mehrere kleinere Teile innerhalb des Satzes
  aufzuteilen; stattdessen sollte ein zusammenhängender Link innerhalb des
  Satzes zu finden sein.
- Halte Linktexte so kurz wie möglich, um Zeilenumbrüche zu vermeiden. Ein
  einzelnes Wort oder eine kurze Phrase sind ideal.
- Setze am Ende des Linktextes keinen Punkt. Eine Ausnahme bilden Fragezeichen,
  falls sie dem Satzbau entsprechen.

  

**✅ Do**

Der Link „Erfahre mehr über Links“ kann auch alleine stehend vom User
    verstanden werden.

```tsx
import {
  Link,
  Text,
} from "@mittwald/flow-react-components";

<>
  <Text>
    Links sind wichte Navigationselemente innerhalb von
    Benutzeroberflächen.
  </Text>
  <Link href="#">Erfahre mehr über Links</Link>
</>
```

  

**⛔️ Don't**

Links müssen einzeln verstanden werden. „Erfahre mehr“ oder „Klick hier“
    sind nicht alleine verständlich.

```tsx
import {
  Link,
  Text,
} from "@mittwald/flow-react-components";

<>
  <Text>
    Links sind wichte Navigationselemente innerhalb von
    Benutzeroberflächen.
  </Text>
  <Link href="#">Erfahre mehr</Link>
</>
```

  

**✅ Do**

Inline Links sollten so kurz wie möglich, aber so lang sein, dass der User
    versteht, wohin sie führen.

```tsx
import {
  Link,
  Text,
} from "@mittwald/flow-react-components";

<Text>
  Mit Hilfe des <Link href="#">Onboardings</Link> kannst du
  direkt loslegen.
</Text>
```

  

**⛔️ Don't**

Markiere keine ganzen Sätze als Inline Link.

```tsx
import {
  Link,
  Text,
} from "@mittwald/flow-react-components";

<Text>
  <Link href="#">
    Mit Hilfe des Onboardings kannst du direkt loslegen.
  </Link>
</Text>
```

# Accessibility

Achte beim Link darauf, dass er gut von Screenreadern erfasst wird. Ein Link
muss auch isoliert betrachtet verständlich sein. Das ist nicht der Fall, wenn
der Linktext nur „hier klicken“ oder „mehr Informationen“ lautet. Bei Bedarf
sollte ein ARIA-Label hinzugefügt werden, um sicherzustellen, dass der Link
korrekt interpretiert wird, falls der Text allein nicht ausreicht.

# Color

Achte bei den Colors Light und Dark auf genügend Kontrast zum Hintergrund. Es
wird empfohlen, die Color in Light zu verwenden, wenn der HSL Lightness-Wert des
Hintergrunds weniger als 50 ist. Die Color Dark wird für Hintergründe empfohlen,
die einen HSL Lightness-Wert von größer als 50 haben. Für beide Colors gilt: Je
weiter der HSL Lightness-Wert von 50 entfernt ist, desto besser ist der
Kontrast.

  

**✅ Do**

Die Color Light kommt besonders gut auf sehr dunklen Hintergründen zur
    Geltung. Verwende sie auf Hintergründen mit einem HSL Lightness-Wert von
    weniger als 50.

```tsx
import { Link } from "@mittwald/flow-react-components";

<Link href="#" color="light">
  Light
</Link>
```

  

**✅ Do**

Color Dark kommt besonders gut auf sehr hellen Hintergründen zur Geltung.
    Verwende sie auf Hintergründen mit einem HSL Lightness-Wert von über 50.

```tsx
import { Link } from "@mittwald/flow-react-components";

<Link href="#" color="dark">
  Dark
</Link>
```

