b2in/resources/views/livewire/admin/cms/display-version-editor.blade.php

304 lines
16 KiB
PHP
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<div>
{{-- Header --}}
<div class="flex items-center justify-between mb-6">
<div class="flex items-center gap-4">
<flux:button :href="route('admin.cms.display-modules')" wire:navigate variant="ghost" icon="arrow-left" size="sm">
{{ __('Zurück') }}
</flux:button>
<div>
<div class="flex items-center gap-3">
<flux:heading size="xl">{{ $version->name }}</flux:heading>
<flux:badge color="{{ match($version->type->value) {
'video-display' => 'purple',
'b2in' => 'blue',
'offers' => 'amber',
} }}">
{{ $version->type->label() }}
</flux:badge>
</div>
<flux:subheading>{{ __('Modul bearbeiten') }}</flux:subheading>
</div>
</div>
<div class="flex items-center gap-3">
@if($version->type->value === 'b2in')
<div class="flex items-center gap-2 px-3 py-1.5 rounded-lg bg-zinc-100 dark:bg-zinc-800 border border-zinc-200 dark:border-zinc-700">
<flux:icon.sun class="w-4 h-4 text-amber-500" />
<flux:switch wire:click="toggleTheme"
:checked="($version->settings['theme'] ?? 'dark') === 'dark'" />
<flux:icon.moon class="w-4 h-4 text-indigo-400" />
</div>
@endif
<flux:button wire:click="openSettingsModal" icon="cog-6-tooth" variant="ghost">
{{ __('Einstellungen') }}
</flux:button>
</div>
</div>
@if (session()->has('success'))
<x-success-alert>
{{ session('success') }}
</x-success-alert>
@endif
{{-- Name bearbeiten --}}
<flux:card class="mb-6">
<form wire:submit.prevent="saveName" class="flex items-end gap-4">
<div class="flex-1">
<flux:input wire:model="versionName" label="Modulname" />
</div>
<flux:button type="submit" variant="primary" size="sm">{{ __('Speichern') }}</flux:button>
</form>
</flux:card>
{{-- Modul-Vorschau --}}
<flux:card class="mb-6">
<div class="mb-4 flex items-center justify-between gap-3">
<div>
<flux:heading size="lg">{{ __('Modul-Vorschau') }}</flux:heading>
<flux:subheading>{{ __('Live gerenderte Einzelmodul-Vorschau im Display-Player') }}</flux:subheading>
</div>
<a href="{{ $this->modulePreviewUrl() }}"
target="_blank"
class="inline-flex items-center gap-1 text-xs text-blue-600 hover:underline dark:text-blue-400">
<flux:icon.arrow-top-right-on-square class="w-3 h-3" />
{{ __('Vollbild-Vorschau') }}
</a>
</div>
<div class="mx-auto aspect-[9/16] w-full max-w-[320px] overflow-hidden rounded-xl border border-zinc-200 bg-black shadow-sm dark:border-zinc-700">
<iframe
wire:key="module-preview-{{ $previewFrameRefreshCounter }}"
src="{{ $this->modulePreviewUrl() }}"
class="h-full w-full border-0"
loading="lazy"
title="{{ __('Modul-Vorschau') }}"
></iframe>
</div>
</flux:card>
{{-- Type-specific content sections --}}
@if($version->type->value === 'video-display')
@include('livewire.admin.cms.partials.version-editor-video', ['items' => $items])
@elseif($version->type->value === 'b2in')
@include('livewire.admin.cms.partials.version-editor-b2in', ['items' => $items])
@elseif($version->type->value === 'offers')
@include('livewire.admin.cms.partials.version-editor-offers', ['items' => $items])
@endif
{{-- Module-level metadata --}}
<flux:card class="mt-8 mb-6">
<form wire:submit.prevent="saveSettings">
<div class="space-y-6">
<div>
<flux:heading size="lg">{{ __('Meta-Einstellungen für dieses Modul') }}</flux:heading>
<flux:subheading>{{ __('Diese Werte gelten für die gesamte Media-Playlist bzw. alle Slides dieses Moduls.') }}</flux:subheading>
</div>
@include('livewire.admin.cms.partials.version-editor-settings', ['context' => 'inline'])
<div class="flex justify-end">
<flux:button type="submit" variant="primary" size="sm">
{{ __('Meta-Einstellungen speichern') }}
</flux:button>
</div>
</div>
</form>
</flux:card>
{{-- Item Modal --}}
<flux:modal :open="$showItemModal" wire:model="showItemModal" class="w-full max-w-5xl">
<form wire:submit.prevent="saveItem">
<div class="space-y-6">
<div>
<flux:heading size="lg">{{ $itemId ? __('Inhalt bearbeiten') : __('Inhalt hinzufügen') }}</flux:heading>
</div>
{{-- Video fields --}}
@if($itemType === 'video')
<livewire:admin.cms.display-media-picker
:value="null"
field="videoFilename"
type="video"
label="Video aus Mediathek"
:key="'picker-video-' . ($itemId ?? 'new')" />
<flux:input wire:model="videoFilename" label="Video-Pfad / URL" placeholder="Wird automatisch gesetzt oder manuell eingeben..."
description="Über die Mediathek auswählen oder direkt Pfad/URL eingeben." />
<flux:input wire:model="videoTitle" label="Titel (optional)" placeholder="z.B. Herbst Kollektion 2025" />
<flux:input wire:model="videoPosition" type="number" min="0" max="100" label="Position (%)"
description="Vertikale Position im Video (0 = oben, 100 = unten)" />
<flux:checkbox wire:model="videoIsActive" label="Aktiv" />
@endif
{{-- Footer fields --}}
@if($itemType === 'footer')
<flux:input wire:model="footerHeadline" label="Überschrift" placeholder="z.B. Beratung & Termin" />
<flux:input wire:model="footerSubline" label="Unterzeile" placeholder="z.B. Jetzt Termin vereinbaren." />
<flux:input wire:model="footerUrl" label="URL (optional)" placeholder="https://..."
description="Leer = kein QR-Code. Mit URL = QR-Code wird generiert." />
<flux:checkbox wire:model="footerIsActive" label="Aktiv" />
@endif
{{-- Media fields (B2in) --}}
@if($itemType === 'media')
<flux:select wire:model="mediaType" label="Medientyp">
<option value="image">Bild</option>
<option value="video">Video</option>
</flux:select>
<flux:select wire:model="mediaCategory" label="Kategorie">
<option value="immobilien">Immobilien</option>
<option value="moebel">Möbel</option>
</flux:select>
<livewire:admin.cms.display-media-picker
:value="null"
field="mediaUrl"
:type="$mediaType === 'video' ? 'video' : 'image'"
label="Aus Mediathek"
:key="'picker-media-' . ($itemId ?? 'new')" />
<flux:input wire:model="mediaUrl" label="Medien-URL" placeholder="Wird automatisch gesetzt oder manuell eingeben..."
description="Über die Mediathek auswählen oder direkt URL eingeben." />
<flux:input wire:model="mediaHeadline" label="Überschrift" placeholder="z.B. Ihr Zuhause. Weltweit." />
<flux:input wire:model="mediaSubline" label="Unterzeile" placeholder="z.B. Beratung und Vermittlung." />
@if($mediaType === 'image')
<flux:input wire:model="mediaDuration" type="number" min="1" max="120" label="Dauer (Sekunden)"
description="Nur für Bilder Videos spielen bis zum Ende." />
@endif
<flux:checkbox wire:model="mediaIsActive" label="Aktiv" />
@endif
{{-- Slide fields (Offers) --}}
@if($itemType === 'slide')
{{-- Basis --}}
<flux:select wire:model.live="slideType" label="Slide-Typ">
<option value="intro">Intro</option>
<option value="product-hero">Produkt-Hero</option>
<option value="product-details">Produkt-Details</option>
<option value="product-impulse">Produkt-Impuls</option>
</flux:select>
<flux:input wire:model="slideDuration" type="number" min="1000" label="Dauer (ms)" />
<livewire:admin.cms.display-media-picker
:value="null"
field="slideImageUrl"
type="image"
label="Bild aus Mediathek"
:key="'picker-slide-' . ($itemId ?? 'new')" />
<flux:input wire:model="slideImageUrl" label="Bild-URL" placeholder="Wird automatisch gesetzt oder manuell eingeben..."
description="Über die Mediathek auswählen oder direkt URL eingeben." />
<flux:input wire:model="slideBadge" label="Badge-Text" placeholder="z.B. Einzelstück" />
<flux:input wire:model="slideEyebrow" label="Eyebrow" placeholder="z.B. Hersteller: Sudbrock" />
<flux:input wire:model="slideTitle" label="Titel" placeholder="z.B. GOYA Sideboard" />
{{-- Intro-spezifisch --}}
@if($slideType === 'intro')
<flux:input wire:model="slideDisclaimer" label="Disclaimer" placeholder="z.B. Zwischenverkauf vorbehalten" />
<flux:checkbox wire:model="slideShowBrandText" label="Brand-Text anzeigen" />
@if($slideShowBrandText)
<flux:input wire:model="slideBrandTagline" label="Brand-Tagline" placeholder="z.B. Planung • Beratung • Lieferung & Montage" />
@endif
@endif
{{-- Product-Hero --}}
@if($slideType === 'product-hero')
<flux:input wire:model="slidePrice" label="Preis" placeholder="z.B. 489 €" />
<flux:input wire:model="slideOriginalPrice" label="Originalpreis" placeholder="z.B. statt 4.744 €" />
@endif
{{-- Product-Details --}}
@if($slideType === 'product-details')
<div>
<flux:heading size="sm" class="mb-2">{{ __('Aufzählungspunkte') }}</flux:heading>
<div class="space-y-2">
@foreach($slideBullets as $i => $bullet)
<div class="flex items-center gap-2" wire:key="bullet-{{ $i }}">
<flux:input wire:model="slideBullets.{{ $i }}" placeholder="Punkt {{ $i + 1 }}" class="flex-1" />
<flux:button wire:click="removeBullet({{ $i }})" size="xs" variant="ghost" icon="x-mark" class="text-red-500"></flux:button>
</div>
@endforeach
</div>
<flux:button wire:click="addBullet" size="xs" variant="ghost" icon="plus" class="mt-2">
{{ __('Punkt hinzufügen') }}
</flux:button>
</div>
@endif
{{-- Product-Impulse --}}
@if($slideType === 'product-impulse')
<flux:input wire:model="slideSubline" label="Subline" placeholder="z.B. Heute mitnehmen" />
<flux:input wire:model="slidePrice" label="Preis" placeholder="z.B. 199 €" />
<flux:input wire:model="slideTagText" label="Tag-Text" placeholder="z.B. Im Store verfügbar" />
@endif
{{-- QR --}}
<div class="border-t border-zinc-200 dark:border-zinc-700 pt-4 mt-2">
<flux:heading size="sm" class="mb-3">{{ __('QR-Code & Kontakt') }}</flux:heading>
<div class="space-y-4">
<flux:input wire:model="slideQrUrl" label="QR-URL" placeholder="z.B. https://cabinet-bielefeld.de" />
<flux:input wire:model="slideQrTitle" label="QR-Titel" placeholder="z.B. Reservieren" />
<flux:input wire:model="slideContact" label="Kontakt" placeholder="z.B. 0521 98620100 / Tel. oder WhatsApp" />
</div>
</div>
<flux:checkbox wire:model="slideIsActive" label="Aktiv" />
@endif
<div class="space-y-3 border-t border-zinc-200 pt-6 dark:border-zinc-700">
<div>
<flux:heading size="sm">{{ __('Einzel-Vorschau im Bearbeiten-Dialog') }}</flux:heading>
<flux:subheading>{{ __('Zeigt nur den aktuell bearbeiteten Inhalt im Display-Player') }}</flux:subheading>
</div>
<div class="mx-auto aspect-[9/16] w-full max-w-[320px] overflow-hidden rounded-xl border border-zinc-200 bg-black shadow-sm dark:border-zinc-700">
<iframe
wire:key="item-modal-module-preview-{{ $previewFrameRefreshCounter }}"
src="{{ $this->itemPreviewUrl() }}"
class="h-full w-full border-0"
loading="lazy"
title="{{ __('Einzel-Vorschau im Bearbeiten-Dialog') }}"
></iframe>
</div>
<a href="{{ $this->itemPreviewUrl() }}"
target="_blank"
class="mx-auto flex max-w-[320px] items-center justify-center gap-1 text-xs text-blue-600 hover:underline dark:text-blue-400">
<flux:icon.arrow-top-right-on-square class="w-3 h-3" />
{{ __('Vollbild öffnen') }}
</a>
</div>
<div class="flex flex-wrap justify-end gap-3 border-t border-zinc-200 pt-4 dark:border-zinc-700">
<flux:button type="submit" variant="primary">
{{ $itemId ? __('Aktualisieren') : __('Hinzufügen') }}
</flux:button>
<flux:button type="button" wire:click="closeItemModal" variant="ghost">
{{ __('Abbrechen') }}
</flux:button>
<flux:button type="button" wire:click="closeItemModal">
{{ __('Schließen') }}
</flux:button>
</div>
</div>
</form>
</flux:modal>
{{-- Settings Modal --}}
<flux:modal :open="$showSettingsModal" wire:model="showSettingsModal">
<form wire:submit.prevent="saveSettings">
<div class="space-y-6">
<div>
<flux:heading size="lg">{{ __('Einstellungen') }}</flux:heading>
<flux:subheading>{{ $version->type->label() }}</flux:subheading>
</div>
@include('livewire.admin.cms.partials.version-editor-settings', ['context' => 'modal'])
<div class="flex justify-end gap-3 pt-4">
<flux:button type="button" wire:click="$set('showSettingsModal', false)" variant="ghost">
{{ __('Abbrechen') }}
</flux:button>
<flux:button type="submit" variant="primary">
{{ __('Speichern') }}
</flux:button>
</div>
</div>
</form>
</flux:modal>
</div>