@formicoidea/labre-framework-cynefin 0.31.0 → 0.32.0

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.
@@ -0,0 +1,4 @@
1
+ import type { BlockStdScope } from '@formicoidea/labre-core/std';
2
+ export declare function createCynefin(std: BlockStdScope): void;
3
+ export declare function createEstuarineMap(std: BlockStdScope): void;
4
+ export declare function createConstraintHexagon(std: BlockStdScope): void;
@@ -0,0 +1,65 @@
1
+ import { DefaultTool } from '@formicoidea/labre-core/blocks/surface';
2
+ import { ShapeStyle, TextFitMode } from '@formicoidea/labre-core/model';
3
+ import { Bound } from '@formicoidea/labre-core/global/gfx';
4
+ import { GfxControllerIdentifier } from '@formicoidea/labre-core/std/gfx';
5
+ import { REF_H as CYN_H, REF_W as CYN_W } from './cynefin/consts.js';
6
+ import { HEX_FILL, HEX_SIZE, HEX_STROKE, HEX_VERTICES, REF_H as EST_H, REF_W as EST_W, } from './estuarine/consts.js';
7
+ /**
8
+ * Creation actions for the Cynefin / Estuarine toolbox — lifted out of
9
+ * `toolbar/menu.ts` by PF3. This is also the framework that emitted NO
10
+ * telemetry at all before the switchover: routing every surface through
11
+ * `runCommand` fixes that for free (`docs/adr/0008`).
12
+ */
13
+ /** Estuarine map default size (REF aspect, scaled up so it reads on canvas). */
14
+ const MAP_SCALE = 1.2;
15
+ const gfxOf = (std) => std.get(GfxControllerIdentifier);
16
+ function finish(gfx, id) {
17
+ gfx.doc.captureSync();
18
+ gfx.tool.setTool(DefaultTool);
19
+ gfx.selection.set({ elements: [id], editing: false });
20
+ }
21
+ export function createCynefin(std) {
22
+ const gfx = gfxOf(std);
23
+ if (!gfx.surface)
24
+ return;
25
+ const { centerX, centerY } = gfx.viewport;
26
+ const id = gfx.surface.addElement({
27
+ type: 'cynefin',
28
+ xywh: new Bound(centerX - CYN_W / 2, centerY - CYN_H / 2, CYN_W, CYN_H).serialize(),
29
+ });
30
+ finish(gfx, id);
31
+ }
32
+ export function createEstuarineMap(std) {
33
+ const gfx = gfxOf(std);
34
+ if (!gfx.surface)
35
+ return;
36
+ const width = EST_W * MAP_SCALE;
37
+ const height = EST_H * MAP_SCALE;
38
+ const { centerX, centerY } = gfx.viewport;
39
+ const id = gfx.surface.addElement({
40
+ type: 'estuarine',
41
+ xywh: new Bound(centerX - width / 2, centerY - height / 2, width, height).serialize(),
42
+ });
43
+ finish(gfx, id);
44
+ }
45
+ export function createConstraintHexagon(std) {
46
+ const gfx = gfxOf(std);
47
+ if (!gfx.surface)
48
+ return;
49
+ const { centerX: cx, centerY: cy } = gfx.viewport;
50
+ const id = gfx.surface.addElement({
51
+ type: 'shape',
52
+ shapeType: 'polygon',
53
+ vertices: HEX_VERTICES,
54
+ filled: true,
55
+ fillColor: HEX_FILL,
56
+ strokeColor: HEX_STROKE,
57
+ strokeWidth: 2,
58
+ shapeStyle: ShapeStyle.General,
59
+ roughness: 0,
60
+ // hexi constraints behave like post-its: fixed hex, text shrinks
61
+ textFitMode: TextFitMode.Contained,
62
+ xywh: new Bound(cx - HEX_SIZE / 2, cy - HEX_SIZE / 2, HEX_SIZE, HEX_SIZE).serialize(),
63
+ });
64
+ finish(gfx, id);
65
+ }
@@ -0,0 +1,4 @@
1
+ import type { CommandDescriptor } from '@formicoidea/labre-core/std';
2
+ import type { TemplateResult } from 'lit';
3
+ export declare const cynefinEstuarineCommands: CommandDescriptor[];
4
+ export declare const cynefinEstuarineCommandIcons: Record<string, TemplateResult>;
@@ -0,0 +1,46 @@
1
+ import { createConstraintHexagon, createCynefin, createEstuarineMap, } from './actions.js';
2
+ import { cynefinMenuIcon, estuarineMenuIcon, hexagonMenuIcon, } from './toolbar/icons.js';
3
+ const SPECS = [
4
+ {
5
+ id: 'addCynefin',
6
+ label: 'Cynefin framework',
7
+ iconKey: 'cynefin.frame',
8
+ element: 'cynefin',
9
+ run: createCynefin,
10
+ },
11
+ {
12
+ id: 'addEstuarineMap',
13
+ label: 'Estuarine map',
14
+ iconKey: 'estuarine.map',
15
+ element: 'estuarine',
16
+ run: createEstuarineMap,
17
+ },
18
+ {
19
+ id: 'addConstraintHexagon',
20
+ label: 'Hexagon node',
21
+ iconKey: 'estuarine.hexagon',
22
+ element: 'node:hexagon',
23
+ run: createConstraintHexagon,
24
+ },
25
+ ];
26
+ export const cynefinEstuarineCommands = SPECS.map((spec, order) => ({
27
+ id: `cynefin-estuarine.${spec.id}`,
28
+ owner: 'cynefin-estuarine',
29
+ kind: 'artefact',
30
+ labelKey: `com.labre.commands.cynefin-estuarine.${spec.id}`,
31
+ labelFallback: spec.label,
32
+ category: 'frames',
33
+ iconKey: spec.iconKey,
34
+ surfaces: ['senior-menu', 'catalogue', 'palette', 'agent'],
35
+ order,
36
+ scope: 'edgeless',
37
+ defaultKeys: { mac: [], other: [] },
38
+ availability: 'always',
39
+ run: spec.run,
40
+ telemetry: { framework: 'cynefin-estuarine', element: spec.element },
41
+ }));
42
+ export const cynefinEstuarineCommandIcons = {
43
+ 'cynefin.frame': cynefinMenuIcon,
44
+ 'estuarine.map': estuarineMenuIcon,
45
+ 'estuarine.hexagon': hexagonMenuIcon,
46
+ };
@@ -1,7 +1,12 @@
1
- import { CynefinEstuarineViewExtension } from './view.js';
2
- /** Host wiring for the cynefin framework. */
1
+ import { CynefinEstuarineRenderViewExtension, CynefinEstuarineViewExtension } from './view.js';
2
+ /** Host wiring for the cynefin-estuarine framework. */
3
3
  export declare const cynefinFramework: {
4
4
  readonly flag: "cynefin-estuarine";
5
- readonly telemetry: "cynefin";
6
- readonly viewExtension: typeof CynefinEstuarineViewExtension;
5
+ readonly telemetryKey: "cynefin";
6
+ readonly extensions: readonly [{
7
+ readonly viewExtension: typeof CynefinEstuarineRenderViewExtension;
8
+ }, {
9
+ readonly flag: "cynefin-estuarine";
10
+ readonly viewExtension: typeof CynefinEstuarineViewExtension;
11
+ }];
7
12
  };
@@ -1,7 +1,10 @@
1
- import { CynefinEstuarineViewExtension } from './view.js';
2
- /** Host wiring for the cynefin framework. */
1
+ import { CynefinEstuarineRenderViewExtension, CynefinEstuarineViewExtension } from './view.js';
2
+ /** Host wiring for the cynefin-estuarine framework. */
3
3
  export const cynefinFramework = {
4
4
  flag: 'cynefin-estuarine',
5
- telemetry: 'cynefin',
6
- viewExtension: CynefinEstuarineViewExtension,
5
+ telemetryKey: 'cynefin',
6
+ extensions: [
7
+ { viewExtension: CynefinEstuarineRenderViewExtension },
8
+ { flag: 'cynefin-estuarine', viewExtension: CynefinEstuarineViewExtension },
9
+ ],
7
10
  };
package/dist/index.d.ts CHANGED
@@ -1 +1,2 @@
1
- export {};
1
+ export { cynefinEstuarineCommandIcons, cynefinEstuarineCommands, } from './commands.js';
2
+ export { cynefinEstuarineTranslationEntries } from './translations.js';
package/dist/index.js CHANGED
@@ -1 +1,2 @@
1
- export {};
1
+ export { cynefinEstuarineCommandIcons, cynefinEstuarineCommands, } from './commands.js';
2
+ export { cynefinEstuarineTranslationEntries } from './translations.js';
@@ -1,17 +1,11 @@
1
1
  import { EmptyTool } from '@formicoidea/labre-core/gfx/pointer';
2
- import { LitElement } from 'lit';
3
- declare const EdgelessCynefinEstuarineMenu_base: typeof LitElement & import("@formicoidea/labre-core/_pkgs/global/utils").Constructor<import("@formicoidea/labre-core/_pkgs/affine-widget-edgeless-toolbar").EdgelessToolbarToolClass>;
2
+ import { EdgelessCommandMenu } from '@formicoidea/labre-core/widgets/edgeless-toolbar';
4
3
  /**
5
- * The popover above the toolbar hosting both frameworks: create the Cynefin
6
- * diagram, the Estuarine map, or a hexagon constraint node.
4
+ * The popover above the toolbar hosting both frameworks. Since PF3 it declares
5
+ * nothing: {@link EdgelessCommandMenu} renders `cynefinEstuarineCommands` for
6
+ * the `senior-menu` surface (`docs/adr/0008`).
7
7
  */
8
- export declare class EdgelessCynefinEstuarineMenu extends EdgelessCynefinEstuarineMenu_base {
9
- static styles: import("lit").CSSResult;
8
+ export declare class EdgelessCynefinEstuarineMenu extends EdgelessCommandMenu {
9
+ protected owner: "cynefin-estuarine";
10
10
  type: typeof EmptyTool;
11
- private _finish;
12
- private _createCynefin;
13
- private _createMap;
14
- private _createHexagon;
15
- render(): import("lit-html").TemplateResult<1>;
16
11
  }
17
- export {};
@@ -1,122 +1,14 @@
1
- import { DefaultTool } from '@formicoidea/labre-core/blocks/surface';
2
1
  import { EmptyTool } from '@formicoidea/labre-core/gfx/pointer';
3
- import { ShapeStyle, TextFitMode } from '@formicoidea/labre-core/model';
4
- import { EdgelessToolbarToolMixin } from '@formicoidea/labre-core/widgets/edgeless-toolbar';
5
- import { Bound } from '@formicoidea/labre-core/global/gfx';
6
- import { css, html, LitElement } from 'lit';
7
- import { REF_H as CYN_H, REF_W as CYN_W } from '../cynefin/consts.js';
8
- import { HEX_FILL, HEX_SIZE, HEX_STROKE, HEX_VERTICES, REF_H as EST_H, REF_W as EST_W, } from '../estuarine/consts.js';
9
- import { cynefinMenuIcon, estuarineMenuIcon, hexagonMenuIcon, } from './icons.js';
10
- /** Estuarine map default size (REF aspect, scaled up so it reads on canvas). */
11
- const MAP_SCALE = 1.2;
2
+ import { EdgelessCommandMenu } from '@formicoidea/labre-core/widgets/edgeless-toolbar';
12
3
  /**
13
- * The popover above the toolbar hosting both frameworks: create the Cynefin
14
- * diagram, the Estuarine map, or a hexagon constraint node.
4
+ * The popover above the toolbar hosting both frameworks. Since PF3 it declares
5
+ * nothing: {@link EdgelessCommandMenu} renders `cynefinEstuarineCommands` for
6
+ * the `senior-menu` surface (`docs/adr/0008`).
15
7
  */
16
- export class EdgelessCynefinEstuarineMenu extends EdgelessToolbarToolMixin(LitElement) {
8
+ export class EdgelessCynefinEstuarineMenu extends EdgelessCommandMenu {
17
9
  constructor() {
18
10
  super(...arguments);
11
+ this.owner = 'cynefin-estuarine';
19
12
  this.type = EmptyTool;
20
13
  }
21
- static { this.styles = css `
22
- :host {
23
- display: flex;
24
- z-index: -1;
25
- justify-content: center;
26
- }
27
- .menu-content {
28
- display: flex;
29
- align-items: center;
30
- justify-content: center;
31
- }
32
- .button-group-container {
33
- display: flex;
34
- align-items: center;
35
- gap: 14px;
36
- fill: var(--affine-icon-color);
37
- }
38
- .button-group-container svg {
39
- width: 24px;
40
- height: 24px;
41
- }
42
- `; }
43
- _finish(id) {
44
- const { gfx } = this;
45
- gfx.doc.captureSync();
46
- gfx.tool.setTool(DefaultTool);
47
- gfx.selection.set({ elements: [id], editing: false });
48
- }
49
- _createCynefin() {
50
- const { gfx } = this;
51
- if (!gfx.surface)
52
- return;
53
- const { centerX, centerY } = gfx.viewport;
54
- const id = gfx.surface.addElement({
55
- type: 'cynefin',
56
- xywh: new Bound(centerX - CYN_W / 2, centerY - CYN_H / 2, CYN_W, CYN_H).serialize(),
57
- });
58
- this._finish(id);
59
- }
60
- _createMap() {
61
- const { gfx } = this;
62
- if (!gfx.surface)
63
- return;
64
- const width = EST_W * MAP_SCALE;
65
- const height = EST_H * MAP_SCALE;
66
- const { centerX, centerY } = gfx.viewport;
67
- const id = gfx.surface.addElement({
68
- type: 'estuarine',
69
- xywh: new Bound(centerX - width / 2, centerY - height / 2, width, height).serialize(),
70
- });
71
- this._finish(id);
72
- }
73
- _createHexagon() {
74
- const { gfx } = this;
75
- if (!gfx.surface)
76
- return;
77
- const { centerX: cx, centerY: cy } = gfx.viewport;
78
- const id = gfx.surface.addElement({
79
- type: 'shape',
80
- shapeType: 'polygon',
81
- vertices: HEX_VERTICES,
82
- filled: true,
83
- fillColor: HEX_FILL,
84
- strokeColor: HEX_STROKE,
85
- strokeWidth: 2,
86
- shapeStyle: ShapeStyle.General,
87
- roughness: 0,
88
- // hexi constraints behave like post-its: fixed hex, text shrinks
89
- textFitMode: TextFitMode.Contained,
90
- xywh: new Bound(cx - HEX_SIZE / 2, cy - HEX_SIZE / 2, HEX_SIZE, HEX_SIZE).serialize(),
91
- });
92
- this._finish(id);
93
- }
94
- render() {
95
- return html `
96
- <edgeless-slide-menu>
97
- <div class="menu-content">
98
- <div class="button-group-container">
99
- <edgeless-tool-icon-button
100
- .tooltip=${'Cynefin framework'}
101
- @click=${this._createCynefin}
102
- >
103
- ${cynefinMenuIcon}
104
- </edgeless-tool-icon-button>
105
- <edgeless-tool-icon-button
106
- .tooltip=${'Estuarine map'}
107
- @click=${this._createMap}
108
- >
109
- ${estuarineMenuIcon}
110
- </edgeless-tool-icon-button>
111
- <edgeless-tool-icon-button
112
- .tooltip=${'Hexagon node'}
113
- @click=${this._createHexagon}
114
- >
115
- ${hexagonMenuIcon}
116
- </edgeless-tool-icon-button>
117
- </div>
118
- </div>
119
- </edgeless-slide-menu>
120
- `;
121
- }
122
14
  }
@@ -0,0 +1,14 @@
1
+ import { type TranslationKeyManifestEntry } from '@formicoidea/labre-core/std';
2
+ /**
3
+ * THIS framework's contribution to the translation-key manifest.
4
+ *
5
+ * Its command labels and descriptions are built from a TEMPLATE, so the
6
+ * concrete keys exist nowhere but in the declarations themselves and the
7
+ * core manifest could not restate them even if it wanted to. The
8
+ * contribution therefore ships WITH the framework: in the bundled
9
+ * distribution `@formicoidea/labre-framework-cynefin` carries it, and a host
10
+ * composes it into its catalogue exactly as it already composes
11
+ * `cynefinEstuarineCommands` into the command registry. See
12
+ * `packages/affine/all/src/translations.ts`.
13
+ */
14
+ export declare const cynefinEstuarineTranslationEntries: TranslationKeyManifestEntry[];
@@ -0,0 +1,15 @@
1
+ import { commandTranslationEntries, } from '@formicoidea/labre-core/std';
2
+ import { cynefinEstuarineCommands } from './commands.js';
3
+ /**
4
+ * THIS framework's contribution to the translation-key manifest.
5
+ *
6
+ * Its command labels and descriptions are built from a TEMPLATE, so the
7
+ * concrete keys exist nowhere but in the declarations themselves and the
8
+ * core manifest could not restate them even if it wanted to. The
9
+ * contribution therefore ships WITH the framework: in the bundled
10
+ * distribution `@formicoidea/labre-framework-cynefin` carries it, and a host
11
+ * composes it into its catalogue exactly as it already composes
12
+ * `cynefinEstuarineCommands` into the command registry. See
13
+ * `packages/affine/all/src/translations.ts`.
14
+ */
15
+ export const cynefinEstuarineTranslationEntries = commandTranslationEntries(cynefinEstuarineCommands);
package/dist/view.d.ts CHANGED
@@ -1,4 +1,19 @@
1
1
  import { type ViewExtensionContext, ViewExtensionProvider } from '@formicoidea/labre-core/ext-loader';
2
+ /**
3
+ * Cynefin / Estuarine rendering — ALWAYS registered, independent of any flag.
4
+ * Disabling `cynefin-estuarine` hides only the creation tooling (see
5
+ * {@link CynefinEstuarineViewExtension}); frames already drawn must still
6
+ * paint, stay selectable, stay editable and keep their contextual toolbar. See
7
+ * `docs/adr/0009`.
8
+ */
9
+ export declare class CynefinEstuarineRenderViewExtension extends ViewExtensionProvider {
10
+ name: string;
11
+ setup(context: ViewExtensionContext): void;
12
+ }
13
+ /**
14
+ * Cynefin / Estuarine creation tooling — flag-gated (`cynefin-estuarine`): the
15
+ * senior toolbar button and both templates categories.
16
+ */
2
17
  export declare class CynefinEstuarineViewExtension extends ViewExtensionProvider {
3
18
  name: string;
4
19
  effect(): void;
package/dist/view.js CHANGED
@@ -1,5 +1,7 @@
1
1
  import { ViewExtensionProvider, } from '@formicoidea/labre-core/ext-loader';
2
2
  import { extendTemplateCategory } from '@formicoidea/labre-core/gfx/template';
3
+ import { CommandExtension } from '@formicoidea/labre-core/std';
4
+ import { cynefinEstuarineCommandIcons, cynefinEstuarineCommands, } from './commands.js';
3
5
  import { CynefinRendererExtension } from './cynefin/element-renderer.js';
4
6
  import { CynefinInteraction, CynefinView } from './cynefin/element-view.js';
5
7
  import { cynefinToolbarExtension } from './cynefin/toolbar/config.js';
@@ -9,6 +11,36 @@ import { EstuarineInteraction, EstuarineView } from './estuarine/element-view.js
9
11
  import { estuarineToolbarExtension } from './estuarine/toolbar/config.js';
10
12
  import { cynefinTemplateCategory, estuarineTemplateCategory, } from './templates/index.js';
11
13
  import { cynefinEstuarineSeniorTool } from './toolbar/senior-tool.js';
14
+ /**
15
+ * Cynefin / Estuarine rendering — ALWAYS registered, independent of any flag.
16
+ * Disabling `cynefin-estuarine` hides only the creation tooling (see
17
+ * {@link CynefinEstuarineViewExtension}); frames already drawn must still
18
+ * paint, stay selectable, stay editable and keep their contextual toolbar. See
19
+ * `docs/adr/0009`.
20
+ */
21
+ export class CynefinEstuarineRenderViewExtension extends ViewExtensionProvider {
22
+ constructor() {
23
+ super(...arguments);
24
+ this.name = 'affine-cynefin-estuarine-render-gfx';
25
+ }
26
+ setup(context) {
27
+ super.setup(context);
28
+ context.register(CynefinView);
29
+ context.register(CynefinRendererExtension);
30
+ context.register(EstuarineView);
31
+ context.register(EstuarineRendererExtension);
32
+ if (this.isEdgeless(context.scope)) {
33
+ context.register(CynefinInteraction);
34
+ context.register(EstuarineInteraction);
35
+ context.register(cynefinToolbarExtension);
36
+ context.register(estuarineToolbarExtension);
37
+ }
38
+ }
39
+ }
40
+ /**
41
+ * Cynefin / Estuarine creation tooling — flag-gated (`cynefin-estuarine`): the
42
+ * senior toolbar button and both templates categories.
43
+ */
12
44
  export class CynefinEstuarineViewExtension extends ViewExtensionProvider {
13
45
  constructor() {
14
46
  super(...arguments);
@@ -16,22 +48,16 @@ export class CynefinEstuarineViewExtension extends ViewExtensionProvider {
16
48
  }
17
49
  effect() {
18
50
  super.effect();
51
+ // Defines the senior button and its menu — tooling-only custom elements.
19
52
  effects();
20
53
  extendTemplateCategory(cynefinTemplateCategory);
21
54
  extendTemplateCategory(estuarineTemplateCategory);
22
55
  }
23
56
  setup(context) {
24
57
  super.setup(context);
25
- context.register(CynefinView);
26
- context.register(CynefinRendererExtension);
27
- context.register(EstuarineView);
28
- context.register(EstuarineRendererExtension);
29
58
  if (this.isEdgeless(context.scope)) {
30
- context.register(CynefinInteraction);
31
- context.register(EstuarineInteraction);
32
59
  context.register(cynefinEstuarineSeniorTool);
33
- context.register(cynefinToolbarExtension);
34
- context.register(estuarineToolbarExtension);
60
+ context.register(CommandExtension(cynefinEstuarineCommands, cynefinEstuarineCommandIcons));
35
61
  }
36
62
  }
37
63
  }
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@formicoidea/labre-framework-cynefin",
3
- "description": "Labre cynefin framework for @formicoidea/labre-core.",
4
- "version": "0.31.0",
3
+ "description": "Labre cynefin-estuarine framework for @formicoidea/labre-core.",
4
+ "version": "0.32.0",
5
5
  "type": "module",
6
6
  "sideEffects": false,
7
7
  "author": "lajola",
@@ -27,7 +27,7 @@
27
27
  "dist"
28
28
  ],
29
29
  "dependencies": {
30
- "@formicoidea/labre-core": "0.31.0",
30
+ "@formicoidea/labre-core": "0.32.0",
31
31
  "lit": "^3.2.0"
32
32
  }
33
33
  }