mirror of
https://github.com/mermaid-js/mermaid.git
synced 2025-01-28 07:03:17 +08:00
Merge branches 'knsv/new-shapes' and 'knsv/new-shapes' of github.com:mermaid-js/mermaid into knsv/new-shapes
This commit is contained in:
commit
4d401c127d
@ -9,7 +9,7 @@ elems
|
||||
gantt
|
||||
gitgraph
|
||||
gzipped
|
||||
handdrawn
|
||||
handDrawn
|
||||
knsv
|
||||
Knut
|
||||
marginx
|
||||
|
@ -1,6 +1,6 @@
|
||||
BRANDES
|
||||
circo
|
||||
handdrawn
|
||||
handDrawn
|
||||
KOEPF
|
||||
neato
|
||||
newbranch
|
||||
|
2
.github/workflows/autofix.yml
vendored
2
.github/workflows/autofix.yml
vendored
@ -38,4 +38,4 @@ jobs:
|
||||
working-directory: ./packages/mermaid
|
||||
run: pnpm run docs:build
|
||||
|
||||
- uses: autofix-ci/action@dd55f44df8f7cdb7a6bf74c78677eb8acd40cd0a
|
||||
- uses: autofix-ci/action@ff86a557419858bb967097bfc916833f5647fa8c
|
||||
|
@ -1,14 +0,0 @@
|
||||
import { urlSnapshotTest, openURLAndVerifyRendering } from '../../helpers/util.ts';
|
||||
|
||||
describe('Flowchart elk', () => {
|
||||
it('should use dagre as fallback', () => {
|
||||
urlSnapshotTest('http://localhost:9000/flow-elk.html', {
|
||||
name: 'flow-elk fallback to dagre',
|
||||
});
|
||||
});
|
||||
it('should allow overriding with external package', () => {
|
||||
urlSnapshotTest('http://localhost:9000/flow-elk.html?elk=true', {
|
||||
name: 'flow-elk overriding dagre with elk',
|
||||
});
|
||||
});
|
||||
});
|
@ -837,6 +837,26 @@ subgraph "\`**Two**\`"
|
||||
in the hat\`") -- "\`1o **ipa**\`" --> d("The dog in the hog")
|
||||
end
|
||||
|
||||
`,
|
||||
{ flowchart: { titleTopMargin: 0 } }
|
||||
);
|
||||
});
|
||||
it('Sub graphs and markdown strings', () => {
|
||||
imgSnapshotTest(
|
||||
`---
|
||||
config:
|
||||
layout: elk
|
||||
---
|
||||
|
||||
flowchart LR
|
||||
subgraph subgraph_ko6czgs5u["Untitled subgraph"]
|
||||
D["Option 1"]
|
||||
end
|
||||
C{"Evaluate"} -- One --> D
|
||||
C -- Two --> E(("Option 2"))
|
||||
D --> E
|
||||
A["A"]
|
||||
|
||||
`,
|
||||
{ flowchart: { titleTopMargin: 0 } }
|
||||
);
|
||||
@ -875,11 +895,10 @@ describe('Title and arrow styling #4813', () => {
|
||||
);
|
||||
cy.get('svg').should((svg) => {
|
||||
const edges = svg[0].querySelectorAll('.edges path');
|
||||
// console.log(edges);
|
||||
// expect(edges[0]).to.have.attr('pattern', 'solid');
|
||||
// expect(edges[1]).to.have.attr('pattern', 'dotted');
|
||||
// expect(edges[2]).to.have.css('stroke-width', '3.5px');
|
||||
// expect(edges[3]).to.have.css('stroke-width', '1.5px');
|
||||
expect(edges[0].getAttribute('class')).to.contain('edge-pattern-solid');
|
||||
expect(edges[1].getAttribute('class')).to.contain('edge-pattern-dotted');
|
||||
expect(edges[2].getAttribute('class')).to.contain('edge-thickness-thick');
|
||||
expect(edges[3].getAttribute('class')).to.contain('edge-thickness-invisible');
|
||||
});
|
||||
});
|
||||
});
|
||||
|
1060
cypress/integration/rendering/flowchart-handDrawn.spec.js
Normal file
1060
cypress/integration/rendering/flowchart-handDrawn.spec.js
Normal file
File diff suppressed because it is too large
Load Diff
@ -30,13 +30,40 @@ describe('newShapes', () => {
|
||||
it('4: should render new flippedTriangle shape', () => {
|
||||
imgSnapshotTest(
|
||||
`flowchart
|
||||
KS --> AC@{ shape: flippedTriangle, label:"This is Final Label" }@
|
||||
FS --> AD@{ shape: flippedTriangle, label:"This is Final Label" }@
|
||||
FE --> AD
|
||||
`,
|
||||
{}
|
||||
);
|
||||
});
|
||||
it('5: should render new hourGlass shape', () => {
|
||||
imgSnapshotTest(
|
||||
`flowchart
|
||||
MS --> AE@{ shape: hourglass, label:"This is Final Label" }@
|
||||
ME --> AE
|
||||
`,
|
||||
{}
|
||||
);
|
||||
});
|
||||
it('6: should render new taggedRect shape', () => {
|
||||
imgSnapshotTest(
|
||||
`flowchart
|
||||
KS --> AC@{ shape: taggedRect, label:"This is Final Label" }@
|
||||
RE --> AC
|
||||
`,
|
||||
{}
|
||||
);
|
||||
});
|
||||
it('5: should render new FlowChart for New Shapes', () => {
|
||||
it('7: should render new multiRect shape', () => {
|
||||
imgSnapshotTest(
|
||||
`flowchart
|
||||
DS --> AF@{ shape: multiRect, label:"This is Final Label" }@
|
||||
DE --> AF
|
||||
`,
|
||||
{}
|
||||
);
|
||||
});
|
||||
it('8: should render new FlowChart for New Shapes', () => {
|
||||
renderGraph(
|
||||
`
|
||||
flowchart
|
||||
@ -45,10 +72,13 @@ describe('newShapes', () => {
|
||||
C@{ shape: tiltedCylinder, label: "write your Test Case"}@
|
||||
D@{ shape: flippedTriangle, label: "new Test Case"}@
|
||||
E@{ shape: waveRectangle, label: "Execute Test Case" }@
|
||||
F@{ shape: slopedRect, label: "Test Passed?" }@
|
||||
G@{ shape: bowTieRect, label: "Pass" }@
|
||||
H@{ shape: dividedRect, label: "Log Defect" }@
|
||||
I@{ shape: curvedTrapezoid, label: "End" }@
|
||||
F@{ shape: hourglass , label: "add test case"}@
|
||||
G@{ shape: taggedRect, label: "execute new test case"}@
|
||||
H@{ shape: slopedRect, label: "Test Passed?" }@
|
||||
I@{ shape: bowTieRect, label: "Pass" }@
|
||||
J@{ shape: dividedRect, label: "Log Defect" }@
|
||||
K@{ shape: curvedTrapezoid, label: "End" }@
|
||||
L@{ shape: multiRect, label: "coming soon"}@
|
||||
|
||||
A --> B
|
||||
B --> C
|
||||
@ -56,9 +86,11 @@ describe('newShapes', () => {
|
||||
D --> E
|
||||
E --> F
|
||||
F -->|Yes| G
|
||||
F -->|No| H
|
||||
G --> I
|
||||
G -->|No| H
|
||||
H --> I
|
||||
I --> J
|
||||
J --> K
|
||||
K --> L
|
||||
`,
|
||||
{ flowchart: { useMaxWidth: true } }
|
||||
);
|
||||
|
@ -134,7 +134,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
flowchart LR
|
||||
id1([This is the text in the box])
|
||||
</pre
|
||||
@ -142,7 +142,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram3" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1([This is the text in the box])
|
||||
</pre
|
||||
@ -150,7 +150,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1([This is the text in the box])
|
||||
</pre
|
||||
@ -185,7 +185,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram6" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
flowchart LR
|
||||
id1[[This is the text in the box]]
|
||||
</pre
|
||||
@ -193,7 +193,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram7" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1[[This is the text in the box]]
|
||||
</pre
|
||||
@ -201,7 +201,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram8" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1[[This is the text in the box]]
|
||||
</pre
|
||||
@ -236,7 +236,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram10" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
flowchart LR
|
||||
id1[(Database)]
|
||||
</pre
|
||||
@ -244,7 +244,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram11" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1[(Database)]
|
||||
</pre
|
||||
@ -252,7 +252,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram12" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1[(Database)]
|
||||
</pre
|
||||
@ -287,7 +287,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram14" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
flowchart LR
|
||||
id1((This is the text in the circle))
|
||||
</pre
|
||||
@ -295,7 +295,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram15" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1((This is the text in the circle))
|
||||
</pre
|
||||
@ -303,7 +303,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram16" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1((This is the text in the circle))
|
||||
</pre
|
||||
@ -338,7 +338,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram18" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
flowchart TD
|
||||
id1(((This is the text in the circle)))
|
||||
</pre
|
||||
@ -346,7 +346,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram19" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
flowchart TD
|
||||
id1(((This is the text in the circle)))
|
||||
</pre
|
||||
@ -354,7 +354,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram20" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
flowchart TD
|
||||
id1(((This is the text in the circle)))
|
||||
</pre
|
||||
@ -389,7 +389,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram22" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
flowchart LR
|
||||
id1>This is the text in the box]
|
||||
</pre
|
||||
@ -397,7 +397,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram23" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1>This is the text in the box]
|
||||
</pre
|
||||
@ -405,7 +405,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram24" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1>This is the text in the box]
|
||||
</pre
|
||||
@ -440,7 +440,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram26" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
flowchart LR
|
||||
id1{This is the text in the box}
|
||||
</pre
|
||||
@ -448,7 +448,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram27" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1{This is the text in the box}
|
||||
</pre
|
||||
@ -456,7 +456,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram28" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1{This is the text in the box}
|
||||
</pre
|
||||
@ -491,7 +491,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram31" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1{{This is the text in the box}}
|
||||
</pre
|
||||
@ -499,7 +499,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram32" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1{{This is the text in the box}}
|
||||
</pre
|
||||
@ -534,7 +534,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram34" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
flowchart TD
|
||||
id1[/This is the text in the box/]
|
||||
</pre
|
||||
@ -542,7 +542,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram35" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
flowchart TD
|
||||
id1[/This is the text in the box/]
|
||||
</pre
|
||||
@ -550,7 +550,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram36" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
flowchart TD
|
||||
id1[/This is the text in the box/]
|
||||
</pre
|
||||
@ -585,7 +585,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram38" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
flowchart TD
|
||||
id1[\This is the text in the box\]
|
||||
</pre
|
||||
@ -593,7 +593,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram39" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
flowchart TD
|
||||
id1[\This is the text in the box\]
|
||||
</pre
|
||||
@ -601,7 +601,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram40" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
flowchart TD
|
||||
id1[\This is the text in the box\]
|
||||
|
||||
@ -637,7 +637,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram42" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
flowchart TD
|
||||
A[/Christmas\]
|
||||
</pre
|
||||
@ -645,7 +645,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram43" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
flowchart TD
|
||||
A[/Christmas\]
|
||||
</pre
|
||||
@ -653,7 +653,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram44" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
flowchart TD
|
||||
A[/Christmas\]
|
||||
</pre
|
||||
@ -688,7 +688,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram46" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
flowchart TD
|
||||
A[\Christmas/]
|
||||
</pre
|
||||
@ -696,7 +696,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram47" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
flowchart TD
|
||||
A[\Christmas/]
|
||||
</pre
|
||||
@ -704,7 +704,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram48" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
flowchart TD
|
||||
A[\Christmas/]
|
||||
</pre
|
||||
@ -739,7 +739,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram50" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
flowchart LR
|
||||
id1(This is the text in the box)
|
||||
</pre
|
||||
@ -747,7 +747,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram51" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1(This is the text in the box)
|
||||
</pre
|
||||
@ -755,7 +755,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram52" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1(This is the text in the box)
|
||||
</pre
|
||||
@ -790,7 +790,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram54" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
flowchart LR
|
||||
id1[This is the text in the box]
|
||||
</pre
|
||||
@ -798,7 +798,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram55" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1[This is the text in the box]
|
||||
</pre
|
||||
@ -806,7 +806,7 @@ flowchart LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram56" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
flowchart LR
|
||||
id1[This is the text in the box]
|
||||
</pre
|
||||
@ -827,7 +827,7 @@ flowchart LR
|
||||
mermaid.parseError = function (err, hash) {};
|
||||
|
||||
mermaid.initialize({
|
||||
handdrawn: false,
|
||||
handDrawn: false,
|
||||
mergeEdges: true,
|
||||
layout: 'dagre',
|
||||
flowchart: { titleTopMargin: 10 },
|
||||
|
@ -125,7 +125,7 @@
|
||||
</th>
|
||||
<td>
|
||||
<pre id="diagram1" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
stateDiagram-v2
|
||||
stateA
|
||||
|
||||
@ -134,7 +134,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
flowchart LR
|
||||
id1[[This is the text in the box]]
|
||||
|
||||
@ -152,7 +152,7 @@ flowchart LR
|
||||
mermaid.parseError = function (err, hash) {};
|
||||
|
||||
mermaid.initialize({
|
||||
handdrawn: false,
|
||||
handDrawn: false,
|
||||
mergeEdges: true,
|
||||
layout: 'dagre',
|
||||
flowchart: { titleTopMargin: 10 },
|
||||
|
@ -1,40 +1,54 @@
|
||||
<html>
|
||||
<head>
|
||||
<link href="https://fonts.googleapis.com/css?family=Montserrat&display=swap" rel="stylesheet" />
|
||||
<link href="https://unpkg.com/tailwindcss@^1.0/dist/tailwind.min.css" rel="stylesheet" />
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.min.css"
|
||||
/>
|
||||
<link
|
||||
href="https://cdn.jsdelivr.net/npm/@mdi/font@6.9.96/css/materialdesignicons.min.css"
|
||||
rel="stylesheet"
|
||||
/>
|
||||
<link
|
||||
href="https://fonts.googleapis.com/css?family=Noto+Sans+SC&display=swap"
|
||||
rel="stylesheet"
|
||||
/>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com" />
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
|
||||
<link
|
||||
href="https://fonts.googleapis.com/css2?family=Kalam:wght@300;400;700&display=swap"
|
||||
rel="stylesheet"
|
||||
/>
|
||||
<link
|
||||
href="https://fonts.googleapis.com/css2?family=Caveat:wght@400..700&family=Kalam:wght@300;400;700&family=Rubik+Mono+One&display=swap"
|
||||
rel="stylesheet"
|
||||
/>
|
||||
<link
|
||||
href="https://fonts.googleapis.com/css2?family=Kalam:wght@300;400;700&family=Rubik+Mono+One&display=swap"
|
||||
rel="stylesheet"
|
||||
/>
|
||||
|
||||
<head>
|
||||
<link href="https://fonts.googleapis.com/css?family=Montserrat&display=swap" rel="stylesheet" />
|
||||
<link href="https://unpkg.com/tailwindcss@^1.0/dist/tailwind.min.css" rel="stylesheet" />
|
||||
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.min.css" />
|
||||
<link href="https://cdn.jsdelivr.net/npm/@mdi/font@6.9.96/css/materialdesignicons.min.css" rel="stylesheet" />
|
||||
<link href="https://fonts.googleapis.com/css?family=Noto+Sans+SC&display=swap" rel="stylesheet" />
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com" />
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
|
||||
<link href="https://fonts.googleapis.com/css2?family=Kalam:wght@300;400;700&display=swap" rel="stylesheet" />
|
||||
<link
|
||||
href="https://fonts.googleapis.com/css2?family=Caveat:wght@400..700&family=Kalam:wght@300;400;700&family=Rubik+Mono+One&display=swap"
|
||||
rel="stylesheet" />
|
||||
<link href="https://fonts.googleapis.com/css2?family=Kalam:wght@300;400;700&family=Rubik+Mono+One&display=swap"
|
||||
rel="stylesheet" />
|
||||
<style>
|
||||
body {
|
||||
/* background: rgb(221, 208, 208); */
|
||||
/* background: #333; */
|
||||
font-family: 'Arial';
|
||||
/* font-size: 18px !important; */
|
||||
}
|
||||
|
||||
<style>
|
||||
body {
|
||||
/* background: rgb(221, 208, 208); */
|
||||
/* background: #333; */
|
||||
font-family: 'Arial';
|
||||
/* font-size: 18px !important; */
|
||||
}
|
||||
h1 {
|
||||
color: grey;
|
||||
}
|
||||
|
||||
h1 {
|
||||
color: grey;
|
||||
}
|
||||
.mermaid2 {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.mermaid2 {
|
||||
display: none;
|
||||
}
|
||||
.mermaid svg {
|
||||
/* font-size: 18px !important; */
|
||||
|
||||
.mermaid svg {
|
||||
/* font-size: 18px !important; */
|
||||
|
||||
/* background-color: #efefef;
|
||||
/* background-color: #efefef;
|
||||
background-image: radial-gradient(#fff 51%, transparent 91%),
|
||||
radial-gradient(#fff 51%, transparent 91%);
|
||||
background-size: 20px 20px;
|
||||
@ -42,19 +56,20 @@
|
||||
0 0,
|
||||
10px 10px;
|
||||
background-repeat: repeat; */
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
<body>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
flowchart
|
||||
|
||||
node_3@{ shape: triangle }@
|
||||
|
||||
|
||||
</pre>
|
||||
<pre id="diagram4" class="mermaid2">
|
||||
</pre
|
||||
>
|
||||
<pre id="diagram4" class="mermaid2">
|
||||
flowchart
|
||||
|
||||
A{"This is a label"}@{
|
||||
@ -73,51 +88,51 @@ flowchart
|
||||
icon: car
|
||||
}@ --> B
|
||||
A(This is a label)
|
||||
</pre>
|
||||
</pre
|
||||
>
|
||||
|
||||
<script type="module">
|
||||
import mermaid from './mermaid.esm.mjs';
|
||||
import { layouts } from './mermaid-layout-elk.esm.mjs';
|
||||
mermaid.registerLayoutLoaders(layouts);
|
||||
mermaid.parseError = function (err, hash) {
|
||||
console.error('Mermaid error: ', err);
|
||||
};
|
||||
window.callback = function () {
|
||||
alert('A callback was triggered');
|
||||
};
|
||||
mermaid.initialize({
|
||||
// theme: 'base',
|
||||
// handdrawnSeed: 12,
|
||||
look: 'classic',
|
||||
// 'elk.nodePlacement.strategy': 'NETWORK_SIMPLEX',
|
||||
'elk.nodePlacement.strategy': 'SIMPLE',
|
||||
// 'elk.nodePlacement.strategy': 'LAYERED',
|
||||
// 'elk.mergeEdges': true,
|
||||
// layout: 'dagre',
|
||||
layout: 'elk',
|
||||
// layout: 'fixed',
|
||||
// htmlLabels: false,
|
||||
flowchart: { titleTopMargin: 10, padding: 8 },
|
||||
// fontFamily: 'Caveat',
|
||||
fontFamily: 'Kalam',
|
||||
// fontFamily: 'courier',
|
||||
sequence: {
|
||||
actorFontFamily: 'courier',
|
||||
noteFontFamily: 'courier',
|
||||
messageFontFamily: 'courier',
|
||||
},
|
||||
fontSize: 12,
|
||||
logLevel: 0,
|
||||
securityLevel: 'loose',
|
||||
});
|
||||
function callback() {
|
||||
alert('It worked');
|
||||
}
|
||||
mermaid.parseError = function (err, hash) {
|
||||
console.error('In parse error:');
|
||||
console.error(err);
|
||||
};
|
||||
</script>
|
||||
</body>
|
||||
|
||||
</html>
|
||||
<script type="module">
|
||||
import mermaid from './mermaid.esm.mjs';
|
||||
import { layouts } from './mermaid-layout-elk.esm.mjs';
|
||||
mermaid.registerLayoutLoaders(layouts);
|
||||
mermaid.parseError = function (err, hash) {
|
||||
console.error('Mermaid error: ', err);
|
||||
};
|
||||
window.callback = function () {
|
||||
alert('A callback was triggered');
|
||||
};
|
||||
mermaid.initialize({
|
||||
// theme: 'base',
|
||||
// handdrawnSeed: 12,
|
||||
look: 'classic',
|
||||
// 'elk.nodePlacement.strategy': 'NETWORK_SIMPLEX',
|
||||
'elk.nodePlacement.strategy': 'SIMPLE',
|
||||
// 'elk.nodePlacement.strategy': 'LAYERED',
|
||||
// 'elk.mergeEdges': true,
|
||||
// layout: 'dagre',
|
||||
layout: 'elk',
|
||||
// layout: 'fixed',
|
||||
// htmlLabels: false,
|
||||
flowchart: { titleTopMargin: 10, padding: 8 },
|
||||
// fontFamily: 'Caveat',
|
||||
fontFamily: 'Kalam',
|
||||
// fontFamily: 'courier',
|
||||
sequence: {
|
||||
actorFontFamily: 'courier',
|
||||
noteFontFamily: 'courier',
|
||||
messageFontFamily: 'courier',
|
||||
},
|
||||
fontSize: 12,
|
||||
logLevel: 0,
|
||||
securityLevel: 'loose',
|
||||
});
|
||||
function callback() {
|
||||
alert('It worked');
|
||||
}
|
||||
mermaid.parseError = function (err, hash) {
|
||||
console.error('In parse error:');
|
||||
console.error(err);
|
||||
};
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
|
@ -63,12 +63,18 @@
|
||||
<body>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
flowchart
|
||||
A@{ shape: titledCylinder, label: "title" }@ --> B@{ shape: titledCylinder, label: "title B" }@
|
||||
|
||||
C@{ shape: titledCylinder, label: "title with very long text but on single line" }@ --> D@{ shape: titledCylinder, label: "title \n with \n multiple \n lines \n of n text" }@
|
||||
A --> D
|
||||
|
||||
|
||||
A
|
||||
B@{ shape: multiRect, label: "title aduwab whgdawhbd wajhdbawj" }@
|
||||
F@{ shape: multiRect, label: "title " }@
|
||||
G@{ shape: multiRect, label: "title \n duawd \n duawd \n duawd \n duawd" }@
|
||||
C
|
||||
D
|
||||
E
|
||||
C -->B
|
||||
B --> D
|
||||
B --> E
|
||||
F --> A
|
||||
A --> F
|
||||
</pre
|
||||
>
|
||||
|
||||
|
@ -115,7 +115,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
stateDiagram-v2
|
||||
stateId
|
||||
|
||||
@ -123,7 +123,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram3" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
stateId
|
||||
|
||||
@ -131,7 +131,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
stateId
|
||||
|
||||
@ -162,21 +162,21 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
stateDiagram-v2
|
||||
state "This is a state description" as s3
|
||||
</pre>
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram3" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
state "This is a state description" as s4
|
||||
</pre>
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
state "This is a state description" as s5
|
||||
</pre>
|
||||
@ -206,7 +206,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
stateDiagram-v2
|
||||
s22 : This is a state description
|
||||
|
||||
@ -214,7 +214,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram3" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
s23 : This is a state description
|
||||
|
||||
@ -222,7 +222,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
s24 : This is a state description
|
||||
|
||||
@ -258,7 +258,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
|
||||
stateDiagram-v2
|
||||
s41 --> s42
|
||||
@ -268,7 +268,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram3" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
s51 --> s52
|
||||
|
||||
@ -277,7 +277,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
s61 --> s62
|
||||
|
||||
@ -316,7 +316,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
|
||||
stateDiagram-v2
|
||||
a3 --> a4: A transition
|
||||
@ -326,7 +326,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram3" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
a5 --> a6: A transition
|
||||
|
||||
@ -335,7 +335,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
a7 --> a8: A transition
|
||||
|
||||
@ -376,7 +376,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
|
||||
stateDiagram-v2
|
||||
[*] --> test
|
||||
@ -387,7 +387,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram3" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
[*] --> test
|
||||
test --> [*]
|
||||
@ -397,7 +397,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
[*] --> test
|
||||
test --> [*]
|
||||
@ -445,7 +445,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
|
||||
stateDiagram-v2
|
||||
[*] --> First
|
||||
@ -459,7 +459,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram3" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
[*] --> First
|
||||
state First {
|
||||
@ -472,7 +472,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
[*] --> First
|
||||
state First {
|
||||
@ -547,7 +547,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
|
||||
stateDiagram-v2
|
||||
[*] --> Level1
|
||||
@ -572,7 +572,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram3" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
[*] --> Level1
|
||||
|
||||
@ -595,7 +595,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
[*] --> Level1
|
||||
|
||||
@ -676,7 +676,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
|
||||
stateDiagram-v2
|
||||
[*] --> B1
|
||||
@ -699,7 +699,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram3" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
[*] --> B1
|
||||
B1 --> B2
|
||||
@ -722,7 +722,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
[*] --> B1
|
||||
B1 --> B2
|
||||
@ -784,7 +784,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
|
||||
stateDiagram-v2
|
||||
state if_state <<choice>>
|
||||
@ -796,7 +796,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram3" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
state if_state <<choice>>
|
||||
[*] --> IsPositive
|
||||
@ -807,7 +807,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
state if_state <<choice>>
|
||||
[*] --> IsPositive
|
||||
@ -865,7 +865,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
stateDiagram-v2
|
||||
state fork_state <<fork>>
|
||||
[*] --> fork_state
|
||||
@ -882,7 +882,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram3" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
state fork_state <<fork>>
|
||||
[*] --> fork_state
|
||||
@ -899,7 +899,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
state fork_state <<fork>>
|
||||
[*] --> fork_state
|
||||
@ -955,7 +955,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
stateDiagram-v2
|
||||
TN3: The state with a note
|
||||
note right of TN3
|
||||
@ -968,7 +968,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram3" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
TN5: The state with a note
|
||||
note right of TN5
|
||||
@ -982,7 +982,7 @@ stateDiagram-v2
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
TN7: The state with a note
|
||||
note right of TN7
|
||||
@ -1052,7 +1052,7 @@ state Active {
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
stateDiagram-v2
|
||||
[*] --> Active
|
||||
|
||||
@ -1073,7 +1073,7 @@ state Active {
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram3" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
[*] --> Active
|
||||
|
||||
@ -1095,7 +1095,7 @@ state Active {
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
[*] --> Active
|
||||
|
||||
@ -1159,7 +1159,7 @@ direction LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram2" class="mermaid">
|
||||
%%{init: {"look": "handdrawn"} }%%
|
||||
%%{init: {"look": "handDrawn"} }%%
|
||||
stateDiagram-v2
|
||||
direction LR
|
||||
[*] --> D1
|
||||
@ -1174,7 +1174,7 @@ direction LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram3" class="mermaid">
|
||||
%%{init: {"handdrawn": false, "layout": "elk"} }%%
|
||||
%%{init: {"handDrawn": false, "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
direction LR
|
||||
[*] --> D1
|
||||
@ -1189,7 +1189,7 @@ direction LR
|
||||
</td>
|
||||
<td>
|
||||
<pre id="diagram4" class="mermaid">
|
||||
%%{init: {"look": "handdrawn", "layout": "elk"} }%%
|
||||
%%{init: {"look": "handDrawn", "layout": "elk"} }%%
|
||||
stateDiagram-v2
|
||||
direction LR
|
||||
[*] --> D1
|
||||
@ -1229,7 +1229,7 @@ direction LR
|
||||
};
|
||||
|
||||
mermaid.initialize({
|
||||
handdrawn: false,
|
||||
handDrawn: false,
|
||||
mergeEdges: true,
|
||||
layout: 'dagre',
|
||||
flowchart: { titleTopMargin: 10 },
|
||||
@ -1254,7 +1254,7 @@ direction LR
|
||||
|
||||
let coll = document.getElementsByClassName("collapsible");
|
||||
for (const element of coll) {
|
||||
element.addEventListener("click", function () {
|
||||
element.addEventListener("click", function () {
|
||||
this.classList.toggle("active");
|
||||
let content = this.nextElementSibling;
|
||||
if (content.style.maxHeight) {
|
||||
|
@ -9,7 +9,6 @@ function b64ToUtf8(str) {
|
||||
|
||||
// Adds a rendered flag to window when rendering is done, so cypress can wait for it.
|
||||
function markRendered() {
|
||||
console.log('Done rendering');
|
||||
if (window.Cypress) {
|
||||
window.rendered = true;
|
||||
}
|
||||
|
@ -210,11 +210,11 @@ If set to true, ignores legacyMathML.
|
||||
|
||||
---
|
||||
|
||||
### handdrawnSeed
|
||||
### handDrawnSeed
|
||||
|
||||
• `Optional` **handdrawnSeed**: `number`
|
||||
• `Optional` **handDrawnSeed**: `number`
|
||||
|
||||
Defines the seed to be used when using handdrawn look. This is important for the automated tests as they will always find differences without the seed. The default value is 0 which gives a random seed.
|
||||
Defines the seed to be used when using handDrawn look. This is important for the automated tests as they will always find differences without the seed. The default value is 0 which gives a random seed.
|
||||
|
||||
#### Defined in
|
||||
|
||||
@ -283,7 +283,7 @@ This option decides the amount of logging to be used by mermaid.
|
||||
|
||||
### look
|
||||
|
||||
• `Optional` **look**: `"classic"` | `"handdrawn"`
|
||||
• `Optional` **look**: `"classic"` | `"handDrawn"`
|
||||
|
||||
Defines which main look to use for the diagram.
|
||||
|
||||
@ -460,7 +460,7 @@ This is useful when you want to control how to handle syntax errors in your appl
|
||||
|
||||
### theme
|
||||
|
||||
• `Optional` **theme**: `"default"` | `"forest"` | `"dark"` | `"neutral"` | `"null"`
|
||||
• `Optional` **theme**: `"default"` | `"base"` | `"dark"` | `"forest"` | `"neutral"` | `"null"`
|
||||
|
||||
Theme, the CSS style sheet.
|
||||
You may also use `themeCSS` to override this value.
|
||||
|
@ -98,7 +98,7 @@
|
||||
"eslint-plugin-markdown": "^5.0.0",
|
||||
"eslint-plugin-no-only-tests": "^3.1.0",
|
||||
"eslint-plugin-tsdoc": "^0.3.0",
|
||||
"eslint-plugin-unicorn": "^54.0.0",
|
||||
"eslint-plugin-unicorn": "^55.0.0",
|
||||
"express": "^4.19.1",
|
||||
"globals": "^15.4.0",
|
||||
"globby": "^14.0.1",
|
||||
|
@ -620,7 +620,7 @@ export const render = async (data4Layout: LayoutData, svg, element, algorithm) =
|
||||
}
|
||||
if (endNode.isGroup) {
|
||||
const bbox = endNode.domId.node().getBBox();
|
||||
ew = Math.max(startNode.width, endNode.labels[0].width + endNode.padding);
|
||||
ew = Math.max(endNode.width, endNode.labels[0].width + endNode.padding);
|
||||
|
||||
log.debug(
|
||||
'UIO width',
|
||||
@ -638,10 +638,6 @@ export const render = async (data4Layout: LayoutData, svg, element, algorithm) =
|
||||
x: startNode.x + startNode.width / 2 + offset.x,
|
||||
y: startNode.y + startNode.height / 2 + offset.y,
|
||||
});
|
||||
edge.points.push({
|
||||
x: endNode.x + endNode.width / 2 + offset.x,
|
||||
y: endNode.y + endNode.height / 2 + offset.y,
|
||||
});
|
||||
}
|
||||
if (endNode.shape === 'diamond') {
|
||||
edge.points.push({
|
||||
@ -665,8 +661,8 @@ export const render = async (data4Layout: LayoutData, svg, element, algorithm) =
|
||||
edge.points = cutPathAtIntersect(
|
||||
edge.points,
|
||||
{
|
||||
x: endNode.x + ew / 2 + offset.x,
|
||||
y: endNode.y + endNode.height / 2 + offset.y,
|
||||
x: endNode.x + ew / 2 + endNode.offset.x,
|
||||
y: endNode.y + endNode.height / 2 + endNode.offset.y,
|
||||
width: ew,
|
||||
height: endNode.height,
|
||||
padding: endNode.padding,
|
||||
|
@ -61,19 +61,19 @@ export interface MermaidConfig {
|
||||
* You may also use `themeCSS` to override this value.
|
||||
*
|
||||
*/
|
||||
theme?: 'default' | 'forest' | 'dark' | 'neutral' | 'null';
|
||||
theme?: 'default' | 'base' | 'dark' | 'forest' | 'neutral' | 'null';
|
||||
themeVariables?: any;
|
||||
themeCSS?: string;
|
||||
/**
|
||||
* Defines which main look to use for the diagram.
|
||||
*
|
||||
*/
|
||||
look?: 'classic' | 'handdrawn';
|
||||
look?: 'classic' | 'handDrawn';
|
||||
/**
|
||||
* Defines the seed to be used when using handdrawn look. This is important for the automated tests as they will always find differences without the seed. The default value is 0 which gives a random seed.
|
||||
* Defines the seed to be used when using handDrawn look. This is important for the automated tests as they will always find differences without the seed. The default value is 0 which gives a random seed.
|
||||
*
|
||||
*/
|
||||
handdrawnSeed?: number;
|
||||
handDrawnSeed?: number;
|
||||
/**
|
||||
* Defines which layout algorithm to use for rendering the diagram.
|
||||
*
|
||||
|
@ -8,13 +8,6 @@ import type { BlockDB } from './blockDB.js';
|
||||
import { layout } from './layout.js';
|
||||
import { calculateBlockSizes, insertBlocks, insertEdges } from './renderHelpers.js';
|
||||
|
||||
/**
|
||||
* Returns the all the styles from classDef statements in the graph definition.
|
||||
*
|
||||
* @param text - The text with the classes
|
||||
* @param diagObj - The diagram object
|
||||
* @returns ClassDef - The styles
|
||||
*/
|
||||
export const getClasses = function (text: any, diagObj: any) {
|
||||
return diagObj.db.getClasses();
|
||||
};
|
||||
@ -45,8 +38,6 @@ export const draw = async function (
|
||||
const markers = ['point', 'circle', 'cross'];
|
||||
|
||||
// Add the marker definitions to the svg as marker tags
|
||||
// insertMarkers(svg, markers, diagObj.type, diagObj.arrowMarkerAbsolute);
|
||||
// insertMarkers(svg, markers, diagObj.type, true);
|
||||
insertMarkers(svg, markers, diagObj.type, id);
|
||||
|
||||
const bl = db.getBlocks();
|
||||
@ -59,11 +50,7 @@ export const draw = async function (
|
||||
await insertBlocks(nodes, bl, db);
|
||||
await insertEdges(nodes, edges, blArr, db, id);
|
||||
|
||||
// log.debug('Here', bl);
|
||||
|
||||
// Establish svg dimensions and get width and height
|
||||
//
|
||||
// const bounds2 = nodes.node().getBoundingClientRect();
|
||||
// Why, oh why ????
|
||||
if (bounds) {
|
||||
const bounds2 = bounds;
|
||||
|
@ -64,7 +64,7 @@ export const addVertex = function (
|
||||
props = {},
|
||||
shapeData: any
|
||||
) {
|
||||
console.log('addVertex', id, shapeData);
|
||||
// console.log('addVertex', id, shapeData);
|
||||
if (!id || id.trim().length === 0) {
|
||||
return;
|
||||
}
|
||||
@ -124,10 +124,10 @@ export const addVertex = function (
|
||||
// detect if shapeData contains a newline character
|
||||
|
||||
if (!shapeData.includes('\n')) {
|
||||
console.log('yamlData shapeData has no new lines', shapeData);
|
||||
// console.log('yamlData shapeData has no new lines', shapeData);
|
||||
yamlData = '{\n' + shapeData + '\n';
|
||||
} else {
|
||||
console.log('yamlData shapeData has new lines', shapeData);
|
||||
// console.log('yamlData shapeData has new lines', shapeData);
|
||||
yamlData = shapeData + '\n';
|
||||
// Find the position of the last } and replace it with a newline
|
||||
const lastPos = yamlData.lastIndexOf('}');
|
||||
@ -136,9 +136,9 @@ export const addVertex = function (
|
||||
}
|
||||
}
|
||||
|
||||
console.log('yamlData', yamlData);
|
||||
// console.log('yamlData', yamlData);
|
||||
const doc = yaml.load(yamlData, { schema: yaml.JSON_SCHEMA });
|
||||
console.log('yamlData doc', doc);
|
||||
// console.log('yamlData doc', doc);
|
||||
if (doc?.shape) {
|
||||
//check if shape has a trailing `,` and remove it
|
||||
if (doc.shape.endsWith(',')) {
|
||||
|
@ -1,7 +1,7 @@
|
||||
// @ts-ignore: JISON doesn't support types
|
||||
import flowParser from './parser/flow.jison';
|
||||
import flowDb from './flowDb.js';
|
||||
import flowRendererV3 from './flowRenderer-v3-unified.js';
|
||||
import renderer from './flowRenderer-v3-unified.js';
|
||||
import flowStyles from './styles.js';
|
||||
import type { MermaidConfig } from '../../config.type.js';
|
||||
import { setConfig } from '../../diagram-api/diagramAPI.js';
|
||||
@ -9,7 +9,7 @@ import { setConfig } from '../../diagram-api/diagramAPI.js';
|
||||
export const diagram = {
|
||||
parser: flowParser,
|
||||
db: flowDb,
|
||||
renderer: flowRendererV3,
|
||||
renderer,
|
||||
styles: flowStyles,
|
||||
init: (cnf: MermaidConfig) => {
|
||||
if (!cnf.flowchart) {
|
||||
|
@ -1,24 +1,23 @@
|
||||
// @ts-ignore: JISON doesn't support types
|
||||
import flowParser from './parser/flow.jison';
|
||||
import flowDb from './flowDb.js';
|
||||
import flowRenderer from './flowRenderer.js';
|
||||
import flowRendererV2 from './flowRenderer-v2.js';
|
||||
import renderer from './flowRenderer-v3-unified.js';
|
||||
import flowStyles from './styles.js';
|
||||
import type { MermaidConfig } from '../../config.type.js';
|
||||
import { setConfig } from '../../diagram-api/diagramAPI.js';
|
||||
|
||||
export const diagram = {
|
||||
parser: flowParser,
|
||||
db: flowDb,
|
||||
renderer: flowRendererV2,
|
||||
renderer,
|
||||
styles: flowStyles,
|
||||
init: (cnf: MermaidConfig) => {
|
||||
if (!cnf.flowchart) {
|
||||
cnf.flowchart = {};
|
||||
}
|
||||
// TODO, broken as of 2022-09-14 (13809b50251845475e6dca65cc395761be38fbd2)
|
||||
cnf.flowchart.arrowMarkerAbsolute = cnf.arrowMarkerAbsolute;
|
||||
flowRenderer.setConf(cnf.flowchart);
|
||||
setConfig({ flowchart: { arrowMarkerAbsolute: cnf.arrowMarkerAbsolute } });
|
||||
flowDb.clear();
|
||||
flowDb.setGen('gen-1');
|
||||
flowDb.setGen('gen-2');
|
||||
},
|
||||
};
|
||||
|
@ -1,515 +0,0 @@
|
||||
import * as graphlib from 'dagre-d3-es/src/graphlib/index.js';
|
||||
import { select, curveLinear, selectAll } from 'd3';
|
||||
import { getConfig } from '../../diagram-api/diagramAPI.js';
|
||||
import utils, { getEdgeId } from '../../utils.js';
|
||||
import { render } from '../../dagre-wrapper/index.js';
|
||||
import { addHtmlLabel } from 'dagre-d3-es/src/dagre-js/label/add-html-label.js';
|
||||
import { log } from '../../logger.js';
|
||||
import common, { evaluate, renderKatex } from '../common/common.js';
|
||||
import { interpolateToCurve, getStylesFromArray } from '../../utils.js';
|
||||
import { setupGraphViewbox } from '../../setupGraphViewbox.js';
|
||||
|
||||
const conf = {};
|
||||
export const setConf = function (cnf) {
|
||||
const keys = Object.keys(cnf);
|
||||
for (const key of keys) {
|
||||
conf[key] = cnf[key];
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Function that adds the vertices found during parsing to the graph to be rendered.
|
||||
*
|
||||
* @param vert Object containing the vertices.
|
||||
* @param g The graph that is to be drawn.
|
||||
* @param svgId
|
||||
* @param root
|
||||
* @param doc
|
||||
* @param diagObj
|
||||
*/
|
||||
export const addVertices = async function (vert, g, svgId, root, doc, diagObj) {
|
||||
const svg = root.select(`[id="${svgId}"]`);
|
||||
|
||||
const keys = vert.keys();
|
||||
|
||||
// Iterate through each item in the vertex object (containing all the vertices found) in the graph definition
|
||||
for (const id of keys) {
|
||||
const vertex = vert.get(id);
|
||||
|
||||
/**
|
||||
* Variable for storing the classes for the vertex
|
||||
*
|
||||
* @type {string}
|
||||
*/
|
||||
let classStr = 'default';
|
||||
if (vertex.classes.length > 0) {
|
||||
classStr = vertex.classes.join(' ');
|
||||
}
|
||||
classStr = classStr + ' flowchart-label';
|
||||
const styles = getStylesFromArray(vertex.styles);
|
||||
|
||||
// Use vertex id as text in the box if no text is provided by the graph definition
|
||||
let vertexText = vertex.text !== undefined ? vertex.text : vertex.id;
|
||||
|
||||
// We create a SVG label, either by delegating to addHtmlLabel or manually
|
||||
let vertexNode;
|
||||
log.info('vertex', vertex, vertex.labelType);
|
||||
if (vertex.labelType === 'markdown') {
|
||||
log.info('vertex', vertex, vertex.labelType);
|
||||
} else {
|
||||
if (evaluate(getConfig().flowchart.htmlLabels)) {
|
||||
// TODO: addHtmlLabel accepts a labelStyle. Do we possibly have that?
|
||||
const node = {
|
||||
label: vertexText,
|
||||
};
|
||||
vertexNode = addHtmlLabel(svg, node).node();
|
||||
vertexNode.parentNode.removeChild(vertexNode);
|
||||
} else {
|
||||
const svgLabel = doc.createElementNS('http://www.w3.org/2000/svg', 'text');
|
||||
svgLabel.setAttribute('style', styles.labelStyle.replace('color:', 'fill:'));
|
||||
|
||||
const rows = vertexText.split(common.lineBreakRegex);
|
||||
|
||||
for (const row of rows) {
|
||||
const tspan = doc.createElementNS('http://www.w3.org/2000/svg', 'tspan');
|
||||
tspan.setAttributeNS('http://www.w3.org/XML/1998/namespace', 'xml:space', 'preserve');
|
||||
tspan.setAttribute('dy', '1em');
|
||||
tspan.setAttribute('x', '1');
|
||||
tspan.textContent = row;
|
||||
svgLabel.appendChild(tspan);
|
||||
}
|
||||
vertexNode = svgLabel;
|
||||
}
|
||||
}
|
||||
|
||||
let radius = 0;
|
||||
let _shape = '';
|
||||
// Set the shape based parameters
|
||||
switch (vertex.type) {
|
||||
case 'round':
|
||||
radius = 5;
|
||||
_shape = 'rect';
|
||||
break;
|
||||
case 'square':
|
||||
_shape = 'rect';
|
||||
break;
|
||||
case 'diamond':
|
||||
_shape = 'question';
|
||||
break;
|
||||
case 'hexagon':
|
||||
_shape = 'hexagon';
|
||||
break;
|
||||
case 'odd':
|
||||
_shape = 'rect_left_inv_arrow';
|
||||
break;
|
||||
case 'lean_right':
|
||||
_shape = 'lean_right';
|
||||
break;
|
||||
case 'lean_left':
|
||||
_shape = 'lean_left';
|
||||
break;
|
||||
case 'trapezoid':
|
||||
_shape = 'trapezoid';
|
||||
break;
|
||||
case 'inv_trapezoid':
|
||||
_shape = 'inv_trapezoid';
|
||||
break;
|
||||
case 'odd_right':
|
||||
_shape = 'rect_left_inv_arrow';
|
||||
break;
|
||||
case 'circle':
|
||||
_shape = 'circle';
|
||||
break;
|
||||
case 'ellipse':
|
||||
_shape = 'ellipse';
|
||||
break;
|
||||
case 'stadium':
|
||||
_shape = 'stadium';
|
||||
break;
|
||||
case 'subroutine':
|
||||
_shape = 'subroutine';
|
||||
break;
|
||||
case 'cylinder':
|
||||
_shape = 'cylinder';
|
||||
break;
|
||||
case 'group':
|
||||
_shape = 'rect';
|
||||
break;
|
||||
case 'doublecircle':
|
||||
_shape = 'doublecircle';
|
||||
break;
|
||||
default:
|
||||
_shape = 'rect';
|
||||
}
|
||||
const labelText = await renderKatex(vertexText, getConfig());
|
||||
|
||||
// Add the node
|
||||
g.setNode(vertex.id, {
|
||||
labelStyle: styles.labelStyle,
|
||||
shape: _shape,
|
||||
labelText,
|
||||
labelType: vertex.labelType,
|
||||
rx: radius,
|
||||
ry: radius,
|
||||
class: classStr,
|
||||
style: styles.style,
|
||||
id: vertex.id,
|
||||
link: vertex.link,
|
||||
linkTarget: vertex.linkTarget,
|
||||
tooltip: diagObj.db.getTooltip(vertex.id) || '',
|
||||
domId: diagObj.db.lookUpDomId(vertex.id),
|
||||
haveCallback: vertex.haveCallback,
|
||||
width: vertex.type === 'group' ? 500 : undefined,
|
||||
dir: vertex.dir,
|
||||
type: vertex.type,
|
||||
props: vertex.props,
|
||||
padding: getConfig().flowchart.padding,
|
||||
});
|
||||
|
||||
log.info('setNode', {
|
||||
labelStyle: styles.labelStyle,
|
||||
labelType: vertex.labelType,
|
||||
shape: _shape,
|
||||
labelText,
|
||||
rx: radius,
|
||||
ry: radius,
|
||||
class: classStr,
|
||||
style: styles.style,
|
||||
id: vertex.id,
|
||||
domId: diagObj.db.lookUpDomId(vertex.id),
|
||||
width: vertex.type === 'group' ? 500 : undefined,
|
||||
type: vertex.type,
|
||||
dir: vertex.dir,
|
||||
props: vertex.props,
|
||||
padding: getConfig().flowchart.padding,
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Add edges to graph based on parsed graph definition
|
||||
*
|
||||
* @param {object} edges The edges to add to the graph
|
||||
* @param {object} g The graph object
|
||||
*/
|
||||
export const addEdges = async function (edges, g) {
|
||||
log.info('abc78 edges = ', edges);
|
||||
let cnt = 0;
|
||||
let linkIdCnt = {};
|
||||
|
||||
let defaultStyle;
|
||||
let defaultLabelStyle;
|
||||
|
||||
if (edges.defaultStyle !== undefined) {
|
||||
const defaultStyles = getStylesFromArray(edges.defaultStyle);
|
||||
defaultStyle = defaultStyles.style;
|
||||
defaultLabelStyle = defaultStyles.labelStyle;
|
||||
}
|
||||
|
||||
for (const edge of edges) {
|
||||
cnt++;
|
||||
|
||||
// Identify Link
|
||||
const linkIdBase = getEdgeId(edge.start, edge.end, {
|
||||
counter: cnt,
|
||||
prefix: 'L',
|
||||
});
|
||||
|
||||
// count the links from+to the same node to give unique id
|
||||
if (linkIdCnt[linkIdBase] === undefined) {
|
||||
linkIdCnt[linkIdBase] = 0;
|
||||
log.info('abc78 new entry', linkIdBase, linkIdCnt[linkIdBase]);
|
||||
} else {
|
||||
linkIdCnt[linkIdBase]++;
|
||||
log.info('abc78 new entry', linkIdBase, linkIdCnt[linkIdBase]);
|
||||
}
|
||||
let linkId = `${linkIdBase}_${linkIdCnt[linkIdBase]}`;
|
||||
|
||||
log.info('abc78 new link id to be used is', linkIdBase, linkId, linkIdCnt[linkIdBase]);
|
||||
const linkNameStart = 'LS-' + edge.start;
|
||||
const linkNameEnd = 'LE-' + edge.end;
|
||||
|
||||
const edgeData = { style: '', labelStyle: '' };
|
||||
edgeData.minlen = edge.length || 1;
|
||||
//edgeData.id = 'id' + cnt;
|
||||
|
||||
// Set link type for rendering
|
||||
if (edge.type === 'arrow_open') {
|
||||
edgeData.arrowhead = 'none';
|
||||
} else {
|
||||
edgeData.arrowhead = 'normal';
|
||||
}
|
||||
|
||||
// Check of arrow types, placed here in order not to break old rendering
|
||||
edgeData.arrowTypeStart = 'arrow_open';
|
||||
edgeData.arrowTypeEnd = 'arrow_open';
|
||||
|
||||
/* eslint-disable no-fallthrough */
|
||||
switch (edge.type) {
|
||||
case 'double_arrow_cross':
|
||||
edgeData.arrowTypeStart = 'arrow_cross';
|
||||
case 'arrow_cross':
|
||||
edgeData.arrowTypeEnd = 'arrow_cross';
|
||||
break;
|
||||
case 'double_arrow_point':
|
||||
edgeData.arrowTypeStart = 'arrow_point';
|
||||
case 'arrow_point':
|
||||
edgeData.arrowTypeEnd = 'arrow_point';
|
||||
break;
|
||||
case 'double_arrow_circle':
|
||||
edgeData.arrowTypeStart = 'arrow_circle';
|
||||
case 'arrow_circle':
|
||||
edgeData.arrowTypeEnd = 'arrow_circle';
|
||||
break;
|
||||
}
|
||||
|
||||
let style = '';
|
||||
let labelStyle = '';
|
||||
|
||||
switch (edge.stroke) {
|
||||
case 'normal':
|
||||
style = 'fill:none;';
|
||||
if (defaultStyle !== undefined) {
|
||||
style = defaultStyle;
|
||||
}
|
||||
if (defaultLabelStyle !== undefined) {
|
||||
labelStyle = defaultLabelStyle;
|
||||
}
|
||||
edgeData.thickness = 'normal';
|
||||
edgeData.pattern = 'solid';
|
||||
break;
|
||||
case 'dotted':
|
||||
edgeData.thickness = 'normal';
|
||||
edgeData.pattern = 'dotted';
|
||||
edgeData.style = 'fill:none;stroke-width:2px;stroke-dasharray:3;';
|
||||
break;
|
||||
case 'thick':
|
||||
edgeData.thickness = 'thick';
|
||||
edgeData.pattern = 'solid';
|
||||
edgeData.style = 'stroke-width: 3.5px;fill:none;';
|
||||
break;
|
||||
case 'invisible':
|
||||
edgeData.thickness = 'invisible';
|
||||
edgeData.pattern = 'solid';
|
||||
edgeData.style = 'stroke-width: 0;fill:none;';
|
||||
break;
|
||||
}
|
||||
if (edge.style !== undefined) {
|
||||
const styles = getStylesFromArray(edge.style);
|
||||
style = styles.style;
|
||||
labelStyle = styles.labelStyle;
|
||||
}
|
||||
|
||||
edgeData.style = edgeData.style += style;
|
||||
edgeData.labelStyle = edgeData.labelStyle += labelStyle;
|
||||
|
||||
if (edge.interpolate !== undefined) {
|
||||
edgeData.curve = interpolateToCurve(edge.interpolate, curveLinear);
|
||||
} else if (edges.defaultInterpolate !== undefined) {
|
||||
edgeData.curve = interpolateToCurve(edges.defaultInterpolate, curveLinear);
|
||||
} else {
|
||||
edgeData.curve = interpolateToCurve(conf.curve, curveLinear);
|
||||
}
|
||||
|
||||
if (edge.text === undefined) {
|
||||
if (edge.style !== undefined) {
|
||||
edgeData.arrowheadStyle = 'fill: #333';
|
||||
}
|
||||
} else {
|
||||
edgeData.arrowheadStyle = 'fill: #333';
|
||||
edgeData.labelpos = 'c';
|
||||
}
|
||||
edgeData.labelType = edge.labelType;
|
||||
edgeData.label = await renderKatex(edge.text.replace(common.lineBreakRegex, '\n'), getConfig());
|
||||
|
||||
if (edge.style === undefined) {
|
||||
edgeData.style = edgeData.style || 'stroke: #333; stroke-width: 1.5px;fill:none;';
|
||||
}
|
||||
|
||||
edgeData.labelStyle = edgeData.labelStyle.replace('color:', 'fill:');
|
||||
|
||||
edgeData.id = linkId;
|
||||
edgeData.classes = 'flowchart-link ' + linkNameStart + ' ' + linkNameEnd;
|
||||
|
||||
// Add the edge to the graph
|
||||
g.setEdge(edge.start, edge.end, edgeData, cnt);
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Returns the all the styles from classDef statements in the graph definition.
|
||||
*
|
||||
* @param text
|
||||
* @param diagObj
|
||||
* @returns {Map<string, import('../../diagram-api/types.js').DiagramStyleClassDef>} ClassDef styles
|
||||
*/
|
||||
export const getClasses = function (text, diagObj) {
|
||||
return diagObj.db.getClasses();
|
||||
};
|
||||
|
||||
/**
|
||||
* Draws a flowchart in the tag with id: id based on the graph definition in text.
|
||||
*
|
||||
* @param text
|
||||
* @param id
|
||||
* @param _version
|
||||
* @param diagObj
|
||||
*/
|
||||
|
||||
export const draw = async function (text, id, _version, diagObj) {
|
||||
log.info('Drawing flowchart');
|
||||
|
||||
// Fetch the default direction, use TD if none was found
|
||||
let dir = diagObj.db.getDirection();
|
||||
if (dir === undefined) {
|
||||
dir = 'TD';
|
||||
}
|
||||
|
||||
const { securityLevel, flowchart: conf } = getConfig();
|
||||
const nodeSpacing = conf.nodeSpacing ?? 50;
|
||||
const rankSpacing = conf.rankSpacing ?? 50;
|
||||
|
||||
// Handle root and document for when rendering in sandbox mode
|
||||
let sandboxElement;
|
||||
if (securityLevel === 'sandbox') {
|
||||
sandboxElement = select('#i' + id);
|
||||
}
|
||||
const root =
|
||||
securityLevel === 'sandbox'
|
||||
? select(sandboxElement.nodes()[0].contentDocument.body)
|
||||
: select('body');
|
||||
const doc = securityLevel === 'sandbox' ? sandboxElement.nodes()[0].contentDocument : document;
|
||||
|
||||
// Create the input mermaid.graph
|
||||
const g = new graphlib.Graph({
|
||||
multigraph: true,
|
||||
compound: true,
|
||||
})
|
||||
.setGraph({
|
||||
rankdir: dir,
|
||||
nodesep: nodeSpacing,
|
||||
ranksep: rankSpacing,
|
||||
marginx: 0,
|
||||
marginy: 0,
|
||||
})
|
||||
.setDefaultEdgeLabel(function () {
|
||||
return {};
|
||||
});
|
||||
|
||||
let subG;
|
||||
const subGraphs = diagObj.db.getSubGraphs();
|
||||
log.info('Subgraphs - ', subGraphs);
|
||||
for (let i = subGraphs.length - 1; i >= 0; i--) {
|
||||
subG = subGraphs[i];
|
||||
log.info('Subgraph - ', subG);
|
||||
diagObj.db.addVertex(
|
||||
subG.id,
|
||||
{ text: subG.title, type: subG.labelType },
|
||||
'group',
|
||||
undefined,
|
||||
subG.classes,
|
||||
subG.dir
|
||||
);
|
||||
}
|
||||
|
||||
// Fetch the vertices/nodes and edges/links from the parsed graph definition
|
||||
const vert = diagObj.db.getVertices();
|
||||
|
||||
const edges = diagObj.db.getEdges();
|
||||
|
||||
log.info('Edges', edges);
|
||||
let i = 0;
|
||||
for (i = subGraphs.length - 1; i >= 0; i--) {
|
||||
subG = subGraphs[i];
|
||||
|
||||
selectAll('cluster').append('text');
|
||||
|
||||
for (const node of subG.nodes) {
|
||||
log.info('Setting up subgraphs', node, subG.id);
|
||||
g.setParent(node, subG.id);
|
||||
}
|
||||
}
|
||||
await addVertices(vert, g, id, root, doc, diagObj);
|
||||
await addEdges(edges, g, diagObj);
|
||||
|
||||
// Add custom shapes
|
||||
// flowChartShapes.addToRenderV2(addShape);
|
||||
|
||||
// Set up an SVG group so that we can translate the final graph.
|
||||
const svg = root.select(`[id="${id}"]`);
|
||||
|
||||
// Run the renderer. This is what draws the final graph.
|
||||
const element = root.select('#' + id + ' g');
|
||||
await render(element, g, ['point', 'circle', 'cross'], 'flowchart', id);
|
||||
|
||||
utils.insertTitle(svg, 'flowchartTitleText', conf.titleTopMargin, diagObj.db.getDiagramTitle());
|
||||
|
||||
setupGraphViewbox(g, svg, conf.diagramPadding, conf.useMaxWidth);
|
||||
|
||||
// Index nodes
|
||||
diagObj.db.indexNodes('subGraph' + i);
|
||||
|
||||
// Add label rects for non html labels
|
||||
if (!conf.htmlLabels) {
|
||||
const labels = doc.querySelectorAll('[id="' + id + '"] .edgeLabel .label');
|
||||
for (const label of labels) {
|
||||
// Get dimensions of label
|
||||
const dim = label.getBBox();
|
||||
|
||||
const rect = doc.createElementNS('http://www.w3.org/2000/svg', 'rect');
|
||||
rect.setAttribute('rx', 0);
|
||||
rect.setAttribute('ry', 0);
|
||||
rect.setAttribute('width', dim.width);
|
||||
rect.setAttribute('height', dim.height);
|
||||
|
||||
label.insertBefore(rect, label.firstChild);
|
||||
}
|
||||
}
|
||||
|
||||
// If node has a link, wrap it in an anchor SVG object.
|
||||
const keys = [...vert.keys()];
|
||||
keys.forEach((key) => {
|
||||
const vertex = vert.get(key);
|
||||
|
||||
if (vertex.link) {
|
||||
const node = select('#' + id + ' [id="' + key + '"]');
|
||||
if (node) {
|
||||
const link = doc.createElementNS('http://www.w3.org/2000/svg', 'a');
|
||||
link.setAttributeNS('http://www.w3.org/2000/svg', 'class', vertex.classes.join(' '));
|
||||
link.setAttributeNS('http://www.w3.org/2000/svg', 'href', vertex.link);
|
||||
link.setAttributeNS('http://www.w3.org/2000/svg', 'rel', 'noopener');
|
||||
if (securityLevel === 'sandbox') {
|
||||
link.setAttributeNS('http://www.w3.org/2000/svg', 'target', '_top');
|
||||
} else if (vertex.linkTarget) {
|
||||
link.setAttributeNS('http://www.w3.org/2000/svg', 'target', vertex.linkTarget);
|
||||
}
|
||||
|
||||
const linkNode = node.insert(function () {
|
||||
return link;
|
||||
}, ':first-child');
|
||||
|
||||
const shape = node.select('.label-container');
|
||||
if (shape) {
|
||||
linkNode.append(function () {
|
||||
return shape.node();
|
||||
});
|
||||
}
|
||||
|
||||
const label = node.select('.label');
|
||||
if (label) {
|
||||
linkNode.append(function () {
|
||||
return label.node();
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
export default {
|
||||
setConf,
|
||||
addVertices,
|
||||
addEdges,
|
||||
getClasses,
|
||||
draw,
|
||||
};
|
@ -1,150 +0,0 @@
|
||||
import flowDb from './flowDb.js';
|
||||
import { parser } from './parser/flow.jison';
|
||||
import flowRenderer from './flowRenderer.js';
|
||||
import { addDiagrams } from '../../diagram-api/diagram-orchestration.js';
|
||||
|
||||
const diag = {
|
||||
db: flowDb,
|
||||
};
|
||||
addDiagrams();
|
||||
|
||||
describe('when using mermaid and ', function () {
|
||||
describe('when calling addEdges ', function () {
|
||||
beforeEach(function () {
|
||||
parser.yy = flowDb;
|
||||
flowDb.clear();
|
||||
flowDb.setGen('gen-2');
|
||||
});
|
||||
it('should handle edges with text', async () => {
|
||||
parser.parse('graph TD;A-->|text ex|B;');
|
||||
flowDb.getVertices();
|
||||
const edges = flowDb.getEdges();
|
||||
|
||||
const mockG = {
|
||||
setEdge: function (start, end, options) {
|
||||
expect(start).toContain('flowchart-A-');
|
||||
expect(end).toContain('flowchart-B-');
|
||||
expect(options.arrowhead).toBe('normal');
|
||||
expect(options.label.match('text ex')).toBeTruthy();
|
||||
},
|
||||
};
|
||||
|
||||
await flowRenderer.addEdges(edges, mockG, diag);
|
||||
});
|
||||
|
||||
it('should handle edges without text', async function () {
|
||||
parser.parse('graph TD;A-->B;');
|
||||
flowDb.getVertices();
|
||||
const edges = flowDb.getEdges();
|
||||
|
||||
const mockG = {
|
||||
setEdge: function (start, end, options) {
|
||||
expect(start).toContain('flowchart-A-');
|
||||
expect(end).toContain('flowchart-B-');
|
||||
expect(options.arrowhead).toBe('normal');
|
||||
},
|
||||
};
|
||||
|
||||
await flowRenderer.addEdges(edges, mockG, diag);
|
||||
});
|
||||
|
||||
it('should handle open-ended edges', async () => {
|
||||
parser.parse('graph TD;A---B;');
|
||||
flowDb.getVertices();
|
||||
const edges = flowDb.getEdges();
|
||||
|
||||
const mockG = {
|
||||
setEdge: function (start, end, options) {
|
||||
expect(start).toContain('flowchart-A-');
|
||||
expect(end).toContain('flowchart-B-');
|
||||
expect(options.arrowhead).toBe('none');
|
||||
},
|
||||
};
|
||||
|
||||
await flowRenderer.addEdges(edges, mockG, diag);
|
||||
});
|
||||
|
||||
it('should handle edges with styles defined', async () => {
|
||||
parser.parse('graph TD;A---B; linkStyle 0 stroke:val1,stroke-width:val2;');
|
||||
flowDb.getVertices();
|
||||
const edges = flowDb.getEdges();
|
||||
|
||||
const mockG = {
|
||||
setEdge: function (start, end, options) {
|
||||
expect(start).toContain('flowchart-A-');
|
||||
expect(end).toContain('flowchart-B-');
|
||||
expect(options.arrowhead).toBe('none');
|
||||
expect(options.style).toBe('stroke:val1;stroke-width:val2;fill:none;');
|
||||
},
|
||||
};
|
||||
|
||||
await flowRenderer.addEdges(edges, mockG, diag);
|
||||
});
|
||||
it('should handle edges with interpolation defined', async () => {
|
||||
parser.parse('graph TD;A---B; linkStyle 0 interpolate basis');
|
||||
flowDb.getVertices();
|
||||
const edges = flowDb.getEdges();
|
||||
|
||||
const mockG = {
|
||||
setEdge: function (start, end, options) {
|
||||
expect(start).toContain('flowchart-A-');
|
||||
expect(end).toContain('flowchart-B-');
|
||||
expect(options.arrowhead).toBe('none');
|
||||
expect(options.curve).toBe('basis'); // mocked as string
|
||||
},
|
||||
};
|
||||
|
||||
await flowRenderer.addEdges(edges, mockG, diag);
|
||||
});
|
||||
it('should handle edges with text and styles defined', async () => {
|
||||
parser.parse('graph TD;A---|the text|B; linkStyle 0 stroke:val1,stroke-width:val2;');
|
||||
flowDb.getVertices();
|
||||
const edges = flowDb.getEdges();
|
||||
|
||||
const mockG = {
|
||||
setEdge: function (start, end, options) {
|
||||
expect(start).toContain('flowchart-A-');
|
||||
expect(end).toContain('flowchart-B-');
|
||||
expect(options.arrowhead).toBe('none');
|
||||
expect(options.label.match('the text')).toBeTruthy();
|
||||
expect(options.style).toBe('stroke:val1;stroke-width:val2;fill:none;');
|
||||
},
|
||||
};
|
||||
|
||||
await flowRenderer.addEdges(edges, mockG, diag);
|
||||
});
|
||||
|
||||
it('should set fill to "none" by default when handling edges', async () => {
|
||||
parser.parse('graph TD;A---B; linkStyle 0 stroke:val1,stroke-width:val2;');
|
||||
flowDb.getVertices();
|
||||
const edges = flowDb.getEdges();
|
||||
|
||||
const mockG = {
|
||||
setEdge: function (start, end, options) {
|
||||
expect(start).toContain('flowchart-A-');
|
||||
expect(end).toContain('flowchart-B');
|
||||
expect(options.arrowhead).toBe('none');
|
||||
expect(options.style).toBe('stroke:val1;stroke-width:val2;fill:none;');
|
||||
},
|
||||
};
|
||||
|
||||
await flowRenderer.addEdges(edges, mockG, diag);
|
||||
});
|
||||
|
||||
it('should not set fill to none if fill is set in linkStyle', async () => {
|
||||
parser.parse('graph TD;A---B; linkStyle 0 stroke:val1,stroke-width:val2,fill:blue;');
|
||||
flowDb.getVertices();
|
||||
const edges = flowDb.getEdges();
|
||||
const mockG = {
|
||||
setEdge: function (start, end, options) {
|
||||
expect(start).toContain('flowchart-A-');
|
||||
expect(end).toContain('flowchart-B-');
|
||||
expect(options.arrowhead).toBe('none');
|
||||
expect(options.style).toBe('stroke:val1;stroke-width:val2;fill:blue;');
|
||||
},
|
||||
};
|
||||
|
||||
await flowRenderer.addEdges(edges, mockG, diag);
|
||||
});
|
||||
});
|
||||
});
|
@ -1,503 +0,0 @@
|
||||
import * as graphlib from 'dagre-d3-es/src/graphlib/index.js';
|
||||
import { select, curveLinear, selectAll } from 'd3';
|
||||
import { getConfig } from '../../diagram-api/diagramAPI.js';
|
||||
import { render as Render } from 'dagre-d3-es';
|
||||
import { applyStyle } from 'dagre-d3-es/src/dagre-js/util.js';
|
||||
import { addHtmlLabel } from 'dagre-d3-es/src/dagre-js/label/add-html-label.js';
|
||||
import { log } from '../../logger.js';
|
||||
import common, { evaluate, renderKatex } from '../common/common.js';
|
||||
import { interpolateToCurve, getStylesFromArray, getEdgeId } from '../../utils.js';
|
||||
import { setupGraphViewbox } from '../../setupGraphViewbox.js';
|
||||
import flowChartShapes from './flowChartShapes.js';
|
||||
import { replaceIconSubstring } from '../../rendering-util/createText.js';
|
||||
|
||||
const conf = {};
|
||||
export const setConf = function (cnf) {
|
||||
const keys = Object.keys(cnf);
|
||||
for (const key of keys) {
|
||||
conf[key] = cnf[key];
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Function that adds the vertices found in the graph definition to the graph to be rendered.
|
||||
*
|
||||
* @param vert Object containing the vertices.
|
||||
* @param g The graph that is to be drawn.
|
||||
* @param svgId
|
||||
* @param root
|
||||
* @param _doc
|
||||
* @param diagObj
|
||||
*/
|
||||
export const addVertices = async function (vert, g, svgId, root, _doc, diagObj) {
|
||||
const svg = !root ? select(`[id="${svgId}"]`) : root.select(`[id="${svgId}"]`);
|
||||
const doc = !_doc ? document : _doc;
|
||||
const keys = Object.keys(vert);
|
||||
|
||||
// Iterate through each item in the vertex object (containing all the vertices found) in the graph definition
|
||||
for (const id of keys) {
|
||||
const vertex = vert[id];
|
||||
|
||||
/**
|
||||
* Variable for storing the classes for the vertex
|
||||
*
|
||||
* @type {string}
|
||||
*/
|
||||
let classStr = 'default';
|
||||
if (vertex.classes.length > 0) {
|
||||
classStr = vertex.classes.join(' ');
|
||||
}
|
||||
|
||||
const styles = getStylesFromArray(vertex.styles);
|
||||
|
||||
// Use vertex id as text in the box if no text is provided by the graph definition
|
||||
let vertexText = vertex.text !== undefined ? vertex.text : vertex.id;
|
||||
|
||||
// We create a SVG label, either by delegating to addHtmlLabel or manually
|
||||
let vertexNode;
|
||||
if (evaluate(getConfig().flowchart.htmlLabels)) {
|
||||
// TODO: addHtmlLabel accepts a labelStyle. Do we possibly have that?
|
||||
const replacedVertexText = replaceIconSubstring(vertexText);
|
||||
const node = {
|
||||
label: await renderKatex(replacedVertexText, getConfig()),
|
||||
};
|
||||
vertexNode = addHtmlLabel(svg, node).node();
|
||||
vertexNode.parentNode.removeChild(vertexNode);
|
||||
} else {
|
||||
const svgLabel = doc.createElementNS('http://www.w3.org/2000/svg', 'text');
|
||||
svgLabel.setAttribute('style', styles.labelStyle.replace('color:', 'fill:'));
|
||||
|
||||
const rows = vertexText.split(common.lineBreakRegex);
|
||||
|
||||
for (const row of rows) {
|
||||
const tspan = doc.createElementNS('http://www.w3.org/2000/svg', 'tspan');
|
||||
tspan.setAttributeNS('http://www.w3.org/XML/1998/namespace', 'xml:space', 'preserve');
|
||||
tspan.setAttribute('dy', '1em');
|
||||
tspan.setAttribute('x', '1');
|
||||
tspan.textContent = row;
|
||||
svgLabel.appendChild(tspan);
|
||||
}
|
||||
vertexNode = svgLabel;
|
||||
}
|
||||
|
||||
let radius = 0;
|
||||
let _shape = '';
|
||||
// Set the shape based parameters
|
||||
switch (vertex.type) {
|
||||
case 'round':
|
||||
radius = 5;
|
||||
_shape = 'rect';
|
||||
break;
|
||||
case 'square':
|
||||
_shape = 'rect';
|
||||
break;
|
||||
case 'diamond':
|
||||
_shape = 'question';
|
||||
break;
|
||||
case 'hexagon':
|
||||
_shape = 'hexagon';
|
||||
break;
|
||||
case 'odd':
|
||||
_shape = 'rect_left_inv_arrow';
|
||||
break;
|
||||
case 'lean_right':
|
||||
_shape = 'lean_right';
|
||||
break;
|
||||
case 'lean_left':
|
||||
_shape = 'lean_left';
|
||||
break;
|
||||
case 'trapezoid':
|
||||
_shape = 'trapezoid';
|
||||
break;
|
||||
case 'inv_trapezoid':
|
||||
_shape = 'inv_trapezoid';
|
||||
break;
|
||||
case 'odd_right':
|
||||
_shape = 'rect_left_inv_arrow';
|
||||
break;
|
||||
case 'circle':
|
||||
_shape = 'circle';
|
||||
break;
|
||||
case 'ellipse':
|
||||
_shape = 'ellipse';
|
||||
break;
|
||||
case 'stadium':
|
||||
_shape = 'stadium';
|
||||
break;
|
||||
case 'subroutine':
|
||||
_shape = 'subroutine';
|
||||
break;
|
||||
case 'cylinder':
|
||||
_shape = 'cylinder';
|
||||
break;
|
||||
case 'group':
|
||||
_shape = 'rect';
|
||||
break;
|
||||
default:
|
||||
_shape = 'rect';
|
||||
}
|
||||
// Add the node
|
||||
log.warn('Adding node', vertex.id, vertex.domId);
|
||||
g.setNode(diagObj.db.lookUpDomId(vertex.id), {
|
||||
labelType: 'svg',
|
||||
labelStyle: styles.labelStyle,
|
||||
shape: _shape,
|
||||
label: vertexNode,
|
||||
rx: radius,
|
||||
ry: radius,
|
||||
class: classStr,
|
||||
style: styles.style,
|
||||
id: diagObj.db.lookUpDomId(vertex.id),
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Add edges to graph based on parsed graph definition
|
||||
*
|
||||
* @param {object} edges The edges to add to the graph
|
||||
* @param {object} g The graph object
|
||||
* @param diagObj
|
||||
*/
|
||||
export const addEdges = async function (edges, g, diagObj) {
|
||||
let cnt = 0;
|
||||
|
||||
let defaultStyle;
|
||||
let defaultLabelStyle;
|
||||
|
||||
if (edges.defaultStyle !== undefined) {
|
||||
const defaultStyles = getStylesFromArray(edges.defaultStyle);
|
||||
defaultStyle = defaultStyles.style;
|
||||
defaultLabelStyle = defaultStyles.labelStyle;
|
||||
}
|
||||
|
||||
for (const edge of edges) {
|
||||
cnt++;
|
||||
|
||||
// Identify Link
|
||||
const linkId = getEdgeId(edge.start, edge.end, {
|
||||
counter: cnt,
|
||||
prefix: 'L',
|
||||
});
|
||||
const linkNameStart = 'LS-' + edge.start;
|
||||
const linkNameEnd = 'LE-' + edge.end;
|
||||
|
||||
const edgeData = {};
|
||||
|
||||
// Set link type for rendering
|
||||
if (edge.type === 'arrow_open') {
|
||||
edgeData.arrowhead = 'none';
|
||||
} else {
|
||||
edgeData.arrowhead = 'normal';
|
||||
}
|
||||
|
||||
let style = '';
|
||||
let labelStyle = '';
|
||||
|
||||
if (edge.style !== undefined) {
|
||||
const styles = getStylesFromArray(edge.style);
|
||||
style = styles.style;
|
||||
labelStyle = styles.labelStyle;
|
||||
} else {
|
||||
switch (edge.stroke) {
|
||||
case 'normal':
|
||||
style = 'fill:none';
|
||||
if (defaultStyle !== undefined) {
|
||||
style = defaultStyle;
|
||||
}
|
||||
if (defaultLabelStyle !== undefined) {
|
||||
labelStyle = defaultLabelStyle;
|
||||
}
|
||||
break;
|
||||
case 'dotted':
|
||||
style = 'fill:none;stroke-width:2px;stroke-dasharray:3;';
|
||||
break;
|
||||
case 'thick':
|
||||
style = ' stroke-width: 3.5px;fill:none';
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
edgeData.style = style;
|
||||
edgeData.labelStyle = labelStyle;
|
||||
|
||||
if (edge.interpolate !== undefined) {
|
||||
edgeData.curve = interpolateToCurve(edge.interpolate, curveLinear);
|
||||
} else if (edges.defaultInterpolate !== undefined) {
|
||||
edgeData.curve = interpolateToCurve(edges.defaultInterpolate, curveLinear);
|
||||
} else {
|
||||
edgeData.curve = interpolateToCurve(conf.curve, curveLinear);
|
||||
}
|
||||
|
||||
if (edge.text === undefined) {
|
||||
if (edge.style !== undefined) {
|
||||
edgeData.arrowheadStyle = 'fill: #333';
|
||||
}
|
||||
} else {
|
||||
edgeData.arrowheadStyle = 'fill: #333';
|
||||
edgeData.labelpos = 'c';
|
||||
|
||||
if (evaluate(getConfig().flowchart.htmlLabels)) {
|
||||
edgeData.labelType = 'html';
|
||||
edgeData.label = `<span id="L-${linkId}" class="edgeLabel L-${linkNameStart}' L-${linkNameEnd}" style="${
|
||||
edgeData.labelStyle
|
||||
}">${await renderKatex(replaceIconSubstring(edge.text), getConfig())}</span>`;
|
||||
} else {
|
||||
edgeData.labelType = 'text';
|
||||
edgeData.label = edge.text.replace(common.lineBreakRegex, '\n');
|
||||
|
||||
if (edge.style === undefined) {
|
||||
edgeData.style = edgeData.style || 'stroke: #333; stroke-width: 1.5px;fill:none';
|
||||
}
|
||||
|
||||
edgeData.labelStyle = edgeData.labelStyle.replace('color:', 'fill:');
|
||||
}
|
||||
}
|
||||
|
||||
edgeData.id = linkId;
|
||||
edgeData.class = linkNameStart + ' ' + linkNameEnd;
|
||||
edgeData.minlen = edge.length || 1;
|
||||
|
||||
// Add the edge to the graph
|
||||
g.setEdge(diagObj.db.lookUpDomId(edge.start), diagObj.db.lookUpDomId(edge.end), edgeData, cnt);
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Returns the all the styles from classDef statements in the graph definition.
|
||||
*
|
||||
* @param text
|
||||
* @param diagObj
|
||||
* @returns {Map<string, import('../../diagram-api/types.js').DiagramStyleClassDef>} ClassDef styles
|
||||
*/
|
||||
export const getClasses = function (text, diagObj) {
|
||||
log.info('Extracting classes');
|
||||
return diagObj.db.getClasses();
|
||||
};
|
||||
|
||||
/**
|
||||
* Draws a flowchart in the tag with id: id based on the graph definition in text.
|
||||
*
|
||||
* @param text
|
||||
* @param id
|
||||
* @param _version
|
||||
* @param diagObj
|
||||
*/
|
||||
export const draw = async function (text, id, _version, diagObj) {
|
||||
log.info('Drawing flowchart');
|
||||
const { securityLevel, flowchart: conf } = getConfig();
|
||||
let sandboxElement;
|
||||
if (securityLevel === 'sandbox') {
|
||||
sandboxElement = select('#i' + id);
|
||||
}
|
||||
const root =
|
||||
securityLevel === 'sandbox'
|
||||
? select(sandboxElement.nodes()[0].contentDocument.body)
|
||||
: select('body');
|
||||
const doc = securityLevel === 'sandbox' ? sandboxElement.nodes()[0].contentDocument : document;
|
||||
|
||||
// Fetch the default direction, use TD if none was found
|
||||
let dir = diagObj.db.getDirection();
|
||||
if (dir === undefined) {
|
||||
dir = 'TD';
|
||||
}
|
||||
const nodeSpacing = conf.nodeSpacing ?? 50;
|
||||
const rankSpacing = conf.rankSpacing ?? 50;
|
||||
|
||||
// Create the input mermaid.graph
|
||||
const g = new graphlib.Graph({
|
||||
multigraph: true,
|
||||
compound: true,
|
||||
})
|
||||
.setGraph({
|
||||
rankdir: dir,
|
||||
nodesep: nodeSpacing,
|
||||
ranksep: rankSpacing,
|
||||
marginx: 8,
|
||||
marginy: 8,
|
||||
})
|
||||
.setDefaultEdgeLabel(function () {
|
||||
return {};
|
||||
});
|
||||
|
||||
let subG;
|
||||
const subGraphs = diagObj.db.getSubGraphs();
|
||||
for (let i = subGraphs.length - 1; i >= 0; i--) {
|
||||
subG = subGraphs[i];
|
||||
diagObj.db.addVertex(subG.id, subG.title, 'group', undefined, subG.classes);
|
||||
}
|
||||
|
||||
// Fetch the vertices/nodes and edges/links from the parsed graph definition
|
||||
const vert = diagObj.db.getVertices();
|
||||
log.warn('Get vertices', vert);
|
||||
|
||||
const edges = diagObj.db.getEdges();
|
||||
|
||||
let i = 0;
|
||||
for (i = subGraphs.length - 1; i >= 0; i--) {
|
||||
subG = subGraphs[i];
|
||||
|
||||
selectAll('cluster').append('text');
|
||||
|
||||
for (const node of subG.nodes) {
|
||||
log.warn(
|
||||
'Setting subgraph',
|
||||
node,
|
||||
diagObj.db.lookUpDomId(node),
|
||||
diagObj.db.lookUpDomId(subG.id)
|
||||
);
|
||||
g.setParent(diagObj.db.lookUpDomId(node), diagObj.db.lookUpDomId(subG.id));
|
||||
}
|
||||
}
|
||||
await addVertices(vert, g, id, root, doc, diagObj);
|
||||
await addEdges(edges, g, diagObj);
|
||||
|
||||
// Create the renderer
|
||||
const render = new Render();
|
||||
|
||||
// Add custom shapes
|
||||
flowChartShapes.addToRender(render);
|
||||
|
||||
// Add our custom arrow - an empty arrowhead
|
||||
render.arrows().none = function normal(parent, id, edge, type) {
|
||||
const marker = parent
|
||||
.append('marker')
|
||||
.attr('id', id)
|
||||
.attr('viewBox', '0 0 10 10')
|
||||
.attr('refX', 9)
|
||||
.attr('refY', 5)
|
||||
.attr('markerUnits', 'strokeWidth')
|
||||
.attr('markerWidth', 8)
|
||||
.attr('markerHeight', 6)
|
||||
.attr('orient', 'auto');
|
||||
|
||||
const path = marker.append('path').attr('d', 'M 0 0 L 0 0 L 0 0 z');
|
||||
applyStyle(path, edge[type + 'Style']);
|
||||
};
|
||||
|
||||
// Override normal arrowhead defined in d3. Remove style & add class to allow css styling.
|
||||
render.arrows().normal = function normal(parent, id) {
|
||||
const marker = parent
|
||||
.append('marker')
|
||||
.attr('id', id)
|
||||
.attr('viewBox', '0 0 10 10')
|
||||
.attr('refX', 9)
|
||||
.attr('refY', 5)
|
||||
.attr('markerUnits', 'strokeWidth')
|
||||
.attr('markerWidth', 8)
|
||||
.attr('markerHeight', 6)
|
||||
.attr('orient', 'auto');
|
||||
|
||||
marker
|
||||
.append('path')
|
||||
.attr('d', 'M 0 0 L 10 5 L 0 10 z')
|
||||
.attr('class', 'arrowheadPath')
|
||||
.style('stroke-width', 1)
|
||||
.style('stroke-dasharray', '1,0');
|
||||
};
|
||||
|
||||
// Set up an SVG group so that we can translate the final graph.
|
||||
const svg = root.select(`[id="${id}"]`);
|
||||
|
||||
// Run the renderer. This is what draws the final graph.
|
||||
const element = root.select('#' + id + ' g');
|
||||
render(element, g);
|
||||
|
||||
element.selectAll('g.node').attr('title', function () {
|
||||
return diagObj.db.getTooltip(this.id);
|
||||
});
|
||||
|
||||
// Index nodes
|
||||
diagObj.db.indexNodes('subGraph' + i);
|
||||
|
||||
// reposition labels
|
||||
for (i = 0; i < subGraphs.length; i++) {
|
||||
subG = subGraphs[i];
|
||||
if (subG.title !== 'undefined') {
|
||||
const clusterRects = doc.querySelectorAll(
|
||||
'#' + id + ' [id="' + diagObj.db.lookUpDomId(subG.id) + '"] rect'
|
||||
);
|
||||
const clusterEl = doc.querySelectorAll(
|
||||
'#' + id + ' [id="' + diagObj.db.lookUpDomId(subG.id) + '"]'
|
||||
);
|
||||
|
||||
const xPos = clusterRects[0].x.baseVal.value;
|
||||
const yPos = clusterRects[0].y.baseVal.value;
|
||||
const _width = clusterRects[0].width.baseVal.value;
|
||||
const cluster = select(clusterEl[0]);
|
||||
const te = cluster.select('.label');
|
||||
te.attr('transform', `translate(${xPos + _width / 2}, ${yPos + 14})`);
|
||||
te.attr('id', id + 'Text');
|
||||
|
||||
for (const className of subG.classes) {
|
||||
clusterEl[0].classList.add(className);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Add label rects for non html labels
|
||||
if (!conf.htmlLabels) {
|
||||
const labels = doc.querySelectorAll('[id="' + id + '"] .edgeLabel .label');
|
||||
for (const label of labels) {
|
||||
// Get dimensions of label
|
||||
const dim = label.getBBox();
|
||||
|
||||
const rect = doc.createElementNS('http://www.w3.org/2000/svg', 'rect');
|
||||
rect.setAttribute('rx', 0);
|
||||
rect.setAttribute('ry', 0);
|
||||
rect.setAttribute('width', dim.width);
|
||||
rect.setAttribute('height', dim.height);
|
||||
// rect.setAttribute('style', 'fill:#e8e8e8;');
|
||||
|
||||
label.insertBefore(rect, label.firstChild);
|
||||
}
|
||||
}
|
||||
setupGraphViewbox(g, svg, conf.diagramPadding, conf.useMaxWidth);
|
||||
|
||||
// If node has a link, wrap it in an anchor SVG object.
|
||||
const keys = [...vert.keys()];
|
||||
keys.forEach(function (key) {
|
||||
const vertex = vert.get(key);
|
||||
|
||||
if (vertex.link) {
|
||||
const node = root.select('#' + id + ' [id="' + diagObj.db.lookUpDomId(key) + '"]');
|
||||
if (node) {
|
||||
const link = doc.createElementNS('http://www.w3.org/2000/svg', 'a');
|
||||
link.setAttributeNS('http://www.w3.org/2000/svg', 'class', vertex.classes.join(' '));
|
||||
link.setAttributeNS('http://www.w3.org/2000/svg', 'href', vertex.link);
|
||||
link.setAttributeNS('http://www.w3.org/2000/svg', 'rel', 'noopener');
|
||||
if (securityLevel === 'sandbox') {
|
||||
link.setAttributeNS('http://www.w3.org/2000/svg', 'target', '_top');
|
||||
} else if (vertex.linkTarget) {
|
||||
link.setAttributeNS('http://www.w3.org/2000/svg', 'target', vertex.linkTarget);
|
||||
}
|
||||
|
||||
const linkNode = node.insert(function () {
|
||||
return link;
|
||||
}, ':first-child');
|
||||
|
||||
const shape = node.select('.label-container');
|
||||
if (shape) {
|
||||
linkNode.append(function () {
|
||||
return shape.node();
|
||||
});
|
||||
}
|
||||
|
||||
const label = node.select('.label');
|
||||
if (label) {
|
||||
linkNode.append(function () {
|
||||
return label.node();
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
export default {
|
||||
setConf,
|
||||
addVertices,
|
||||
addEdges,
|
||||
getClasses,
|
||||
draw,
|
||||
};
|
@ -1,277 +0,0 @@
|
||||
/* eslint-disable @typescript-eslint/restrict-template-expressions */
|
||||
import { addVertices, addEdges } from './flowRenderer.js';
|
||||
import { setConfig } from '../../diagram-api/diagramAPI.js';
|
||||
|
||||
setConfig({
|
||||
flowchart: {
|
||||
htmlLabels: false,
|
||||
},
|
||||
});
|
||||
|
||||
describe('the flowchart renderer', function () {
|
||||
describe('when adding vertices to a graph', function () {
|
||||
[
|
||||
['round', 'rect', 5],
|
||||
['square', 'rect'],
|
||||
['diamond', 'question'],
|
||||
['hexagon', 'hexagon'],
|
||||
['odd', 'rect_left_inv_arrow'],
|
||||
['lean_right', 'lean_right'],
|
||||
['lean_left', 'lean_left'],
|
||||
['trapezoid', 'trapezoid'],
|
||||
['inv_trapezoid', 'inv_trapezoid'],
|
||||
['odd_right', 'rect_left_inv_arrow'],
|
||||
['circle', 'circle'],
|
||||
['ellipse', 'ellipse'],
|
||||
['stadium', 'stadium'],
|
||||
['subroutine', 'subroutine'],
|
||||
['cylinder', 'cylinder'],
|
||||
['group', 'rect'],
|
||||
].forEach(function ([type, expectedShape, expectedRadios = 0]) {
|
||||
it(`should add the correct shaped node to the graph for vertex type ${type}`, async function () {
|
||||
const fakeDiag = {
|
||||
db: {
|
||||
lookUpDomId: () => {
|
||||
return 'my-node-id';
|
||||
},
|
||||
},
|
||||
};
|
||||
const addedNodes = [];
|
||||
const mockG = {
|
||||
setNode: function (id, object) {
|
||||
addedNodes.push([id, object]);
|
||||
},
|
||||
};
|
||||
await addVertices(
|
||||
{
|
||||
v1: {
|
||||
type,
|
||||
id: 'my-node-id',
|
||||
classes: [],
|
||||
styles: [],
|
||||
text: 'my vertex text',
|
||||
},
|
||||
},
|
||||
mockG,
|
||||
'svg-id',
|
||||
undefined,
|
||||
undefined,
|
||||
fakeDiag
|
||||
);
|
||||
expect(addedNodes).toHaveLength(1);
|
||||
expect(addedNodes[0][0]).toEqual('my-node-id');
|
||||
expect(addedNodes[0][1]).toHaveProperty('id', 'my-node-id');
|
||||
expect(addedNodes[0][1]).toHaveProperty('labelType', 'svg');
|
||||
expect(addedNodes[0][1]).toHaveProperty('shape', expectedShape);
|
||||
expect(addedNodes[0][1]).toHaveProperty('rx', expectedRadios);
|
||||
expect(addedNodes[0][1]).toHaveProperty('ry', expectedRadios);
|
||||
});
|
||||
});
|
||||
|
||||
['Multi<br>Line', 'Multi<br/>Line', 'Multi<br />Line', 'Multi<br\t/>Line'].forEach(
|
||||
function (labelText) {
|
||||
it('should handle multiline texts with different line breaks', async function () {
|
||||
const addedNodes = [];
|
||||
const fakeDiag = {
|
||||
db: {
|
||||
lookUpDomId: () => {
|
||||
return 'my-node-id';
|
||||
},
|
||||
},
|
||||
};
|
||||
const mockG = {
|
||||
setNode: function (id, object) {
|
||||
addedNodes.push([id, object]);
|
||||
},
|
||||
};
|
||||
await addVertices(
|
||||
{
|
||||
v1: {
|
||||
type: 'rect',
|
||||
id: 'my-node-id',
|
||||
classes: [],
|
||||
styles: [],
|
||||
text: 'Multi<br>Line',
|
||||
},
|
||||
},
|
||||
mockG,
|
||||
'svg-id',
|
||||
false,
|
||||
document,
|
||||
fakeDiag
|
||||
);
|
||||
expect(addedNodes).toHaveLength(1);
|
||||
expect(addedNodes[0][0]).toEqual('my-node-id');
|
||||
expect(addedNodes[0][1]).toHaveProperty('id', 'my-node-id');
|
||||
expect(addedNodes[0][1]).toHaveProperty('labelType', 'svg');
|
||||
expect(addedNodes[0][1].label).toBeDefined();
|
||||
expect(addedNodes[0][1].label).toBeDefined(); // <text> node
|
||||
expect(addedNodes[0][1].label.firstChild.innerHTML).toEqual('Multi'); // <tspan> node, line 1
|
||||
expect(addedNodes[0][1].label.lastChild.innerHTML).toEqual('Line'); // <tspan> node, line 2
|
||||
});
|
||||
}
|
||||
);
|
||||
|
||||
[
|
||||
[['fill:#fff'], 'fill:#fff;', ''],
|
||||
[['color:#ccc'], '', 'color:#ccc;'],
|
||||
[['fill:#fff', 'color:#ccc'], 'fill:#fff;', 'color:#ccc;'],
|
||||
[
|
||||
['fill:#fff', 'color:#ccc', 'text-align:center'],
|
||||
'fill:#fff;',
|
||||
'color:#ccc;text-align:center;',
|
||||
],
|
||||
].forEach(function ([style, expectedStyle, expectedLabelStyle]) {
|
||||
it(`should add the styles to style and/or labelStyle for style ${style}`, async function () {
|
||||
const addedNodes = [];
|
||||
const fakeDiag = {
|
||||
db: {
|
||||
lookUpDomId: () => {
|
||||
return 'my-node-id';
|
||||
},
|
||||
},
|
||||
};
|
||||
const mockG = {
|
||||
setNode: function (id, object) {
|
||||
addedNodes.push([id, object]);
|
||||
},
|
||||
};
|
||||
await addVertices(
|
||||
{
|
||||
v1: {
|
||||
type: 'rect',
|
||||
id: 'my-node-id',
|
||||
classes: [],
|
||||
styles: style,
|
||||
text: 'my vertex text',
|
||||
},
|
||||
},
|
||||
mockG,
|
||||
'svg-id',
|
||||
undefined,
|
||||
undefined,
|
||||
fakeDiag
|
||||
);
|
||||
expect(addedNodes).toHaveLength(1);
|
||||
expect(addedNodes[0][0]).toEqual('my-node-id');
|
||||
expect(addedNodes[0][1]).toHaveProperty('id', 'my-node-id');
|
||||
expect(addedNodes[0][1]).toHaveProperty('labelType', 'svg');
|
||||
expect(addedNodes[0][1]).toHaveProperty('style', expectedStyle);
|
||||
expect(addedNodes[0][1]).toHaveProperty('labelStyle', expectedLabelStyle);
|
||||
});
|
||||
});
|
||||
|
||||
it(`should add default class to all nodes which do not have another class assigned`, async function () {
|
||||
const addedNodes = [];
|
||||
const mockG = {
|
||||
setNode: function (id, object) {
|
||||
addedNodes.push([id, object]);
|
||||
},
|
||||
};
|
||||
const fakeDiag = {
|
||||
db: {
|
||||
lookUpDomId: () => {
|
||||
return 'my-node-id';
|
||||
},
|
||||
},
|
||||
};
|
||||
await addVertices(
|
||||
{
|
||||
v1: {
|
||||
type: 'rect',
|
||||
id: 'my-node-id',
|
||||
classes: [],
|
||||
styles: [],
|
||||
text: 'my vertex text',
|
||||
},
|
||||
v2: {
|
||||
type: 'rect',
|
||||
id: 'myNode',
|
||||
classes: ['myClass'],
|
||||
styles: [],
|
||||
text: 'my vertex text',
|
||||
},
|
||||
},
|
||||
mockG,
|
||||
'svg-id',
|
||||
undefined,
|
||||
undefined,
|
||||
fakeDiag
|
||||
);
|
||||
expect(addedNodes).toHaveLength(2);
|
||||
expect(addedNodes[0][0]).toEqual('my-node-id');
|
||||
expect(addedNodes[0][1]).toHaveProperty('class', 'default');
|
||||
expect(addedNodes[1][0]).toEqual('my-node-id');
|
||||
expect(addedNodes[1][1]).toHaveProperty('class', 'myClass');
|
||||
});
|
||||
});
|
||||
|
||||
describe('when adding edges to a graph', function () {
|
||||
it('should handle multiline texts and set centered label position', async function () {
|
||||
const addedEdges = [];
|
||||
const fakeDiag = {
|
||||
db: {
|
||||
lookUpDomId: () => {
|
||||
return 'my-node-id';
|
||||
},
|
||||
},
|
||||
};
|
||||
const mockG = {
|
||||
setEdge: function (s, e, data, c) {
|
||||
addedEdges.push(data);
|
||||
},
|
||||
};
|
||||
await addEdges(
|
||||
[
|
||||
{ text: 'Multi<br>Line' },
|
||||
{ text: 'Multi<br/>Line' },
|
||||
{ text: 'Multi<br />Line' },
|
||||
{ text: 'Multi<br\t/>Line' },
|
||||
{ style: ['stroke:DarkGray', 'stroke-width:2px'], text: 'Multi<br>Line' },
|
||||
{ style: ['stroke:DarkGray', 'stroke-width:2px'], text: 'Multi<br/>Line' },
|
||||
{ style: ['stroke:DarkGray', 'stroke-width:2px'], text: 'Multi<br />Line' },
|
||||
{ style: ['stroke:DarkGray', 'stroke-width:2px'], text: 'Multi<br\t/>Line' },
|
||||
],
|
||||
mockG,
|
||||
fakeDiag
|
||||
);
|
||||
|
||||
addedEdges.forEach(function (edge) {
|
||||
expect(edge).toHaveProperty('label', 'Multi\nLine');
|
||||
expect(edge).toHaveProperty('labelpos', 'c');
|
||||
});
|
||||
});
|
||||
|
||||
[
|
||||
[['stroke:DarkGray'], 'stroke:DarkGray;', ''],
|
||||
[['color:red'], '', 'fill:red;'],
|
||||
[['stroke:DarkGray', 'color:red'], 'stroke:DarkGray;', 'fill:red;'],
|
||||
[
|
||||
['stroke:DarkGray', 'color:red', 'stroke-width:2px'],
|
||||
'stroke:DarkGray;stroke-width:2px;',
|
||||
'fill:red;',
|
||||
],
|
||||
].forEach(function ([style, expectedStyle, expectedLabelStyle]) {
|
||||
it(`should add the styles to style and/or labelStyle for style ${style}`, async function () {
|
||||
const addedEdges = [];
|
||||
const fakeDiag = {
|
||||
db: {
|
||||
lookUpDomId: () => {
|
||||
return 'my-node-id';
|
||||
},
|
||||
},
|
||||
};
|
||||
const mockG = {
|
||||
setEdge: function (s, e, data, c) {
|
||||
addedEdges.push(data);
|
||||
},
|
||||
};
|
||||
await addEdges([{ style: style, text: 'styling' }], mockG, fakeDiag);
|
||||
|
||||
expect(addedEdges).toHaveLength(1);
|
||||
expect(addedEdges[0]).toHaveProperty('style', expectedStyle);
|
||||
expect(addedEdges[0]).toHaveProperty('labelStyle', expectedLabelStyle);
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
@ -18,7 +18,6 @@ describe('when parsing directions', function () {
|
||||
D@{ shape: rounded }@`);
|
||||
|
||||
const data4Layout = flow.parser.yy.getData();
|
||||
console.log(data4Layout.nodes);
|
||||
expect(data4Layout.nodes.length).toBe(1);
|
||||
expect(data4Layout.nodes[0].shape).toEqual('rounded');
|
||||
expect(data4Layout.nodes[0].label).toEqual('D');
|
||||
@ -76,7 +75,6 @@ describe('when parsing directions', function () {
|
||||
`);
|
||||
|
||||
const data4Layout = flow.parser.yy.getData();
|
||||
console.log(data4Layout.edges);
|
||||
expect(data4Layout.nodes.length).toBe(2);
|
||||
expect(data4Layout.nodes[0].shape).toEqual('squareRect');
|
||||
expect(data4Layout.nodes[0].label).toEqual('A');
|
||||
@ -126,7 +124,6 @@ describe('when parsing directions', function () {
|
||||
`);
|
||||
|
||||
const data4Layout = flow.parser.yy.getData();
|
||||
console.log(data4Layout.nodes);
|
||||
expect(data4Layout.nodes.length).toBe(1);
|
||||
expect(data4Layout.nodes[0].shape).toEqual('diamond');
|
||||
expect(data4Layout.nodes[0].label).toEqual('This is a label');
|
||||
|
@ -59,7 +59,7 @@ const getStyles = (options: FlowChartStyleOptions) =>
|
||||
stroke: ${options.nodeBorder};
|
||||
stroke-width: 1px;
|
||||
}
|
||||
.node .label text {
|
||||
.rough-node .label text , .node .label text {
|
||||
text-anchor: middle;
|
||||
}
|
||||
// .flowchart-label .text-outer-tspan {
|
||||
|
@ -23,7 +23,7 @@ export interface FlowEdge {
|
||||
end: string;
|
||||
interpolate?: string;
|
||||
type?: string;
|
||||
stroke?: 'normal' | 'thick' | 'invisible';
|
||||
stroke?: 'normal' | 'thick' | 'invisible' | 'dotted';
|
||||
style?: string[];
|
||||
length?: number;
|
||||
text: string;
|
||||
|
@ -1088,6 +1088,19 @@ export const draw = async function (_text: string, id: string, _version: string,
|
||||
|
||||
const { bounds: box } = bounds.getBounds();
|
||||
|
||||
if (box.startx === undefined) {
|
||||
box.startx = 0;
|
||||
}
|
||||
if (box.starty === undefined) {
|
||||
box.starty = 0;
|
||||
}
|
||||
if (box.stopx === undefined) {
|
||||
box.stopx = 0;
|
||||
}
|
||||
if (box.stopy === undefined) {
|
||||
box.stopy = 0;
|
||||
}
|
||||
|
||||
// Make sure the height of the diagram supports long menus.
|
||||
let boxHeight = box.stopy - box.starty;
|
||||
if (boxHeight < requiredBoxSize.maxHeight) {
|
||||
|
@ -131,12 +131,6 @@ const getDir = (parsedItem, defaultDir = DEFAULT_NESTED_DOC_DIR) => {
|
||||
return dir;
|
||||
};
|
||||
|
||||
/**
|
||||
*
|
||||
* @param nodes
|
||||
* @param nodeData
|
||||
* @param classes
|
||||
*/
|
||||
function insertOrUpdateNode(nodes, nodeData, classes) {
|
||||
if (!nodeData.id || nodeData.id === '</join></fork>' || nodeData.id === '</choice>') {
|
||||
return;
|
||||
|
@ -11,12 +11,12 @@ import { createRoundedRectPathD } from './shapes/roundedRectPath.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
|
||||
const rect = async (parent, node) => {
|
||||
log.info('Creating subgraph rect for ', node.id, node);
|
||||
const siteConfig = getConfig();
|
||||
const { themeVariables, handdrawnSeed } = siteConfig;
|
||||
const { themeVariables, handDrawnSeed } = siteConfig;
|
||||
const { clusterBkg, clusterBorder } = themeVariables;
|
||||
|
||||
const { labelStyles, nodeStyles } = styles2String(node);
|
||||
@ -33,9 +33,6 @@ const rect = async (parent, node) => {
|
||||
// Create the label and insert it after the rect
|
||||
const labelEl = shapeSvg.insert('g').attr('class', 'cluster-label ');
|
||||
|
||||
// const text = label
|
||||
// .node()
|
||||
// .appendChild(createLabel(node.label, node.labelStyle, undefined, true));
|
||||
const text = await createText(labelEl, node.label, {
|
||||
style: node.labelStyle,
|
||||
useHtmlLabels,
|
||||
@ -53,10 +50,7 @@ const rect = async (parent, node) => {
|
||||
dv.attr('height', bbox.height);
|
||||
}
|
||||
|
||||
const padding = 0 * node.padding;
|
||||
|
||||
const width =
|
||||
(node.width <= bbox.width + node.padding ? bbox.width + node.padding : node.width) + padding;
|
||||
const width = node.width <= bbox.width + node.padding ? bbox.width + node.padding : node.width;
|
||||
if (node.width <= bbox.width + node.padding) {
|
||||
node.diff = (width - node.width) / 2 - node.padding;
|
||||
} else {
|
||||
@ -66,11 +60,10 @@ const rect = async (parent, node) => {
|
||||
const height = node.height;
|
||||
const x = node.x - width / 2;
|
||||
const y = node.y - height / 2;
|
||||
// console.log('UIO diff 2', node.id, node.diff, 'totalWidth: ', width);
|
||||
|
||||
log.trace('Data ', node, JSON.stringify(node));
|
||||
let rect;
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore TODO: Fix rough typings
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {
|
||||
@ -79,10 +72,9 @@ const rect = async (parent, node) => {
|
||||
// fill: 'red',
|
||||
stroke: clusterBorder,
|
||||
fillWeight: 3,
|
||||
seed: handdrawnSeed,
|
||||
seed: handDrawnSeed,
|
||||
});
|
||||
const roughNode = rc.path(createRoundedRectPathD(x, y, width, height, 0), options);
|
||||
// console.log('Rough node insert CXC', roughNode);
|
||||
rect = shapeSvg.insert(() => {
|
||||
log.debug('Rough node insert CXC', roughNode);
|
||||
return roughNode;
|
||||
@ -170,7 +162,7 @@ const noteGroup = (parent, node) => {
|
||||
const roundedWithTitle = async (parent, node) => {
|
||||
const siteConfig = getConfig();
|
||||
|
||||
const { themeVariables, handdrawnSeed } = siteConfig;
|
||||
const { themeVariables, handDrawnSeed } = siteConfig;
|
||||
const { altBackground, compositeBackground, compositeTitleBackground, nodeBorder } =
|
||||
themeVariables;
|
||||
|
||||
@ -226,7 +218,7 @@ const roundedWithTitle = async (parent, node) => {
|
||||
|
||||
// add the rect
|
||||
let rect;
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
const isAlt = node.cssClasses.includes('statediagram-cluster-alt');
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const roughOuterNode =
|
||||
@ -236,16 +228,16 @@ const roundedWithTitle = async (parent, node) => {
|
||||
fill: compositeTitleBackground,
|
||||
fillStyle: 'solid',
|
||||
stroke: nodeBorder,
|
||||
seed: handdrawnSeed,
|
||||
seed: handDrawnSeed,
|
||||
})
|
||||
: rc.rectangle(x, y, width, height, { seed: handdrawnSeed });
|
||||
: rc.rectangle(x, y, width, height, { seed: handDrawnSeed });
|
||||
|
||||
rect = shapeSvg.insert(() => roughOuterNode, ':first-child');
|
||||
const roughInnerNode = rc.rectangle(x, innerY, width, innerHeight, {
|
||||
fill: isAlt ? altBackground : compositeBackground,
|
||||
fillStyle: isAlt ? 'hachure' : 'solid',
|
||||
stroke: nodeBorder,
|
||||
seed: handdrawnSeed,
|
||||
seed: handDrawnSeed,
|
||||
});
|
||||
|
||||
rect = shapeSvg.insert(() => roughOuterNode, ':first-child');
|
||||
@ -291,7 +283,7 @@ const roundedWithTitle = async (parent, node) => {
|
||||
const divider = (parent, node) => {
|
||||
const siteConfig = getConfig();
|
||||
|
||||
const { themeVariables, handdrawnSeed } = siteConfig;
|
||||
const { themeVariables, handDrawnSeed } = siteConfig;
|
||||
const { nodeBorder } = themeVariables;
|
||||
|
||||
// Add outer g element
|
||||
@ -318,14 +310,14 @@ const divider = (parent, node) => {
|
||||
|
||||
// add the rect
|
||||
let rect;
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const roughOuterNode = rc.rectangle(x, y, width, height, {
|
||||
fill: 'lightgrey',
|
||||
roughness: 0.5,
|
||||
strokeLineDash: [5],
|
||||
stroke: nodeBorder,
|
||||
seed: handdrawnSeed,
|
||||
seed: handDrawnSeed,
|
||||
});
|
||||
|
||||
rect = shapeSvg.insert(() => roughOuterNode, ':first-child');
|
||||
|
@ -31,7 +31,7 @@ async function addHtmlLabel(node) {
|
||||
'<span class="' +
|
||||
labelClass +
|
||||
'" ' +
|
||||
(node.labelStyle ? 'style="' + node.labelStyle + '"' : '') +
|
||||
(node.labelStyle ? 'style="' + node.labelStyle + '"' : '') + // codeql [js/html-constructed-from-input] : false positive
|
||||
'>' +
|
||||
label +
|
||||
'</span>'
|
||||
|
@ -423,7 +423,7 @@ const fixCorners = function (lineData) {
|
||||
};
|
||||
|
||||
export const insertEdge = function (elem, edge, clusterDb, diagramType, startNode, endNode, id) {
|
||||
const { handdrawnSeed } = getConfig();
|
||||
const { handDrawnSeed } = getConfig();
|
||||
let points = edge.points;
|
||||
let pointsHasChanged = false;
|
||||
const tail = startNode;
|
||||
@ -510,13 +510,13 @@ export const insertEdge = function (elem, edge, clusterDb, diagramType, startNod
|
||||
let svgPath;
|
||||
let linePath = lineFunction(lineData);
|
||||
const edgeStyles = Array.isArray(edge.style) ? edge.style : [edge.style];
|
||||
if (edge.look === 'handdrawn') {
|
||||
if (edge.look === 'handDrawn') {
|
||||
const rc = rough.svg(elem);
|
||||
Object.assign([], lineData);
|
||||
|
||||
const svgPathNode = rc.path(linePath, {
|
||||
roughness: 0.3,
|
||||
seed: handdrawnSeed,
|
||||
seed: handDrawnSeed,
|
||||
});
|
||||
|
||||
strokeClasses += ' transition';
|
||||
|
@ -38,6 +38,10 @@ import { titledCylinder } from './shapes/tiltedCylinder.js';
|
||||
import { trapezoidalPentagon } from './shapes/trapezoidalPentagon.js';
|
||||
import { flippedTriangle } from './shapes/flippedTriangle.js';
|
||||
import { hourglass } from './shapes/hourglass.js';
|
||||
import { taggedRect } from './shapes/taggedRect.js';
|
||||
import { multiRect } from './shapes/multiRect.js';
|
||||
import { linedCylinder } from './shapes/linedCylinder.js';
|
||||
import { waveEdgedRectangle } from './shapes/waveEdgedRectangle.js';
|
||||
|
||||
const shapes = {
|
||||
state,
|
||||
@ -79,6 +83,10 @@ const shapes = {
|
||||
trapezoidalPentagon,
|
||||
flippedTriangle,
|
||||
hourglass,
|
||||
taggedRect,
|
||||
multiRect,
|
||||
linedCylinder,
|
||||
waveEdgedRectangle,
|
||||
};
|
||||
|
||||
const nodeElems = new Map();
|
||||
|
@ -1,17 +1,16 @@
|
||||
import { log } from '$root/logger.js';
|
||||
import { labelHelper, updateNodeBounds, getNodeClasses } from './util.js';
|
||||
import { updateNodeBounds, getNodeClasses } from './util.js';
|
||||
import intersect from '../intersect/index.js';
|
||||
import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
export const anchor = async (parent: SVGAElement, node: Node): Promise<SVGAElement> => {
|
||||
const { labelStyles, nodeStyles } = styles2String(node);
|
||||
export const anchor = (parent: SVGAElement, node: Node): Promise<SVGAElement> => {
|
||||
const { labelStyles } = styles2String(node);
|
||||
node.labelStyle = labelStyles;
|
||||
// const { shapeSvg, bbox, halfPadding } = await labelHelper(parent, node, getNodeClasses(node));
|
||||
const classes = getNodeClasses(node);
|
||||
let cssClasses = classes;
|
||||
if (!classes) {
|
||||
@ -23,32 +22,19 @@ export const anchor = async (parent: SVGAElement, node: Node): Promise<SVGAEleme
|
||||
.attr('id', node.domId || node.id);
|
||||
|
||||
const radius = 1;
|
||||
let circleElem;
|
||||
|
||||
const { cssStyles } = node;
|
||||
|
||||
// if (node.look === 'handdrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, { fill: 'black', stroke: 'none', fillStyle: 'solid' });
|
||||
|
||||
if (node.look !== 'handdrawn') {
|
||||
if (node.look !== 'handDrawn') {
|
||||
options.roughness = 0;
|
||||
}
|
||||
const roughNode = rc.circle(0, 0, radius * 2, options);
|
||||
|
||||
console.log('IPI roughNode:', options);
|
||||
|
||||
circleElem = shapeSvg.insert(() => roughNode, ':first-child');
|
||||
const circleElem = shapeSvg.insert(() => roughNode, ':first-child');
|
||||
circleElem.attr('class', 'anchor').attr('style', cssStyles);
|
||||
// } else {
|
||||
// circleElem = shapeSvg
|
||||
// .insert('circle', ':first-child')
|
||||
// .attr('class', 'basic label-container')
|
||||
// .attr('style', nodeStyles)
|
||||
// .attr('r', radius)
|
||||
// .attr('cx', 0)
|
||||
// .attr('cy', 0);
|
||||
// }
|
||||
|
||||
updateNodeBounds(node, circleElem);
|
||||
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
function createBowTieRectPathD(x: number, y: number, totalWidth: number, totalHeight: number) {
|
||||
@ -21,7 +21,7 @@ export const bowTieRect = async (parent: SVGAElement, node: Node) => {
|
||||
let shape: d3.Selection<SVGPathElement | SVGGElement, unknown, null, undefined>;
|
||||
const { cssStyles } = node;
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const pathData = createBowTieRectPathD(0, 0, w, h);
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
import { insertPolygonShape } from './insertPolygonShape.js';
|
||||
@ -21,17 +21,13 @@ export async function card(parent: SVGAElement, node: Node): Promise<SVGAElement
|
||||
node.labelStyle = labelStyles;
|
||||
const { shapeSvg, bbox } = await labelHelper(parent, node, getNodeClasses(node));
|
||||
|
||||
const f = 4;
|
||||
const h = bbox.height + node.padding;
|
||||
// const m = h / f;
|
||||
const m = 10;
|
||||
const padding = 12;
|
||||
const w = bbox.width + node.padding + padding;
|
||||
const left = 0;
|
||||
const right = w;
|
||||
const top = -h;
|
||||
const bottom = 0;
|
||||
// const w = bbox.width + 2 * m + node.padding;
|
||||
const points = [
|
||||
{ x: left + padding, y: top },
|
||||
{ x: right, y: top },
|
||||
@ -44,7 +40,7 @@ export async function card(parent: SVGAElement, node: Node): Promise<SVGAElement
|
||||
let polygon: d3.Selection<SVGPolygonElement | SVGGElement, unknown, null, undefined>;
|
||||
const { cssStyles } = node;
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
@ -3,7 +3,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import type { SVG } from '$root/diagram-api/types.js';
|
||||
// @ts-ignore TODO: Fix rough typings
|
||||
import rough from 'roughjs';
|
||||
import { solidStateFill, styles2String } from './handdrawnStyles.js';
|
||||
import { solidStateFill, styles2String } from './handDrawnShapeStyles.js';
|
||||
import { getConfig } from '$root/diagram-api/diagramAPI.js';
|
||||
|
||||
export const choice = (parent: SVG, node: Node) => {
|
||||
@ -25,7 +25,7 @@ export const choice = (parent: SVG, node: Node) => {
|
||||
];
|
||||
|
||||
let choice;
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore TODO: Fix rough typings
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const pointArr = points.map(function (d) {
|
||||
|
@ -5,7 +5,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
export const circle = async (parent: SVGAElement, node: Node): Promise<SVGAElement> => {
|
||||
@ -17,7 +17,7 @@ export const circle = async (parent: SVGAElement, node: Node): Promise<SVGAEleme
|
||||
let circleElem;
|
||||
const { cssStyles } = node;
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import intersect from '../intersect/index.js';
|
||||
|
||||
@ -33,7 +33,7 @@ export const crossedCircle = async (parent: SVGAElement, node: Node) => {
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
||||
if (node.look !== 'handdrawn') {
|
||||
if (node.look !== 'handDrawn') {
|
||||
options.roughness = 0;
|
||||
options.fillStyle = 'solid';
|
||||
}
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
function createCurvedTrapezoidPathD(
|
||||
@ -43,7 +43,7 @@ export const curvedTrapezoid = async (parent: SVGAElement, node: Node) => {
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
||||
if (node.look !== 'handdrawn') {
|
||||
if (node.look !== 'handDrawn') {
|
||||
options.roughness = 0;
|
||||
options.fillStyle = 'solid';
|
||||
}
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
export const createCylinderPathD = (
|
||||
@ -63,7 +63,7 @@ export const cylinder = async (parent: SVGAElement, node: Node) => {
|
||||
let cylinder: d3.Selection<SVGPathElement | SVGGElement, unknown, null, undefined>;
|
||||
const { cssStyles } = node;
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const outerPathData = createOuterCylinderPathD(0, 0, w, h, rx, ry);
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
export function createDividedRectPathD(
|
||||
@ -48,7 +48,7 @@ export const dividedRect = async (parent: SVGAElement, node: Node) => {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
if (node.look !== 'handdrawn') {
|
||||
if (node.look !== 'handDrawn') {
|
||||
options.roughness = 0;
|
||||
options.fillStyle = 'solid';
|
||||
}
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
export const createCylinderPathD = (
|
||||
@ -63,7 +63,7 @@ export const cylinder = async (parent: SVGAElement, node: Node) => {
|
||||
let cylinder: d3.Selection<SVGPathElement | SVGGElement, unknown, null, undefined>;
|
||||
const { cssStyles } = node;
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const outerPathData = createOuterCylinderPathD(0, 0, w, h, rx, ry);
|
||||
|
@ -5,7 +5,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
export const doublecircle = async (parent: SVGAElement, node: Node): Promise<SVGAElement> => {
|
||||
@ -19,7 +19,7 @@ export const doublecircle = async (parent: SVGAElement, node: Node): Promise<SVG
|
||||
let circleGroup;
|
||||
const { cssStyles } = node;
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const outerOptions = userNodeOverrides(node, { roughness: 0.2, strokeWidth: 2.5 });
|
||||
|
@ -5,7 +5,7 @@ import { createRoundedRectPathD } from './roundedRectPath.js';
|
||||
import {
|
||||
userNodeOverrides,
|
||||
styles2String,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
export const drawRect = async (parent: SVGAElement, node: Node, options: RectOptions) => {
|
||||
@ -31,7 +31,7 @@ export const drawRect = async (parent: SVGAElement, node: Node, options: RectOpt
|
||||
ry = options.ry;
|
||||
}
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore TODO: Fix rough typings
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
@ -5,7 +5,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import { createPathFromPoints } from './util.js';
|
||||
|
||||
@ -27,7 +27,7 @@ export const flippedTriangle = async (parent: SVGAElement, node: Node): Promise<
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
if (node.look !== 'handdrawn') {
|
||||
if (node.look !== 'handDrawn') {
|
||||
options.roughness = 0;
|
||||
options.fillStyle = 'solid';
|
||||
}
|
||||
|
@ -3,7 +3,7 @@ import intersect from '../intersect/index.js';
|
||||
import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import type { SVG } from '$root/diagram-api/types.js';
|
||||
import rough from 'roughjs';
|
||||
import { solidStateFill } from './handdrawnStyles.js';
|
||||
import { solidStateFill } from './handDrawnShapeStyles.js';
|
||||
import { getConfig } from '$root/diagram-api/diagramAPI.js';
|
||||
|
||||
export const forkJoin = (parent: SVG, node: Node, dir: string) => {
|
||||
@ -25,7 +25,7 @@ export const forkJoin = (parent: SVG, node: Node, dir: string) => {
|
||||
const y = (-1 * height) / 2;
|
||||
|
||||
let shape;
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore TODO: Fix rough typings
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const roughNode = rc.rectangle(x, y, width, height, solidStateFill(lineColor));
|
||||
|
@ -5,7 +5,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
function createHalfRoundedRectShapePathD(
|
||||
@ -45,7 +45,7 @@ export const halfRoundedRectangle = async (parent: SVGAElement, node: Node) => {
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
||||
if (node.look !== 'handdrawn') {
|
||||
if (node.look !== 'handDrawn') {
|
||||
options.roughness = 0;
|
||||
options.fillStyle = 'solid';
|
||||
}
|
||||
|
@ -3,7 +3,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
|
||||
// Striped fill like start or fork nodes in state diagrams
|
||||
export const solidStateFill = (color: string) => {
|
||||
const { handdrawnSeed } = getConfig();
|
||||
const { handDrawnSeed } = getConfig();
|
||||
return {
|
||||
fill: color,
|
||||
hachureAngle: 120, // angle of hachure,
|
||||
@ -11,7 +11,7 @@ export const solidStateFill = (color: string) => {
|
||||
fillWeight: 2,
|
||||
roughness: 0.7,
|
||||
stroke: color,
|
||||
seed: handdrawnSeed,
|
||||
seed: handDrawnSeed,
|
||||
};
|
||||
};
|
||||
|
||||
@ -72,7 +72,7 @@ export const styles2String = (node: Node) => {
|
||||
// Striped fill like start or fork nodes in state diagrams
|
||||
// TODO remove any
|
||||
export const userNodeOverrides = (node: Node, options: any) => {
|
||||
const { themeVariables, handdrawnSeed } = getConfig();
|
||||
const { themeVariables, handDrawnSeed } = getConfig();
|
||||
const { nodeBorder, mainBkg } = themeVariables;
|
||||
const { stylesMap } = compileStyles(node);
|
||||
|
||||
@ -84,7 +84,7 @@ export const userNodeOverrides = (node: Node, options: any) => {
|
||||
fillStyle: 'hachure', // solid fill
|
||||
fillWeight: 4,
|
||||
stroke: stylesMap.get('stroke') || nodeBorder,
|
||||
seed: handdrawnSeed,
|
||||
seed: handDrawnSeed,
|
||||
strokeWidth: 1.3,
|
||||
},
|
||||
options
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
import { insertPolygonShape } from './insertPolygonShape.js';
|
||||
@ -48,7 +48,7 @@ export const hexagon = async (parent: SVGAElement, node: Node): Promise<SVGAElem
|
||||
let polygon: d3.Selection<SVGPolygonElement | SVGGElement, unknown, null, undefined>;
|
||||
const { cssStyles } = node;
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
@ -5,7 +5,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
export const hourglass = async (parent: SVGAElement, node: Node) => {
|
||||
@ -23,7 +23,7 @@ export const hourglass = async (parent: SVGAElement, node: Node) => {
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
||||
if (node.look !== 'handdrawn') {
|
||||
if (node.look !== 'handDrawn') {
|
||||
options.roughness = 0;
|
||||
options.fillStyle = 'solid';
|
||||
}
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import { insertPolygonShape } from './insertPolygonShape.js';
|
||||
|
||||
@ -40,7 +40,7 @@ export const inv_trapezoid = async (parent: SVGAElement, node: Node): Promise<SV
|
||||
let polygon: d3.Selection<SVGPolygonElement | SVGGElement, unknown, null, undefined>;
|
||||
const { cssStyles } = node;
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import { insertPolygonShape } from './insertPolygonShape.js';
|
||||
|
||||
@ -40,7 +40,7 @@ export const lean_left = async (parent: SVGAElement, node: Node): Promise<SVGAEl
|
||||
let polygon: d3.Selection<SVGPolygonElement | SVGGElement, unknown, null, undefined>;
|
||||
const { cssStyles } = node;
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import { insertPolygonShape } from './insertPolygonShape.js';
|
||||
|
||||
@ -40,7 +40,7 @@ export const lean_right = async (parent: SVGAElement, node: Node): Promise<SVGAE
|
||||
let polygon: d3.Selection<SVGPolygonElement | SVGGElement, unknown, null, undefined>;
|
||||
const { cssStyles } = node;
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
@ -0,0 +1,96 @@
|
||||
import { labelHelper, updateNodeBounds, getNodeClasses } from './util.js';
|
||||
import intersect from '../intersect/index.js';
|
||||
import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import rough from 'roughjs';
|
||||
import { styles2String, userNodeOverrides } from './handDrawnShapeStyles.js';
|
||||
|
||||
export const createCylinderPathWithInnerArcD = (
|
||||
x: number,
|
||||
y: number,
|
||||
width: number,
|
||||
height: number,
|
||||
rx: number,
|
||||
ry: number,
|
||||
outerOffset: number
|
||||
): string => {
|
||||
return [
|
||||
`M${x},${y + ry}`,
|
||||
`a${rx},${ry} 0,0,0 ${width},0`,
|
||||
`a${rx},${ry} 0,0,0 ${-width},0`,
|
||||
`l0,${height}`,
|
||||
`a${rx},${ry} 0,0,0 ${width},0`,
|
||||
`l0,${-height}`,
|
||||
`M${x},${y + ry + outerOffset}`, // Move to the start of the offset top arc
|
||||
`a${rx},${ry} 0,0,0 ${width},0`, // Draw the duplicated top ellipse
|
||||
].join(' ');
|
||||
};
|
||||
|
||||
export const linedCylinder = async (parent: SVGAElement, node: Node) => {
|
||||
const { labelStyles, nodeStyles } = styles2String(node);
|
||||
node.labelStyle = labelStyles;
|
||||
const { shapeSvg, bbox, label } = await labelHelper(parent, node, getNodeClasses(node));
|
||||
const w = bbox.width + node.padding;
|
||||
const rx = w / 2;
|
||||
const ry = rx / (2.5 + w / 50);
|
||||
const h = bbox.height + ry + node.padding;
|
||||
const outerOffset = h * 0.1; // 10% of height
|
||||
|
||||
let cylinder: d3.Selection<SVGPathElement | SVGGElement, unknown, null, undefined>;
|
||||
const { cssStyles } = node;
|
||||
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
const pathData = createCylinderPathWithInnerArcD(0, ry, w, h, rx, ry, outerOffset);
|
||||
const innerLine = rc.path(pathData, options);
|
||||
|
||||
cylinder = shapeSvg.insert(() => innerLine, ':first-child');
|
||||
cylinder.attr('class', 'basic label-container');
|
||||
if (cssStyles) {
|
||||
cylinder.attr('style', cssStyles);
|
||||
}
|
||||
} else {
|
||||
const pathData = createCylinderPathWithInnerArcD(0, 0, w, h, rx, ry, outerOffset);
|
||||
cylinder = shapeSvg
|
||||
.insert('path', ':first-child')
|
||||
.attr('d', pathData)
|
||||
.attr('class', 'basic label-container')
|
||||
.attr('style', cssStyles)
|
||||
.attr('style', nodeStyles);
|
||||
}
|
||||
|
||||
cylinder.attr('label-offset-y', ry);
|
||||
cylinder.attr('transform', `translate(${-w / 2}, ${-(h / 2 + ry)})`);
|
||||
|
||||
updateNodeBounds(node, cylinder);
|
||||
|
||||
label.attr('transform', `translate(${-bbox.width / 2}, ${h / 2 - bbox.height + outerOffset})`);
|
||||
|
||||
node.intersect = function (point) {
|
||||
const pos = intersect.rect(node, point);
|
||||
const x = pos.x - (node.x ?? 0);
|
||||
|
||||
if (
|
||||
rx != 0 &&
|
||||
(Math.abs(x) < (node.width ?? 0) / 2 ||
|
||||
(Math.abs(x) == (node.width ?? 0) / 2 &&
|
||||
Math.abs(pos.y - (node.y ?? 0)) > (node.height ?? 0) / 2 - ry))
|
||||
) {
|
||||
let y = ry * ry * (1 - (x * x) / (rx * rx));
|
||||
if (y != 0) {
|
||||
y = Math.sqrt(y);
|
||||
}
|
||||
y = ry - y;
|
||||
if (point.y - (node.y ?? 0) > 0) {
|
||||
y = -y;
|
||||
}
|
||||
|
||||
pos.y += y;
|
||||
}
|
||||
|
||||
return pos;
|
||||
};
|
||||
|
||||
return shapeSvg;
|
||||
};
|
@ -0,0 +1,87 @@
|
||||
import { labelHelper, getNodeClasses, updateNodeBounds, createPathFromPoints } from './util.js';
|
||||
import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import intersect from '../intersect/index.js';
|
||||
|
||||
export const multiRect = async (parent: SVGAElement, node: Node) => {
|
||||
const { labelStyles, nodeStyles } = styles2String(node);
|
||||
node.labelStyle = labelStyles;
|
||||
const { shapeSvg, bbox, label } = await labelHelper(parent, node, getNodeClasses(node));
|
||||
const h = bbox.height + node.padding;
|
||||
const w = bbox.width + node.padding;
|
||||
const x = -w / 2;
|
||||
const y = -h / 2;
|
||||
const rectOffset = 5;
|
||||
const { cssStyles } = node;
|
||||
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
||||
const rectPoints = [
|
||||
{ x, y },
|
||||
{ x: x + w, y },
|
||||
{ x: x + w, y: y + h },
|
||||
{ x, y: y + h },
|
||||
];
|
||||
const secondRectPoints = [
|
||||
{ x: x + rectOffset, y: y - rectOffset },
|
||||
{ x: x + w + rectOffset, y: y - rectOffset },
|
||||
{ x: x + w + rectOffset, y: y + h - rectOffset },
|
||||
{ x: x + rectOffset, y: y + h - rectOffset },
|
||||
];
|
||||
const thirdRectPoints = [
|
||||
{ x: x + 2 * rectOffset, y: y - 2 * rectOffset },
|
||||
{ x: x + w + 2 * rectOffset, y: y - 2 * rectOffset },
|
||||
{ x: x + w + 2 * rectOffset, y: y + h - 2 * rectOffset },
|
||||
{ x: x + 2 * rectOffset, y: y + h - 2 * rectOffset },
|
||||
];
|
||||
|
||||
if (node.look !== 'handdrawn') {
|
||||
options.roughness = 0;
|
||||
options.fillStyle = 'solid';
|
||||
}
|
||||
|
||||
const rectPath = createPathFromPoints(rectPoints);
|
||||
const rectNode = rc.path(rectPath, options);
|
||||
|
||||
const secondRectPath = createPathFromPoints(secondRectPoints);
|
||||
const secondRectNode = rc.path(secondRectPath, options);
|
||||
|
||||
const thirdRectPath = createPathFromPoints(thirdRectPoints);
|
||||
const thirdRectNode = rc.path(thirdRectPath, options);
|
||||
|
||||
const taggedRect = shapeSvg.insert('g', ':first-child');
|
||||
taggedRect.insert(() => thirdRectNode, ':first-child');
|
||||
taggedRect.insert(() => secondRectNode);
|
||||
taggedRect.insert(() => rectNode);
|
||||
|
||||
taggedRect.attr('class', 'basic label-container');
|
||||
|
||||
if (cssStyles) {
|
||||
taggedRect.attr('style', cssStyles);
|
||||
}
|
||||
|
||||
if (nodeStyles) {
|
||||
taggedRect.attr('style', nodeStyles);
|
||||
}
|
||||
|
||||
taggedRect.attr('transform', `translate(-${rectOffset},${rectOffset})`);
|
||||
label.attr(
|
||||
'transform',
|
||||
`translate(${-(bbox.width / 2) - rectOffset}, ${h / 2 - bbox.height - 4 * rectOffset})`
|
||||
);
|
||||
|
||||
updateNodeBounds(node, taggedRect);
|
||||
|
||||
node.intersect = function (point) {
|
||||
const pos = intersect.rect(node, point);
|
||||
return pos;
|
||||
};
|
||||
|
||||
return shapeSvg;
|
||||
};
|
@ -6,7 +6,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import rough from 'roughjs';
|
||||
|
||||
export const note = async (parent: SVGAElement, node: Node) => {
|
||||
const { themeVariables, handdrawnSeed } = getConfig();
|
||||
const { themeVariables, handDrawnSeed } = getConfig();
|
||||
const { noteBorderColor, noteBkgColor } = themeVariables;
|
||||
|
||||
const useHtmlLabels = node.useHtmlLabels;
|
||||
@ -23,7 +23,7 @@ export const note = async (parent: SVGAElement, node: Node) => {
|
||||
const x = -totalWidth / 2;
|
||||
const y = -totalHeight / 2;
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// add the rect
|
||||
// @ts-ignore TODO: Fix rough typings
|
||||
const rc = rough.svg(shapeSvg);
|
||||
@ -31,7 +31,7 @@ export const note = async (parent: SVGAElement, node: Node) => {
|
||||
roughness: 0.7,
|
||||
fill: noteBkgColor,
|
||||
fillWeight: 3,
|
||||
seed: handdrawnSeed,
|
||||
seed: handDrawnSeed,
|
||||
// fillStyle: 'solid', // solid fill'
|
||||
stroke: noteBorderColor,
|
||||
});
|
||||
|
@ -5,7 +5,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import { insertPolygonShape } from './insertPolygonShape.js';
|
||||
|
||||
@ -38,7 +38,7 @@ export const question = async (parent: SVGAElement, node: Node): Promise<SVGAEle
|
||||
let polygon: d3.Selection<SVGPolygonElement | SVGGElement, unknown, null, undefined>;
|
||||
const { cssStyles } = node;
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import { insertPolygonShape } from './insertPolygonShape.js';
|
||||
|
||||
@ -40,7 +40,7 @@ export const rect_left_inv_arrow = async (
|
||||
let polygon;
|
||||
const { cssStyles } = node;
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
@ -7,7 +7,7 @@ import intersect from '../intersect/index.js';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import { getConfig } from '$root/diagram-api/diagramAPI.js';
|
||||
import { createRoundedRectPathD } from './roundedRectPath.js';
|
||||
@ -104,7 +104,7 @@ export const rectWithTitle = async (parent: SVGElement, node: Node) => {
|
||||
const y = -bbox.height / 2 - halfPadding;
|
||||
let rect;
|
||||
let innerLine;
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore No typings for rough
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
@ -134,6 +134,7 @@ export const rectWithTitle = async (parent: SVGElement, node: Node) => {
|
||||
innerLine = g.insert('line');
|
||||
rect
|
||||
.attr('class', 'outer title-state')
|
||||
.attr('style', nodeStyles)
|
||||
.attr('x', -bbox.width / 2 - halfPadding)
|
||||
.attr('y', -bbox.height / 2 - halfPadding)
|
||||
.attr('width', bbox.width + (node.padding || 0))
|
||||
|
@ -4,10 +4,8 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import { insertPolygonShape } from './insertPolygonShape.js';
|
||||
import { createPathFromPoints } from './util.js';
|
||||
|
||||
export const shadedProcess = async (parent: SVGAElement, node: Node) => {
|
||||
const { labelStyles, nodeStyles } = styles2String(node);
|
||||
@ -18,26 +16,13 @@ export const shadedProcess = async (parent: SVGAElement, node: Node) => {
|
||||
const h = bbox.height + node.padding;
|
||||
const x = -bbox.width / 2 - halfPadding;
|
||||
const y = -bbox.height / 2 - halfPadding;
|
||||
let rect;
|
||||
const { cssStyles } = node;
|
||||
const points = [
|
||||
{ x: 0, y: 0 },
|
||||
{ x: w, y: 0 },
|
||||
{ x: w, y: -h },
|
||||
{ x: 0, y: -h },
|
||||
{ x: 0, y: 0 },
|
||||
{ x: -8, y: 0 },
|
||||
{ x: w + 8, y: 0 },
|
||||
{ x: w + 8, y: -h },
|
||||
{ x: -8, y: -h },
|
||||
{ x: -8, y: 0 },
|
||||
];
|
||||
|
||||
const { cssStyles } = node;
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
||||
if (node.look !== 'handdrawn') {
|
||||
if (node.look !== 'handDrawn') {
|
||||
options.roughness = 0;
|
||||
options.fillStyle = 'solid';
|
||||
}
|
||||
@ -46,7 +31,7 @@ export const shadedProcess = async (parent: SVGAElement, node: Node) => {
|
||||
const l1 = rc.line(x, y, x, y + h, options);
|
||||
|
||||
shapeSvg.insert(() => l1, ':first-child');
|
||||
rect = shapeSvg.insert(() => roughNode, ':first-child');
|
||||
const rect = shapeSvg.insert(() => roughNode, ':first-child');
|
||||
|
||||
rect.attr('class', 'basic label-container').attr('style', cssStyles);
|
||||
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
function createSlopedRectPathD(x: number, y: number, totalWidth: number, totalHeight: number) {
|
||||
@ -36,7 +36,7 @@ export const slopedRect = async (parent: SVGAElement, node: Node) => {
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
||||
if (node.look !== 'handdrawn') {
|
||||
if (node.look !== 'handDrawn') {
|
||||
options.roughness = 0;
|
||||
options.fillStyle = 'solid';
|
||||
}
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import { createRoundedRectPathD } from './roundedRectPath.js';
|
||||
|
||||
@ -63,7 +63,7 @@ export const stadium = async (parent: SVGAElement, node: Node) => {
|
||||
|
||||
let rect;
|
||||
const { cssStyles } = node;
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
@ -3,7 +3,7 @@ import intersect from '../intersect/index.js';
|
||||
import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import type { SVG } from '$root/diagram-api/types.js';
|
||||
import rough from 'roughjs';
|
||||
import { solidStateFill } from './handdrawnStyles.js';
|
||||
import { solidStateFill } from './handDrawnShapeStyles.js';
|
||||
import { getConfig } from '$root/diagram-api/diagramAPI.js';
|
||||
|
||||
export const stateEnd = (parent: SVG, node: Node) => {
|
||||
@ -16,7 +16,7 @@ export const stateEnd = (parent: SVG, node: Node) => {
|
||||
|
||||
let circle;
|
||||
let innerCircle;
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore TODO: Fix rough typings
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const roughNode = rc.circle(0, 0, 14, { ...solidStateFill(lineColor), roughness: 0.5 });
|
||||
|
@ -3,7 +3,7 @@ import intersect from '../intersect/index.js';
|
||||
import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import type { SVG } from '$root/diagram-api/types.js';
|
||||
import rough from 'roughjs';
|
||||
import { solidStateFill } from './handdrawnStyles.js';
|
||||
import { solidStateFill } from './handDrawnShapeStyles.js';
|
||||
import { getConfig } from '$root/diagram-api/diagramAPI.js';
|
||||
|
||||
export const stateStart = (parent: SVG, node: Node) => {
|
||||
@ -16,7 +16,7 @@ export const stateStart = (parent: SVG, node: Node) => {
|
||||
.attr('id', node.domId || node.id);
|
||||
|
||||
let circle;
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore TODO: Fix rough typings
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const roughNode = rc.circle(0, 0, 14, solidStateFill(lineColor));
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import { insertPolygonShape } from './insertPolygonShape.js';
|
||||
|
||||
@ -43,8 +43,7 @@ export const subroutine = async (parent: SVGAElement, node: Node) => {
|
||||
const h = bbox.height + node.padding;
|
||||
const x = -bbox.width / 2 - halfPadding;
|
||||
const y = -bbox.height / 2 - halfPadding;
|
||||
let rect;
|
||||
const { cssStyles } = node;
|
||||
|
||||
const points = [
|
||||
{ x: 0, y: 0 },
|
||||
{ x: w, y: 0 },
|
||||
@ -58,7 +57,7 @@ export const subroutine = async (parent: SVGAElement, node: Node) => {
|
||||
{ x: -8, y: 0 },
|
||||
];
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
@ -69,9 +68,10 @@ export const subroutine = async (parent: SVGAElement, node: Node) => {
|
||||
|
||||
shapeSvg.insert(() => l1, ':first-child');
|
||||
shapeSvg.insert(() => l2, ':first-child');
|
||||
rect = shapeSvg.insert(() => roughNode, ':first-child');
|
||||
|
||||
const rect = shapeSvg.insert(() => roughNode, ':first-child');
|
||||
const { cssStyles } = node;
|
||||
rect.attr('class', 'basic label-container').attr('style', cssStyles);
|
||||
updateNodeBounds(node, rect);
|
||||
} else {
|
||||
const el = insertPolygonShape(shapeSvg, w, h, points);
|
||||
if (nodeStyles) {
|
||||
|
@ -0,0 +1,73 @@
|
||||
import { labelHelper, getNodeClasses, updateNodeBounds, createPathFromPoints } from './util.js';
|
||||
import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import intersect from '../intersect/index.js';
|
||||
|
||||
export const taggedRect = async (parent: SVGAElement, node: Node) => {
|
||||
const { labelStyles, nodeStyles } = styles2String(node);
|
||||
node.labelStyle = labelStyles;
|
||||
const { shapeSvg, bbox } = await labelHelper(parent, node, getNodeClasses(node));
|
||||
const h = bbox.height + node.padding;
|
||||
const w = bbox.width + node.padding;
|
||||
const x = -w / 2;
|
||||
const y = -h / 2;
|
||||
const tagWidth = 0.2 * w;
|
||||
const tagHeight = 0.2 * h;
|
||||
const { cssStyles } = node;
|
||||
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
||||
const rectPoints = [
|
||||
{ x, y },
|
||||
{ x: x + w, y },
|
||||
{ x: x + w, y: y + h },
|
||||
{ x, y: y + h },
|
||||
];
|
||||
|
||||
const tagPoints = [
|
||||
{ x: x + w - tagWidth, y: y + h },
|
||||
{ x: x + w, y: y + h },
|
||||
{ x: x + w, y: y + h - tagHeight },
|
||||
];
|
||||
|
||||
if (node.look !== 'handDrawn') {
|
||||
options.roughness = 0;
|
||||
options.fillStyle = 'solid';
|
||||
}
|
||||
|
||||
const rectPath = createPathFromPoints(rectPoints);
|
||||
const rectNode = rc.path(rectPath, options);
|
||||
|
||||
const tagPath = createPathFromPoints(tagPoints);
|
||||
const tagNode = rc.path(tagPath, options);
|
||||
|
||||
const taggedRect = shapeSvg.insert('g', ':first-child');
|
||||
taggedRect.insert(() => rectNode, ':first-child');
|
||||
taggedRect.insert(() => tagNode);
|
||||
|
||||
taggedRect.attr('class', 'basic label-container');
|
||||
|
||||
if (cssStyles) {
|
||||
taggedRect.attr('style', cssStyles);
|
||||
}
|
||||
|
||||
if (nodeStyles) {
|
||||
taggedRect.attr('style', nodeStyles);
|
||||
}
|
||||
|
||||
updateNodeBounds(node, taggedRect);
|
||||
|
||||
node.intersect = function (point) {
|
||||
const pos = intersect.rect(node, point);
|
||||
|
||||
return pos;
|
||||
};
|
||||
|
||||
return shapeSvg;
|
||||
};
|
@ -1,12 +1,12 @@
|
||||
import { labelHelper, updateNodeBounds, getNodeClasses } from './util.js';
|
||||
import intersect from '../intersect/index.js';
|
||||
import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import { styles2String } from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
import { styles2String } from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
|
||||
export async function text(parent: SVGAElement, node: Node): Promise<SVGAElement> {
|
||||
const { labelStyles, nodeStyles } = styles2String(node);
|
||||
node.labelStyle = labelStyles;
|
||||
// console.log('IPI labelStyles:', labelStyles);
|
||||
|
||||
const { shapeSvg, bbox } = await labelHelper(parent, node, getNodeClasses(node));
|
||||
|
||||
const totalWidth = Math.max(bbox.width + node.padding, node?.width || 0);
|
||||
@ -14,12 +14,7 @@ export async function text(parent: SVGAElement, node: Node): Promise<SVGAElement
|
||||
const x = -totalWidth / 2;
|
||||
const y = -totalHeight / 2;
|
||||
|
||||
// log.info('IPI node = ', node);
|
||||
|
||||
let rect;
|
||||
const { cssStyles } = node;
|
||||
|
||||
rect = shapeSvg.insert('rect', ':first-child');
|
||||
const rect = shapeSvg.insert('rect', ':first-child');
|
||||
|
||||
rect
|
||||
.attr('class', 'text')
|
||||
|
@ -3,7 +3,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import intersect from '../intersect/index.js';
|
||||
|
||||
@ -30,7 +30,7 @@ export const titledCylinder = async (parent: SVGAElement, node: Node) => {
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
||||
if (node.look !== 'handdrawn') {
|
||||
if (node.look !== 'handDrawn') {
|
||||
options.roughness = 0;
|
||||
options.fillStyle = 'solid';
|
||||
}
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import { insertPolygonShape } from './insertPolygonShape.js';
|
||||
|
||||
@ -40,7 +40,7 @@ export const trapezoid = async (parent: SVGAElement, node: Node): Promise<SVGAEl
|
||||
let polygon: d3.Selection<SVGPolygonElement | SVGGElement, unknown, null, undefined>;
|
||||
const { cssStyles } = node;
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
function createTrapezoidalPentagonPathD(width = 100, height = 80) {
|
||||
@ -35,7 +35,7 @@ export const trapezoidalPentagon = async (parent: SVGAElement, node: Node) => {
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
||||
if (node.look !== 'handdrawn') {
|
||||
if (node.look !== 'handDrawn') {
|
||||
options.roughness = 0;
|
||||
options.fillStyle = 'solid';
|
||||
}
|
||||
|
@ -5,7 +5,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
import { createPathFromPoints } from './util.js';
|
||||
|
||||
@ -27,7 +27,7 @@ export const triangle = async (parent: SVGAElement, node: Node): Promise<SVGAEle
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
if (node.look !== 'handdrawn') {
|
||||
if (node.look !== 'handDrawn') {
|
||||
options.roughness = 0;
|
||||
options.fillStyle = 'solid';
|
||||
}
|
||||
|
@ -133,7 +133,7 @@ export function insertPolygonShape(parent, w, h, points) {
|
||||
}
|
||||
|
||||
export const getNodeClasses = (node, extra) =>
|
||||
(node.look === 'handdrawn' ? 'rough-node' : 'node') + ' ' + node.cssClasses + ' ' + (extra || '');
|
||||
(node.look === 'handDrawn' ? 'rough-node' : 'node') + ' ' + node.cssClasses + ' ' + (extra || '');
|
||||
|
||||
export function createPathFromPoints(points) {
|
||||
const pointStrings = points.map((p, i) => `${i === 0 ? 'M' : 'L'}${p.x},${p.y}`);
|
||||
|
@ -0,0 +1,80 @@
|
||||
import { labelHelper, updateNodeBounds, getNodeClasses } from './util.js';
|
||||
import intersect from '../intersect/index.js';
|
||||
import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import rough from 'roughjs';
|
||||
import { styles2String, userNodeOverrides } from './handDrawnShapeStyles.js';
|
||||
|
||||
export function createWaveEdgedRectanglePathD(width: number, height: number) {
|
||||
// Calculate control points
|
||||
const rightX = width;
|
||||
const midX = width / 2;
|
||||
const controlY1 = height * 0.8;
|
||||
const controlY2 = height * 1.15;
|
||||
const endY = height * 0.94;
|
||||
|
||||
// Construct the path
|
||||
const path = `M0 0
|
||||
H${rightX}
|
||||
V${controlY1}
|
||||
C${midX} ${controlY1}, ${midX} ${controlY2}, 0 ${endY}
|
||||
Z`;
|
||||
|
||||
return path;
|
||||
}
|
||||
|
||||
export const waveEdgedRectangle = async (parent: SVGAElement, node: Node) => {
|
||||
const { labelStyles, nodeStyles } = styles2String(node);
|
||||
node.labelStyle = labelStyles;
|
||||
const { shapeSvg, bbox } = await labelHelper(parent, node, getNodeClasses(node));
|
||||
const w = bbox.width + node.padding;
|
||||
const h = bbox.height + node.padding + 20;
|
||||
|
||||
const { cssStyles } = node;
|
||||
|
||||
const rightX = w;
|
||||
const midX = w / 2;
|
||||
const controlY1 = h * 0.8;
|
||||
const controlY2 = h * 1.15;
|
||||
const endY = h * 0.94;
|
||||
|
||||
const points = [
|
||||
{ x: 0, y: 0 },
|
||||
{ x: rightX, y: 0 },
|
||||
{ x: rightX, y: controlY1 },
|
||||
{ x: midX, y: controlY1 },
|
||||
{ x: midX, y: controlY2 * 0.8 },
|
||||
{ x: 0, y: endY },
|
||||
];
|
||||
const pathData = createWaveEdgedRectanglePathD(w, h);
|
||||
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const options = userNodeOverrides(node, {});
|
||||
|
||||
if (node.look !== 'handDrawn') {
|
||||
options.roughness = 0;
|
||||
options.fillStyle = 'solid';
|
||||
}
|
||||
const shapeNode = rc.path(pathData, options);
|
||||
const shape = shapeSvg.insert(() => shapeNode, ':first-child');
|
||||
shape.attr('class', 'basic label-container');
|
||||
|
||||
if (cssStyles) {
|
||||
shape.attr('style', cssStyles);
|
||||
}
|
||||
|
||||
if (nodeStyles) {
|
||||
shape.attr('style', nodeStyles);
|
||||
}
|
||||
|
||||
shape.attr('transform', `translate(${-w / 2}, ${-h / 2})`);
|
||||
|
||||
updateNodeBounds(node, shape);
|
||||
|
||||
node.intersect = function (point) {
|
||||
const pos = intersect.polygon(node, points, point);
|
||||
return pos;
|
||||
};
|
||||
|
||||
return shapeSvg;
|
||||
};
|
@ -4,7 +4,7 @@ import type { Node } from '$root/rendering-util/types.d.ts';
|
||||
import {
|
||||
styles2String,
|
||||
userNodeOverrides,
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handdrawnStyles.js';
|
||||
} from '$root/rendering-util/rendering-elements/shapes/handDrawnShapeStyles.js';
|
||||
import rough from 'roughjs';
|
||||
|
||||
function createWaveRectanglePathD(x: number, y: number, width: number, height: number) {
|
||||
@ -32,7 +32,7 @@ export const waveRectangle = async (parent: SVGAElement, node: Node) => {
|
||||
let shape: d3.Selection<SVGPathElement | SVGGElement, unknown, null, undefined>;
|
||||
const { cssStyles } = node;
|
||||
|
||||
if (node.look === 'handdrawn') {
|
||||
if (node.look === 'handDrawn') {
|
||||
// @ts-ignore - rough is not typed
|
||||
const rc = rough.svg(shapeSvg);
|
||||
const pathData = createWaveRectanglePathD(0, 0, w, h);
|
||||
|
@ -94,7 +94,7 @@ interface Edge {
|
||||
labelStyle?: string[];
|
||||
minlen?: number;
|
||||
pattern?: string;
|
||||
thickness?: 'normal' | 'thick' | 'invisible';
|
||||
thickness?: 'normal' | 'thick' | 'invisible' | 'dotted';
|
||||
look?: string;
|
||||
}
|
||||
|
||||
|
@ -79,11 +79,11 @@ properties:
|
||||
type: string
|
||||
enum:
|
||||
- classic
|
||||
- handdrawn
|
||||
- handDrawn
|
||||
default: 'classic'
|
||||
handdrawnSeed:
|
||||
handDrawnSeed:
|
||||
description: |
|
||||
Defines the seed to be used when using handdrawn look. This is important for the automated tests as they will always find differences without the seed. The default value is 0 which gives a random seed.
|
||||
Defines the seed to be used when using handDrawn look. This is important for the automated tests as they will always find differences without the seed. The default value is 0 which gives a random seed.
|
||||
type: number
|
||||
default: 0
|
||||
layout:
|
||||
|
@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@mermaid-js/parser",
|
||||
"version": "0.1.0-rc.1",
|
||||
"version": "0.1.0-rc.2",
|
||||
"description": "MermaidJS parser",
|
||||
"author": "Yokozuna59",
|
||||
"contributors": [
|
||||
|
3309
pnpm-lock.yaml
generated
3309
pnpm-lock.yaml
generated
File diff suppressed because it is too large
Load Diff
Loading…
x
Reference in New Issue
Block a user