@bpmn-nova/vue 0.3.1-preview → 0.3.3-preview
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 +123 -8
- package/dist/index.d.ts +99 -6
- package/dist/index.js +151 -19
- package/dist/styles.css +12 -3
- package/llms-full.txt +3322 -0
- package/llms.txt +236 -0
- package/package.json +6 -4
package/README.md
CHANGED
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
# @bpmn-nova/vue
|
|
2
2
|
|
|
3
|
-
BPMN Nova 的 Vue 3.3+ Adapter,提供 Studio、Designer、Viewer、审批轨迹、Properties 和 Expose 实例方法。
|
|
3
|
+
BPMN Nova 的 Vue 3.3+ Adapter,提供 Studio、Designer、Viewer、审批轨迹、Palette、Properties 和 Expose 实例方法。
|
|
4
4
|
|
|
5
5
|
> **English summary:** Vue 3.3+ components and exposed instance methods for BPMN Nova process design, viewing, approval traces, properties, themes, and SVG export.
|
|
6
6
|
|
|
7
|
-
> 当前版本为 `0.3.
|
|
7
|
+
> 当前版本为 `0.3.3-preview`。Vue 由宿主工程提供,本包不会替应用选择或升级框架版本。
|
|
8
8
|
|
|
9
9
|

|
|
10
10
|
|
|
@@ -20,6 +20,8 @@ import '@bpmn-nova/vue/styles.css'
|
|
|
20
20
|
|
|
21
21
|
只安装本包;`@bpmn-nova/studio` 会作为内部依赖自动解析。容器必须有明确高度。
|
|
22
22
|
|
|
23
|
+
使用代码生成助手或 IDE Agent 接入时,从随包的 `llms.txt` 开始;需要完整接口和定制资料时再读取 `llms-full.txt`。两份文件都包含在 npm tarball 中,不依赖源码仓库可见性。
|
|
24
|
+
|
|
23
25
|
## 流程设计
|
|
24
26
|
|
|
25
27
|
```vue
|
|
@@ -28,7 +30,7 @@ import { ref } from 'vue'
|
|
|
28
30
|
import { BpmnStudio } from '@bpmn-nova/vue'
|
|
29
31
|
import '@bpmn-nova/vue/styles.css'
|
|
30
32
|
|
|
31
|
-
defineProps({
|
|
33
|
+
const props = defineProps({ initialXml: String })
|
|
32
34
|
const studioRef = ref(null)
|
|
33
35
|
|
|
34
36
|
function handleChange(model, reason, nextXml) {
|
|
@@ -40,17 +42,126 @@ function handleChange(model, reason, nextXml) {
|
|
|
40
42
|
<div style="height: 720px">
|
|
41
43
|
<BpmnStudio
|
|
42
44
|
ref="studioRef"
|
|
43
|
-
:xml="
|
|
45
|
+
:xml="props.initialXml"
|
|
44
46
|
engine="flowable"
|
|
45
47
|
mode="design"
|
|
48
|
+
:allowed-modes="['design']"
|
|
49
|
+
theme="auto"
|
|
50
|
+
@change="handleChange"
|
|
51
|
+
/>
|
|
52
|
+
</div>
|
|
53
|
+
</template>
|
|
54
|
+
```
|
|
55
|
+
|
|
56
|
+
Expose 提供 `getActions()`、`validate()`、`exportXml()`、`fitView()`、`setTheme()`、`exportSvg()` 和 `openSvgExportPreview()`。
|
|
57
|
+
|
|
58
|
+
`xml`/`model` 是外部替换输入,`change` 的 XML 是草稿输出。宿主回写完全相同的导出 XML 不会重新导入或清空撤销历史;切换服务器 revision 或流程时传入不同 XML 会替换模型。Activiti 宿主应显式使用 `engine="activiti"`。
|
|
59
|
+
|
|
60
|
+
## 组合宿主头部与业务属性面板
|
|
61
|
+
|
|
62
|
+
默认 `BpmnStudio` 是包含 Header、Palette、Canvas、Properties 和 Statusbar 的完整工作台。下面的接入显式隐藏 Nova Properties,保留 Nova Palette,并只替换 Header 左侧品牌区:
|
|
63
|
+
|
|
64
|
+
```vue
|
|
65
|
+
<script setup>
|
|
66
|
+
import { ref } from 'vue'
|
|
67
|
+
import { BpmnStudio } from '@bpmn-nova/vue'
|
|
68
|
+
import '@bpmn-nova/vue/styles.css'
|
|
69
|
+
|
|
70
|
+
const studioRef = ref(null)
|
|
71
|
+
const selectedElement = ref(null)
|
|
72
|
+
const supportedNodeTypes = ['startEvent', 'userTask', 'exclusiveGateway', 'endEvent']
|
|
73
|
+
|
|
74
|
+
function handleSelectionChange(selection, element) {
|
|
75
|
+
selectedElement.value = selection ? element : null
|
|
76
|
+
}
|
|
77
|
+
</script>
|
|
78
|
+
|
|
79
|
+
<template>
|
|
80
|
+
<div class="process-design-workbench">
|
|
81
|
+
<BpmnStudio
|
|
82
|
+
ref="studioRef"
|
|
83
|
+
:xml="xml"
|
|
84
|
+
engine="activiti"
|
|
85
|
+
mode="design"
|
|
86
|
+
:allowed-modes="['design']"
|
|
87
|
+
:allowed-node-types="supportedNodeTypes"
|
|
88
|
+
:allowed-edge-types="['sequenceFlow']"
|
|
89
|
+
:regions="{ right: 'hidden' }"
|
|
46
90
|
theme="auto"
|
|
47
91
|
@change="handleChange"
|
|
92
|
+
@selection-change="handleSelectionChange"
|
|
93
|
+
@validation="handleValidation"
|
|
94
|
+
>
|
|
95
|
+
<template #header-start="{ state, actions }">
|
|
96
|
+
<button type="button" @click="back">← 返回审批列表</button>
|
|
97
|
+
<ApprovalIcon :icon="icon" />
|
|
98
|
+
<strong>{{ processName }}</strong>
|
|
99
|
+
<span>{{ processType }}</span>
|
|
100
|
+
</template>
|
|
101
|
+
<template #header-actions="{ actions, mode }">
|
|
102
|
+
<button type="button" :disabled="mode !== 'design'" @click="actions.validate()">校验</button>
|
|
103
|
+
<button type="button" :disabled="mode !== 'design'" @click="saveDraft(actions.exportXml())">保存</button>
|
|
104
|
+
<button type="button" :disabled="mode !== 'design'" @click="publishProcess(actions)">发布</button>
|
|
105
|
+
</template>
|
|
106
|
+
</BpmnStudio>
|
|
107
|
+
|
|
108
|
+
<DxProcessProperties
|
|
109
|
+
v-if="selectedElement"
|
|
110
|
+
:element-id="selectedElement.id"
|
|
48
111
|
/>
|
|
49
112
|
</div>
|
|
50
113
|
</template>
|
|
51
114
|
```
|
|
52
115
|
|
|
53
|
-
|
|
116
|
+
`header-start` 与 `header-actions` 使用 Vue Teleport 在当前应用内渲染,因此保留 provide/inject、响应式状态与组件生命周期。`header-actions` 只替换默认“校验 / 导入 / 导出”动作组,完整 `header` 的优先级更高。默认 Header 的最佳视图只保留在底部缩放区;若整个 Header 都不需要,配置 `regions.header = 'hidden'`。
|
|
117
|
+
|
|
118
|
+
`actions.validate()` 以 `toolbar` 来源先更新 Nova 默认状态栏,再发送 `validation` 事件并返回 issues;Expose `validate()` 使用 `api` 来源。事件的 `valid` 仅在存在 error 时为 `false`,warning 不默认阻止发布。保存与发布仍由宿主负责。
|
|
119
|
+
|
|
120
|
+
```js
|
|
121
|
+
async function publishProcess(actions) {
|
|
122
|
+
const issues = actions.validate()
|
|
123
|
+
if (issues.some((issue) => issue.level === 'error')) return
|
|
124
|
+
await publishXml(actions.exportXml())
|
|
125
|
+
}
|
|
126
|
+
```
|
|
127
|
+
|
|
128
|
+
编辑器属性面板应订阅 `selection-change`,该事件覆盖节点、连线、多选、清空和键盘选择。`element-click` 是点击观察事件,不能代替选择状态。宿主使用稳定 BPMN Element ID 关联业务配置,并自行拥有保存、发布、权限和服务端事务。
|
|
129
|
+
|
|
130
|
+
## Mode 双向同步与副标题刷新
|
|
131
|
+
|
|
132
|
+
```vue
|
|
133
|
+
<script setup>
|
|
134
|
+
import { ref } from 'vue'
|
|
135
|
+
|
|
136
|
+
const studioRef = ref(null)
|
|
137
|
+
const mode = ref('design')
|
|
138
|
+
const summaries = new Map()
|
|
139
|
+
const resolveSubtitle = ({ node }) => summaries.has(node.id)
|
|
140
|
+
? summaries.get(node.id)
|
|
141
|
+
: undefined
|
|
142
|
+
|
|
143
|
+
function updateSummary() {
|
|
144
|
+
summaries.set('ServiceTask_Archive', '归档到采购系统')
|
|
145
|
+
studioRef.value?.refreshPresentation()
|
|
146
|
+
}
|
|
147
|
+
</script>
|
|
148
|
+
|
|
149
|
+
<template>
|
|
150
|
+
<BpmnStudio
|
|
151
|
+
ref="studioRef"
|
|
152
|
+
v-model:mode="mode"
|
|
153
|
+
:allowed-modes="['design', 'viewer']"
|
|
154
|
+
:node-subtitle-resolver="resolveSubtitle"
|
|
155
|
+
@mode-change="event => console.log(event.source)"
|
|
156
|
+
>
|
|
157
|
+
<template #header-start="{ mode: actualMode }">
|
|
158
|
+
<HostHeader :mode="actualMode" />
|
|
159
|
+
</template>
|
|
160
|
+
</BpmnStudio>
|
|
161
|
+
</template>
|
|
162
|
+
```
|
|
163
|
+
|
|
164
|
+
Expose 的 `getMode()` / `setMode()` 使用 Shell 实际状态。Resolver 返回 `undefined` 保留默认值、`null` 移除副标题行、字符串替换显示;函数引用变化会自动刷新,稳定闭包内部数据变化需显式调用 `refreshPresentation()`。Resolver 只影响 Design/Viewer 标准卡片和 SVG,不覆盖 Instance Runtime Presentation,也不修改 XML、History、Selection 或 Viewport。
|
|
54
165
|
|
|
55
166
|
## 只读展示与审批轨迹
|
|
56
167
|
|
|
@@ -164,12 +275,16 @@ studioRef.value?.openSvgExportPreview({
|
|
|
164
275
|
|
|
165
276
|
本包还导出:
|
|
166
277
|
|
|
167
|
-
- `BpmnDesigner`、`BpmnCanvas`、`BpmnPropertiesPanel`
|
|
278
|
+
- `BpmnDesigner`、`BpmnCanvas`、`BpmnPalettePanel`、`BpmnPropertiesPanel`
|
|
168
279
|
- `useBpmnStudio`
|
|
169
280
|
- `createVuePropertyComponent`
|
|
170
281
|
- `createVueRuntimeDetailsComponent`
|
|
171
282
|
- `createVueRuntimeTransitionDetailsComponent`
|
|
172
283
|
- `createVueRuntimeTimelineComponent`
|
|
284
|
+
- `createStudioController`、`createEmptyProcess`、`importBpmn`、`exportBpmn`
|
|
285
|
+
- Palette、Properties、Context Menu、Icon 和 Template Registry 的公开创建函数
|
|
286
|
+
|
|
287
|
+
完整工作台可通过 `allowedNodeTypes` 与 `allowedEdgeTypes` 限制宿主支持的图元类型,通过 `allowedModes` 限制可切换的工作台模式。图元限制同时作用于 XML 导入、Palette、连接、快捷新增、模板和节点类型转换。
|
|
173
288
|
|
|
174
289
|
## 常见问题
|
|
175
290
|
|
|
@@ -181,11 +296,11 @@ studioRef.value?.openSvgExportPreview({
|
|
|
181
296
|
|
|
182
297
|
## 文档与 AI
|
|
183
298
|
|
|
299
|
+
- npm 包内 `llms.txt`:可执行安装入口
|
|
300
|
+
- npm 包内 `llms-full.txt`:完整 AI 上下文
|
|
184
301
|
- [完整项目能力](https://github.com/daxiangme/bpmn-nova)
|
|
185
302
|
- [React/Vue 组件说明](https://github.com/daxiangme/bpmn-nova/blob/dev/docs/COMPONENTS.md)
|
|
186
303
|
- [公开 Interface](https://github.com/daxiangme/bpmn-nova/blob/dev/docs/API.md)
|
|
187
|
-
- [AI 接入入口](https://raw.githubusercontent.com/daxiangme/bpmn-nova/dev/llms.txt)
|
|
188
|
-
- [AI 完整上下文](https://raw.githubusercontent.com/daxiangme/bpmn-nova/dev/llms-full.txt)
|
|
189
304
|
|
|
190
305
|
## License
|
|
191
306
|
|
package/dist/index.d.ts
CHANGED
|
@@ -1,8 +1,14 @@
|
|
|
1
|
-
import type { Component, DefineComponent } from 'vue'
|
|
2
|
-
import type { BpmnEdge, BpmnNode, ElementSelection, EngineId, LayoutOptions, ProcessModel } from '@bpmn-nova/studio'
|
|
1
|
+
import type { Component, DefineComponent, VNodeChild } from 'vue'
|
|
2
|
+
import type { BpmnEdge, BpmnNode, EdgeType, ElementSelection, EngineId, LayoutOptions, NodeType, ProcessModel } from '@bpmn-nova/studio'
|
|
3
3
|
import type { BpmnDesigner as DesignerInstance } from '@bpmn-nova/studio/designer'
|
|
4
4
|
import type { IconRegistry } from '@bpmn-nova/studio'
|
|
5
|
-
import type {
|
|
5
|
+
import type {
|
|
6
|
+
PaletteItemRenderer,
|
|
7
|
+
PalettePanel as PalettePanelInstance,
|
|
8
|
+
PaletteProvider,
|
|
9
|
+
PaletteRegistry,
|
|
10
|
+
PaletteSectionRenderer,
|
|
11
|
+
} from '@bpmn-nova/studio'
|
|
6
12
|
import type { PropertiesContext, PropertiesProvider, PropertiesRegistry, PropertyEntry } from '@bpmn-nova/studio'
|
|
7
13
|
import type { ProcessInstanceSnapshot } from '@bpmn-nova/studio/runtime'
|
|
8
14
|
import type { SvgExportArtifact, SvgExportOptions, SvgExportPreviewController } from '@bpmn-nova/studio/export-svg'
|
|
@@ -10,9 +16,17 @@ import type {
|
|
|
10
16
|
BpmnCanvas as CanvasInstance,
|
|
11
17
|
BpmnStudioController,
|
|
12
18
|
BpmnStudioShell,
|
|
19
|
+
ContextMenuRegistry,
|
|
13
20
|
InteractionController,
|
|
21
|
+
NodeSubtitleResolver,
|
|
14
22
|
StudioCommands,
|
|
23
|
+
StudioMode,
|
|
24
|
+
StudioModeChangeEvent,
|
|
25
|
+
StudioValidationEvent,
|
|
26
|
+
StudioValidationIssue,
|
|
27
|
+
StudioShellActions,
|
|
15
28
|
StudioShellOptions,
|
|
29
|
+
StudioShellRegions,
|
|
16
30
|
StudioShellSlots,
|
|
17
31
|
StudioState,
|
|
18
32
|
TemplateRegistry,
|
|
@@ -28,13 +42,41 @@ import type {
|
|
|
28
42
|
ViewerProjection,
|
|
29
43
|
} from '@bpmn-nova/studio/viewer'
|
|
30
44
|
|
|
45
|
+
export type {
|
|
46
|
+
NodeSubtitleResolver,
|
|
47
|
+
NodeSubtitleResolverContext,
|
|
48
|
+
StudioValidationEvent,
|
|
49
|
+
StudioValidationIssue,
|
|
50
|
+
StudioValidationSource,
|
|
51
|
+
} from '@bpmn-nova/studio'
|
|
52
|
+
|
|
53
|
+
export {
|
|
54
|
+
createContextMenuRegistry,
|
|
55
|
+
createDefaultContextMenuRegistry,
|
|
56
|
+
createDefaultIconRegistry,
|
|
57
|
+
createDefaultPaletteRegistry,
|
|
58
|
+
createDefaultPropertiesRegistry,
|
|
59
|
+
createEmptyProcess,
|
|
60
|
+
createPaletteRegistry,
|
|
61
|
+
createPropertiesRegistry,
|
|
62
|
+
createStudioController,
|
|
63
|
+
createTemplateRegistry,
|
|
64
|
+
exportBpmn,
|
|
65
|
+
importBpmn,
|
|
66
|
+
propertyEntry,
|
|
67
|
+
propertyGroup,
|
|
68
|
+
registerActivitiProperties,
|
|
69
|
+
registerBpmnProperties,
|
|
70
|
+
registerFlowableProperties,
|
|
71
|
+
} from '@bpmn-nova/studio'
|
|
72
|
+
|
|
31
73
|
export interface BpmnNovaVisualProps {
|
|
32
74
|
theme?: NovaThemeInput
|
|
33
75
|
runtimeAppearance?: RuntimeAppearanceOptions
|
|
34
76
|
onThemeChange?: (state: NovaThemeState) => void
|
|
35
77
|
}
|
|
36
78
|
export interface BpmnModelProps { model?: ProcessModel; xml?: string; engine?: EngineId }
|
|
37
|
-
export interface UseBpmnStudioOptions extends BpmnModelProps { studio?: BpmnStudioController; propertiesProfile?: 'business' | 'developer' }
|
|
79
|
+
export interface UseBpmnStudioOptions extends BpmnModelProps { studio?: BpmnStudioController; propertiesProfile?: 'business' | 'developer'; allowedNodeTypes?: NodeType[]; allowedEdgeTypes?: EdgeType[] }
|
|
38
80
|
export interface UseBpmnStudioResult { studio: BpmnStudioController; state: StudioState; commands: StudioCommands }
|
|
39
81
|
export function useBpmnStudio(options?: UseBpmnStudioOptions): UseBpmnStudioResult
|
|
40
82
|
|
|
@@ -45,28 +87,53 @@ export interface BpmnCanvasProps extends BpmnNovaVisualProps {
|
|
|
45
87
|
iconRegistry?: IconRegistry
|
|
46
88
|
nodeRenderers?: Record<string, Function>
|
|
47
89
|
nodeRenderer?: Function
|
|
90
|
+
nodeSubtitleResolver?: NodeSubtitleResolver
|
|
48
91
|
svgExport?: ViewerOptions['svgExport']
|
|
49
92
|
}
|
|
50
93
|
export interface BpmnCanvasExposed {
|
|
51
94
|
getCanvas(): CanvasInstance | null
|
|
52
95
|
fitView(): void
|
|
96
|
+
refreshPresentation(): void
|
|
53
97
|
setTheme(theme: NovaThemeInput): NovaThemeState | undefined
|
|
54
98
|
exportSvg(options?: SvgExportOptions): Promise<SvgExportArtifact> | undefined
|
|
55
99
|
openSvgExportPreview(options?: SvgExportOptions & { previewTitle?: string; onDownload?: (artifact: SvgExportArtifact) => void }): SvgExportPreviewController | undefined
|
|
56
100
|
}
|
|
57
101
|
export const BpmnCanvas: DefineComponent<BpmnCanvasProps>
|
|
58
102
|
|
|
103
|
+
export interface BpmnPalettePanelProps extends BpmnNovaVisualProps {
|
|
104
|
+
studio: BpmnStudioController
|
|
105
|
+
interactions?: InteractionController
|
|
106
|
+
templates?: TemplateRegistry
|
|
107
|
+
registry?: PaletteRegistry
|
|
108
|
+
providers?: PaletteProvider[]
|
|
109
|
+
canvas?: CanvasInstance | null
|
|
110
|
+
iconRegistry?: IconRegistry
|
|
111
|
+
renderItem?: PaletteItemRenderer
|
|
112
|
+
renderSection?: PaletteSectionRenderer
|
|
113
|
+
}
|
|
114
|
+
export interface BpmnPalettePanelExposed {
|
|
115
|
+
getPanel(): PalettePanelInstance | null
|
|
116
|
+
render(): void
|
|
117
|
+
setTheme(theme: NovaThemeInput): NovaThemeState | undefined
|
|
118
|
+
}
|
|
119
|
+
export const BpmnPalettePanel: DefineComponent<BpmnPalettePanelProps>
|
|
120
|
+
|
|
59
121
|
export interface BpmnStudioProps extends BpmnNovaVisualProps, BpmnModelProps {
|
|
60
122
|
studio?: BpmnStudioController
|
|
61
123
|
propertiesProfile?: 'business' | 'developer'
|
|
124
|
+
allowedNodeTypes?: NodeType[]
|
|
125
|
+
allowedEdgeTypes?: EdgeType[]
|
|
62
126
|
iconRegistry?: IconRegistry
|
|
63
127
|
paletteRegistry?: PaletteRegistry
|
|
64
128
|
propertiesRegistry?: PropertiesRegistry
|
|
65
129
|
templateRegistry?: TemplateRegistry
|
|
130
|
+
contextMenuRegistry?: ContextMenuRegistry
|
|
66
131
|
nodeRenderers?: Record<string, Function>
|
|
67
132
|
nodeRenderer?: Function
|
|
133
|
+
nodeSubtitleResolver?: NodeSubtitleResolver
|
|
68
134
|
slotsConfig?: StudioShellSlots
|
|
69
135
|
layout?: StudioShellOptions['layout']
|
|
136
|
+
regions?: StudioShellRegions
|
|
70
137
|
leftWidth?: number
|
|
71
138
|
rightWidth?: number
|
|
72
139
|
runtime?: ProcessInstanceSnapshot | null
|
|
@@ -85,7 +152,8 @@ export interface BpmnStudioProps extends BpmnNovaVisualProps, BpmnModelProps {
|
|
|
85
152
|
runtimeTraceOptions?: ViewerOptions['runtimeTraceOptions']
|
|
86
153
|
onTraceClick?: (event: RuntimeTraceClickEvent) => void
|
|
87
154
|
onElementClick?: ViewerOptions['onElementClick']
|
|
88
|
-
mode?:
|
|
155
|
+
mode?: StudioMode
|
|
156
|
+
allowedModes?: readonly StudioMode[]
|
|
89
157
|
projection?: ViewerProjection
|
|
90
158
|
responsive?: boolean
|
|
91
159
|
projectionOptions?: Array<{ value: ViewerProjection; label: string }>
|
|
@@ -93,13 +161,34 @@ export interface BpmnStudioProps extends BpmnNovaVisualProps, BpmnModelProps {
|
|
|
93
161
|
export interface BpmnStudioExposed {
|
|
94
162
|
getStudio(): BpmnStudioController
|
|
95
163
|
getShell(): BpmnStudioShell | null
|
|
164
|
+
getActions(): StudioShellActions | null
|
|
165
|
+
getMode(): StudioMode | undefined
|
|
166
|
+
getAllowedModes(): readonly StudioMode[]
|
|
167
|
+
setMode(mode: StudioMode): boolean
|
|
168
|
+
setAllowedModes(modes: readonly StudioMode[]): readonly StudioMode[]
|
|
169
|
+
refreshPresentation(): void
|
|
170
|
+
validate(): StudioValidationIssue[]
|
|
96
171
|
exportXml(engine?: EngineId): string
|
|
97
172
|
fitView(): void
|
|
98
173
|
setTheme(theme: NovaThemeInput): NovaThemeState | undefined
|
|
99
174
|
exportSvg(options?: SvgExportOptions): Promise<SvgExportArtifact> | undefined
|
|
100
175
|
openSvgExportPreview(options?: SvgExportOptions & { previewTitle?: string; onDownload?: (artifact: SvgExportArtifact) => void }): SvgExportPreviewController | null | undefined
|
|
101
176
|
}
|
|
102
|
-
export
|
|
177
|
+
export interface BpmnStudioSlotContext {
|
|
178
|
+
readonly studio: BpmnStudioController
|
|
179
|
+
readonly shell: BpmnStudioShell
|
|
180
|
+
readonly actions: StudioShellActions
|
|
181
|
+
readonly state: Readonly<StudioState>
|
|
182
|
+
readonly mode: StudioMode
|
|
183
|
+
}
|
|
184
|
+
export interface BpmnStudioSlots {
|
|
185
|
+
'header-start'?(context: BpmnStudioSlotContext): VNodeChild
|
|
186
|
+
'header-actions'?(context: BpmnStudioSlotContext): VNodeChild
|
|
187
|
+
header?(context: BpmnStudioSlotContext): VNodeChild
|
|
188
|
+
}
|
|
189
|
+
export const BpmnStudio: DefineComponent<BpmnStudioProps> & {
|
|
190
|
+
new(): { $slots: BpmnStudioSlots }
|
|
191
|
+
}
|
|
103
192
|
|
|
104
193
|
export interface BpmnDesignerProps extends BpmnNovaVisualProps, BpmnModelProps { svgExport?: ViewerOptions['svgExport'] }
|
|
105
194
|
export interface BpmnDesignerExposed {
|
|
@@ -119,6 +208,7 @@ export interface BpmnViewerProps extends BpmnNovaVisualProps, BpmnModelProps, Om
|
|
|
119
208
|
export interface BpmnViewerExposed {
|
|
120
209
|
getInstance(): ViewerInstance | null
|
|
121
210
|
fitView(): void
|
|
211
|
+
refreshPresentation(): void
|
|
122
212
|
setProjection(projection: ViewerProjection): void
|
|
123
213
|
setDisplayOptions(options: Parameters<ViewerInstance['setDisplayOptions']>[0]): void
|
|
124
214
|
setTheme(theme: NovaThemeInput): NovaThemeState | undefined
|
|
@@ -160,6 +250,9 @@ export interface BpmnStudioEmits {
|
|
|
160
250
|
'scope-change': [activeScopeId: string, scopePath: StudioState['scopePath'], state: StudioState]
|
|
161
251
|
'element-click': [payload: Parameters<NonNullable<ViewerOptions['onElementClick']>>[0]]
|
|
162
252
|
'trace-click': [payload: RuntimeTraceClickEvent]
|
|
253
|
+
'update:mode': [mode: StudioMode]
|
|
254
|
+
'mode-change': [event: StudioModeChangeEvent]
|
|
255
|
+
validation: [event: StudioValidationEvent]
|
|
163
256
|
}
|
|
164
257
|
export interface BpmnDesignerEmits {
|
|
165
258
|
change: [model: ProcessModel, reason: string, xml: string]
|
package/dist/index.js
CHANGED
|
@@ -1,9 +1,30 @@
|
|
|
1
|
-
import { createApp, defineComponent, h, onBeforeUnmount, onMounted, reactive, ref, watch } from 'vue';
|
|
1
|
+
import { Fragment, Teleport, createApp, defineComponent, h, onBeforeUnmount, onMounted, reactive, ref, watch } from 'vue';
|
|
2
2
|
import { BpmnDesigner as CoreDesigner } from '@bpmn-nova/studio/designer';
|
|
3
3
|
import { BpmnViewer as CoreViewer } from '@bpmn-nova/studio/viewer';
|
|
4
4
|
import { importBpmn, exportBpmn } from '@bpmn-nova/studio';
|
|
5
5
|
import { createEmptyProcess } from '@bpmn-nova/studio';
|
|
6
6
|
import { BpmnCanvas as CoreCanvas, BpmnStudioShell as CoreStudioShell, createInteractionController, createStudioController, createTemplateRegistry } from '@bpmn-nova/studio';
|
|
7
|
+
import { PalettePanel as CorePalettePanel, createDefaultPaletteRegistry as createCoreDefaultPaletteRegistry } from '@bpmn-nova/studio';
|
|
8
|
+
|
|
9
|
+
export {
|
|
10
|
+
createContextMenuRegistry,
|
|
11
|
+
createDefaultContextMenuRegistry,
|
|
12
|
+
createDefaultIconRegistry,
|
|
13
|
+
createDefaultPaletteRegistry,
|
|
14
|
+
createDefaultPropertiesRegistry,
|
|
15
|
+
createEmptyProcess,
|
|
16
|
+
createPaletteRegistry,
|
|
17
|
+
createPropertiesRegistry,
|
|
18
|
+
createStudioController,
|
|
19
|
+
createTemplateRegistry,
|
|
20
|
+
exportBpmn,
|
|
21
|
+
importBpmn,
|
|
22
|
+
propertyEntry,
|
|
23
|
+
propertyGroup,
|
|
24
|
+
registerActivitiProperties,
|
|
25
|
+
registerBpmnProperties,
|
|
26
|
+
registerFlowableProperties,
|
|
27
|
+
} from '@bpmn-nova/studio';
|
|
7
28
|
|
|
8
29
|
export function createVueRuntimeDetailsComponent(Component) {
|
|
9
30
|
return ({ container, ...context }) => {
|
|
@@ -28,7 +49,7 @@ function resolveModel(props) {
|
|
|
28
49
|
}
|
|
29
50
|
|
|
30
51
|
export function useBpmnStudio(options = {}) {
|
|
31
|
-
const studio = options.studio || createStudioController({ model: resolveModel(options), propertiesProfile: options.propertiesProfile });
|
|
52
|
+
const studio = options.studio || createStudioController({ model: resolveModel(options), propertiesProfile: options.propertiesProfile, allowedNodeTypes: options.allowedNodeTypes, allowedEdgeTypes: options.allowedEdgeTypes });
|
|
32
53
|
const state = reactive(studio.getState());
|
|
33
54
|
const off = studio.subscribe((event) => Object.assign(state, event.state));
|
|
34
55
|
onBeforeUnmount(() => { off(); if (!options.studio) studio.destroy(); });
|
|
@@ -37,56 +58,148 @@ export function useBpmnStudio(options = {}) {
|
|
|
37
58
|
|
|
38
59
|
export const BpmnCanvas = defineComponent({
|
|
39
60
|
name: 'BpmnNovaCanvas',
|
|
40
|
-
props: { studio: { type: Object, required: true }, interactions: Object, templates: Object, iconRegistry: Object, nodeRenderers: Object, nodeRenderer: Function, svgExport: Object, theme: [Object, String], onThemeChange: Function },
|
|
61
|
+
props: { studio: { type: Object, required: true }, interactions: Object, templates: Object, iconRegistry: Object, nodeRenderers: Object, nodeRenderer: Function, nodeSubtitleResolver: Function, svgExport: Object, theme: [Object, String], onThemeChange: Function },
|
|
41
62
|
setup(props, { expose, attrs }) {
|
|
42
63
|
const host = ref(null);
|
|
43
64
|
let canvas = null;
|
|
65
|
+
const nodeSubtitleResolver = (context) => props.nodeSubtitleResolver?.(context);
|
|
44
66
|
onMounted(() => {
|
|
45
67
|
const interactions = props.interactions || createInteractionController({ studio: props.studio, templates: props.templates || createTemplateRegistry() });
|
|
46
|
-
canvas = new CoreCanvas({ container: host.value, studio: props.studio, interactions, theme: props.theme, onThemeChange: props.onThemeChange, rendererOptions: { iconRegistry: props.iconRegistry, nodeRenderers: props.nodeRenderers, nodeRenderer: props.nodeRenderer, svgExport: props.svgExport } });
|
|
68
|
+
canvas = new CoreCanvas({ container: host.value, studio: props.studio, interactions, theme: props.theme, onThemeChange: props.onThemeChange, nodeSubtitleResolver, rendererOptions: { iconRegistry: props.iconRegistry, nodeRenderers: props.nodeRenderers, nodeRenderer: props.nodeRenderer, svgExport: props.svgExport } });
|
|
47
69
|
requestAnimationFrame(() => canvas.fitView());
|
|
48
70
|
});
|
|
49
71
|
onBeforeUnmount(() => canvas?.destroy());
|
|
50
72
|
watch(() => props.theme, (value) => { if (value !== undefined) canvas?.setTheme(value); });
|
|
51
|
-
|
|
73
|
+
watch(() => props.nodeSubtitleResolver, () => canvas?.refreshPresentation());
|
|
74
|
+
expose({ getCanvas: () => canvas, fitView: () => canvas?.fitView(), refreshPresentation: () => canvas?.refreshPresentation(), setTheme: (value) => canvas?.setTheme(value), exportSvg: (options) => canvas?.exportSvg(options), openSvgExportPreview: (options) => canvas?.openSvgExportPreview(options) });
|
|
52
75
|
return () => h('div', { ...attrs, ref: host, style: { width: '100%', height: '100%', minHeight: '320px', ...(attrs.style || {}) } });
|
|
53
76
|
},
|
|
54
77
|
});
|
|
55
78
|
|
|
79
|
+
export const BpmnPalettePanel = defineComponent({
|
|
80
|
+
name: 'BpmnNovaPalettePanel',
|
|
81
|
+
props: {
|
|
82
|
+
studio: { type: Object, required: true },
|
|
83
|
+
interactions: Object,
|
|
84
|
+
templates: Object,
|
|
85
|
+
registry: Object,
|
|
86
|
+
providers: Array,
|
|
87
|
+
canvas: Object,
|
|
88
|
+
iconRegistry: Object,
|
|
89
|
+
renderItem: Function,
|
|
90
|
+
renderSection: Function,
|
|
91
|
+
theme: [Object, String],
|
|
92
|
+
onThemeChange: Function,
|
|
93
|
+
},
|
|
94
|
+
setup(props, { expose, attrs }) {
|
|
95
|
+
const host = ref(null);
|
|
96
|
+
let panel = null;
|
|
97
|
+
|
|
98
|
+
const mountPanel = () => {
|
|
99
|
+
if (!host.value || !props.studio) return;
|
|
100
|
+
panel?.destroy();
|
|
101
|
+
const interactions = props.interactions || createInteractionController({ studio: props.studio, templates: props.templates || createTemplateRegistry() });
|
|
102
|
+
const registry = props.registry || createCoreDefaultPaletteRegistry({ providers: props.providers || [] });
|
|
103
|
+
panel = new CorePalettePanel({
|
|
104
|
+
container: host.value,
|
|
105
|
+
registry,
|
|
106
|
+
studio: props.studio,
|
|
107
|
+
interactions,
|
|
108
|
+
canvas: props.canvas || null,
|
|
109
|
+
iconRegistry: props.iconRegistry,
|
|
110
|
+
renderItem: props.renderItem,
|
|
111
|
+
renderSection: props.renderSection,
|
|
112
|
+
theme: props.theme,
|
|
113
|
+
onThemeChange: props.onThemeChange,
|
|
114
|
+
});
|
|
115
|
+
};
|
|
116
|
+
|
|
117
|
+
onMounted(mountPanel);
|
|
118
|
+
watch(() => [props.studio, props.registry, props.interactions, props.templates, props.canvas, props.providers, props.iconRegistry, props.renderItem, props.renderSection], mountPanel);
|
|
119
|
+
watch(() => props.theme, (value) => { if (value !== undefined) panel?.setTheme(value); });
|
|
120
|
+
onBeforeUnmount(() => panel?.destroy());
|
|
121
|
+
expose({ getPanel: () => panel, render: () => panel?.render(), setTheme: (value) => panel?.setTheme(value) });
|
|
122
|
+
return () => h('div', { ...attrs, ref: host, style: { width: '100%', height: '100%', overflow: 'auto', ...(attrs.style || {}) } });
|
|
123
|
+
},
|
|
124
|
+
});
|
|
125
|
+
|
|
56
126
|
export const BpmnStudio = defineComponent({
|
|
57
127
|
name: 'BpmnNovaStudio',
|
|
58
128
|
props: {
|
|
59
|
-
studio: Object, model: Object, xml: String, engine: { type: String, default: 'flowable' }, propertiesProfile: String,
|
|
60
|
-
iconRegistry: Object, paletteRegistry: Object, propertiesRegistry: Object, templateRegistry: Object,
|
|
61
|
-
nodeRenderers: Object, nodeRenderer: Function, slotsConfig: Object, layout: Function, leftWidth: Number, rightWidth: Number,
|
|
129
|
+
studio: Object, model: Object, xml: String, engine: { type: String, default: 'flowable' }, propertiesProfile: String, allowedNodeTypes: Array, allowedEdgeTypes: Array,
|
|
130
|
+
iconRegistry: Object, paletteRegistry: Object, propertiesRegistry: Object, templateRegistry: Object, contextMenuRegistry: Object,
|
|
131
|
+
nodeRenderers: Object, nodeRenderer: Function, nodeSubtitleResolver: Function, slotsConfig: Object, layout: Function, regions: Object, leftWidth: Number, rightWidth: Number,
|
|
62
132
|
runtime: Object, runtimePresenter: Function, runtimeTraceProjector: Function, runtimeAssetResolver: Function, runtimeTimelineRenderer: Function, onRuntimeTraceItemClick: Function, runtimeDetailsRenderer: Function, onRuntimeDetailsOpen: Function,
|
|
63
133
|
runtimeTransitionDetailsRenderer: Function, onRuntimeTransitionDetailsOpen: Function,
|
|
64
134
|
timeline: Object, runtimeDetails: Object, runtimeTraceOptions: Object, onTraceClick: Function, onElementClick: Function,
|
|
65
|
-
mode: String, projection: String, responsive: { type: Boolean, default: false }, projectionOptions: Array,
|
|
135
|
+
mode: String, allowedModes: Array, projection: String, responsive: { type: Boolean, default: false }, projectionOptions: Array,
|
|
66
136
|
theme: [Object, String], runtimeAppearance: Object, svgExport: Object, onThemeChange: Function,
|
|
67
137
|
},
|
|
68
|
-
emits: ['change', 'selection-change', 'scope-change', 'element-click', 'trace-click'],
|
|
69
|
-
setup(props, { emit, expose, attrs }) {
|
|
138
|
+
emits: ['change', 'selection-change', 'scope-change', 'element-click', 'trace-click', 'update:mode', 'mode-change', 'validation'],
|
|
139
|
+
setup(props, { emit, expose, attrs, slots }) {
|
|
70
140
|
const host = ref(null);
|
|
141
|
+
const headerTarget = ref(null);
|
|
142
|
+
const headerStartTarget = ref(null);
|
|
143
|
+
const headerActionsTarget = ref(null);
|
|
144
|
+
const headerContext = ref(null);
|
|
145
|
+
const headerStartContext = ref(null);
|
|
146
|
+
const headerActionsContext = ref(null);
|
|
71
147
|
const owned = !props.studio;
|
|
72
|
-
const studio = props.studio || createStudioController({ model: resolveModel(props), propertiesProfile: props.propertiesProfile });
|
|
148
|
+
const studio = props.studio || createStudioController({ model: resolveModel(props), propertiesProfile: props.propertiesProfile, allowedNodeTypes: props.allowedNodeTypes, allowedEdgeTypes: props.allowedEdgeTypes });
|
|
149
|
+
const state = reactive(studio.getState());
|
|
150
|
+
const actualMode = ref(props.mode || props.allowedModes?.[0] || 'design');
|
|
151
|
+
const nodeSubtitleResolver = (context) => props.nodeSubtitleResolver?.(context);
|
|
73
152
|
let shell = null;
|
|
74
153
|
let off = null;
|
|
154
|
+
let offMode = null;
|
|
155
|
+
let offValidation = null;
|
|
156
|
+
|
|
157
|
+
const createTeleportSlot = (target, contextRef) => (context) => {
|
|
158
|
+
target.value = context.container;
|
|
159
|
+
contextRef.value = context;
|
|
160
|
+
return () => {
|
|
161
|
+
if (target.value === context.container) target.value = null;
|
|
162
|
+
if (contextRef.value === context) contextRef.value = null;
|
|
163
|
+
};
|
|
164
|
+
};
|
|
165
|
+
|
|
75
166
|
onMounted(() => {
|
|
76
|
-
|
|
167
|
+
const shellSlots = { ...(props.slotsConfig || {}) };
|
|
168
|
+
if (slots.header) shellSlots.header = createTeleportSlot(headerTarget, headerContext);
|
|
169
|
+
else if (!shellSlots.header) {
|
|
170
|
+
if (slots['header-start']) shellSlots.headerStart = createTeleportSlot(headerStartTarget, headerStartContext);
|
|
171
|
+
if (slots['header-actions']) shellSlots.headerActions = createTeleportSlot(headerActionsTarget, headerActionsContext);
|
|
172
|
+
}
|
|
173
|
+
shell = new CoreStudioShell({ container: host.value, studio, iconRegistry: props.iconRegistry, paletteRegistry: props.paletteRegistry, propertiesRegistry: props.propertiesRegistry, templateRegistry: props.templateRegistry, contextMenuRegistry: props.contextMenuRegistry, rendererOptions: { nodeRenderers: props.nodeRenderers, nodeRenderer: props.nodeRenderer, nodeSubtitleResolver, runtimePresenter: props.runtimePresenter, runtimeTraceProjector: props.runtimeTraceProjector, runtimeAssetResolver: props.runtimeAssetResolver, runtimeTraceOptions: props.runtimeTraceOptions, runtimeTimelineRenderer: props.runtimeTimelineRenderer, timeline: props.timeline, runtimeDetails: props.runtimeDetails, onRuntimeTraceItemClick: (payload) => props.onRuntimeTraceItemClick?.(payload), runtimeDetailsRenderer: props.runtimeDetailsRenderer, onRuntimeDetailsOpen: (payload) => props.onRuntimeDetailsOpen?.(payload), runtimeTransitionDetailsRenderer: props.runtimeTransitionDetailsRenderer, onRuntimeTransitionDetailsOpen: (payload) => props.onRuntimeTransitionDetailsOpen?.(payload), onElementClick: (payload) => emit('element-click', payload), onTraceClick: (payload) => emit('trace-click', payload) }, slots: shellSlots, layout: props.layout, regions: props.regions, runtime: props.runtime, mode: props.mode, allowedModes: props.allowedModes, projection: props.projection, responsive: props.responsive, projectionOptions: props.projectionOptions, leftWidth: props.leftWidth, rightWidth: props.rightWidth, theme: props.theme, runtimeAppearance: props.runtimeAppearance, svgExport: props.svgExport, onThemeChange: props.onThemeChange });
|
|
174
|
+
actualMode.value = shell.getMode();
|
|
175
|
+
offMode = shell.subscribeMode((event) => {
|
|
176
|
+
actualMode.value = event.mode;
|
|
177
|
+
emit('update:mode', event.mode);
|
|
178
|
+
emit('mode-change', event);
|
|
179
|
+
});
|
|
180
|
+
offValidation = shell.subscribeValidation((event) => emit('validation', event));
|
|
77
181
|
off = studio.subscribe((event) => {
|
|
182
|
+
Object.assign(state, event.state);
|
|
78
183
|
if (event.type === 'modelChanged') emit('change', studio.model, event.reason, studio.exportXml());
|
|
79
184
|
if (event.type === 'selectionChanged') emit('selection-change', studio.selection, studio.getSelectedElement());
|
|
80
185
|
if (event.type === 'scopeChanged') emit('scope-change', event.activeScopeId, event.scopePath, studio.getState());
|
|
81
186
|
});
|
|
82
187
|
});
|
|
83
188
|
watch(() => props.model, (value) => { if (value && value !== studio.model) studio.setModel(value); });
|
|
84
|
-
watch(() => props.xml, (value) => {
|
|
189
|
+
watch(() => props.xml, (value) => {
|
|
190
|
+
if (value && value !== studio.exportXml(props.engine)) studio.importXml(value, props.engine);
|
|
191
|
+
});
|
|
85
192
|
watch(() => props.runtime, (value) => { if (value !== undefined) shell?.setRuntime(value); });
|
|
86
|
-
watch(() => props.mode, (
|
|
193
|
+
watch(() => [props.allowedModes, props.mode], ([allowedModes, mode]) => {
|
|
194
|
+
if (!shell) return;
|
|
195
|
+
if (allowedModes !== undefined) shell.setAllowedModes(allowedModes);
|
|
196
|
+
if (mode) shell.setMode(mode);
|
|
197
|
+
}, { deep: true });
|
|
87
198
|
watch(() => props.projection, (value) => { if (value) shell?.setProjection(value); });
|
|
199
|
+
watch(() => props.regions, (value) => { if (value !== undefined) shell?.setRegions(value); }, { deep: true });
|
|
88
200
|
watch(() => props.theme, (value) => { if (value !== undefined) shell?.setTheme(value); });
|
|
89
201
|
watch(() => props.runtimeAppearance, (value) => { if (value !== undefined) shell?.setRuntimeAppearance(value); });
|
|
202
|
+
watch(() => props.nodeSubtitleResolver, () => shell?.refreshPresentation());
|
|
90
203
|
watch(() => [props.timeline, props.runtimeDetails, props.runtimeTraceOptions], ([timeline, runtimeDetails, runtimeTraceOptions]) => {
|
|
91
204
|
if (!shell) return;
|
|
92
205
|
shell.rendererOptions.timeline = timeline;
|
|
@@ -94,9 +207,24 @@ export const BpmnStudio = defineComponent({
|
|
|
94
207
|
shell.rendererOptions.runtimeTraceOptions = runtimeTraceOptions;
|
|
95
208
|
shell.viewer?.setDisplayOptions({ timeline, runtimeDetails, runtimeTraceOptions });
|
|
96
209
|
});
|
|
97
|
-
onBeforeUnmount(() => { off?.(); shell?.destroy(); if (owned) studio.destroy(); });
|
|
98
|
-
expose({ getStudio: () => studio, getShell: () => shell, exportXml: (engine) => studio.exportXml(engine), exportSvg: (options) => shell?.exportSvg(options), openSvgExportPreview: (options) => shell?.openSvgExportPreview(options), fitView: () => shell?.
|
|
99
|
-
|
|
210
|
+
onBeforeUnmount(() => { offMode?.(); offValidation?.(); off?.(); shell?.destroy(); if (owned) studio.destroy(); });
|
|
211
|
+
expose({ getStudio: () => studio, getShell: () => shell, getActions: () => shell?.actions || null, getMode: () => shell?.getMode(), getAllowedModes: () => shell?.getAllowedModes() || [], setMode: (value) => shell?.setMode(value) || false, setAllowedModes: (value) => shell?.setAllowedModes(value) || [], refreshPresentation: () => shell?.refreshPresentation(), validate: () => shell?.validate() || [], exportXml: (engine) => studio.exportXml(engine), exportSvg: (options) => shell?.exportSvg(options), openSvgExportPreview: (options) => shell?.openSvgExportPreview(options), fitView: () => shell?.fitView(), setTheme: (value) => shell?.setTheme(value) });
|
|
212
|
+
const renderSlot = (name, target, contextRef) => {
|
|
213
|
+
if (!slots[name] || !target.value || !contextRef.value) return null;
|
|
214
|
+
return h(Teleport, { to: target.value }, slots[name]({
|
|
215
|
+
studio: contextRef.value.studio,
|
|
216
|
+
shell: contextRef.value.shell,
|
|
217
|
+
actions: contextRef.value.actions,
|
|
218
|
+
state,
|
|
219
|
+
mode: actualMode.value,
|
|
220
|
+
}));
|
|
221
|
+
};
|
|
222
|
+
return () => h(Fragment, null, [
|
|
223
|
+
h('div', { ...attrs, ref: host, style: { width: '100%', height: '100%', minHeight: '520px', ...(attrs.style || {}) } }),
|
|
224
|
+
renderSlot('header', headerTarget, headerContext),
|
|
225
|
+
renderSlot('header-start', headerStartTarget, headerStartContext),
|
|
226
|
+
renderSlot('header-actions', headerActionsTarget, headerActionsContext),
|
|
227
|
+
]);
|
|
100
228
|
},
|
|
101
229
|
});
|
|
102
230
|
|
|
@@ -162,6 +290,7 @@ export const BpmnViewer = defineComponent({
|
|
|
162
290
|
iconRegistry: Object,
|
|
163
291
|
nodeRenderers: Object,
|
|
164
292
|
nodeRenderer: Function,
|
|
293
|
+
nodeSubtitleResolver: Function,
|
|
165
294
|
timeline: Object,
|
|
166
295
|
runtimeDetails: Object,
|
|
167
296
|
runtimePresenter: Function,
|
|
@@ -187,6 +316,7 @@ export const BpmnViewer = defineComponent({
|
|
|
187
316
|
setup(props, { emit, expose, attrs }) {
|
|
188
317
|
const host = ref(null);
|
|
189
318
|
let instance = null;
|
|
319
|
+
const nodeSubtitleResolver = (context) => props.nodeSubtitleResolver?.(context);
|
|
190
320
|
onMounted(() => {
|
|
191
321
|
instance = new CoreViewer({
|
|
192
322
|
container: host.value,
|
|
@@ -195,6 +325,7 @@ export const BpmnViewer = defineComponent({
|
|
|
195
325
|
iconRegistry: props.iconRegistry,
|
|
196
326
|
nodeRenderers: props.nodeRenderers,
|
|
197
327
|
nodeRenderer: props.nodeRenderer,
|
|
328
|
+
nodeSubtitleResolver,
|
|
198
329
|
timeline: props.timeline,
|
|
199
330
|
runtimeDetails: props.runtimeDetails,
|
|
200
331
|
runtimePresenter: props.runtimePresenter,
|
|
@@ -224,10 +355,11 @@ export const BpmnViewer = defineComponent({
|
|
|
224
355
|
watch(() => props.projection, (value) => instance?.setProjection(value));
|
|
225
356
|
watch(() => props.theme, (value) => { if (value !== undefined) instance?.setTheme(value); });
|
|
226
357
|
watch(() => props.runtimeAppearance, (value) => { if (value !== undefined) instance?.setRuntimeAppearance(value); });
|
|
358
|
+
watch(() => props.nodeSubtitleResolver, () => instance?.refreshPresentation());
|
|
227
359
|
watch(() => [props.timeline, props.runtimeDetails, props.runtimeTraceOptions, props.runtimeAssetResolver], ([timeline, runtimeDetails, runtimeTraceOptions, runtimeAssetResolver]) => instance?.setDisplayOptions({ timeline, runtimeDetails, runtimeTraceOptions, runtimeAssetResolver }));
|
|
228
360
|
watch(() => props.model, (value) => { if (value) instance?.setModel(value); });
|
|
229
361
|
watch(() => props.xml, (value) => { if (value) instance?.setModel(importBpmn(value, props.engine)); });
|
|
230
|
-
expose({ getInstance: () => instance, fitView: () => instance?.fitView(), setProjection: (p) => instance?.setProjection(p), setDisplayOptions: (value) => instance?.setDisplayOptions(value), setTheme: (value) => instance?.setTheme(value), exportSvg: (options) => instance?.exportSvg(options), openSvgExportPreview: (options) => instance?.openSvgExportPreview(options) });
|
|
362
|
+
expose({ getInstance: () => instance, fitView: () => instance?.fitView(), refreshPresentation: () => instance?.refreshPresentation(), setProjection: (p) => instance?.setProjection(p), setDisplayOptions: (value) => instance?.setDisplayOptions(value), setTheme: (value) => instance?.setTheme(value), exportSvg: (options) => instance?.exportSvg(options), openSvgExportPreview: (options) => instance?.openSvgExportPreview(options) });
|
|
231
363
|
return () => h('div', { ...attrs, ref: host, style: { width: '100%', height: '100%', minHeight: '260px', ...(attrs.style || {}) } });
|
|
232
364
|
},
|
|
233
365
|
});
|