From dce39792ac7d7c7943a5a1cab00c9eb769a95de1 Mon Sep 17 00:00:00 2001
From: David Evans
Date: Fri, 24 Nov 2017 23:15:39 +0000
Subject: [PATCH] Support requirejs loading [#25]
---
index.html | 111 +++++++++++++++++++++++++-----------
lib/sequence-diagram.js | 8 +++
lib/sequence-diagram.min.js | 2 +-
package.json | 4 +-
scripts/standalone.js | 8 +++
styles/home.css | 12 ----
6 files changed, 97 insertions(+), 48 deletions(-)
diff --git a/index.html b/index.html
index a90729b..9de7191 100644
--- a/index.html
+++ b/index.html
@@ -4,8 +4,8 @@
+
+
+
+
+
+
+
+
+
+
+
-
@@ -76,8 +113,16 @@ This library renders sequence diagrams from code. It is
open-source
(LGPL-3.0), and including it in a website is as simple as adding the script:
-
-<script src= "lib/sequence-diagram.min.js" ></script>
+
+<script src="lib/sequence-diagram.min.js"></script>
+
+
+Or if you are using requirejs:
+
+
+requirejs(['lib/sequence-diagram.min'], (SequenceDiagram) => {
+ SequenceDiagram.convertAll();
+});
@@ -86,23 +131,23 @@ converted when the page loads:
-
+
A -> B: foo
B -> A: bar
-
-<pre class= "sequence-diagram" >
+
+<pre class="sequence-diagram">
A -> B: foo
B -> A: bar
-</pre>
+</pre>
Language
Connection Types
-
+
title Connection Types
begin Foo, Bar, Baz
@@ -135,7 +180,7 @@ Foo <- ]: From the right
Notes & State
-
+
title Note Placements
note over Foo: Foo says something
@@ -151,7 +196,7 @@ state over Foo: Foo is ponderous
Logic
-
+
title At the Bank
begin Person, ATM, Bank
@@ -173,7 +218,7 @@ end
Label Templates
-
+
autolabel "[<inc>] <label>"
begin "Underpants\nGnomes" as A
@@ -183,7 +228,7 @@ A <- ]: Profit!
Multiline Text
-
+
title 'My Multiline
Title'
@@ -200,7 +245,7 @@ too!'
Short-Lived Agents
-
+
title "Baz doesn't live long"
note over Foo, Bar: Using begin / end
@@ -222,7 +267,7 @@ terminators bar
Agent Aliases
-
+
define My complicated agent name as A
define "Another agent name,
and this one's multi-line!" as B
@@ -232,7 +277,7 @@ A <- B: than writing the whole name
Alternative Agent Ordering
-
+
define Baz, Foo
Foo -> Bar
@@ -265,7 +310,7 @@ For more advanced usage, an API is available:
-
+
var diagram = new SequenceDiagram();
diagram.set('A -> B\nB -> A');
document.body.appendChild(diagram.dom());
@@ -274,7 +319,7 @@ diagram.setHighlight(1); // Highlight elements created in line 1 (0-based)
Constructor
-
+
diagram = new SequenceDiagram(code, options);
diagram = new SequenceDiagram(code);
diagram = new SequenceDiagram(options);
@@ -293,7 +338,7 @@ Creates a new SequenceDiagram object. Options is an object which can contain:
.clone
-
+
newDiagram = diagram.clone(options);
newDiagram = diagram.clone();
@@ -306,7 +351,7 @@ so all the same options are available).
.set
-
+
diagram.set(code);
@@ -316,7 +361,7 @@ Changes the code for the diagram and causes a re-render.
.process
-
+
processed = diagram.process(code);
@@ -329,7 +374,7 @@ error notifications. The resulting object can be passed to
.render
-
+
diagram.render();
diagram.render(processed);
@@ -342,7 +387,7 @@ Optionally, the result of an earlier call to
.setHighlight
-
+
diagram.setHighlight(line);
diagram.setHighlight();
@@ -355,7 +400,7 @@ with no parameter (or null
) will remove the highlighting.
.addTheme
-
+
diagram.addTheme(theme);
@@ -370,7 +415,7 @@ useful.
.getThemeNames
-
+
names = diagram.getThemeNames();
@@ -381,7 +426,7 @@ can be specified in a theme <name>
line in the code.
.getThemes
-
+
themes = diagram.getThemes();
@@ -391,7 +436,7 @@ Returns a list of themes which are available to this diagram.
.getSVGSynchronous
-
+
svgURL = diagram.getSVGSynchronous();
@@ -401,7 +446,7 @@ Returns a blob URL which contains the SVG code for the current diagram.
.getSVG
-
+
diagram.getSVG().then(({url, latest}) => { ... });
@@ -419,7 +464,7 @@ which has no synchronous equivalent.
.getPNG
-
+
diagram.getPNG(options).then(({url, latest}) => { ... });
@@ -439,7 +484,7 @@ Generates a PNG image and returns a blob URL.
.getSize
-
+
size = diagram.getSize();
@@ -450,7 +495,7 @@ properties, corresponding to the size of the diagram in units.
.setContainer
-
+
diagram.setContainer(node);
@@ -460,7 +505,7 @@ Same as calling node.appendChild(diagram.dom())
.
.dom
-
+
node = diagram.dom();
diff --git a/lib/sequence-diagram.js b/lib/sequence-diagram.js
index 7bed586..a3f987d 100644
--- a/lib/sequence-diagram.js
+++ b/lib/sequence-diagram.js
@@ -6075,6 +6075,14 @@ define('sequence/SequenceDiagram',[
requirejs(['sequence/SequenceDiagram'], (SequenceDiagram) => {
'use strict';
+ const def = window.define;
+ if(def && def.amd) {
+ def(() => {
+ return SequenceDiagram;
+ });
+ return;
+ }
+
document.addEventListener('DOMContentLoaded', () => {
SequenceDiagram.convertAll();
}, {once: true});
diff --git a/lib/sequence-diagram.min.js b/lib/sequence-diagram.min.js
index e1b7eb4..7af1b9a 100644
--- a/lib/sequence-diagram.min.js
+++ b/lib/sequence-diagram.min.js
@@ -1 +1 @@
-!function(){var requirejs,require,define;!function(undef){function hasProp(obj,prop){return hasOwn.call(obj,prop)}function normalize(name,baseName){var nameParts,nameSegment,mapValue,foundMap,lastIndex,foundI,foundStarMap,starI,i,j,part,baseParts=baseName&&baseName.split("/"),map=config.map,starMap=map&&map["*"]||{};if(name){for(lastIndex=(name=name.split("/")).length-1,config.nodeIdCompat&&jsSuffixRegExp.test(name[lastIndex])&&(name[lastIndex]=name[lastIndex].replace(jsSuffixRegExp,"")),"."===name[0].charAt(0)&&baseParts&&(name=baseParts.slice(0,baseParts.length-1).concat(name)),i=0;i0&&(name.splice(i-1,2),i-=2)}name=name.join("/")}if((baseParts||starMap)&&map){for(i=(nameParts=name.split("/")).length;i>0;i-=1){if(nameSegment=nameParts.slice(0,i).join("/"),baseParts)for(j=baseParts.length;j>0;j-=1)if((mapValue=map[baseParts.slice(0,j).join("/")])&&(mapValue=mapValue[nameSegment])){foundMap=mapValue,foundI=i;break}if(foundMap)break;!foundStarMap&&starMap&&starMap[nameSegment]&&(foundStarMap=starMap[nameSegment],starI=i)}!foundMap&&foundStarMap&&(foundMap=foundStarMap,foundI=starI),foundMap&&(nameParts.splice(0,foundI,foundMap),name=nameParts.join("/"))}return name}function makeRequire(relName,forceSync){return function(){var args=aps.call(arguments,0);return"string"!=typeof args[0]&&1===args.length&&args.push(null),req.apply(undef,args.concat([relName,forceSync]))}}function makeLoad(depName){return function(value){defined[depName]=value}}function callDep(name){if(hasProp(waiting,name)){var args=waiting[name];delete waiting[name],defining[name]=!0,main.apply(undef,args)}if(!hasProp(defined,name)&&!hasProp(defining,name))throw new Error("No "+name);return defined[name]}function splitPrefix(name){var prefix,index=name?name.indexOf("!"):-1;return index>-1&&(prefix=name.substring(0,index),name=name.substring(index+1,name.length)),[prefix,name]}function makeRelParts(relName){return relName?splitPrefix(relName):[]}var main,req,makeMap,handlers,defined={},waiting={},config={},defining={},hasOwn=Object.prototype.hasOwnProperty,aps=[].slice,jsSuffixRegExp=/\.js$/;makeMap=function(name,relParts){var plugin,parts=splitPrefix(name),prefix=parts[0],relResourceName=relParts[1];return name=parts[1],prefix&&(plugin=callDep(prefix=normalize(prefix,relResourceName))),prefix?name=plugin&&plugin.normalize?plugin.normalize(name,function(relName){return function(name){return normalize(name,relName)}}(relResourceName)):normalize(name,relResourceName):(prefix=(parts=splitPrefix(name=normalize(name,relResourceName)))[0],name=parts[1],prefix&&(plugin=callDep(prefix))),{f:prefix?prefix+"!"+name:name,n:name,pr:prefix,p:plugin}},handlers={require:function(name){return makeRequire(name)},exports:function(name){var e=defined[name];return void 0!==e?e:defined[name]={}},module:function(name){return{id:name,uri:"",exports:defined[name],config:function(name){return function(){return config&&config.config&&config.config[name]||{}}}(name)}}},main=function(name,deps,callback,relName){var cjsModule,depName,ret,map,i,relParts,usingExports,args=[],callbackType=typeof callback;if(relName=relName||name,relParts=makeRelParts(relName),"undefined"===callbackType||"function"===callbackType){for(deps=!deps.length&&callback.length?["require","exports","module"]:deps,i=0;i{"use strict";return class{constructor(){this.listeners=new Map,this.forwards=new Set}addEventListener(type,callback){const l=this.listeners.get(type);l?l.push(callback):this.listeners.set(type,[callback])}removeEventListener(type,fn){const l=this.listeners.get(type);if(!l)return;const i=l.indexOf(fn);-1!==i&&l.splice(i,1)}countEventListeners(type){return(this.listeners.get(type)||[]).length}removeAllEventListeners(type){type?this.listeners.delete(type):this.listeners.clear()}addEventForwarding(target){this.forwards.add(target)}removeEventForwarding(target){this.forwards.delete(target)}removeAllEventForwardings(){this.forwards.clear()}trigger(type,params=[]){(this.listeners.get(type)||[]).forEach(listener=>listener.apply(null,params)),this.forwards.forEach(fwd=>fwd.trigger(type,params))}}}),define("core/ArrayUtilities",[],()=>{"use strict";function indexOf(list,element,equalityCheck=null){if(null===equalityCheck)return list.indexOf(element);for(let i=0;i=parts.length)return void target.push(current.slice());const choices=parts[position];if(!Array.isArray(choices))return current.push(choices),combineRecur(parts,position+1,current,target),void current.pop();for(let i=0;i{result.push(...fn(item))}),result}}}),define("sequence/CodeMirrorMode",["core/ArrayUtilities"],array=>{"use strict";function cmGetSuggestions(state,token,previous,current){return""===token?function(state,previous,current){return"object"==typeof current.suggest&¤t.suggest.global?[current.suggest]:"string"!=typeof current.suggest||previous.suggest===current.suggest?null:state["known"+current.suggest]}(state,previous,current):!0===current.suggest?[function(token,current){return Object.keys(current.then).length>0?token+" ":token+"\n"}(token,current)]:Array.isArray(current.suggest)?current.suggest:current.suggest?[current.suggest]:null}function cmMakeCompletions(state,path){const comp=[],current=array.last(path);return Object.keys(current.then).forEach(token=>{let next=current.then[token];"number"==typeof next&&(next=path[path.length-next-1]),array.mergeSets(comp,cmGetSuggestions(state,token,current,next))}),comp}function updateSuggestion(state,locals,token,{suggest:suggest,override:override}){locals.type&&suggest!==locals.type&&(override&&(locals.type=override),array.mergeSets(state["known"+locals.type],[locals.value+" "]),locals.type="",locals.value=""),"string"==typeof suggest&&state["known"+suggest]&&(locals.type=suggest,locals.value&&(locals.value+=token.s),locals.value+=token.v)}function cmCheckToken(state,eol,commands){const suggestions={type:"",value:""};let current=commands;const path=[current];return state.line.forEach((token,i)=>{i===state.line.length-1&&(state.completions=cmMakeCompletions(state,path));const keywordToken=token.q?"":token.v,found=current.then[keywordToken]||current.then[""];"number"==typeof found?path.length-=found:path.push(found||CM_ERROR),current=array.last(path),updateSuggestion(state,suggestions,token,current)}),eol&&updateSuggestion(state,suggestions,null,{}),state.nextCompletions=cmMakeCompletions(state,path),state.valid=Boolean(current.then["\n"])||0===Object.keys(current.then).length,current.type}function getInitialToken(block){const baseToken=block.baseToken||{};return{value:baseToken.v||"",quoted:baseToken.q||!1}}const CM_ERROR={type:"error line-error",then:{"":0}},makeCommands=(()=>{function textTo(exit){return{type:"string",then:Object.assign({"":0},exit)}}function agentListTo(exit){return{type:"variable",suggest:"Agent",then:Object.assign({},exit,{"":0,",":{type:"operator",suggest:!0,then:{"":1}}})}}function makeSideNote(side){return{type:"keyword",suggest:[side+" of ",side+": "],then:{of:{type:"keyword",suggest:!0,then:{"":agentListToText}},":":{type:"operator",suggest:!0,then:{"":textToEnd}},"":agentListToText}}}function makeOpBlock(exit){const op={type:"operator",suggest:!0,then:{"+":CM_ERROR,"-":CM_ERROR,"*":CM_ERROR,"!":CM_ERROR,"":exit}};return{"+":{type:"operator",suggest:!0,then:{"+":CM_ERROR,"-":CM_ERROR,"*":op,"!":CM_ERROR,"":exit}},"-":{type:"operator",suggest:!0,then:{"+":CM_ERROR,"-":CM_ERROR,"*":op,"!":{type:"operator",then:{"+":CM_ERROR,"-":CM_ERROR,"*":CM_ERROR,"!":CM_ERROR,"":exit}},"":exit}},"*":{type:"operator",suggest:!0,then:{"+":op,"-":op,"*":CM_ERROR,"!":CM_ERROR,"":exit}},"!":op,"":exit}}const end={type:"",suggest:"\n",then:{}},textToEnd=textTo({"\n":end}),aliasListToEnd={type:"variable",suggest:"Agent",then:{"":0,"\n":end,",":{type:"operator",suggest:!0,then:{"":1}},as:{type:"keyword",suggest:!0,then:{"":{type:"variable",suggest:"Agent",then:{"":0,",":{type:"operator",suggest:!0,then:{"":3}},"\n":end}}}}}},agentListToText=agentListTo({":":{type:"operator",suggest:!0,then:{"":textToEnd}}}),agentList2ToText={type:"variable",suggest:"Agent",then:{"":0,",":{type:"operator",suggest:!0,then:{"":agentListToText}},":":CM_ERROR}},singleAgentToText={type:"variable",suggest:"Agent",then:{"":0,",":CM_ERROR,":":{type:"operator",suggest:!0,then:{"":textToEnd}}}},agentToOptText={type:"variable",suggest:"Agent",then:{"":0,":":{type:"operator",suggest:!0,then:{"":textToEnd,"\n":{type:"",then:{}}}},"\n":end}},referenceName={":":{type:"operator",suggest:!0,then:{"":textTo({as:{type:"keyword",suggest:!0,then:{"":{type:"variable",suggest:"Agent",then:{"":0,"\n":end}}}}})}}},refDef={type:"keyword",suggest:!0,then:Object.assign({over:{type:"keyword",suggest:!0,then:{"":agentListTo(referenceName)}}},referenceName)},BASE_THEN={title:{type:"keyword",suggest:!0,then:{"":textToEnd}},theme:{type:"keyword",suggest:!0,then:{"":{type:"string",suggest:{global:"themes",suffix:"\n"},then:{"":0,"\n":end}}}},headers:{type:"keyword",suggest:!0,then:{none:{type:"keyword",suggest:!0,then:{}},cross:{type:"keyword",suggest:!0,then:{}},box:{type:"keyword",suggest:!0,then:{}},fade:{type:"keyword",suggest:!0,then:{}},bar:{type:"keyword",suggest:!0,then:{}}}},terminators:{type:"keyword",suggest:!0,then:{none:{type:"keyword",suggest:!0,then:{}},cross:{type:"keyword",suggest:!0,then:{}},box:{type:"keyword",suggest:!0,then:{}},fade:{type:"keyword",suggest:!0,then:{}},bar:{type:"keyword",suggest:!0,then:{}}}},define:{type:"keyword",suggest:!0,then:{"":aliasListToEnd,as:CM_ERROR}},begin:{type:"keyword",suggest:!0,then:{"":aliasListToEnd,reference:refDef,as:CM_ERROR}},end:{type:"keyword",suggest:!0,then:{"":aliasListToEnd,as:CM_ERROR,"\n":end}},if:{type:"keyword",suggest:!0,then:{"":textToEnd,":":{type:"operator",suggest:!0,then:{"":textToEnd}},"\n":end}},else:{type:"keyword",suggest:["else\n","else if: "],then:{if:{type:"keyword",suggest:"if: ",then:{"":textToEnd,":":{type:"operator",suggest:!0,then:{"":textToEnd}}}},"\n":end}},repeat:{type:"keyword",suggest:!0,then:{"":textToEnd,":":{type:"operator",suggest:!0,then:{"":textToEnd}},"\n":end}},note:{type:"keyword",suggest:!0,then:{over:{type:"keyword",suggest:!0,then:{"":agentListToText}},left:makeSideNote("left"),right:makeSideNote("right"),between:{type:"keyword",suggest:!0,then:{"":agentList2ToText}}}},state:{type:"keyword",suggest:"state over ",then:{over:{type:"keyword",suggest:!0,then:{"":singleAgentToText}}}},text:{type:"keyword",suggest:!0,then:{left:makeSideNote("left"),right:makeSideNote("right")}},autolabel:{type:"keyword",suggest:!0,then:{off:{type:"keyword",suggest:!0,then:{}},"":textToEnd}},simultaneously:{type:"keyword",suggest:!0,then:{":":{type:"operator",suggest:!0,then:{}},with:{type:"keyword",suggest:!0,then:{"":{type:"variable",suggest:"Label",then:{"":0,":":{type:"operator",suggest:!0,then:{}}}}}}}}};return arrows=>({type:"error line-error",then:Object.assign({},BASE_THEN,function(arrows){const connect={type:"keyword",suggest:!0,then:makeOpBlock(agentToOptText)},then={"":0};return arrows.forEach(arrow=>then[arrow]=connect),then[":"]={type:"operator",suggest:!0,override:"Label",then:{}},makeOpBlock({type:"variable",suggest:"Agent",then:then})}(arrows))})})();return class{constructor(tokenDefinitions,arrows){this.tokenDefinitions=tokenDefinitions,this.commands=makeCommands(arrows),this.lineComment="#"}startState(){return{currentType:-1,current:"",currentSpace:"",currentQuoted:!1,knownAgent:[],knownLabel:[],beginCompletions:cmMakeCompletions({},[this.commands]),completions:[],nextCompletions:[],valid:!0,line:[],indent:0}}_matchPattern(stream,pattern,consume){return pattern?(pattern.lastIndex=0,stream.match(pattern,consume)):null}_tokenBegin(stream,state){state.currentSpace="";let lastChar="";for(;;){if(stream.eol())return!1;state.currentSpace+=lastChar;for(let i=0;i{"use strict";function execAt(str,reg,i){return reg.lastIndex=i,reg.exec(str)}function unescape(match){return"n"===match[1]?"\n":match[1]}function tokAdvance(src,i,block){return block?function(src,i,block){if(block.escape){const match=execAt(src,block.escape,i);if(match)return{newBlock:null,end:!1,appendSpace:"",appendValue:block.escapeWith(match),skip:match[0].length}}const match=execAt(src,block.end,i);return match?{newBlock:null,end:!0,appendSpace:"",appendValue:"",skip:match[0].length}:{newBlock:null,end:!1,appendSpace:"",appendValue:src[i],skip:1}}(src,i,block):function(src,i){for(let j=0;j,])/y,end:/(?=[ \t\r\n:+\-~*!<>,])|$/y},{start:/(?=[\-~<>])/y,end:/(?=[^\-~<>])|$/y},{start:/,/y,baseToken:{v:","}},{start:/:/y,baseToken:{v:":"}},{start:/!/y,baseToken:{v:"!"}},{start:/\+/y,baseToken:{v:"+"}},{start:/\*/y,baseToken:{v:"*"}},{start:/\n/y,baseToken:{v:"\n"}}];class TokenState{constructor(src){this.src=src,this.block=null,this.token=null,this.pos={i:0,ln:0,ch:0},this.reset()}isOver(){return this.pos.i>this.src.length}reset(){this.token={s:"",v:"",q:!1,b:null,e:null},this.block=null}beginToken(advance){this.block=advance.newBlock,Object.assign(this.token,this.block.baseToken),this.token.b=copyPos(this.pos)}endToken(){let token=null;return this.block.omit||(this.token.e=copyPos(this.pos),token=this.token),this.reset(),token}advance(){const advance=tokAdvance(this.src,this.pos.i,this.block);return advance.newBlock&&this.beginToken(advance),this.token.s+=advance.appendSpace,this.token.v+=advance.appendValue,function(pos,src,steps){for(let i=0;i{token.q||"\n"!==token.v?line.push(token):line.length>0&&(lines.push(line),line=[])}),line.length>0&&lines.push(line),lines}}}),define("sequence/LabelPatternParser",[],()=>{"use strict";function countDP(value){const match=DP_PATTERN.exec(value);return match&&match[1]?match[1].length:0}function parseToken(token){if("label"===token)return{token:"label"};const p=token.indexOf(" ");let type=null,args=null;return-1===p?(type=token,args=[]):(type=token.substr(0,p),args=token.substr(p+1).split(",")),"inc"===type?function(args){let start=1,inc=1,dp=0;return args[0]&&(start=Number(args[0]),dp=Math.max(dp,countDP(args[0]))),args[1]&&(inc=Number(args[1]),dp=Math.max(dp,countDP(args[1]))),{start:start,inc:inc,dp:dp}}(args):"<"+token+">"}const LABEL_PATTERN=/(.*?)<([^<>]*)>/g,DP_PATTERN=/\.([0-9]*)/;return function(raw){const pattern=[];let match=null,end=0;for(LABEL_PATTERN.lastIndex=0;match=LABEL_PATTERN.exec(raw);)match[1]&&pattern.push(match[1]),match[2]&&pattern.push(parseToken(match[2])),end=LABEL_PATTERN.lastIndex;const remainder=raw.substr(end);return remainder&&pattern.push(remainder),pattern}}),define("sequence/CodeMirrorHints",["core/ArrayUtilities"],array=>{"use strict";function makeHintItem(text,ranges){return{text:text,displayText:"\n"===text?"":text.trim(),className:"\n"===text?"pick-virtual":null,from:SQUASH_START.test(text)?ranges.squashFrom:ranges.wordFrom,to:SQUASH_END.test(text)?ranges.squashTo:ranges.wordTo}}function getGlobals({global:global,prefix:prefix="",suffix:suffix=""},globals){const identified=globals[global];return identified?identified.map(item=>prefix+item+suffix):[]}const TRIMMER=/^([ \t]*)(.*)$/,SQUASH_START=/^[ \t\r\n:,]/,SQUASH_END=/[ \t\r\n]$/;return{getHints:function(cm,options){const cur=cm.getCursor(),token=cm.getTokenAt(cur);let partial=token.string;token.end>cur.ch&&(partial=partial.substr(0,cur.ch-token.start));const parts=TRIMMER.exec(partial);partial=parts[2];const from=token.start+parts[1].length,continuation=cur.ch>0&&token.state.line.length>0;let comp=continuation?token.state.completions:token.state.beginCompletions;continuation||(comp=comp.concat(token.state.knownAgent)),function(suggestions,globals={}){for(let i=0;i0&&" "===ln[chFrom-1]&&ranges.squashFrom.ch--," "===ln[chTo]&&ranges.squashTo.ch++,ranges}(cm,cur.line,from,token.end);let selfValid=!1;const list=comp.filter(opt=>opt.startsWith(partial)).map(opt=>opt!==partial+" "||options.completeSingle?makeHintItem(opt,ranges):(selfValid=!0,null)).filter(opt=>null!==opt);return selfValid&&list.length>0&&list.unshift(makeHintItem(partial+" ",ranges)),{list:list,from:ranges.wordFrom,to:ranges.wordTo}}}}),define("sequence/Parser",["core/ArrayUtilities","./Tokeniser","./LabelPatternParser","./CodeMirrorHints"],(array,Tokeniser,labelPatternParser,CMHints)=>{"use strict";function makeError(message,token=null){let suffix="";return token&&(suffix=" at line "+(token.b.ln+1)+", character "+token.b.ch),new Error(message+suffix)}function joinLabel(line,begin=0,end=null){if(null===end&&(end=line.length),end<=begin)return"";let result=line[begin].v;for(let i=begin+1;i=end)&&(aliasSep=end),start>=aliasSep)throw makeError("Missing agent name",function(line,pos){if(pos{const arrows=array.combine([[{tok:"",type:0},{tok:"<",type:1},{tok:"<<",type:2}],[{tok:"-",type:"solid"},{tok:"--",type:"dash"},{tok:"~",type:"wave"}],[{tok:"",type:0},{tok:">",type:1},{tok:">>",type:2}]]).filter(arrow=>0!==arrow[0].type||0!==arrow[2].type),types=new Map;return arrows.forEach(arrow=>{types.set(arrow.map(part=>part.tok).join(""),{line:arrow[1].type,left:arrow[0].type,right:arrow[2].type})}),types})(),CONNECT_AGENT_FLAGS={"*":"begin","+":"start","-":"stop","!":"end"},TERMINATOR_TYPES=["none","box","cross","fade","bar"],NOTE_TYPES={text:{mode:"text",types:{left:{type:"note left",skip:["of"],min:0,max:null},right:{type:"note right",skip:["of"],min:0,max:null}}},note:{mode:"note",types:{over:{type:"note over",skip:[],min:0,max:null},left:{type:"note left",skip:["of"],min:0,max:null},right:{type:"note right",skip:["of"],min:0,max:null},between:{type:"note between",skip:[],min:2,max:null}}},state:{mode:"state",types:{over:{type:"note over",skip:[],min:1,max:1}}}},AGENT_MANIPULATION_TYPES={define:{type:"agent define"},begin:{type:"agent begin",mode:"box"},end:{type:"agent end",mode:"cross"}},PARSERS=[(line,meta)=>"title"!==tokenKeyword(line[0])?null:(meta.title=joinLabel(line,1),!0),(line,meta)=>"theme"!==tokenKeyword(line[0])?null:(meta.theme=joinLabel(line,1),!0),(line,meta)=>{if("terminators"!==tokenKeyword(line[0]))return null;const type=tokenKeyword(line[1]);if(!type)throw makeError("Unspecified termination",line[0]);if(-1===TERMINATOR_TYPES.indexOf(type))throw makeError('Unknown termination "'+type+'"',line[1]);return meta.terminators=type,!0},(line,meta)=>{if("headers"!==tokenKeyword(line[0]))return null;const type=tokenKeyword(line[1]);if(!type)throw makeError("Unspecified header",line[0]);if(-1===TERMINATOR_TYPES.indexOf(type))throw makeError('Unknown header "'+type+'"',line[1]);return meta.headers=type,!0},line=>{if("autolabel"!==tokenKeyword(line[0]))return null;let raw=null;return raw="off"===tokenKeyword(line[1])?"":joinLabel(line,1),{type:"label pattern",pattern:labelPatternParser(raw)}},line=>{if("end"===tokenKeyword(line[0])&&1===line.length)return{type:"block end"};const type=BLOCK_TYPES[tokenKeyword(line[0])];if(!type)return null;let skip=1;return line.length>skip&&(skip=skipOver(line,skip,type.skip,"Invalid block command")),skip=skipOver(line,skip,[":"]),{type:type.type,mode:type.mode,label:joinLabel(line,skip)}},line=>{if("begin"!==tokenKeyword(line[0])||"reference"!==tokenKeyword(line[1]))return null;let agents=[];const labelSep=findToken(line,":");if("over"===tokenKeyword(line[2])&&labelSep>3)agents=readAgentList(line,3,labelSep);else if(2!==labelSep)throw makeError('Expected ":" or "over"',line[2]);const def=readAgent(line,labelSep+1,line.length,{aliases:!0});if(!def.alias)throw makeError("Reference must have an alias",line[labelSep]);return{type:"group begin",agents:agents,mode:"ref",label:def.name,alias:def.alias}},line=>{const type=AGENT_MANIPULATION_TYPES[tokenKeyword(line[0])];return!type||line.length<=1?null:Object.assign({agents:readAgentList(line,1,line.length,{aliases:!0})},type)},line=>{if("simultaneously"!==tokenKeyword(line[0]))return null;if(":"!==tokenKeyword(array.last(line)))return null;let target="";if(line.length>2){if("with"!==tokenKeyword(line[1]))return null;target=joinLabel(line,2,line.length-1)}return{type:"async",target:target}},line=>{const mode=NOTE_TYPES[tokenKeyword(line[0])],labelSep=findToken(line,":");if(!mode||-1===labelSep)return null;const type=mode.types[tokenKeyword(line[1])];if(!type)return null;let skip=2;const agents=readAgentList(line,skip=skipOver(line,skip,type.skip),labelSep);if(agents.lengthtype.max)throw makeError("Too many agents for "+mode.mode,line[0]);return{type:type.type,agents:agents,mode:mode.mode,label:joinLabel(line,labelSep+1)}},line=>{let labelSep=findToken(line,":");-1===labelSep&&(labelSep=line.length);let typePos=-1,options=null;for(let j=0;j=labelSep-1)return null;const readAgentOpts={flagTypes:CONNECT_AGENT_FLAGS};return{type:"connect",agents:[readAgent(line,0,typePos,readAgentOpts),readAgent(line,typePos+1,labelSep,readAgentOpts)],label:joinLabel(line,labelSep+1),options:options}},line=>line.length<2||":"!==tokenKeyword(array.last(line))?null:{type:"mark",name:joinLabel(line,0,line.length-1)}],SHARED_TOKENISER=new Tokeniser;return class{getCodeMirrorMode(){return SHARED_TOKENISER.getCodeMirrorMode(Array.from(CONNECT_TYPES.keys()))}getCodeMirrorHints(){return CMHints.getHints}parseLines(lines){const result={meta:{title:"",theme:"",terminators:"none",headers:"box"},stages:[]};return lines.forEach(line=>(function(line,{meta:meta,stages:stages}){let stage=null;for(let i=0;i{"use strict";function mergableParallel(target,copy){const info=MERGABLE[target.type];return!(!info||target.type!==copy.type)&&!info.check.some(c=>target[c]!==copy[c])}function performMerge(target,copy){MERGABLE[target.type].merge.forEach(m=>{array.mergeSets(target[m],copy[m])})}function iterateRemoval(list,fn){for(let i=0;i{for(let j=0;jtype);return types.forEach(type=>{const info=MERGABLE[type];info&&types.every(sType=>type===sType||info.siblings.has(sType))&&mergers.add(type)}),mergers}function performSequentialMergers(lastViable,viable,lastStages,stages){iterateRemoval(stages,stage=>{if(!lastViable.has(stage.type)||!viable.has(stage.type))return!1;for(let j=0;j{"agent begin"===subStage.type&&(subStage.mode=mode,any=!0)}),any}return!1}function addBounds(target,agentL,agentR,involvedAgents=null){array.remove(target,agentL,Agent.equals),array.remove(target,agentR,Agent.equals);let indexL=0,indexR=target.length;if(involvedAgents){const found=involvedAgents.map(agent=>array.indexOf(target,agent,Agent.equals)).filter(p=>-1!==p);indexL=found.reduce((a,b)=>Math.min(a,b),target.length),indexR=found.reduce((a,b)=>Math.max(a,b),indexL)+1}return target.splice(indexL,0,agentL),target.splice(indexR+1,0,agentR),{indexL:indexL,indexR:indexR+1}}class AgentState{constructor({visible:visible=!1,locked:locked=!1,blocked:blocked=!1,highlighted:highlighted=!1,group:group=null,covered:covered=!1}={}){this.visible=visible,this.locked=locked,this.blocked=blocked,this.highlighted=highlighted,this.group=group,this.covered=covered}}AgentState.LOCKED=new AgentState({locked:!0}),AgentState.DEFAULT=new AgentState;const Agent={equals:(a,b)=>a.name===b.name,make:(name,{anchorRight:anchorRight=!1}={})=>({name:name,anchorRight:anchorRight}),getName:agent=>agent.name,hasFlag:(flag,has=!0)=>agent=>agent.flags.includes(flag)===has},MERGABLE={"agent begin":{check:["mode"],merge:["agentNames"],siblings:new Set(["agent highlight"])},"agent end":{check:["mode"],merge:["agentNames"],siblings:new Set(["agent highlight"])},"agent highlight":{check:["highlighted"],merge:["agentNames"],siblings:new Set(["agent begin","agent end"])}},NOTE_DEFAULT_AGENTS={"note over":[{name:"[",flags:[]},{name:"]",flags:[]}],"note left":[{name:"[",flags:[]}],"note right":[{name:"]",flags:[]}]};return class{constructor(){this.agentStates=new Map,this.agentAliases=new Map,this.activeGroups=new Map,this.agents=[],this.labelPattern=null,this.blockCount=0,this.nesting=[],this.markers=new Set,this.currentSection=null,this.currentNest=null,this.stageHandlers={"block begin":this.handleBlockBegin.bind(this),"block split":this.handleBlockSplit.bind(this),"block end":this.handleBlockEnd.bind(this),"group begin":this.handleGroupBegin.bind(this),mark:this.handleMark.bind(this),async:this.handleAsync.bind(this),"agent define":this.handleAgentDefine.bind(this),"agent begin":this.handleAgentBegin.bind(this),"agent end":this.handleAgentEnd.bind(this),"label pattern":this.handleLabelPattern.bind(this),connect:this.handleConnect.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)},this.expandGroupedAgent=this.expandGroupedAgent.bind(this),this.handleStage=this.handleStage.bind(this),this.convertAgent=this.convertAgent.bind(this),this.endGroup=this.endGroup.bind(this)}convertAgent({alias:alias,name:name}){if(alias){if(this.agentAliases.has(name))throw new Error("Cannot alias "+name+"; it is already an alias");const old=this.agentAliases.get(alias);if(old&&old!==alias||this.agents.some(agent=>agent.name===alias))throw new Error("Cannot use "+alias+" as an alias; it is already in use");this.agentAliases.set(alias,name)}return Agent.make(this.agentAliases.get(name)||name)}addStage(stage,isVisible=!0){stage&&(void 0===stage.ln&&(stage.ln=this.latestLine),this.currentSection.stages.push(stage),isVisible&&(this.currentNest.hasContent=!0))}addParallelStages(stages){const viableStages=stages.filter(stage=>Boolean(stage));if(0!==viableStages.length)return 1===viableStages.length?this.addStage(viableStages[0]):(viableStages.forEach(stage=>{void 0===stage.ln&&(stage.ln=this.latestLine)}),this.addStage({type:"parallel",stages:viableStages}))}defineAgents(colAgents){array.mergeSets(this.currentNest.agents,colAgents,Agent.equals),array.mergeSets(this.agents,colAgents,Agent.equals)}getAgentState(agent){return this.agentStates.get(agent.name)||AgentState.DEFAULT}updateAgentState(agent,change){const state=this.agentStates.get(agent.name);state?Object.assign(state,change):this.agentStates.set(agent.name,new AgentState(change))}validateAgents(agents,{allowGrouped:allowGrouped=!1,rejectGrouped:rejectGrouped=!1}={}){agents.forEach(agent=>{const state=this.getAgentState(agent);if(state.covered)throw new Error("Agent "+agent.name+" is hidden behind group");if(rejectGrouped&&null!==state.group)throw new Error("Agent "+agent.name+" is in a group");if(state.blocked&&(!allowGrouped||null===state.group))throw new Error("Duplicate agent name: "+agent.name);if(agent.name.startsWith("__"))throw new Error(agent.name+" is a reserved name")})}setAgentVis(colAgents,visible,mode,checked=!1){const seen=new Set,filteredAgents=colAgents.filter(agent=>{if(seen.has(agent.name))return!1;seen.add(agent.name);const state=this.getAgentState(agent);if(state.locked||state.blocked){if(checked)throw new Error("Cannot begin/end agent: "+agent.name);return!1}return state.visible!==visible});return 0===filteredAgents.length?null:(filteredAgents.forEach(agent=>{this.updateAgentState(agent,{visible:visible})}),this.defineAgents(filteredAgents),{type:visible?"agent begin":"agent end",agentNames:filteredAgents.map(Agent.getName),mode:mode})}setAgentHighlight(colAgents,highlighted,checked=!1){const filteredAgents=colAgents.filter(agent=>{const state=this.getAgentState(agent);if(state.locked||state.blocked){if(checked)throw new Error("Cannot highlight agent: "+agent.name);return!1}return state.visible&&state.highlighted!==highlighted});return 0===filteredAgents.length?null:(filteredAgents.forEach(agent=>{this.updateAgentState(agent,{highlighted:highlighted})}),{type:"agent highlight",agentNames:filteredAgents.map(Agent.getName),highlighted:highlighted})}beginNested(mode,label,name,ln){const leftAgent=Agent.make(name+"[",{anchorRight:!0}),rightAgent=Agent.make(name+"]"),agents=[leftAgent,rightAgent],stages=[];return this.currentSection={header:{type:"block begin",mode:mode,label:label,left:leftAgent.name,right:rightAgent.name,ln:ln},stages:stages},this.currentNest={mode:mode,agents:agents,leftAgent:leftAgent,rightAgent:rightAgent,hasContent:!1,sections:[this.currentSection]},this.agentStates.set(leftAgent.name,AgentState.LOCKED),this.agentStates.set(rightAgent.name,AgentState.LOCKED),this.nesting.push(this.currentNest),{agents:agents,stages:stages}}nextBlockName(){const name="__BLOCK"+this.blockCount;return++this.blockCount,name}handleBlockBegin({ln:ln,mode:mode,label:label}){this.beginNested(mode,label,this.nextBlockName(),ln)}handleBlockSplit({ln:ln,mode:mode,label:label}){if("if"!==this.currentNest.mode)throw new Error('Invalid block nesting ("else" inside '+this.currentNest.mode+")");optimiseStages(this.currentSection.stages),this.currentSection={header:{type:"block split",mode:mode,label:label,left:this.currentNest.leftAgent.name,right:this.currentNest.rightAgent.name,ln:ln},stages:[]},this.currentNest.sections.push(this.currentSection)}handleBlockEnd(){if(this.nesting.length<=1)throw new Error('Invalid block nesting (too many "end"s)');optimiseStages(this.currentSection.stages);const nested=this.nesting.pop();if(this.currentNest=array.last(this.nesting),this.currentSection=array.last(this.currentNest.sections),!nested.hasContent)throw new Error("Empty block");this.defineAgents(nested.agents),addBounds(this.agents,nested.leftAgent,nested.rightAgent,nested.agents),nested.sections.forEach(section=>{this.currentSection.stages.push(section.header),this.currentSection.stages.push(...section.stages)}),this.addStage({type:"block end",left:nested.leftAgent.name,right:nested.rightAgent.name})}makeGroupDetails(agents,alias){const colAgents=agents.map(this.convertAgent);if(this.validateAgents(colAgents,{rejectGrouped:!0}),this.agentStates.has(alias))throw new Error("Duplicate agent name: "+alias);const name=this.nextBlockName(),leftAgent=Agent.make(name+"[",{anchorRight:!0}),rightAgent=Agent.make(name+"]");this.agentStates.set(leftAgent.name,AgentState.LOCKED),this.agentStates.set(rightAgent.name,AgentState.LOCKED),this.updateAgentState({name:alias},{blocked:!0,group:alias}),this.defineAgents(colAgents);const{indexL:indexL,indexR:indexR}=addBounds(this.agents,leftAgent,rightAgent,colAgents),agentsCovered=[],agentsContained=colAgents.slice();for(let i=indexL+1;i{this.updateAgentState(agent,{group:alias})}),details.agentsCovered.forEach(agent=>{this.updateAgentState(agent,{covered:!0})}),this.activeGroups.set(alias,details),this.addStage(this.setAgentVis(details.colAgents,!0,"box")),this.addStage({type:"block begin",mode:mode,label:label,left:details.leftAgent.name,right:details.rightAgent.name})}endGroup({name:name}){const details=this.activeGroups.get(name);return details?(this.activeGroups.delete(name),details.agentsContained.forEach(agent=>{this.updateAgentState(agent,{group:null})}),details.agentsCovered.forEach(agent=>{this.updateAgentState(agent,{covered:!1})}),this.updateAgentState({name:name},{group:null}),{type:"block end",left:details.leftAgent.name,right:details.rightAgent.name}):null}handleMark({name:name}){this.markers.add(name),this.addStage({type:"mark",name:name},!1)}handleAsync({target:target}){if(""!==target&&!this.markers.has(target))throw new Error("Unknown marker: "+target);this.addStage({type:"async",target:target},!1)}handleLabelPattern({pattern:pattern}){this.labelPattern=pattern.slice();for(let i=0;i{"string"==typeof part?result+=part:void 0!==part.token?result+=tokens[part.token]:void 0!==part.current&&(result+=part.current.toFixed(part.dp),part.current+=part.inc)}),result}expandGroupedAgent(agent){const group=this.getAgentState(agent).group;if(!group)return[agent];const details=this.activeGroups.get(group);return[details.leftAgent,details.rightAgent]}expandGroupedAgentConnection(agents){const agents1=this.expandGroupedAgent(agents[0]),agents2=this.expandGroupedAgent(agents[1]);let ind1=array.indexOf(this.agents,agents1[0],Agent.equals),ind2=array.indexOf(this.agents,agents2[0],Agent.equals);return-1===ind1&&(ind1=this.agents.length),-1===ind2&&(ind2=this.agents.length),ind1===ind2?[array.last(agents1),array.last(agents2)]:ind1this.activeGroups.has(agent.name)),colAgents=agents.filter(agent=>!this.activeGroups.has(agent.name)).map(this.convertAgent);this.validateAgents(colAgents),this.addParallelStages([this.setAgentHighlight(colAgents,!1),this.setAgentVis(colAgents,!1,mode,!0),...groupAgents.map(this.endGroup)])}handleStage(stage){this.latestLine=stage.ln;try{const handler=this.stageHandlers[stage.type];if(!handler)throw new Error("Unknown command: "+stage.type);handler(stage)}catch(e){if("object"==typeof e&&e.message)throw new Error(e.message+" at line "+(stage.ln+1))}}generate({stages:stages,meta:meta={}}){this.agentStates.clear(),this.markers.clear(),this.agentAliases.clear(),this.activeGroups.clear(),this.agents.length=0,this.blockCount=0,this.nesting.length=0,this.labelPattern=[{token:"label"}];const globals=this.beginNested("global","","",0);if(stages.forEach(this.handleStage),1!==this.nesting.length)throw new Error("Unterminated section at line "+(this.currentSection.header.ln+1));if(this.activeGroups.size>0)throw new Error("Unterminated group");const terminators=meta.terminators||"none";return this.addParallelStages([this.setAgentHighlight(this.agents,!1),this.setAgentVis(this.agents,!1,terminators)]),addBounds(this.agents,this.currentNest.leftAgent,this.currentNest.rightAgent),optimiseStages(globals.stages),function(stages,mode){for(let i=0;i{"use strict";function make(type,attrs={}){const o=document.createElementNS(NS,type);for(let k in attrs)attrs.hasOwnProperty(k)&&o.setAttribute(k,attrs[k]);return o}const NS="http://www.w3.org/2000/svg";return{makeText:function(text=""){return document.createTextNode(text)},make:make,makeContainer:function(attrs={}){return make("svg",Object.assign({xmlns:NS,version:"1.1"},attrs))},empty:function(node){for(;node.childNodes.length>0;)node.removeChild(node.lastChild)}}}),define("svg/SVGTextBlock",["./SVGUtilities"],svg=>{"use strict";function fontDetails(attrs){const size=Number(attrs["font-size"]);return{size:size,lineHeight:size*(Number(attrs["line-height"])||1)}}const firefox=void 0!==window.InstallTrigger;class SVGTextBlock{constructor(container,initialState={}){this.container=container,this.state={attrs:{},text:"",x:0,y:0},this.width=0,this.height=0,this.nodes=[],this.set(initialState)}_rebuildNodes(count){if(count>this.nodes.length){const attrs=Object.assign({x:this.state.x},this.state.attrs);for(;this.nodes.lengthcount;){const{element:element}=this.nodes.pop();this.container.removeChild(element)}}_reset(){this._rebuildNodes(0),this.width=0,this.height=0}_renderText(){if(!this.state.text)return void this._reset();const lines=this.state.text.split("\n");this._rebuildNodes(lines.length);let maxWidth=0;this.nodes.forEach(({text:text,element:element},i)=>{text.nodeValue!==lines[i]&&(text.nodeValue=lines[i]),maxWidth=Math.max(maxWidth,element.getComputedTextLength())}),this.width=maxWidth}_updateX(){this.nodes.forEach(({element:element})=>{element.setAttribute("x",this.state.x)})}_updateY(){const{size:size,lineHeight:lineHeight}=fontDetails(this.state.attrs);this.nodes.forEach(({element:element},i)=>{element.setAttribute("y",this.state.y+i*lineHeight+size)}),this.height=lineHeight*this.nodes.length}firstLine(){return this.nodes.length>0?this.nodes[0].element:null}set(newState){const oldState=Object.assign({},this.state);!function(state,newState){for(let k in state)state.hasOwnProperty(k)&&null!==newState[k]&&void 0!==newState[k]&&(state[k]=newState[k])}(this.state,newState),this.state.attrs!==oldState.attrs&&(this._reset(),oldState.text="");const oldNodes=this.nodes.length;this.state.text!==oldState.text&&this._renderText(),this.state.x!==oldState.x&&this._updateX(),this.state.y===oldState.y&&this.nodes.length===oldNodes||this._updateY()}}class SizeTester{constructor(container){this.testers=svg.make("g",{display:firefox?"block":"none",visibility:"hidden"}),this.container=container,this.cache=new Map}measure(attrs,content){if(!content)return{width:0,height:0};let tester=this.cache.get(attrs);if(!tester){const text=svg.makeText(),node=svg.make("text",attrs);node.appendChild(text),this.testers.appendChild(node),tester={text:text,node:node},this.cache.set(attrs,tester)}this.testers.parentNode||this.container.appendChild(this.testers);const lines=content.split("\n");let width=0;return lines.forEach(line=>{tester.text.nodeValue=line,width=Math.max(width,tester.node.getComputedTextLength())}),{width:width,height:lines.length*fontDetails(attrs).lineHeight}}measureHeight(attrs,content){if(!content)return 0;return content.split("\n").length*fontDetails(attrs).lineHeight}resetCache(){svg.empty(this.testers),this.cache.clear()}detach(){this.testers.parentNode&&this.container.removeChild(this.testers)}}return SVGTextBlock.SizeTester=SizeTester,SVGTextBlock}),define("svg/SVGShapes",["./SVGUtilities","./SVGTextBlock"],(svg,SVGTextBlock)=>{"use strict";function renderBox(attrs,position){return svg.make("rect",Object.assign({},position,attrs))}return{renderBox:renderBox,renderNote:function(attrs,flickAttrs,position){const g=svg.make("g"),x0=position.x,x1=position.x+position.width,y0=position.y,y1=position.y+position.height;return g.appendChild(svg.make("polygon",Object.assign({points:x0+" "+y0+" "+(x1-7)+" "+y0+" "+x1+" "+(y0+7)+" "+x1+" "+y1+" "+x0+" "+y1},attrs))),g.appendChild(svg.make("polyline",Object.assign({points:x1-7+" "+y0+" "+(x1-7)+" "+(y0+7)+" "+x1+" "+(y0+7)},flickAttrs))),g},renderBoxedText:function(text,{x:x,y:y,padding:padding,boxAttrs:boxAttrs,labelAttrs:labelAttrs,boxLayer:boxLayer,labelLayer:labelLayer,boxRenderer:boxRenderer=null,SVGTextBlockClass:SVGTextBlockClass=SVGTextBlock}){if(!text)return{width:0,height:0,label:null,box:null};let shift=0,anchorX=x;switch(labelAttrs["text-anchor"]){case"middle":shift=.5,anchorX+=(padding.left-padding.right)/2;break;case"end":shift=1,anchorX-=padding.right;break;default:shift=0,anchorX+=padding.left}const label=new SVGTextBlockClass(labelLayer,{attrs:labelAttrs,text:text,x:anchorX,y:y+padding.top}),width=label.width+padding.left+padding.right,height=label.height+padding.top+padding.bottom;let box=null;return box=boxRenderer?boxRenderer({x:anchorX-label.width*shift-padding.left,y:y,width:width,height:height}):renderBox(boxAttrs,{x:anchorX-label.width*shift-padding.left,y:y,width:width,height:height}),boxLayer===labelLayer?boxLayer.insertBefore(box,label.firstLine()):boxLayer.appendChild(box),{width:width,height:height,label:label,box:box}},TextBlock:SVGTextBlock}}),define("sequence/components/BaseComponent",[],()=>{"use strict";class BaseComponent{makeState(){}resetState(state){this.makeState(state)}separationPre(){}separation(){}renderPre(){}render(){}}BaseComponent.cleanRenderPreResult=(({topShift:topShift=0,agentNames:agentNames=[],asynchronousY:asynchronousY=null}={},currentY=null)=>({topShift:topShift,agentNames:agentNames,asynchronousY:null!==asynchronousY?asynchronousY:currentY}));const components=new Map;return BaseComponent.register=((name,component)=>{components.set(name,component)}),BaseComponent.getComponents=(()=>components),BaseComponent}),define("sequence/components/Block",["./BaseComponent","core/ArrayUtilities","svg/SVGUtilities","svg/SVGShapes"],(BaseComponent,array,svg,SVGShapes)=>{"use strict";class BlockSplit extends BaseComponent{separation({left:left,right:right,mode:mode,label:label},env){const config=env.theme.block.section,width=env.textSizer.measure(config.mode.labelAttrs,mode).width+config.mode.padding.left+config.mode.padding.right+env.textSizer.measure(config.label.labelAttrs,label).width+config.label.padding.left+config.label.padding.right;env.addSeparation(left,right,width)}renderPre({left:left,right:right}){return{agentNames:[left,right]}}render({left:left,right:right,mode:mode,label:label},env,first=!1){const config=env.theme.block,agentInfoL=env.agentInfos.get(left),agentInfoR=env.agentInfos.get(right);let y=env.primaryY;first||(y+=config.section.padding.bottom,env.sectionLayer.appendChild(svg.make("line",Object.assign({x1:agentInfoL.x,y1:y,x2:agentInfoR.x,y2:y},config.separator.attrs))));const modeRender=SVGShapes.renderBoxedText(mode,{x:agentInfoL.x,y:y,padding:config.section.mode.padding,boxAttrs:config.section.mode.boxAttrs,labelAttrs:config.section.mode.labelAttrs,boxLayer:env.blockLayer,labelLayer:env.labelLayer,SVGTextBlockClass:env.SVGTextBlockClass}),labelRender=SVGShapes.renderBoxedText(label,{x:agentInfoL.x+modeRender.width,y:y,padding:config.section.label.padding,boxAttrs:{fill:"#000000"},labelAttrs:config.section.label.labelAttrs,boxLayer:env.maskLayer,labelLayer:env.labelLayer,SVGTextBlockClass:env.SVGTextBlockClass});return y+(Math.max(modeRender.height,labelRender.height)+config.section.padding.top)}}class BlockBegin extends BlockSplit{makeState(state){state.blocks=new Map}resetState(state){state.blocks.clear()}separation(stage,env){array.mergeSets(env.visibleAgents,[stage.left,stage.right]),super.separation(stage,env)}renderPre({left:left,right:right},env){return{agentNames:[left,right],topShift:env.theme.block.margin.top}}render(stage,env){return env.state.blocks.set(stage.left,{mode:stage.mode,startY:env.primaryY}),super.render(stage,env,!0)}}class BlockEnd extends BaseComponent{separation({left:left,right:right},env){array.removeAll(env.visibleAgents,[left,right])}renderPre({left:left,right:right},env){return{agentNames:[left,right],topShift:env.theme.block.section.padding.bottom}}render({left:left,right:right},env){const config=env.theme.block,{startY:startY,mode:mode}=env.state.blocks.get(left),agentInfoL=env.agentInfos.get(left),agentInfoR=env.agentInfos.get(right),configMode=config.modes[mode]||config.modes[""];return env.blockLayer.appendChild(svg.make("rect",Object.assign({x:agentInfoL.x,y:startY,width:agentInfoR.x-agentInfoL.x,height:env.primaryY-startY},configMode.boxAttrs))),env.primaryY+config.margin.bottom+env.theme.actionMargin}}return BaseComponent.register("block begin",new BlockBegin),BaseComponent.register("block split",new BlockSplit),BaseComponent.register("block end",new BlockEnd),{BlockBegin:BlockBegin,BlockSplit:BlockSplit,BlockEnd:BlockEnd}}),define("sequence/components/Parallel",["./BaseComponent","core/ArrayUtilities"],(BaseComponent,array)=>{"use strict";function mergeResults(a,b){return array.mergeSets(a.agentNames,b.agentNames),{topShift:Math.max(a.topShift,b.topShift),agentNames:a.agentNames,asynchronousY:function(a=null,b=null){return null===a?b:null===b?a:Math.max(a,b)}(a.asynchronousY,b.asynchronousY)}}class Parallel extends BaseComponent{separationPre(stage,env){stage.stages.forEach(subStage=>{env.components.get(subStage.type).separationPre(subStage,env)})}separation(stage,env){stage.stages.forEach(subStage=>{env.components.get(subStage.type).separation(subStage,env)})}renderPre(stage,env){return stage.stages.map(subStage=>{const subResult=env.components.get(subStage.type).renderPre(subStage,env);return BaseComponent.cleanRenderPreResult(subResult)}).reduce(mergeResults,{topShift:0,agentNames:[],asynchronousY:null})}render(stage,env){const originalMakeRegion=env.makeRegion;let bottomY=0;return stage.stages.forEach(subStage=>{env.makeRegion=((o,stageOverride=null)=>originalMakeRegion(o,stageOverride||subStage));const baseY=env.components.get(subStage.type).render(subStage,env)||0;bottomY=Math.max(bottomY,baseY)}),env.makeRegion=originalMakeRegion,bottomY}}return BaseComponent.register("parallel",new Parallel),Parallel}),define("sequence/components/Marker",["./BaseComponent"],BaseComponent=>{"use strict";class Mark extends BaseComponent{makeState(state){state.marks=new Map}resetState(state){state.marks.clear()}render({name:name},{topY:topY,state:state}){state.marks.set(name,topY)}}class Async extends BaseComponent{renderPre({target:target},{state:state}){let y=0;return target&&state.marks&&(y=state.marks.get(target)||0),{asynchronousY:y}}}return BaseComponent.register("mark",new Mark),BaseComponent.register("async",new Async),{Mark:Mark,Async:Async}}),define("sequence/components/AgentCap",["./BaseComponent","core/ArrayUtilities","svg/SVGUtilities","svg/SVGShapes"],(BaseComponent,array,svg,SVGShapes)=>{"use strict";class CapBox{separation({label:label},env){const config=env.theme.agentCap.box,width=env.textSizer.measure(config.labelAttrs,label).width+config.padding.left+config.padding.right;return{left:width/2,right:width/2,radius:width/2}}topShift({label:label},env){const config=env.theme.agentCap.box,height=env.textSizer.measureHeight(config.labelAttrs,label)+config.padding.top+config.padding.bottom;return Math.max(0,height-config.arrowBottom)}render(y,{x:x,label:label},env){const config=env.theme.agentCap.box,clickable=env.makeRegion(),{width:width,height:height}=SVGShapes.renderBoxedText(label,{x:x,y:y,padding:config.padding,boxAttrs:config.boxAttrs,labelAttrs:config.labelAttrs,boxLayer:env.shapeLayer,labelLayer:clickable,SVGTextBlockClass:env.SVGTextBlockClass});return clickable.insertBefore(svg.make("rect",{x:x-width/2,y:y,width:width,height:height,fill:"transparent"}),clickable.firstChild),{lineTop:0,lineBottom:height,height:height}}}class CapCross{separation(agentInfo,env){const config=env.theme.agentCap.cross;return{left:config.size/2,right:config.size/2,radius:0}}topShift(agentInfo,env){return env.theme.agentCap.cross.size/2}render(y,{x:x},env){const config=env.theme.agentCap.cross,d=config.size/2;return env.shapeLayer.appendChild(svg.make("path",Object.assign({d:"M "+(x-d)+" "+y+" L "+(x+d)+" "+(y+2*d)+" M "+(x+d)+" "+y+" L "+(x-d)+" "+(y+2*d)},config.attrs))),env.makeRegion().appendChild(svg.make("rect",{x:x-d,y:y,width:2*d,height:2*d,fill:"transparent"})),{lineTop:d,lineBottom:d,height:2*d}}}class CapBar{separation({label:label},env){const config=env.theme.agentCap.box,width=env.textSizer.measure(config.labelAttrs,label).width+config.padding.left+config.padding.right;return{left:width/2,right:width/2,radius:width/2}}topShift(agentInfo,env){return env.theme.agentCap.bar.attrs.height/2}render(y,{x:x,label:label},env){const configB=env.theme.agentCap.box,config=env.theme.agentCap.bar,width=env.textSizer.measure(configB.labelAttrs,label).width+configB.padding.left+configB.padding.right;return env.shapeLayer.appendChild(svg.make("rect",Object.assign({x:x-width/2,y:y,width:width},config.attrs))),env.makeRegion().appendChild(svg.make("rect",{x:x-width/2,y:y,width:width,height:config.attrs.height,fill:"transparent"})),{lineTop:0,lineBottom:config.attrs.height,height:config.attrs.height}}}class CapFade{separation({currentRad:currentRad}){return{left:currentRad,right:currentRad,radius:currentRad}}topShift(agentInfo,env,isBegin){const config=env.theme.agentCap.fade;return isBegin?config.height:0}render(y,{x:x,label:label},env,isBegin){const config=env.theme.agentCap.fade,gradID=env.addDef(isBegin?"FadeIn":"FadeOut",()=>{const grad=svg.make("linearGradient",{x1:"0%",y1:isBegin?"100%":"0%",x2:"0%",y2:isBegin?"0%":"100%"});return grad.appendChild(svg.make("stop",{offset:100/12+"%","stop-color":"#FFFFFF"})),grad.appendChild(svg.make("stop",{offset:1100/12+"%","stop-color":"#000000"})),grad});return env.maskLayer.appendChild(svg.make("rect",{x:x-config.width/2,y:y-.1*config.height,width:config.width,height:1.2*config.height,fill:"url(#"+gradID+")"})),env.makeRegion().appendChild(svg.make("rect",{x:x-config.width/2,y:y,width:config.width,height:config.height,fill:"transparent"})),{lineTop:config.height,lineBottom:0,height:config.height}}}class CapNone{separation({currentRad:currentRad}){return{left:currentRad,right:currentRad,radius:currentRad}}topShift(agentInfo,env){return env.theme.agentCap.none.height}render(y,{x:x},env){const config=env.theme.agentCap.none;return env.makeRegion().appendChild(svg.make("rect",{x:x-5,y:y,width:10,height:config.height,fill:"transparent"})),{lineTop:config.height,lineBottom:0,height:config.height}}}const AGENT_CAPS={box:new CapBox,cross:new CapCross,bar:new CapBar,fade:new CapFade,none:new CapNone};class AgentCap extends BaseComponent{constructor(begin){super(),this.begin=begin}separationPre({mode:mode,agentNames:agentNames},env){agentNames.forEach(name=>{const agentInfo=env.agentInfos.get(name),sep=AGENT_CAPS[mode].separation(agentInfo,env,this.begin);env.addSpacing(name,sep),agentInfo.currentMaxRad=Math.max(agentInfo.currentMaxRad,sep.radius)})}separation({mode:mode,agentNames:agentNames},env){this.begin?array.mergeSets(env.visibleAgents,agentNames):array.removeAll(env.visibleAgents,agentNames)}renderPre({mode:mode,agentNames:agentNames},env){let maxTopShift=0;return agentNames.forEach(name=>{const agentInfo=env.agentInfos.get(name),cap=AGENT_CAPS[mode],topShift=cap.topShift(agentInfo,env,this.begin);maxTopShift=Math.max(maxTopShift,topShift);const r=cap.separation(agentInfo,env,this.begin).radius;agentInfo.currentMaxRad=Math.max(agentInfo.currentMaxRad,r)}),{agentNames:agentNames,topShift:maxTopShift}}render({mode:mode,agentNames:agentNames},env){let maxEnd=0;return agentNames.forEach(name=>{const agentInfo=env.agentInfos.get(name),cap=AGENT_CAPS[mode],topShift=cap.topShift(agentInfo,env,this.begin),y0=env.primaryY-topShift,shifts=cap.render(y0,agentInfo,env,this.begin);maxEnd=Math.max(maxEnd,y0+shifts.height),this.begin?env.drawAgentLine(name,y0+shifts.lineBottom):env.drawAgentLine(name,y0+shifts.lineTop,!0)}),maxEnd+env.theme.actionMargin}}return BaseComponent.register("agent begin",new AgentCap(!0)),BaseComponent.register("agent end",new AgentCap(!1)),AgentCap}),define("sequence/components/AgentHighlight",["./BaseComponent"],BaseComponent=>{"use strict";class AgentHighlight extends BaseComponent{radius(highlighted,env){return highlighted?env.theme.agentLineHighlightRadius:0}separationPre({agentNames:agentNames,highlighted:highlighted},env){const r=this.radius(highlighted,env);agentNames.forEach(name=>{const agentInfo=env.agentInfos.get(name);agentInfo.currentRad=r,agentInfo.currentMaxRad=Math.max(agentInfo.currentMaxRad,r)})}renderPre({agentNames:agentNames,highlighted:highlighted},env){const r=this.radius(highlighted,env);agentNames.forEach(name=>{const agentInfo=env.agentInfos.get(name);agentInfo.currentMaxRad=Math.max(agentInfo.currentMaxRad,r)})}render({agentNames:agentNames,highlighted:highlighted},env){const r=this.radius(highlighted,env);return agentNames.forEach(name=>{env.drawAgentLine(name,env.primaryY),env.agentInfos.get(name).currentRad=r}),env.primaryY+env.theme.actionMargin}}return BaseComponent.register("agent highlight",new AgentHighlight),AgentHighlight}),define("sequence/components/Connect",["./BaseComponent","svg/SVGUtilities","svg/SVGShapes"],(BaseComponent,svg,SVGShapes)=>{"use strict";function makeWavyLineHeights(height){return[0,2*-height/3,-height,2*-height/3,0,2*height/3,height,2*height/3]}class Arrowhead{constructor(propName){this.propName=propName}getConfig(theme){return theme.connect.arrow[this.propName]}short(theme){const arrow=this.getConfig(theme),join=arrow.attrs["stroke-linejoin"]||"miter",t=.5*arrow.attrs["stroke-width"],lineStroke=.5*theme.agentLineAttrs["stroke-width"];if("round"===join)return lineStroke+t;{const h=arrow.height/2,w=arrow.width;return lineStroke+t*Math.sqrt(w*w/(h*h)+1)}}render(layer,theme,{x:x,y:y,dir:dir}){const config=this.getConfig(theme);!function(container,{x:x,y:y,dx:dx,dy:dy,attrs:attrs}){container.appendChild(svg.make("none"===attrs.fill?"polyline":"polygon",Object.assign({points:x+dx+" "+(y-dy)+" "+x+" "+y+" "+(x+dx)+" "+(y+dy)},attrs)))}(layer,{x:x+this.short(theme)*dir,y:y,dx:config.width*dir,dy:config.height/2,attrs:config.attrs})}width(theme){return this.short(theme)+this.getConfig(theme).width}height(theme){return this.getConfig(theme).height}lineGap(theme,lineAttrs){const arrow=this.getConfig(theme),short=this.short(theme);if("none"===arrow.attrs.fill){const h=arrow.height/2,w=arrow.width;return(short+(short+lineAttrs["stroke-width"]/2*(w/h)))/2}return short+arrow.width/2}}const ARROWHEADS=[{render:()=>{},width:()=>0,height:()=>0,lineGap:()=>0},new Arrowhead("single"),new Arrowhead("double")];class ConnectingLine{renderFlat(container,{x1:x1,x2:x2,y:y},attrs){const ww=attrs["wave-width"],hh=attrs["wave-height"];if(!ww||!hh)return void container.appendChild(svg.make("line",Object.assign({x1:x1,y1:y,x2:x2,y2:y},attrs)));const heights=makeWavyLineHeights(hh),dw=ww/heights.length;let p=0,points="";for(let x=x1;x+dw<=x2;x+=dw)points+=x+" "+(y+heights[p++%heights.length])+" ";points+=x2+" "+y,container.appendChild(svg.make("polyline",Object.assign({points:points},attrs)))}renderRev(container,{xL1:xL1,xL2:xL2,y1:y1,y2:y2,xR:xR},attrs){const r=(y2-y1)/2,ww=attrs["wave-width"],hh=attrs["wave-height"];if(!ww||!hh)return void container.appendChild(svg.make("path",Object.assign({d:"M "+xL1+" "+y1+" L "+xR+" "+y1+" A "+r+" "+r+" 0 0 1 "+xR+" "+y2+" L "+xL2+" "+y2},attrs)));const heights=makeWavyLineHeights(hh),dw=ww/heights.length;let p=0,points="";for(let x=xL1;x+dw<=xR;x+=dw)points+=x+" "+(y1+heights[p++%heights.length])+" ";const ym=(y1+y2)/2;for(let t=0;t+dw/r<=Math.PI;t+=dw/r){const h=heights[p++%heights.length];points+=xR+Math.sin(t)*(r-h)+" "+(ym-Math.cos(t)*(r-h))+" "}for(let x=xR;x-dw>=xL2;x-=dw)points+=x+" "+(y2-heights[p++%heights.length])+" ";points+=xL2+" "+y2,container.appendChild(svg.make("polyline",Object.assign({points:points},attrs)))}}const CONNECTING_LINE=new ConnectingLine;class Connect extends BaseComponent{separation({label:label,agentNames:agentNames,options:options},env){const config=env.theme.connect,lArrow=ARROWHEADS[options.left],rArrow=ARROWHEADS[options.right];let labelWidth=env.textSizer.measure(config.label.attrs,label).width;labelWidth>0&&(labelWidth+=2*config.label.padding);const info1=env.agentInfos.get(agentNames[0]);if(agentNames[0]===agentNames[1])env.addSpacing(agentNames[0],{left:0,right:info1.currentMaxRad+Math.max(labelWidth+lArrow.width(env.theme),rArrow.width(env.theme))+config.loopbackRadius});else{const info2=env.agentInfos.get(agentNames[1]);env.addSeparation(agentNames[0],agentNames[1],info1.currentMaxRad+info2.currentMaxRad+labelWidth+2*Math.max(lArrow.width(env.theme),rArrow.width(env.theme)))}}renderSelfConnect({label:label,agentNames:agentNames,options:options},env){const config=env.theme.connect,from=env.agentInfos.get(agentNames[0]),lArrow=ARROWHEADS[options.left],rArrow=ARROWHEADS[options.right],height=label?env.textSizer.measureHeight(config.label.attrs,label)+config.label.margin.top+config.label.margin.bottom:0,lineX=from.x+from.currentMaxRad,y0=env.primaryY,x0=lineX+lArrow.width(env.theme)+(label?config.label.padding:0),clickable=env.makeRegion(),renderedText=SVGShapes.renderBoxedText(label,{x:x0-config.mask.padding.left,y:y0-height+config.label.margin.top,padding:config.mask.padding,boxAttrs:{fill:"#000000"},labelAttrs:config.label.loopbackAttrs,boxLayer:env.maskLayer,labelLayer:clickable,SVGTextBlockClass:env.SVGTextBlockClass}),labelW=label?renderedText.width+config.label.padding-config.mask.padding.left-config.mask.padding.right:0,r=config.loopbackRadius,x1=Math.max(lineX+rArrow.width(env.theme),x0+labelW),y1=y0+2*r,lineAttrs=config.lineAttrs[options.line];CONNECTING_LINE.renderRev(env.shapeLayer,{xL1:lineX+lArrow.lineGap(env.theme,lineAttrs),xL2:lineX+rArrow.lineGap(env.theme,lineAttrs),y1:y0,y2:y1,xR:x1},lineAttrs),lArrow.render(env.shapeLayer,env.theme,{x:lineX,y:y0,dir:1}),rArrow.render(env.shapeLayer,env.theme,{x:lineX,y:y1,dir:1});const raise=Math.max(height,lArrow.height(env.theme)/2),arrowDip=rArrow.height(env.theme)/2;return clickable.insertBefore(svg.make("rect",{x:lineX,y:y0-raise,width:x1+r-lineX,height:raise+2*r+arrowDip,fill:"transparent"}),clickable.firstChild),y1+Math.max(arrowDip+env.theme.minActionMargin,env.theme.actionMargin)}renderSimpleConnect({label:label,agentNames:agentNames,options:options},env){const config=env.theme.connect,from=env.agentInfos.get(agentNames[0]),to=env.agentInfos.get(agentNames[1]),lArrow=ARROWHEADS[options.left],rArrow=ARROWHEADS[options.right],dir=from.x{"use strict";function findExtremes(agentInfos,agentNames){let min=null,max=null;return agentNames.forEach(name=>{const info=agentInfos.get(name);(null===min||info.indexmax.index)&&(max=info)}),{left:min.label,right:max.label}}class NoteComponent extends BaseComponent{renderPre({agentNames:agentNames}){return{agentNames:agentNames}}renderNote({xMid:xMid=null,x0:x0=null,x1:x1=null,anchor:anchor,mode:mode,label:label},env){const config=env.theme.note[mode],clickable=env.makeRegion(),y=env.topY+config.margin.top+config.padding.top,labelNode=new env.SVGTextBlockClass(clickable,{attrs:config.labelAttrs,text:label,y:y}),fullW=labelNode.width+config.padding.left+config.padding.right,fullH=config.padding.top+labelNode.height+config.padding.bottom;switch(null===x0&&null!==xMid&&(x0=xMid-fullW/2),null===x1&&null!==x0?x1=x0+fullW:null===x0&&(x0=x1-fullW),config.labelAttrs["text-anchor"]){case"middle":labelNode.set({x:(x0+config.padding.left+x1-config.padding.right)/2,y:y});break;case"end":labelNode.set({x:x1-config.padding.right,y:y});break;default:labelNode.set({x:x0+config.padding.left,y:y})}return env.shapeLayer.appendChild(config.boxRenderer({x:x0,y:env.topY+config.margin.top,width:x1-x0,height:fullH})),clickable.insertBefore(svg.make("rect",{x:x0,y:env.topY+config.margin.top,width:x1-x0,height:fullH,fill:"transparent"}),clickable.firstChild),env.topY+config.margin.top+fullH+config.margin.bottom+env.theme.actionMargin}}class NoteOver extends NoteComponent{separation({agentNames:agentNames,mode:mode,label:label},env){const config=env.theme.note[mode],width=env.textSizer.measure(config.labelAttrs,label).width+config.padding.left+config.padding.right,{left:left,right:right}=findExtremes(env.agentInfos,agentNames),infoL=env.agentInfos.get(left),infoR=env.agentInfos.get(right);if(infoL!==infoR){const hangL=infoL.currentMaxRad+config.overlap.left,hangR=infoR.currentMaxRad+config.overlap.right;env.addSeparation(left,right,width-hangL-hangR),env.addSpacing(left,{left:hangL,right:0}),env.addSpacing(right,{left:0,right:hangR})}else env.addSpacing(left,{left:width/2,right:width/2})}render({agentNames:agentNames,mode:mode,label:label},env){const config=env.theme.note[mode],{left:left,right:right}=findExtremes(env.agentInfos,agentNames),infoL=env.agentInfos.get(left),infoR=env.agentInfos.get(right);if(infoL!==infoR)return this.renderNote({x0:infoL.x-infoL.currentMaxRad-config.overlap.left,x1:infoR.x+infoR.currentMaxRad+config.overlap.right,anchor:"middle",mode:mode,label:label},env);{const xMid=infoL.x;return this.renderNote({xMid:xMid,anchor:"middle",mode:mode,label:label},env)}}}class NoteSide extends NoteComponent{constructor(isRight){super(),this.isRight=isRight}separation({agentNames:agentNames,mode:mode,label:label},env){const config=env.theme.note[mode],{left:left,right:right}=findExtremes(env.agentInfos,agentNames),width=env.textSizer.measure(config.labelAttrs,label).width+config.padding.left+config.padding.right+config.margin.left+config.margin.right;if(this.isRight){const info=env.agentInfos.get(right);env.addSpacing(right,{left:0,right:width+info.currentMaxRad})}else{const info=env.agentInfos.get(left);env.addSpacing(left,{left:width+info.currentMaxRad,right:0})}}render({agentNames:agentNames,mode:mode,label:label},env){const config=env.theme.note[mode],{left:left,right:right}=findExtremes(env.agentInfos,agentNames);if(this.isRight){const info=env.agentInfos.get(right),x0=info.x+info.currentMaxRad+config.margin.left;return this.renderNote({x0:x0,anchor:"start",mode:mode,label:label},env)}{const info=env.agentInfos.get(left),x1=info.x-info.currentMaxRad-config.margin.right;return this.renderNote({x1:x1,anchor:"end",mode:mode,label:label},env)}}}class NoteBetween extends NoteComponent{separation({agentNames:agentNames,mode:mode,label:label},env){const config=env.theme.note[mode],{left:left,right:right}=findExtremes(env.agentInfos,agentNames),infoL=env.agentInfos.get(left),infoR=env.agentInfos.get(right);env.addSeparation(left,right,env.textSizer.measure(config.labelAttrs,label).width+config.padding.left+config.padding.right+config.margin.left+config.margin.right+infoL.currentMaxRad+infoR.currentMaxRad)}render({agentNames:agentNames,mode:mode,label:label},env){const{left:left,right:right}=findExtremes(env.agentInfos,agentNames),infoL=env.agentInfos.get(left),infoR=env.agentInfos.get(right),xMid=(infoL.x+infoL.currentMaxRad+infoR.x-infoR.currentMaxRad)/2;return this.renderNote({xMid:xMid,anchor:"middle",mode:mode,label:label},env)}}return NoteComponent.NoteOver=NoteOver,NoteComponent.NoteSide=NoteSide,NoteComponent.NoteBetween=NoteBetween,BaseComponent.register("note over",new NoteOver),BaseComponent.register("note left",new NoteSide(!1)),BaseComponent.register("note right",new NoteSide(!0)),BaseComponent.register("note between",new NoteBetween),NoteComponent}),define("sequence/Renderer",["core/ArrayUtilities","core/EventObject","svg/SVGUtilities","svg/SVGShapes","./components/BaseComponent","./components/Block","./components/Parallel","./components/Marker","./components/AgentCap","./components/AgentHighlight","./components/Connect","./components/Note"],(array,EventObject,svg,SVGShapes,BaseComponent)=>{"use strict";function findExtremes(agentInfos,agentNames){let min=null,max=null;return agentNames.forEach(name=>{const info=agentInfos.get(name);(null===min||info.indexmax.index)&&(max=info)}),{left:min.label,right:max.label}}let globalNamespace=0;return class extends EventObject{constructor({themes:themes=[],namespace:namespace=null,components:components=null,SVGTextBlockClass:SVGTextBlockClass=SVGShapes.TextBlock}={}){super(),null===components&&(components=BaseComponent.getComponents()),this.separationStage=this.separationStage.bind(this),this.renderStage=this.renderStage.bind(this),this.addSeparation=this.addSeparation.bind(this),this.addDef=this.addDef.bind(this),this.state={},this.width=0,this.height=0,this.themes=function(themes){if(0===themes.length)throw new Error("Cannot render without a theme");const themeMap=new Map;return themes.forEach(theme=>{themeMap.set(theme.name,theme)}),themeMap.set("",themes[0]),themeMap}(themes),this.theme=null,this.namespace=function(namespace){return null===namespace&&(namespace="R"+globalNamespace,++globalNamespace),namespace}(namespace),this.components=components,this.SVGTextBlockClass=SVGTextBlockClass,this.knownDefs=new Set,this.highlights=new Map,this.currentHighlight=-1,this.buildStaticElements(),this.components.forEach(component=>{component.makeState(this.state)})}addTheme(theme){this.themes.set(theme.name,theme)}buildStaticElements(){this.base=svg.makeContainer(),this.defs=svg.make("defs"),this.mask=svg.make("mask",{id:this.namespace+"LineMask",maskUnits:"userSpaceOnUse"}),this.maskReveal=svg.make("rect",{fill:"#FFFFFF"}),this.agentLines=svg.make("g",{mask:"url(#"+this.namespace+"LineMask)"}),this.blocks=svg.make("g"),this.sections=svg.make("g"),this.actionShapes=svg.make("g"),this.actionLabels=svg.make("g"),this.base.appendChild(this.defs),this.base.appendChild(this.agentLines),this.base.appendChild(this.blocks),this.base.appendChild(this.sections),this.base.appendChild(this.actionShapes),this.base.appendChild(this.actionLabels),this.title=new this.SVGTextBlockClass(this.base),this.sizer=new this.SVGTextBlockClass.SizeTester(this.base)}addDef(name,generator){const namespacedName=this.namespace+name;if(this.knownDefs.has(name))return namespacedName;this.knownDefs.add(name);const def=generator();return def.setAttribute("id",namespacedName),this.defs.appendChild(def),namespacedName}addSeparation(agentName1,agentName2,dist){const info1=this.agentInfos.get(agentName1),info2=this.agentInfos.get(agentName2),d1=info1.separations.get(agentName2)||0;info1.separations.set(agentName2,Math.max(d1,dist));const d2=info2.separations.get(agentName1)||0;info2.separations.set(agentName1,Math.max(d2,dist))}separationStage(stage){const agentSpaces=new Map,agentNames=this.visibleAgents.slice();this.agentInfos.forEach(agentInfo=>{const rad=agentInfo.currentRad;agentInfo.currentMaxRad=rad,agentSpaces.set(agentInfo.label,{left:rad,right:rad})});const env={theme:this.theme,agentInfos:this.agentInfos,visibleAgents:this.visibleAgents,textSizer:this.sizer,addSpacing:(agentName,{left:left,right:right})=>{const current=agentSpaces.get(agentName);current.left=Math.max(current.left,left),current.right=Math.max(current.right,right)},addSeparation:this.addSeparation,components:this.components},component=this.components.get(stage.type);if(!component)throw new Error("Unknown component: "+stage.type);component.separationPre(stage,env),component.separation(stage,env),array.mergeSets(agentNames,this.visibleAgents),agentNames.forEach(agentNameR=>{const infoR=this.agentInfos.get(agentNameR),sepR=agentSpaces.get(agentNameR);infoR.maxRPad=Math.max(infoR.maxRPad,sepR.right),infoR.maxLPad=Math.max(infoR.maxLPad,sepR.left),agentNames.forEach(agentNameL=>{if(this.agentInfos.get(agentNameL).index>=infoR.index)return;const sepL=agentSpaces.get(agentNameL);this.addSeparation(agentNameR,agentNameL,sepR.left+sepL.right+this.theme.agentMargin)})})}checkAgentRange(agentNames,topY=0){if(0===agentNames.length)return topY;const{left:left,right:right}=findExtremes(this.agentInfos,agentNames),leftX=this.agentInfos.get(left).x,rightX=this.agentInfos.get(right).x;let baseY=topY;return this.agentInfos.forEach(agentInfo=>{agentInfo.x>=leftX&&agentInfo.x<=rightX&&(baseY=Math.max(baseY,agentInfo.latestY))}),baseY}markAgentRange(agentNames,y){if(0===agentNames.length)return;const{left:left,right:right}=findExtremes(this.agentInfos,agentNames),leftX=this.agentInfos.get(left).x,rightX=this.agentInfos.get(right).x;this.agentInfos.forEach(agentInfo=>{agentInfo.x>=leftX&&agentInfo.x<=rightX&&(agentInfo.latestY=y)})}drawAgentLine(agentInfo,toY){if(null===agentInfo.latestYStart||toY<=agentInfo.latestYStart)return;const r=agentInfo.currentRad;r>0?this.agentLines.appendChild(svg.make("rect",Object.assign({x:agentInfo.x-r,y:agentInfo.latestYStart,width:2*r,height:toY-agentInfo.latestYStart,class:"agent-"+agentInfo.index+"-line"},this.theme.agentLineAttrs))):this.agentLines.appendChild(svg.make("line",Object.assign({x1:agentInfo.x,y1:agentInfo.latestYStart,x2:agentInfo.x,y2:toY,class:"agent-"+agentInfo.index+"-line"},this.theme.agentLineAttrs)))}addHighlightObject(line,o){let list=this.highlights.get(line);list||(list=[],this.highlights.set(line,list)),list.push(o)}renderStage(stage){this.agentInfos.forEach(agentInfo=>{const rad=agentInfo.currentRad;agentInfo.currentMaxRad=rad});const envPre={theme:this.theme,agentInfos:this.agentInfos,textSizer:this.sizer,state:this.state,components:this.components},component=this.components.get(stage.type),result=component.renderPre(stage,envPre),{topShift:topShift,agentNames:agentNames,asynchronousY:asynchronousY}=BaseComponent.cleanRenderPreResult(result,this.currentY),topY=this.checkAgentRange(agentNames,asynchronousY),env={topY:topY,primaryY:topY+topShift,blockLayer:this.blocks,sectionLayer:this.sections,shapeLayer:this.actionShapes,labelLayer:this.actionLabels,maskLayer:this.mask,theme:this.theme,agentInfos:this.agentInfos,textSizer:this.sizer,SVGTextBlockClass:this.SVGTextBlockClass,state:this.state,drawAgentLine:(agentName,toY,andStop=!1)=>{const agentInfo=this.agentInfos.get(agentName);this.drawAgentLine(agentInfo,toY),agentInfo.latestYStart=andStop?null:toY},addDef:this.addDef,makeRegion:(o,stageOverride=null)=>{o||(o=svg.make("g"));const targetStage=stageOverride||stage;return this.addHighlightObject(targetStage.ln,o),o.setAttribute("class","region"),o.addEventListener("mouseenter",()=>{this.trigger("mouseover",[targetStage])}),o.addEventListener("mouseleave",()=>{this.trigger("mouseout")}),o.addEventListener("click",()=>{this.trigger("click",[targetStage])}),this.actionLabels.appendChild(o),o},components:this.components},bottomY=Math.max(topY,component.render(stage,env)||0);this.markAgentRange(agentNames,bottomY),this.currentY=bottomY}positionAgents(){const orderedInfos=[];this.agentInfos.forEach(agentInfo=>{let currentX=0;agentInfo.separations.forEach((dist,otherAgent)=>{const otherAgentInfo=this.agentInfos.get(otherAgent);otherAgentInfo.index{let currentX=previousInfo.x;previousInfo=agentInfo,agentInfo.anchorRight&&(agentInfo.separations.forEach((dist,otherAgent)=>{const otherAgentInfo=this.agentInfos.get(otherAgent);otherAgentInfo.index>agentInfo.index&&(currentX=Math.min(currentX,otherAgentInfo.x-dist))}),agentInfo.x=currentX)}),this.agentInfos.forEach(({label:label,x:x,maxRPad:maxRPad,maxLPad:maxLPad})=>{this.minX=Math.min(this.minX,x-maxLPad),this.maxX=Math.max(this.maxX,x+maxRPad)})}buildAgentInfos(agents,stages){this.agentInfos=new Map,agents.forEach((agent,index)=>{this.agentInfos.set(agent.name,{label:agent.name,anchorRight:agent.anchorRight,index:index,x:null,latestYStart:null,currentRad:0,currentMaxRad:0,latestY:0,maxRPad:0,maxLPad:0,separations:new Map})}),this.visibleAgents=["[","]"],stages.forEach(this.separationStage),this.positionAgents()}updateBounds(stagesHeight){const cx=(this.minX+this.maxX)/2,titleY=this.title.height>0?-this.theme.titleMargin-this.title.height:0;this.title.set({x:cx,y:titleY});const halfTitleWidth=this.title.width/2,margin=this.theme.outerMargin,x0=Math.min(this.minX,cx-halfTitleWidth)-margin,x1=Math.max(this.maxX,cx+halfTitleWidth)+margin,y0=titleY-margin,y1=stagesHeight+margin;this.maskReveal.setAttribute("x",x0),this.maskReveal.setAttribute("y",y0),this.maskReveal.setAttribute("width",x1-x0),this.maskReveal.setAttribute("height",y1-y0),this.base.setAttribute("viewBox",x0+" "+y0+" "+(x1-x0)+" "+(y1-y0)),this.width=x1-x0,this.height=y1-y0}_reset(){this.knownDefs.clear(),this.highlights.clear(),this.currentHighlight=-1,svg.empty(this.defs),svg.empty(this.mask),svg.empty(this.agentLines),svg.empty(this.blocks),svg.empty(this.sections),svg.empty(this.actionShapes),svg.empty(this.actionLabels),this.mask.appendChild(this.maskReveal),this.defs.appendChild(this.mask),this.components.forEach(component=>{component.resetState(this.state)})}setHighlight(line=null){null!==line&&this.highlights.has(line)||(line=-1),this.currentHighlight!==line&&(-1!==this.currentHighlight&&this.highlights.get(this.currentHighlight).forEach(o=>{o.setAttribute("class","region")}),-1!==line&&this.highlights.get(line).forEach(o=>{o.setAttribute("class","region focus")}),this.currentHighlight=line)}render(sequence){const prevHighlight=this.currentHighlight;this._reset();const themeName=sequence.meta.theme;this.theme=this.themes.get(themeName),this.theme||(this.theme=this.themes.get("")),this.title.set({attrs:this.theme.titleAttrs,text:sequence.meta.title}),this.minX=0,this.maxX=0,this.buildAgentInfos(sequence.agents,sequence.stages),this.currentY=0,sequence.stages.forEach(this.renderStage);const bottomY=this.checkAgentRange(["[","]"],this.currentY),stagesHeight=Math.max(bottomY-this.theme.actionMargin,0);this.updateBounds(stagesHeight),this.sizer.resetCache(),this.sizer.detach(),this.setHighlight(prevHighlight)}getThemeNames(){return Array.from(this.themes.keys()).filter(name=>""!==name)}getThemes(){return this.getThemeNames().map(name=>this.themes.get(name))}getAgentX(name){return this.agentInfos.get(name).x}svg(){return this.base}}}),define("sequence/Exporter",[],()=>{"use strict";const safari=/^((?!chrome|android).)*safari/i.test(navigator.userAgent),firefox=void 0!==window.InstallTrigger;return class{constructor(){this.latestSVG=null,this.latestInternalSVG=null,this.canvas=null,this.context=null,this.indexPNG=0,this.latestPNGIndex=0,this.latestPNG=null}getSVGContent(renderer,size=null){let code=renderer.svg().outerHTML;return firefox&&size&&(code=code.replace(/^{this.canvas.width=width,this.canvas.height=height,this.context.drawImage(img,0,0),safariHackaround&&document.body.removeChild(safariHackaround),this.canvas.toBlob(callback,"image/png")},{once:!0}),img.src=this.getSVGURL(renderer,{width:width,height:height})}getPNGURL(renderer,resolution,callback){++this.indexPNG;const index=this.indexPNG;this.getPNGBlob(renderer,resolution,blob=>{const url=URL.createObjectURL(blob);index>=this.latestPNGIndex?(this.latestPNG&&URL.revokeObjectURL(this.latestPNG),this.latestPNG=url,this.latestPNGIndex=index,callback(url,!0)):(callback(url,!1),URL.revokeObjectURL(url))})}}}),define("sequence/themes/Basic",["core/ArrayUtilities","svg/SVGShapes"],(array,SVGShapes)=>{"use strict";const SETTINGS={titleMargin:10,outerMargin:5,agentMargin:10,actionMargin:10,minActionMargin:3,agentLineHighlightRadius:4,agentCap:{box:{padding:{top:5,left:10,right:10,bottom:5},arrowBottom:12.8,boxAttrs:{fill:"#FFFFFF",stroke:"#000000","stroke-width":1},labelAttrs:{"font-family":"sans-serif","font-size":12,"line-height":1.3,"text-anchor":"middle"}},cross:{size:20,attrs:{fill:"none",stroke:"#000000","stroke-width":1}},bar:{attrs:{fill:"#000000",stroke:"#000000","stroke-width":1,height:4}},fade:{width:5,height:6},none:{height:10}},connect:{loopbackRadius:6,lineAttrs:{solid:{fill:"none",stroke:"#000000","stroke-width":1},dash:{fill:"none",stroke:"#000000","stroke-width":1,"stroke-dasharray":"4, 2"},wave:{fill:"none",stroke:"#000000","stroke-width":1,"stroke-linejoin":"round","stroke-linecap":"round","wave-width":6,"wave-height":.5}},arrow:{single:{width:5,height:10,attrs:{fill:"#000000","stroke-width":0,"stroke-linejoin":"miter"}},double:{width:4,height:6,attrs:{fill:"none",stroke:"#000000","stroke-width":1,"stroke-linejoin":"miter"}}},label:{padding:6,margin:{top:2,bottom:1},attrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3,"text-anchor":"middle"},loopbackAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}},mask:{padding:{top:0,left:3,right:3,bottom:1}}},block:{margin:{top:0,bottom:0},modes:{ref:{boxAttrs:{fill:"#FFFFFF",stroke:"#000000","stroke-width":1.5,rx:2,ry:2}},"":{boxAttrs:{fill:"none",stroke:"#000000","stroke-width":1.5,rx:2,ry:2}}},section:{padding:{top:3,bottom:2},mode:{padding:{top:1,left:3,right:3,bottom:0},boxAttrs:{fill:"#FFFFFF",stroke:"#000000","stroke-width":1,rx:2,ry:2},labelAttrs:{"font-family":"sans-serif","font-weight":"bold","font-size":9,"line-height":1.3,"text-anchor":"left"}},label:{padding:{top:1,left:5,right:3,bottom:0},labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3,"text-anchor":"left"}}},separator:{attrs:{stroke:"#000000","stroke-width":1.5,"stroke-dasharray":"4, 2"}}},note:{text:{margin:{top:0,left:2,right:2,bottom:0},padding:{top:2,left:2,right:2,bottom:2},overlap:{left:10,right:10},boxRenderer:SVGShapes.renderBox.bind(null,{fill:"#FFFFFF"}),labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}},note:{margin:{top:0,left:5,right:5,bottom:0},padding:{top:5,left:5,right:10,bottom:5},overlap:{left:10,right:10},boxRenderer:SVGShapes.renderNote.bind(null,{fill:"#FFFFFF",stroke:"#000000","stroke-width":1},{fill:"none",stroke:"#000000","stroke-width":1}),labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}},state:{margin:{top:0,left:5,right:5,bottom:0},padding:{top:7,left:7,right:7,bottom:7},overlap:{left:10,right:10},boxRenderer:SVGShapes.renderBox.bind(null,{fill:"#FFFFFF",stroke:"#000000","stroke-width":1,rx:10,ry:10}),labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}}},titleAttrs:{"font-family":"sans-serif","font-size":20,"line-height":1.3,"text-anchor":"middle",class:"title"},agentLineAttrs:{fill:"none",stroke:"#000000","stroke-width":1}};return class{constructor(){this.name="basic",Object.assign(this,SETTINGS)}}}),define("sequence/themes/Chunky",["core/ArrayUtilities","svg/SVGShapes"],(array,SVGShapes)=>{"use strict";const SETTINGS={titleMargin:12,outerMargin:5,agentMargin:8,actionMargin:5,minActionMargin:5,agentLineHighlightRadius:4,agentCap:{box:{padding:{top:1,left:3,right:3,bottom:1},arrowBottom:11.1,boxAttrs:{fill:"#FFFFFF",stroke:"#000000","stroke-width":3,rx:4,ry:4},labelAttrs:{"font-family":"sans-serif","font-weight":"bold","font-size":14,"line-height":1.3,"text-anchor":"middle"}},cross:{size:20,attrs:{fill:"none",stroke:"#000000","stroke-width":3,"stroke-linecap":"round"}},bar:{attrs:{fill:"#000000",stroke:"#000000","stroke-width":3,height:4,rx:2,ry:2}},fade:{width:5,height:10},none:{height:10}},connect:{loopbackRadius:8,lineAttrs:{solid:{fill:"none",stroke:"#000000","stroke-width":3},dash:{fill:"none",stroke:"#000000","stroke-width":3,"stroke-dasharray":"10, 4"},wave:{fill:"none",stroke:"#000000","stroke-width":3,"stroke-linejoin":"round","stroke-linecap":"round","wave-width":10,"wave-height":1}},arrow:{single:{width:10,height:12,attrs:{fill:"#000000",stroke:"#000000","stroke-width":3,"stroke-linejoin":"round"}},double:{width:10,height:12,attrs:{fill:"none",stroke:"#000000","stroke-width":3,"stroke-linejoin":"round","stroke-linecap":"round"}}},label:{padding:7,margin:{top:2,bottom:3},attrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3,"text-anchor":"middle"},loopbackAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}},mask:{padding:{top:1,left:5,right:5,bottom:3}}},block:{margin:{top:0,bottom:0},modes:{ref:{boxAttrs:{fill:"#FFFFFF",stroke:"#000000","stroke-width":4,rx:5,ry:5}},"":{boxAttrs:{fill:"none",stroke:"#000000","stroke-width":4,rx:5,ry:5}}},section:{padding:{top:3,bottom:4},mode:{padding:{top:2,left:5,right:5,bottom:1},boxAttrs:{fill:"#FFFFFF",stroke:"#000000","stroke-width":2,rx:3,ry:3},labelAttrs:{"font-family":"sans-serif","font-weight":"bold","font-size":9,"line-height":1.3,"text-anchor":"left"}},label:{padding:{top:2,left:5,right:3,bottom:0},labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3,"text-anchor":"left"}}},separator:{attrs:{stroke:"#000000","stroke-width":2,"stroke-dasharray":"5, 3"}}},note:{text:{margin:{top:0,left:2,right:2,bottom:0},padding:{top:2,left:2,right:2,bottom:2},overlap:{left:10,right:10},boxRenderer:SVGShapes.renderBox.bind(null,{fill:"#FFFFFF"}),labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}},note:{margin:{top:0,left:5,right:5,bottom:0},padding:{top:3,left:3,right:10,bottom:3},overlap:{left:10,right:10},boxRenderer:SVGShapes.renderNote.bind(null,{fill:"#FFFFFF",stroke:"#000000","stroke-width":2,"stroke-linejoin":"round"},{fill:"none",stroke:"#000000","stroke-width":1}),labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}},state:{margin:{top:0,left:5,right:5,bottom:0},padding:{top:5,left:7,right:7,bottom:5},overlap:{left:10,right:10},boxRenderer:SVGShapes.renderBox.bind(null,{fill:"#FFFFFF",stroke:"#000000","stroke-width":3,rx:10,ry:10}),labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}}},titleAttrs:{"font-family":"sans-serif","font-weight":"bolder","font-size":20,"line-height":1.3,"text-anchor":"middle",class:"title"},agentLineAttrs:{fill:"none",stroke:"#000000","stroke-width":3}};return class{constructor(){this.name="chunky",Object.assign(this,SETTINGS)}}}),define("sequence/SequenceDiagram",["core/EventObject","./Parser","./Generator","./Renderer","./Exporter","./themes/Basic","./themes/Chunky"],(EventObject,Parser,Generator,Renderer,Exporter,BasicTheme,ChunkyTheme)=>{"use strict";function registerCodeMirrorMode(CodeMirror,modeName="sequence"){CodeMirror||(CodeMirror=window.CodeMirror),CodeMirror.defineMode(modeName,()=>CMMode),CodeMirror.registerHelper("hint",modeName,CMHints)}function convert(element,code=null,options={}){if("svg"===element.tagName)return null;null===code?code=element.innerText:"object"==typeof code&&(code=(options=code).code);const diagram=new SequenceDiagram(code,options),newElement=diagram.dom();element.parentNode.insertBefore(newElement,element),element.parentNode.removeChild(element);const attrs=element.attributes;for(let i=0;i{this.exporter.getPNGURL(this.renderer,resolution,(url,latest)=>{resolve({url:url,latest:latest})})})}getSize(){return{width:this.renderer.width,height:this.renderer.height}}render(processed=null){const dom=this.renderer.svg(),originalParent=dom.parentNode;document.body.contains(dom)||(originalParent&&originalParent.removeChild(dom),document.body.appendChild(dom));try{processed||(processed=this.process(this.code)),this.renderer.render(processed)}finally{dom.parentNode!==originalParent&&(document.body.removeChild(dom),originalParent&&originalParent.appendChild(dom))}}setContainer(node=null){const dom=this.dom();dom.parentNode&&dom.parentNode.removeChild(dom),node&&node.appendChild(dom)}dom(){return this.renderer.svg()}}return Object.assign(SequenceDiagram,{Parser:Parser,Generator:Generator,Renderer:Renderer,Exporter:Exporter,themes:themes,addTheme:function(theme){themes.push(theme)},registerCodeMirrorMode:registerCodeMirrorMode,convert:convert,convertAll:function(root=null,className="sequence-diagram"){"string"==typeof root&&(className=root,root=null);let elements=null;elements=root&&void 0!==root.length?root:(root||document).getElementsByClassName(className);const els=[];for(let i=0;iconvert(el))}})}),requirejs(["sequence/SequenceDiagram"],SequenceDiagram=>{"use strict";document.addEventListener("DOMContentLoaded",()=>{SequenceDiagram.convertAll()},{once:!0}),window.CodeMirror&&SequenceDiagram.registerCodeMirrorMode(window.CodeMirror),window.SequenceDiagram=SequenceDiagram},null,!0),define("standalone",function(){})}();
\ No newline at end of file
+!function(){var requirejs,require,define;!function(undef){function hasProp(obj,prop){return hasOwn.call(obj,prop)}function normalize(name,baseName){var nameParts,nameSegment,mapValue,foundMap,lastIndex,foundI,foundStarMap,starI,i,j,part,baseParts=baseName&&baseName.split("/"),map=config.map,starMap=map&&map["*"]||{};if(name){for(lastIndex=(name=name.split("/")).length-1,config.nodeIdCompat&&jsSuffixRegExp.test(name[lastIndex])&&(name[lastIndex]=name[lastIndex].replace(jsSuffixRegExp,"")),"."===name[0].charAt(0)&&baseParts&&(name=baseParts.slice(0,baseParts.length-1).concat(name)),i=0;i0&&(name.splice(i-1,2),i-=2)}name=name.join("/")}if((baseParts||starMap)&&map){for(i=(nameParts=name.split("/")).length;i>0;i-=1){if(nameSegment=nameParts.slice(0,i).join("/"),baseParts)for(j=baseParts.length;j>0;j-=1)if((mapValue=map[baseParts.slice(0,j).join("/")])&&(mapValue=mapValue[nameSegment])){foundMap=mapValue,foundI=i;break}if(foundMap)break;!foundStarMap&&starMap&&starMap[nameSegment]&&(foundStarMap=starMap[nameSegment],starI=i)}!foundMap&&foundStarMap&&(foundMap=foundStarMap,foundI=starI),foundMap&&(nameParts.splice(0,foundI,foundMap),name=nameParts.join("/"))}return name}function makeRequire(relName,forceSync){return function(){var args=aps.call(arguments,0);return"string"!=typeof args[0]&&1===args.length&&args.push(null),req.apply(undef,args.concat([relName,forceSync]))}}function makeLoad(depName){return function(value){defined[depName]=value}}function callDep(name){if(hasProp(waiting,name)){var args=waiting[name];delete waiting[name],defining[name]=!0,main.apply(undef,args)}if(!hasProp(defined,name)&&!hasProp(defining,name))throw new Error("No "+name);return defined[name]}function splitPrefix(name){var prefix,index=name?name.indexOf("!"):-1;return index>-1&&(prefix=name.substring(0,index),name=name.substring(index+1,name.length)),[prefix,name]}function makeRelParts(relName){return relName?splitPrefix(relName):[]}var main,req,makeMap,handlers,defined={},waiting={},config={},defining={},hasOwn=Object.prototype.hasOwnProperty,aps=[].slice,jsSuffixRegExp=/\.js$/;makeMap=function(name,relParts){var plugin,parts=splitPrefix(name),prefix=parts[0],relResourceName=relParts[1];return name=parts[1],prefix&&(plugin=callDep(prefix=normalize(prefix,relResourceName))),prefix?name=plugin&&plugin.normalize?plugin.normalize(name,function(relName){return function(name){return normalize(name,relName)}}(relResourceName)):normalize(name,relResourceName):(prefix=(parts=splitPrefix(name=normalize(name,relResourceName)))[0],name=parts[1],prefix&&(plugin=callDep(prefix))),{f:prefix?prefix+"!"+name:name,n:name,pr:prefix,p:plugin}},handlers={require:function(name){return makeRequire(name)},exports:function(name){var e=defined[name];return void 0!==e?e:defined[name]={}},module:function(name){return{id:name,uri:"",exports:defined[name],config:function(name){return function(){return config&&config.config&&config.config[name]||{}}}(name)}}},main=function(name,deps,callback,relName){var cjsModule,depName,ret,map,i,relParts,usingExports,args=[],callbackType=typeof callback;if(relName=relName||name,relParts=makeRelParts(relName),"undefined"===callbackType||"function"===callbackType){for(deps=!deps.length&&callback.length?["require","exports","module"]:deps,i=0;i{"use strict";return class{constructor(){this.listeners=new Map,this.forwards=new Set}addEventListener(type,callback){const l=this.listeners.get(type);l?l.push(callback):this.listeners.set(type,[callback])}removeEventListener(type,fn){const l=this.listeners.get(type);if(!l)return;const i=l.indexOf(fn);-1!==i&&l.splice(i,1)}countEventListeners(type){return(this.listeners.get(type)||[]).length}removeAllEventListeners(type){type?this.listeners.delete(type):this.listeners.clear()}addEventForwarding(target){this.forwards.add(target)}removeEventForwarding(target){this.forwards.delete(target)}removeAllEventForwardings(){this.forwards.clear()}trigger(type,params=[]){(this.listeners.get(type)||[]).forEach(listener=>listener.apply(null,params)),this.forwards.forEach(fwd=>fwd.trigger(type,params))}}}),define("core/ArrayUtilities",[],()=>{"use strict";function indexOf(list,element,equalityCheck=null){if(null===equalityCheck)return list.indexOf(element);for(let i=0;i=parts.length)return void target.push(current.slice());const choices=parts[position];if(!Array.isArray(choices))return current.push(choices),combineRecur(parts,position+1,current,target),void current.pop();for(let i=0;i{result.push(...fn(item))}),result}}}),define("sequence/CodeMirrorMode",["core/ArrayUtilities"],array=>{"use strict";function cmGetSuggestions(state,token,previous,current){return""===token?function(state,previous,current){return"object"==typeof current.suggest&¤t.suggest.global?[current.suggest]:"string"!=typeof current.suggest||previous.suggest===current.suggest?null:state["known"+current.suggest]}(state,previous,current):!0===current.suggest?[function(token,current){return Object.keys(current.then).length>0?token+" ":token+"\n"}(token,current)]:Array.isArray(current.suggest)?current.suggest:current.suggest?[current.suggest]:null}function cmMakeCompletions(state,path){const comp=[],current=array.last(path);return Object.keys(current.then).forEach(token=>{let next=current.then[token];"number"==typeof next&&(next=path[path.length-next-1]),array.mergeSets(comp,cmGetSuggestions(state,token,current,next))}),comp}function updateSuggestion(state,locals,token,{suggest:suggest,override:override}){locals.type&&suggest!==locals.type&&(override&&(locals.type=override),array.mergeSets(state["known"+locals.type],[locals.value+" "]),locals.type="",locals.value=""),"string"==typeof suggest&&state["known"+suggest]&&(locals.type=suggest,locals.value&&(locals.value+=token.s),locals.value+=token.v)}function cmCheckToken(state,eol,commands){const suggestions={type:"",value:""};let current=commands;const path=[current];return state.line.forEach((token,i)=>{i===state.line.length-1&&(state.completions=cmMakeCompletions(state,path));const keywordToken=token.q?"":token.v,found=current.then[keywordToken]||current.then[""];"number"==typeof found?path.length-=found:path.push(found||CM_ERROR),current=array.last(path),updateSuggestion(state,suggestions,token,current)}),eol&&updateSuggestion(state,suggestions,null,{}),state.nextCompletions=cmMakeCompletions(state,path),state.valid=Boolean(current.then["\n"])||0===Object.keys(current.then).length,current.type}function getInitialToken(block){const baseToken=block.baseToken||{};return{value:baseToken.v||"",quoted:baseToken.q||!1}}const CM_ERROR={type:"error line-error",then:{"":0}},makeCommands=(()=>{function textTo(exit){return{type:"string",then:Object.assign({"":0},exit)}}function agentListTo(exit){return{type:"variable",suggest:"Agent",then:Object.assign({},exit,{"":0,",":{type:"operator",suggest:!0,then:{"":1}}})}}function makeSideNote(side){return{type:"keyword",suggest:[side+" of ",side+": "],then:{of:{type:"keyword",suggest:!0,then:{"":agentListToText}},":":{type:"operator",suggest:!0,then:{"":textToEnd}},"":agentListToText}}}function makeOpBlock(exit){const op={type:"operator",suggest:!0,then:{"+":CM_ERROR,"-":CM_ERROR,"*":CM_ERROR,"!":CM_ERROR,"":exit}};return{"+":{type:"operator",suggest:!0,then:{"+":CM_ERROR,"-":CM_ERROR,"*":op,"!":CM_ERROR,"":exit}},"-":{type:"operator",suggest:!0,then:{"+":CM_ERROR,"-":CM_ERROR,"*":op,"!":{type:"operator",then:{"+":CM_ERROR,"-":CM_ERROR,"*":CM_ERROR,"!":CM_ERROR,"":exit}},"":exit}},"*":{type:"operator",suggest:!0,then:{"+":op,"-":op,"*":CM_ERROR,"!":CM_ERROR,"":exit}},"!":op,"":exit}}const end={type:"",suggest:"\n",then:{}},textToEnd=textTo({"\n":end}),aliasListToEnd={type:"variable",suggest:"Agent",then:{"":0,"\n":end,",":{type:"operator",suggest:!0,then:{"":1}},as:{type:"keyword",suggest:!0,then:{"":{type:"variable",suggest:"Agent",then:{"":0,",":{type:"operator",suggest:!0,then:{"":3}},"\n":end}}}}}},agentListToText=agentListTo({":":{type:"operator",suggest:!0,then:{"":textToEnd}}}),agentList2ToText={type:"variable",suggest:"Agent",then:{"":0,",":{type:"operator",suggest:!0,then:{"":agentListToText}},":":CM_ERROR}},singleAgentToText={type:"variable",suggest:"Agent",then:{"":0,",":CM_ERROR,":":{type:"operator",suggest:!0,then:{"":textToEnd}}}},agentToOptText={type:"variable",suggest:"Agent",then:{"":0,":":{type:"operator",suggest:!0,then:{"":textToEnd,"\n":{type:"",then:{}}}},"\n":end}},referenceName={":":{type:"operator",suggest:!0,then:{"":textTo({as:{type:"keyword",suggest:!0,then:{"":{type:"variable",suggest:"Agent",then:{"":0,"\n":end}}}}})}}},refDef={type:"keyword",suggest:!0,then:Object.assign({over:{type:"keyword",suggest:!0,then:{"":agentListTo(referenceName)}}},referenceName)},BASE_THEN={title:{type:"keyword",suggest:!0,then:{"":textToEnd}},theme:{type:"keyword",suggest:!0,then:{"":{type:"string",suggest:{global:"themes",suffix:"\n"},then:{"":0,"\n":end}}}},headers:{type:"keyword",suggest:!0,then:{none:{type:"keyword",suggest:!0,then:{}},cross:{type:"keyword",suggest:!0,then:{}},box:{type:"keyword",suggest:!0,then:{}},fade:{type:"keyword",suggest:!0,then:{}},bar:{type:"keyword",suggest:!0,then:{}}}},terminators:{type:"keyword",suggest:!0,then:{none:{type:"keyword",suggest:!0,then:{}},cross:{type:"keyword",suggest:!0,then:{}},box:{type:"keyword",suggest:!0,then:{}},fade:{type:"keyword",suggest:!0,then:{}},bar:{type:"keyword",suggest:!0,then:{}}}},define:{type:"keyword",suggest:!0,then:{"":aliasListToEnd,as:CM_ERROR}},begin:{type:"keyword",suggest:!0,then:{"":aliasListToEnd,reference:refDef,as:CM_ERROR}},end:{type:"keyword",suggest:!0,then:{"":aliasListToEnd,as:CM_ERROR,"\n":end}},if:{type:"keyword",suggest:!0,then:{"":textToEnd,":":{type:"operator",suggest:!0,then:{"":textToEnd}},"\n":end}},else:{type:"keyword",suggest:["else\n","else if: "],then:{if:{type:"keyword",suggest:"if: ",then:{"":textToEnd,":":{type:"operator",suggest:!0,then:{"":textToEnd}}}},"\n":end}},repeat:{type:"keyword",suggest:!0,then:{"":textToEnd,":":{type:"operator",suggest:!0,then:{"":textToEnd}},"\n":end}},note:{type:"keyword",suggest:!0,then:{over:{type:"keyword",suggest:!0,then:{"":agentListToText}},left:makeSideNote("left"),right:makeSideNote("right"),between:{type:"keyword",suggest:!0,then:{"":agentList2ToText}}}},state:{type:"keyword",suggest:"state over ",then:{over:{type:"keyword",suggest:!0,then:{"":singleAgentToText}}}},text:{type:"keyword",suggest:!0,then:{left:makeSideNote("left"),right:makeSideNote("right")}},autolabel:{type:"keyword",suggest:!0,then:{off:{type:"keyword",suggest:!0,then:{}},"":textToEnd}},simultaneously:{type:"keyword",suggest:!0,then:{":":{type:"operator",suggest:!0,then:{}},with:{type:"keyword",suggest:!0,then:{"":{type:"variable",suggest:"Label",then:{"":0,":":{type:"operator",suggest:!0,then:{}}}}}}}}};return arrows=>({type:"error line-error",then:Object.assign({},BASE_THEN,function(arrows){const connect={type:"keyword",suggest:!0,then:makeOpBlock(agentToOptText)},then={"":0};return arrows.forEach(arrow=>then[arrow]=connect),then[":"]={type:"operator",suggest:!0,override:"Label",then:{}},makeOpBlock({type:"variable",suggest:"Agent",then:then})}(arrows))})})();return class{constructor(tokenDefinitions,arrows){this.tokenDefinitions=tokenDefinitions,this.commands=makeCommands(arrows),this.lineComment="#"}startState(){return{currentType:-1,current:"",currentSpace:"",currentQuoted:!1,knownAgent:[],knownLabel:[],beginCompletions:cmMakeCompletions({},[this.commands]),completions:[],nextCompletions:[],valid:!0,line:[],indent:0}}_matchPattern(stream,pattern,consume){return pattern?(pattern.lastIndex=0,stream.match(pattern,consume)):null}_tokenBegin(stream,state){state.currentSpace="";let lastChar="";for(;;){if(stream.eol())return!1;state.currentSpace+=lastChar;for(let i=0;i{"use strict";function execAt(str,reg,i){return reg.lastIndex=i,reg.exec(str)}function unescape(match){return"n"===match[1]?"\n":match[1]}function tokAdvance(src,i,block){return block?function(src,i,block){if(block.escape){const match=execAt(src,block.escape,i);if(match)return{newBlock:null,end:!1,appendSpace:"",appendValue:block.escapeWith(match),skip:match[0].length}}const match=execAt(src,block.end,i);return match?{newBlock:null,end:!0,appendSpace:"",appendValue:"",skip:match[0].length}:{newBlock:null,end:!1,appendSpace:"",appendValue:src[i],skip:1}}(src,i,block):function(src,i){for(let j=0;j,])/y,end:/(?=[ \t\r\n:+\-~*!<>,])|$/y},{start:/(?=[\-~<>])/y,end:/(?=[^\-~<>])|$/y},{start:/,/y,baseToken:{v:","}},{start:/:/y,baseToken:{v:":"}},{start:/!/y,baseToken:{v:"!"}},{start:/\+/y,baseToken:{v:"+"}},{start:/\*/y,baseToken:{v:"*"}},{start:/\n/y,baseToken:{v:"\n"}}];class TokenState{constructor(src){this.src=src,this.block=null,this.token=null,this.pos={i:0,ln:0,ch:0},this.reset()}isOver(){return this.pos.i>this.src.length}reset(){this.token={s:"",v:"",q:!1,b:null,e:null},this.block=null}beginToken(advance){this.block=advance.newBlock,Object.assign(this.token,this.block.baseToken),this.token.b=copyPos(this.pos)}endToken(){let token=null;return this.block.omit||(this.token.e=copyPos(this.pos),token=this.token),this.reset(),token}advance(){const advance=tokAdvance(this.src,this.pos.i,this.block);return advance.newBlock&&this.beginToken(advance),this.token.s+=advance.appendSpace,this.token.v+=advance.appendValue,function(pos,src,steps){for(let i=0;i{token.q||"\n"!==token.v?line.push(token):line.length>0&&(lines.push(line),line=[])}),line.length>0&&lines.push(line),lines}}}),define("sequence/LabelPatternParser",[],()=>{"use strict";function countDP(value){const match=DP_PATTERN.exec(value);return match&&match[1]?match[1].length:0}function parseToken(token){if("label"===token)return{token:"label"};const p=token.indexOf(" ");let type=null,args=null;return-1===p?(type=token,args=[]):(type=token.substr(0,p),args=token.substr(p+1).split(",")),"inc"===type?function(args){let start=1,inc=1,dp=0;return args[0]&&(start=Number(args[0]),dp=Math.max(dp,countDP(args[0]))),args[1]&&(inc=Number(args[1]),dp=Math.max(dp,countDP(args[1]))),{start:start,inc:inc,dp:dp}}(args):"<"+token+">"}const LABEL_PATTERN=/(.*?)<([^<>]*)>/g,DP_PATTERN=/\.([0-9]*)/;return function(raw){const pattern=[];let match=null,end=0;for(LABEL_PATTERN.lastIndex=0;match=LABEL_PATTERN.exec(raw);)match[1]&&pattern.push(match[1]),match[2]&&pattern.push(parseToken(match[2])),end=LABEL_PATTERN.lastIndex;const remainder=raw.substr(end);return remainder&&pattern.push(remainder),pattern}}),define("sequence/CodeMirrorHints",["core/ArrayUtilities"],array=>{"use strict";function makeHintItem(text,ranges){return{text:text,displayText:"\n"===text?"":text.trim(),className:"\n"===text?"pick-virtual":null,from:SQUASH_START.test(text)?ranges.squashFrom:ranges.wordFrom,to:SQUASH_END.test(text)?ranges.squashTo:ranges.wordTo}}function getGlobals({global:global,prefix:prefix="",suffix:suffix=""},globals){const identified=globals[global];return identified?identified.map(item=>prefix+item+suffix):[]}const TRIMMER=/^([ \t]*)(.*)$/,SQUASH_START=/^[ \t\r\n:,]/,SQUASH_END=/[ \t\r\n]$/;return{getHints:function(cm,options){const cur=cm.getCursor(),token=cm.getTokenAt(cur);let partial=token.string;token.end>cur.ch&&(partial=partial.substr(0,cur.ch-token.start));const parts=TRIMMER.exec(partial);partial=parts[2];const from=token.start+parts[1].length,continuation=cur.ch>0&&token.state.line.length>0;let comp=continuation?token.state.completions:token.state.beginCompletions;continuation||(comp=comp.concat(token.state.knownAgent)),function(suggestions,globals={}){for(let i=0;i0&&" "===ln[chFrom-1]&&ranges.squashFrom.ch--," "===ln[chTo]&&ranges.squashTo.ch++,ranges}(cm,cur.line,from,token.end);let selfValid=!1;const list=comp.filter(opt=>opt.startsWith(partial)).map(opt=>opt!==partial+" "||options.completeSingle?makeHintItem(opt,ranges):(selfValid=!0,null)).filter(opt=>null!==opt);return selfValid&&list.length>0&&list.unshift(makeHintItem(partial+" ",ranges)),{list:list,from:ranges.wordFrom,to:ranges.wordTo}}}}),define("sequence/Parser",["core/ArrayUtilities","./Tokeniser","./LabelPatternParser","./CodeMirrorHints"],(array,Tokeniser,labelPatternParser,CMHints)=>{"use strict";function makeError(message,token=null){let suffix="";return token&&(suffix=" at line "+(token.b.ln+1)+", character "+token.b.ch),new Error(message+suffix)}function joinLabel(line,begin=0,end=null){if(null===end&&(end=line.length),end<=begin)return"";let result=line[begin].v;for(let i=begin+1;i=end)&&(aliasSep=end),start>=aliasSep)throw makeError("Missing agent name",function(line,pos){if(pos{const arrows=array.combine([[{tok:"",type:0},{tok:"<",type:1},{tok:"<<",type:2}],[{tok:"-",type:"solid"},{tok:"--",type:"dash"},{tok:"~",type:"wave"}],[{tok:"",type:0},{tok:">",type:1},{tok:">>",type:2}]]).filter(arrow=>0!==arrow[0].type||0!==arrow[2].type),types=new Map;return arrows.forEach(arrow=>{types.set(arrow.map(part=>part.tok).join(""),{line:arrow[1].type,left:arrow[0].type,right:arrow[2].type})}),types})(),CONNECT_AGENT_FLAGS={"*":"begin","+":"start","-":"stop","!":"end"},TERMINATOR_TYPES=["none","box","cross","fade","bar"],NOTE_TYPES={text:{mode:"text",types:{left:{type:"note left",skip:["of"],min:0,max:null},right:{type:"note right",skip:["of"],min:0,max:null}}},note:{mode:"note",types:{over:{type:"note over",skip:[],min:0,max:null},left:{type:"note left",skip:["of"],min:0,max:null},right:{type:"note right",skip:["of"],min:0,max:null},between:{type:"note between",skip:[],min:2,max:null}}},state:{mode:"state",types:{over:{type:"note over",skip:[],min:1,max:1}}}},AGENT_MANIPULATION_TYPES={define:{type:"agent define"},begin:{type:"agent begin",mode:"box"},end:{type:"agent end",mode:"cross"}},PARSERS=[(line,meta)=>"title"!==tokenKeyword(line[0])?null:(meta.title=joinLabel(line,1),!0),(line,meta)=>"theme"!==tokenKeyword(line[0])?null:(meta.theme=joinLabel(line,1),!0),(line,meta)=>{if("terminators"!==tokenKeyword(line[0]))return null;const type=tokenKeyword(line[1]);if(!type)throw makeError("Unspecified termination",line[0]);if(-1===TERMINATOR_TYPES.indexOf(type))throw makeError('Unknown termination "'+type+'"',line[1]);return meta.terminators=type,!0},(line,meta)=>{if("headers"!==tokenKeyword(line[0]))return null;const type=tokenKeyword(line[1]);if(!type)throw makeError("Unspecified header",line[0]);if(-1===TERMINATOR_TYPES.indexOf(type))throw makeError('Unknown header "'+type+'"',line[1]);return meta.headers=type,!0},line=>{if("autolabel"!==tokenKeyword(line[0]))return null;let raw=null;return raw="off"===tokenKeyword(line[1])?"":joinLabel(line,1),{type:"label pattern",pattern:labelPatternParser(raw)}},line=>{if("end"===tokenKeyword(line[0])&&1===line.length)return{type:"block end"};const type=BLOCK_TYPES[tokenKeyword(line[0])];if(!type)return null;let skip=1;return line.length>skip&&(skip=skipOver(line,skip,type.skip,"Invalid block command")),skip=skipOver(line,skip,[":"]),{type:type.type,mode:type.mode,label:joinLabel(line,skip)}},line=>{if("begin"!==tokenKeyword(line[0])||"reference"!==tokenKeyword(line[1]))return null;let agents=[];const labelSep=findToken(line,":");if("over"===tokenKeyword(line[2])&&labelSep>3)agents=readAgentList(line,3,labelSep);else if(2!==labelSep)throw makeError('Expected ":" or "over"',line[2]);const def=readAgent(line,labelSep+1,line.length,{aliases:!0});if(!def.alias)throw makeError("Reference must have an alias",line[labelSep]);return{type:"group begin",agents:agents,mode:"ref",label:def.name,alias:def.alias}},line=>{const type=AGENT_MANIPULATION_TYPES[tokenKeyword(line[0])];return!type||line.length<=1?null:Object.assign({agents:readAgentList(line,1,line.length,{aliases:!0})},type)},line=>{if("simultaneously"!==tokenKeyword(line[0]))return null;if(":"!==tokenKeyword(array.last(line)))return null;let target="";if(line.length>2){if("with"!==tokenKeyword(line[1]))return null;target=joinLabel(line,2,line.length-1)}return{type:"async",target:target}},line=>{const mode=NOTE_TYPES[tokenKeyword(line[0])],labelSep=findToken(line,":");if(!mode||-1===labelSep)return null;const type=mode.types[tokenKeyword(line[1])];if(!type)return null;let skip=2;const agents=readAgentList(line,skip=skipOver(line,skip,type.skip),labelSep);if(agents.lengthtype.max)throw makeError("Too many agents for "+mode.mode,line[0]);return{type:type.type,agents:agents,mode:mode.mode,label:joinLabel(line,labelSep+1)}},line=>{let labelSep=findToken(line,":");-1===labelSep&&(labelSep=line.length);let typePos=-1,options=null;for(let j=0;j=labelSep-1)return null;const readAgentOpts={flagTypes:CONNECT_AGENT_FLAGS};return{type:"connect",agents:[readAgent(line,0,typePos,readAgentOpts),readAgent(line,typePos+1,labelSep,readAgentOpts)],label:joinLabel(line,labelSep+1),options:options}},line=>line.length<2||":"!==tokenKeyword(array.last(line))?null:{type:"mark",name:joinLabel(line,0,line.length-1)}],SHARED_TOKENISER=new Tokeniser;return class{getCodeMirrorMode(){return SHARED_TOKENISER.getCodeMirrorMode(Array.from(CONNECT_TYPES.keys()))}getCodeMirrorHints(){return CMHints.getHints}parseLines(lines){const result={meta:{title:"",theme:"",terminators:"none",headers:"box"},stages:[]};return lines.forEach(line=>(function(line,{meta:meta,stages:stages}){let stage=null;for(let i=0;i{"use strict";function mergableParallel(target,copy){const info=MERGABLE[target.type];return!(!info||target.type!==copy.type)&&!info.check.some(c=>target[c]!==copy[c])}function performMerge(target,copy){MERGABLE[target.type].merge.forEach(m=>{array.mergeSets(target[m],copy[m])})}function iterateRemoval(list,fn){for(let i=0;i{for(let j=0;jtype);return types.forEach(type=>{const info=MERGABLE[type];info&&types.every(sType=>type===sType||info.siblings.has(sType))&&mergers.add(type)}),mergers}function performSequentialMergers(lastViable,viable,lastStages,stages){iterateRemoval(stages,stage=>{if(!lastViable.has(stage.type)||!viable.has(stage.type))return!1;for(let j=0;j{"agent begin"===subStage.type&&(subStage.mode=mode,any=!0)}),any}return!1}function addBounds(target,agentL,agentR,involvedAgents=null){array.remove(target,agentL,Agent.equals),array.remove(target,agentR,Agent.equals);let indexL=0,indexR=target.length;if(involvedAgents){const found=involvedAgents.map(agent=>array.indexOf(target,agent,Agent.equals)).filter(p=>-1!==p);indexL=found.reduce((a,b)=>Math.min(a,b),target.length),indexR=found.reduce((a,b)=>Math.max(a,b),indexL)+1}return target.splice(indexL,0,agentL),target.splice(indexR+1,0,agentR),{indexL:indexL,indexR:indexR+1}}class AgentState{constructor({visible:visible=!1,locked:locked=!1,blocked:blocked=!1,highlighted:highlighted=!1,group:group=null,covered:covered=!1}={}){this.visible=visible,this.locked=locked,this.blocked=blocked,this.highlighted=highlighted,this.group=group,this.covered=covered}}AgentState.LOCKED=new AgentState({locked:!0}),AgentState.DEFAULT=new AgentState;const Agent={equals:(a,b)=>a.name===b.name,make:(name,{anchorRight:anchorRight=!1}={})=>({name:name,anchorRight:anchorRight}),getName:agent=>agent.name,hasFlag:(flag,has=!0)=>agent=>agent.flags.includes(flag)===has},MERGABLE={"agent begin":{check:["mode"],merge:["agentNames"],siblings:new Set(["agent highlight"])},"agent end":{check:["mode"],merge:["agentNames"],siblings:new Set(["agent highlight"])},"agent highlight":{check:["highlighted"],merge:["agentNames"],siblings:new Set(["agent begin","agent end"])}},NOTE_DEFAULT_AGENTS={"note over":[{name:"[",flags:[]},{name:"]",flags:[]}],"note left":[{name:"[",flags:[]}],"note right":[{name:"]",flags:[]}]};return class{constructor(){this.agentStates=new Map,this.agentAliases=new Map,this.activeGroups=new Map,this.agents=[],this.labelPattern=null,this.blockCount=0,this.nesting=[],this.markers=new Set,this.currentSection=null,this.currentNest=null,this.stageHandlers={"block begin":this.handleBlockBegin.bind(this),"block split":this.handleBlockSplit.bind(this),"block end":this.handleBlockEnd.bind(this),"group begin":this.handleGroupBegin.bind(this),mark:this.handleMark.bind(this),async:this.handleAsync.bind(this),"agent define":this.handleAgentDefine.bind(this),"agent begin":this.handleAgentBegin.bind(this),"agent end":this.handleAgentEnd.bind(this),"label pattern":this.handleLabelPattern.bind(this),connect:this.handleConnect.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)},this.expandGroupedAgent=this.expandGroupedAgent.bind(this),this.handleStage=this.handleStage.bind(this),this.convertAgent=this.convertAgent.bind(this),this.endGroup=this.endGroup.bind(this)}convertAgent({alias:alias,name:name}){if(alias){if(this.agentAliases.has(name))throw new Error("Cannot alias "+name+"; it is already an alias");const old=this.agentAliases.get(alias);if(old&&old!==alias||this.agents.some(agent=>agent.name===alias))throw new Error("Cannot use "+alias+" as an alias; it is already in use");this.agentAliases.set(alias,name)}return Agent.make(this.agentAliases.get(name)||name)}addStage(stage,isVisible=!0){stage&&(void 0===stage.ln&&(stage.ln=this.latestLine),this.currentSection.stages.push(stage),isVisible&&(this.currentNest.hasContent=!0))}addParallelStages(stages){const viableStages=stages.filter(stage=>Boolean(stage));if(0!==viableStages.length)return 1===viableStages.length?this.addStage(viableStages[0]):(viableStages.forEach(stage=>{void 0===stage.ln&&(stage.ln=this.latestLine)}),this.addStage({type:"parallel",stages:viableStages}))}defineAgents(colAgents){array.mergeSets(this.currentNest.agents,colAgents,Agent.equals),array.mergeSets(this.agents,colAgents,Agent.equals)}getAgentState(agent){return this.agentStates.get(agent.name)||AgentState.DEFAULT}updateAgentState(agent,change){const state=this.agentStates.get(agent.name);state?Object.assign(state,change):this.agentStates.set(agent.name,new AgentState(change))}validateAgents(agents,{allowGrouped:allowGrouped=!1,rejectGrouped:rejectGrouped=!1}={}){agents.forEach(agent=>{const state=this.getAgentState(agent);if(state.covered)throw new Error("Agent "+agent.name+" is hidden behind group");if(rejectGrouped&&null!==state.group)throw new Error("Agent "+agent.name+" is in a group");if(state.blocked&&(!allowGrouped||null===state.group))throw new Error("Duplicate agent name: "+agent.name);if(agent.name.startsWith("__"))throw new Error(agent.name+" is a reserved name")})}setAgentVis(colAgents,visible,mode,checked=!1){const seen=new Set,filteredAgents=colAgents.filter(agent=>{if(seen.has(agent.name))return!1;seen.add(agent.name);const state=this.getAgentState(agent);if(state.locked||state.blocked){if(checked)throw new Error("Cannot begin/end agent: "+agent.name);return!1}return state.visible!==visible});return 0===filteredAgents.length?null:(filteredAgents.forEach(agent=>{this.updateAgentState(agent,{visible:visible})}),this.defineAgents(filteredAgents),{type:visible?"agent begin":"agent end",agentNames:filteredAgents.map(Agent.getName),mode:mode})}setAgentHighlight(colAgents,highlighted,checked=!1){const filteredAgents=colAgents.filter(agent=>{const state=this.getAgentState(agent);if(state.locked||state.blocked){if(checked)throw new Error("Cannot highlight agent: "+agent.name);return!1}return state.visible&&state.highlighted!==highlighted});return 0===filteredAgents.length?null:(filteredAgents.forEach(agent=>{this.updateAgentState(agent,{highlighted:highlighted})}),{type:"agent highlight",agentNames:filteredAgents.map(Agent.getName),highlighted:highlighted})}beginNested(mode,label,name,ln){const leftAgent=Agent.make(name+"[",{anchorRight:!0}),rightAgent=Agent.make(name+"]"),agents=[leftAgent,rightAgent],stages=[];return this.currentSection={header:{type:"block begin",mode:mode,label:label,left:leftAgent.name,right:rightAgent.name,ln:ln},stages:stages},this.currentNest={mode:mode,agents:agents,leftAgent:leftAgent,rightAgent:rightAgent,hasContent:!1,sections:[this.currentSection]},this.agentStates.set(leftAgent.name,AgentState.LOCKED),this.agentStates.set(rightAgent.name,AgentState.LOCKED),this.nesting.push(this.currentNest),{agents:agents,stages:stages}}nextBlockName(){const name="__BLOCK"+this.blockCount;return++this.blockCount,name}handleBlockBegin({ln:ln,mode:mode,label:label}){this.beginNested(mode,label,this.nextBlockName(),ln)}handleBlockSplit({ln:ln,mode:mode,label:label}){if("if"!==this.currentNest.mode)throw new Error('Invalid block nesting ("else" inside '+this.currentNest.mode+")");optimiseStages(this.currentSection.stages),this.currentSection={header:{type:"block split",mode:mode,label:label,left:this.currentNest.leftAgent.name,right:this.currentNest.rightAgent.name,ln:ln},stages:[]},this.currentNest.sections.push(this.currentSection)}handleBlockEnd(){if(this.nesting.length<=1)throw new Error('Invalid block nesting (too many "end"s)');optimiseStages(this.currentSection.stages);const nested=this.nesting.pop();if(this.currentNest=array.last(this.nesting),this.currentSection=array.last(this.currentNest.sections),!nested.hasContent)throw new Error("Empty block");this.defineAgents(nested.agents),addBounds(this.agents,nested.leftAgent,nested.rightAgent,nested.agents),nested.sections.forEach(section=>{this.currentSection.stages.push(section.header),this.currentSection.stages.push(...section.stages)}),this.addStage({type:"block end",left:nested.leftAgent.name,right:nested.rightAgent.name})}makeGroupDetails(agents,alias){const colAgents=agents.map(this.convertAgent);if(this.validateAgents(colAgents,{rejectGrouped:!0}),this.agentStates.has(alias))throw new Error("Duplicate agent name: "+alias);const name=this.nextBlockName(),leftAgent=Agent.make(name+"[",{anchorRight:!0}),rightAgent=Agent.make(name+"]");this.agentStates.set(leftAgent.name,AgentState.LOCKED),this.agentStates.set(rightAgent.name,AgentState.LOCKED),this.updateAgentState({name:alias},{blocked:!0,group:alias}),this.defineAgents(colAgents);const{indexL:indexL,indexR:indexR}=addBounds(this.agents,leftAgent,rightAgent,colAgents),agentsCovered=[],agentsContained=colAgents.slice();for(let i=indexL+1;i{this.updateAgentState(agent,{group:alias})}),details.agentsCovered.forEach(agent=>{this.updateAgentState(agent,{covered:!0})}),this.activeGroups.set(alias,details),this.addStage(this.setAgentVis(details.colAgents,!0,"box")),this.addStage({type:"block begin",mode:mode,label:label,left:details.leftAgent.name,right:details.rightAgent.name})}endGroup({name:name}){const details=this.activeGroups.get(name);return details?(this.activeGroups.delete(name),details.agentsContained.forEach(agent=>{this.updateAgentState(agent,{group:null})}),details.agentsCovered.forEach(agent=>{this.updateAgentState(agent,{covered:!1})}),this.updateAgentState({name:name},{group:null}),{type:"block end",left:details.leftAgent.name,right:details.rightAgent.name}):null}handleMark({name:name}){this.markers.add(name),this.addStage({type:"mark",name:name},!1)}handleAsync({target:target}){if(""!==target&&!this.markers.has(target))throw new Error("Unknown marker: "+target);this.addStage({type:"async",target:target},!1)}handleLabelPattern({pattern:pattern}){this.labelPattern=pattern.slice();for(let i=0;i{"string"==typeof part?result+=part:void 0!==part.token?result+=tokens[part.token]:void 0!==part.current&&(result+=part.current.toFixed(part.dp),part.current+=part.inc)}),result}expandGroupedAgent(agent){const group=this.getAgentState(agent).group;if(!group)return[agent];const details=this.activeGroups.get(group);return[details.leftAgent,details.rightAgent]}expandGroupedAgentConnection(agents){const agents1=this.expandGroupedAgent(agents[0]),agents2=this.expandGroupedAgent(agents[1]);let ind1=array.indexOf(this.agents,agents1[0],Agent.equals),ind2=array.indexOf(this.agents,agents2[0],Agent.equals);return-1===ind1&&(ind1=this.agents.length),-1===ind2&&(ind2=this.agents.length),ind1===ind2?[array.last(agents1),array.last(agents2)]:ind1this.activeGroups.has(agent.name)),colAgents=agents.filter(agent=>!this.activeGroups.has(agent.name)).map(this.convertAgent);this.validateAgents(colAgents),this.addParallelStages([this.setAgentHighlight(colAgents,!1),this.setAgentVis(colAgents,!1,mode,!0),...groupAgents.map(this.endGroup)])}handleStage(stage){this.latestLine=stage.ln;try{const handler=this.stageHandlers[stage.type];if(!handler)throw new Error("Unknown command: "+stage.type);handler(stage)}catch(e){if("object"==typeof e&&e.message)throw new Error(e.message+" at line "+(stage.ln+1))}}generate({stages:stages,meta:meta={}}){this.agentStates.clear(),this.markers.clear(),this.agentAliases.clear(),this.activeGroups.clear(),this.agents.length=0,this.blockCount=0,this.nesting.length=0,this.labelPattern=[{token:"label"}];const globals=this.beginNested("global","","",0);if(stages.forEach(this.handleStage),1!==this.nesting.length)throw new Error("Unterminated section at line "+(this.currentSection.header.ln+1));if(this.activeGroups.size>0)throw new Error("Unterminated group");const terminators=meta.terminators||"none";return this.addParallelStages([this.setAgentHighlight(this.agents,!1),this.setAgentVis(this.agents,!1,terminators)]),addBounds(this.agents,this.currentNest.leftAgent,this.currentNest.rightAgent),optimiseStages(globals.stages),function(stages,mode){for(let i=0;i{"use strict";function make(type,attrs={}){const o=document.createElementNS(NS,type);for(let k in attrs)attrs.hasOwnProperty(k)&&o.setAttribute(k,attrs[k]);return o}const NS="http://www.w3.org/2000/svg";return{makeText:function(text=""){return document.createTextNode(text)},make:make,makeContainer:function(attrs={}){return make("svg",Object.assign({xmlns:NS,version:"1.1"},attrs))},empty:function(node){for(;node.childNodes.length>0;)node.removeChild(node.lastChild)}}}),define("svg/SVGTextBlock",["./SVGUtilities"],svg=>{"use strict";function fontDetails(attrs){const size=Number(attrs["font-size"]);return{size:size,lineHeight:size*(Number(attrs["line-height"])||1)}}const firefox=void 0!==window.InstallTrigger;class SVGTextBlock{constructor(container,initialState={}){this.container=container,this.state={attrs:{},text:"",x:0,y:0},this.width=0,this.height=0,this.nodes=[],this.set(initialState)}_rebuildNodes(count){if(count>this.nodes.length){const attrs=Object.assign({x:this.state.x},this.state.attrs);for(;this.nodes.lengthcount;){const{element:element}=this.nodes.pop();this.container.removeChild(element)}}_reset(){this._rebuildNodes(0),this.width=0,this.height=0}_renderText(){if(!this.state.text)return void this._reset();const lines=this.state.text.split("\n");this._rebuildNodes(lines.length);let maxWidth=0;this.nodes.forEach(({text:text,element:element},i)=>{text.nodeValue!==lines[i]&&(text.nodeValue=lines[i]),maxWidth=Math.max(maxWidth,element.getComputedTextLength())}),this.width=maxWidth}_updateX(){this.nodes.forEach(({element:element})=>{element.setAttribute("x",this.state.x)})}_updateY(){const{size:size,lineHeight:lineHeight}=fontDetails(this.state.attrs);this.nodes.forEach(({element:element},i)=>{element.setAttribute("y",this.state.y+i*lineHeight+size)}),this.height=lineHeight*this.nodes.length}firstLine(){return this.nodes.length>0?this.nodes[0].element:null}set(newState){const oldState=Object.assign({},this.state);!function(state,newState){for(let k in state)state.hasOwnProperty(k)&&null!==newState[k]&&void 0!==newState[k]&&(state[k]=newState[k])}(this.state,newState),this.state.attrs!==oldState.attrs&&(this._reset(),oldState.text="");const oldNodes=this.nodes.length;this.state.text!==oldState.text&&this._renderText(),this.state.x!==oldState.x&&this._updateX(),this.state.y===oldState.y&&this.nodes.length===oldNodes||this._updateY()}}class SizeTester{constructor(container){this.testers=svg.make("g",{display:firefox?"block":"none",visibility:"hidden"}),this.container=container,this.cache=new Map}measure(attrs,content){if(!content)return{width:0,height:0};let tester=this.cache.get(attrs);if(!tester){const text=svg.makeText(),node=svg.make("text",attrs);node.appendChild(text),this.testers.appendChild(node),tester={text:text,node:node},this.cache.set(attrs,tester)}this.testers.parentNode||this.container.appendChild(this.testers);const lines=content.split("\n");let width=0;return lines.forEach(line=>{tester.text.nodeValue=line,width=Math.max(width,tester.node.getComputedTextLength())}),{width:width,height:lines.length*fontDetails(attrs).lineHeight}}measureHeight(attrs,content){if(!content)return 0;return content.split("\n").length*fontDetails(attrs).lineHeight}resetCache(){svg.empty(this.testers),this.cache.clear()}detach(){this.testers.parentNode&&this.container.removeChild(this.testers)}}return SVGTextBlock.SizeTester=SizeTester,SVGTextBlock}),define("svg/SVGShapes",["./SVGUtilities","./SVGTextBlock"],(svg,SVGTextBlock)=>{"use strict";function renderBox(attrs,position){return svg.make("rect",Object.assign({},position,attrs))}return{renderBox:renderBox,renderNote:function(attrs,flickAttrs,position){const g=svg.make("g"),x0=position.x,x1=position.x+position.width,y0=position.y,y1=position.y+position.height;return g.appendChild(svg.make("polygon",Object.assign({points:x0+" "+y0+" "+(x1-7)+" "+y0+" "+x1+" "+(y0+7)+" "+x1+" "+y1+" "+x0+" "+y1},attrs))),g.appendChild(svg.make("polyline",Object.assign({points:x1-7+" "+y0+" "+(x1-7)+" "+(y0+7)+" "+x1+" "+(y0+7)},flickAttrs))),g},renderBoxedText:function(text,{x:x,y:y,padding:padding,boxAttrs:boxAttrs,labelAttrs:labelAttrs,boxLayer:boxLayer,labelLayer:labelLayer,boxRenderer:boxRenderer=null,SVGTextBlockClass:SVGTextBlockClass=SVGTextBlock}){if(!text)return{width:0,height:0,label:null,box:null};let shift=0,anchorX=x;switch(labelAttrs["text-anchor"]){case"middle":shift=.5,anchorX+=(padding.left-padding.right)/2;break;case"end":shift=1,anchorX-=padding.right;break;default:shift=0,anchorX+=padding.left}const label=new SVGTextBlockClass(labelLayer,{attrs:labelAttrs,text:text,x:anchorX,y:y+padding.top}),width=label.width+padding.left+padding.right,height=label.height+padding.top+padding.bottom;let box=null;return box=boxRenderer?boxRenderer({x:anchorX-label.width*shift-padding.left,y:y,width:width,height:height}):renderBox(boxAttrs,{x:anchorX-label.width*shift-padding.left,y:y,width:width,height:height}),boxLayer===labelLayer?boxLayer.insertBefore(box,label.firstLine()):boxLayer.appendChild(box),{width:width,height:height,label:label,box:box}},TextBlock:SVGTextBlock}}),define("sequence/components/BaseComponent",[],()=>{"use strict";class BaseComponent{makeState(){}resetState(state){this.makeState(state)}separationPre(){}separation(){}renderPre(){}render(){}}BaseComponent.cleanRenderPreResult=(({topShift:topShift=0,agentNames:agentNames=[],asynchronousY:asynchronousY=null}={},currentY=null)=>({topShift:topShift,agentNames:agentNames,asynchronousY:null!==asynchronousY?asynchronousY:currentY}));const components=new Map;return BaseComponent.register=((name,component)=>{components.set(name,component)}),BaseComponent.getComponents=(()=>components),BaseComponent}),define("sequence/components/Block",["./BaseComponent","core/ArrayUtilities","svg/SVGUtilities","svg/SVGShapes"],(BaseComponent,array,svg,SVGShapes)=>{"use strict";class BlockSplit extends BaseComponent{separation({left:left,right:right,mode:mode,label:label},env){const config=env.theme.block.section,width=env.textSizer.measure(config.mode.labelAttrs,mode).width+config.mode.padding.left+config.mode.padding.right+env.textSizer.measure(config.label.labelAttrs,label).width+config.label.padding.left+config.label.padding.right;env.addSeparation(left,right,width)}renderPre({left:left,right:right}){return{agentNames:[left,right]}}render({left:left,right:right,mode:mode,label:label},env,first=!1){const config=env.theme.block,agentInfoL=env.agentInfos.get(left),agentInfoR=env.agentInfos.get(right);let y=env.primaryY;first||(y+=config.section.padding.bottom,env.sectionLayer.appendChild(svg.make("line",Object.assign({x1:agentInfoL.x,y1:y,x2:agentInfoR.x,y2:y},config.separator.attrs))));const modeRender=SVGShapes.renderBoxedText(mode,{x:agentInfoL.x,y:y,padding:config.section.mode.padding,boxAttrs:config.section.mode.boxAttrs,labelAttrs:config.section.mode.labelAttrs,boxLayer:env.blockLayer,labelLayer:env.labelLayer,SVGTextBlockClass:env.SVGTextBlockClass}),labelRender=SVGShapes.renderBoxedText(label,{x:agentInfoL.x+modeRender.width,y:y,padding:config.section.label.padding,boxAttrs:{fill:"#000000"},labelAttrs:config.section.label.labelAttrs,boxLayer:env.maskLayer,labelLayer:env.labelLayer,SVGTextBlockClass:env.SVGTextBlockClass});return y+(Math.max(modeRender.height,labelRender.height)+config.section.padding.top)}}class BlockBegin extends BlockSplit{makeState(state){state.blocks=new Map}resetState(state){state.blocks.clear()}separation(stage,env){array.mergeSets(env.visibleAgents,[stage.left,stage.right]),super.separation(stage,env)}renderPre({left:left,right:right},env){return{agentNames:[left,right],topShift:env.theme.block.margin.top}}render(stage,env){return env.state.blocks.set(stage.left,{mode:stage.mode,startY:env.primaryY}),super.render(stage,env,!0)}}class BlockEnd extends BaseComponent{separation({left:left,right:right},env){array.removeAll(env.visibleAgents,[left,right])}renderPre({left:left,right:right},env){return{agentNames:[left,right],topShift:env.theme.block.section.padding.bottom}}render({left:left,right:right},env){const config=env.theme.block,{startY:startY,mode:mode}=env.state.blocks.get(left),agentInfoL=env.agentInfos.get(left),agentInfoR=env.agentInfos.get(right),configMode=config.modes[mode]||config.modes[""];return env.blockLayer.appendChild(svg.make("rect",Object.assign({x:agentInfoL.x,y:startY,width:agentInfoR.x-agentInfoL.x,height:env.primaryY-startY},configMode.boxAttrs))),env.primaryY+config.margin.bottom+env.theme.actionMargin}}return BaseComponent.register("block begin",new BlockBegin),BaseComponent.register("block split",new BlockSplit),BaseComponent.register("block end",new BlockEnd),{BlockBegin:BlockBegin,BlockSplit:BlockSplit,BlockEnd:BlockEnd}}),define("sequence/components/Parallel",["./BaseComponent","core/ArrayUtilities"],(BaseComponent,array)=>{"use strict";function mergeResults(a,b){return array.mergeSets(a.agentNames,b.agentNames),{topShift:Math.max(a.topShift,b.topShift),agentNames:a.agentNames,asynchronousY:function(a=null,b=null){return null===a?b:null===b?a:Math.max(a,b)}(a.asynchronousY,b.asynchronousY)}}class Parallel extends BaseComponent{separationPre(stage,env){stage.stages.forEach(subStage=>{env.components.get(subStage.type).separationPre(subStage,env)})}separation(stage,env){stage.stages.forEach(subStage=>{env.components.get(subStage.type).separation(subStage,env)})}renderPre(stage,env){return stage.stages.map(subStage=>{const subResult=env.components.get(subStage.type).renderPre(subStage,env);return BaseComponent.cleanRenderPreResult(subResult)}).reduce(mergeResults,{topShift:0,agentNames:[],asynchronousY:null})}render(stage,env){const originalMakeRegion=env.makeRegion;let bottomY=0;return stage.stages.forEach(subStage=>{env.makeRegion=((o,stageOverride=null)=>originalMakeRegion(o,stageOverride||subStage));const baseY=env.components.get(subStage.type).render(subStage,env)||0;bottomY=Math.max(bottomY,baseY)}),env.makeRegion=originalMakeRegion,bottomY}}return BaseComponent.register("parallel",new Parallel),Parallel}),define("sequence/components/Marker",["./BaseComponent"],BaseComponent=>{"use strict";class Mark extends BaseComponent{makeState(state){state.marks=new Map}resetState(state){state.marks.clear()}render({name:name},{topY:topY,state:state}){state.marks.set(name,topY)}}class Async extends BaseComponent{renderPre({target:target},{state:state}){let y=0;return target&&state.marks&&(y=state.marks.get(target)||0),{asynchronousY:y}}}return BaseComponent.register("mark",new Mark),BaseComponent.register("async",new Async),{Mark:Mark,Async:Async}}),define("sequence/components/AgentCap",["./BaseComponent","core/ArrayUtilities","svg/SVGUtilities","svg/SVGShapes"],(BaseComponent,array,svg,SVGShapes)=>{"use strict";class CapBox{separation({label:label},env){const config=env.theme.agentCap.box,width=env.textSizer.measure(config.labelAttrs,label).width+config.padding.left+config.padding.right;return{left:width/2,right:width/2,radius:width/2}}topShift({label:label},env){const config=env.theme.agentCap.box,height=env.textSizer.measureHeight(config.labelAttrs,label)+config.padding.top+config.padding.bottom;return Math.max(0,height-config.arrowBottom)}render(y,{x:x,label:label},env){const config=env.theme.agentCap.box,clickable=env.makeRegion(),{width:width,height:height}=SVGShapes.renderBoxedText(label,{x:x,y:y,padding:config.padding,boxAttrs:config.boxAttrs,labelAttrs:config.labelAttrs,boxLayer:env.shapeLayer,labelLayer:clickable,SVGTextBlockClass:env.SVGTextBlockClass});return clickable.insertBefore(svg.make("rect",{x:x-width/2,y:y,width:width,height:height,fill:"transparent"}),clickable.firstChild),{lineTop:0,lineBottom:height,height:height}}}class CapCross{separation(agentInfo,env){const config=env.theme.agentCap.cross;return{left:config.size/2,right:config.size/2,radius:0}}topShift(agentInfo,env){return env.theme.agentCap.cross.size/2}render(y,{x:x},env){const config=env.theme.agentCap.cross,d=config.size/2;return env.shapeLayer.appendChild(svg.make("path",Object.assign({d:"M "+(x-d)+" "+y+" L "+(x+d)+" "+(y+2*d)+" M "+(x+d)+" "+y+" L "+(x-d)+" "+(y+2*d)},config.attrs))),env.makeRegion().appendChild(svg.make("rect",{x:x-d,y:y,width:2*d,height:2*d,fill:"transparent"})),{lineTop:d,lineBottom:d,height:2*d}}}class CapBar{separation({label:label},env){const config=env.theme.agentCap.box,width=env.textSizer.measure(config.labelAttrs,label).width+config.padding.left+config.padding.right;return{left:width/2,right:width/2,radius:width/2}}topShift(agentInfo,env){return env.theme.agentCap.bar.attrs.height/2}render(y,{x:x,label:label},env){const configB=env.theme.agentCap.box,config=env.theme.agentCap.bar,width=env.textSizer.measure(configB.labelAttrs,label).width+configB.padding.left+configB.padding.right;return env.shapeLayer.appendChild(svg.make("rect",Object.assign({x:x-width/2,y:y,width:width},config.attrs))),env.makeRegion().appendChild(svg.make("rect",{x:x-width/2,y:y,width:width,height:config.attrs.height,fill:"transparent"})),{lineTop:0,lineBottom:config.attrs.height,height:config.attrs.height}}}class CapFade{separation({currentRad:currentRad}){return{left:currentRad,right:currentRad,radius:currentRad}}topShift(agentInfo,env,isBegin){const config=env.theme.agentCap.fade;return isBegin?config.height:0}render(y,{x:x,label:label},env,isBegin){const config=env.theme.agentCap.fade,gradID=env.addDef(isBegin?"FadeIn":"FadeOut",()=>{const grad=svg.make("linearGradient",{x1:"0%",y1:isBegin?"100%":"0%",x2:"0%",y2:isBegin?"0%":"100%"});return grad.appendChild(svg.make("stop",{offset:100/12+"%","stop-color":"#FFFFFF"})),grad.appendChild(svg.make("stop",{offset:1100/12+"%","stop-color":"#000000"})),grad});return env.maskLayer.appendChild(svg.make("rect",{x:x-config.width/2,y:y-.1*config.height,width:config.width,height:1.2*config.height,fill:"url(#"+gradID+")"})),env.makeRegion().appendChild(svg.make("rect",{x:x-config.width/2,y:y,width:config.width,height:config.height,fill:"transparent"})),{lineTop:config.height,lineBottom:0,height:config.height}}}class CapNone{separation({currentRad:currentRad}){return{left:currentRad,right:currentRad,radius:currentRad}}topShift(agentInfo,env){return env.theme.agentCap.none.height}render(y,{x:x},env){const config=env.theme.agentCap.none;return env.makeRegion().appendChild(svg.make("rect",{x:x-5,y:y,width:10,height:config.height,fill:"transparent"})),{lineTop:config.height,lineBottom:0,height:config.height}}}const AGENT_CAPS={box:new CapBox,cross:new CapCross,bar:new CapBar,fade:new CapFade,none:new CapNone};class AgentCap extends BaseComponent{constructor(begin){super(),this.begin=begin}separationPre({mode:mode,agentNames:agentNames},env){agentNames.forEach(name=>{const agentInfo=env.agentInfos.get(name),sep=AGENT_CAPS[mode].separation(agentInfo,env,this.begin);env.addSpacing(name,sep),agentInfo.currentMaxRad=Math.max(agentInfo.currentMaxRad,sep.radius)})}separation({mode:mode,agentNames:agentNames},env){this.begin?array.mergeSets(env.visibleAgents,agentNames):array.removeAll(env.visibleAgents,agentNames)}renderPre({mode:mode,agentNames:agentNames},env){let maxTopShift=0;return agentNames.forEach(name=>{const agentInfo=env.agentInfos.get(name),cap=AGENT_CAPS[mode],topShift=cap.topShift(agentInfo,env,this.begin);maxTopShift=Math.max(maxTopShift,topShift);const r=cap.separation(agentInfo,env,this.begin).radius;agentInfo.currentMaxRad=Math.max(agentInfo.currentMaxRad,r)}),{agentNames:agentNames,topShift:maxTopShift}}render({mode:mode,agentNames:agentNames},env){let maxEnd=0;return agentNames.forEach(name=>{const agentInfo=env.agentInfos.get(name),cap=AGENT_CAPS[mode],topShift=cap.topShift(agentInfo,env,this.begin),y0=env.primaryY-topShift,shifts=cap.render(y0,agentInfo,env,this.begin);maxEnd=Math.max(maxEnd,y0+shifts.height),this.begin?env.drawAgentLine(name,y0+shifts.lineBottom):env.drawAgentLine(name,y0+shifts.lineTop,!0)}),maxEnd+env.theme.actionMargin}}return BaseComponent.register("agent begin",new AgentCap(!0)),BaseComponent.register("agent end",new AgentCap(!1)),AgentCap}),define("sequence/components/AgentHighlight",["./BaseComponent"],BaseComponent=>{"use strict";class AgentHighlight extends BaseComponent{radius(highlighted,env){return highlighted?env.theme.agentLineHighlightRadius:0}separationPre({agentNames:agentNames,highlighted:highlighted},env){const r=this.radius(highlighted,env);agentNames.forEach(name=>{const agentInfo=env.agentInfos.get(name);agentInfo.currentRad=r,agentInfo.currentMaxRad=Math.max(agentInfo.currentMaxRad,r)})}renderPre({agentNames:agentNames,highlighted:highlighted},env){const r=this.radius(highlighted,env);agentNames.forEach(name=>{const agentInfo=env.agentInfos.get(name);agentInfo.currentMaxRad=Math.max(agentInfo.currentMaxRad,r)})}render({agentNames:agentNames,highlighted:highlighted},env){const r=this.radius(highlighted,env);return agentNames.forEach(name=>{env.drawAgentLine(name,env.primaryY),env.agentInfos.get(name).currentRad=r}),env.primaryY+env.theme.actionMargin}}return BaseComponent.register("agent highlight",new AgentHighlight),AgentHighlight}),define("sequence/components/Connect",["./BaseComponent","svg/SVGUtilities","svg/SVGShapes"],(BaseComponent,svg,SVGShapes)=>{"use strict";function makeWavyLineHeights(height){return[0,2*-height/3,-height,2*-height/3,0,2*height/3,height,2*height/3]}class Arrowhead{constructor(propName){this.propName=propName}getConfig(theme){return theme.connect.arrow[this.propName]}short(theme){const arrow=this.getConfig(theme),join=arrow.attrs["stroke-linejoin"]||"miter",t=.5*arrow.attrs["stroke-width"],lineStroke=.5*theme.agentLineAttrs["stroke-width"];if("round"===join)return lineStroke+t;{const h=arrow.height/2,w=arrow.width;return lineStroke+t*Math.sqrt(w*w/(h*h)+1)}}render(layer,theme,{x:x,y:y,dir:dir}){const config=this.getConfig(theme);!function(container,{x:x,y:y,dx:dx,dy:dy,attrs:attrs}){container.appendChild(svg.make("none"===attrs.fill?"polyline":"polygon",Object.assign({points:x+dx+" "+(y-dy)+" "+x+" "+y+" "+(x+dx)+" "+(y+dy)},attrs)))}(layer,{x:x+this.short(theme)*dir,y:y,dx:config.width*dir,dy:config.height/2,attrs:config.attrs})}width(theme){return this.short(theme)+this.getConfig(theme).width}height(theme){return this.getConfig(theme).height}lineGap(theme,lineAttrs){const arrow=this.getConfig(theme),short=this.short(theme);if("none"===arrow.attrs.fill){const h=arrow.height/2,w=arrow.width;return(short+(short+lineAttrs["stroke-width"]/2*(w/h)))/2}return short+arrow.width/2}}const ARROWHEADS=[{render:()=>{},width:()=>0,height:()=>0,lineGap:()=>0},new Arrowhead("single"),new Arrowhead("double")];class ConnectingLine{renderFlat(container,{x1:x1,x2:x2,y:y},attrs){const ww=attrs["wave-width"],hh=attrs["wave-height"];if(!ww||!hh)return void container.appendChild(svg.make("line",Object.assign({x1:x1,y1:y,x2:x2,y2:y},attrs)));const heights=makeWavyLineHeights(hh),dw=ww/heights.length;let p=0,points="";for(let x=x1;x+dw<=x2;x+=dw)points+=x+" "+(y+heights[p++%heights.length])+" ";points+=x2+" "+y,container.appendChild(svg.make("polyline",Object.assign({points:points},attrs)))}renderRev(container,{xL1:xL1,xL2:xL2,y1:y1,y2:y2,xR:xR},attrs){const r=(y2-y1)/2,ww=attrs["wave-width"],hh=attrs["wave-height"];if(!ww||!hh)return void container.appendChild(svg.make("path",Object.assign({d:"M "+xL1+" "+y1+" L "+xR+" "+y1+" A "+r+" "+r+" 0 0 1 "+xR+" "+y2+" L "+xL2+" "+y2},attrs)));const heights=makeWavyLineHeights(hh),dw=ww/heights.length;let p=0,points="";for(let x=xL1;x+dw<=xR;x+=dw)points+=x+" "+(y1+heights[p++%heights.length])+" ";const ym=(y1+y2)/2;for(let t=0;t+dw/r<=Math.PI;t+=dw/r){const h=heights[p++%heights.length];points+=xR+Math.sin(t)*(r-h)+" "+(ym-Math.cos(t)*(r-h))+" "}for(let x=xR;x-dw>=xL2;x-=dw)points+=x+" "+(y2-heights[p++%heights.length])+" ";points+=xL2+" "+y2,container.appendChild(svg.make("polyline",Object.assign({points:points},attrs)))}}const CONNECTING_LINE=new ConnectingLine;class Connect extends BaseComponent{separation({label:label,agentNames:agentNames,options:options},env){const config=env.theme.connect,lArrow=ARROWHEADS[options.left],rArrow=ARROWHEADS[options.right];let labelWidth=env.textSizer.measure(config.label.attrs,label).width;labelWidth>0&&(labelWidth+=2*config.label.padding);const info1=env.agentInfos.get(agentNames[0]);if(agentNames[0]===agentNames[1])env.addSpacing(agentNames[0],{left:0,right:info1.currentMaxRad+Math.max(labelWidth+lArrow.width(env.theme),rArrow.width(env.theme))+config.loopbackRadius});else{const info2=env.agentInfos.get(agentNames[1]);env.addSeparation(agentNames[0],agentNames[1],info1.currentMaxRad+info2.currentMaxRad+labelWidth+2*Math.max(lArrow.width(env.theme),rArrow.width(env.theme)))}}renderSelfConnect({label:label,agentNames:agentNames,options:options},env){const config=env.theme.connect,from=env.agentInfos.get(agentNames[0]),lArrow=ARROWHEADS[options.left],rArrow=ARROWHEADS[options.right],height=label?env.textSizer.measureHeight(config.label.attrs,label)+config.label.margin.top+config.label.margin.bottom:0,lineX=from.x+from.currentMaxRad,y0=env.primaryY,x0=lineX+lArrow.width(env.theme)+(label?config.label.padding:0),clickable=env.makeRegion(),renderedText=SVGShapes.renderBoxedText(label,{x:x0-config.mask.padding.left,y:y0-height+config.label.margin.top,padding:config.mask.padding,boxAttrs:{fill:"#000000"},labelAttrs:config.label.loopbackAttrs,boxLayer:env.maskLayer,labelLayer:clickable,SVGTextBlockClass:env.SVGTextBlockClass}),labelW=label?renderedText.width+config.label.padding-config.mask.padding.left-config.mask.padding.right:0,r=config.loopbackRadius,x1=Math.max(lineX+rArrow.width(env.theme),x0+labelW),y1=y0+2*r,lineAttrs=config.lineAttrs[options.line];CONNECTING_LINE.renderRev(env.shapeLayer,{xL1:lineX+lArrow.lineGap(env.theme,lineAttrs),xL2:lineX+rArrow.lineGap(env.theme,lineAttrs),y1:y0,y2:y1,xR:x1},lineAttrs),lArrow.render(env.shapeLayer,env.theme,{x:lineX,y:y0,dir:1}),rArrow.render(env.shapeLayer,env.theme,{x:lineX,y:y1,dir:1});const raise=Math.max(height,lArrow.height(env.theme)/2),arrowDip=rArrow.height(env.theme)/2;return clickable.insertBefore(svg.make("rect",{x:lineX,y:y0-raise,width:x1+r-lineX,height:raise+2*r+arrowDip,fill:"transparent"}),clickable.firstChild),y1+Math.max(arrowDip+env.theme.minActionMargin,env.theme.actionMargin)}renderSimpleConnect({label:label,agentNames:agentNames,options:options},env){const config=env.theme.connect,from=env.agentInfos.get(agentNames[0]),to=env.agentInfos.get(agentNames[1]),lArrow=ARROWHEADS[options.left],rArrow=ARROWHEADS[options.right],dir=from.x{"use strict";function findExtremes(agentInfos,agentNames){let min=null,max=null;return agentNames.forEach(name=>{const info=agentInfos.get(name);(null===min||info.indexmax.index)&&(max=info)}),{left:min.label,right:max.label}}class NoteComponent extends BaseComponent{renderPre({agentNames:agentNames}){return{agentNames:agentNames}}renderNote({xMid:xMid=null,x0:x0=null,x1:x1=null,anchor:anchor,mode:mode,label:label},env){const config=env.theme.note[mode],clickable=env.makeRegion(),y=env.topY+config.margin.top+config.padding.top,labelNode=new env.SVGTextBlockClass(clickable,{attrs:config.labelAttrs,text:label,y:y}),fullW=labelNode.width+config.padding.left+config.padding.right,fullH=config.padding.top+labelNode.height+config.padding.bottom;switch(null===x0&&null!==xMid&&(x0=xMid-fullW/2),null===x1&&null!==x0?x1=x0+fullW:null===x0&&(x0=x1-fullW),config.labelAttrs["text-anchor"]){case"middle":labelNode.set({x:(x0+config.padding.left+x1-config.padding.right)/2,y:y});break;case"end":labelNode.set({x:x1-config.padding.right,y:y});break;default:labelNode.set({x:x0+config.padding.left,y:y})}return env.shapeLayer.appendChild(config.boxRenderer({x:x0,y:env.topY+config.margin.top,width:x1-x0,height:fullH})),clickable.insertBefore(svg.make("rect",{x:x0,y:env.topY+config.margin.top,width:x1-x0,height:fullH,fill:"transparent"}),clickable.firstChild),env.topY+config.margin.top+fullH+config.margin.bottom+env.theme.actionMargin}}class NoteOver extends NoteComponent{separation({agentNames:agentNames,mode:mode,label:label},env){const config=env.theme.note[mode],width=env.textSizer.measure(config.labelAttrs,label).width+config.padding.left+config.padding.right,{left:left,right:right}=findExtremes(env.agentInfos,agentNames),infoL=env.agentInfos.get(left),infoR=env.agentInfos.get(right);if(infoL!==infoR){const hangL=infoL.currentMaxRad+config.overlap.left,hangR=infoR.currentMaxRad+config.overlap.right;env.addSeparation(left,right,width-hangL-hangR),env.addSpacing(left,{left:hangL,right:0}),env.addSpacing(right,{left:0,right:hangR})}else env.addSpacing(left,{left:width/2,right:width/2})}render({agentNames:agentNames,mode:mode,label:label},env){const config=env.theme.note[mode],{left:left,right:right}=findExtremes(env.agentInfos,agentNames),infoL=env.agentInfos.get(left),infoR=env.agentInfos.get(right);if(infoL!==infoR)return this.renderNote({x0:infoL.x-infoL.currentMaxRad-config.overlap.left,x1:infoR.x+infoR.currentMaxRad+config.overlap.right,anchor:"middle",mode:mode,label:label},env);{const xMid=infoL.x;return this.renderNote({xMid:xMid,anchor:"middle",mode:mode,label:label},env)}}}class NoteSide extends NoteComponent{constructor(isRight){super(),this.isRight=isRight}separation({agentNames:agentNames,mode:mode,label:label},env){const config=env.theme.note[mode],{left:left,right:right}=findExtremes(env.agentInfos,agentNames),width=env.textSizer.measure(config.labelAttrs,label).width+config.padding.left+config.padding.right+config.margin.left+config.margin.right;if(this.isRight){const info=env.agentInfos.get(right);env.addSpacing(right,{left:0,right:width+info.currentMaxRad})}else{const info=env.agentInfos.get(left);env.addSpacing(left,{left:width+info.currentMaxRad,right:0})}}render({agentNames:agentNames,mode:mode,label:label},env){const config=env.theme.note[mode],{left:left,right:right}=findExtremes(env.agentInfos,agentNames);if(this.isRight){const info=env.agentInfos.get(right),x0=info.x+info.currentMaxRad+config.margin.left;return this.renderNote({x0:x0,anchor:"start",mode:mode,label:label},env)}{const info=env.agentInfos.get(left),x1=info.x-info.currentMaxRad-config.margin.right;return this.renderNote({x1:x1,anchor:"end",mode:mode,label:label},env)}}}class NoteBetween extends NoteComponent{separation({agentNames:agentNames,mode:mode,label:label},env){const config=env.theme.note[mode],{left:left,right:right}=findExtremes(env.agentInfos,agentNames),infoL=env.agentInfos.get(left),infoR=env.agentInfos.get(right);env.addSeparation(left,right,env.textSizer.measure(config.labelAttrs,label).width+config.padding.left+config.padding.right+config.margin.left+config.margin.right+infoL.currentMaxRad+infoR.currentMaxRad)}render({agentNames:agentNames,mode:mode,label:label},env){const{left:left,right:right}=findExtremes(env.agentInfos,agentNames),infoL=env.agentInfos.get(left),infoR=env.agentInfos.get(right),xMid=(infoL.x+infoL.currentMaxRad+infoR.x-infoR.currentMaxRad)/2;return this.renderNote({xMid:xMid,anchor:"middle",mode:mode,label:label},env)}}return NoteComponent.NoteOver=NoteOver,NoteComponent.NoteSide=NoteSide,NoteComponent.NoteBetween=NoteBetween,BaseComponent.register("note over",new NoteOver),BaseComponent.register("note left",new NoteSide(!1)),BaseComponent.register("note right",new NoteSide(!0)),BaseComponent.register("note between",new NoteBetween),NoteComponent}),define("sequence/Renderer",["core/ArrayUtilities","core/EventObject","svg/SVGUtilities","svg/SVGShapes","./components/BaseComponent","./components/Block","./components/Parallel","./components/Marker","./components/AgentCap","./components/AgentHighlight","./components/Connect","./components/Note"],(array,EventObject,svg,SVGShapes,BaseComponent)=>{"use strict";function findExtremes(agentInfos,agentNames){let min=null,max=null;return agentNames.forEach(name=>{const info=agentInfos.get(name);(null===min||info.indexmax.index)&&(max=info)}),{left:min.label,right:max.label}}let globalNamespace=0;return class extends EventObject{constructor({themes:themes=[],namespace:namespace=null,components:components=null,SVGTextBlockClass:SVGTextBlockClass=SVGShapes.TextBlock}={}){super(),null===components&&(components=BaseComponent.getComponents()),this.separationStage=this.separationStage.bind(this),this.renderStage=this.renderStage.bind(this),this.addSeparation=this.addSeparation.bind(this),this.addDef=this.addDef.bind(this),this.state={},this.width=0,this.height=0,this.themes=function(themes){if(0===themes.length)throw new Error("Cannot render without a theme");const themeMap=new Map;return themes.forEach(theme=>{themeMap.set(theme.name,theme)}),themeMap.set("",themes[0]),themeMap}(themes),this.theme=null,this.namespace=function(namespace){return null===namespace&&(namespace="R"+globalNamespace,++globalNamespace),namespace}(namespace),this.components=components,this.SVGTextBlockClass=SVGTextBlockClass,this.knownDefs=new Set,this.highlights=new Map,this.currentHighlight=-1,this.buildStaticElements(),this.components.forEach(component=>{component.makeState(this.state)})}addTheme(theme){this.themes.set(theme.name,theme)}buildStaticElements(){this.base=svg.makeContainer(),this.defs=svg.make("defs"),this.mask=svg.make("mask",{id:this.namespace+"LineMask",maskUnits:"userSpaceOnUse"}),this.maskReveal=svg.make("rect",{fill:"#FFFFFF"}),this.agentLines=svg.make("g",{mask:"url(#"+this.namespace+"LineMask)"}),this.blocks=svg.make("g"),this.sections=svg.make("g"),this.actionShapes=svg.make("g"),this.actionLabels=svg.make("g"),this.base.appendChild(this.defs),this.base.appendChild(this.agentLines),this.base.appendChild(this.blocks),this.base.appendChild(this.sections),this.base.appendChild(this.actionShapes),this.base.appendChild(this.actionLabels),this.title=new this.SVGTextBlockClass(this.base),this.sizer=new this.SVGTextBlockClass.SizeTester(this.base)}addDef(name,generator){const namespacedName=this.namespace+name;if(this.knownDefs.has(name))return namespacedName;this.knownDefs.add(name);const def=generator();return def.setAttribute("id",namespacedName),this.defs.appendChild(def),namespacedName}addSeparation(agentName1,agentName2,dist){const info1=this.agentInfos.get(agentName1),info2=this.agentInfos.get(agentName2),d1=info1.separations.get(agentName2)||0;info1.separations.set(agentName2,Math.max(d1,dist));const d2=info2.separations.get(agentName1)||0;info2.separations.set(agentName1,Math.max(d2,dist))}separationStage(stage){const agentSpaces=new Map,agentNames=this.visibleAgents.slice();this.agentInfos.forEach(agentInfo=>{const rad=agentInfo.currentRad;agentInfo.currentMaxRad=rad,agentSpaces.set(agentInfo.label,{left:rad,right:rad})});const env={theme:this.theme,agentInfos:this.agentInfos,visibleAgents:this.visibleAgents,textSizer:this.sizer,addSpacing:(agentName,{left:left,right:right})=>{const current=agentSpaces.get(agentName);current.left=Math.max(current.left,left),current.right=Math.max(current.right,right)},addSeparation:this.addSeparation,components:this.components},component=this.components.get(stage.type);if(!component)throw new Error("Unknown component: "+stage.type);component.separationPre(stage,env),component.separation(stage,env),array.mergeSets(agentNames,this.visibleAgents),agentNames.forEach(agentNameR=>{const infoR=this.agentInfos.get(agentNameR),sepR=agentSpaces.get(agentNameR);infoR.maxRPad=Math.max(infoR.maxRPad,sepR.right),infoR.maxLPad=Math.max(infoR.maxLPad,sepR.left),agentNames.forEach(agentNameL=>{if(this.agentInfos.get(agentNameL).index>=infoR.index)return;const sepL=agentSpaces.get(agentNameL);this.addSeparation(agentNameR,agentNameL,sepR.left+sepL.right+this.theme.agentMargin)})})}checkAgentRange(agentNames,topY=0){if(0===agentNames.length)return topY;const{left:left,right:right}=findExtremes(this.agentInfos,agentNames),leftX=this.agentInfos.get(left).x,rightX=this.agentInfos.get(right).x;let baseY=topY;return this.agentInfos.forEach(agentInfo=>{agentInfo.x>=leftX&&agentInfo.x<=rightX&&(baseY=Math.max(baseY,agentInfo.latestY))}),baseY}markAgentRange(agentNames,y){if(0===agentNames.length)return;const{left:left,right:right}=findExtremes(this.agentInfos,agentNames),leftX=this.agentInfos.get(left).x,rightX=this.agentInfos.get(right).x;this.agentInfos.forEach(agentInfo=>{agentInfo.x>=leftX&&agentInfo.x<=rightX&&(agentInfo.latestY=y)})}drawAgentLine(agentInfo,toY){if(null===agentInfo.latestYStart||toY<=agentInfo.latestYStart)return;const r=agentInfo.currentRad;r>0?this.agentLines.appendChild(svg.make("rect",Object.assign({x:agentInfo.x-r,y:agentInfo.latestYStart,width:2*r,height:toY-agentInfo.latestYStart,class:"agent-"+agentInfo.index+"-line"},this.theme.agentLineAttrs))):this.agentLines.appendChild(svg.make("line",Object.assign({x1:agentInfo.x,y1:agentInfo.latestYStart,x2:agentInfo.x,y2:toY,class:"agent-"+agentInfo.index+"-line"},this.theme.agentLineAttrs)))}addHighlightObject(line,o){let list=this.highlights.get(line);list||(list=[],this.highlights.set(line,list)),list.push(o)}renderStage(stage){this.agentInfos.forEach(agentInfo=>{const rad=agentInfo.currentRad;agentInfo.currentMaxRad=rad});const envPre={theme:this.theme,agentInfos:this.agentInfos,textSizer:this.sizer,state:this.state,components:this.components},component=this.components.get(stage.type),result=component.renderPre(stage,envPre),{topShift:topShift,agentNames:agentNames,asynchronousY:asynchronousY}=BaseComponent.cleanRenderPreResult(result,this.currentY),topY=this.checkAgentRange(agentNames,asynchronousY),env={topY:topY,primaryY:topY+topShift,blockLayer:this.blocks,sectionLayer:this.sections,shapeLayer:this.actionShapes,labelLayer:this.actionLabels,maskLayer:this.mask,theme:this.theme,agentInfos:this.agentInfos,textSizer:this.sizer,SVGTextBlockClass:this.SVGTextBlockClass,state:this.state,drawAgentLine:(agentName,toY,andStop=!1)=>{const agentInfo=this.agentInfos.get(agentName);this.drawAgentLine(agentInfo,toY),agentInfo.latestYStart=andStop?null:toY},addDef:this.addDef,makeRegion:(o,stageOverride=null)=>{o||(o=svg.make("g"));const targetStage=stageOverride||stage;return this.addHighlightObject(targetStage.ln,o),o.setAttribute("class","region"),o.addEventListener("mouseenter",()=>{this.trigger("mouseover",[targetStage])}),o.addEventListener("mouseleave",()=>{this.trigger("mouseout")}),o.addEventListener("click",()=>{this.trigger("click",[targetStage])}),this.actionLabels.appendChild(o),o},components:this.components},bottomY=Math.max(topY,component.render(stage,env)||0);this.markAgentRange(agentNames,bottomY),this.currentY=bottomY}positionAgents(){const orderedInfos=[];this.agentInfos.forEach(agentInfo=>{let currentX=0;agentInfo.separations.forEach((dist,otherAgent)=>{const otherAgentInfo=this.agentInfos.get(otherAgent);otherAgentInfo.index{let currentX=previousInfo.x;previousInfo=agentInfo,agentInfo.anchorRight&&(agentInfo.separations.forEach((dist,otherAgent)=>{const otherAgentInfo=this.agentInfos.get(otherAgent);otherAgentInfo.index>agentInfo.index&&(currentX=Math.min(currentX,otherAgentInfo.x-dist))}),agentInfo.x=currentX)}),this.agentInfos.forEach(({label:label,x:x,maxRPad:maxRPad,maxLPad:maxLPad})=>{this.minX=Math.min(this.minX,x-maxLPad),this.maxX=Math.max(this.maxX,x+maxRPad)})}buildAgentInfos(agents,stages){this.agentInfos=new Map,agents.forEach((agent,index)=>{this.agentInfos.set(agent.name,{label:agent.name,anchorRight:agent.anchorRight,index:index,x:null,latestYStart:null,currentRad:0,currentMaxRad:0,latestY:0,maxRPad:0,maxLPad:0,separations:new Map})}),this.visibleAgents=["[","]"],stages.forEach(this.separationStage),this.positionAgents()}updateBounds(stagesHeight){const cx=(this.minX+this.maxX)/2,titleY=this.title.height>0?-this.theme.titleMargin-this.title.height:0;this.title.set({x:cx,y:titleY});const halfTitleWidth=this.title.width/2,margin=this.theme.outerMargin,x0=Math.min(this.minX,cx-halfTitleWidth)-margin,x1=Math.max(this.maxX,cx+halfTitleWidth)+margin,y0=titleY-margin,y1=stagesHeight+margin;this.maskReveal.setAttribute("x",x0),this.maskReveal.setAttribute("y",y0),this.maskReveal.setAttribute("width",x1-x0),this.maskReveal.setAttribute("height",y1-y0),this.base.setAttribute("viewBox",x0+" "+y0+" "+(x1-x0)+" "+(y1-y0)),this.width=x1-x0,this.height=y1-y0}_reset(){this.knownDefs.clear(),this.highlights.clear(),this.currentHighlight=-1,svg.empty(this.defs),svg.empty(this.mask),svg.empty(this.agentLines),svg.empty(this.blocks),svg.empty(this.sections),svg.empty(this.actionShapes),svg.empty(this.actionLabels),this.mask.appendChild(this.maskReveal),this.defs.appendChild(this.mask),this.components.forEach(component=>{component.resetState(this.state)})}setHighlight(line=null){null!==line&&this.highlights.has(line)||(line=-1),this.currentHighlight!==line&&(-1!==this.currentHighlight&&this.highlights.get(this.currentHighlight).forEach(o=>{o.setAttribute("class","region")}),-1!==line&&this.highlights.get(line).forEach(o=>{o.setAttribute("class","region focus")}),this.currentHighlight=line)}render(sequence){const prevHighlight=this.currentHighlight;this._reset();const themeName=sequence.meta.theme;this.theme=this.themes.get(themeName),this.theme||(this.theme=this.themes.get("")),this.title.set({attrs:this.theme.titleAttrs,text:sequence.meta.title}),this.minX=0,this.maxX=0,this.buildAgentInfos(sequence.agents,sequence.stages),this.currentY=0,sequence.stages.forEach(this.renderStage);const bottomY=this.checkAgentRange(["[","]"],this.currentY),stagesHeight=Math.max(bottomY-this.theme.actionMargin,0);this.updateBounds(stagesHeight),this.sizer.resetCache(),this.sizer.detach(),this.setHighlight(prevHighlight)}getThemeNames(){return Array.from(this.themes.keys()).filter(name=>""!==name)}getThemes(){return this.getThemeNames().map(name=>this.themes.get(name))}getAgentX(name){return this.agentInfos.get(name).x}svg(){return this.base}}}),define("sequence/Exporter",[],()=>{"use strict";const safari=/^((?!chrome|android).)*safari/i.test(navigator.userAgent),firefox=void 0!==window.InstallTrigger;return class{constructor(){this.latestSVG=null,this.latestInternalSVG=null,this.canvas=null,this.context=null,this.indexPNG=0,this.latestPNGIndex=0,this.latestPNG=null}getSVGContent(renderer,size=null){let code=renderer.svg().outerHTML;return firefox&&size&&(code=code.replace(/^{this.canvas.width=width,this.canvas.height=height,this.context.drawImage(img,0,0),safariHackaround&&document.body.removeChild(safariHackaround),this.canvas.toBlob(callback,"image/png")},{once:!0}),img.src=this.getSVGURL(renderer,{width:width,height:height})}getPNGURL(renderer,resolution,callback){++this.indexPNG;const index=this.indexPNG;this.getPNGBlob(renderer,resolution,blob=>{const url=URL.createObjectURL(blob);index>=this.latestPNGIndex?(this.latestPNG&&URL.revokeObjectURL(this.latestPNG),this.latestPNG=url,this.latestPNGIndex=index,callback(url,!0)):(callback(url,!1),URL.revokeObjectURL(url))})}}}),define("sequence/themes/Basic",["core/ArrayUtilities","svg/SVGShapes"],(array,SVGShapes)=>{"use strict";const SETTINGS={titleMargin:10,outerMargin:5,agentMargin:10,actionMargin:10,minActionMargin:3,agentLineHighlightRadius:4,agentCap:{box:{padding:{top:5,left:10,right:10,bottom:5},arrowBottom:12.8,boxAttrs:{fill:"#FFFFFF",stroke:"#000000","stroke-width":1},labelAttrs:{"font-family":"sans-serif","font-size":12,"line-height":1.3,"text-anchor":"middle"}},cross:{size:20,attrs:{fill:"none",stroke:"#000000","stroke-width":1}},bar:{attrs:{fill:"#000000",stroke:"#000000","stroke-width":1,height:4}},fade:{width:5,height:6},none:{height:10}},connect:{loopbackRadius:6,lineAttrs:{solid:{fill:"none",stroke:"#000000","stroke-width":1},dash:{fill:"none",stroke:"#000000","stroke-width":1,"stroke-dasharray":"4, 2"},wave:{fill:"none",stroke:"#000000","stroke-width":1,"stroke-linejoin":"round","stroke-linecap":"round","wave-width":6,"wave-height":.5}},arrow:{single:{width:5,height:10,attrs:{fill:"#000000","stroke-width":0,"stroke-linejoin":"miter"}},double:{width:4,height:6,attrs:{fill:"none",stroke:"#000000","stroke-width":1,"stroke-linejoin":"miter"}}},label:{padding:6,margin:{top:2,bottom:1},attrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3,"text-anchor":"middle"},loopbackAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}},mask:{padding:{top:0,left:3,right:3,bottom:1}}},block:{margin:{top:0,bottom:0},modes:{ref:{boxAttrs:{fill:"#FFFFFF",stroke:"#000000","stroke-width":1.5,rx:2,ry:2}},"":{boxAttrs:{fill:"none",stroke:"#000000","stroke-width":1.5,rx:2,ry:2}}},section:{padding:{top:3,bottom:2},mode:{padding:{top:1,left:3,right:3,bottom:0},boxAttrs:{fill:"#FFFFFF",stroke:"#000000","stroke-width":1,rx:2,ry:2},labelAttrs:{"font-family":"sans-serif","font-weight":"bold","font-size":9,"line-height":1.3,"text-anchor":"left"}},label:{padding:{top:1,left:5,right:3,bottom:0},labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3,"text-anchor":"left"}}},separator:{attrs:{stroke:"#000000","stroke-width":1.5,"stroke-dasharray":"4, 2"}}},note:{text:{margin:{top:0,left:2,right:2,bottom:0},padding:{top:2,left:2,right:2,bottom:2},overlap:{left:10,right:10},boxRenderer:SVGShapes.renderBox.bind(null,{fill:"#FFFFFF"}),labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}},note:{margin:{top:0,left:5,right:5,bottom:0},padding:{top:5,left:5,right:10,bottom:5},overlap:{left:10,right:10},boxRenderer:SVGShapes.renderNote.bind(null,{fill:"#FFFFFF",stroke:"#000000","stroke-width":1},{fill:"none",stroke:"#000000","stroke-width":1}),labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}},state:{margin:{top:0,left:5,right:5,bottom:0},padding:{top:7,left:7,right:7,bottom:7},overlap:{left:10,right:10},boxRenderer:SVGShapes.renderBox.bind(null,{fill:"#FFFFFF",stroke:"#000000","stroke-width":1,rx:10,ry:10}),labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}}},titleAttrs:{"font-family":"sans-serif","font-size":20,"line-height":1.3,"text-anchor":"middle",class:"title"},agentLineAttrs:{fill:"none",stroke:"#000000","stroke-width":1}};return class{constructor(){this.name="basic",Object.assign(this,SETTINGS)}}}),define("sequence/themes/Chunky",["core/ArrayUtilities","svg/SVGShapes"],(array,SVGShapes)=>{"use strict";const SETTINGS={titleMargin:12,outerMargin:5,agentMargin:8,actionMargin:5,minActionMargin:5,agentLineHighlightRadius:4,agentCap:{box:{padding:{top:1,left:3,right:3,bottom:1},arrowBottom:11.1,boxAttrs:{fill:"#FFFFFF",stroke:"#000000","stroke-width":3,rx:4,ry:4},labelAttrs:{"font-family":"sans-serif","font-weight":"bold","font-size":14,"line-height":1.3,"text-anchor":"middle"}},cross:{size:20,attrs:{fill:"none",stroke:"#000000","stroke-width":3,"stroke-linecap":"round"}},bar:{attrs:{fill:"#000000",stroke:"#000000","stroke-width":3,height:4,rx:2,ry:2}},fade:{width:5,height:10},none:{height:10}},connect:{loopbackRadius:8,lineAttrs:{solid:{fill:"none",stroke:"#000000","stroke-width":3},dash:{fill:"none",stroke:"#000000","stroke-width":3,"stroke-dasharray":"10, 4"},wave:{fill:"none",stroke:"#000000","stroke-width":3,"stroke-linejoin":"round","stroke-linecap":"round","wave-width":10,"wave-height":1}},arrow:{single:{width:10,height:12,attrs:{fill:"#000000",stroke:"#000000","stroke-width":3,"stroke-linejoin":"round"}},double:{width:10,height:12,attrs:{fill:"none",stroke:"#000000","stroke-width":3,"stroke-linejoin":"round","stroke-linecap":"round"}}},label:{padding:7,margin:{top:2,bottom:3},attrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3,"text-anchor":"middle"},loopbackAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}},mask:{padding:{top:1,left:5,right:5,bottom:3}}},block:{margin:{top:0,bottom:0},modes:{ref:{boxAttrs:{fill:"#FFFFFF",stroke:"#000000","stroke-width":4,rx:5,ry:5}},"":{boxAttrs:{fill:"none",stroke:"#000000","stroke-width":4,rx:5,ry:5}}},section:{padding:{top:3,bottom:4},mode:{padding:{top:2,left:5,right:5,bottom:1},boxAttrs:{fill:"#FFFFFF",stroke:"#000000","stroke-width":2,rx:3,ry:3},labelAttrs:{"font-family":"sans-serif","font-weight":"bold","font-size":9,"line-height":1.3,"text-anchor":"left"}},label:{padding:{top:2,left:5,right:3,bottom:0},labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3,"text-anchor":"left"}}},separator:{attrs:{stroke:"#000000","stroke-width":2,"stroke-dasharray":"5, 3"}}},note:{text:{margin:{top:0,left:2,right:2,bottom:0},padding:{top:2,left:2,right:2,bottom:2},overlap:{left:10,right:10},boxRenderer:SVGShapes.renderBox.bind(null,{fill:"#FFFFFF"}),labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}},note:{margin:{top:0,left:5,right:5,bottom:0},padding:{top:3,left:3,right:10,bottom:3},overlap:{left:10,right:10},boxRenderer:SVGShapes.renderNote.bind(null,{fill:"#FFFFFF",stroke:"#000000","stroke-width":2,"stroke-linejoin":"round"},{fill:"none",stroke:"#000000","stroke-width":1}),labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}},state:{margin:{top:0,left:5,right:5,bottom:0},padding:{top:5,left:7,right:7,bottom:5},overlap:{left:10,right:10},boxRenderer:SVGShapes.renderBox.bind(null,{fill:"#FFFFFF",stroke:"#000000","stroke-width":3,rx:10,ry:10}),labelAttrs:{"font-family":"sans-serif","font-size":8,"line-height":1.3}}},titleAttrs:{"font-family":"sans-serif","font-weight":"bolder","font-size":20,"line-height":1.3,"text-anchor":"middle",class:"title"},agentLineAttrs:{fill:"none",stroke:"#000000","stroke-width":3}};return class{constructor(){this.name="chunky",Object.assign(this,SETTINGS)}}}),define("sequence/SequenceDiagram",["core/EventObject","./Parser","./Generator","./Renderer","./Exporter","./themes/Basic","./themes/Chunky"],(EventObject,Parser,Generator,Renderer,Exporter,BasicTheme,ChunkyTheme)=>{"use strict";function registerCodeMirrorMode(CodeMirror,modeName="sequence"){CodeMirror||(CodeMirror=window.CodeMirror),CodeMirror.defineMode(modeName,()=>CMMode),CodeMirror.registerHelper("hint",modeName,CMHints)}function convert(element,code=null,options={}){if("svg"===element.tagName)return null;null===code?code=element.innerText:"object"==typeof code&&(code=(options=code).code);const diagram=new SequenceDiagram(code,options),newElement=diagram.dom();element.parentNode.insertBefore(newElement,element),element.parentNode.removeChild(element);const attrs=element.attributes;for(let i=0;i{this.exporter.getPNGURL(this.renderer,resolution,(url,latest)=>{resolve({url:url,latest:latest})})})}getSize(){return{width:this.renderer.width,height:this.renderer.height}}render(processed=null){const dom=this.renderer.svg(),originalParent=dom.parentNode;document.body.contains(dom)||(originalParent&&originalParent.removeChild(dom),document.body.appendChild(dom));try{processed||(processed=this.process(this.code)),this.renderer.render(processed)}finally{dom.parentNode!==originalParent&&(document.body.removeChild(dom),originalParent&&originalParent.appendChild(dom))}}setContainer(node=null){const dom=this.dom();dom.parentNode&&dom.parentNode.removeChild(dom),node&&node.appendChild(dom)}dom(){return this.renderer.svg()}}return Object.assign(SequenceDiagram,{Parser:Parser,Generator:Generator,Renderer:Renderer,Exporter:Exporter,themes:themes,addTheme:function(theme){themes.push(theme)},registerCodeMirrorMode:registerCodeMirrorMode,convert:convert,convertAll:function(root=null,className="sequence-diagram"){"string"==typeof root&&(className=root,root=null);let elements=null;elements=root&&void 0!==root.length?root:(root||document).getElementsByClassName(className);const els=[];for(let i=0;iconvert(el))}})}),requirejs(["sequence/SequenceDiagram"],SequenceDiagram=>{"use strict";const def=window.define;def&&def.amd?def(()=>SequenceDiagram):(document.addEventListener("DOMContentLoaded",()=>{SequenceDiagram.convertAll()},{once:!0}),window.CodeMirror&&SequenceDiagram.registerCodeMirrorMode(window.CodeMirror),window.SequenceDiagram=SequenceDiagram)},null,!0),define("standalone",function(){})}();
\ No newline at end of file
diff --git a/package.json b/package.json
index 9321604..1985fbd 100644
--- a/package.json
+++ b/package.json
@@ -16,8 +16,8 @@
],
"main": "lib/sequence-diagram",
"scripts": {
- "serve": "node_modules/http-server/bin/http-server",
- "minify": "node node_modules/requirejs/bin/r.js -o scripts/build.js && node_modules/uglify-es/bin/uglifyjs --compress --warn --output lib/sequence-diagram.min.js -- lib/sequence-diagram.js"
+ "serve": "node_modules/.bin/http-server",
+ "minify": "node node_modules/.bin/r.js -o scripts/build.js && node_modules/.bin/uglifyjs --compress --warn --output lib/sequence-diagram.min.js -- lib/sequence-diagram.js"
},
"devDependencies": {
"almond": "^0.3.3",
diff --git a/scripts/standalone.js b/scripts/standalone.js
index 4ce8954..0c0e76a 100644
--- a/scripts/standalone.js
+++ b/scripts/standalone.js
@@ -1,6 +1,14 @@
requirejs(['sequence/SequenceDiagram'], (SequenceDiagram) => {
'use strict';
+ const def = window.define;
+ if(def && def.amd) {
+ def(() => {
+ return SequenceDiagram;
+ });
+ return;
+ }
+
document.addEventListener('DOMContentLoaded', () => {
SequenceDiagram.convertAll();
}, {once: true});
diff --git a/styles/home.css b/styles/home.css
index c149823..aaf058f 100644
--- a/styles/home.css
+++ b/styles/home.css
@@ -101,18 +101,6 @@ pre {
line-height: 1.2;
}
-pre .tag {
- color: #BB44AA;
-}
-
-pre .attr {
- color: #887722;
-}
-
-pre .literal {
- color: #AA3322;
-}
-
nav {
display: block;
position: sticky;