feat(admin): configure filament panel with custom branding and notifications

Enhance the Filament admin panel configuration to align with the new design system and enable core features.

- Implement custom color palette including dark navy for sidebar
- Set Vazirmatn as the primary font
- Enable SPA mode and collapsible sidebar for improved UX
- Configure database-driven notifications and global search bindings
- Add necessary web middleware stack for session and cookie management
- Create new migration for the notifications system
- Add directory for custom Filament render hooks
This commit is contained in:
Kazem Alghasi 2026-08-09 05:14:36 +03:30
parent 1f70fe5ee0
commit 810004aab1
3 changed files with 255 additions and 12 deletions

View File

@ -2,13 +2,21 @@
namespace App\Providers\Filament;
use App\Filament\Pages\Auth\Login;
use App\Filament\Pages\Dashboard;
use Filament\Http\Middleware\Authenticate;
use Filament\Http\Middleware\DisableBladeIconComponents;
use Filament\Http\Middleware\DispatchServingFilamentEvent;
use Filament\Pages;
use Filament\Panel;
use Filament\PanelProvider;
use Filament\Support\Colors\Color;
use Filament\Widgets;
use Illuminate\Cookie\Middleware\AddQueuedCookiesToResponse;
use Illuminate\Cookie\Middleware\EncryptCookies;
use Illuminate\Foundation\Http\Middleware\VerifyCsrfToken;
use Illuminate\Routing\Middleware\SubstituteBindings;
use Illuminate\Session\Middleware\AuthenticateSession;
use Illuminate\Session\Middleware\StartSession;
use Illuminate\View\Middleware\ShareErrorsFromSession;
class AdminPanelProvider extends PanelProvider
{
@ -20,29 +28,61 @@ class AdminPanelProvider extends PanelProvider
->path('admin')
->login()
->brandName('IFNEX Logistics')
->brandLogo('<img src="' . asset('images/ifnex-logo.svg') . '" alt="IFNEX" style="height: 40px;">')
->favicon(asset('images/favicon.svg'))
// 🎨 رنگ‌بندی سفارشی مطابق طراحی
->colors([
'primary' => Color::Amber,
'gray' => [
50 => '#f8fafc',
100 => '#f1f5f9',
200 => '#e2e8f0',
300 => '#cbd5e1',
400 => '#94a3b8',
500 => '#64748b',
600 => '#475569',
700 => '#334155',
800 => '#1e293b',
900 => '#1a1a2e', // 🎯 Dark Navy برای Sidebar
950 => '#0f172a',
],
'danger' => Color::Red,
'info' => Color::Blue,
'success' => Color::Emerald,
'warning' => Color::Amber,
])
->font('Vazirmatn')
->spa()
->sidebarCollapsibleOnDesktop()
->darkMode(true)
->databaseNotifications()
->globalSearchKeyBindings(['command+k', 'ctrl+k'])
->discoverResources(in: app_path('Filament/Resources'), for: 'App\\Filament\\Resources')
->discoverPages(in: app_path('Filament/Pages'), for: 'App\\Filament\\Pages')
->pages([
Dashboard::class,
\App\Filament\Pages\Reports\FinancialReport::class,
Pages\Dashboard::class,
])
->discoverWidgets(in: app_path('Filament/Widgets'), for: 'App\\Filament\\Widgets')
->widgets([
\Filament\Widgets\AccountWidget::class,
\Filament\Widgets\FilamentInfoWidget::class,
Widgets\AccountWidget::class,
Widgets\FilamentInfoWidget::class,
])
->middleware([
'web',
EncryptCookies::class,
AddQueuedCookiesToResponse::class,
StartSession::class,
AuthenticateSession::class,
ShareErrorsFromSession::class,
VerifyCsrfToken::class,
SubstituteBindings::class,
DisableBladeIconComponents::class,
DispatchServingFilamentEvent::class,
])
->authMiddleware([
Authenticate::class,
])
->sidebarWidth('18rem')
->maxContentWidth('xl');
// 🎯 اضافه کردن CSS/JS سفارشی
->renderHook(
'panels::head.start',
fn () => view('filament.hooks.head')
);
}
}

View File

@ -0,0 +1,31 @@
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
/**
* Run the migrations.
*/
public function up(): void
{
Schema::create('notifications', function (Blueprint $table) {
$table->uuid('id')->primary();
$table->string('type');
$table->morphs('notifiable');
$table->text('data');
$table->timestamp('read_at')->nullable();
$table->timestamps();
});
}
/**
* Reverse the migrations.
*/
public function down(): void
{
Schema::dropIfExists('notifications');
}
};

View File

@ -0,0 +1,172 @@
<!-- فونت وزیرمتن برای فارسی -->
<link rel="preconnect" href="https://fonts.googleapis.com">
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=Vazirmatn:wght@300;400;500;600;700;800;900&display=swap" rel="stylesheet">
<style>
/* ─── تنظیمات پایه RTL ─── */
html {
direction: rtl;
font-family: 'Vazirmatn', 'IranYekan', Tahoma, sans-serif !important;
}
body {
font-family: 'Vazirmatn', 'IranYekan', Tahoma, sans-serif !important;
}
/* ─── Sidebar استایل سفارشی ─── */
.fi-sidebar {
background: linear-gradient(180deg, #1a1a2e 0%, #16213e 100%) !important;
}
.fi-sidebar-item a {
transition: all 0.25s cubic-bezier(.4,0,.2,1);
}
.fi-sidebar-item-active > a {
background: rgba(245, 158, 11, 0.15) !important;
border-right: 3px solid #f59e0b !important;
}
.fi-sidebar-item-active > a .fi-sidebar-item-label {
color: #f59e0b !important;
font-weight: 700;
}
.fi-sidebar-item-active > a .fi-icon {
color: #f59e0b !important;
}
/* ─── دکمه‌ها ─── */
.fi-btn.fi-btn-color-primary {
box-shadow: 0 8px 20px rgba(245, 158, 11, 0.35);
}
/* ─── کارت‌های Stat ─── */
.fi-wi-stats-overview-stat {
border-radius: 16px !important;
border: 1px solid #e5e7eb;
}
/* ─── Logo استایل ─── */
.fi-brand {
font-family: 'Vazirmatn', sans-serif;
font-weight: 900;
letter-spacing: -0.5px;
}
.fi-brand-name {
font-family: 'Vazirmatn', sans-serif !important;
font-weight: 900 !important;
}
/* ─── اعداد فارسی ─── */
.fi-wi-stats-overview-stat-value,
.fi-tables-column-type-numeric {
font-family: 'Vazirmatn', sans-serif !important;
}
/* ─── Dark Mode بهبودها ─── */
.dark .fi-sidebar {
background: linear-gradient(180deg, #0f172a 0%, #1a1a2e 100%) !important;
}
.dark .fi-sidebar-item-active > a {
background: rgba(245, 158, 11, 0.2) !important;
}
/* ─── Notifications badge ─── */
.fi-badge {
font-family: 'Vazirmatn', sans-serif !important;
}
/* ─── Tables RTL fix ─── */
.fi-ta-ctn {
direction: rtl;
}
.fi-ta-header-heading {
font-family: 'Vazirmatn', sans-serif;
font-weight: 700;
}
/* ─── Forms RTL ─── */
.fi-input-wrp {
direction: rtl;
}
.fi-input-wrp-input {
text-align: right;
}
/* ─── Login Page بهبود ─── */
.fi-auth-layout {
background: linear-gradient(135deg, #1a0a00 0%, #3d1a00 30%, #7c3100 60%, #d97706 85%, #f59e0b 100%);
}
.fi-auth-card {
backdrop-filter: blur(20px);
background: rgba(255, 255, 255, 0.97) !important;
border-radius: 20px !important;
box-shadow: 0 25px 80px rgba(0, 0, 0, 0.25) !important;
}
.fi-login-heading {
font-family: 'Vazirmatn', sans-serif;
font-weight: 800;
color: #111827;
}
/* ─── Scrollbar سفارشی ─── */
::-webkit-scrollbar {
width: 8px;
height: 8px;
}
::-webkit-scrollbar-track {
background: #f1f5f9;
}
::-webkit-scrollbar-thumb {
background: #f59e0b;
border-radius: 4px;
}
::-webkit-scrollbar-thumb:hover {
background: #d97706;
}
/* ─── Page transitions ─── */
.fi-section {
transition: all 0.3s ease;
}
/* ─── Fix برای اعداد فارسی ─── */
.fi-wi-stats-overview-stat-description,
.fi-wi-stats-overview-stat-label {
font-family: 'Vazirmatn', sans-serif;
}
/* ─── Stats card hover ─── */
.fi-wi-stats-overview-stat:hover {
transform: translateY(-4px);
box-shadow: 0 10px 30px rgba(0, 0, 0, 0.1);
transition: all 0.3s ease;
}
/* ─── Badge colors ─── */
.fi-badge.fi-badge-color-success {
background: #d1fae5 !important;
color: #065f46 !important;
}
.fi-badge.fi-badge-color-danger {
background: #fee2e2 !important;
color: #991b1b !important;
}
.fi-badge.fi-badge-color-warning {
background: #fef3c7 !important;
color: #92400e !important;
}
</style>