From dff34e2b9f35b1f6470660f25fd21f01de2ad40d Mon Sep 17 00:00:00 2001 From: pxpm Date: Wed, 5 Nov 2025 11:46:08 +0000 Subject: [PATCH 1/3] add save action docs --- 7.x-dev/base-components.md | 28 ++++++++++++ 7.x-dev/crud-save-actions.md | 85 ++++++++++++++++++++++++++++++++++++ 2 files changed, 113 insertions(+) diff --git a/7.x-dev/base-components.md b/7.x-dev/base-components.md index ef7e21e1..c86928fc 100644 --- a/7.x-dev/base-components.md +++ b/7.x-dev/base-components.md @@ -100,6 +100,7 @@ This component helps you show a form _anywhere you want_, so the admin can easil - `operation='create'` - by default, the datatable component will pick up everything that controller sets up for the Create operation; if you want to change the operation it will initialize, you can pass this parameter; - `:entry="\App\Models\Invoice::find(1)"` - if you want to use UpdateOperation or a custom form operation that needs the entry; - `:setup="function($crud, $parent) {}"` - if you want to make changes to the operation setup (eg. add/remove fields, configure functionality), you can use this parameter; the closure passed here will be run _after_ the setup of that operation had already completed; +- `:save-actions="[]"` - provide an array of save action definitions or save action classes to replace the defaults (see [Custom save actions](#dataform-custom-save-actions)); **Advanced example:** @@ -115,6 +116,33 @@ This component helps you show a form _anywhere you want_, so the admin can easil /> ``` + +#### Custom save actions + +The Dataform component can swap out the default `Save and back / edit / new` buttons with your own logic. Pass an array to the `:save-actions` attribute containing save action classes (or definitions) that implement Backpack's `SaveActionInterface`: + +```php +@php + use App\Backpack\Crud\SaveActions\SaveAndApprove; + use Backpack\CRUD\app\Library\CrudPanel\SaveActions\SaveAndBack; +@endphp + + +``` + +Each entry in the array can be: +- an instance of a class that implements `SaveActionInterface` (recommended); +- the fully qualified class name of a save action (the container will resolve it); +- a plain array definition (see [`crud-save-actions.md`](crud-save-actions.md)). + +Backpack will replace the default actions for that form, honour the order defined by each class, and fallback to the first action if no default applies. +
diff --git a/7.x-dev/crud-save-actions.md b/7.x-dev/crud-save-actions.md index 4fb61c85..38e3b09a 100644 --- a/7.x-dev/crud-save-actions.md +++ b/7.x-dev/crud-save-actions.md @@ -16,6 +16,91 @@ There are four save actions registered by Backpack by default. They are: - ```save_and_new``` (Save and go to create new entity page) - ```save_and_preview``` (Save and go to show the current entity) + +## Save Action Classes + +Save actions are now first-class citizens. Instead of maintaining large array definitions in each CrudController, you can encapsulate the behaviour inside PHP classes that implement `Backpack\CRUD\app\Library\CrudPanel\SaveActions\SaveActionInterface`. Backpack ships with `SaveAndBack`, `SaveAndEdit`, `SaveAndNew`, and `SaveAndPreview` as examples. + +### Quick start + +1. **Create a class** inside your application (for example `app/Backpack/Crud/SaveActions/SaveAndApprove.php`). +2. **Extend** `AbstractSaveAction` (recommended) or implement `SaveActionInterface` directly. +3. **Override** the methods that describe your button. +4. **Register** the class with `CRUD::addSaveAction()` / `CRUD::replaceSaveActions()` or pass it to Blade components like ``. + +```php +hasAccess('update') && $crud->entry?->canBeApproved(); + } + + public function getRedirectUrl(CrudPanel $crud, Request $request, $itemId = null): ?string + { + return route('admin.invoices.approve', $itemId ?? $request->input('id')); + } +} +``` + +> **Tip:** `AbstractSaveAction` already implements `toArray()`, order handling, and sensible defaults. Override only what you need. If you must store additional data, you can still return a custom array by implementing `SaveActionInterface` yourself. + +### Registering class-based actions + +Inside your CrudController you can now pass the class instead of an array: + +```php +use App\Backpack\Crud\SaveActions\SaveAndApprove; + +CRUD::replaceSaveActions([ + new SaveAndApprove(), + \Backpack\CRUD\app\Library\CrudPanel\SaveActions\SaveAndBack::class, +]); +``` + +Backpack recognizes three inputs when registering save actions: +- an instantiated save action class; +- the fully qualified class name (it is resolved via the container so dependencies can be injected); +- the legacy associative array definition (still supported). + +The action `order` is taken from the class (or array) and Backpack reorders conflicts automatically. If you need to adjust the order later you can still call `CRUD::orderSaveActions()`. + +### Using classes in Blade components + +The `bp-dataform` component accept save action classes through the `:save-actions` attribute. This allows you to reuse the same custom buttons outside CrudControllers: + +```php + +``` + +When no save actions are provided, Backpack falls back to the defaults registered on the controller. + ## Save Actions API From 4dc199c8d1809a640a3c6a1d7587e24076bdd70b Mon Sep 17 00:00:00 2001 From: pxpm Date: Thu, 6 Nov 2025 15:00:40 +0000 Subject: [PATCH 2/3] wip --- 7.x-dev/base-components.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/7.x-dev/base-components.md b/7.x-dev/base-components.md index c86928fc..fe61496e 100644 --- a/7.x-dev/base-components.md +++ b/7.x-dev/base-components.md @@ -101,6 +101,7 @@ This component helps you show a form _anywhere you want_, so the admin can easil - `:entry="\App\Models\Invoice::find(1)"` - if you want to use UpdateOperation or a custom form operation that needs the entry; - `:setup="function($crud, $parent) {}"` - if you want to make changes to the operation setup (eg. add/remove fields, configure functionality), you can use this parameter; the closure passed here will be run _after_ the setup of that operation had already completed; - `:save-actions="[]"` - provide an array of save action definitions or save action classes to replace the defaults (see [Custom save actions](#dataform-custom-save-actions)); +- `:form-inside-card="true"` - render the form inside a Backpack card wrapper so it visually matches the default create/update screens; leave it `false` to output only the raw form markup. **Advanced example:** @@ -200,6 +201,7 @@ Useful if you want to show the entries in the database, for an Eloquent model. T **Configuration options:** - `name='invoices_datatable'` - by default, a name will be generated; but you can pick one you can recognize; - `operation='list'` - by default, the datatable component will pick up everything that controller sets up for the List operation; if you want to change the operation it will initialize, you can pass this parameter; +- `:useFixedHeader="false"` - set this to explicitly enable or disable the sticky header; it defaults to the operation's `useFixedHeader` setting, falling back to `true`; - `:setup="function($crud, $parent) {}"` - if you want to make changes to the operation setup (eg. add/remove columns, configure functionality), you can use this parameter; the closure passed here will be run _after_ the setup of that operation had already completed; **Advanced example:** From 67390def0b5b106c122c4a504736e837ddbefd92 Mon Sep 17 00:00:00 2001 From: pxpm Date: Fri, 7 Nov 2025 10:42:36 +0000 Subject: [PATCH 3/3] wip --- 7.x-dev/base-components.md | 1 + 7.x-dev/crud-save-actions.md | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/7.x-dev/base-components.md b/7.x-dev/base-components.md index fe61496e..dd5da5a9 100644 --- a/7.x-dev/base-components.md +++ b/7.x-dev/base-components.md @@ -169,6 +169,7 @@ use \Backpack\DataformModal\Http\Controllers\Operations\CreateInModalOperation; - `operation='createInModal'` - by default, the component will pick up everything that controller sets up for the Create operation; if you want to change the operation it will initialize, you can pass this parameter, eg: `updateInModal` - `:entry="\App\Models\Invoice::find(1)"` - if you want to use UpdateInModalOperation or a custom form operation that needs the entry; - `:setup="function($crud, $parent) {}"` - if you want to make changes to the operation setup (eg. add/remove fields, configure functionality), you can use this parameter; the closure passed here will be run _after_ the setup of that operation had already completed; +- `:save-actions="[]"` - replace the default modal buttons with your own save action classes. **Advanced example:** diff --git a/7.x-dev/crud-save-actions.md b/7.x-dev/crud-save-actions.md index 38e3b09a..679aac24 100644 --- a/7.x-dev/crud-save-actions.md +++ b/7.x-dev/crud-save-actions.md @@ -19,7 +19,7 @@ There are four save actions registered by Backpack by default. They are: ## Save Action Classes -Save actions are now first-class citizens. Instead of maintaining large array definitions in each CrudController, you can encapsulate the behaviour inside PHP classes that implement `Backpack\CRUD\app\Library\CrudPanel\SaveActions\SaveActionInterface`. Backpack ships with `SaveAndBack`, `SaveAndEdit`, `SaveAndNew`, and `SaveAndPreview` as examples. +Save actions are now first-class citizens. Instead of maintaining large array definitions in each CrudController, you can encapsulate the behaviour inside PHP classes that implement `Backpack\CRUD\app\Library\CrudPanel\SaveActions\SaveActionInterface`. Backpack ships with `SaveAndBack`, `SaveAndEdit`, `SaveAndNew`, and `SaveAndPreview` as examples, and also provides `SaveAndList` for projects that want an explicit "Save and go to list" button. ### Quick start