@praxisui/expansion 9.0.0-beta.1 → 9.0.0-beta.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +86 -212
- package/package.json +6 -6
package/README.md
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
title: "Expansion"
|
|
3
3
|
slug: "expansion-overview"
|
|
4
|
-
description: "
|
|
4
|
+
description: "Public npm documentation for @praxisui/expansion: metadata-driven accordion panels, persistence, providers, lazy panel content and runtime authoring."
|
|
5
5
|
doc_type: "reference"
|
|
6
6
|
document_kind: "component-overview"
|
|
7
7
|
component: "expansion"
|
|
@@ -24,7 +24,7 @@ icon: "expand"
|
|
|
24
24
|
toc: true
|
|
25
25
|
sidebar: true
|
|
26
26
|
search_boost: 1.0
|
|
27
|
-
reading_time:
|
|
27
|
+
reading_time: 5
|
|
28
28
|
estimated_setup_time: 15
|
|
29
29
|
version: "1.0"
|
|
30
30
|
related_docs:
|
|
@@ -35,267 +35,141 @@ keywords:
|
|
|
35
35
|
- "expansion panel"
|
|
36
36
|
- "metadata"
|
|
37
37
|
- "providers"
|
|
38
|
-
last_updated: "2026-
|
|
38
|
+
last_updated: "2026-06-16"
|
|
39
39
|
---
|
|
40
40
|
|
|
41
|
-
# @praxisui/expansion
|
|
41
|
+
# @praxisui/expansion
|
|
42
42
|
|
|
43
|
-
|
|
43
|
+
`@praxisui/expansion` renders Angular Material expansion panels from Praxis metadata. Install it when a host needs governed accordion layouts with panel persistence, dynamic field/widget content, runtime editing and registry projection for dynamic pages.
|
|
44
44
|
|
|
45
|
-
|
|
46
|
-
- Quickstart reference app: https://github.com/codexrodrigues/praxis-ui-quickstart
|
|
47
|
-
- Live Praxis UI demo: https://praxis-ui-4e602.web.app
|
|
48
|
-
- Recommended for: accordion and panel layouts driven by metadata with editor integration
|
|
45
|
+
The package owns the expansion shell and metadata shape. The host owns domain data, widget providers, authorization, persistence beyond component config and any business effect triggered from panel actions.
|
|
49
46
|
|
|
50
|
-
##
|
|
51
|
-
|
|
52
|
-
- Organizar blocos expansivos em telas configuradas por metadata
|
|
53
|
-
- Reaproveitar paines tipo accordion em fluxos com editor embutido
|
|
54
|
-
- Manter comportamento e defaults de expansion alinhados no ecossistema Praxis UI
|
|
55
|
-
|
|
56
|
-
Widget baseado em Angular Material (MatAccordion/MatExpansionPanel) com configuração via metadata, editor embutido e integração com o `ComponentMetadataRegistry` para uso em páginas dinâmicas canônicas.
|
|
57
|
-
|
|
58
|
-
## Instalação e Providers
|
|
47
|
+
## Install
|
|
59
48
|
|
|
60
49
|
```bash
|
|
61
50
|
npm i @praxisui/expansion@latest
|
|
62
51
|
```
|
|
63
52
|
|
|
64
53
|
Peer dependencies:
|
|
65
|
-
- `@angular/core` `^21.0.0`
|
|
66
|
-
- `@angular/common` `^21.0.0`
|
|
67
|
-
- `@angular/forms` `^21.0.0`
|
|
68
|
-
- `@angular/router` `^21.0.0`
|
|
69
|
-
- `@angular/cdk` `^21.0.0`
|
|
70
|
-
- `@angular/material` `^21.0.0`
|
|
71
|
-
- `@praxisui/core` `^9.0.0-beta.1`
|
|
72
|
-
- `@praxisui/dynamic-fields` `^9.0.0-beta.1`
|
|
73
|
-
- `@praxisui/settings-panel` `^9.0.0-beta.1`
|
|
74
|
-
- `@praxisui/ai` `^9.0.0-beta.1`
|
|
75
|
-
- `rxjs` `~7.8.0`
|
|
76
|
-
|
|
77
|
-
- Registrar o metadata do componente:
|
|
78
54
|
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
bootstrapApplication(AppComponent, {
|
|
83
|
-
providers: [providePraxisExpansionMetadata()],
|
|
84
|
-
});
|
|
85
|
-
```
|
|
55
|
+
- `@angular/common`, `@angular/core`, `@angular/forms`, `@angular/router`, `@angular/cdk`, `@angular/material` `^21.0.0`
|
|
56
|
+
- `@praxisui/core`, `@praxisui/dynamic-fields`, `@praxisui/settings-panel`, `@praxisui/ai` `^9.0.0-beta.1`
|
|
57
|
+
- `rxjs` `~7.8.0`
|
|
86
58
|
|
|
87
|
-
|
|
59
|
+
## App Providers
|
|
88
60
|
|
|
89
61
|
```ts
|
|
90
|
-
import {
|
|
62
|
+
import { ApplicationConfig } from '@angular/core';
|
|
63
|
+
import {
|
|
64
|
+
providePraxisExpansionDefaults,
|
|
65
|
+
providePraxisExpansionMetadata,
|
|
66
|
+
} from '@praxisui/expansion';
|
|
91
67
|
|
|
92
|
-
|
|
68
|
+
export const appConfig: ApplicationConfig = {
|
|
93
69
|
providers: [
|
|
94
|
-
|
|
70
|
+
providePraxisExpansionMetadata(),
|
|
71
|
+
providePraxisExpansionDefaults({
|
|
72
|
+
collapsedHeight: '48px',
|
|
73
|
+
expandedHeight: '64px',
|
|
74
|
+
hideToggle: false,
|
|
75
|
+
}),
|
|
95
76
|
],
|
|
96
|
-
}
|
|
77
|
+
};
|
|
97
78
|
```
|
|
98
79
|
|
|
99
|
-
|
|
80
|
+
`providePraxisExpansionMetadata()` registers `praxis-expansion` for the Praxis component metadata registry. `providePraxisExpansionDefaults()` is optional; instance `defaultOptions` take precedence.
|
|
100
81
|
|
|
101
|
-
|
|
102
|
-
import { ExpansionMetadata } from '@praxisui/expansion';
|
|
82
|
+
## Minimal Standalone Panel
|
|
103
83
|
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
84
|
+
```ts
|
|
85
|
+
import { Component } from '@angular/core';
|
|
86
|
+
import { PraxisExpansion, type ExpansionMetadata } from '@praxisui/expansion';
|
|
87
|
+
|
|
88
|
+
@Component({
|
|
89
|
+
selector: 'app-expansion-host',
|
|
90
|
+
standalone: true,
|
|
91
|
+
imports: [PraxisExpansion],
|
|
92
|
+
template: `
|
|
93
|
+
<praxis-expansion
|
|
94
|
+
expansionId="customer-panels"
|
|
95
|
+
[config]="config"
|
|
96
|
+
[enableCustomization]="true"
|
|
97
|
+
(expandedChange)="onExpandedChange($event)"
|
|
98
|
+
/>
|
|
99
|
+
`,
|
|
100
|
+
})
|
|
101
|
+
export class ExpansionHostComponent {
|
|
102
|
+
readonly config: ExpansionMetadata = {
|
|
103
|
+
accordion: { multi: true, displayMode: 'default', togglePosition: 'after' },
|
|
104
|
+
panels: [
|
|
105
|
+
{ id: 'general', title: 'General', description: 'Main customer data', expanded: true },
|
|
106
|
+
{ id: 'history', title: 'History', description: 'Timeline and related records' },
|
|
107
|
+
],
|
|
108
|
+
};
|
|
112
109
|
|
|
113
|
-
|
|
114
|
-
|
|
110
|
+
onExpandedChange(event: { panelId?: string; panelIndex: number; expanded: boolean }): void {
|
|
111
|
+
console.log('panel changed', event);
|
|
112
|
+
}
|
|
113
|
+
}
|
|
115
114
|
```
|
|
116
115
|
|
|
117
|
-
##
|
|
116
|
+
## Main Inputs And Outputs
|
|
118
117
|
|
|
119
|
-
-
|
|
120
|
-
-
|
|
118
|
+
- `config: ExpansionMetadata | null`: canonical accordion and panel configuration.
|
|
119
|
+
- `expansionId: string`: required stable id used for local configuration persistence.
|
|
120
|
+
- `componentInstanceId?: string`: disambiguates repeated instances on the same route.
|
|
121
|
+
- `context: Record<string, unknown>`: context passed to dynamic child widgets.
|
|
122
|
+
- `strictValidation: boolean`: keeps runtime validation strict by default.
|
|
123
|
+
- `enableCustomization: boolean`: opens runtime authoring affordances.
|
|
124
|
+
- `defaultOptions?: MatExpansionPanelDefaultOptions`: instance Material expansion defaults.
|
|
125
|
+
- Events: `opened`, `closed`, `expandedChange`, `afterExpand`, `afterCollapse`, `destroyed`.
|
|
126
|
+
- `widgetEvent`: legacy/advanced bridge for nested widget and panel action events.
|
|
121
127
|
|
|
122
|
-
|
|
128
|
+
The component also exposes imperative methods by template ref: `open(idOrIndex)`, `close(idOrIndex)`, `toggle(idOrIndex)`, `openAll()` and `closeAll()`.
|
|
123
129
|
|
|
124
|
-
|
|
130
|
+
## Metadata Shape
|
|
125
131
|
|
|
126
132
|
```ts
|
|
127
|
-
const
|
|
133
|
+
const config: ExpansionMetadata = {
|
|
128
134
|
accordion: { multi: true },
|
|
129
135
|
panels: [
|
|
130
136
|
{
|
|
131
|
-
id: '
|
|
132
|
-
title: '
|
|
137
|
+
id: 'details',
|
|
138
|
+
title: 'Details',
|
|
133
139
|
expanded: true,
|
|
134
|
-
// Campos dinâmicos (renderizados ao abrir)
|
|
135
140
|
content: [
|
|
136
|
-
{ id: '
|
|
141
|
+
{ id: 'name', inputs: { field: { name: 'name', label: 'Name' } } },
|
|
137
142
|
],
|
|
138
143
|
},
|
|
139
144
|
{
|
|
140
|
-
id: '
|
|
141
|
-
title: '
|
|
142
|
-
// Widgets dinâmicos (renderizados ao abrir)
|
|
145
|
+
id: 'orders',
|
|
146
|
+
title: 'Orders',
|
|
143
147
|
widgets: [
|
|
144
|
-
{ id: 'praxis-table', inputs: {
|
|
148
|
+
{ id: 'praxis-table', inputs: { resourcePath: 'orders' } },
|
|
145
149
|
],
|
|
146
|
-
},
|
|
147
|
-
],
|
|
148
|
-
};
|
|
149
|
-
```
|
|
150
|
-
|
|
151
|
-
## Nested Ports e Conexoes
|
|
152
|
-
|
|
153
|
-
Para conectar widgets dentro de paineis a estado ou widgets externos, use `composition.links` com endpoint `component-port + nestedPath`.
|
|
154
|
-
|
|
155
|
-
Exemplo de output de chart dentro do painel `analytics`:
|
|
156
|
-
|
|
157
|
-
```json
|
|
158
|
-
{
|
|
159
|
-
"kind": "component-port",
|
|
160
|
-
"ref": {
|
|
161
|
-
"widget": "expansion-widget",
|
|
162
|
-
"nestedPath": [
|
|
163
|
-
{ "kind": "panel", "id": "analytics", "index": 0 },
|
|
164
|
-
{ "kind": "widget", "key": "payroll-chart", "componentType": "praxis-chart" }
|
|
165
|
-
],
|
|
166
|
-
"port": "pointClick",
|
|
167
|
-
"direction": "output"
|
|
168
|
-
}
|
|
169
|
-
}
|
|
170
|
-
```
|
|
171
|
-
|
|
172
|
-
Regras:
|
|
173
|
-
|
|
174
|
-
- `ref.widget` e a instancia top-level de `praxis-expansion`;
|
|
175
|
-
- o segmento terminal deve ser `kind: "widget"` com `key` estavel;
|
|
176
|
-
- `widgetEvent` permanece como bridge avancada/legado, nao como contrato principal;
|
|
177
|
-
- inputs nested devem atualizar o config declarativo do widget filho, inclusive quando o painel ainda nao montou por lazy loading.
|
|
178
|
-
|
|
179
|
-
## Action Row por painel
|
|
180
|
-
|
|
181
|
-
Adicione botões de ação no rodapé do painel com `actionButtons`. O evento é reemitido via `widgetEvent` com `output: 'action'`; trate esse fluxo como bridge avancada/legado para acoes de painel, nao como modelo principal de nested component ports.
|
|
182
|
-
|
|
183
|
-
```ts
|
|
184
|
-
const expansionConfig: ExpansionMetadata = {
|
|
185
|
-
panels: [
|
|
186
|
-
{
|
|
187
|
-
id: 'general',
|
|
188
|
-
title: 'Geral',
|
|
189
150
|
actionButtons: [
|
|
190
|
-
{ label: '
|
|
191
|
-
{ label: 'Cancelar', icon: 'close', action: 'cancel-general' },
|
|
151
|
+
{ label: 'Refresh', icon: 'refresh', action: 'refresh-orders' },
|
|
192
152
|
],
|
|
193
153
|
},
|
|
194
154
|
],
|
|
195
155
|
};
|
|
196
156
|
```
|
|
197
157
|
|
|
198
|
-
|
|
199
|
-
<praxis-expansion expansionId="expansion-demo"
|
|
200
|
-
[config]="expansionConfig"
|
|
201
|
-
(widgetEvent)="onExpansionEvent($event)">
|
|
202
|
-
</praxis-expansion>
|
|
203
|
-
```
|
|
204
|
-
|
|
205
|
-
```ts
|
|
206
|
-
onExpansionEvent(ev: { panelId?: string; panelIndex?: number; sourceId: string; output?: string; payload?: any }) {
|
|
207
|
-
if (ev.output === 'action') {
|
|
208
|
-
// ev.payload.action -> 'save-general' | 'cancel-general' | ...
|
|
209
|
-
}
|
|
210
|
-
}
|
|
211
|
-
```
|
|
212
|
-
|
|
213
|
-
## Defaults (heights e toggle) por instância
|
|
214
|
-
|
|
215
|
-
Você pode passar `defaultOptions` direto no componente, que tem precedência sobre os valores providos globalmente via provider.
|
|
216
|
-
|
|
217
|
-
```html
|
|
218
|
-
<praxis-expansion expansionId="expansion-demo"
|
|
219
|
-
[config]="expansionConfig"
|
|
220
|
-
[defaultOptions]="{ collapsedHeight: '48px', expandedHeight: '64px', hideToggle: false }">
|
|
221
|
-
</praxis-expansion>
|
|
222
|
-
```
|
|
223
|
-
|
|
224
|
-
## Controle programático: open/close/toggle/openAll/closeAll
|
|
225
|
-
|
|
226
|
-
O componente expõe métodos para controlar a expansão por índice (numérico) ou por id (string):
|
|
227
|
-
|
|
228
|
-
```html
|
|
229
|
-
<praxis-expansion expansionId="expansion-demo" #expRef [config]="expansionConfig"></praxis-expansion>
|
|
230
|
-
|
|
231
|
-
<button (click)="expRef.open('general')">Abrir Geral</button>
|
|
232
|
-
<button (click)="expRef.close(1)">Fechar painel 2</button>
|
|
233
|
-
<button (click)="expRef.toggle('advanced')">Alternar Avançado</button>
|
|
234
|
-
<button (click)="expRef.openAll()">Abrir todos</button>
|
|
235
|
-
<button (click)="expRef.closeAll()">Fechar todos</button>
|
|
236
|
-
```
|
|
237
|
-
|
|
238
|
-
## Eventos suportados
|
|
239
|
-
|
|
240
|
-
```html
|
|
241
|
-
<praxis-expansion expansionId="expansion-demo"
|
|
242
|
-
[config]="expansionConfig"
|
|
243
|
-
(opened)="onOpened($event)"
|
|
244
|
-
(afterExpand)="onAfterExpand($event)"
|
|
245
|
-
(expandedChange)="onExpandedChange($event)"
|
|
246
|
-
(afterCollapse)="onAfterCollapse($event)"
|
|
247
|
-
(closed)="onClosed($event)"
|
|
248
|
-
(destroyed)="onDestroyed($event)">
|
|
249
|
-
</praxis-expansion>
|
|
250
|
-
```
|
|
251
|
-
|
|
252
|
-
Cada evento inclui `{ panelId?: string; panelIndex: number }` (ou `expanded: boolean` no caso de `expandedChange`).
|
|
253
|
-
|
|
254
|
-
## Agentic Authoring
|
|
255
|
-
|
|
256
|
-
O contrato executavel de authoring fica em `PRAXIS_EXPANSION_AUTHORING_MANIFEST`.
|
|
257
|
-
Ele modela edicoes em `ExpansionMetadata` por operacoes atomicas sobre paineis,
|
|
258
|
-
cabecalhos, conteudo lazy, estado expandido/desabilitado e comportamento do
|
|
259
|
-
accordion.
|
|
260
|
-
|
|
261
|
-
Quando `enableCustomization` esta ativo, o runtime abre o `PraxisAiAssistantShellComponent`
|
|
262
|
-
com contexto semantico dos paineis e registra a sessao no dock global de assistentes.
|
|
263
|
-
O assistente envia estado atual, perfil dos paineis, campos de schema e referencia ao
|
|
264
|
-
manifesto de authoring para a IA. Patches JSON livres nao sao aplicados no runtime:
|
|
265
|
-
mudancas locais devem nascer de um `componentEditPlan` validado pelo manifesto, e
|
|
266
|
-
regras compartilhadas seguem por `domain-rules/intake`.
|
|
158
|
+
Panel `content` and `widgets` are rendered lazily with `matExpansionPanelContent`, so child runtime is created when the panel opens. Use stable `panels[].id` values; authoring, persistence and nested paths rely on them.
|
|
267
159
|
|
|
268
|
-
|
|
160
|
+
## Persistence And Authoring
|
|
269
161
|
|
|
270
|
-
|
|
271
|
-
- `panel.title.set`, `panel.description.set`, `panel.icon.set`
|
|
272
|
-
- `panel.disabled.set`
|
|
273
|
-
- `behavior.multiExpand.set`
|
|
274
|
-
- `behavior.defaultExpanded.set`
|
|
275
|
-
- `panel.content.set`
|
|
162
|
+
When `expansionId` is provided, configuration is stored under a key derived from route, component type, `expansionId` and optional `componentInstanceId`. `enableCustomization` opens Settings Panel editing and the governed semantic assistant flow.
|
|
276
163
|
|
|
277
|
-
|
|
278
|
-
com `content`, `widgets` ou `actionButtons` exige confirmacao explicita. Quando
|
|
279
|
-
`accordion.multi` estiver desabilitado, somente um painel pode ficar expandido por
|
|
280
|
-
padrao; o authoring deve colapsar os demais ou falhar validacao.
|
|
164
|
+
`PRAXIS_EXPANSION_AUTHORING_MANIFEST` describes supported AI/tooling operations for panel add/remove/order, titles, descriptions, icons, disabled state, default expanded state, multi-expand behavior and panel content. Free JSON patches are not the public authoring contract.
|
|
281
165
|
|
|
282
|
-
|
|
283
|
-
`affectedPaths`, `effects` e `submissionImpact` tipado. Edicoes de conteudo de
|
|
284
|
-
painel podem afetar dados schema-backed porque `panels[].content` hospeda
|
|
285
|
-
`FieldMetadata[]`; widgets filhos continuam governados pelos contratos dos
|
|
286
|
-
respectivos componentes.
|
|
166
|
+
## Public API Snapshot
|
|
287
167
|
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
Os tokens opcionais em `appearance.tokens` permitem customizações rápidas por instância; por exemplo:
|
|
291
|
-
|
|
292
|
-
```ts
|
|
293
|
-
const expansionConfig: ExpansionMetadata = {
|
|
294
|
-
appearance: { tokens: { 'header-background-color': 'rgba(0,0,0,0.04)' } },
|
|
295
|
-
panels: [ /* ... */ ],
|
|
296
|
-
};
|
|
297
|
-
``;
|
|
168
|
+
Main exports include `PraxisExpansion`, `ExpansionMetadata`, `PanelMetadata`, `PraxisExpansionConfigEditor`, `PraxisExpansionWidgetConfigEditor`, `providePraxisExpansionMetadata`, `providePraxisExpansionDefaults`, AI capability metadata and `PRAXIS_EXPANSION_AUTHORING_MANIFEST`.
|
|
298
169
|
|
|
299
|
-
##
|
|
170
|
+
## Official Links
|
|
300
171
|
|
|
301
|
-
|
|
172
|
+
- Documentation: https://praxisui.dev/components/expansion
|
|
173
|
+
- Live demo: https://praxis-ui-4e602.web.app
|
|
174
|
+
- Quickstart repository: https://github.com/codexrodrigues/praxis-ui-quickstart
|
|
175
|
+
- Source and issues: https://github.com/codexrodrigues/praxis-ui-angular
|
package/package.json
CHANGED
|
@@ -1,18 +1,18 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@praxisui/expansion",
|
|
3
|
-
"version": "9.0.0-beta.
|
|
3
|
+
"version": "9.0.0-beta.2",
|
|
4
4
|
"description": "Expansion panel (accordion) components for Praxis UI with metadata configuration and editor integration.",
|
|
5
5
|
"peerDependencies": {
|
|
6
6
|
"@angular/common": "^21.0.0",
|
|
7
7
|
"@angular/core": "^21.0.0",
|
|
8
8
|
"@angular/material": "^21.0.0",
|
|
9
9
|
"@angular/cdk": "^21.0.0",
|
|
10
|
-
"@praxisui/core": "^9.0.0-beta.
|
|
11
|
-
"@praxisui/dynamic-fields": "^9.0.0-beta.
|
|
12
|
-
"@praxisui/settings-panel": "^9.0.0-beta.
|
|
10
|
+
"@praxisui/core": "^9.0.0-beta.2",
|
|
11
|
+
"@praxisui/dynamic-fields": "^9.0.0-beta.2",
|
|
12
|
+
"@praxisui/settings-panel": "^9.0.0-beta.2",
|
|
13
13
|
"@angular/forms": "^21.0.0",
|
|
14
14
|
"@angular/router": "^21.0.0",
|
|
15
|
-
"@praxisui/ai": "^9.0.0-beta.
|
|
15
|
+
"@praxisui/ai": "^9.0.0-beta.2",
|
|
16
16
|
"rxjs": "~7.8.0"
|
|
17
17
|
},
|
|
18
18
|
"dependencies": {
|
|
@@ -24,7 +24,7 @@
|
|
|
24
24
|
},
|
|
25
25
|
"repository": {
|
|
26
26
|
"type": "git",
|
|
27
|
-
"url": "https://github.com/codexrodrigues/praxis-ui-angular"
|
|
27
|
+
"url": "git+https://github.com/codexrodrigues/praxis-ui-angular.git"
|
|
28
28
|
},
|
|
29
29
|
"homepage": "https://praxisui.dev",
|
|
30
30
|
"bugs": {
|