Agents as objects after generate
This commit is contained in:
parent
1016f9aac0
commit
2d8e3d60e1
|
@ -1,31 +1,43 @@
|
||||||
define(() => {
|
define(() => {
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
function mergeSets(target, b = null) {
|
function indexOf(list, element, equalityCheck = null) {
|
||||||
|
if(equalityCheck === null) {
|
||||||
|
return list.indexOf(element);
|
||||||
|
}
|
||||||
|
for(let i = 0; i < list.length; ++ i) {
|
||||||
|
if(equalityCheck(list[i], element)) {
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
function mergeSets(target, b = null, equalityCheck = null) {
|
||||||
if(!b) {
|
if(!b) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
for(let i = 0; i < b.length; ++ i) {
|
for(let i = 0; i < b.length; ++ i) {
|
||||||
if(target.indexOf(b[i]) === -1) {
|
if(indexOf(target, b[i], equalityCheck) === -1) {
|
||||||
target.push(b[i]);
|
target.push(b[i]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function removeAll(target, b = null) {
|
function removeAll(target, b = null, equalityCheck = null) {
|
||||||
if(!b) {
|
if(!b) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
for(let i = 0; i < b.length; ++ i) {
|
for(let i = 0; i < b.length; ++ i) {
|
||||||
const p = target.indexOf(b[i]);
|
const p = indexOf(target, b[i], equalityCheck);
|
||||||
if(p !== -1) {
|
if(p !== -1) {
|
||||||
target.splice(p, 1);
|
target.splice(p, 1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function remove(list, item) {
|
function remove(list, item, equalityCheck = null) {
|
||||||
const p = list.indexOf(item);
|
const p = indexOf(list, item, equalityCheck);
|
||||||
if(p !== -1) {
|
if(p !== -1) {
|
||||||
list.splice(p, 1);
|
list.splice(p, 1);
|
||||||
}
|
}
|
||||||
|
@ -36,6 +48,7 @@ define(() => {
|
||||||
}
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
|
indexOf,
|
||||||
mergeSets,
|
mergeSets,
|
||||||
removeAll,
|
removeAll,
|
||||||
remove,
|
remove,
|
||||||
|
|
|
@ -35,6 +35,17 @@ defineDescribe('ArrayUtilities', ['./ArrayUtilities'], (array) => {
|
||||||
array.mergeSets(p1, p2);
|
array.mergeSets(p1, p2);
|
||||||
expect(p1).toEqual(['a', 'x', 'c', 'd', 'e']);
|
expect(p1).toEqual(['a', 'x', 'c', 'd', 'e']);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('uses the given equality check function', () => {
|
||||||
|
const p1 = ['a', 'b', 'c', 'd'];
|
||||||
|
const p2 = ['b', 'B', 'E', 'e'];
|
||||||
|
array.mergeSets(
|
||||||
|
p1,
|
||||||
|
p2,
|
||||||
|
(a, b) => (a.toLowerCase() === b.toLowerCase())
|
||||||
|
);
|
||||||
|
expect(p1).toEqual(['a', 'b', 'c', 'd', 'E']);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('.removeAll', () => {
|
describe('.removeAll', () => {
|
||||||
|
@ -71,32 +82,53 @@ defineDescribe('ArrayUtilities', ['./ArrayUtilities'], (array) => {
|
||||||
array.removeAll(p1, p2);
|
array.removeAll(p1, p2);
|
||||||
expect(p1).toEqual(['a', 'x', 'd']);
|
expect(p1).toEqual(['a', 'x', 'd']);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('uses the given equality check function', () => {
|
||||||
|
const p1 = ['a', 'b', 'c', 'd'];
|
||||||
|
const p2 = ['B', 'e'];
|
||||||
|
array.removeAll(
|
||||||
|
p1,
|
||||||
|
p2,
|
||||||
|
(a, b) => (a.toLowerCase() === b.toLowerCase())
|
||||||
|
);
|
||||||
|
expect(p1).toEqual(['a', 'c', 'd']);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('.remove', () => {
|
describe('.remove', () => {
|
||||||
it('removes one element matching the parameter', () => {
|
it('removes one element matching the parameter', () => {
|
||||||
const p1 = ['a', 'b'];
|
const p1 = ['a', 'b'];
|
||||||
array.removeAll(p1, 'b');
|
array.remove(p1, 'b');
|
||||||
expect(p1).toEqual(['a']);
|
expect(p1).toEqual(['a']);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('removes only the first element matching the parameter', () => {
|
it('removes only the first element matching the parameter', () => {
|
||||||
const p1 = ['a', 'b', 'c', 'b'];
|
const p1 = ['a', 'b', 'c', 'b'];
|
||||||
array.removeAll(p1, 'b');
|
array.remove(p1, 'b');
|
||||||
expect(p1).toEqual(['a', 'c', 'b']);
|
expect(p1).toEqual(['a', 'c', 'b']);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('ignores if not found', () => {
|
it('ignores if not found', () => {
|
||||||
const p1 = ['a', 'b', 'c'];
|
const p1 = ['a', 'b', 'c'];
|
||||||
array.removeAll(p1, 'nope');
|
array.remove(p1, 'nope');
|
||||||
expect(p1).toEqual(['a', 'b', 'c']);
|
expect(p1).toEqual(['a', 'b', 'c']);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('maintains input ordering', () => {
|
it('maintains input ordering', () => {
|
||||||
const p1 = ['a', 'b', 'c'];
|
const p1 = ['a', 'b', 'c'];
|
||||||
array.removeAll(p1, 'b');
|
array.remove(p1, 'b');
|
||||||
expect(p1).toEqual(['a', 'c']);
|
expect(p1).toEqual(['a', 'c']);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('uses the given equality check function', () => {
|
||||||
|
const p1 = ['a', 'b', 'c', 'd'];
|
||||||
|
array.remove(
|
||||||
|
p1,
|
||||||
|
'B',
|
||||||
|
(a, b) => (a.toLowerCase() === b.toLowerCase())
|
||||||
|
);
|
||||||
|
expect(p1).toEqual(['a', 'c', 'd']);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('.last', () => {
|
describe('.last', () => {
|
||||||
|
|
|
@ -8,6 +8,22 @@ define(['core/ArrayUtilities'], (array) => {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function agentEqCheck(a, b) {
|
||||||
|
return a.name === b.name;
|
||||||
|
}
|
||||||
|
|
||||||
|
function makeAgent(name, {anchorRight = false} = {}) {
|
||||||
|
return {name, anchorRight};
|
||||||
|
}
|
||||||
|
|
||||||
|
function convertAgent(agent) {
|
||||||
|
return makeAgent(agent.name);
|
||||||
|
}
|
||||||
|
|
||||||
|
function getAgentName(agent) {
|
||||||
|
return agent.name;
|
||||||
|
}
|
||||||
|
|
||||||
const LOCKED_AGENT = new AgentState(false, true);
|
const LOCKED_AGENT = new AgentState(false, true);
|
||||||
const DEFAULT_AGENT = new AgentState(false);
|
const DEFAULT_AGENT = new AgentState(false);
|
||||||
|
|
||||||
|
@ -30,12 +46,14 @@ define(['core/ArrayUtilities'], (array) => {
|
||||||
this.stageHandlers = {
|
this.stageHandlers = {
|
||||||
'mark': this.handleMark.bind(this),
|
'mark': this.handleMark.bind(this),
|
||||||
'async': this.handleAsync.bind(this),
|
'async': this.handleAsync.bind(this),
|
||||||
'note over': this.handleNote.bind(this),
|
|
||||||
'note left': this.handleNote.bind(this),
|
|
||||||
'note right': this.handleNote.bind(this),
|
|
||||||
'agent define': this.handleAgentDefine.bind(this),
|
'agent define': this.handleAgentDefine.bind(this),
|
||||||
'agent begin': this.handleAgentBegin.bind(this),
|
'agent begin': this.handleAgentBegin.bind(this),
|
||||||
'agent end': this.handleAgentEnd.bind(this),
|
'agent end': this.handleAgentEnd.bind(this),
|
||||||
|
'connection': this.handleConnection.bind(this),
|
||||||
|
'note over': this.handleNote.bind(this),
|
||||||
|
'note left': this.handleNote.bind(this),
|
||||||
|
'note right': this.handleNote.bind(this),
|
||||||
|
'note between': this.handleNote.bind(this),
|
||||||
'block begin': this.handleBlockBegin.bind(this),
|
'block begin': this.handleBlockBegin.bind(this),
|
||||||
'block split': this.handleBlockSplit.bind(this),
|
'block split': this.handleBlockSplit.bind(this),
|
||||||
'block end': this.handleBlockEnd.bind(this),
|
'block end': this.handleBlockEnd.bind(this),
|
||||||
|
@ -44,14 +62,14 @@ define(['core/ArrayUtilities'], (array) => {
|
||||||
}
|
}
|
||||||
|
|
||||||
addBounds(target, agentL, agentR, involvedAgents = null) {
|
addBounds(target, agentL, agentR, involvedAgents = null) {
|
||||||
array.remove(target, agentL);
|
array.remove(target, agentL, agentEqCheck);
|
||||||
array.remove(target, agentR);
|
array.remove(target, agentR, agentEqCheck);
|
||||||
|
|
||||||
let indexL = 0;
|
let indexL = 0;
|
||||||
let indexR = target.length;
|
let indexR = target.length;
|
||||||
if(involvedAgents) {
|
if(involvedAgents) {
|
||||||
const found = (involvedAgents
|
const found = (involvedAgents
|
||||||
.map((agent) => target.indexOf(agent))
|
.map((agent) => array.indexOf(target, agent, agentEqCheck))
|
||||||
.filter((p) => (p !== -1))
|
.filter((p) => (p !== -1))
|
||||||
);
|
);
|
||||||
indexL = found.reduce((a, b) => Math.min(a, b), target.length);
|
indexL = found.reduce((a, b) => Math.min(a, b), target.length);
|
||||||
|
@ -62,9 +80,21 @@ define(['core/ArrayUtilities'], (array) => {
|
||||||
target.splice(indexR + 1, 0, agentR);
|
target.splice(indexR + 1, 0, agentR);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
addStage(stage, isVisible = true) {
|
||||||
|
this.currentSection.stages.push(stage);
|
||||||
|
if(isVisible) {
|
||||||
|
this.currentNest.hasContent = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
defineAgents(agents) {
|
||||||
|
array.mergeSets(this.currentNest.agents, agents, agentEqCheck);
|
||||||
|
array.mergeSets(this.agents, agents, agentEqCheck);
|
||||||
|
}
|
||||||
|
|
||||||
setAgentVis(agents, visible, mode, checked = false) {
|
setAgentVis(agents, visible, mode, checked = false) {
|
||||||
const filteredAgents = agents.filter((agent) => {
|
const filteredAgents = agents.filter((agent) => {
|
||||||
const state = this.agentStates.get(agent) || DEFAULT_AGENT;
|
const state = this.agentStates.get(agent.name) || DEFAULT_AGENT;
|
||||||
if(state.locked) {
|
if(state.locked) {
|
||||||
if(checked) {
|
if(checked) {
|
||||||
throw new Error('Cannot begin/end agent: ' + agent);
|
throw new Error('Cannot begin/end agent: ' + agent);
|
||||||
|
@ -78,33 +108,32 @@ define(['core/ArrayUtilities'], (array) => {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
filteredAgents.forEach((agent) => {
|
filteredAgents.forEach((agent) => {
|
||||||
const state = this.agentStates.get(agent);
|
const state = this.agentStates.get(agent.name);
|
||||||
if(state) {
|
if(state) {
|
||||||
state.visible = visible;
|
state.visible = visible;
|
||||||
} else {
|
} else {
|
||||||
this.agentStates.set(agent, new AgentState(visible));
|
this.agentStates.set(agent.name, new AgentState(visible));
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
const type = (visible ? 'agent begin' : 'agent end');
|
const type = (visible ? 'agent begin' : 'agent end');
|
||||||
const existing = array.last(this.currentSection.stages) || {};
|
const existing = array.last(this.currentSection.stages) || {};
|
||||||
|
const agentNames = filteredAgents.map(getAgentName);
|
||||||
if(existing.type === type && existing.mode === mode) {
|
if(existing.type === type && existing.mode === mode) {
|
||||||
array.mergeSets(existing.agents, filteredAgents);
|
array.mergeSets(existing.agentNames, agentNames);
|
||||||
} else {
|
} else {
|
||||||
this.currentSection.stages.push({
|
this.addStage({
|
||||||
type,
|
type,
|
||||||
agents: filteredAgents,
|
agentNames,
|
||||||
mode,
|
mode,
|
||||||
});
|
});
|
||||||
this.currentNest.hasContent = true;
|
|
||||||
}
|
}
|
||||||
array.mergeSets(this.currentNest.agents, filteredAgents);
|
this.defineAgents(filteredAgents);
|
||||||
array.mergeSets(this.agents, filteredAgents);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
beginNested(mode, label, name) {
|
beginNested(mode, label, name) {
|
||||||
const nameL = name + '[';
|
const leftAgent = makeAgent(name + '[', {anchorRight: true});
|
||||||
const nameR = name + ']';
|
const rightAgent = makeAgent(name + ']');
|
||||||
const agents = [nameL, nameR];
|
const agents = [leftAgent, rightAgent];
|
||||||
const stages = [];
|
const stages = [];
|
||||||
this.currentSection = {
|
this.currentSection = {
|
||||||
mode,
|
mode,
|
||||||
|
@ -113,57 +142,80 @@ define(['core/ArrayUtilities'], (array) => {
|
||||||
};
|
};
|
||||||
this.currentNest = {
|
this.currentNest = {
|
||||||
agents,
|
agents,
|
||||||
|
leftAgent,
|
||||||
|
rightAgent,
|
||||||
hasContent: false,
|
hasContent: false,
|
||||||
stage: {
|
stage: {
|
||||||
type: 'block',
|
type: 'block',
|
||||||
sections: [this.currentSection],
|
sections: [this.currentSection],
|
||||||
left: nameL,
|
left: leftAgent.name,
|
||||||
right: nameR,
|
right: rightAgent.name,
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
this.agentStates.set(nameL, LOCKED_AGENT);
|
this.agentStates.set(leftAgent.name, LOCKED_AGENT);
|
||||||
this.agentStates.set(nameR, LOCKED_AGENT);
|
this.agentStates.set(rightAgent.name, LOCKED_AGENT);
|
||||||
this.nesting.push(this.currentNest);
|
this.nesting.push(this.currentNest);
|
||||||
|
|
||||||
return {agents, stages};
|
return {agents, stages};
|
||||||
}
|
}
|
||||||
|
|
||||||
handleMark(stage) {
|
handleMark({name}) {
|
||||||
this.markers.add(stage.name);
|
this.markers.add(name);
|
||||||
this.currentSection.stages.push(stage);
|
this.addStage({type: 'mark', name}, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
handleAsync(stage) {
|
handleAsync({target}) {
|
||||||
if(stage.target !== '' && !this.markers.has(stage.target)) {
|
if(target !== '' && !this.markers.has(target)) {
|
||||||
throw new Error('Unknown marker: ' + stage.target);
|
throw new Error('Unknown marker: ' + target);
|
||||||
}
|
}
|
||||||
this.currentSection.stages.push(stage);
|
this.addStage({type: 'async', target}, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
handleNote(stage) {
|
handleConnection({agents, label, line, left, right}) {
|
||||||
if(stage.agents.length === 0) {
|
const colAgents = agents.map(convertAgent);
|
||||||
this.handleUnknownStage(Object.assign({}, stage, {
|
this.setAgentVis(colAgents, true, 'box');
|
||||||
agents: NOTE_DEFAULT_AGENTS[stage.type] || [],
|
this.defineAgents(colAgents);
|
||||||
}));
|
|
||||||
|
this.addStage({
|
||||||
|
type: 'connection',
|
||||||
|
agentNames: agents.map(getAgentName),
|
||||||
|
label,
|
||||||
|
line,
|
||||||
|
left,
|
||||||
|
right,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
handleNote({type, agents, mode, label}) {
|
||||||
|
let colAgents = null;
|
||||||
|
if(agents.length === 0) {
|
||||||
|
colAgents = NOTE_DEFAULT_AGENTS[type] || [];
|
||||||
} else {
|
} else {
|
||||||
this.handleUnknownStage(stage);
|
colAgents = agents.map(convertAgent);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
this.setAgentVis(colAgents, true, 'box');
|
||||||
|
this.defineAgents(colAgents);
|
||||||
|
|
||||||
|
this.addStage({
|
||||||
|
type,
|
||||||
|
agentNames: colAgents.map(getAgentName),
|
||||||
|
mode,
|
||||||
|
label,
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
handleAgentDefine({agents}) {
|
handleAgentDefine({agents}) {
|
||||||
const agentNames = agents.map((agent) => agent.name);
|
const colAgents = agents.map(convertAgent);
|
||||||
array.mergeSets(this.currentNest.agents, agentNames);
|
this.defineAgents(colAgents);
|
||||||
array.mergeSets(this.agents, agentNames);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
handleAgentBegin({agents, mode}) {
|
handleAgentBegin({agents, mode}) {
|
||||||
const agentNames = agents.map((agent) => agent.name);
|
this.setAgentVis(agents.map(convertAgent), true, mode, true);
|
||||||
this.setAgentVis(agentNames, true, mode, true);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
handleAgentEnd({agents, mode}) {
|
handleAgentEnd({agents, mode}) {
|
||||||
const agentNames = agents.map((agent) => agent.name);
|
this.setAgentVis(agents.map(convertAgent), false, mode, true);
|
||||||
this.setAgentVis(agentNames, false, mode, true);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
handleBlockBegin({mode, label}) {
|
handleBlockBegin({mode, label}) {
|
||||||
|
@ -192,45 +244,23 @@ define(['core/ArrayUtilities'], (array) => {
|
||||||
if(this.nesting.length <= 1) {
|
if(this.nesting.length <= 1) {
|
||||||
throw new Error('Invalid block nesting (too many "end"s)');
|
throw new Error('Invalid block nesting (too many "end"s)');
|
||||||
}
|
}
|
||||||
const {hasContent, stage, agents} = this.nesting.pop();
|
const nested = this.nesting.pop();
|
||||||
this.currentNest = array.last(this.nesting);
|
this.currentNest = array.last(this.nesting);
|
||||||
this.currentSection = array.last(this.currentNest.stage.sections);
|
this.currentSection = array.last(this.currentNest.stage.sections);
|
||||||
if(hasContent) {
|
if(nested.hasContent) {
|
||||||
array.mergeSets(this.currentNest.agents, agents);
|
this.defineAgents(nested.agents);
|
||||||
array.mergeSets(this.agents, agents);
|
|
||||||
this.addBounds(
|
this.addBounds(
|
||||||
this.agents,
|
this.agents,
|
||||||
stage.left,
|
nested.leftAgent,
|
||||||
stage.right,
|
nested.rightAgent,
|
||||||
agents
|
nested.agents
|
||||||
);
|
);
|
||||||
this.currentSection.stages.push(stage);
|
this.addStage(nested.stage);
|
||||||
this.currentNest.hasContent = true;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
handleUnknownStage(stage) {
|
|
||||||
if(stage.agents) {
|
|
||||||
const agentNames = stage.agents.map((agent) => agent.name);
|
|
||||||
this.setAgentVis(agentNames, true, 'box');
|
|
||||||
array.mergeSets(this.currentNest.agents, agentNames);
|
|
||||||
array.mergeSets(this.agents, agentNames);
|
|
||||||
this.currentSection.stages.push(Object.assign({}, stage, {
|
|
||||||
agents: agentNames,
|
|
||||||
}));
|
|
||||||
} else {
|
|
||||||
this.currentSection.stages.push(stage);
|
|
||||||
}
|
|
||||||
this.currentNest.hasContent = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
handleStage(stage) {
|
handleStage(stage) {
|
||||||
const handler = this.stageHandlers[stage.type];
|
this.stageHandlers[stage.type](stage);
|
||||||
if(handler) {
|
|
||||||
handler(stage);
|
|
||||||
} else {
|
|
||||||
this.handleUnknownStage(stage);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
generate({stages, meta = {}}) {
|
generate({stages, meta = {}}) {
|
||||||
|
@ -254,8 +284,8 @@ define(['core/ArrayUtilities'], (array) => {
|
||||||
|
|
||||||
this.addBounds(
|
this.addBounds(
|
||||||
this.agents,
|
this.agents,
|
||||||
this.currentNest.stage.left,
|
this.currentNest.leftAgent,
|
||||||
this.currentNest.stage.right
|
this.currentNest.rightAgent
|
||||||
);
|
);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
|
|
|
@ -3,13 +3,122 @@ defineDescribe('Sequence Generator', ['./Generator'], (Generator) => {
|
||||||
|
|
||||||
const generator = new Generator();
|
const generator = new Generator();
|
||||||
|
|
||||||
const AGENT_DEFINE = 'agent define';
|
const parsed = {
|
||||||
const AGENT_BEGIN = 'agent begin';
|
blockBegin: (mode, label) => {
|
||||||
const AGENT_END = 'agent end';
|
return {type: 'block begin', mode, label};
|
||||||
|
},
|
||||||
|
|
||||||
const BLOCK_BEGIN = 'block begin';
|
blockSplit: (mode, label) => {
|
||||||
const BLOCK_SPLIT = 'block split';
|
return {type: 'block split', mode, label};
|
||||||
const BLOCK_END = 'block end';
|
},
|
||||||
|
|
||||||
|
blockEnd: () => {
|
||||||
|
return {type: 'block end'};
|
||||||
|
},
|
||||||
|
|
||||||
|
defineAgents: (agentNames) => {
|
||||||
|
return {
|
||||||
|
type: 'agent define',
|
||||||
|
agents: agentNames.map((name) => ({name})),
|
||||||
|
};
|
||||||
|
},
|
||||||
|
|
||||||
|
beginAgents: (agentNames, {mode = 'box'} = {}) => {
|
||||||
|
return {
|
||||||
|
type: 'agent begin',
|
||||||
|
agents: agentNames.map((name) => ({name})),
|
||||||
|
mode,
|
||||||
|
};
|
||||||
|
},
|
||||||
|
|
||||||
|
endAgents: (agentNames, {mode = 'cross'} = {}) => {
|
||||||
|
return {
|
||||||
|
type: 'agent end',
|
||||||
|
agents: agentNames.map((name) => ({name})),
|
||||||
|
mode,
|
||||||
|
};
|
||||||
|
},
|
||||||
|
|
||||||
|
connect: (agentNames, {
|
||||||
|
label = '',
|
||||||
|
line = '',
|
||||||
|
left = false,
|
||||||
|
right = false,
|
||||||
|
} = {}) => {
|
||||||
|
return {
|
||||||
|
type: 'connection',
|
||||||
|
agents: agentNames.map((name) => ({name})),
|
||||||
|
label,
|
||||||
|
line,
|
||||||
|
left,
|
||||||
|
right,
|
||||||
|
};
|
||||||
|
},
|
||||||
|
|
||||||
|
note: (agentNames, {
|
||||||
|
type = 'note over',
|
||||||
|
mode = '',
|
||||||
|
label = '',
|
||||||
|
} = {}) => {
|
||||||
|
return {
|
||||||
|
type,
|
||||||
|
agents: agentNames.map((name) => ({name})),
|
||||||
|
mode,
|
||||||
|
label,
|
||||||
|
};
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
const generated = {
|
||||||
|
beginAgents: (agentNames, {
|
||||||
|
mode = jasmine.anything(),
|
||||||
|
} = {}) => {
|
||||||
|
return {
|
||||||
|
type: 'agent begin',
|
||||||
|
agentNames,
|
||||||
|
mode,
|
||||||
|
};
|
||||||
|
},
|
||||||
|
|
||||||
|
endAgents: (agentNames, {
|
||||||
|
mode = jasmine.anything(),
|
||||||
|
} = {}) => {
|
||||||
|
return {
|
||||||
|
type: 'agent end',
|
||||||
|
agentNames,
|
||||||
|
mode,
|
||||||
|
};
|
||||||
|
},
|
||||||
|
|
||||||
|
connect: (agentNames, {
|
||||||
|
label = jasmine.anything(),
|
||||||
|
line = jasmine.anything(),
|
||||||
|
left = jasmine.anything(),
|
||||||
|
right = jasmine.anything(),
|
||||||
|
} = {}) => {
|
||||||
|
return {
|
||||||
|
type: 'connection',
|
||||||
|
agentNames,
|
||||||
|
label,
|
||||||
|
line,
|
||||||
|
left,
|
||||||
|
right,
|
||||||
|
};
|
||||||
|
},
|
||||||
|
|
||||||
|
note: (agentNames, {
|
||||||
|
type = jasmine.anything(),
|
||||||
|
mode = jasmine.anything(),
|
||||||
|
label = jasmine.anything(),
|
||||||
|
} = {}) => {
|
||||||
|
return {
|
||||||
|
type,
|
||||||
|
agentNames,
|
||||||
|
mode,
|
||||||
|
label,
|
||||||
|
};
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
describe('.generate', () => {
|
describe('.generate', () => {
|
||||||
it('propagates title metadata', () => {
|
it('propagates title metadata', () => {
|
||||||
|
@ -28,7 +137,10 @@ defineDescribe('Sequence Generator', ['./Generator'], (Generator) => {
|
||||||
|
|
||||||
it('includes implicit hidden left/right agents', () => {
|
it('includes implicit hidden left/right agents', () => {
|
||||||
const sequence = generator.generate({stages: []});
|
const sequence = generator.generate({stages: []});
|
||||||
expect(sequence.agents).toEqual(['[', ']']);
|
expect(sequence.agents).toEqual([
|
||||||
|
{name: '[', anchorRight: true},
|
||||||
|
{name: ']', anchorRight: false},
|
||||||
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('passes marks and async through', () => {
|
it('passes marks and async through', () => {
|
||||||
|
@ -53,39 +165,54 @@ defineDescribe('Sequence Generator', ['./Generator'], (Generator) => {
|
||||||
|
|
||||||
it('returns aggregated agents', () => {
|
it('returns aggregated agents', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: '<-', agents: [{name: 'C'}, {name: 'D'}]},
|
parsed.connect(['C', 'D']),
|
||||||
{type: AGENT_BEGIN, agents: [{name: 'E'}], mode: 'box'},
|
parsed.beginAgents(['E']),
|
||||||
]});
|
]});
|
||||||
expect(sequence.agents).toEqual(
|
expect(sequence.agents).toEqual([
|
||||||
['[', 'A', 'B', 'C', 'D', 'E', ']']
|
{name: '[', anchorRight: true},
|
||||||
);
|
{name: 'A', anchorRight: false},
|
||||||
|
{name: 'B', anchorRight: false},
|
||||||
|
{name: 'C', anchorRight: false},
|
||||||
|
{name: 'D', anchorRight: false},
|
||||||
|
{name: 'E', anchorRight: false},
|
||||||
|
{name: ']', anchorRight: false},
|
||||||
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('always puts the implicit right agent on the right', () => {
|
it('always puts the implicit right agent on the right', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: '->', agents: [{name: ']'}, {name: 'B'}]},
|
parsed.connect([']', 'B']),
|
||||||
]});
|
]});
|
||||||
expect(sequence.agents).toEqual(['[', 'B', ']']);
|
expect(sequence.agents).toEqual([
|
||||||
|
{name: '[', anchorRight: true},
|
||||||
|
{name: 'B', anchorRight: false},
|
||||||
|
{name: ']', anchorRight: false},
|
||||||
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('accounts for define calls when ordering agents', () => {
|
it('accounts for define calls when ordering agents', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: AGENT_DEFINE, agents: [{name: 'B'}]},
|
parsed.defineAgents(['B']),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
]});
|
]});
|
||||||
expect(sequence.agents).toEqual(['[', 'B', 'A', ']']);
|
expect(sequence.agents).toEqual([
|
||||||
|
{name: '[', anchorRight: true},
|
||||||
|
{name: 'B', anchorRight: false},
|
||||||
|
{name: 'A', anchorRight: false},
|
||||||
|
{name: ']', anchorRight: false},
|
||||||
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('creates implicit begin stages for agents when used', () => {
|
it('creates implicit begin stages for agents when used', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: '->', agents: [{name: 'B'}, {name: 'C'}]},
|
parsed.connect(['B', 'C']),
|
||||||
]});
|
]});
|
||||||
expect(sequence.stages).toEqual([
|
expect(sequence.stages).toEqual([
|
||||||
{type: AGENT_BEGIN, agents: ['A', 'B'], mode: 'box'},
|
generated.beginAgents(['A', 'B']),
|
||||||
jasmine.anything(),
|
jasmine.anything(),
|
||||||
{type: AGENT_BEGIN, agents: ['C'], mode: 'box'},
|
generated.beginAgents(['C']),
|
||||||
jasmine.anything(),
|
jasmine.anything(),
|
||||||
jasmine.anything(),
|
jasmine.anything(),
|
||||||
]);
|
]);
|
||||||
|
@ -93,11 +220,32 @@ defineDescribe('Sequence Generator', ['./Generator'], (Generator) => {
|
||||||
|
|
||||||
it('passes connections through', () => {
|
it('passes connections through', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
]});
|
]});
|
||||||
expect(sequence.stages).toEqual([
|
expect(sequence.stages).toEqual([
|
||||||
jasmine.anything(),
|
jasmine.anything(),
|
||||||
{type: '->', agents: ['A', 'B']},
|
generated.connect(['A', 'B']),
|
||||||
|
jasmine.anything(),
|
||||||
|
]);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('propagates connection information', () => {
|
||||||
|
const sequence = generator.generate({stages: [
|
||||||
|
parsed.connect(['A', 'B'], {
|
||||||
|
label: 'foo',
|
||||||
|
line: 'bar',
|
||||||
|
left: true,
|
||||||
|
right: false,
|
||||||
|
}),
|
||||||
|
]});
|
||||||
|
expect(sequence.stages).toEqual([
|
||||||
|
jasmine.anything(),
|
||||||
|
generated.connect(['A', 'B'], {
|
||||||
|
label: 'foo',
|
||||||
|
line: 'bar',
|
||||||
|
left: true,
|
||||||
|
right: false,
|
||||||
|
}),
|
||||||
jasmine.anything(),
|
jasmine.anything(),
|
||||||
]);
|
]);
|
||||||
});
|
});
|
||||||
|
@ -108,189 +256,182 @@ defineDescribe('Sequence Generator', ['./Generator'], (Generator) => {
|
||||||
terminators: 'foo',
|
terminators: 'foo',
|
||||||
},
|
},
|
||||||
stages: [
|
stages: [
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
],
|
],
|
||||||
});
|
});
|
||||||
expect(sequence.stages).toEqual([
|
expect(sequence.stages).toEqual([
|
||||||
jasmine.anything(),
|
jasmine.anything(),
|
||||||
jasmine.anything(),
|
jasmine.anything(),
|
||||||
{type: AGENT_END, agents: ['A', 'B'], mode: 'foo'},
|
generated.endAgents(['A', 'B'], {mode: 'foo'}),
|
||||||
|
]);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('defaults to mode "none" for implicit end stages', () => {
|
||||||
|
const sequence = generator.generate({stages: [
|
||||||
|
parsed.connect(['A', 'B']),
|
||||||
|
]});
|
||||||
|
expect(sequence.stages).toEqual([
|
||||||
|
jasmine.anything(),
|
||||||
|
jasmine.anything(),
|
||||||
|
generated.endAgents(['A', 'B'], {mode: 'none'}),
|
||||||
|
]);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('defaults to mode "cross" for explicit end stages', () => {
|
||||||
|
const sequence = generator.generate({stages: [
|
||||||
|
parsed.connect(['A', 'B']),
|
||||||
|
parsed.endAgents(['A', 'B']),
|
||||||
|
]});
|
||||||
|
expect(sequence.stages).toEqual([
|
||||||
|
jasmine.anything(),
|
||||||
|
jasmine.anything(),
|
||||||
|
generated.endAgents(['A', 'B'], {mode: 'cross'}),
|
||||||
]);
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('does not create duplicate begin stages', () => {
|
it('does not create duplicate begin stages', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: AGENT_BEGIN, agents: [
|
parsed.beginAgents(['A', 'B', 'C']),
|
||||||
{name: 'A'},
|
parsed.connect(['A', 'B']),
|
||||||
{name: 'B'},
|
parsed.connect(['B', 'C']),
|
||||||
{name: 'C'},
|
|
||||||
], mode: 'box'},
|
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
|
||||||
{type: '->', agents: [{name: 'B'}, {name: 'C'}]},
|
|
||||||
]});
|
]});
|
||||||
expect(sequence.stages).toEqual([
|
expect(sequence.stages).toEqual([
|
||||||
{type: AGENT_BEGIN, agents: ['A', 'B', 'C'], mode: 'box'},
|
generated.beginAgents(['A', 'B', 'C']),
|
||||||
{type: '->', agents: jasmine.anything()},
|
generated.connect(jasmine.anything()),
|
||||||
{type: '->', agents: jasmine.anything()},
|
generated.connect(jasmine.anything()),
|
||||||
{type: AGENT_END, agents: ['A', 'B', 'C'], mode: 'none'},
|
generated.endAgents(['A', 'B', 'C']),
|
||||||
]);
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('redisplays agents if they have been hidden', () => {
|
it('redisplays agents if they have been hidden', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: AGENT_BEGIN, agents: [
|
parsed.beginAgents(['A', 'B']),
|
||||||
{name: 'A'},
|
parsed.connect(['A', 'B']),
|
||||||
{name: 'B'},
|
parsed.endAgents(['B']),
|
||||||
], mode: 'box'},
|
parsed.connect(['A', 'B']),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
|
||||||
{type: AGENT_END, agents: [{name: 'B'}], mode: 'cross'},
|
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
|
||||||
]});
|
]});
|
||||||
expect(sequence.stages).toEqual([
|
expect(sequence.stages).toEqual([
|
||||||
{type: AGENT_BEGIN, agents: ['A', 'B'], mode: 'box'},
|
|
||||||
jasmine.anything(),
|
jasmine.anything(),
|
||||||
{type: AGENT_END, agents: ['B'], mode: 'cross'},
|
|
||||||
{type: AGENT_BEGIN, agents: ['B'], mode: 'box'},
|
|
||||||
jasmine.anything(),
|
jasmine.anything(),
|
||||||
{type: AGENT_END, agents: ['A', 'B'], mode: 'none'},
|
generated.endAgents(['B']),
|
||||||
|
generated.beginAgents(['B']),
|
||||||
|
jasmine.anything(),
|
||||||
|
jasmine.anything(),
|
||||||
]);
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('collapses adjacent begin statements', () => {
|
it('collapses adjacent begin statements', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: AGENT_BEGIN, agents: [{name: 'D'}], mode: 'box'},
|
parsed.beginAgents(['D']),
|
||||||
{type: '->', agents: [{name: 'B'}, {name: 'C'}]},
|
parsed.connect(['B', 'C']),
|
||||||
{type: '->', agents: [{name: 'C'}, {name: 'D'}]},
|
parsed.connect(['C', 'D']),
|
||||||
]});
|
]});
|
||||||
expect(sequence.stages).toEqual([
|
expect(sequence.stages).toEqual([
|
||||||
{type: AGENT_BEGIN, agents: ['A', 'B'], mode: 'box'},
|
generated.beginAgents(['A', 'B']),
|
||||||
{type: '->', agents: jasmine.anything()},
|
generated.connect(jasmine.anything()),
|
||||||
{type: AGENT_BEGIN, agents: ['D', 'C'], mode: 'box'},
|
generated.beginAgents(['D', 'C']),
|
||||||
{type: '->', agents: jasmine.anything()},
|
generated.connect(jasmine.anything()),
|
||||||
{type: '->', agents: jasmine.anything()},
|
generated.connect(jasmine.anything()),
|
||||||
jasmine.anything(),
|
jasmine.anything(),
|
||||||
]);
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('removes superfluous begin statements', () => {
|
it('removes superfluous begin statements', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: AGENT_BEGIN, agents: [
|
parsed.beginAgents(['A', 'C', 'D']),
|
||||||
{name: 'A'},
|
parsed.beginAgents(['C', 'E']),
|
||||||
{name: 'C'},
|
|
||||||
{name: 'D'},
|
|
||||||
], mode: 'box'},
|
|
||||||
{type: AGENT_BEGIN, agents: [
|
|
||||||
{name: 'C'},
|
|
||||||
{name: 'E'},
|
|
||||||
], mode: 'box'},
|
|
||||||
]});
|
]});
|
||||||
expect(sequence.stages).toEqual([
|
expect(sequence.stages).toEqual([
|
||||||
{type: AGENT_BEGIN, agents: ['A', 'B'], mode: 'box'},
|
generated.beginAgents(['A', 'B']),
|
||||||
{type: '->', agents: jasmine.anything()},
|
generated.connect(jasmine.anything()),
|
||||||
{type: AGENT_BEGIN, agents: ['C', 'D', 'E'], mode: 'box'},
|
generated.beginAgents(['C', 'D', 'E']),
|
||||||
jasmine.anything(),
|
jasmine.anything(),
|
||||||
]);
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('removes superfluous end statements', () => {
|
it('removes superfluous end statements', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: AGENT_DEFINE, agents: [{name: 'E'}]},
|
parsed.defineAgents(['E']),
|
||||||
{type: AGENT_BEGIN, agents: [
|
parsed.beginAgents(['C', 'D']),
|
||||||
{name: 'C'},
|
parsed.connect(['A', 'B']),
|
||||||
{name: 'D'},
|
parsed.endAgents(['A', 'B', 'C']),
|
||||||
], mode: 'box'},
|
parsed.endAgents(['A', 'D', 'E']),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
|
||||||
{type: AGENT_END, agents: [
|
|
||||||
{name: 'A'},
|
|
||||||
{name: 'B'},
|
|
||||||
{name: 'C'},
|
|
||||||
], mode: 'cross'},
|
|
||||||
{type: AGENT_END, agents: [
|
|
||||||
{name: 'A'},
|
|
||||||
{name: 'D'},
|
|
||||||
{name: 'E'},
|
|
||||||
], mode: 'cross'},
|
|
||||||
]});
|
]});
|
||||||
expect(sequence.stages).toEqual([
|
expect(sequence.stages).toEqual([
|
||||||
jasmine.anything(),
|
jasmine.anything(),
|
||||||
{type: '->', agents: jasmine.anything()},
|
generated.connect(jasmine.anything()),
|
||||||
{type: AGENT_END, agents: ['A', 'B', 'C', 'D'], mode: 'cross'},
|
generated.endAgents(['A', 'B', 'C', 'D']),
|
||||||
]);
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('does not merge different modes of end', () => {
|
it('does not merge different modes of end', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: AGENT_BEGIN, agents: [
|
parsed.beginAgents(['C', 'D']),
|
||||||
{name: 'C'},
|
parsed.connect(['A', 'B']),
|
||||||
{name: 'D'},
|
parsed.endAgents(['A', 'B', 'C']),
|
||||||
], mode: 'box'},
|
|
||||||
{type: '->', agents: [
|
|
||||||
{name: 'A'},
|
|
||||||
{name: 'B'},
|
|
||||||
]},
|
|
||||||
{type: AGENT_END, agents: [
|
|
||||||
{name: 'A'},
|
|
||||||
{name: 'B'},
|
|
||||||
{name: 'C'},
|
|
||||||
], mode: 'cross'},
|
|
||||||
]});
|
]});
|
||||||
expect(sequence.stages).toEqual([
|
expect(sequence.stages).toEqual([
|
||||||
jasmine.anything(),
|
jasmine.anything(),
|
||||||
{type: '->', agents: jasmine.anything()},
|
generated.connect(jasmine.anything()),
|
||||||
{type: AGENT_END, agents: ['A', 'B', 'C'], mode: 'cross'},
|
generated.endAgents(['A', 'B', 'C'], {mode: 'cross'}),
|
||||||
{type: AGENT_END, agents: ['D'], mode: 'none'},
|
generated.endAgents(['D'], {mode: 'none'}),
|
||||||
]);
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('creates virtual agents for block statements', () => {
|
it('creates virtual agents for block statements', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
]});
|
]});
|
||||||
|
|
||||||
expect(sequence.agents).toEqual(
|
expect(sequence.agents).toEqual([
|
||||||
['[', '__BLOCK0[', 'A', 'B', '__BLOCK0]', ']']
|
{name: '[', anchorRight: true},
|
||||||
);
|
{name: '__BLOCK0[', anchorRight: true},
|
||||||
|
{name: 'A', anchorRight: false},
|
||||||
|
{name: 'B', anchorRight: false},
|
||||||
|
{name: '__BLOCK0]', anchorRight: false},
|
||||||
|
{name: ']', anchorRight: false},
|
||||||
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('positions virtual block agents near involved agents', () => {
|
it('positions virtual block agents near involved agents', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: '->', agents: [{name: 'C'}, {name: 'D'}]},
|
parsed.connect(['C', 'D']),
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: '->', agents: [{name: 'E'}, {name: 'F'}]},
|
parsed.connect(['E', 'F']),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
{type: '->', agents: [{name: 'G'}, {name: 'H'}]},
|
parsed.connect(['G', 'H']),
|
||||||
]});
|
]});
|
||||||
|
|
||||||
expect(sequence.agents).toEqual([
|
expect(sequence.agents).toEqual([
|
||||||
'[',
|
{name: '[', anchorRight: true},
|
||||||
'A',
|
{name: 'A', anchorRight: false},
|
||||||
'B',
|
{name: 'B', anchorRight: false},
|
||||||
'__BLOCK0[',
|
{name: '__BLOCK0[', anchorRight: true},
|
||||||
'C',
|
{name: 'C', anchorRight: false},
|
||||||
'D',
|
{name: 'D', anchorRight: false},
|
||||||
'__BLOCK1[',
|
{name: '__BLOCK1[', anchorRight: true},
|
||||||
'E',
|
{name: 'E', anchorRight: false},
|
||||||
'F',
|
{name: 'F', anchorRight: false},
|
||||||
'__BLOCK1]',
|
{name: '__BLOCK1]', anchorRight: false},
|
||||||
'__BLOCK0]',
|
{name: '__BLOCK0]', anchorRight: false},
|
||||||
'G',
|
{name: 'G', anchorRight: false},
|
||||||
'H',
|
{name: 'H', anchorRight: false},
|
||||||
']',
|
{name: ']', anchorRight: false},
|
||||||
]);
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('records virtual block agent names in blocks', () => {
|
it('records virtual block agent names in blocks', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
]});
|
]});
|
||||||
|
|
||||||
const block0 = sequence.stages[0];
|
const block0 = sequence.stages[0];
|
||||||
|
@ -301,47 +442,47 @@ defineDescribe('Sequence Generator', ['./Generator'], (Generator) => {
|
||||||
|
|
||||||
it('records all sections within blocks', () => {
|
it('records all sections within blocks', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: BLOCK_SPLIT, mode: 'else', label: 'xyz'},
|
parsed.blockSplit('else', 'xyz'),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'C'}]},
|
parsed.connect(['A', 'C']),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
]});
|
]});
|
||||||
|
|
||||||
const block0 = sequence.stages[0];
|
const block0 = sequence.stages[0];
|
||||||
expect(block0.sections).toEqual([
|
expect(block0.sections).toEqual([
|
||||||
{mode: 'if', label: 'abc', stages: [
|
{mode: 'if', label: 'abc', stages: [
|
||||||
{type: AGENT_BEGIN, agents: ['A', 'B'], mode: 'box'},
|
generated.beginAgents(['A', 'B']),
|
||||||
{type: '->', agents: ['A', 'B']},
|
generated.connect(['A', 'B']),
|
||||||
]},
|
]},
|
||||||
{mode: 'else', label: 'xyz', stages: [
|
{mode: 'else', label: 'xyz', stages: [
|
||||||
{type: AGENT_BEGIN, agents: ['C'], mode: 'box'},
|
generated.beginAgents(['C']),
|
||||||
{type: '->', agents: ['A', 'C']},
|
generated.connect(['A', 'C']),
|
||||||
]},
|
]},
|
||||||
]);
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('records virtual block agents in nested blocks', () => {
|
it('records virtual block agents in nested blocks', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: BLOCK_SPLIT, mode: 'else', label: 'xyz'},
|
parsed.blockSplit('else', 'xyz'),
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'def'},
|
parsed.blockBegin('if', 'def'),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'C'}]},
|
parsed.connect(['A', 'C']),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
]});
|
]});
|
||||||
|
|
||||||
expect(sequence.agents).toEqual([
|
expect(sequence.agents).toEqual([
|
||||||
'[',
|
{name: '[', anchorRight: true},
|
||||||
'__BLOCK0[',
|
{name: '__BLOCK0[', anchorRight: true},
|
||||||
'__BLOCK1[',
|
{name: '__BLOCK1[', anchorRight: true},
|
||||||
'A',
|
{name: 'A', anchorRight: false},
|
||||||
'B',
|
{name: 'B', anchorRight: false},
|
||||||
'C',
|
{name: 'C', anchorRight: false},
|
||||||
'__BLOCK1]',
|
{name: '__BLOCK1]', anchorRight: false},
|
||||||
'__BLOCK0]',
|
{name: '__BLOCK0]', anchorRight: false},
|
||||||
']',
|
{name: ']', anchorRight: false},
|
||||||
]);
|
]);
|
||||||
const block0 = sequence.stages[0];
|
const block0 = sequence.stages[0];
|
||||||
expect(block0.type).toEqual('block');
|
expect(block0.type).toEqual('block');
|
||||||
|
@ -356,23 +497,23 @@ defineDescribe('Sequence Generator', ['./Generator'], (Generator) => {
|
||||||
|
|
||||||
it('preserves block boundaries when agents exist outside', () => {
|
it('preserves block boundaries when agents exist outside', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'def'},
|
parsed.blockBegin('if', 'def'),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
]});
|
]});
|
||||||
|
|
||||||
expect(sequence.agents).toEqual([
|
expect(sequence.agents).toEqual([
|
||||||
'[',
|
{name: '[', anchorRight: true},
|
||||||
'__BLOCK0[',
|
{name: '__BLOCK0[', anchorRight: true},
|
||||||
'__BLOCK1[',
|
{name: '__BLOCK1[', anchorRight: true},
|
||||||
'A',
|
{name: 'A', anchorRight: false},
|
||||||
'B',
|
{name: 'B', anchorRight: false},
|
||||||
'__BLOCK1]',
|
{name: '__BLOCK1]', anchorRight: false},
|
||||||
'__BLOCK0]',
|
{name: '__BLOCK0]', anchorRight: false},
|
||||||
']',
|
{name: ']', anchorRight: false},
|
||||||
]);
|
]);
|
||||||
const block0 = sequence.stages[2];
|
const block0 = sequence.stages[2];
|
||||||
expect(block0.type).toEqual('block');
|
expect(block0.type).toEqual('block');
|
||||||
|
@ -387,10 +528,10 @@ defineDescribe('Sequence Generator', ['./Generator'], (Generator) => {
|
||||||
|
|
||||||
it('allows empty block parts after split', () => {
|
it('allows empty block parts after split', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: BLOCK_SPLIT, mode: 'else', label: 'xyz'},
|
parsed.blockSplit('else', 'xyz'),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
]});
|
]});
|
||||||
|
|
||||||
const block0 = sequence.stages[0];
|
const block0 = sequence.stages[0];
|
||||||
|
@ -405,10 +546,10 @@ defineDescribe('Sequence Generator', ['./Generator'], (Generator) => {
|
||||||
|
|
||||||
it('allows empty block parts before split', () => {
|
it('allows empty block parts before split', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: BLOCK_SPLIT, mode: 'else', label: 'xyz'},
|
parsed.blockSplit('else', 'xyz'),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
]});
|
]});
|
||||||
|
|
||||||
const block0 = sequence.stages[0];
|
const block0 = sequence.stages[0];
|
||||||
|
@ -423,11 +564,11 @@ defineDescribe('Sequence Generator', ['./Generator'], (Generator) => {
|
||||||
|
|
||||||
it('removes entirely empty blocks', () => {
|
it('removes entirely empty blocks', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: BLOCK_SPLIT, mode: 'else', label: 'xyz'},
|
parsed.blockSplit('else', 'xyz'),
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
]});
|
]});
|
||||||
|
|
||||||
expect(sequence.stages).toEqual([]);
|
expect(sequence.stages).toEqual([]);
|
||||||
|
@ -435,10 +576,10 @@ defineDescribe('Sequence Generator', ['./Generator'], (Generator) => {
|
||||||
|
|
||||||
it('removes blocks containing only define statements / markers', () => {
|
it('removes blocks containing only define statements / markers', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: AGENT_DEFINE, agents: [{name: 'A'}]},
|
parsed.defineAgents(['A']),
|
||||||
{type: 'mark', name: 'foo'},
|
{type: 'mark', name: 'foo'},
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
]});
|
]});
|
||||||
|
|
||||||
expect(sequence.stages).toEqual([]);
|
expect(sequence.stages).toEqual([]);
|
||||||
|
@ -446,24 +587,27 @@ defineDescribe('Sequence Generator', ['./Generator'], (Generator) => {
|
||||||
|
|
||||||
it('does not create virtual agents for empty blocks', () => {
|
it('does not create virtual agents for empty blocks', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: BLOCK_SPLIT, mode: 'else', label: 'xyz'},
|
parsed.blockSplit('else', 'xyz'),
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
]});
|
]});
|
||||||
|
|
||||||
expect(sequence.agents).toEqual(['[', ']']);
|
expect(sequence.agents).toEqual([
|
||||||
|
{name: '[', anchorRight: true},
|
||||||
|
{name: ']', anchorRight: false},
|
||||||
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('removes entirely empty nested blocks', () => {
|
it('removes entirely empty nested blocks', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: BLOCK_SPLIT, mode: 'else', label: 'xyz'},
|
parsed.blockSplit('else', 'xyz'),
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
]});
|
]});
|
||||||
|
|
||||||
const block0 = sequence.stages[0];
|
const block0 = sequence.stages[0];
|
||||||
|
@ -478,83 +622,100 @@ defineDescribe('Sequence Generator', ['./Generator'], (Generator) => {
|
||||||
|
|
||||||
it('rejects unterminated blocks', () => {
|
it('rejects unterminated blocks', () => {
|
||||||
expect(() => generator.generate({stages: [
|
expect(() => generator.generate({stages: [
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
]})).toThrow();
|
]})).toThrow();
|
||||||
|
|
||||||
expect(() => generator.generate({stages: [
|
expect(() => generator.generate({stages: [
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'def'},
|
parsed.blockBegin('if', 'def'),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
]})).toThrow();
|
]})).toThrow();
|
||||||
});
|
});
|
||||||
|
|
||||||
it('rejects extra block terminations', () => {
|
it('rejects extra block terminations', () => {
|
||||||
expect(() => generator.generate({stages: [
|
expect(() => generator.generate({stages: [
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
]})).toThrow();
|
]})).toThrow();
|
||||||
|
|
||||||
expect(() => generator.generate({stages: [
|
expect(() => generator.generate({stages: [
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
]})).toThrow();
|
]})).toThrow();
|
||||||
});
|
});
|
||||||
|
|
||||||
it('rejects block splitting without a block', () => {
|
it('rejects block splitting without a block', () => {
|
||||||
expect(() => generator.generate({stages: [
|
expect(() => generator.generate({stages: [
|
||||||
{type: BLOCK_SPLIT, mode: 'else', label: 'xyz'},
|
parsed.blockSplit('else', 'xyz'),
|
||||||
]})).toThrow();
|
]})).toThrow();
|
||||||
|
|
||||||
expect(() => generator.generate({stages: [
|
expect(() => generator.generate({stages: [
|
||||||
{type: BLOCK_BEGIN, mode: 'if', label: 'abc'},
|
parsed.blockBegin('if', 'abc'),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
{type: BLOCK_SPLIT, mode: 'else', label: 'xyz'},
|
parsed.blockSplit('else', 'xyz'),
|
||||||
]})).toThrow();
|
]})).toThrow();
|
||||||
});
|
});
|
||||||
|
|
||||||
it('rejects block splitting in non-splittable blocks', () => {
|
it('rejects block splitting in non-splittable blocks', () => {
|
||||||
expect(() => generator.generate({stages: [
|
expect(() => generator.generate({stages: [
|
||||||
{type: BLOCK_BEGIN, mode: 'repeat', label: 'abc'},
|
parsed.blockBegin('repeat', 'abc'),
|
||||||
{type: BLOCK_SPLIT, mode: 'else', label: 'xyz'},
|
parsed.blockSplit('else', 'xyz'),
|
||||||
{type: '->', agents: [{name: 'A'}, {name: 'B'}]},
|
parsed.connect(['A', 'B']),
|
||||||
{type: BLOCK_END},
|
parsed.blockEnd(),
|
||||||
]})).toThrow();
|
]})).toThrow();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('passes notes through', () => {
|
||||||
|
const sequence = generator.generate({stages: [
|
||||||
|
parsed.note(['A', 'B'], {
|
||||||
|
type: 'note right',
|
||||||
|
mode: 'foo',
|
||||||
|
label: 'bar',
|
||||||
|
}),
|
||||||
|
]});
|
||||||
|
expect(sequence.stages).toEqual([
|
||||||
|
jasmine.anything(),
|
||||||
|
generated.note(['A', 'B'], {
|
||||||
|
type: 'note right',
|
||||||
|
mode: 'foo',
|
||||||
|
label: 'bar',
|
||||||
|
}),
|
||||||
|
jasmine.anything(),
|
||||||
|
]);
|
||||||
|
});
|
||||||
|
|
||||||
it('defaults to showing notes around the entire diagram', () => {
|
it('defaults to showing notes around the entire diagram', () => {
|
||||||
const sequence = generator.generate({stages: [
|
const sequence = generator.generate({stages: [
|
||||||
{type: 'note right', agents: [], foo: 'bar'},
|
parsed.note([], {type: 'note right'}),
|
||||||
{type: 'note left', agents: [], foo: 'bar'},
|
parsed.note([], {type: 'note left'}),
|
||||||
{type: 'note over', agents: [], foo: 'bar'},
|
parsed.note([], {type: 'note over'}),
|
||||||
{type: 'note right', agents: [{name: '['}], foo: 'bar'},
|
|
||||||
]});
|
]});
|
||||||
expect(sequence.stages).toEqual([
|
expect(sequence.stages).toEqual([
|
||||||
{type: 'note right', agents: [']'], foo: 'bar'},
|
generated.note([']'], {type: 'note right'}),
|
||||||
{type: 'note left', agents: ['['], foo: 'bar'},
|
generated.note(['['], {type: 'note left'}),
|
||||||
{type: 'note over', agents: ['[', ']'], foo: 'bar'},
|
generated.note(['[', ']'], {type: 'note over'}),
|
||||||
{type: 'note right', agents: ['['], foo: 'bar'},
|
|
||||||
]);
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('rejects attempts to change implicit agents', () => {
|
it('rejects attempts to change implicit agents', () => {
|
||||||
expect(() => generator.generate({stages: [
|
expect(() => generator.generate({stages: [
|
||||||
{type: AGENT_BEGIN, agents: [{name: '['}], mode: 'box'},
|
parsed.beginAgents(['[']),
|
||||||
]})).toThrow();
|
]})).toThrow();
|
||||||
|
|
||||||
expect(() => generator.generate({stages: [
|
expect(() => generator.generate({stages: [
|
||||||
{type: AGENT_BEGIN, agents: [{name: ']'}], mode: 'box'},
|
parsed.beginAgents([']']),
|
||||||
]})).toThrow();
|
]})).toThrow();
|
||||||
|
|
||||||
expect(() => generator.generate({stages: [
|
expect(() => generator.generate({stages: [
|
||||||
{type: AGENT_END, agents: [{name: '['}], mode: 'cross'},
|
parsed.endAgents(['[']),
|
||||||
]})).toThrow();
|
]})).toThrow();
|
||||||
|
|
||||||
expect(() => generator.generate({stages: [
|
expect(() => generator.generate({stages: [
|
||||||
{type: AGENT_END, agents: [{name: ']'}], mode: 'cross'},
|
parsed.endAgents([']']),
|
||||||
]})).toThrow();
|
]})).toThrow();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
|
@ -140,11 +140,11 @@ define([
|
||||||
this.sizer = new this.SVGTextBlockClass.SizeTester(this.base);
|
this.sizer = new this.SVGTextBlockClass.SizeTester(this.base);
|
||||||
}
|
}
|
||||||
|
|
||||||
findExtremes(agents) {
|
findExtremes(agentNames) {
|
||||||
let min = null;
|
let min = null;
|
||||||
let max = null;
|
let max = null;
|
||||||
agents.forEach((agent) => {
|
agentNames.forEach((name) => {
|
||||||
const info = this.agentInfos.get(agent);
|
const info = this.agentInfos.get(name);
|
||||||
if(min === null || info.index < min.index) {
|
if(min === null || info.index < min.index) {
|
||||||
min = info;
|
min = info;
|
||||||
}
|
}
|
||||||
|
@ -158,32 +158,32 @@ define([
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
addSeparation(agent1, agent2, dist) {
|
addSeparation(agentName1, agentName2, dist) {
|
||||||
const info1 = this.agentInfos.get(agent1);
|
const info1 = this.agentInfos.get(agentName1);
|
||||||
const info2 = this.agentInfos.get(agent2);
|
const info2 = this.agentInfos.get(agentName2);
|
||||||
|
|
||||||
const d1 = info1.separations.get(agent2) || 0;
|
const d1 = info1.separations.get(agentName2) || 0;
|
||||||
info1.separations.set(agent2, Math.max(d1, dist));
|
info1.separations.set(agentName2, Math.max(d1, dist));
|
||||||
|
|
||||||
const d2 = info2.separations.get(agent1) || 0;
|
const d2 = info2.separations.get(agentName1) || 0;
|
||||||
info2.separations.set(agent1, Math.max(d2, dist));
|
info2.separations.set(agentName1, Math.max(d2, dist));
|
||||||
}
|
}
|
||||||
|
|
||||||
addSeparations(agents, agentSpaces) {
|
addSeparations(agentNames, agentSpaces) {
|
||||||
agents.forEach((agentR) => {
|
agentNames.forEach((agentNameR) => {
|
||||||
const infoR = this.agentInfos.get(agentR);
|
const infoR = this.agentInfos.get(agentNameR);
|
||||||
const sepR = agentSpaces.get(agentR) || SEP_ZERO;
|
const sepR = agentSpaces.get(agentNameR) || SEP_ZERO;
|
||||||
infoR.maxRPad = Math.max(infoR.maxRPad, sepR.right);
|
infoR.maxRPad = Math.max(infoR.maxRPad, sepR.right);
|
||||||
infoR.maxLPad = Math.max(infoR.maxLPad, sepR.left);
|
infoR.maxLPad = Math.max(infoR.maxLPad, sepR.left);
|
||||||
agents.forEach((agentL) => {
|
agentNames.forEach((agentNameL) => {
|
||||||
const infoL = this.agentInfos.get(agentL);
|
const infoL = this.agentInfos.get(agentNameL);
|
||||||
if(infoL.index >= infoR.index) {
|
if(infoL.index >= infoR.index) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const sepL = agentSpaces.get(agentL) || SEP_ZERO;
|
const sepL = agentSpaces.get(agentNameL) || SEP_ZERO;
|
||||||
this.addSeparation(
|
this.addSeparation(
|
||||||
agentR,
|
agentNameR,
|
||||||
agentL,
|
agentNameL,
|
||||||
sepR.left + sepL.right + this.theme.agentMargin
|
sepR.left + sepL.right + this.theme.agentMargin
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
@ -236,25 +236,25 @@ define([
|
||||||
return {left: 0, right: 0};
|
return {left: 0, right: 0};
|
||||||
}
|
}
|
||||||
|
|
||||||
separationAgent({type, mode, agents}) {
|
separationAgent({type, mode, agentNames}) {
|
||||||
if(type === 'agent begin') {
|
if(type === 'agent begin') {
|
||||||
array.mergeSets(this.visibleAgents, agents);
|
array.mergeSets(this.visibleAgents, agentNames);
|
||||||
}
|
}
|
||||||
|
|
||||||
const agentSpaces = new Map();
|
const agentSpaces = new Map();
|
||||||
agents.forEach((agent) => {
|
agentNames.forEach((name) => {
|
||||||
const info = this.agentInfos.get(agent);
|
const info = this.agentInfos.get(name);
|
||||||
const separationFn = this.separationAgentCap[mode];
|
const separationFn = this.separationAgentCap[mode];
|
||||||
agentSpaces.set(agent, separationFn(info));
|
agentSpaces.set(name, separationFn(info));
|
||||||
});
|
});
|
||||||
this.addSeparations(this.visibleAgents, agentSpaces);
|
this.addSeparations(this.visibleAgents, agentSpaces);
|
||||||
|
|
||||||
if(type === 'agent end') {
|
if(type === 'agent end') {
|
||||||
array.removeAll(this.visibleAgents, agents);
|
array.removeAll(this.visibleAgents, agentNames);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
separationConnection({agents, label}) {
|
separationConnection({agentNames, label}) {
|
||||||
const config = this.theme.connect;
|
const config = this.theme.connect;
|
||||||
|
|
||||||
const labelWidth = (
|
const labelWidth = (
|
||||||
|
@ -263,9 +263,9 @@ define([
|
||||||
);
|
);
|
||||||
const strokeWidth = this.theme.agentLineAttrs['stroke-width'];
|
const strokeWidth = this.theme.agentLineAttrs['stroke-width'];
|
||||||
|
|
||||||
if(agents[0] === agents[1]) {
|
if(agentNames[0] === agentNames[1]) {
|
||||||
const agentSpaces = new Map();
|
const agentSpaces = new Map();
|
||||||
agentSpaces.set(agents[0], {
|
agentSpaces.set(agentNames[0], {
|
||||||
left: 0,
|
left: 0,
|
||||||
right: (
|
right: (
|
||||||
labelWidth +
|
labelWidth +
|
||||||
|
@ -277,14 +277,14 @@ define([
|
||||||
this.addSeparations(this.visibleAgents, agentSpaces);
|
this.addSeparations(this.visibleAgents, agentSpaces);
|
||||||
} else {
|
} else {
|
||||||
this.addSeparation(
|
this.addSeparation(
|
||||||
agents[0],
|
agentNames[0],
|
||||||
agents[1],
|
agentNames[1],
|
||||||
labelWidth + config.arrow.width * 2 + strokeWidth
|
labelWidth + config.arrow.width * 2 + strokeWidth
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
separationNoteOver({agents, mode, label}) {
|
separationNoteOver({agentNames, mode, label}) {
|
||||||
const config = this.theme.note[mode];
|
const config = this.theme.note[mode];
|
||||||
const width = (
|
const width = (
|
||||||
this.sizer.measure(config.labelAttrs, label).width +
|
this.sizer.measure(config.labelAttrs, label).width +
|
||||||
|
@ -293,8 +293,8 @@ define([
|
||||||
);
|
);
|
||||||
|
|
||||||
const agentSpaces = new Map();
|
const agentSpaces = new Map();
|
||||||
if(agents.length > 1) {
|
if(agentNames.length > 1) {
|
||||||
const {left, right} = this.findExtremes(agents);
|
const {left, right} = this.findExtremes(agentNames);
|
||||||
|
|
||||||
this.addSeparation(
|
this.addSeparation(
|
||||||
left,
|
left,
|
||||||
|
@ -308,7 +308,7 @@ define([
|
||||||
agentSpaces.set(left, {left: config.overlap.left, right: 0});
|
agentSpaces.set(left, {left: config.overlap.left, right: 0});
|
||||||
agentSpaces.set(right, {left: 0, right: config.overlap.right});
|
agentSpaces.set(right, {left: 0, right: config.overlap.right});
|
||||||
} else {
|
} else {
|
||||||
agentSpaces.set(agents[0], {
|
agentSpaces.set(agentNames[0], {
|
||||||
left: width / 2,
|
left: width / 2,
|
||||||
right: width / 2,
|
right: width / 2,
|
||||||
});
|
});
|
||||||
|
@ -316,9 +316,9 @@ define([
|
||||||
this.addSeparations(this.visibleAgents, agentSpaces);
|
this.addSeparations(this.visibleAgents, agentSpaces);
|
||||||
}
|
}
|
||||||
|
|
||||||
separationNoteSide(isRight, {agents, mode, label}) {
|
separationNoteSide(isRight, {agentNames, mode, label}) {
|
||||||
const config = this.theme.note[mode];
|
const config = this.theme.note[mode];
|
||||||
const {left, right} = this.findExtremes(agents);
|
const {left, right} = this.findExtremes(agentNames);
|
||||||
const width = (
|
const width = (
|
||||||
this.sizer.measure(config.labelAttrs, label).width +
|
this.sizer.measure(config.labelAttrs, label).width +
|
||||||
config.padding.left +
|
config.padding.left +
|
||||||
|
@ -336,9 +336,9 @@ define([
|
||||||
this.addSeparations(this.visibleAgents, agentSpaces);
|
this.addSeparations(this.visibleAgents, agentSpaces);
|
||||||
}
|
}
|
||||||
|
|
||||||
separationNoteBetween({agents, mode, label}) {
|
separationNoteBetween({agentNames, mode, label}) {
|
||||||
const config = this.theme.note[mode];
|
const config = this.theme.note[mode];
|
||||||
const {left, right} = this.findExtremes(agents);
|
const {left, right} = this.findExtremes(agentNames);
|
||||||
|
|
||||||
this.addSeparation(
|
this.addSeparation(
|
||||||
left,
|
left,
|
||||||
|
@ -462,8 +462,8 @@ define([
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
checkAgentRange(agents) {
|
checkAgentRange(agentNames) {
|
||||||
const {left, right} = this.findExtremes(agents);
|
const {left, right} = this.findExtremes(agentNames);
|
||||||
const leftX = this.agentInfos.get(left).x;
|
const leftX = this.agentInfos.get(left).x;
|
||||||
const rightX = this.agentInfos.get(right).x;
|
const rightX = this.agentInfos.get(right).x;
|
||||||
this.agentInfos.forEach((agentInfo) => {
|
this.agentInfos.forEach((agentInfo) => {
|
||||||
|
@ -473,8 +473,8 @@ define([
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
markAgentRange(agents) {
|
markAgentRange(agentNames) {
|
||||||
const {left, right} = this.findExtremes(agents);
|
const {left, right} = this.findExtremes(agentNames);
|
||||||
const leftX = this.agentInfos.get(left).x;
|
const leftX = this.agentInfos.get(left).x;
|
||||||
const rightX = this.agentInfos.get(right).x;
|
const rightX = this.agentInfos.get(right).x;
|
||||||
this.agentInfos.forEach((agentInfo) => {
|
this.agentInfos.forEach((agentInfo) => {
|
||||||
|
@ -484,24 +484,24 @@ define([
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
renderAgentBegin({mode, agents}) {
|
renderAgentBegin({mode, agentNames}) {
|
||||||
this.checkAgentRange(agents);
|
this.checkAgentRange(agentNames);
|
||||||
let maxHeight = 0;
|
let maxHeight = 0;
|
||||||
agents.forEach((agent) => {
|
agentNames.forEach((name) => {
|
||||||
const agentInfo = this.agentInfos.get(agent);
|
const agentInfo = this.agentInfos.get(name);
|
||||||
const shifts = this.renderAgentCap[mode](agentInfo);
|
const shifts = this.renderAgentCap[mode](agentInfo);
|
||||||
maxHeight = Math.max(maxHeight, shifts.height);
|
maxHeight = Math.max(maxHeight, shifts.height);
|
||||||
agentInfo.latestYStart = this.currentY + shifts.lineBottom;
|
agentInfo.latestYStart = this.currentY + shifts.lineBottom;
|
||||||
});
|
});
|
||||||
this.currentY += maxHeight + this.theme.actionMargin;
|
this.currentY += maxHeight + this.theme.actionMargin;
|
||||||
this.markAgentRange(agents);
|
this.markAgentRange(agentNames);
|
||||||
}
|
}
|
||||||
|
|
||||||
renderAgentEnd({mode, agents}) {
|
renderAgentEnd({mode, agentNames}) {
|
||||||
this.checkAgentRange(agents);
|
this.checkAgentRange(agentNames);
|
||||||
let maxHeight = 0;
|
let maxHeight = 0;
|
||||||
agents.forEach((agent) => {
|
agentNames.forEach((name) => {
|
||||||
const agentInfo = this.agentInfos.get(agent);
|
const agentInfo = this.agentInfos.get(name);
|
||||||
const x = agentInfo.x;
|
const x = agentInfo.x;
|
||||||
const shifts = this.renderAgentCap[mode](agentInfo);
|
const shifts = this.renderAgentCap[mode](agentInfo);
|
||||||
maxHeight = Math.max(maxHeight, shifts.height);
|
maxHeight = Math.max(maxHeight, shifts.height);
|
||||||
|
@ -515,12 +515,12 @@ define([
|
||||||
agentInfo.latestYStart = null;
|
agentInfo.latestYStart = null;
|
||||||
});
|
});
|
||||||
this.currentY += maxHeight + this.theme.actionMargin;
|
this.currentY += maxHeight + this.theme.actionMargin;
|
||||||
this.markAgentRange(agents);
|
this.markAgentRange(agentNames);
|
||||||
}
|
}
|
||||||
|
|
||||||
renderSelfConnection({label, agents, line, left, right}) {
|
renderSelfConnection({label, agentNames, line, left, right}) {
|
||||||
const config = this.theme.connect;
|
const config = this.theme.connect;
|
||||||
const from = this.agentInfos.get(agents[0]);
|
const from = this.agentInfos.get(agentNames[0]);
|
||||||
|
|
||||||
const dy = config.arrow.height / 2;
|
const dy = config.arrow.height / 2;
|
||||||
const short = this.theme.agentLineAttrs['stroke-width'];
|
const short = this.theme.agentLineAttrs['stroke-width'];
|
||||||
|
@ -591,10 +591,10 @@ define([
|
||||||
this.currentY = y1 + dy + this.theme.actionMargin;
|
this.currentY = y1 + dy + this.theme.actionMargin;
|
||||||
}
|
}
|
||||||
|
|
||||||
renderSimpleConnection({label, agents, line, left, right}) {
|
renderSimpleConnection({label, agentNames, line, left, right}) {
|
||||||
const config = this.theme.connect;
|
const config = this.theme.connect;
|
||||||
const from = this.agentInfos.get(agents[0]);
|
const from = this.agentInfos.get(agentNames[0]);
|
||||||
const to = this.agentInfos.get(agents[1]);
|
const to = this.agentInfos.get(agentNames[1]);
|
||||||
|
|
||||||
const dy = config.arrow.height / 2;
|
const dy = config.arrow.height / 2;
|
||||||
const dir = (from.x < to.x) ? 1 : -1;
|
const dir = (from.x < to.x) ? 1 : -1;
|
||||||
|
@ -650,13 +650,13 @@ define([
|
||||||
}
|
}
|
||||||
|
|
||||||
renderConnection(stage) {
|
renderConnection(stage) {
|
||||||
this.checkAgentRange(stage.agents);
|
this.checkAgentRange(stage.agentNames);
|
||||||
if(stage.agents[0] === stage.agents[1]) {
|
if(stage.agentNames[0] === stage.agentNames[1]) {
|
||||||
this.renderSelfConnection(stage);
|
this.renderSelfConnection(stage);
|
||||||
} else {
|
} else {
|
||||||
this.renderSimpleConnection(stage);
|
this.renderSimpleConnection(stage);
|
||||||
}
|
}
|
||||||
this.markAgentRange(stage.agents);
|
this.markAgentRange(stage.agentNames);
|
||||||
}
|
}
|
||||||
|
|
||||||
renderNote({xMid = null, x0 = null, x1 = null}, anchor, mode, label) {
|
renderNote({xMid = null, x0 = null, x1 = null}, anchor, mode, label) {
|
||||||
|
@ -721,53 +721,53 @@ define([
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
renderNoteOver({agents, mode, label}) {
|
renderNoteOver({agentNames, mode, label}) {
|
||||||
this.checkAgentRange(agents);
|
this.checkAgentRange(agentNames);
|
||||||
const config = this.theme.note[mode];
|
const config = this.theme.note[mode];
|
||||||
|
|
||||||
if(agents.length > 1) {
|
if(agentNames.length > 1) {
|
||||||
const {left, right} = this.findExtremes(agents);
|
const {left, right} = this.findExtremes(agentNames);
|
||||||
this.renderNote({
|
this.renderNote({
|
||||||
x0: this.agentInfos.get(left).x - config.overlap.left,
|
x0: this.agentInfos.get(left).x - config.overlap.left,
|
||||||
x1: this.agentInfos.get(right).x + config.overlap.right,
|
x1: this.agentInfos.get(right).x + config.overlap.right,
|
||||||
}, 'middle', mode, label);
|
}, 'middle', mode, label);
|
||||||
} else {
|
} else {
|
||||||
const xMid = this.agentInfos.get(agents[0]).x;
|
const xMid = this.agentInfos.get(agentNames[0]).x;
|
||||||
this.renderNote({xMid}, 'middle', mode, label);
|
this.renderNote({xMid}, 'middle', mode, label);
|
||||||
}
|
}
|
||||||
this.markAgentRange(agents);
|
this.markAgentRange(agentNames);
|
||||||
}
|
}
|
||||||
|
|
||||||
renderNoteLeft({agents, mode, label}) {
|
renderNoteLeft({agentNames, mode, label}) {
|
||||||
this.checkAgentRange(agents);
|
this.checkAgentRange(agentNames);
|
||||||
const config = this.theme.note[mode];
|
const config = this.theme.note[mode];
|
||||||
|
|
||||||
const {left} = this.findExtremes(agents);
|
const {left} = this.findExtremes(agentNames);
|
||||||
const x1 = this.agentInfos.get(left).x - config.margin.right;
|
const x1 = this.agentInfos.get(left).x - config.margin.right;
|
||||||
this.renderNote({x1}, 'end', mode, label);
|
this.renderNote({x1}, 'end', mode, label);
|
||||||
this.markAgentRange(agents);
|
this.markAgentRange(agentNames);
|
||||||
}
|
}
|
||||||
|
|
||||||
renderNoteRight({agents, mode, label}) {
|
renderNoteRight({agentNames, mode, label}) {
|
||||||
this.checkAgentRange(agents);
|
this.checkAgentRange(agentNames);
|
||||||
const config = this.theme.note[mode];
|
const config = this.theme.note[mode];
|
||||||
|
|
||||||
const {right} = this.findExtremes(agents);
|
const {right} = this.findExtremes(agentNames);
|
||||||
const x0 = this.agentInfos.get(right).x + config.margin.left;
|
const x0 = this.agentInfos.get(right).x + config.margin.left;
|
||||||
this.renderNote({x0}, 'start', mode, label);
|
this.renderNote({x0}, 'start', mode, label);
|
||||||
this.markAgentRange(agents);
|
this.markAgentRange(agentNames);
|
||||||
}
|
}
|
||||||
|
|
||||||
renderNoteBetween({agents, mode, label}) {
|
renderNoteBetween({agentNames, mode, label}) {
|
||||||
this.checkAgentRange(agents);
|
this.checkAgentRange(agentNames);
|
||||||
const {left, right} = this.findExtremes(agents);
|
const {left, right} = this.findExtremes(agentNames);
|
||||||
const xMid = (
|
const xMid = (
|
||||||
this.agentInfos.get(left).x +
|
this.agentInfos.get(left).x +
|
||||||
this.agentInfos.get(right).x
|
this.agentInfos.get(right).x
|
||||||
) / 2;
|
) / 2;
|
||||||
|
|
||||||
this.renderNote({xMid}, 'middle', mode, label);
|
this.renderNote({xMid}, 'middle', mode, label);
|
||||||
this.markAgentRange(agents);
|
this.markAgentRange(agentNames);
|
||||||
}
|
}
|
||||||
|
|
||||||
renderBlockBegin(scope, {left, right}) {
|
renderBlockBegin(scope, {left, right}) {
|
||||||
|
@ -891,9 +891,9 @@ define([
|
||||||
buildAgentInfos(agents, stages) {
|
buildAgentInfos(agents, stages) {
|
||||||
this.agentInfos = new Map();
|
this.agentInfos = new Map();
|
||||||
agents.forEach((agent, index) => {
|
agents.forEach((agent, index) => {
|
||||||
this.agentInfos.set(agent, {
|
this.agentInfos.set(agent.name, {
|
||||||
label: agent,
|
label: agent.name,
|
||||||
anchorRight: agent.endsWith('['),
|
anchorRight: agent.anchorRight,
|
||||||
index,
|
index,
|
||||||
x: null,
|
x: null,
|
||||||
latestYStart: null,
|
latestYStart: null,
|
||||||
|
|
|
@ -25,13 +25,13 @@ defineDescribe('Sequence Renderer', [
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
function connectionStage(agents, label = '') {
|
function connectionStage(agentNames, label = '') {
|
||||||
return {
|
return {
|
||||||
type: 'connection',
|
type: 'connection',
|
||||||
line: 'solid',
|
line: 'solid',
|
||||||
left: false,
|
left: false,
|
||||||
right: true,
|
right: true,
|
||||||
agents,
|
agentNames,
|
||||||
label,
|
label,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
@ -40,7 +40,12 @@ defineDescribe('Sequence Renderer', [
|
||||||
it('populates the SVG with content', () => {
|
it('populates the SVG with content', () => {
|
||||||
renderer.render({
|
renderer.render({
|
||||||
meta: {title: 'Title'},
|
meta: {title: 'Title'},
|
||||||
agents: ['[', 'Col 1', 'Col 2', ']'],
|
agents: [
|
||||||
|
{name: '[', anchorRight: true},
|
||||||
|
{name: 'Col 1', anchorRight: false},
|
||||||
|
{name: 'Col 2', anchorRight: false},
|
||||||
|
{name: ']', anchorRight: false},
|
||||||
|
],
|
||||||
stages: [],
|
stages: [],
|
||||||
});
|
});
|
||||||
const element = renderer.svg();
|
const element = renderer.svg();
|
||||||
|
@ -55,11 +60,16 @@ defineDescribe('Sequence Renderer', [
|
||||||
|
|
||||||
renderer.render({
|
renderer.render({
|
||||||
meta: {title: ''},
|
meta: {title: ''},
|
||||||
agents: ['[', 'A', 'B', ']'],
|
agents: [
|
||||||
|
{name: '[', anchorRight: true},
|
||||||
|
{name: 'A', anchorRight: false},
|
||||||
|
{name: 'B', anchorRight: false},
|
||||||
|
{name: ']', anchorRight: false},
|
||||||
|
],
|
||||||
stages: [
|
stages: [
|
||||||
{type: 'agent begin', agents: ['A', 'B'], mode: 'box'},
|
{type: 'agent begin', agentNames: ['A', 'B'], mode: 'box'},
|
||||||
connectionStage(['A', 'B']),
|
connectionStage(['A', 'B']),
|
||||||
{type: 'agent end', agents: ['A', 'B'], mode: 'none'},
|
{type: 'agent end', agentNames: ['A', 'B'], mode: 'none'},
|
||||||
],
|
],
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -80,14 +90,28 @@ defineDescribe('Sequence Renderer', [
|
||||||
|
|
||||||
renderer.render({
|
renderer.render({
|
||||||
meta: {title: ''},
|
meta: {title: ''},
|
||||||
agents: ['[', 'A', 'B', 'C', ']'],
|
agents: [
|
||||||
|
{name: '[', anchorRight: true},
|
||||||
|
{name: 'A', anchorRight: false},
|
||||||
|
{name: 'B', anchorRight: false},
|
||||||
|
{name: 'C', anchorRight: false},
|
||||||
|
{name: ']', anchorRight: false},
|
||||||
|
],
|
||||||
stages: [
|
stages: [
|
||||||
{type: 'agent begin', agents: ['A', 'B', 'C'], mode: 'box'},
|
{
|
||||||
|
type: 'agent begin',
|
||||||
|
agentNames: ['A', 'B', 'C'],
|
||||||
|
mode: 'box',
|
||||||
|
},
|
||||||
connectionStage(['[', 'A']),
|
connectionStage(['[', 'A']),
|
||||||
connectionStage(['A', 'B']),
|
connectionStage(['A', 'B']),
|
||||||
connectionStage(['B', 'C']),
|
connectionStage(['B', 'C']),
|
||||||
connectionStage(['C', ']']),
|
connectionStage(['C', ']']),
|
||||||
{type: 'agent end', agents: ['A', 'B', 'C'], mode: 'none'},
|
{
|
||||||
|
type: 'agent end',
|
||||||
|
agentNames: ['A', 'B', 'C'],
|
||||||
|
mode: 'none',
|
||||||
|
},
|
||||||
],
|
],
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -115,17 +139,24 @@ defineDescribe('Sequence Renderer', [
|
||||||
|
|
||||||
renderer.render({
|
renderer.render({
|
||||||
meta: {title: ''},
|
meta: {title: ''},
|
||||||
agents: ['[', 'A', 'B', 'C', 'D', ']'],
|
agents: [
|
||||||
|
{name: '[', anchorRight: true},
|
||||||
|
{name: 'A', anchorRight: false},
|
||||||
|
{name: 'B', anchorRight: false},
|
||||||
|
{name: 'C', anchorRight: false},
|
||||||
|
{name: 'D', anchorRight: false},
|
||||||
|
{name: ']', anchorRight: false},
|
||||||
|
],
|
||||||
stages: [
|
stages: [
|
||||||
{type: 'agent begin', agents: ['A', 'B'], mode: 'box'},
|
{type: 'agent begin', agentNames: ['A', 'B'], mode: 'box'},
|
||||||
connectionStage(['A', 'B'], 'short'),
|
connectionStage(['A', 'B'], 'short'),
|
||||||
{type: 'agent end', agents: ['B'], mode: 'cross'},
|
{type: 'agent end', agentNames: ['B'], mode: 'cross'},
|
||||||
{type: 'agent begin', agents: ['C'], mode: 'box'},
|
{type: 'agent begin', agentNames: ['C'], mode: 'box'},
|
||||||
connectionStage(['A', 'C'], 'long description here'),
|
connectionStage(['A', 'C'], 'long description here'),
|
||||||
{type: 'agent end', agents: ['C'], mode: 'cross'},
|
{type: 'agent end', agentNames: ['C'], mode: 'cross'},
|
||||||
{type: 'agent begin', agents: ['D'], mode: 'box'},
|
{type: 'agent begin', agentNames: ['D'], mode: 'box'},
|
||||||
connectionStage(['A', 'D'], 'short again'),
|
connectionStage(['A', 'D'], 'short again'),
|
||||||
{type: 'agent end', agents: ['A', 'D'], mode: 'cross'},
|
{type: 'agent end', agentNames: ['A', 'D'], mode: 'cross'},
|
||||||
],
|
],
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
/* jshint -W072 */
|
/* jshint -W072 */
|
||||||
defineDescribe('Sequence Renderer', [
|
defineDescribe('Sequence Integration', [
|
||||||
'./Parser',
|
'./Parser',
|
||||||
'./Generator',
|
'./Generator',
|
||||||
'./Renderer',
|
'./Renderer',
|
||||||
|
|
Loading…
Reference in New Issue