From 53f38ba794aa4468bca7ccacb793d5c6764013aa Mon Sep 17 00:00:00 2001 From: isaacclad Date: Fri, 19 Jun 2026 09:33:27 +0000 Subject: [PATCH] Unify logged-in profile dropdown with platform account menu. Wire UserProfileMenu and shared Blade partial into topbar, mobile nav, and layouts so menu items match the account portal (Ladill Mail excluded). Co-authored-by: Cursor --- app/Support/UserProfileMenu.php | 96 +++++++++++++++++++ resources/views/layouts/email.blade.php | 3 +- resources/views/layouts/hosting.blade.php | 3 +- .../partials/mobile-bottom-nav.blade.php | 24 +---- resources/views/partials/topbar.blade.php | 17 ++-- .../partials/user-profile-menu.blade.php | 68 +++++++++++++ 6 files changed, 177 insertions(+), 34 deletions(-) create mode 100644 app/Support/UserProfileMenu.php create mode 100644 resources/views/partials/user-profile-menu.blade.php diff --git a/app/Support/UserProfileMenu.php b/app/Support/UserProfileMenu.php new file mode 100644 index 0000000..8af3f5d --- /dev/null +++ b/app/Support/UserProfileMenu.php @@ -0,0 +1,96 @@ +> */ + public static function items(?Authenticatable $user = null): array + { + $user ??= auth()->user(); + + if (! $user) { + return []; + } + + $items = []; + + foreach ([ + ['label' => 'Home', 'path' => '', 'host' => 'home'], + ['label' => 'Profile', 'path' => 'profile'], + ['label' => 'Account Settings', 'path' => 'account-settings'], + ['label' => 'Dashboard', 'path' => 'dashboard'], + ['label' => 'Billing', 'path' => 'billing'], + ] as $link) { + $items[] = [ + 'type' => 'link', + 'label' => $link['label'], + 'href' => self::platformUrl($link['host'] ?? 'account', $link['path']), + ]; + } + + if (self::userIsAdmin($user)) { + $items[] = [ + 'type' => 'link', + 'label' => 'Admin', + 'href' => self::platformUrl('account', 'admin'), + ]; + } + + if (Route::has('logout')) { + $items[] = [ + 'type' => 'logout', + 'label' => 'Logout', + 'action' => route('logout'), + ]; + } + + return $items; + } + + private static function platformUrl(string $host, string $path = ''): string + { + if ($host === 'home') { + if (function_exists('ladill_home_url')) { + return ladill_home_url($path); + } + + $domain = config('app.home_domain'); + if (! $domain) { + $platform = (string) config('app.platform_domain', parse_url((string) config('app.url', ''), PHP_URL_HOST) ?: ''); + $domain = $platform !== '' ? 'home.'.$platform : (string) config('app.account_domain'); + } + + return self::absoluteUrl((string) $domain, $path); + } + + if (function_exists('ladill_account_url')) { + return ladill_account_url($path); + } + + return self::absoluteUrl((string) config('app.account_domain'), $path); + } + + private static function absoluteUrl(string $domain, string $path = ''): string + { + $base = 'https://'.trim($domain, '/'); + + if ($path === '') { + return $base; + } + + return $base.'/'.ltrim($path, '/'); + } + + private static function userIsAdmin(Authenticatable $user): bool + { + if (method_exists($user, 'isAdmin')) { + return $user->isAdmin(); + } + + return (bool) ($user->is_admin ?? false); + } +} diff --git a/resources/views/layouts/email.blade.php b/resources/views/layouts/email.blade.php index 0c5c074..6c9e347 100644 --- a/resources/views/layouts/email.blade.php +++ b/resources/views/layouts/email.blade.php @@ -46,8 +46,7 @@ 'profileActive' => false, 'profileName' => $navUser?->name ?? '', 'profileSubtitle' => $navUser?->email ?? '', - 'profileMenuItems' => [ - ['type' => 'link', 'label' => 'Home', 'href' => ladill_home_url()], + 'profileMenuItems' => \App\Support\UserProfileMenu::items($navUser), ['type' => 'link', 'label' => 'Profile', 'href' => ladill_account_url('profile')], ['type' => 'link', 'label' => 'Account Settings', 'href' => ladill_account_url('account-settings')], ['type' => 'link', 'label' => 'Dashboard', 'href' => route('email.dashboard')], diff --git a/resources/views/layouts/hosting.blade.php b/resources/views/layouts/hosting.blade.php index 6526ffb..d300308 100644 --- a/resources/views/layouts/hosting.blade.php +++ b/resources/views/layouts/hosting.blade.php @@ -45,8 +45,7 @@ 'profileActive' => false, 'profileName' => $navUser?->name ?? '', 'profileSubtitle' => $navUser?->email ?? '', - 'profileMenuItems' => [ - ['type' => 'link', 'label' => 'Home', 'href' => ladill_home_url()], + 'profileMenuItems' => \App\Support\UserProfileMenu::items($navUser), ['type' => 'link', 'label' => 'Profile', 'href' => ladill_account_url('profile')], ['type' => 'link', 'label' => 'Account Settings', 'href' => ladill_account_url('account-settings')], ['type' => 'link', 'label' => 'Dashboard', 'href' => route('hosting.dashboard')], diff --git a/resources/views/partials/mobile-bottom-nav.blade.php b/resources/views/partials/mobile-bottom-nav.blade.php index 8a2e2b2..8613313 100644 --- a/resources/views/partials/mobile-bottom-nav.blade.php +++ b/resources/views/partials/mobile-bottom-nav.blade.php @@ -113,25 +113,11 @@ @endif -
- @foreach ($profileMenuItems as $item) - @if (($item['type'] ?? 'link') === 'link') - - {{ $item['label'] }} - - @elseif (($item['type'] ?? '') === 'logout') -
- @csrf - -
- @endif - @endforeach -
+ @include('partials.user-profile-menu', [ + 'items' => $profileMenuItems, + 'variant' => 'sheet', + 'onNavigate' => 'profileOpen = false', + ]) diff --git a/resources/views/partials/topbar.blade.php b/resources/views/partials/topbar.blade.php index e29798d..89f2767 100644 --- a/resources/views/partials/topbar.blade.php +++ b/resources/views/partials/topbar.blade.php @@ -78,18 +78,13 @@ @endif -
- Home - Profile - Account Settings - Dashboard - Billing -
-
@csrf - -
+
+ @include('partials.user-profile-menu', [ + 'items' => \App\Support\UserProfileMenu::items($user), + ])
-
+ @include('partials.afia-button', ['compact' => true]) @else Sign in diff --git a/resources/views/partials/user-profile-menu.blade.php b/resources/views/partials/user-profile-menu.blade.php new file mode 100644 index 0000000..ee7e421 --- /dev/null +++ b/resources/views/partials/user-profile-menu.blade.php @@ -0,0 +1,68 @@ +@props([ + 'items' => [], + 'user' => null, + 'showUser' => false, + 'variant' => 'dropdown', + 'onNavigate' => null, +]) + +@php + $linkClass = match ($variant) { + 'dark' => 'block rounded-md px-3 py-2 text-sm text-slate-200 hover:bg-slate-800', + 'sheet' => 'block rounded-xl px-4 py-3 text-sm font-medium text-slate-700 transition hover:bg-slate-100', + default => 'block rounded-lg px-3 py-2 text-sm text-slate-700 hover:bg-slate-100', + }; + + $logoutClass = match ($variant) { + 'dark' => 'w-full rounded-md px-3 py-2 text-left text-sm text-rose-300 hover:bg-rose-950/40', + 'sheet' => 'w-full rounded-xl px-4 py-3 text-left text-sm font-medium text-rose-600 transition hover:bg-rose-50', + default => 'w-full rounded-lg px-3 py-2 text-left text-sm text-rose-600 hover:bg-rose-50', + }; + + $logoutWrapperClass = match ($variant) { + 'sheet' => 'border-t border-slate-100 pt-2', + 'dark' => '', + default => '', + }; + + $dividerClass = match ($variant) { + 'dark' => 'my-1 border-t border-slate-800', + default => 'my-1 border-t border-slate-100', + }; + + $containerClass = match ($variant) { + 'dark' => 'mt-2 rounded-lg border border-slate-800 bg-slate-900 p-1', + 'sheet' => 'space-y-1 p-2 pb-4', + default => 'p-1', + }; +@endphp + +
merge(['class' => $containerClass]) }}> + @if ($showUser && $user) +
+

{{ $user->name ?? 'Your account' }}

+

{{ $user->email }}

+
+
+ @endif + + @foreach ($items as $item) + @if (($item['type'] ?? 'link') === 'link') + + {{ $item['label'] }} + + @elseif (($item['type'] ?? '') === 'logout') + @if ($variant !== 'sheet') +
+ @endif +
+ @csrf + +
+ @endif + @endforeach +