Skip to content

Commit 43b68e7

Browse files
committed
wip
1 parent 72e3f91 commit 43b68e7

8 files changed

Lines changed: 66 additions & 109 deletions

File tree

resources/dist/inspirecms.css

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

resources/views/filament/forms/components/content-tree.blade.php

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,6 @@
66
77
$limit = $getLimits();
88
$maxSelections = $limit['max'] ?? null;
9-
$multipleSelection = $maxSelections > 1;
109
@endphp
1110
<x-dynamic-component
1211
:component="$getFieldWrapperView()"
@@ -17,7 +16,6 @@
1716
lazy
1817
:startNodeId="$startNode"
1918
:filter="$getFilter()"
20-
:multipleSelection="$multipleSelection"
2119
:maxSelections="$maxSelections"
2220
:isDisabled="$isDisabled()"
2321
:filterByPermission="$isFilteringByPermission()"

resources/views/livewire/content-sidebar.blade.php

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,6 @@ class="content-sidebar-modal"
1818
:autofocus="false"
1919
alignment="center"
2020
:close-button="true"
21-
header=" "
2221
>
2322
<x-slot name="trigger">
2423
<div class="fixed top-16 right-0 z-10 px-2 py-2 lg:hidden">

src/Base/Filament/Concerns/ContentPageTrait.php

Lines changed: 10 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ function () {
2525
$livewireData = $this->getLivewireData();
2626

2727
return Blade::render(<<<'Blade'
28-
<livewire:inspirecms::content-sidebar :data="$livewireData" />
28+
@livewire('inspirecms::content-sidebar', $livewireData)
2929
Blade, [
3030
'livewireData' => $livewireData,
3131
]);
@@ -151,28 +151,24 @@ protected function getRedirectUrlParameters(): array
151151

152152
protected function getLivewireData(): array
153153
{
154-
$selectedModelItemKey = null;
155-
$expandedModelItemKeys = [];
154+
$selectedKey = null;
155+
$expandedKeys = [];
156156

157157
if ($this instanceof EditRecord || $this instanceof ViewRecord) {
158158
$record = $this->getRecord();
159-
$selectedModelItemKey = $record->getKey();
160-
$expandedModelItemKeys[] = $record->parent_id;
159+
160+
$selectedKey = $record->getKey();
161+
$expandedKeys = $record?->ancestorsAndSelf?->map(fn ($r) => $r->getKey())->all() ?? [];
161162
} elseif ($this instanceof BaseContentCreatePage) {
162-
$selectedModelItemKey = $this->parent;
163+
$selectedKey = $this->parent;
163164
}
164165

165166
return [
166167
'redirectUrlParameters' => $this->getRedirectUrlParameters(),
167168
'activeLocale' => $this->activeLocale, // from queryString
168-
'selectedModelItemKeys' => array_filter([$selectedModelItemKey]),
169-
'expandedModelItemKeys' => $expandedModelItemKeys,
170-
'pageName' => match (true) {
171-
$this instanceof EditRecord => 'edit',
172-
$this instanceof ViewRecord => 'view',
173-
$this instanceof BaseContentCreatePage => 'create',
174-
default => 'index',
175-
},
169+
'selectedNodes' => array_filter([$selectedKey]),
170+
'expandedNodes' => $expandedKeys,
171+
'filamentPage' => get_class($this),
176172
];
177173
}
178174

src/Livewire/BaseContentTreeNode.php

Lines changed: 26 additions & 66 deletions
Original file line numberDiff line numberDiff line change
@@ -15,15 +15,23 @@
1515
use SolutionForest\InspireCms\InspireCmsConfig;
1616
use SolutionForest\InspireCms\Models\Contracts\Content;
1717
use SolutionForest\InspireCms\Support\Helpers\TreeNodeActionHelper;
18+
use SolutionForest\InspireCms\Support\TreeNode\Concerns\CanCacheRecords;
1819
use SolutionForest\InspireCms\Support\TreeNode\Livewire\ServerSideTreeComponent;
1920

2021
class BaseContentTreeNode extends ServerSideTreeComponent
2122
{
23+
use CanCacheRecords {
24+
getModel as protected getBaseModel;
25+
getElquentQuery as protected getBaseElquentQuery;
26+
}
27+
2228
protected static bool $showNodeActions = false;
2329

24-
public ?string $activeLocale = null;
30+
protected static bool $enableSelection = true;
2531

26-
protected array $nodeRecordsCache = []; // Cache model records by node ID
32+
protected static bool $skipChildrenIfTableView = true;
33+
34+
public ?string $activeLocale = null;
2735

2836
public array $redirectUrlParameters = []; // Additional URL parameters for resource links
2937

@@ -38,21 +46,6 @@ public function mount()
3846
}
3947
}
4048

41-
// public function getExtraAlpineAttributes()
42-
// {
43-
// $attributes = [];
44-
45-
// if ($this->isContentPickerModal()) {
46-
// if (isset($this->modalConfig['modelable']) && is_array($this->modalConfig['modelable'])) {
47-
48-
// $attributes['x-modelable'] = array_key_first($this->modalConfig['modelable']);
49-
// $attributes['x-model'] = Arr::first($this->modalConfig['modelable']);
50-
// }
51-
// }
52-
53-
// return new \Illuminate\View\ComponentAttributeBag($attributes);
54-
// }
55-
5649
protected function getRootNodes(): array
5750
{
5851
// Return array of root nodes
@@ -118,11 +111,20 @@ protected function transformRecordIntoNode($record)
118111
);
119112
}
120113

114+
$hasChildren = $record->children_count > 0;
115+
116+
if (static::$skipChildrenIfTableView
117+
&& ($documentType = $record?->documentType)
118+
&& $documentType->show_as_table === true
119+
) {
120+
$hasChildren = false;
121+
}
122+
121123
$node = [
122124
'id' => $record->getKey(),
123125
'name' => $record->title,
124126
'icon' => $record->documentType?->icon,
125-
'has_children' => $record->children_count > 0,
127+
'has_children' => $hasChildren,
126128
'parent_id' => $record->getParentId(),
127129
'depth' => $depth,
128130

@@ -169,7 +171,9 @@ protected function resolveTreeNodeAction(array $action, array $parentActions): ?
169171

170172
if ($recordKey && $resolvedAction && is_null($resolvedAction->getRecord())) {
171173

172-
$resolvedAction = $resolvedAction->record($this->retrieveRecordById($recordKey));
174+
$record = $this->retrieveRecordById($recordKey);
175+
176+
$resolvedAction->getRootGroup()?->record($record) ?? $resolvedAction->record($record);
173177

174178
}
175179

@@ -191,6 +195,7 @@ public function getNodeItemActionsHtml($id)
191195
->all(),
192196
livewireActions: $actions,
193197
model: $this->getModel(),
198+
livewire: $this,
194199
resolveRecordUsing: function ($arguments, $key) {
195200
if ($key instanceof Model) {
196201
return $key;
@@ -215,7 +220,8 @@ public function getNodeItemActionsHtml($id)
215220
public function getNodeLabel($node): array
216221
{
217222
$currentLocale = $this->activeLocale;
218-
$currentLocaleTitle = $node['translatable']['title'][$currentLocale] ?? null;
223+
$fallbackLocale = InspireCms::getFallbackLanguage()?->code ?? app()->getLocale();
224+
$currentLocaleTitle = $node['translatable']['title'][$currentLocale] ?? $node['translatable']['title'][$fallbackLocale] ?? null;
219225

220226
return [
221227
'title' => $currentLocaleTitle ?? $node['title'] ?? 'Untitled',
@@ -241,52 +247,6 @@ public function getNodeUrl(array $node): ?string
241247
return $node['url'] ?? null;
242248
}
243249

244-
protected function cacheRecordAppend($record, $key = null)
245-
{
246-
$key = $key ?? $record->getKey();
247-
if (! isset($this->nodeRecordsCache[$key])) {
248-
$this->nodeRecordsCache[$key] = $record;
249-
}
250-
}
251-
252-
protected function retrieveRecordById($recordKey)
253-
{
254-
if (isset($this->nodeRecordsCache[$recordKey])) {
255-
return $this->nodeRecordsCache[$recordKey];
256-
}
257-
258-
$record = $this->getElquentQuery()->find($recordKey);
259-
260-
$this->cacheRecordAppend($record);
261-
262-
return $record;
263-
}
264-
265-
/**
266-
* Clear all caches - useful when data changes
267-
*/
268-
public function clearRecordCaches(): void
269-
{
270-
$this->nodeRecordsCache = [];
271-
}
272-
273-
/**
274-
* Clear cache for specific nodes
275-
*/
276-
public function clearNodeRecordCache(array $nodeIds): void
277-
{
278-
// Clear record cache for specific nodes
279-
foreach ($nodeIds as $nodeId) {
280-
unset($this->nodeRecordsCache[$nodeId]);
281-
}
282-
}
283-
284-
public function refreshTree(): void
285-
{
286-
$this->clearRecordCaches(); // Clear record caches when refreshing
287-
parent::refreshTree();
288-
}
289-
290250
/**
291251
* @return class-string<Model>
292252
*/

src/Livewire/ContentSidebar.php

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,10 @@ class ContentSidebar extends BaseContentTreeNode
2323

2424
protected static bool $enableNodeUrls = true;
2525

26+
public ?int $maxSelections = 1; // Maximum number of selections allowed (null = unlimited)
27+
28+
public ?string $filamentPage = null;
29+
2630
protected $listeners = [
2731
'updatedActiveLocale' => '$refresh',
2832
];
@@ -83,9 +87,11 @@ protected function getNodeItemActions(): array
8387

8488
ActionGroup::make([
8589

86-
SetDefaultContentPageAction::make(),
90+
SetDefaultContentPageAction::make()
91+
->after(fn () => $this->refreshTree()),
8792

88-
UpdateContentRouteAction::make(),
93+
UpdateContentRouteAction::make()
94+
->after(fn () => $this->refreshTree()),
8995

9096
ActionGroup::make([
9197

@@ -102,7 +108,8 @@ protected function getNodeItemActions(): array
102108
->color('gray')
103109
->iconPosition(IconPosition::After)
104110
->icon(Heroicon::ArrowRight)
105-
->label(__('inspirecms::buttons.move_to.label')),
111+
->label(__('inspirecms::buttons.move_to.label'))
112+
->dropdownPlacement('right-start'),
106113

107114
DeleteAction::make()
108115
->after(fn () => $this->refreshTree()),

src/Livewire/ContentTreeNode.php

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -4,16 +4,13 @@
44

55
use Illuminate\Support\Arr;
66
use Livewire\Attributes\Locked;
7-
use Livewire\Attributes\On;
8-
use Livewire\Attributes\Renderless;
97
use SolutionForest\InspireCms\Filament\Forms\Components\ContentTree\FilterCollection;
8+
use SolutionForest\InspireCms\Livewire\BaseContentTreeNode;
109

1110
class ContentTreeNode extends BaseContentTreeNode
1211
{
1312
protected static bool $showNavigationHeader = false;
1413

15-
protected static bool $enableSelection = true;
16-
1714
public ?string $search = null;
1815

1916
public array $limits = [];

src/Livewire/NavigationTree.php

Lines changed: 18 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -20,10 +20,16 @@
2020
use SolutionForest\InspireCms\Helpers\FilamentResourceHelper;
2121
use SolutionForest\InspireCms\InspireCmsConfig;
2222
use SolutionForest\InspireCms\Support\Helpers\TreeNodeActionHelper;
23+
use SolutionForest\InspireCms\Support\TreeNode\Concerns\CanCacheRecords;
2324
use SolutionForest\InspireCms\Support\TreeNode\Livewire\SortableTreeComponent;
2425

2526
class NavigationTree extends SortableTreeComponent
2627
{
28+
use CanCacheRecords {
29+
getModel as protected getBaseModel;
30+
getElquentQuery as protected getBaseElquentQuery;
31+
}
32+
2733
protected static bool $showToolbarActions = true;
2834

2935
protected static bool $searchable = true;
@@ -63,7 +69,7 @@ public function saveOrder()
6369
{
6470
$data = collect($this->nodes)->map(fn ($node) => $this->transformNodeIntoRecord($node))->toArray();
6571

66-
$this->getTreeQuery()->rebuildTree($data);
72+
$this->getElquentQuery()->rebuildTree($data);
6773

6874
Notification::make()
6975
->title('Tree Updated')
@@ -78,7 +84,7 @@ public function refreshNodes()
7884
{
7985
// Implement the logic to refresh the nodes, e.g., fetch from database
8086
// $this->nodes = ...;
81-
$records = $this->getTreeQuery()->get()->toTree();
87+
$records = $this->getElquentQuery()->get()->toTree();
8288

8389
$this->nodes = collect($records)->map(fn ($record) => $this->transformRecordIntoNode($record))->toArray();
8490
}
@@ -154,27 +160,18 @@ public function getDefaultActionUrl(Action $action): ?string
154160
return null;
155161
}
156162

157-
protected function resolveRecursiveTreeNodeAction(array $action, array $parentActions): ?Action
163+
protected function resolveTreeNodeAction(array $action, array $parentActions): ?Action
158164
{
159-
$resolvedAction = parent::resolveRecursiveTreeNodeAction($action, $parentActions);
165+
$resolvedAction = $this->resolveBaseAction($action, $parentActions);
160166

161-
if ($resolvedAction) {
167+
$recordKey = $action['context']['recordKey'] ?? $action['arguments']['node']['id'] ?? null;
162168

163-
$resolvedAction->model($this->getModel());
169+
if ($recordKey && $resolvedAction && is_null($resolvedAction->getRecord())) {
164170

165-
$record = ($action['context']['recordKey'] ?? null) ? $this->getTreeQuery()->find($action['context']['recordKey']) : null;
171+
$record = $this->retrieveRecordById($recordKey);
166172

167173
$resolvedAction->getRootGroup()?->record($record) ?? $resolvedAction->record($record);
168174

169-
if (($url = $this->getDefaultActionUrl($resolvedAction)) &&
170-
filled($url)
171-
) {
172-
173-
redirect($url);
174-
175-
// Avoid modal opening before redirect
176-
return null;
177-
}
178175
}
179176

180177
return $resolvedAction;
@@ -244,16 +241,19 @@ public function getNodeItemActionsHtml($id)
244241
node: $node,
245242
livewireActions: $actions,
246243
model: $this->getModel(),
244+
livewire: $this,
247245
resolveRecordUsing: function ($arguments, $key) {
248246
if ($key instanceof Model) {
249247
return $key;
250248
}
249+
251250
$recordKey = $arguments['nodeId'] ?? $key ?? null;
251+
252252
if (is_null($recordKey) || empty($recordKey)) {
253253
return null;
254254
}
255255

256-
return $this->getTreeQuery()->find($recordKey);
256+
return $this->retrieveRecordById($recordKey);
257257
},
258258
);
259259
}
@@ -263,7 +263,7 @@ public function getNodeItemActionsHtml($id)
263263
->all();
264264
}
265265

266-
protected function getTreeQuery(): Builder
266+
protected function getElquentQuery(): Builder
267267
{
268268
return $this->getModel()::scoped(['category' => $this->category])
269269
->withDepth()

0 commit comments

Comments
 (0)