5.4: <x-portal.empty-state> + admin/press-releases/index umgestellt

Zweite Struktur-Component: buendelt den empty-stage-Block (runder Icon-Rahmen
+ Titel + Subtext + optionale Aktionen). Props: title, subtitle, variant
(default|warm|err); Slots :icon und :actions.

Erst-Umstellung: die zwei Leerzustaende der Admin-PM-Liste (gefiltert = warm
mit 'Filter zuruecksetzen', leer = Standard mit 'Neue PM anlegen'). Weitere
Vorkommen (customer/press-releases, customer/press-kits) folgen nach Sicht-
pruefung. 36 Tests gruen.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
Kevin Adametz 2026-07-01 11:05:19 +00:00
parent feda8be4d3
commit 077d313baa
2 changed files with 55 additions and 22 deletions

View file

@ -0,0 +1,36 @@
@props([
/** Überschrift (bereits übersetzt übergeben) */
'title' => '',
/** Erläuternder Text unter der Überschrift */
'subtitle' => '',
/** Icon-Farbvariante: default | warm (gefilterte Leerzustände) | err */
'variant' => 'default',
])
{{--
Zentrierter Leerzustand für Tabellen/Listen. Ersetzt den mehrfach kopierten
empty-stage-Block. Slots:
<x-slot:icon> – Icon (flux:icon.* oder inline-<svg>) im runden Rahmen
<x-slot:actions> – optionale Buttons unter dem Text
--}}
<div class="empty-stage">
<div @class(['empty-ico', 'warm' => $variant === 'warm', 'err' => $variant === 'err'])>
{{ $icon ?? '' }}
</div>
@if (filled($title))
<h3 class="empty-title">{{ $title }}</h3>
@endif
@if (filled($subtitle))
<p class="empty-sub">{{ $subtitle }}</p>
@endif
@isset($actions)
<div class="flex items-center gap-2.5 mt-6">
{{ $actions }}
</div>
@endisset
</div>

View file

@ -1026,41 +1026,38 @@ new #[Layout('components.layouts.app'), Title('Pressemitteilungen')] class exten
<flux:table.row>
<flux:table.cell colspan="7">
@if ($hasAnyFilter)
<div class="empty-stage">
<div class="empty-ico warm">
<x-portal.empty-state
variant="warm"
:title="__('Keine Pressemitteilungen mit diesen Filtern')"
:subtitle="__('Passen Sie die Filter an oder setzen Sie alle Filter zurück, um wieder alle PMs zu sehen.')"
>
<x-slot:icon>
<svg width="28" height="28" viewBox="0 0 24 24" fill="none">
<path d="M4 6h16M7 12h10M10 18h4" stroke="currentColor" stroke-width="1.8"
stroke-linecap="round" />
</svg>
</div>
<h3 class="empty-title">
{{ __('Keine Pressemitteilungen mit diesen Filtern') }}
</h3>
<p class="empty-sub">
{{ __('Passen Sie die Filter an oder setzen Sie alle Filter zurück, um wieder alle PMs zu sehen.') }}
</p>
<div class="flex items-center gap-2.5 mt-6">
</x-slot:icon>
<x-slot:actions>
<flux:button variant="primary" wire:click="resetFilters">
{{ __('Filter zurücksetzen') }}
</flux:button>
</div>
</div>
</x-slot:actions>
</x-portal.empty-state>
@else
<div class="empty-stage">
<div class="empty-ico">
<x-portal.empty-state
:title="__('Noch keine Pressemitteilungen')"
:subtitle="__('Sobald Kunden PMs anlegen oder einreichen, erscheinen sie hier zur Bearbeitung.')"
>
<x-slot:icon>
<flux:icon.newspaper class="size-7" />
</div>
<h3 class="empty-title">{{ __('Noch keine Pressemitteilungen') }}</h3>
<p class="empty-sub">
{{ __('Sobald Kunden PMs anlegen oder einreichen, erscheinen sie hier zur Bearbeitung.') }}
</p>
<div class="flex items-center gap-2.5 mt-6">
</x-slot:icon>
<x-slot:actions>
<flux:button variant="primary" icon="plus"
href="{{ route('admin.press-releases.create') }}" wire:navigate>
{{ __('Neue PM anlegen') }}
</flux:button>
</div>
</div>
</x-slot:actions>
</x-portal.empty-state>
@endif
</flux:table.cell>
</flux:table.row>