diff --git a/app/Enums/ApplicationStatus.php b/app/Enums/ApplicationStatus.php
index 7519ccf..5e6d133 100644
--- a/app/Enums/ApplicationStatus.php
+++ b/app/Enums/ApplicationStatus.php
@@ -1,6 +1,7 @@
value)->replace('_', ' ')->title()->value();
+ }
}
diff --git a/app/Filament/Widgets/AbstractApplicationTablesChart.php b/app/Filament/Widgets/AbstractApplicationTablesChart.php
new file mode 100644
index 0000000..a8b1b75
--- /dev/null
+++ b/app/Filament/Widgets/AbstractApplicationTablesChart.php
@@ -0,0 +1,58 @@
+retrieveData();
+ return [
+ 'datasets' => [
+ [
+ 'label' => 'Total Tables',
+ 'data' => $data->pluck('count')->all(),
+ 'backgroundColor' => [
+ 'rgb(200, 180, 90)',
+ 'rgb(0, 200, 255)',
+ 'rgb(255, 200, 80)',
+ 'rgb(250, 100, 200)',
+ 'rgb(150, 100, 255)',
+ 'rgb(0, 180, 0)',
+ 'rgb(250, 80, 50)',
+ ],
+ ],
+ ],
+ 'labels' => $data->pluck('type')->all(),
+ ];
+ }
+
+ protected function getOptions(): array
+ {
+ return [
+ 'scales' => [
+ 'x' => [
+ 'display' => false,
+ ],
+ 'y' => [
+ 'display' => false,
+ ],
+ ],
+ ];
+ }
+}
diff --git a/app/Filament/Widgets/ApplicationStats.php b/app/Filament/Widgets/ApplicationStats.php
new file mode 100644
index 0000000..cacda99
--- /dev/null
+++ b/app/Filament/Widgets/ApplicationStats.php
@@ -0,0 +1,23 @@
+ Application::query()->toBase()->select(DB::raw('type, COUNT(*) as count'))->whereNull('canceled_at')->whereNull('waiting_at')->groupBy('type')->get());
+ return [
+ Stat::make('Total Applications (active)', fn() => $data->sum('count')),
+ Stat::make('Total Dealers (active)', fn() => $data->firstWhere('type', 'dealer')?->count ?? 0),
+ Stat::make('Total Shares (active)', fn() => $data->firstWhere('type', 'share')?->count ?? 0),
+ Stat::make('Total Assistants (active)', fn() => $data->firstWhere('type', 'assistant')?->count ?? 0),
+ ];
+ }
+}
diff --git a/app/Filament/Widgets/ApplicationStatusChart.php b/app/Filament/Widgets/ApplicationStatusChart.php
new file mode 100644
index 0000000..008aa40
--- /dev/null
+++ b/app/Filament/Widgets/ApplicationStatusChart.php
@@ -0,0 +1,67 @@
+ [
+ ApplicationStatus::Canceled->displayName() => ApplicationStatus::Canceled->orWhere(Application::query())->count(),
+ ApplicationStatus::Open->displayName() => ApplicationStatus::Open->orWhere(Application::query())->count(),
+ ApplicationStatus::Waiting->displayName() => ApplicationStatus::Waiting->orWhere(Application::query())->count(),
+ ApplicationStatus::TableAssigned->displayName() => ApplicationStatus::TableAssigned->orWhere(Application::query())->count(),
+ ApplicationStatus::TableOffered->displayName() => ApplicationStatus::TableOffered->orWhere(Application::query())->count(),
+ ApplicationStatus::TableAccepted->displayName() => ApplicationStatus::TableAccepted->orWhere(Application::query())->count(),
+ ApplicationStatus::CheckedIn->displayName() => ApplicationStatus::CheckedIn->orWhere(Application::query())->count(),
+ ApplicationStatus::CheckedOut->displayName() => ApplicationStatus::CheckedOut->orWhere(Application::query())->count(),
+ ]);
+
+ return [
+ 'datasets' => [
+ [
+ 'label' => 'Total Applications',
+ 'data' => array_values($status),
+ 'backgroundColor' => [
+ 'rgb(250, 80, 80)',
+ 'rgb(0, 200, 255)',
+ 'rgb(255, 200, 80)',
+ 'rgb(250, 100, 200)',
+ 'rgb(150, 100, 255)',
+ 'rgb(100, 255, 100)',
+ 'rgb(0, 180, 0)',
+ 'rgb(120, 120, 120)',
+ ],
+ ],
+ ],
+ 'labels' => array_keys($status),
+ ];
+ }
+
+ protected function getOptions(): array
+ {
+ return [
+ 'scales' => [
+ 'x' => [
+ 'display' => false,
+ ],
+ 'y' => [
+ 'display' => false,
+ ],
+ ],
+ ];
+ }
+}
diff --git a/app/Filament/Widgets/ApplicationTablesAssignedChart.php b/app/Filament/Widgets/ApplicationTablesAssignedChart.php
new file mode 100644
index 0000000..fcba31e
--- /dev/null
+++ b/app/Filament/Widgets/ApplicationTablesAssignedChart.php
@@ -0,0 +1,17 @@
+ Application::query()->toBase()->join('table_types', 'table_type_assigned', '=', 'table_types.id')->select(DB::raw('COUNT(*) as count, name as type'))->where('type', '=', 'dealer')->whereNull('canceled_at')->whereNull('waiting_at')->groupBy('name')->get());
+ }
+}
diff --git a/app/Filament/Widgets/ApplicationTablesRequestedChart.php b/app/Filament/Widgets/ApplicationTablesRequestedChart.php
new file mode 100644
index 0000000..d91e62c
--- /dev/null
+++ b/app/Filament/Widgets/ApplicationTablesRequestedChart.php
@@ -0,0 +1,17 @@
+ Application::query()->toBase()->join('table_types', 'table_type_requested', '=', 'table_types.id')->select(DB::raw('COUNT(*) as count, name as type'))->where('type', '=', 'dealer')->whereNull('canceled_at')->whereNull('waiting_at')->groupBy('name')->get());
+ }
+}
diff --git a/app/Filament/Widgets/DashboardInfo.php b/app/Filament/Widgets/DashboardInfo.php
new file mode 100644
index 0000000..deaef40
--- /dev/null
+++ b/app/Filament/Widgets/DashboardInfo.php
@@ -0,0 +1,11 @@
+whereNull('canceled_at')->whereNull('waiting_at')->get()
+ ->map(fn (Application $application): string => $registrations[$application->user_id]['status'] ?? 'unknown')
+ ->reduce(function (array $statusCount, string $status) {
+ $statusCount[$status] += 1;
+ return $statusCount;
+ }, [
+ 'new' => 0,
+ 'approved' => 0,
+ 'partially paid' => 0,
+ 'paid' => 0,
+ 'checked in' => 0,
+ 'unknown' => 0,
+ 'cancelled' => 0,
+ ]);
+ });
+ return [
+ 'datasets' => [
+ [
+ 'label' => 'Total Applications',
+ 'data' => array_values($data),
+ 'backgroundColor' => [
+ 'rgb(255, 200, 80)',
+ 'rgb(0, 200, 255)',
+ 'rgb(250, 100, 200)',
+ 'rgb(100, 255, 100)',
+ 'rgb(0, 180, 0)',
+ 'rgb(120, 120, 120)',
+ 'rgb(250, 80, 80)',
+ ],
+ ],
+ ],
+ 'labels' => array_keys($data),
+ ];
+ }
+
+ protected function getOptions(): array
+ {
+ return [
+ 'scales' => [
+ 'x' => [
+ 'display' => false,
+ ],
+ 'y' => [
+ 'display' => false,
+ ],
+ ],
+ ];
+ }
+}
diff --git a/app/Models/User.php b/app/Models/User.php
index 2155eef..aace90e 100644
--- a/app/Models/User.php
+++ b/app/Models/User.php
@@ -4,13 +4,15 @@
// use Illuminate\Contracts\Auth\MustVerifyEmail;
use Filament\Models\Contracts\FilamentUser;
+use Filament\Models\Contracts\HasAvatar;
use Filament\Panel;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Foundation\Auth\User as Authenticatable;
use Illuminate\Notifications\Notifiable;
+use Illuminate\Support\Facades\Session;
use Laravel\Sanctum\HasApiTokens;
-class User extends Authenticatable implements FilamentUser
+class User extends Authenticatable implements FilamentUser, HasAvatar
{
use HasApiTokens, HasFactory, Notifiable;
/**
@@ -81,4 +83,9 @@ public function canAccessPanel(Panel $panel): bool
{
return $this->isAdmin();
}
+
+ public function getFilamentAvatarUrl(): ?string
+ {
+ return Session::get('avatar');
+ }
}
diff --git a/app/Providers/Filament/AdminPanelProvider.php b/app/Providers/Filament/AdminPanelProvider.php
index 6685dd6..1d5757a 100644
--- a/app/Providers/Filament/AdminPanelProvider.php
+++ b/app/Providers/Filament/AdminPanelProvider.php
@@ -2,10 +2,10 @@
namespace App\Providers\Filament;
-use Filament\Http\Middleware\Authenticate;
+use App\Http\Middleware\Authenticate;
use Filament\Http\Middleware\DisableBladeIconComponents;
use Filament\Http\Middleware\DispatchServingFilamentEvent;
-use Filament\Navigation\NavigationGroup;
+use Filament\Navigation\MenuItem;
use Filament\Pages;
use Filament\Panel;
use Filament\PanelProvider;
@@ -27,7 +27,9 @@ public function panel(Panel $panel): Panel
->default()
->id('admin')
->path('admin')
- ->login()
+ ->userMenuItems([
+ 'logout' => MenuItem::make()->label('Log out')->url(fn () => route('auth.frontchannel-logout')),
+ ])
->colors([
'primary' => Color::Amber,
])
@@ -36,10 +38,14 @@ public function panel(Panel $panel): Panel
->pages([
Pages\Dashboard::class,
])
- ->discoverWidgets(in: app_path('Filament/Widgets'), for: 'App\\Filament\\Widgets')
+ //->discoverWidgets(in: app_path('Filament/Widgets'), for: 'App\\Filament\\Widgets')
->widgets([
- Widgets\AccountWidget::class,
- Widgets\FilamentInfoWidget::class,
+ \App\Filament\Widgets\DashboardInfo::class,
+ \App\Filament\Widgets\ApplicationStats::class,
+ \App\Filament\Widgets\ApplicationStatusChart::class,
+ \App\Filament\Widgets\RegistrationStatusChart::class,
+ \App\Filament\Widgets\ApplicationTablesRequestedChart::class,
+ \App\Filament\Widgets\ApplicationTablesAssignedChart::class,
])
->middleware([
EncryptCookies::class,
@@ -56,4 +62,4 @@ public function panel(Panel $panel): Panel
Authenticate::class,
]);
}
-}
\ No newline at end of file
+}
diff --git a/resources/views/filament/widgets/dashboard-info.blade.php b/resources/views/filament/widgets/dashboard-info.blade.php
new file mode 100644
index 0000000..c86c6ec
--- /dev/null
+++ b/resources/views/filament/widgets/dashboard-info.blade.php
@@ -0,0 +1,51 @@
+@php
+ $user = filament()->auth()->user();
+@endphp
+
+
+ {{ filament()->getUserName($user) }}
+
+ The data on this dashboard will be refreshed every 60 seconds.
+
+ Applications are considered active if they are neither canceled nor waiting.
+
+ Welcome to the Dealers' Den Admin Panel
+
+
+