@likec4/diagram 1.59.2 → 1.59.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (233) hide show
  1. package/README.md +53 -0
  2. package/dist/LikeC4Diagram.d.ts +1 -1
  3. package/dist/LikeC4Diagram.js +36 -21
  4. package/dist/LikeC4Diagram.props.d.ts +23 -0
  5. package/dist/LikeC4MantineProvider.d.ts +24 -0
  6. package/dist/LikeC4MantineProvider.js +156 -0
  7. package/dist/LikeC4ProjectsOverview.js +1 -1
  8. package/dist/LikeC4ProjectsProvider.d.ts +17 -2
  9. package/dist/LikeC4Styles.d.ts +13 -3
  10. package/dist/LikeC4Styles.js +10 -6
  11. package/dist/LikeC4View.js +2 -2
  12. package/dist/StaticLikeC4Diagram.d.ts +1 -1
  13. package/dist/base/BaseXYFlow.d.ts +1 -1
  14. package/dist/base/BaseXYFlow.js +19 -9
  15. package/dist/base/const.d.ts +1 -0
  16. package/dist/base/const.js +3 -1
  17. package/dist/base-primitives/Markdown.d.ts +3 -3
  18. package/dist/base-primitives/compound/CompoundNodeContainer.js +2 -3
  19. package/dist/base-primitives/compound/CompoundTitle.js +5 -4
  20. package/dist/base-primitives/compound/actionbtns.css.d.ts +3 -3
  21. package/dist/base-primitives/compound/actionbtns.css.js +3 -3
  22. package/dist/base-primitives/element/ElementData.js +6 -1
  23. package/dist/base-primitives/element/ElementShape.js +9 -10
  24. package/dist/base-primitives/element/ElementTags.d.ts +2 -2
  25. package/dist/base-primitives/element/ElementTags.js +5 -5
  26. package/dist/components/EmptyBox.d.ts +3 -0
  27. package/dist/components/EmptyBox.js +9 -0
  28. package/dist/components/ErrorFallback.js +7 -6
  29. package/dist/components/FloatingWindow.d.ts +18 -0
  30. package/dist/components/FloatingWindow.js +89 -0
  31. package/dist/components/Link.js +7 -7
  32. package/dist/components/NavigationPanel.d.ts +2 -2
  33. package/dist/components/NavigationPanel.js +5 -6
  34. package/dist/components/SearchControl.css.js +10 -12
  35. package/dist/components/ViewIcon.d.ts +11 -0
  36. package/dist/components/ViewIcon.js +71 -0
  37. package/dist/context/CurrentViewModelProvider.js +2 -1
  38. package/dist/context/DiagramEventHandlers.js +4 -2
  39. package/dist/context/EnsureMantine.js +3 -3
  40. package/dist/context/IconRenderer.d.ts +2 -1
  41. package/dist/context/IconRenderer.js +78 -26
  42. package/dist/context/LikeC4ProjectsContext.d.ts +3 -2
  43. package/dist/context/TagStylesContext.d.ts +11 -4
  44. package/dist/context/TagStylesContext.js +39 -27
  45. package/dist/custom/index.d.ts +3 -0
  46. package/dist/custom/index.js +7 -4
  47. package/dist/editor/LikeC4EditorCallbacks.d.ts +20 -1
  48. package/dist/editor/LikeC4EditorCallbacks.js +4 -1
  49. package/dist/editor/actor/setup.d.ts +1 -0
  50. package/dist/editor/actor/setup.js +17 -12
  51. package/dist/editor/actor/state.sync-queue.js +1 -0
  52. package/dist/editor/applyChangesToManualLayout.js +5 -2
  53. package/dist/editor/index.d.ts +1 -1
  54. package/dist/editor/useEditorActorLogic.js +10 -3
  55. package/dist/hooks/safeContext.d.ts +12 -4
  56. package/dist/hooks/safeContext.js +2 -2
  57. package/dist/hooks/useCurrentView.js +5 -5
  58. package/dist/hooks/useDiagram.js +3 -23
  59. package/dist/hooks/useDiagramCompareLayout.d.ts +16 -6
  60. package/dist/hooks/useDiagramCompareLayout.js +20 -17
  61. package/dist/hooks/useEditorActor.js +3 -5
  62. package/dist/hooks/useLikeC4Model.js +8 -3
  63. package/dist/hooks/useLikeC4Project.d.ts +4 -3
  64. package/dist/hooks/useOverlaysActor.d.ts +1 -1
  65. package/dist/hooks/useUpdateEffect.js +2 -1
  66. package/dist/index.d.ts +6 -4
  67. package/dist/index.js +8 -6
  68. package/dist/likec4diagram/DiagramUI.js +4 -3
  69. package/dist/likec4diagram/DiagramXYFlow.d.ts +6 -0
  70. package/dist/likec4diagram/DiagramXYFlow.js +33 -19
  71. package/dist/likec4diagram/custom/edges/EdgeDrifts.js +4 -4
  72. package/dist/likec4diagram/custom/edges/RelationshipEdge.js +2 -4
  73. package/dist/likec4diagram/custom/edges/SequenceStepEdge.js +1 -3
  74. package/dist/likec4diagram/custom/edges/edges.css.js +13 -13
  75. package/dist/likec4diagram/custom/edges/useRelationshipEdgePath.js +3 -2
  76. package/dist/likec4diagram/custom/nodes/NodeDrifts.js +2 -2
  77. package/dist/likec4diagram/custom/nodes/NodeNotes.js +4 -4
  78. package/dist/likec4diagram/custom/nodes/SequenceActorNode.js +2 -2
  79. package/dist/likec4diagram/custom/nodes/SequenceSubFlow.js +8 -5
  80. package/dist/likec4diagram/custom/nodes/nodes.js +8 -5
  81. package/dist/likec4diagram/custom/nodes/toolbar/ColorButton.js +2 -2
  82. package/dist/likec4diagram/custom/nodes/toolbar/Toolbar.js +9 -8
  83. package/dist/likec4diagram/custom/nodes/toolbar/styles.css.js +1 -1
  84. package/dist/likec4diagram/relationship-popover/RelationshipPopover.js +3 -2
  85. package/dist/likec4diagram/relationship-popover/components.d.ts +1 -1
  86. package/dist/likec4diagram/relationship-popover/components.js +6 -2
  87. package/dist/likec4diagram/state/DiagramActorProvider.d.ts +7 -2
  88. package/dist/likec4diagram/state/DiagramActorProvider.js +20 -4
  89. package/dist/likec4diagram/state/assign.js +1 -1
  90. package/dist/likec4diagram/state/createViewChange.js +1 -6
  91. package/dist/likec4diagram/state/diagram-api.d.ts +2 -2
  92. package/dist/likec4diagram/state/diagram-api.js +3 -2
  93. package/dist/likec4diagram/state/machine.actions.js +15 -8
  94. package/dist/likec4diagram/state/machine.actions.layout.d.ts +1 -0
  95. package/dist/likec4diagram/state/machine.actions.layout.js +7 -5
  96. package/dist/likec4diagram/state/machine.setup.d.ts +10 -1
  97. package/dist/likec4diagram/state/machine.setup.js +15 -9
  98. package/dist/likec4diagram/state/machine.state.initializing.d.ts +2 -26
  99. package/dist/likec4diagram/state/machine.state.initializing.js +9 -6
  100. package/dist/likec4diagram/state/machine.state.navigating.js +1 -1
  101. package/dist/likec4diagram/state/machine.state.ready.d.ts +134 -3
  102. package/dist/likec4diagram/state/machine.state.ready.js +2 -1
  103. package/dist/likec4diagram/state/machine.state.ready.walkthrough.d.ts +106 -1
  104. package/dist/likec4diagram/state/machine.state.ready.walkthrough.js +40 -7
  105. package/dist/likec4diagram/state/utils.d.ts +1 -1
  106. package/dist/likec4diagram/state/utils.js +7 -4
  107. package/dist/likec4diagram/ui/FloatingSequenceActors.js +2 -1
  108. package/dist/likec4diagram/ui/LayoutDriftFrame.js +16 -10
  109. package/dist/likec4diagram/ui/index.d.ts +1 -1
  110. package/dist/likec4diagram/ui/notation/NotationPanel.css.js +13 -15
  111. package/dist/likec4diagram/ui/notation/NotationPanel.js +9 -9
  112. package/dist/likec4diagram/ui/sequence-outline/ActiveTrail.d.ts +9 -0
  113. package/dist/likec4diagram/ui/sequence-outline/ActiveTrail.js +81 -0
  114. package/dist/likec4diagram/ui/sequence-outline/FlowRow.d.ts +11 -0
  115. package/dist/likec4diagram/ui/sequence-outline/FlowRow.js +70 -0
  116. package/dist/likec4diagram/ui/sequence-outline/OutlineBody.d.ts +2 -0
  117. package/dist/likec4diagram/ui/sequence-outline/OutlineBody.js +106 -0
  118. package/dist/likec4diagram/ui/sequence-outline/OutlineHeader.d.ts +2 -0
  119. package/dist/likec4diagram/ui/sequence-outline/OutlineHeader.js +140 -0
  120. package/dist/likec4diagram/ui/sequence-outline/OutlineNodes.d.ts +17 -0
  121. package/dist/likec4diagram/ui/sequence-outline/OutlineNodes.js +83 -0
  122. package/dist/likec4diagram/ui/sequence-outline/SequenceOutlinePanel.d.ts +4 -0
  123. package/dist/likec4diagram/ui/sequence-outline/SequenceOutlinePanel.js +49 -525
  124. package/dist/likec4diagram/ui/sequence-outline/StepBadge.d.ts +8 -0
  125. package/dist/likec4diagram/ui/sequence-outline/StepBadge.js +52 -0
  126. package/dist/likec4diagram/ui/sequence-outline/StepRow.d.ts +7 -0
  127. package/dist/likec4diagram/ui/sequence-outline/StepRow.js +190 -0
  128. package/dist/likec4diagram/ui/sequence-outline/StoreProvider.d.ts +238 -0
  129. package/dist/likec4diagram/ui/sequence-outline/StoreProvider.js +94 -0
  130. package/dist/likec4diagram/ui/sequence-outline/depth-of-field.d.ts +21 -0
  131. package/dist/likec4diagram/ui/sequence-outline/depth-of-field.js +71 -0
  132. package/dist/likec4diagram/ui/sequence-outline/index.d.ts +2 -0
  133. package/dist/likec4diagram/ui/sequence-outline/motion.d.ts +13 -0
  134. package/dist/likec4diagram/ui/sequence-outline/motion.js +21 -0
  135. package/dist/likec4diagram/ui/sequence-outline/presentation.d.ts +10 -0
  136. package/dist/likec4diagram/ui/sequence-outline/presentation.js +80 -0
  137. package/dist/likec4diagram/ui/sequence-outline/tree.d.ts +9 -0
  138. package/dist/likec4diagram/ui/sequence-outline/tree.js +67 -0
  139. package/dist/likec4diagram/ui/sequence-outline/{state.d.ts → types.d.ts} +4 -2
  140. package/dist/likec4diagram/ui/sequence-outline/types.js +12 -0
  141. package/dist/likec4diagram/useLayoutConstraints.js +13 -1
  142. package/dist/likec4diagram/xyflow-sequence/layouter.js +8 -10
  143. package/dist/likec4diagram/xyflow-sequence/sequence-view-to-xy.js +1 -0
  144. package/dist/likec4diagram/xyflow-sequence/utils.js +0 -1
  145. package/dist/navigationpanel/NavigationPanel.js +45 -41
  146. package/dist/navigationpanel/NavigationPanelControls.js +102 -63
  147. package/dist/navigationpanel/NavigationPanelDropdown.js +52 -77
  148. package/dist/navigationpanel/_common.d.ts +6 -6
  149. package/dist/navigationpanel/_common.js +31 -42
  150. package/dist/navigationpanel/actor.actions.js +6 -5
  151. package/dist/navigationpanel/actor.js +2 -2
  152. package/dist/navigationpanel/actor.setup.d.ts +6 -6
  153. package/dist/navigationpanel/actor.setup.js +2 -1
  154. package/dist/navigationpanel/comparepanel/CompareActionsMenu.js +2 -4
  155. package/dist/navigationpanel/comparepanel/ComparePanel.js +8 -10
  156. package/dist/navigationpanel/comparepanel/DriftsSummary.d.ts +1 -1
  157. package/dist/navigationpanel/comparepanel/DriftsSummary.js +11 -9
  158. package/dist/navigationpanel/controls/LayoutWarning.js +69 -72
  159. package/dist/navigationpanel/controls/NavigationButtons.d.ts +1 -1
  160. package/dist/navigationpanel/controls/NavigationButtons.js +8 -8
  161. package/dist/navigationpanel/controls/OpenSource.d.ts +1 -1
  162. package/dist/navigationpanel/controls/OpenSource.js +5 -8
  163. package/dist/navigationpanel/controls/SearchControl.js +24 -9
  164. package/dist/navigationpanel/controls/ToggleReadonly.d.ts +4 -1
  165. package/dist/navigationpanel/controls/ToggleReadonly.js +56 -76
  166. package/dist/navigationpanel/controls/ViewDetailsButton.d.ts +5 -0
  167. package/dist/navigationpanel/controls/ViewDetailsButton.js +121 -0
  168. package/dist/navigationpanel/controls/index.d.ts +1 -1
  169. package/dist/navigationpanel/dropdown/ProjectsMenu.js +27 -16
  170. package/dist/navigationpanel/editorpanel/ApplySemanticLayout.js +2 -1
  171. package/dist/navigationpanel/editorpanel/ChangeAutoLayoutButton.js +12 -10
  172. package/dist/navigationpanel/editorpanel/ManualLayoutToolsButton.d.ts +2 -0
  173. package/dist/navigationpanel/editorpanel/ManualLayoutToolsButton.js +19 -10
  174. package/dist/navigationpanel/editorpanel/styles.js +8 -15
  175. package/dist/navigationpanel/hooks.d.ts +6 -2
  176. package/dist/navigationpanel/styles.css.d.ts +2 -2
  177. package/dist/navigationpanel/styles.css.js +0 -1
  178. package/dist/navigationpanel/walkthrough/ActiveWalkthroughControls.js +3 -2
  179. package/dist/navigationpanel/walkthrough/DynamicViewControls.d.ts +5 -4
  180. package/dist/navigationpanel/walkthrough/DynamicViewControls.js +10 -39
  181. package/dist/navigationpanel/walkthrough/DynamicViewModeSwitcher.d.ts +1 -0
  182. package/dist/navigationpanel/walkthrough/DynamicViewModeSwitcher.js +49 -0
  183. package/dist/navigationpanel/walkthrough/WalkthroughPanel.js +8 -8
  184. package/dist/navigationpanel/windows/ViewDetailsWindow.d.ts +1 -0
  185. package/dist/navigationpanel/windows/ViewDetailsWindow.js +379 -0
  186. package/dist/overlays/Overlays.js +29 -17
  187. package/dist/overlays/element-details/ElementDetailsCard.css.js +28 -36
  188. package/dist/overlays/element-details/ElementDetailsCard.js +3 -3
  189. package/dist/overlays/element-details/MetadataValue.js +18 -16
  190. package/dist/overlays/element-details/TabPanelDeployments.css.js +6 -14
  191. package/dist/overlays/element-details/TabPanelRelationships.css.js +8 -12
  192. package/dist/overlays/element-details/TabPanelStructure.css.js +4 -8
  193. package/dist/overlays/hooks.d.ts +3 -1
  194. package/dist/overlays/overlay/Overlay.js +8 -7
  195. package/dist/overlays/overlaysActor.js +20 -17
  196. package/dist/overlays/relationship-details/RelationshipDetails.js +2 -1
  197. package/dist/overlays/relationship-details/SelectEdge.css.js +14 -9
  198. package/dist/overlays/relationship-details/actor.js +1 -1
  199. package/dist/overlays/relationship-details/hooks.js +2 -1
  200. package/dist/overlays/relationships-browser/RelationshipsBrowser.d.ts +6 -0
  201. package/dist/overlays/relationships-browser/RelationshipsBrowser.js +15 -8
  202. package/dist/overlays/relationships-browser/SelectElement.css.js +2 -8
  203. package/dist/overlays/relationships-browser/SelectElement.js +5 -1
  204. package/dist/overlays/relationships-browser/actor.js +3 -2
  205. package/dist/overlays/relationships-browser/custom/ElementActions.js +39 -38
  206. package/dist/overlays/relationships-browser/custom/EmptyNode.js +7 -9
  207. package/dist/overlays/relationships-browser/hooks.js +2 -1
  208. package/dist/projects-overview/ProjectsOverview.js +8 -7
  209. package/dist/projects-overview/actor.js +1 -1
  210. package/dist/projects-overview/hooks.js +2 -1
  211. package/dist/search/Search.js +9 -7
  212. package/dist/search/components/ElementsColumn.css.js +6 -5
  213. package/dist/search/components/ElementsColumn.js +4 -3
  214. package/dist/search/components/SearchByTags.js +3 -3
  215. package/dist/search/components/ViewsColum.js +46 -43
  216. package/dist/search/components/ViewsColumn.css.js +4 -4
  217. package/dist/search/components/_shared.css.d.ts +2 -2
  218. package/dist/search/components/_shared.css.js +31 -46
  219. package/dist/search/components/styles.css.js +4 -4
  220. package/dist/search/hooks.js +2 -1
  221. package/dist/shadowroot/ShadowRoot.js +6 -5
  222. package/dist/styles2.js +1 -1
  223. package/dist/utils/index.js +3 -3
  224. package/package.json +29 -29
  225. package/panda.buildinfo.json +342 -299
  226. package/styles-min.css +1 -1
  227. package/styles-xyflow.css +1 -1
  228. package/styles.css +1 -1
  229. package/dist/context/DefaultMantineProvider.d.ts +0 -2
  230. package/dist/context/DefaultMantineProvider.js +0 -48
  231. package/dist/likec4diagram/ui/sequence-outline/state.js +0 -55
  232. package/dist/navigationpanel/controls/DetailsControls.d.ts +0 -2
  233. package/dist/navigationpanel/controls/DetailsControls.js +0 -223
@@ -0,0 +1,80 @@
1
+ import { css } from "@likec4/styles/css";
2
+ import { IconAlertTriangle, IconArrowFork, IconArrowGuide, IconCornerDownRight, IconPlayerStop, IconRepeat } from "@tabler/icons-react";
3
+ //#region src/likec4diagram/ui/sequence-outline/presentation.ts
4
+ /**
5
+ * PandaCSS `colorPalette` classes for each sub-flow palette.
6
+ * Declared as literals so the static analyzer can extract them.
7
+ */
8
+ var palette = {
9
+ loop: css({ colorPalette: "subflow.loop" }),
10
+ opt: css({ colorPalette: "subflow.opt" }),
11
+ par: css({ colorPalette: "subflow.par" }),
12
+ break: css({ colorPalette: "subflow.break" }),
13
+ alt: css({ colorPalette: "subflow.alt" }),
14
+ try: css({ colorPalette: "subflow.try" })
15
+ };
16
+ /** How each sub-flow operator is labelled and coloured in the outline. */
17
+ var flowPresentation = {
18
+ loop: {
19
+ paletteClass: palette.loop,
20
+ tag: "loop",
21
+ Icon: IconRepeat
22
+ },
23
+ opt: {
24
+ paletteClass: palette.opt,
25
+ tag: "opt",
26
+ Icon: IconArrowGuide
27
+ },
28
+ par: {
29
+ paletteClass: palette.par,
30
+ tag: "par",
31
+ Icon: IconArrowFork
32
+ },
33
+ break: {
34
+ paletteClass: palette.break,
35
+ tag: "break",
36
+ Icon: IconPlayerStop
37
+ },
38
+ alt: {
39
+ paletteClass: palette.alt,
40
+ tag: "alt",
41
+ Icon: IconArrowFork
42
+ },
43
+ "alt-when": {
44
+ paletteClass: palette.alt,
45
+ tag: "when",
46
+ Icon: IconCornerDownRight
47
+ },
48
+ "alt-else": {
49
+ paletteClass: palette.alt,
50
+ tag: "else",
51
+ Icon: IconCornerDownRight
52
+ },
53
+ "alt-if": {
54
+ paletteClass: palette.alt,
55
+ tag: "if",
56
+ Icon: IconCornerDownRight
57
+ },
58
+ try: {
59
+ paletteClass: palette.try,
60
+ tag: "try",
61
+ Icon: IconAlertTriangle
62
+ },
63
+ "try-block": {
64
+ paletteClass: palette.try,
65
+ tag: "block",
66
+ Icon: IconCornerDownRight
67
+ },
68
+ "try-catch": {
69
+ paletteClass: palette.break,
70
+ tag: "catch",
71
+ Icon: IconCornerDownRight
72
+ },
73
+ "try-finally": {
74
+ paletteClass: palette.break,
75
+ tag: "finally",
76
+ Icon: IconCornerDownRight
77
+ }
78
+ };
79
+ //#endregion
80
+ export { flowPresentation };
@@ -0,0 +1,9 @@
1
+ import { DynamicViewFlow, StepPath } from '@likec4/core/types';
2
+ import { OutlineTreeNodeFlow, OutlineTreeNodes } from './types';
3
+ /** Flattens the walkthrough flow into the nested step/sub-flow tree the outline renders. */
4
+ export declare function buildTree(flow: DynamicViewFlow): OutlineTreeNodes;
5
+ export declare function useTreeData(flow: DynamicViewFlow): OutlineTreeNodes;
6
+ /** The first step inside a fragment — where the breadcrumb jumps to. */
7
+ export declare function firstStepOf(nodes: OutlineTreeNodes): StepPath | null;
8
+ /** The chain of sub-flows the active step is nested inside, outermost first. */
9
+ export declare function collectTrail(nodes: OutlineTreeNodes, ancestors: readonly string[]): OutlineTreeNodeFlow[];
@@ -0,0 +1,67 @@
1
+ import "../../../_virtual/_rolldown/runtime.js";
2
+ import { isOutlineFlowNode } from "./types.js";
3
+ import "react";
4
+ //#region src/likec4diagram/ui/sequence-outline/tree.ts
5
+ /** Flattens the walkthrough flow into the nested step/sub-flow tree the outline renders. */
6
+ function buildTree(flow) {
7
+ const tree = [];
8
+ let currentFlow = tree;
9
+ flow.walk({
10
+ step: ({ step, stepnum, source, target, edge }) => {
11
+ currentFlow.push({
12
+ label: edge.label ?? `${source.title} → ${target.title}`,
13
+ value: step,
14
+ nodeProps: {
15
+ type: "step",
16
+ stepnum: stepnum.global,
17
+ source: source.title,
18
+ target: target.title,
19
+ label: edge.label,
20
+ notes: edge.notes ?? null,
21
+ edge
22
+ }
23
+ });
24
+ },
25
+ subflow: ({ subflow }) => {
26
+ const node = {
27
+ label: subflow.title ?? subflow._type,
28
+ value: subflow.id,
29
+ nodeProps: {
30
+ type: subflow._type,
31
+ title: subflow.title
32
+ },
33
+ children: []
34
+ };
35
+ const parent = currentFlow;
36
+ parent.push(node);
37
+ currentFlow = node.children;
38
+ return () => {
39
+ currentFlow = parent;
40
+ };
41
+ }
42
+ });
43
+ return tree;
44
+ }
45
+ /** The first step inside a fragment — where the breadcrumb jumps to. */
46
+ function firstStepOf(nodes) {
47
+ for (const node of nodes) if (isOutlineFlowNode(node)) {
48
+ const found = firstStepOf(node.children);
49
+ if (found) return found;
50
+ } else return node.value;
51
+ return null;
52
+ }
53
+ /** The chain of sub-flows the active step is nested inside, outermost first. */
54
+ function collectTrail(nodes, ancestors) {
55
+ const trail = [];
56
+ const walk = (list) => {
57
+ for (const node of list) if (isOutlineFlowNode(node) && ancestors.includes(node.value)) {
58
+ trail.push(node);
59
+ walk(node.children);
60
+ return;
61
+ }
62
+ };
63
+ walk(nodes);
64
+ return trail;
65
+ }
66
+ //#endregion
67
+ export { buildTree, collectTrail, firstStepOf };
@@ -1,6 +1,8 @@
1
- import { DynamicViewFlow, scalar, StepPath } from '@likec4/core';
1
+ import { DiagramEdge, DynamicViewFlow, scalar, StepPath } from '@likec4/core/types';
2
2
  import { TreeNodeData } from '@mantine/core';
3
3
  import { DiagramContext } from '../../state/types';
4
+ /** Sub-flows the user has folded away, keyed by {@link StepPath}. */
5
+ export type CollapsedFlows = DiagramContext['collapsedSequenceFlows'];
4
6
  export interface OutlineTreeNodeStep extends TreeNodeData {
5
7
  readonly value: StepPath;
6
8
  readonly nodeProps: Readonly<{
@@ -14,6 +16,7 @@ export interface OutlineTreeNodeStep extends TreeNodeData {
14
16
  /** Relationship label, if any */
15
17
  readonly label: string | null;
16
18
  readonly notes: scalar.MarkdownOrString | null;
19
+ readonly edge: DiagramEdge;
17
20
  }>;
18
21
  }
19
22
  export interface OutlineTreeNodeFlow extends TreeNodeData {
@@ -33,4 +36,3 @@ export type OutlineTreeNodes = OutlineTreeNodeData[];
33
36
  * is needed for reliable narrowing.)
34
37
  */
35
38
  export declare function isOutlineFlowNode(node: OutlineTreeNodeData): node is OutlineTreeNodeFlow;
36
- export declare function useTreeData(flow: DynamicViewFlow, collapsed: DiagramContext['collapsedSequenceFlows']): OutlineTreeNodes;
@@ -0,0 +1,12 @@
1
+ import "../../../_virtual/_rolldown/runtime.js";
2
+ //#region src/likec4diagram/ui/sequence-outline/types.ts
3
+ /**
4
+ * Type guard narrowing a tree node to a sub-flow node.
5
+ * (The discriminant lives on the nested `nodeProps.type`, so an explicit guard
6
+ * is needed for reliable narrowing.)
7
+ */
8
+ function isOutlineFlowNode(node) {
9
+ return node.nodeProps.type !== "step";
10
+ }
11
+ //#endregion
12
+ export { isOutlineFlowNode };
@@ -158,8 +158,13 @@ function makeRelativeEdgeModifier(edge, movingRect, anchorNode, staticNode) {
158
158
  };
159
159
  const d = vector$1(dx, dy);
160
160
  const relativePoint = (pt) => {
161
+ if (staticToAnchorLength === 0) return {
162
+ x: pt.x,
163
+ y: pt.y
164
+ };
161
165
  const point = vector$1(pt);
162
- const coeff = clamp(point.subtract(staticV).dot(staticToAnchor) / staticToAnchorLength ** 2, {
166
+ const projLength = point.subtract(staticV).dot(staticToAnchor);
167
+ const coeff = clamp(projLength / staticToAnchorLength ** 2, {
163
168
  min: -1,
164
169
  max: 1
165
170
  });
@@ -174,6 +179,13 @@ function makeRelativeEdgeModifier(edge, movingRect, anchorNode, staticNode) {
174
179
  type: "replace",
175
180
  item: produce(current, (draft) => {
176
181
  draft.data.controlPoints = controlPoints.map(relativePoint);
182
+ draft.data.points = map(edge.data.points, ([x, y]) => {
183
+ const point = relativePoint({
184
+ x,
185
+ y
186
+ });
187
+ return [point.x, point.y];
188
+ });
177
189
  if (edge.data.labelBBox) {
178
190
  draft.data.labelBBox ??= edge.data.labelBBox;
179
191
  const { x, y } = relativePoint(edge.data.labelBBox);
@@ -198,8 +198,10 @@ var SequenceViewLayouter = class {
198
198
  target.maxRow = Math.max(target.maxRow, step.to.row);
199
199
  const [left, right] = source.column <= target.column ? [source, target] : [target, source];
200
200
  const width = (step.label?.width ?? 100) + 50;
201
- if (Math.abs(target.column - source.column) <= 1) if (left !== right) this.constraint(left.centerX.plus(width), "<=", right.centerX);
202
- else this.constraint(left.centerX.plus(width), "<=", left.offset.right);
201
+ if (Math.abs(target.column - source.column) <= 1) {
202
+ if (left !== right) this.constraint(left.centerX.plus(width), "<=", right.centerX);
203
+ else this.constraint(left.centerX.plus(width), "<=", left.offset.right);
204
+ }
203
205
  let height = step.label?.height ? step.label.height + 50 + 24 : 100;
204
206
  height = Math.max(height, 100) + step.offset;
205
207
  this.ensureRow(step.from.row, height);
@@ -262,7 +264,6 @@ var SequenceViewLayouter = class {
262
264
  this.put(offset.bottom).before(y2, PADDING);
263
265
  }
264
266
  this.put(y2).before(bottom);
265
- break;
266
267
  }
267
268
  for (var col = from.column; col <= to.column; col++) {
268
269
  const offset = this.actorBox(col).offset;
@@ -400,7 +401,8 @@ var SequenceViewLayouter = class {
400
401
  }
401
402
  };
402
403
  const createSubflowArea = (subflow) => {
403
- const rect = rectFromSteps(selectSteps(subflow.id));
404
+ const steps = selectSteps(subflow.id);
405
+ const rect = rectFromSteps(steps);
404
406
  let space;
405
407
  switch (true) {
406
408
  case flowGuards.isAltOrTry(subflow):
@@ -420,9 +422,7 @@ var SequenceViewLayouter = class {
420
422
  bottom: 0
421
423
  };
422
424
  break;
423
- default:
424
- space = spacing;
425
- break;
425
+ default: space = spacing;
426
426
  }
427
427
  const area = {
428
428
  ...this.wrapAroundRect(rect, space),
@@ -507,9 +507,7 @@ var SequenceViewLayouter = class {
507
507
  this.constraint(left, "==", right, Strength.weak);
508
508
  break;
509
509
  case "<= 0":
510
- case ">= 0":
511
- this.constraint(left, "== 0", void 0, Strength.weak);
512
- break;
510
+ case ">= 0": this.constraint(left, "== 0", void 0, Strength.weak);
513
511
  }
514
512
  return constraint;
515
513
  }
@@ -76,6 +76,7 @@ function toCompoundArea({ id, x, y, width, height, depth }, node, view) {
76
76
  },
77
77
  draggable: false,
78
78
  selectable: false,
79
+ deletable: false,
79
80
  focusable: false,
80
81
  style: { pointerEvents: "none" },
81
82
  width,
@@ -1,7 +1,6 @@
1
1
  import "../../_virtual/_rolldown/runtime.js";
2
2
  import "remeda";
3
3
  import { Stack, invariant, isAncestor } from "@likec4/core/utils";
4
- import "@likec4/core/types";
5
4
  //#region src/likec4diagram/xyflow-sequence/utils.ts
6
5
  var paddingFromNumber = (spacing) => ({
7
6
  left: spacing,
@@ -14,8 +14,8 @@ import { Fragment as Fragment$1, jsx, jsxs } from "react/jsx-runtime";
14
14
  import { Popover, PopoverTarget } from "@mantine/core";
15
15
  import { AnimatePresence, LayoutGroup } from "motion/react";
16
16
  import { useSelector } from "@xstate/react";
17
- import { VStack } from "@likec4/styles/jsx";
18
17
  import { hasProp, isDynamicView } from "@likec4/core/types";
18
+ import { VStack } from "@likec4/styles/jsx";
19
19
  import { hstack } from "@likec4/styles/patterns";
20
20
  import * as m$1 from "motion/react-m";
21
21
  //#region src/navigationpanel/NavigationPanel.tsx
@@ -24,36 +24,38 @@ var select = selectDiagramContext((s) => {
24
24
  if (isDynamicView(s.view) && isActiveWalkthrough) {
25
25
  const isSequenceView = s.dynamicViewVariant === "sequence";
26
26
  return {
27
- view: s.view,
27
+ viewId: s.view.id,
28
28
  mode: isSequenceView && hasProp(s.view, "flow") ? "walkthrough-flow" : "walkthrough"
29
29
  };
30
30
  }
31
31
  return {
32
- view: s.view,
32
+ viewId: s.view.id,
33
33
  mode: "default"
34
34
  };
35
35
  });
36
36
  var stateHasActiveTag = (state) => state.hasTag("active");
37
37
  var NavigationPanel = memo(({ actorRef }) => {
38
- const { view, mode } = useDiagramSelector(select);
39
- const viewModel = useOptionalCurrentViewModel();
40
38
  const opened = useSelector(actorRef, stateHasActiveTag);
41
39
  const portalProps = useMantinePortalProps();
40
+ const { viewId, mode } = useDiagramSelector(select);
41
+ const viewModel = useOptionalCurrentViewModel();
42
+ const viewFolder = !!viewModel && viewModel.id === viewId ? viewModel.folder.path : void 0;
42
43
  useEffect(() => {
43
44
  actorRef.send({
44
45
  type: "update.inputs",
45
46
  inputs: {
46
- viewModel,
47
- view
47
+ viewId,
48
+ viewFolder
48
49
  }
49
50
  });
50
51
  }, [
51
52
  actorRef,
52
- viewModel,
53
- view
53
+ viewId,
54
+ viewFolder
54
55
  ]);
55
56
  return /* @__PURE__ */ jsx(VStack, {
56
57
  css: {
58
+ zIndex: "panel",
57
59
  alignItems: "flex-start",
58
60
  pointerEvents: "none",
59
61
  position: "absolute",
@@ -62,49 +64,51 @@ var NavigationPanel = memo(({ actorRef }) => {
62
64
  margin: "0",
63
65
  width: "100%",
64
66
  gap: "xxs",
65
- maxWidth: ["calc(100vw)", "calc(100cqw)"],
67
+ maxWidth: ["100vw", "100cqw"],
66
68
  "@/sm": {
67
69
  margin: "xs",
68
70
  gap: "xs",
69
71
  width: "max-content",
70
- maxWidth: ["calc(100vw - 2 * {spacing.md})", "calc(100cqw - 2 * {spacing.md})"]
72
+ maxWidth: ["[calc(100vw - 2 * {spacing.md})]", "[calc(100cqw - 2 * {spacing.md})]"]
71
73
  },
72
74
  _print: { display: "none" }
73
75
  },
74
76
  children: /* @__PURE__ */ jsx(NavigationPanelActorContextProvider, {
75
77
  value: actorRef,
76
78
  children: mode !== "walkthrough-flow" && /* @__PURE__ */ jsxs(Fragment$1, { children: [
77
- /* @__PURE__ */ jsxs(Popover, {
78
- offset: { mainAxis: 4 },
79
- opened,
80
- position: "bottom-start",
81
- trapFocus: opened,
82
- ...portalProps,
83
- clickOutsideEvents: [
84
- "pointerdown",
85
- "mousedown",
86
- "click"
87
- ],
88
- onDismiss: () => actorRef.send({ type: "dropdown.dismiss" }),
89
- children: [/* @__PURE__ */ jsx(LayoutGroup, { children: /* @__PURE__ */ jsx(PopoverTarget, { children: /* @__PURE__ */ jsx(m$1.div, {
90
- layout: true,
91
- layoutDependency: mode,
92
- className: hstack({
93
- layerStyle: "likec4.panel",
94
- position: "relative",
95
- gap: "xs",
96
- cursor: "pointer",
97
- pointerEvents: "all",
98
- width: "100%"
99
- }),
100
- onMouseLeave: () => actorRef.send({ type: "breadcrumbs.mouseLeave" }),
101
- children: /* @__PURE__ */ jsx(AnimatePresence, {
102
- propagate: true,
103
- initial: false,
79
+ /* @__PURE__ */ jsx(LayoutGroup, { children: /* @__PURE__ */ jsx(AnimatePresence, {
80
+ propagate: true,
81
+ initial: false,
82
+ children: /* @__PURE__ */ jsxs(Popover, {
83
+ offset: { mainAxis: 4 },
84
+ opened,
85
+ position: "bottom-start",
86
+ trapFocus: opened,
87
+ keepMounted: false,
88
+ ...portalProps,
89
+ clickOutsideEvents: [
90
+ "pointerdown",
91
+ "mousedown",
92
+ "click"
93
+ ],
94
+ onDismiss: () => actorRef.send({ type: "dropdown.dismiss" }),
95
+ children: [/* @__PURE__ */ jsx(PopoverTarget, { children: /* @__PURE__ */ jsx(m$1.div, {
96
+ layout: "size",
97
+ layoutDependency: [mode, viewId],
98
+ className: hstack({
99
+ layerStyle: "likec4.panel",
100
+ position: "relative",
101
+ gap: "xs",
102
+ cursor: "pointer",
103
+ pointerEvents: "all",
104
+ width: "100%"
105
+ }),
106
+ "data-panel": "navigation",
107
+ onMouseLeave: () => actorRef.send({ type: "breadcrumbs.mouseLeave" }),
104
108
  children: mode === "walkthrough" ? /* @__PURE__ */ jsx(ActiveWalkthroughControls, {}) : /* @__PURE__ */ jsx(NavigationPanelControls, {})
105
- })
106
- }) }) }), opened && /* @__PURE__ */ jsx(NavigationPanelDropdown, {})]
107
- }),
109
+ }) }), /* @__PURE__ */ jsx(NavigationPanelDropdown, {})]
110
+ })
111
+ }) }),
108
112
  /* @__PURE__ */ jsx(ComparePanel, {}),
109
113
  mode === "walkthrough" && /* @__PURE__ */ jsx(WalkthroughPanel, {}),
110
114
  /* @__PURE__ */ jsx(EditorPanel, {})
@@ -1,60 +1,85 @@
1
1
  import "../_virtual/_rolldown/runtime.js";
2
2
  import { useEnabledFeatures } from "../context/DiagramFeatures.js";
3
- import { BreadcrumbsSeparator } from "./_common.js";
3
+ import { selectDiagramContext, useDiagramSelector } from "../hooks/safeContext.js";
4
+ import { useOptionalCurrentViewModel } from "../context/LikeC4ModelContext.js";
5
+ import { deriveToggledFeatures } from "../likec4diagram/state/machine.setup.js";
4
6
  import { useNavigationActor } from "./hooks.js";
5
- import { DetailsControls } from "./controls/DetailsControls.js";
6
7
  import { LayoutWarning } from "./controls/LayoutWarning.js";
7
8
  import { LogoButton } from "./controls/LogoButton.js";
8
9
  import { NavigationButtons } from "./controls/NavigationButtons.js";
9
10
  import { OpenSource } from "./controls/OpenSource.js";
10
11
  import { SearchControl } from "./controls/SearchControl.js";
11
12
  import { ToggleReadonly } from "./controls/ToggleReadonly.js";
13
+ import { ViewDetailsButton } from "./controls/ViewDetailsButton.js";
12
14
  import { breadcrumbTitle } from "./styles.css.js";
13
15
  import { DynamicViewControls } from "./walkthrough/DynamicViewControls.js";
14
16
  import { css, cx } from "@likec4/styles/css";
17
+ import { IconChevronRight } from "@tabler/icons-react";
15
18
  import { memo } from "react";
16
- import { jsx, jsxs } from "react/jsx-runtime";
17
- import { deepEqual } from "fast-equals";
19
+ import { Fragment as Fragment$1, jsx, jsxs } from "react/jsx-runtime";
20
+ import { isTruthy } from "remeda";
18
21
  import { UnstyledButton } from "@mantine/core";
19
- import { AnimatePresence } from "motion/react";
20
- import { useSelector } from "@xstate/react";
22
+ import { LayoutGroup } from "motion/react";
21
23
  import { hstack } from "@likec4/styles/patterns";
22
24
  import * as m$1 from "motion/react-m";
23
25
  import { extractViewTitleFromPath } from "@likec4/core/model";
24
26
  //#region src/navigationpanel/NavigationPanelControls.tsx
25
- var selectBreadcrumbs = ({ context }) => {
26
- const view = context.view;
27
- const folder = context.viewModel?.folder;
27
+ var selectViewData = selectDiagramContext((s) => {
28
+ const comparingLatest = deriveToggledFeatures(s).enableCompareWithLatest && !!s.view.drifts && s.view._layout === "auto";
29
+ const noActiveWalkthrough = !isTruthy(s.activeWalkthrough);
30
+ const hasEditor = s.features.enableEditor;
31
+ const isReadOnly = s.toggledFeatures.enableReadOnly ?? false;
28
32
  return {
29
- folders: !folder || folder.isRoot ? [] : folder.breadcrumbs.map((s) => ({
30
- folderPath: s.path,
31
- title: s.title
32
- })),
33
- viewId: view.id,
34
- viewTitle: context.viewModel?.title ?? (view.title && extractViewTitleFromPath(view.title)) ?? "Untitled View",
35
- isDynamicView: (context.viewModel?._type ?? view._type) === "dynamic"
33
+ viewId: s.view.id,
34
+ viewTitle: (s.view.title && extractViewTitleFromPath(s.view.title)) ?? "Untitled View",
35
+ isDynamicView: s.view._type === "dynamic",
36
+ editBtnVisible: hasEditor && noActiveWalkthrough,
37
+ editBtnDisabled: comparingLatest,
38
+ isReadOnly
36
39
  };
40
+ });
41
+ var breadcrumbAnimation = {
42
+ initial: {
43
+ opacity: .5,
44
+ translateX: -10,
45
+ translateY: 0
46
+ },
47
+ animate: {
48
+ opacity: 1,
49
+ translateX: 0,
50
+ translateY: 0
51
+ },
52
+ exit: {
53
+ opacity: 0,
54
+ translateX: -10,
55
+ translateY: 0
56
+ },
57
+ whileTap: { translateY: 1 }
37
58
  };
38
59
  var NavigationPanelControls = memo(() => {
39
60
  const actor = useNavigationActor();
40
- const { enableNavigationButtons, enableDynamicViewWalkthrough, enableCompareWithLatest, enableSearch } = useEnabledFeatures();
41
- const { folders, viewTitle, isDynamicView } = useSelector(actor.actorRef, selectBreadcrumbs, deepEqual);
42
- const folderBreadcrumbs = folders.flatMap(({ folderPath, title }, i) => [/* @__PURE__ */ jsx(UnstyledButton, {
61
+ const { enableNavigationButtons, enableDynamicViewWalkthrough, enableCompareWithLatest, enableSearch, enableVscode } = useEnabledFeatures();
62
+ const viewModel = useOptionalCurrentViewModel();
63
+ const { editBtnDisabled, editBtnVisible, isReadOnly, viewTitle, isDynamicView } = useDiagramSelector(selectViewData);
64
+ const folder = viewModel?.folder;
65
+ const folderBreadcrumbs = (!folder || folder.isRoot ? [] : folder.breadcrumbs.map((s) => ({
66
+ folderPath: s.path,
67
+ title: s.title
68
+ }))).flatMap(({ folderPath, title }, index, all) => [/* @__PURE__ */ jsx(UnstyledButton, {
43
69
  component: m$1.button,
70
+ layout: "position",
44
71
  className: cx(breadcrumbTitle({
45
72
  dimmed: true,
46
73
  truncate: true
47
- }), "mantine-active", css({
74
+ }), css({
48
75
  userSelect: "none",
49
- maxWidth: "200px",
76
+ maxWidth: "[150px]",
50
77
  display: {
51
78
  base: "none",
52
79
  "@/md": "block"
53
80
  }
54
81
  })),
55
- initial: { opacity: 0 },
56
- animate: { opacity: 1 },
57
- exit: { opacity: 0 },
82
+ ...breadcrumbAnimation,
58
83
  title,
59
84
  onMouseEnter: () => actor.send({
60
85
  type: "breadcrumbs.mouseEnter.folder",
@@ -72,13 +97,23 @@ var NavigationPanelControls = memo(() => {
72
97
  });
73
98
  },
74
99
  children: title
75
- }, folderPath), /* @__PURE__ */ jsx(BreadcrumbsSeparator, {}, `separator-${i}`)]);
100
+ }, folderPath), /* @__PURE__ */ jsx(m$1.div, {
101
+ layout: true,
102
+ className: css({
103
+ display: {
104
+ base: "none",
105
+ "@/md": "block"
106
+ },
107
+ color: "text.non-essential"
108
+ }),
109
+ children: /* @__PURE__ */ jsx(IconChevronRight, { size: 16 })
110
+ }, folderPath + "-separator")]);
76
111
  const viewBreadcrumb = /* @__PURE__ */ jsx(UnstyledButton, {
112
+ layoutId: "view-title",
77
113
  component: m$1.button,
78
- initial: { opacity: 0 },
79
- animate: { opacity: 1 },
80
- exit: { opacity: 0 },
81
- className: cx("mantine-active", breadcrumbTitle({ truncate: true }), css({ userSelect: "none" })),
114
+ layout: "position",
115
+ ...breadcrumbAnimation,
116
+ className: cx(breadcrumbTitle({ truncate: true }), css({ userSelect: "none" })),
82
117
  title: viewTitle,
83
118
  onMouseEnter: () => actor.send({ type: "breadcrumbs.mouseEnter.viewtitle" }),
84
119
  onMouseLeave: () => actor.send({ type: "breadcrumbs.mouseLeave.viewtitle" }),
@@ -87,41 +122,45 @@ var NavigationPanelControls = memo(() => {
87
122
  actor.send({ type: "breadcrumbs.click.viewtitle" });
88
123
  },
89
124
  children: viewTitle
90
- }, "view-title");
91
- return /* @__PURE__ */ jsxs(AnimatePresence, {
92
- propagate: true,
93
- mode: "popLayout",
94
- children: [
95
- /* @__PURE__ */ jsx(LogoButton, {}, "logo-button"),
96
- enableNavigationButtons && /* @__PURE__ */ jsx(NavigationButtons, {}, "nav-buttons"),
97
- /* @__PURE__ */ jsxs(m$1.div, {
98
- layout: "position",
99
- className: hstack({
100
- gap: "1",
101
- flexShrink: 1,
102
- flexGrow: 1,
103
- overflow: "hidden"
104
- }),
105
- children: [folderBreadcrumbs, viewBreadcrumb]
106
- }, "breadcrumbs"),
107
- /* @__PURE__ */ jsxs(m$1.div, {
108
- layout: "position",
109
- className: hstack({
110
- gap: "0.5",
111
- flexGrow: 0,
112
- _empty: { display: "none" }
113
- }),
114
- children: [
115
- /* @__PURE__ */ jsx(DetailsControls, { onOpen: () => actor.closeDropdown() }),
116
- /* @__PURE__ */ jsx(OpenSource, {}),
117
- /* @__PURE__ */ jsx(ToggleReadonly, {})
118
- ]
119
- }, "actions"),
120
- enableDynamicViewWalkthrough && isDynamicView && /* @__PURE__ */ jsx(DynamicViewControls, {}, "dynamic-view-controls"),
121
- enableSearch && !enableCompareWithLatest && /* @__PURE__ */ jsx(SearchControl, {}, "search-control"),
122
- /* @__PURE__ */ jsx(LayoutWarning, {}, "outdated-manual-layout-warning")
123
- ]
124
125
  });
126
+ return /* @__PURE__ */ jsxs(Fragment$1, { children: [
127
+ /* @__PURE__ */ jsx(LogoButton, {}, "logo-button"),
128
+ enableNavigationButtons && /* @__PURE__ */ jsx(NavigationButtons, {}, "nav-buttons"),
129
+ /* @__PURE__ */ jsx(m$1.div, {
130
+ layout: "size",
131
+ className: hstack({
132
+ gap: "1",
133
+ flexShrink: 1,
134
+ flexGrow: 1,
135
+ flexWrap: "nowrap",
136
+ overflow: "hidden"
137
+ }),
138
+ children: /* @__PURE__ */ jsxs(LayoutGroup, {
139
+ id: "navigation-panel-breadcrumbs",
140
+ children: [folderBreadcrumbs, viewBreadcrumb]
141
+ })
142
+ }, "breadcrumbs"),
143
+ /* @__PURE__ */ jsxs(m$1.div, {
144
+ layout: "size",
145
+ className: hstack({
146
+ gap: "1.5",
147
+ flexShrink: 0,
148
+ flexWrap: "nowrap",
149
+ flexGrow: 0
150
+ }),
151
+ children: [
152
+ /* @__PURE__ */ jsx(ViewDetailsButton, { onOpen: () => actor.closeDropdown() }, "details"),
153
+ enableVscode && /* @__PURE__ */ jsx(OpenSource, {}, "open-source"),
154
+ editBtnVisible && /* @__PURE__ */ jsx(ToggleReadonly, {
155
+ disabled: editBtnDisabled,
156
+ isReadOnly
157
+ }, "toggle-readonly"),
158
+ enableDynamicViewWalkthrough && isDynamicView && /* @__PURE__ */ jsx(DynamicViewControls, {}, "dynamic-view-controls"),
159
+ enableSearch && !enableCompareWithLatest && /* @__PURE__ */ jsx(SearchControl, {}, "search-control"),
160
+ /* @__PURE__ */ jsx(LayoutWarning, {}, "outdated-manual-layout-warning")
161
+ ]
162
+ }, "actions")
163
+ ] });
125
164
  });
126
165
  NavigationPanelControls.displayName = "NavigationPanelControls";
127
166
  //#endregion