presseportale/resources/views/web/newsroom.blade.php
Kevin Adametz 326ff9b2a0 Editorial-Frontend: oeffentliche Unterseiten, Preise & Linkpflege
Oeffentliche Strecke durchgaengig auf das Editorial-Design umgestellt und
datengetrieben gemacht:

- Newsrooms-Verzeichnis + Newsroom-Detailseiten (Suche, Pagination)
- Preise-Seite neu (Abos via Plan, Einzel-PM via config/billing, Add-ons via
  config/credits); Texte ausgelagert nach lang/{de,en}/pricing.php
- Pricing-Teaser-Komponente auf den Startseiten + Preise-Link in Header/Footer
- Statische Seiten im Editorial-Design ueber neue Komponente x-web.static-page:
  impressum, datenschutz, agb, cookies, faq (Akkordeon), hilfe, kontakt,
  ueber-uns, api (altes Theme/gradient-hero entfernt)
- Header/Footer-Linkpflege: tote #-Anker raus, FAQ/Hilfe/Cookies verlinkt,
  "Anmelden" fuehrt in den Hub
- Legacy-URL-Redirects (.html, presskit->newsroom, Regionen)
- Datums-Bugfix in Feed-Komponenten

Tests: NewsroomPage, PreisePage, PricingTeaser, StaticPages, NavigationLinks,
LegacyRedirect. Doku in docs/frontend aktualisiert.

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-06-17 16:08:46 +00:00

227 lines
14 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.

@extends('web.layouts.web-master')
@php
use Illuminate\Support\Str;
\Carbon\Carbon::setLocale(app()->getLocale());
$brandConfig = config('domains.domains.'.config('app.theme').'.brand', []);
$brandName = $brandConfig['name'] ?? 'businessportal';
$brandAccent = $brandConfig['accent'] ?? '24';
$fmt = fn ($value) => number_format((int) $value, 0, ',', '.');
$palette = ['#0098A6', '#21A038', '#0018A8', '#1E1E1E', '#E20074', '#003781', '#C84A1E', '#5A6E2F'];
$logoUrl = $company->logoUrl();
$initial = mb_strtoupper(mb_substr((string) $company->name, 0, 1));
$color = $palette[crc32((string) $company->id) % count($palette)];
$boilerplate = filled($company->boilerplate)
? trim((string) Str::of(strip_tags((string) $company->boilerplate))->squish())
: null;
$websiteHost = filled($company->website) ? preg_replace('#^https?://(www\.)?#', '', rtrim((string) $company->website, '/')) : null;
$leadImage = $leadRelease?->images->first();
$leadImageUrl = $leadImage?->variantUrl('detail') ?? $leadImage?->variantUrl('card') ?? $leadImage?->url();
$leadCat = $leadRelease?->category?->translations->firstWhere('locale', app()->getLocale()) ?? $leadRelease?->category?->translations->first();
$leadLead = $leadRelease
? (filled($leadRelease->subtitle)
? $leadRelease->subtitle
: (string) Str::of(strip_tags((string) $leadRelease->text))->squish()->limit(220))
: null;
$leadWords = $leadRelease ? str_word_count(strip_tags((string) $leadRelease->text)) : 0;
$leadReadTime = max(1, (int) round($leadWords / 200));
@endphp
@section('title', $company->name.' – Newsroom · '.$brandName.$brandAccent)
@section('meta_description', Str::limit($boilerplate ?? ('Newsroom von '.$company->name.': alle redaktionell geprüften Pressemitteilungen gebündelt an einem Ort.'), 155))
@section('og_type', 'profile')
@section('hreflang')
<link rel="alternate" hreflang="de" href="{{ url('/de/newsroom/'.$company->slug) }}">
<link rel="alternate" hreflang="en" href="{{ url('/en/newsroom/'.$company->slug) }}">
<link rel="alternate" hreflang="x-default" href="{{ url('/de/newsroom/'.$company->slug) }}">
@endsection
@section('content')
<x-web.site-header />
<main class="bg-bg text-ink">
{{-- Breadcrumb --}}
<div class="border-b border-bg-rule">
<div class="max-w-layout mx-auto px-4 sm:px-6 lg:px-8 py-2.5 flex items-center gap-2 text-[11.5px] text-ink-3">
<a href="{{ route('web.home') }}" class="hover:text-ink transition-colors">Startseite</a>
<span class="text-ink-4" aria-hidden="true">/</span>
<a href="{{ route('newsrooms') }}" class="hover:text-ink transition-colors">Newsrooms</a>
<span class="text-ink-4" aria-hidden="true">/</span>
<span class="text-ink font-semibold truncate max-w-[55vw]">{{ $company->name }}</span>
</div>
</div>
{{-- Masthead --}}
<section class="max-w-layout mx-auto px-4 sm:px-6 lg:px-8 pt-8 lg:pt-9">
<div class="flex items-center justify-between gap-4 mb-4">
<div class="eyebrow">Newsroom</div>
<a href="{{ route('newsrooms') }}" class="inline-flex items-center gap-1.5 text-[12px] font-semibold text-ink-3 hover:text-ink transition-colors whitespace-nowrap" aria-label="Zurück zu allen Newsrooms">
<svg width="13" height="13" viewBox="0 0 24 24" fill="none" aria-hidden="true"><path d="M15 19l-7-7 7-7" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>
Alle Newsrooms
</a>
</div>
{{-- Firmenprofil --}}
<div class="bg-bg-elev border border-bg-rule p-6 sm:p-8">
<div class="flex items-start gap-4 sm:gap-6">
@if ($logoUrl)
<img src="{{ $logoUrl }}" alt="{{ $company->name }}" class="w-16 h-16 sm:w-24 sm:h-24 object-contain bg-white border border-bg-rule flex-shrink-0">
@else
<div class="w-16 h-16 sm:w-24 sm:h-24 flex items-center justify-center text-white text-[30px] sm:text-[44px] font-bold font-serif flex-shrink-0" style="background: {{ $color }};">
{{ $initial }}
</div>
@endif
<div class="min-w-0 flex-1">
<h1 class="font-serif text-[28px] sm:text-[38px] lg:text-[42px] font-semibold m-0 leading-[1.05] tracking-[-1px] text-ink">{{ $company->name }}</h1>
<div class="mt-3 text-[12px] text-ink-3 flex items-center gap-2.5 flex-wrap">
@if ($websiteHost)
<a href="{{ $company->website }}" target="_blank" rel="nofollow noopener" class="inline-flex items-center gap-1.5 font-medium hover:text-ink transition-colors">
<svg width="12" height="12" viewBox="0 0 12 12" fill="none" aria-hidden="true"><circle cx="6" cy="6" r="5" stroke="currentColor" stroke-width="1"/><path d="M1 6h10M6 1c2 1.5 2 8.5 0 10M6 1c-2 1.5-2 8.5 0 10" stroke="currentColor" stroke-width="1"/></svg>
{{ $websiteHost }}
</a>
<span class="text-ink-4" aria-hidden="true">·</span>
@endif
<span class="inline-flex items-center gap-1.5">
<span class="w-1.5 h-1.5 rounded-full bg-brand pulse-dot"></span>
{{ $fmt($newsroomStats['recent'] ?? 0) }} Meldungen in den letzten 30 Tagen
</span>
@if (! empty($newsroomStats['sinceYear']))
<span class="text-ink-4" aria-hidden="true">·</span>
<span>Newsroom seit {{ $newsroomStats['sinceYear'] }}</span>
@endif
</div>
</div>
</div>
@if ($boilerplate)
<p class="font-serif text-[15.5px] leading-[1.6] m-0 mt-5 pt-5 border-t border-bg-rule text-ink-2">{{ Str::limit($boilerplate, 360) }}</p>
@endif
@if ($categories->isNotEmpty())
<div class="flex flex-wrap items-center gap-2 mt-5 pt-5 border-t border-bg-rule">
<span class="eyebrow muted text-[10px] mr-1.5">Branchen</span>
@foreach ($categories as $cat)
<a href="{{ $cat['href'] }}" class="inline-flex items-baseline gap-[7px] px-3 py-1.5 text-[12px] font-medium border border-bg-rule-strong bg-bg text-ink hover:bg-white hover:border-brand transition-colors">
{{ $cat['name'] }}
<span class="font-mono text-[10.5px] text-ink-3 font-medium">{{ $fmt($cat['count']) }}</span>
</a>
@endforeach
</div>
@endif
</div>
</section>
{{-- Stat strip --}}
<section class="max-w-layout mx-auto px-4 sm:px-6 lg:px-8 mt-6">
<div class="grid grid-cols-2 lg:grid-cols-4 border-y border-bg-rule">
<div class="px-6 py-5 border-r border-bg-rule">
<div class="eyebrow muted text-[10px] mb-2.5">Meldungen aktueller Tag</div>
<div class="font-serif text-[32px] sm:text-[36px] font-semibold leading-none tracking-[-0.6px] text-ink">{{ $fmt($newsroomStats['today'] ?? 0) }}</div>
<div class="text-[11.5px] text-ink-3 mt-2">Stand {{ $referenceNow->translatedFormat('j. M Y') }}</div>
</div>
<div class="px-6 py-5 lg:border-r border-bg-rule">
<div class="eyebrow muted text-[10px] mb-2.5">Letzte 30 Tage</div>
<div class="font-serif text-[32px] sm:text-[36px] font-semibold leading-none tracking-[-0.6px] text-ink">{{ $fmt($newsroomStats['recent'] ?? 0) }}</div>
<div class="text-[11.5px] text-ink-3 mt-2">veröffentlichte Meldungen</div>
</div>
<div class="px-6 py-5 border-r border-bg-rule border-t lg:border-t-0">
<div class="eyebrow muted text-[10px] mb-2.5">Im Archiv</div>
<div class="font-serif text-[32px] sm:text-[36px] font-semibold leading-none tracking-[-0.6px] text-ink">{{ $fmt($newsroomStats['total'] ?? 0) }}</div>
<div class="text-[11.5px] text-ink-3 mt-2">Meldungen gesamt</div>
</div>
<div class="px-6 py-5 border-t lg:border-t-0">
<div class="eyebrow muted text-[10px] mb-2.5">Aufrufe gesamt</div>
<div class="font-serif text-[32px] sm:text-[36px] font-semibold leading-none tracking-[-0.6px] text-ink">{{ $fmt($newsroomStats['totalHits'] ?? 0) }}</div>
<div class="text-[11.5px] text-ink-3 mt-2">über alle Meldungen</div>
</div>
</div>
</section>
@if ($leadRelease)
{{-- Top-Meldung --}}
<section class="max-w-layout mx-auto px-4 sm:px-6 lg:px-8 mt-10">
<article>
<a href="{{ route('release.detail', ['slug' => $leadRelease->slug]) }}" class="block group">
<div class="relative overflow-hidden bg-hero-grad hatch-dark" style="aspect-ratio: 16 / 9;">
@if ($leadImageUrl)
<img src="{{ $leadImageUrl }}" alt="{{ $leadRelease->title }}" class="absolute inset-0 w-full h-full object-cover" loading="lazy">
@endif
<div class="absolute top-5 left-5 flex gap-2">
<span class="bp-tag">Aktuellste Meldung</span>
</div>
<div class="absolute left-0 right-0 bottom-0 px-6 sm:px-9 pb-8 pt-[70px] text-white" style="background:linear-gradient(180deg,transparent,rgba(0,0,0,0.92));">
@if ($leadCat)
<div class="eyebrow mb-3" style="color:#FF8B6F;">{{ $leadCat->name }}</div>
@endif
<h2 class="font-serif text-[26px] sm:text-[34px] font-semibold m-0 leading-[1.12] tracking-[-0.6px] max-w-[760px] group-hover:text-white">
{{ $leadRelease->title }}
</h2>
@if ($leadLead)
<p class="font-serif text-[14.5px] leading-[1.5] mt-3.5 max-w-[640px] text-white/85">{{ $leadLead }}</p>
@endif
<div class="mt-[18px] flex items-center gap-3.5 text-[12px] text-white/70 flex-wrap">
@if ($leadRelease->published_at)
<span class="font-mono">{{ $leadRelease->published_at->translatedFormat('d.m.Y · H:i') }}</span>
<span aria-hidden="true">·</span>
@endif
<span>{{ $leadReadTime }} Min. Lesezeit</span>
</div>
</div>
</div>
</a>
</article>
</section>
@endif
{{-- Meldungen + Sidebar --}}
<section class="max-w-layout mx-auto px-4 sm:px-6 lg:px-8 mt-12 mb-16 grid gap-9 lg:grid-cols-[1.7fr_1fr]">
<div>
<header class="flex items-baseline justify-between mb-4 min-h-[34px] flex-wrap gap-3">
<h2 class="font-serif text-[28px] font-semibold m-0 tracking-[-0.3px] text-ink">
Alle Meldungen <span class="text-[14px] text-ink-3 font-normal ml-1.5">· {{ $fmt($newsroomStats['total'] ?? 0) }}</span>
</h2>
</header>
<hr class="rule-strong">
@forelse ($releases as $release)
<x-web.feed-item :release="$release" />
@empty
<p class="text-[13px] text-ink-3 py-6">Aktuell keine weiteren Meldungen in diesem Newsroom.</p>
@endforelse
<x-web.pagination :paginator="$releases" />
</div>
<aside class="flex flex-col gap-9">
<x-web.most-read :releases="$mostReadReleases ?? []" />
{{-- Eigenen Newsroom starten --}}
<section class="border border-bg-rule-strong bg-bg-elev p-6">
<div class="eyebrow mb-2">Für Unternehmen</div>
<h3 class="font-serif text-[20px] font-semibold m-0 mb-2 tracking-[-0.2px] leading-[1.2] text-ink">
Eigenen Newsroom starten
</h3>
<p class="text-[12.5px] leading-[1.5] m-0 mb-4 text-ink-2">
Bündeln Sie alle Ihre Pressemitteilungen unter einer eigenen Marken-URL – mit Logo, Branchen-Zuordnung und SEO-Vorteil.
</p>
<a href="{{ route('veroeffentlichen') }}"
class="w-full inline-flex items-center justify-center gap-2 px-[18px] py-2.5 text-[13px] font-semibold bg-white border border-bg-rule-strong text-ink rounded-[2px] cursor-pointer hover:border-brand hover:text-brand transition-colors">
Newsroom anlegen →
</a>
</section>
<x-web.publisher-cta />
</aside>
</section>
</main>
<x-web.site-footer />
@endsection