Files
livewire-material/resources/views/components/rich-tooltip.blade.php
T
Andreas Reinhold / reiniandClaude Opus 5 648ad8efaf
tests / lint (push) Successful in 1m3s
tests / feature (8.4) (push) Failing after 1m5s
tests / feature (8.5) (push) Failing after 1m4s
tests / browser (chrome, chromium) (push) Failing after 1m5s
tests / browser (firefox, firefox) (push) Failing after 1m1s
tests / browser (safari, webkit) (push) Failing after 1m1s
Add the snackbar, badges, rich tooltips, alerts, stats and empty states
<x-toast> hosts the snackbar queue for the Toasts concern and
window.materialToast(), one at a time, paused on hover and focus, with
an optional action; it listens from the moment its script loads, so a
toast dispatched before Alpine starts is shown rather than lost.
<x-badge> is M3's dot and count, plus a tonal or outlined status label;
<x-rich-tooltip> is transient or persistent; <x-alert>, <x-stat> and
<x-empty-state> are built from M3's parts.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01V9NnLxnPp8vaaurb3Z1MFy
2026-09-13 06:59:40 +02:00

63 lines
3.0 KiB
PHP

{{-- An M3 rich tooltip: a few lines of context for a control, with an optional subhead and actions.
<x-rich-tooltip title="Expiry" text="Recipients lose access after this time. Admins can change the longest allowed.">
<x-button icon="help" aria-label="About expiry" />
<x-slot:actions><x-button label="Learn more" link="/help/expiry" /></x-slot:actions>
</x-rich-tooltip>
It wraps its trigger. By default it shows on hover and keyboard focus like a plain tooltip;
`persistent` makes it open on press instead and stay until a press elsewhere or Escape the
form M3 asks for when it has actions. The bubble is a popover in surface-container with a
medium corner and elevation 2, 312px at most, placed by anchor positioning on `side`.
RichTooltipTokens (androidx Compose Material 3, Apache-2.0): title-small subhead and body-medium
text in on-surface-variant, label-large actions in primary. --}}
@props([
'title' => null,
'text' => null,
'side' => 'bottom',
'persistent' => false,
])
@php
$side = in_array($side, ['top', 'bottom', 'left', 'right'], true) ? $side : 'bottom';
$key = \Illuminate\Support\Str::lower(\Illuminate\Support\Str::random(10));
$anchor = "--material-rich-tooltip-{$key}";
@endphp
<span
{{ $attributes->class('inline-flex') }}
style="anchor-name: {{ $anchor }}"
x-data="materialRichTooltip({{ $persistent ? 'true' : 'false' }})"
>
{{ $trigger ?? $slot }}
<span
x-ref="bubble"
id="material-rich-tooltip-{{ $key }}"
popover="{{ $persistent ? 'auto' : 'manual' }}"
role="{{ $persistent ? 'dialog' : 'tooltip' }}"
@if ($title) aria-label="{{ $title }}" @endif
style="position-anchor: {{ $anchor }}"
@class([
'm-0 w-max max-w-78 overflow-visible border-0 rounded-corner-md bg-surface-container px-4 pt-3 pb-2 text-start whitespace-normal shadow-elevation-2 [inset:auto]',
'opacity-0 transition-[opacity,display,overlay] transition-discrete duration-(--md-sys-motion-effects-fast-duration) ease-effects-fast open:opacity-100 starting:open:opacity-0',
'my-1 [position-area:bottom_span-right] [position-try-fallbacks:flip-block,flip-inline]' => $side === 'bottom',
'my-1 [position-area:top_span-right] [position-try-fallbacks:flip-block,flip-inline]' => $side === 'top',
'mx-1 [position-area:left_span-bottom] [position-try-fallbacks:flip-inline,flip-block]' => $side === 'left',
'mx-1 [position-area:right_span-bottom] [position-try-fallbacks:flip-inline,flip-block]' => $side === 'right',
])
>
@if ($title)
<span class="mb-1 block type-title-sm text-on-surface-variant">{{ $title }}</span>
@endif
<span class="block pb-2 type-body-md text-on-surface-variant">{{ $text }}</span>
@isset($actions)
<span class="-ms-3 flex flex-wrap gap-2">{{ $actions }}</span>
@endisset
</span>
</span>