Skip to content

Commit

Permalink
feat: decouple DI from businessObject
Browse files Browse the repository at this point in the history
In the diagram `di` is now accessed via the diagram element, not the
business object. This has the benefit that elements in multiple diagrams
can easily be represented.

Related to #1472

BREAKING CHANGE:

* Instead of referencing the `di` from the business object, reference it
  from the diagram element representing it.
  • Loading branch information
marstamm authored and nikku committed Aug 27, 2021
1 parent 03352e8 commit 683715d
Show file tree
Hide file tree
Showing 7 changed files with 48 additions and 52 deletions.
13 changes: 0 additions & 13 deletions lib/BaseViewer.js
Original file line number Diff line number Diff line change
Expand Up @@ -528,19 +528,6 @@ BaseViewer.prototype.clear = function() {
return;
}

// remove businessObject#di binding
//
// this is necessary, as we establish the bindings
// in the BpmnTreeWalker (and assume none are given
// on reimport)
this.get('elementRegistry').forEach(function(element) {
var bo = element.businessObject;

if (bo && bo.di) {
delete bo.di;
}
});

// remove drawn elements
Diagram.prototype.clear.call(this);
};
Expand Down
2 changes: 1 addition & 1 deletion lib/draw/BpmnRenderUtil.js
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ export function isCollection(element) {
}

export function getDi(element) {
return element.businessObject.di;
return element.di;
}

export function getSemantic(element) {
Expand Down
39 changes: 20 additions & 19 deletions lib/import/BpmnImporter.js
Original file line number Diff line number Diff line change
Expand Up @@ -26,17 +26,18 @@ import {
} from './Util';


function elementData(semantic, attrs) {
function elementData(semantic, di, attrs) {
return assign({
id: semantic.id,
type: semantic.$type,
businessObject: semantic
businessObject: semantic,
di: di
}, attrs);
}

function getWaypoints(bo, source, target) {
function getWaypoints(di, source, target) {

var waypoints = bo.di.waypoint;
var waypoints = di.waypoint;

if (!waypoints || waypoints.length < 2) {
return [ getMid(source), getMid(target) ];
Expand Down Expand Up @@ -92,12 +93,12 @@ BpmnImporter.$inject = [
* Add bpmn element (semantic) to the canvas onto the
* specified parent shape.
*/
BpmnImporter.prototype.add = function(semantic, parentElement) {

var di = semantic.di,
element,
BpmnImporter.prototype.add = function(context, parentElement) {
var element,
translate = this._translate,
hidden;
hidden,
semantic = context.element,
di = context.di;

var parentIndex;

Expand All @@ -107,21 +108,21 @@ BpmnImporter.prototype.add = function(semantic, parentElement) {
if (is(di, 'bpmndi:BPMNPlane')) {

// add a virtual element (not being drawn)
element = this._elementFactory.createRoot(elementData(semantic));
element = this._elementFactory.createRoot(elementData(semantic, di));

this._canvas.setRootElement(element);
}

// SHAPE
else if (is(di, 'bpmndi:BPMNShape')) {

var collapsed = !isExpanded(semantic),
var collapsed = !isExpanded(semantic, di),
isFrame = isFrameElement(semantic);
hidden = parentElement && (parentElement.hidden || parentElement.collapsed);

var bounds = semantic.di.bounds;
var bounds = di.bounds;

element = this._elementFactory.createShape(elementData(semantic, {
element = this._elementFactory.createShape(elementData(semantic, di, {
collapsed: collapsed,
hidden: hidden,
x: Math.round(bounds.x),
Expand Down Expand Up @@ -159,11 +160,11 @@ BpmnImporter.prototype.add = function(semantic, parentElement) {

hidden = parentElement && (parentElement.hidden || parentElement.collapsed);

element = this._elementFactory.createConnection(elementData(semantic, {
element = this._elementFactory.createConnection(elementData(semantic, di, {
hidden: hidden,
source: source,
target: target,
waypoints: getWaypoints(semantic, source, target)
waypoints: getWaypoints(di, source, target)
}));

if (is(semantic, 'bpmn:DataAssociation')) {
Expand All @@ -190,7 +191,7 @@ BpmnImporter.prototype.add = function(semantic, parentElement) {

// (optional) LABEL
if (isLabelExternal(semantic) && getLabel(element)) {
this.addLabel(semantic, element);
this.addLabel(semantic, di, element);
}


Expand Down Expand Up @@ -239,12 +240,12 @@ BpmnImporter.prototype._attachBoundary = function(boundarySemantic, boundaryElem
/**
* add label for an element
*/
BpmnImporter.prototype.addLabel = function(semantic, element) {
BpmnImporter.prototype.addLabel = function(semantic, di, element) {
var bounds,
text,
label;

bounds = getExternalLabelBounds(semantic, element);
bounds = getExternalLabelBounds(di, element);

text = getLabel(element);

Expand All @@ -254,7 +255,7 @@ BpmnImporter.prototype.addLabel = function(semantic, element) {
bounds = this._textRenderer.getExternalLabelBounds(bounds, text);
}

label = this._elementFactory.createLabel(elementData(semantic, {
label = this._elementFactory.createLabel(elementData(semantic, di, {
id: semantic.id + '_label',
labelTarget: element,
type: 'label',
Expand Down
21 changes: 8 additions & 13 deletions lib/import/BpmnTreeWalker.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,17 +4,10 @@ import {
forEach
} from 'min-dash';

import Refs from 'object-refs';

import {
elementToString
} from './Util';

var diRefs = new Refs(
{ name: 'bpmnElement', enumerable: true },
{ name: 'di', configurable: true }
);

/**
* Returns true if an element has the given meta-model type
*
Expand Down Expand Up @@ -48,6 +41,8 @@ export default function BpmnTreeWalker(handler, translate) {
// prerequisites are drawn
var deferred = [];

var diMap = {};

// Helpers //////////////////////

function contextual(fn, ctx) {
Expand Down Expand Up @@ -76,17 +71,17 @@ export default function BpmnTreeWalker(handler, translate) {
}

// call handler
return handler.element(element, ctx);
return handler.element({ element: element, di: diMap[element.id] }, ctx);
}

function visitRoot(element, diagram) {
return handler.root(element, diagram);
return handler.root({ element: element, di: diMap[element.id] }, diagram);
}

function visitIfDi(element, ctx) {

try {
var gfx = element.di && visit(element, ctx);
var gfx = diMap[element.id] && visit(element, ctx);

handled(element);

Expand All @@ -109,16 +104,15 @@ export default function BpmnTreeWalker(handler, translate) {
var bpmnElement = di.bpmnElement;

if (bpmnElement) {
if (bpmnElement.di) {
if (diMap[bpmnElement.id]) {
logError(
translate('multiple DI elements defined for {element}', {
element: elementToString(bpmnElement)
}),
{ element: bpmnElement }
);
} else {
diRefs.bind(bpmnElement, 'di');
bpmnElement.di = di;
diMap[bpmnElement.id] = di;
}
} else {
logError(
Expand Down Expand Up @@ -175,6 +169,7 @@ export default function BpmnTreeWalker(handler, translate) {
}

// load DI from selected diagram only
diMap = {};
handleDiagram(diagram);


Expand Down
9 changes: 6 additions & 3 deletions lib/util/DiUtil.js
Original file line number Diff line number Diff line change
@@ -1,21 +1,24 @@
import {
is,
getBusinessObject
getBusinessObject,
getDi
} from './ModelUtil';

import {
forEach
} from 'min-dash';


export function isExpanded(element) {
export function isExpanded(element, di) {

if (is(element, 'bpmn:CallActivity')) {
return false;
}

if (is(element, 'bpmn:SubProcess')) {
return getBusinessObject(element).di && !!getBusinessObject(element).di.isExpanded;
di = di || getDi(element);

return di && !!di.isExpanded;
}

if (is(element, 'bpmn:Participant')) {
Expand Down
5 changes: 2 additions & 3 deletions lib/util/LabelUtil.js
Original file line number Diff line number Diff line change
Expand Up @@ -116,15 +116,14 @@ export function getExternalLabelMid(element) {
* Returns the bounds of an elements label, parsed from the elements DI or
* generated from its bounds.
*
* @param {BpmnElement} semantic
* @param {BpmndDi} di
* @param {djs.model.Base} element
*/
export function getExternalLabelBounds(semantic, element) {
export function getExternalLabelBounds(di, element) {

var mid,
size,
bounds,
di = semantic.di,
label = di.label;

if (label && label.bounds) {
Expand Down
11 changes: 11 additions & 0 deletions lib/util/ModelUtil.js
Original file line number Diff line number Diff line change
Expand Up @@ -22,4 +22,15 @@ export function is(element, type) {
*/
export function getBusinessObject(element) {
return (element && element.businessObject) || element;
}

/**
* Return the di object for a given element.
*
* @param {djs.model.Base} element
*
* @return {ModdleElement}
*/
export function getDi(element) {
return element && element.di;
}

0 comments on commit 683715d

Please sign in to comment.