Teilen-Funktion: Öffentliche Share-Seite mit OG-Meta-Tags und Share-Button
- Öffentliche Route /e/{event} für Social-Media-Crawler (WhatsApp, Facebook)
- Share-View mit OG-Meta-Tags (Titel, Datum, Bild) für Link-Vorschau
- Teilen-Button auf Event-Detailseite (Web Share API + Clipboard-Fallback)
- Buttons: Teilen (helles Blau) + Bearbeiten (Standard-Blau)
- Hinweistext mit 3,5s Anzeige nach Link-Kopieren
- Event-Typ-Logos als neue Bilddateien
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -32,9 +32,25 @@
|
||||
</p>
|
||||
@endif
|
||||
</div>
|
||||
@if (auth()->user()->canAccessAdminPanel())
|
||||
<a href="{{ route('admin.events.edit', $event) }}" class="text-sm text-blue-600 hover:underline">{{ __('ui.edit') }}</a>
|
||||
@endif
|
||||
<div class="flex items-center gap-3">
|
||||
{{-- Teilen-Button --}}
|
||||
<div x-data="shareButton()" class="relative">
|
||||
<button @click="doShare()" type="button"
|
||||
class="inline-flex items-center gap-1.5 text-sm font-medium text-white bg-blue-400 hover:bg-blue-500 px-3 py-1.5 rounded-md transition">
|
||||
<svg class="w-4 h-4" fill="none" viewBox="0 0 24 24" stroke="currentColor">
|
||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2"
|
||||
d="M8.684 13.342C8.886 12.938 9 12.482 9 12c0-.482-.114-.938-.316-1.342m0 2.684a3 3 0 110-2.684m0 2.684l6.632 3.316m-6.632-6l6.632-3.316m0 0a3 3 0 105.367-2.684 3 3 0 00-5.367 2.684zm0 9.316a3 3 0 105.368 2.684 3 3 0 00-5.368-2.684z"/>
|
||||
</svg>
|
||||
{{ __('events.share') }}
|
||||
</button>
|
||||
<div x-show="copied" x-transition.opacity class="absolute top-full mt-2 right-0 bg-blue-600 text-white text-sm px-4 py-2 rounded-md shadow-lg whitespace-nowrap z-10">
|
||||
{{ __('events.share_link_copied') }}
|
||||
</div>
|
||||
</div>
|
||||
@if (auth()->user()->canAccessAdminPanel())
|
||||
<a href="{{ route('admin.events.edit', $event) }}" class="inline-flex items-center gap-1.5 text-sm font-medium text-white bg-blue-600 hover:bg-blue-700 px-3 py-1.5 rounded-md transition">{{ __('ui.edit') }}</a>
|
||||
@endif
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="mt-4 space-y-2 text-sm text-gray-700">
|
||||
@@ -595,6 +611,44 @@
|
||||
<a href="{{ route('events.index') }}" class="text-sm text-blue-600 hover:underline">← {{ __('events.back_to_list') }}</a>
|
||||
</div>
|
||||
|
||||
{{-- Share-Button Script --}}
|
||||
@push('scripts')
|
||||
<script>
|
||||
function shareButton() {
|
||||
return {
|
||||
copied: false,
|
||||
async doShare() {
|
||||
const shareData = {
|
||||
title: @js($event->title),
|
||||
text: @js($event->title . ' — ' . $event->start_at->translatedFormat(__('ui.date_format_long')) . ' ' . __('ui.clock')),
|
||||
url: @js(route('events.share', $event)),
|
||||
};
|
||||
if (navigator.share) {
|
||||
try { await navigator.share(shareData); } catch (e) {}
|
||||
return;
|
||||
}
|
||||
try {
|
||||
await navigator.clipboard.writeText(shareData.url);
|
||||
this.copied = true;
|
||||
setTimeout(() => this.copied = false, 3500);
|
||||
} catch (e) {
|
||||
const ta = document.createElement('textarea');
|
||||
ta.value = shareData.url;
|
||||
ta.style.position = 'fixed';
|
||||
ta.style.opacity = '0';
|
||||
document.body.appendChild(ta);
|
||||
ta.select();
|
||||
document.execCommand('copy');
|
||||
document.body.removeChild(ta);
|
||||
this.copied = true;
|
||||
setTimeout(() => this.copied = false, 3500);
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
</script>
|
||||
@endpush
|
||||
|
||||
{{-- Leaflet.js Karte --}}
|
||||
@if ($event->hasCoordinates())
|
||||
@push('styles')
|
||||
|
||||
Reference in New Issue
Block a user