Modal 1.2.0
<velin-modal> is a centered dialog overlay with header, body, and optional footer slot.
In 1.2.0, open/close lifecycle uses Fokus-manager for background inert and body scroll lock. English: Modal
Reifegrad: Dokumentiert als stabil in VelinStyle 1.2.0. Design Intelligence (Plan / Review / Agent-Meta) ist separat und Beta / Grundlage wo entsprechend angegeben.
Wann verwenden
- Blocking tasks that need a titled panel (forms, details, multi-step confirmations with custom UI).
- Content that benefits from a footer slot for primary/secondary actions.
- Prefer
<velin-modal>over ad-hoc fixed overlays so Fokus trap, Escape, and inert stacking stay consistent.
Wann nicht verwenden
- Simple alert / confirm / prompt — use
<velin-dialog>(promise API + native<dialog>). - Non-blocking tips — use Tooltip or Popover.
- Side navigation or filters — use Schublade or Sheet.
Einfaches Modal
Öffnen with open() or the open attribute. Set the sichtbar title with title (HTML-escaped). Standard slot is the body; use slot="footer" for actions.
This is a basic modal with a title and body content.
<button type="button" class="velin-btn velin-btn--primary"
onclick="document.getElementById('myModal').open()">
Open Modal
</button>
<velin-modal id="myModal" title="Modal title">
<p>This is a basic modal body.</p>
<button type="button" class="velin-btn velin-btn--primary" slot="footer"
onclick="document.getElementById('myModal').close()">Done</button>
</velin-modal>
Footer-Slot
Place action Buttons in the named footer slot. They render in the dialog footer bar.
<velin-modal id="confirmUi" title="Save changes?">
<p>Unsaved edits will be lost if you leave.</p>
<button type="button" class="velin-btn velin-btn--outline" slot="footer"
onclick="this.closest('velin-modal').close()">Cancel</button>
<button type="button" class="velin-btn velin-btn--primary" slot="footer">Save</button>
</velin-modal>
Barrierefreiheit
- Inner panel:
role="dialog",aria-modal="true". - With
title: labelled viaaria-labelledby. Withouttitle: usesaria-label(attribute or Standard"Dialog"); title node is visually verborgen. - Built-in close control:
aria-label="Schließen"(part="close"). - Beim Öffnen:
Fokus-managersaves Fokus, sets siblinginert, locks body overflow; Fokus moves to the first focusable in the shadow tree. - Tab / Shift+Tab trap inside the shadow root; Escape calls
close(). - Beim Schließen / Disconnect: clears inert + scroll lock for this host and restores previous Fokus.
close()dispatches bubblingvelin-close.- Backdrop click (overlay target only) closes the modal.
Dark Mode, Responsivität, Bewegung, RTL
- Dark Mode / Themes: surfaces use
--velin-color-surface-bright, borders, and text tokens — follow the active theme. - Responsiv: dialog width is
min(90vw, 32rem); max height85vhwith a scrollable body. - Bewegung: overlay and dialog transitions are disabled under
prefers-reduced-motion: reduce. - RTL: layout uses logical padding/sizing; no side-specific transform.
API
Attribut
| Attribut | Typ | Beschreibung |
|---|---|---|
open | Boolean | Observed — presence opens the modal |
title | String | Header title (escaped); drives aria-labelledby when set |
aria-label | String | Fallback name when title is empty |
Slots & parts
| Name | Art | Beschreibung |
|---|---|---|
| (Standard) | Slot | Modal body |
footer | Slot | Footer actions |
overlay, dialog, header, body, footer, close | CSS parts | Shadow styling hooks |
Methoden & events
| API | Beschreibung |
|---|---|
open() | Sets open |
close() | Removes open; dispatches velin-close (bubbles) |
velin-close | Fired from close() |
CSS-Variablen
| Variable | Rolle |
|---|---|
--velin-z-modal | Overlay-Z-Index (Standard 500) |
--velin-color-overlay | Backdrop |
--velin-color-surface-bright | Dialog background |
--velin-radius-lg | Dialog radius |
--velin-shadow-xl | Dialog shadow |
Best practices & pitfalls
- Call
open()/close()(or toggleopen) — do not invent asizeorheadingattribute; they are not in the Komponente. - Always provide a clear
titleoraria-labelfor assistive tech. - Listen for
velin-close, not a Komponente-prefixed close event. - Stacking is supported: each host registers its own inert layer; removing an open modal from the DOM still clears inert/overflow for that host.
- Attribut bridge:
velin-modalon a plain element can bridge to<velin-modal>via the runtime attribute registry — prefer the custom element in new code.