概览
简介


创建小部件
可用 make:filament-widget 命令创建小部件:
php artisan make:filament-widget MyWidget该命令会询问要创建的小部件类型。可选:
排序小部件
每个小部件类都有 $sort 属性,可用于调整其相对其他小部件在页面上的顺序:
protected static ?int $sort = 2;自定义仪表盘页面
若要自定义仪表盘类(例如更改小部件列数),请在 app/Filament/Pages/Dashboard.php 创建新文件:
<?php
namespace App\Filament\Pages;
use Filament\Pages\Dashboard as BaseDashboard;
class Dashboard extends BaseDashboard
{
// ...
}最后,从配置文件中移除原来的 Dashboard 类:
use Filament\Panel;
public function panel(Panel $panel): Panel
{
return $panel
// ...
->discoverPages(in: app_path('Filament/Pages'), for: 'App\\Filament\\Pages')
->pages([]);
}若未在新建仪表盘类所在目录用 discoverPages() 发现页面,应在 pages() 方法中手动注册该类:
use App\Filament\Pages\Dashboard;
use Filament\Panel;
public function panel(Panel $panel): Panel
{
return $panel
// ...
->pages([
Dashboard::class,
]);
}创建多个仪表盘
若要创建多个仪表盘,可重复上述流程。创建扩展 Dashboard 类的新页面即可按需添加任意数量的仪表盘。
还需为额外仪表盘定义 URL 路径,否则会落在 /:
protected static string $routePath = 'finance';也可通过覆盖 $title 属性自定义仪表盘标题:
protected static ?string $title = 'Finance dashboard';向用户展示的主仪表盘是其有权限访问的第一个(由 canAccess() 方法 控制),并按已定义的导航排序。
仪表盘默认排序为 -2。可用 $navigationSort 控制自定义仪表盘的排序:
protected static ?int $navigationSort = 15;自定义小部件网格
可更改用于展示小部件的网格列数。
首先,必须替换原来的 Dashboard 页面。
然后在新的 app/Filament/Pages/Dashboard.php 中覆盖 getColumns() 方法,返回要使用的网格列数:
public function getColumns(): int | array
{
return 2;
}响应式小部件网格
你可能希望按浏览器响应式 断点 更改小部件网格列数。可用数组指定各断点应使用的列数:
public function getColumns(): int | array
{
return [
'md' => 4,
'xl' => 5,
];
}这与响应式小部件宽度搭配效果很好。
自定义小部件宽度
可用 $columnSpan 属性自定义小部件宽度。可用 1 到 12 的数字表示跨越列数,或用 full 占满整页宽度:
protected int | string | array $columnSpan = 'full';响应式小部件宽度
你可能希望按浏览器响应式 断点 更改小部件宽度。可用数组指定各断点应占用的列数:
protected int | string | array $columnSpan = [
'md' => 2,
'xl' => 3,
];在使用响应式小部件网格时尤其有用。


按条件隐藏小部件
可覆盖小部件上的静态 canView() 方法,按条件隐藏它们:
public static function canView(): bool
{
return auth()->user()->isAdmin();
}表格小部件
可轻松向仪表盘添加表格。先用命令创建小部件:
php artisan make:filament-widget LatestOrders --table随后可通过编辑小部件文件自定义表格。
自定义小部件
开始构建 BlogPostsOverview 小部件:
php artisan make:filament-widget BlogPostsOverview该命令会创建两个文件:Filament 目录下 /Widgets 中的小部件类,以及 Filament 视图目录下 /widgets 中的视图。
该类是 Livewire 组件,因此可使用全部 Livewire 功能。Blade 视图可包含任意 HTML,并可在视图中访问任何公开的 Livewire 属性。也可用 $this 访问 Livewire 组件实例。
筛选小部件数据
可在仪表盘上添加表单,让用户筛选所有小部件展示的数据。筛选更新后,小部件会以新数据重新加载。
首先,必须替换原来的 Dashboard 页面。
然后在新的 app/Filament/Pages/Dashboard.php 中加入 HasFiltersForm trait,并添加 filtersForm() 方法以返回表单组件:
use Filament\Forms\Components\DatePicker;
use Filament\Pages\Dashboard as BaseDashboard;
use Filament\Pages\Dashboard\Concerns\HasFiltersForm;
use Filament\Schemas\Components\Section;
use Filament\Schemas\Schema;
class Dashboard extends BaseDashboard
{
use HasFiltersForm;
public function filtersForm(Schema $schema): Schema
{
return $schema
->components([
Section::make()
->schema([
DatePicker::make('startDate'),
DatePicker::make('endDate'),
// ...
])
->columns(3),
]);
}
}

需要筛选数据的小部件类应加入 InteractsWithPageFilters trait,以便用 $this->pageFilters 访问筛选表单的原始数据:
use App\Models\BlogPost;
use Carbon\CarbonImmutable;
use Filament\Widgets\StatsOverviewWidget;
use Filament\Widgets\Concerns\InteractsWithPageFilters;
use Illuminate\Database\Eloquent\Builder;
class BlogPostsOverview extends StatsOverviewWidget
{
use InteractsWithPageFilters;
public function getStats(): array
{
$startDate = $this->pageFilters['startDate'] ?? null;
$endDate = $this->pageFilters['endDate'] ?? null;
return [
StatsOverviewWidget\Stat::make(
label: 'Total posts',
value: BlogPost::query()
->when($startDate, fn (Builder $query) => $query->whereDate('created_at', '>=', $startDate))
->when($endDate, fn (Builder $query) => $query->whereDate('created_at', '<=', $endDate))
->count(),
),
// ...
];
}
}$this->pageFilters 数组始终反映当前表单数据。请注意该数据未经验证,因实时可用,且仅应用于查询数据库。使用前必须确保数据有效。本例中在用于查询前会检查是否已设置开始日期。
用操作模态筛选小部件数据
也可将筛选表单换成操作模态,通过点击页头按钮打开。该方式有多项好处:
- 筛选表单不必始终可见,可将整页高度留给小部件。
- 筛选在用户点击「Apply」按钮前不会更新小部件,即用户准备好后才重新加载,可在小部件加载成本较高时提升性能。
- 可对筛选表单做校验,小部件可依赖数据已有效——未通过校验无法提交。取消模态会丢弃用户更改。
要用操作模态代替筛选表单,可改用 HasFiltersAction trait(而非 HasFiltersForm),并在 getHeaderActions() 中将 FilterAction 注册为操作:
use Filament\Forms\Components\DatePicker;
use Filament\Pages\Dashboard as BaseDashboard;
use Filament\Pages\Dashboard\Actions\FilterAction;
use Filament\Pages\Dashboard\Concerns\HasFiltersAction;
class Dashboard extends BaseDashboard
{
use HasFiltersAction;
protected function getHeaderActions(): array
{
return [
FilterAction::make()
->schema([
DatePicker::make('startDate'),
DatePicker::make('endDate'),
// ...
]),
];
}
}处理筛选操作的数据与处理页头筛选表单相同,区别是传给小部件前会先校验。仍需使用 InteractsWithPageFilters trait。


在用户会话中持久化小部件筛选
默认情况下,已应用的仪表盘筛选会在页面加载之间保存在用户会话中。要禁用,请在仪表盘页面类中覆盖 $persistsFiltersInSession 属性:
use Filament\Pages\Dashboard as BaseDashboard;
use Filament\Pages\Dashboard\Concerns\HasFiltersForm;
class Dashboard extends BaseDashboard
{
use HasFiltersForm;
protected bool $persistsFiltersInSession = false;
}也可在仪表盘页面类中覆盖 persistsFiltersInSession() 方法:
use Filament\Pages\Dashboard as BaseDashboard;
use Filament\Pages\Dashboard\Concerns\HasFiltersForm;
class Dashboard extends BaseDashboard
{
use HasFiltersForm;
public function persistsFiltersInSession(): bool
{
return false;
}
}禁用默认小部件
默认情况下,仪表盘会显示两个小部件。可通过更新配置中的 widgets() 数组禁用它们:
use Filament\Panel;
public function panel(Panel $panel): Panel
{
return $panel
// ...
->widgets([]);
}