Ein Header-Dropdown oben rechts (Desktop) bzw. im Mobile-Header zeigt fuer alle Kunden-Panel-User den aktuellen Status: aktuelle Buchung/Tarif, verbleibendes PM-Kontingent und Credit-Guthaben. Ohne aktive Buchung weist es direkt auf die noetige Buchung hin und verlinkt die Buchungsseite. CustomerStatusSummary buendelt die Anzeige-Werte ueber die oeffentliche User-API (Gating bleibt Single Source of Truth im Modell); die anonyme Blade-Komponente x-customer.status-menu rendert das Dropdown. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
84 lines
4.7 KiB
PHP
84 lines
4.7 KiB
PHP
@props(['user' => null])
|
|
|
|
@php
|
|
$user ??= auth()->user();
|
|
$status = $user ? \App\Services\Customer\CustomerStatusSummary::fromUser($user) : null;
|
|
@endphp
|
|
|
|
@if ($status)
|
|
<flux:dropdown position="bottom" align="end">
|
|
{{-- Trigger: kompaktes Status-Badge in der Topbar --}}
|
|
<button
|
|
type="button"
|
|
class="inline-flex items-center gap-2 rounded-full border border-[color:var(--color-bg-rule)] bg-[color:var(--color-bg-card)] px-3 py-1.5 text-[12px] font-semibold text-[color:var(--color-ink)] transition-colors hover:border-[color:var(--color-hub)] hover:text-[color:var(--color-hub)]"
|
|
aria-label="{{ __('Mein Status & Guthaben') }}"
|
|
>
|
|
<flux:icon name="wallet" variant="micro" class="size-3.5 text-[color:var(--color-hub)]" />
|
|
<span class="whitespace-nowrap font-mono">{{ $status->badgeLabel() }}</span>
|
|
<flux:icon name="chevron-down" variant="micro" class="size-3 text-[color:var(--color-ink-3)]" />
|
|
</button>
|
|
|
|
<flux:menu class="w-[268px]">
|
|
{{-- Aktuelle Buchung --}}
|
|
<div class="px-3 pt-2 pb-1">
|
|
<div class="mb-1 text-[10px] font-semibold uppercase tracking-[0.16em] text-[color:var(--color-ink-3)]">
|
|
{{ __('Aktuelle Buchung') }}
|
|
</div>
|
|
<div class="flex items-center justify-between gap-2">
|
|
<span class="text-[13.5px] font-semibold text-[color:var(--color-ink)]">
|
|
{{ $status->bookingLabel() }}
|
|
@if ($status->billingIntervalLabel())
|
|
<span class="font-normal text-[color:var(--color-ink-3)]">· {{ $status->billingIntervalLabel() }}</span>
|
|
@endif
|
|
</span>
|
|
@if ($status->hasActiveBooking)
|
|
<span class="inline-flex items-center gap-1 text-[11px] font-semibold text-[color:var(--color-ok)]">
|
|
<span class="size-1.5 rounded-full bg-[color:var(--color-ok)]"></span>{{ __('aktiv') }}
|
|
</span>
|
|
@else
|
|
<span class="text-[11px] font-semibold text-[color:var(--color-warn)]">{{ __('keine') }}</span>
|
|
@endif
|
|
</div>
|
|
</div>
|
|
|
|
<flux:menu.separator />
|
|
|
|
{{-- Kennzahlen: PM-Kontingent & Credits --}}
|
|
<div class="grid grid-cols-2 gap-px bg-[color:var(--color-bg-rule)] mx-3 my-1 rounded-[5px] overflow-hidden border border-[color:var(--color-bg-rule)]">
|
|
<div class="bg-[color:var(--color-bg-card)] p-2.5">
|
|
<div class="text-[10px] font-semibold uppercase tracking-[0.14em] text-[color:var(--color-ink-3)]">
|
|
{{ __('PMs frei') }}
|
|
</div>
|
|
<div class="mt-0.5 text-[18px] font-bold leading-none text-[color:var(--color-ink)]">
|
|
@if ($status->unlimitedQuota)
|
|
∞
|
|
@else
|
|
{{ $status->quotaRemaining }}<span class="text-[12px] font-medium text-[color:var(--color-ink-3)]"> / {{ $status->quotaTotal }}</span>
|
|
@endif
|
|
</div>
|
|
</div>
|
|
<div class="bg-[color:var(--color-bg-card)] p-2.5">
|
|
<div class="text-[10px] font-semibold uppercase tracking-[0.14em] text-[color:var(--color-ink-3)]">
|
|
{{ __('Guthaben') }}
|
|
</div>
|
|
<div class="mt-0.5 text-[18px] font-bold leading-none text-[color:var(--color-ink)]">
|
|
{{ $status->creditBalance }}<span class="text-[12px] font-medium text-[color:var(--color-ink-3)]"> Cr</span>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
@unless ($status->hasActiveBooking)
|
|
<div class="mx-3 my-1.5 flex items-start gap-1.5 rounded-[4px] border border-[color:color-mix(in_srgb,var(--color-warn)_45%,transparent)] bg-[color:var(--color-warn-soft,transparent)] px-2.5 py-2 text-[11px] leading-[1.45] text-[color:var(--color-ink-2)]">
|
|
<flux:icon name="exclamation-triangle" variant="micro" class="mt-0.5 size-3.5 flex-shrink-0 text-[color:var(--color-warn)]" />
|
|
<span>{{ __('Zum Veröffentlichen brauchst du eine Buchung.') }}</span>
|
|
</div>
|
|
@endunless
|
|
|
|
<flux:menu.separator />
|
|
|
|
<flux:menu.item :href="route('me.bookings.index')" icon="shopping-bag" wire:navigate>
|
|
{{ __('Buchungen & Add-ons') }}
|
|
</flux:menu.item>
|
|
</flux:menu>
|
|
</flux:dropdown>
|
|
@endif
|