Skip to content

Commit 2acf486

Browse files
committed
feat: implement InfolistContainer for dynamic schema generation and model handling
1 parent 98dbb7b commit 2acf486

File tree

2 files changed

+117
-3
lines changed

2 files changed

+117
-3
lines changed

src/Filament/Integration/Builders/InfolistBuilder.php

Lines changed: 21 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,13 +6,15 @@
66

77
use Filament\Infolists\Components\Entry;
88
use Filament\Schemas\Components\Component;
9-
use Filament\Schemas\Components\Grid;
9+
use Illuminate\Database\Eloquent\Model;
1010
use Illuminate\Support\Collection;
1111
use Relaticle\CustomFields\Filament\Integration\Factories\FieldInfolistsFactory;
1212
use Relaticle\CustomFields\Filament\Integration\Factories\SectionInfolistsFactory;
13+
use Relaticle\CustomFields\Models\Contracts\HasCustomFields;
1314
use Relaticle\CustomFields\Models\CustomField;
1415
use Relaticle\CustomFields\Models\CustomFieldSection;
1516
use Relaticle\CustomFields\Services\Visibility\BackendVisibilityService;
17+
use Throwable;
1618

1719
final class InfolistBuilder extends BaseBuilder
1820
{
@@ -24,14 +26,30 @@ final class InfolistBuilder extends BaseBuilder
2426

2527
public function build(): Component
2628
{
27-
return Grid::make(1)->schema($this->values()->toArray());
29+
try {
30+
$model = $this->model;
31+
} catch (Throwable) {
32+
$model = null;
33+
}
34+
35+
return InfolistContainer::make()
36+
->forModel($model)
37+
->hiddenLabels($this->hiddenLabels)
38+
->visibleWhenFilled($this->visibleWhenFilled)
39+
->withoutSections($this->withoutSections)
40+
->only($this->only)
41+
->except($this->except);
2842
}
2943

3044
/**
3145
* @return Collection<int, mixed>
3246
*/
33-
public function values(): Collection
47+
public function values(null | (Model & HasCustomFields) $model = null): Collection
3448
{
49+
if ($model !== null) {
50+
$this->forModel($model);
51+
}
52+
3553
$fieldInfolistsFactory = app(FieldInfolistsFactory::class);
3654
$sectionInfolistsFactory = app(SectionInfolistsFactory::class);
3755
$backendVisibilityService = app(BackendVisibilityService::class);
Lines changed: 96 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,96 @@
1+
<?php
2+
3+
namespace Relaticle\CustomFields\Filament\Integration\Builders;
4+
5+
use Filament\Forms\Components\Field;
6+
use Filament\Schemas\Components\Component;
7+
use Illuminate\Database\Eloquent\Model;
8+
9+
final class InfolistContainer extends Component
10+
{
11+
protected string $view = 'filament-schemas::components.grid';
12+
13+
protected Model|string|null $recordModel;
14+
15+
protected array $except = [];
16+
17+
protected array $only = [];
18+
19+
private bool $hiddenLabels = false;
20+
21+
private bool $visibleWhenFilled = false;
22+
23+
private bool $withoutSections = false;
24+
25+
public function __construct()
26+
{
27+
// Defer schema generation until we can safely access the record
28+
$this->schema(fn() => $this->generateSchema());
29+
}
30+
31+
public static function make(): static
32+
{
33+
return app(self::class);
34+
}
35+
36+
public function forModel(Model|string|null $model): static
37+
{
38+
$this->recordModel = $model;
39+
40+
return $this;
41+
}
42+
43+
public function except(array $fieldCodes): static
44+
{
45+
$this->except = $fieldCodes;
46+
47+
return $this;
48+
}
49+
50+
public function only(array $fieldCodes): static
51+
{
52+
$this->only = $fieldCodes;
53+
54+
return $this;
55+
}
56+
57+
public function hiddenLabels(bool $hiddenLabels = true): static
58+
{
59+
$this->hiddenLabels = $hiddenLabels;
60+
61+
return $this;
62+
}
63+
64+
public function visibleWhenFilled(bool $visibleWhenFilled = true): static
65+
{
66+
$this->visibleWhenFilled = $visibleWhenFilled;
67+
68+
return $this;
69+
}
70+
71+
public function withoutSections(bool $withoutSections = true): static
72+
{
73+
$this->withoutSections = $withoutSections;
74+
75+
return $this;
76+
}
77+
78+
/**
79+
* @return array<int, Field>
80+
*/
81+
protected function generateSchema(): array
82+
{
83+
$model = $this->recordModel ?? $this->getRecord() ?? $this->getModel();
84+
85+
$builder = app(InfolistBuilder::class);
86+
87+
return $builder
88+
->only($this->only)
89+
->except($this->except)
90+
->hiddenLabels($this->hiddenLabels)
91+
->visibleWhenFilled($this->visibleWhenFilled)
92+
->withoutSections($this->withoutSections)
93+
->values($model)
94+
->toArray();
95+
}
96+
}

0 commit comments

Comments
 (0)