@neta-art/cohub 12.1.0 → 12.2.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.
- package/README.md +8 -5
- package/dist/board/editor/editor.d.ts +1 -0
- package/dist/board/editor/editor.js +4 -0
- package/dist/board/editor/snapshots.js +5 -57
- package/dist/board/export/index.d.ts +2 -2
- package/dist/board/export/node/fonts.js +4 -0
- package/dist/board/export/node/index.d.ts +3 -0
- package/dist/board/export/node/index.js +13 -1
- package/dist/board/export/scene.d.ts +2 -2
- package/dist/board/export/scene.js +2 -2
- package/dist/board/model/asset-key.d.ts +16 -0
- package/dist/board/model/asset-key.js +92 -0
- package/dist/board/model/export-assets.d.ts +7 -3
- package/dist/board/model/export-assets.js +34 -13
- package/dist/board/model/index.d.ts +7 -5
- package/dist/board/model/index.js +9 -7
- package/dist/board/model/items/create.js +1 -1
- package/dist/board/model/media-sizes.d.ts +28 -0
- package/dist/board/model/media-sizes.js +64 -0
- package/dist/board/model/palette.d.ts +1 -0
- package/dist/board/model/palette.js +20 -130
- package/dist/board/model/text-metrics.d.ts +8 -3
- package/dist/board/model/text-metrics.js +13 -2
- package/dist/board/model/themes.d.ts +488 -0
- package/dist/board/model/themes.js +495 -0
- package/dist/board/render/card-tag.js +2 -2
- package/dist/board/render/index.d.ts +6 -4
- package/dist/board/render/index.js +5 -3
- package/dist/board/render/lod.d.ts +22 -0
- package/dist/board/render/lod.js +27 -0
- package/dist/board/render/media-interaction.js +1 -1
- package/dist/board/render/palette.js +2 -25
- package/dist/board/render/renderers/audio-card-renderer.js +2 -1
- package/dist/board/render/renderers/board-renderer-registry.d.ts +10 -0
- package/dist/board/render/renderers/custom-card-renderer.js +5 -5
- package/dist/board/render/renderers/far-plate.d.ts +11 -1
- package/dist/board/render/renderers/far-plate.js +27 -8
- package/dist/board/render/renderers/file-card-renderer.js +3 -5
- package/dist/board/render/renderers/image-card-renderer.js +32 -6
- package/dist/board/render/renderers/model-card-renderer.js +1 -1
- package/dist/board/render/renderers/shape-card-renderer.js +25 -24
- package/dist/board/render/renderers/task-card-renderer.js +7 -8
- package/dist/board/render/renderers/text-card-renderer.js +86 -41
- package/dist/board/render/renderers/video-card-renderer.js +2 -1
- package/dist/board/render/style.d.ts +7 -2
- package/dist/board/render/style.js +5 -1
- package/dist/board/render/surface.d.ts +5 -0
- package/dist/board/render/surface.js +13 -3
- package/dist/board/render/text-fit.js +8 -12
- package/dist/board/render/text-measurement.d.ts +15 -1
- package/dist/board/render/text-measurement.js +113 -20
- package/dist/board/render/text-resolution.d.ts +1 -6
- package/dist/board/render/text-resolution.js +1 -10
- package/dist/board/render/theme.d.ts +15 -0
- package/dist/board/render/theme.js +15 -0
- package/dist/board/stage/assets.d.ts +15 -4
- package/dist/board/stage/assets.js +155 -89
- package/dist/board/stage/index.d.ts +5 -5
- package/dist/board/stage/index.js +4 -4
- package/dist/board/stage/lru.d.ts +13 -9
- package/dist/board/stage/lru.js +38 -20
- package/dist/board/stage/scene.d.ts +11 -1
- package/dist/board/stage/scene.js +213 -138
- package/dist/board/stage/stage.d.ts +12 -1
- package/dist/board/stage/stage.js +97 -24
- package/dist/board/stage/texture-pool.d.ts +8 -1
- package/dist/board/stage/texture-pool.js +37 -1
- package/dist/chunks/app-realtime.js +1 -1
- package/dist/chunks/{transport.js → http-error.js} +37 -1
- package/dist/chunks/http.js +30 -10
- package/dist/http.js +1 -1
- package/dist/index.js +139 -131
- package/dist/media.d.ts +3 -27
- package/dist/media.js +3 -82
- package/dist/protocol/dist/board-constants.js +3 -3
- package/dist/protocol/dist/board-layout.d.ts +17 -3
- package/dist/protocol/dist/board-layout.js +68 -11
- package/dist/protocol/dist/core/media.d.ts +35 -1
- package/dist/protocol/dist/core/media.js +123 -1
- package/dist/protocol/dist/index.d.ts +2 -2
- package/dist/websocket.js +951 -1
- package/package.json +3 -2
- package/dist/board/model/image-key.d.ts +0 -9
- package/dist/board/model/image-key.js +0 -33
- package/dist/chunks/websocket.js +0 -988
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import { BoardItem } from "../../protocol/dist/board-model.js";
|
|
2
|
+
import "../../protocol/dist/index.js";
|
|
3
|
+
//#region src/board/model/media-sizes.d.ts
|
|
4
|
+
type BoardMediaSize = {
|
|
5
|
+
width: number;
|
|
6
|
+
height: number;
|
|
7
|
+
};
|
|
8
|
+
type BoardMediaTarget = {
|
|
9
|
+
id: string;
|
|
10
|
+
type: "image" | "video";
|
|
11
|
+
source: {
|
|
12
|
+
kind: "file" | "url";
|
|
13
|
+
value: string;
|
|
14
|
+
};
|
|
15
|
+
};
|
|
16
|
+
type BoardMediaFileResolver = (path: string, type: BoardMediaTarget["type"], signal?: AbortSignal) => Promise<BoardMediaSize | string | null>;
|
|
17
|
+
type BoardMediaSizeOptions = {
|
|
18
|
+
resolveFile?: BoardMediaFileResolver;
|
|
19
|
+
signal?: AbortSignal;
|
|
20
|
+
};
|
|
21
|
+
declare function boardMediaTarget(id: string, item: BoardItem): BoardMediaTarget | null;
|
|
22
|
+
declare function probeBoardMediaSize(target: Omit<BoardMediaTarget, "id">, options?: BoardMediaSizeOptions): Promise<BoardMediaSize | null>;
|
|
23
|
+
/** Probes each unique media source once; unresolved items are left as is. */
|
|
24
|
+
declare function settleBoardMediaSizes(items: Readonly<Record<string, BoardItem>>, options?: Omit<BoardMediaSizeOptions, "signal"> & {
|
|
25
|
+
timeoutMs?: number;
|
|
26
|
+
}): Promise<Record<string, BoardItem>>;
|
|
27
|
+
//#endregion
|
|
28
|
+
export { BoardMediaFileResolver, BoardMediaSize, BoardMediaSizeOptions, BoardMediaTarget, boardMediaTarget, probeBoardMediaSize, settleBoardMediaSizes };
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
import { probeMediaSize } from "../../protocol/dist/core/media.js";
|
|
2
|
+
import { parseBoardMediaSource } from "../../protocol/dist/board-model.js";
|
|
3
|
+
import { featuredTaskArtifact } from "../../protocol/dist/board-task.js";
|
|
4
|
+
import { adoptBoardNaturalSize } from "../../protocol/dist/board-layout.js";
|
|
5
|
+
//#region src/board/model/media-sizes.ts
|
|
6
|
+
function boardMediaTarget(id, item) {
|
|
7
|
+
if (item.type === "image" || item.type === "video") {
|
|
8
|
+
if (item.props.snapshot?.naturalWidth && item.props.snapshot.naturalHeight) return null;
|
|
9
|
+
const source = parseBoardMediaSource(item.props.src);
|
|
10
|
+
return source ? {
|
|
11
|
+
id,
|
|
12
|
+
type: item.type,
|
|
13
|
+
source
|
|
14
|
+
} : null;
|
|
15
|
+
}
|
|
16
|
+
if (item.type !== "task") return null;
|
|
17
|
+
const artifact = featuredTaskArtifact(item.props.snapshot.artifacts);
|
|
18
|
+
if (artifact?.type !== "image" && artifact?.type !== "video" || artifact.naturalWidth && artifact.naturalHeight) return null;
|
|
19
|
+
return {
|
|
20
|
+
id,
|
|
21
|
+
type: artifact.type,
|
|
22
|
+
source: {
|
|
23
|
+
kind: "url",
|
|
24
|
+
value: artifact.url
|
|
25
|
+
}
|
|
26
|
+
};
|
|
27
|
+
}
|
|
28
|
+
async function probeBoardMediaSize(target, options = {}) {
|
|
29
|
+
const { type, source } = target;
|
|
30
|
+
try {
|
|
31
|
+
const resolved = source.kind === "url" ? source.value : await options.resolveFile?.(source.value, type, options.signal);
|
|
32
|
+
if (typeof resolved !== "string") return resolved ?? null;
|
|
33
|
+
return await probeMediaSize(resolved, type, { signal: options.signal });
|
|
34
|
+
} catch {
|
|
35
|
+
return null;
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
const CONCURRENCY = 8;
|
|
39
|
+
/** Probes each unique media source once; unresolved items are left as is. */
|
|
40
|
+
async function settleBoardMediaSizes(items, options = {}) {
|
|
41
|
+
const targets = Object.entries(items).flatMap(([id, item]) => boardMediaTarget(id, item) ?? []);
|
|
42
|
+
const signal = AbortSignal.timeout(options.timeoutMs ?? 5e3);
|
|
43
|
+
const probes = /* @__PURE__ */ new Map();
|
|
44
|
+
const settled = {};
|
|
45
|
+
let next = 0;
|
|
46
|
+
const work = async () => {
|
|
47
|
+
for (let target = targets[next++]; target; target = targets[next++]) {
|
|
48
|
+
const key = `${target.type}:${target.source.kind}:${target.source.value}`;
|
|
49
|
+
const probe = probes.get(key) ?? probeBoardMediaSize(target, {
|
|
50
|
+
...options,
|
|
51
|
+
signal
|
|
52
|
+
});
|
|
53
|
+
probes.set(key, probe);
|
|
54
|
+
const size = await probe;
|
|
55
|
+
const item = items[target.id];
|
|
56
|
+
const adopted = size && item && adoptBoardNaturalSize(item, size);
|
|
57
|
+
if (adopted) settled[target.id] = adopted;
|
|
58
|
+
}
|
|
59
|
+
};
|
|
60
|
+
await Promise.all(Array.from({ length: CONCURRENCY }, work));
|
|
61
|
+
return settled;
|
|
62
|
+
}
|
|
63
|
+
//#endregion
|
|
64
|
+
export { boardMediaTarget, probeBoardMediaSize, settleBoardMediaSizes };
|
|
@@ -13,6 +13,7 @@ type BoardColorEntry = {
|
|
|
13
13
|
dark: BoardColorValue;
|
|
14
14
|
light: BoardColorValue;
|
|
15
15
|
};
|
|
16
|
+
/** Swatches with the colors of the default dark and light themes. */
|
|
16
17
|
declare const BOARD_COLORS: readonly BoardColorEntry[];
|
|
17
18
|
declare const DEFAULT_BOARD_COLOR: BoardColorId;
|
|
18
19
|
declare function isBoardColorId(value: unknown): value is BoardColorId;
|
|
@@ -1,134 +1,24 @@
|
|
|
1
|
+
import { BOARD_COLOR_TOKENS } from "../../protocol/dist/board-model.js";
|
|
2
|
+
import { BOARD_THEME_DATA } from "./themes.js";
|
|
1
3
|
//#region src/board/model/palette.ts
|
|
2
|
-
const
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
}
|
|
19
|
-
|
|
20
|
-
id: "neutral",
|
|
21
|
-
label: "Neutral",
|
|
22
|
-
dark: {
|
|
23
|
-
stroke: 10133670,
|
|
24
|
-
fill: 10133670,
|
|
25
|
-
label: LABEL_DARK
|
|
26
|
-
},
|
|
27
|
-
light: {
|
|
28
|
-
stroke: 6251368,
|
|
29
|
-
fill: 6251368,
|
|
30
|
-
label: LABEL_LIGHT
|
|
31
|
-
}
|
|
32
|
-
},
|
|
33
|
-
{
|
|
34
|
-
id: "black",
|
|
35
|
-
label: "Black",
|
|
36
|
-
dark: {
|
|
37
|
-
stroke: 0,
|
|
38
|
-
fill: 0,
|
|
39
|
-
label: LABEL_DARK
|
|
40
|
-
},
|
|
41
|
-
light: {
|
|
42
|
-
stroke: 0,
|
|
43
|
-
fill: 0,
|
|
44
|
-
label: LABEL_LIGHT
|
|
45
|
-
}
|
|
46
|
-
},
|
|
47
|
-
{
|
|
48
|
-
id: "white",
|
|
49
|
-
label: "White",
|
|
50
|
-
dark: {
|
|
51
|
-
stroke: 16777215,
|
|
52
|
-
fill: 16777215,
|
|
53
|
-
label: LABEL_DARK
|
|
54
|
-
},
|
|
55
|
-
light: {
|
|
56
|
-
stroke: 16777215,
|
|
57
|
-
fill: 16777215,
|
|
58
|
-
label: LABEL_LIGHT
|
|
59
|
-
}
|
|
60
|
-
},
|
|
61
|
-
{
|
|
62
|
-
id: "blue",
|
|
63
|
-
label: "Blue",
|
|
64
|
-
dark: {
|
|
65
|
-
stroke: 3718648,
|
|
66
|
-
fill: 3718648,
|
|
67
|
-
label: LABEL_DARK
|
|
68
|
-
},
|
|
69
|
-
light: {
|
|
70
|
-
stroke: 2450411,
|
|
71
|
-
fill: 2450411,
|
|
72
|
-
label: LABEL_LIGHT
|
|
73
|
-
}
|
|
74
|
-
},
|
|
75
|
-
{
|
|
76
|
-
id: "green",
|
|
77
|
-
label: "Green",
|
|
78
|
-
dark: {
|
|
79
|
-
stroke: 3462041,
|
|
80
|
-
fill: 3462041,
|
|
81
|
-
label: LABEL_DARK
|
|
82
|
-
},
|
|
83
|
-
light: {
|
|
84
|
-
stroke: 1483594,
|
|
85
|
-
fill: 1483594,
|
|
86
|
-
label: LABEL_LIGHT
|
|
87
|
-
}
|
|
88
|
-
},
|
|
89
|
-
{
|
|
90
|
-
id: "amber",
|
|
91
|
-
label: "Amber",
|
|
92
|
-
dark: {
|
|
93
|
-
stroke: 16096779,
|
|
94
|
-
fill: 16096779,
|
|
95
|
-
label: LABEL_DARK
|
|
96
|
-
},
|
|
97
|
-
light: {
|
|
98
|
-
stroke: 14251782,
|
|
99
|
-
fill: 14251782,
|
|
100
|
-
label: LABEL_LIGHT
|
|
101
|
-
}
|
|
102
|
-
},
|
|
103
|
-
{
|
|
104
|
-
id: "violet",
|
|
105
|
-
label: "Violet",
|
|
106
|
-
dark: {
|
|
107
|
-
stroke: 10980346,
|
|
108
|
-
fill: 10980346,
|
|
109
|
-
label: LABEL_DARK
|
|
110
|
-
},
|
|
111
|
-
light: {
|
|
112
|
-
stroke: 8141549,
|
|
113
|
-
fill: 8141549,
|
|
114
|
-
label: LABEL_LIGHT
|
|
115
|
-
}
|
|
116
|
-
},
|
|
117
|
-
{
|
|
118
|
-
id: "rose",
|
|
119
|
-
label: "Rose",
|
|
120
|
-
dark: {
|
|
121
|
-
stroke: 16478597,
|
|
122
|
-
fill: 16478597,
|
|
123
|
-
label: LABEL_DARK
|
|
124
|
-
},
|
|
125
|
-
light: {
|
|
126
|
-
stroke: 14753096,
|
|
127
|
-
fill: 14753096,
|
|
128
|
-
label: LABEL_LIGHT
|
|
129
|
-
}
|
|
130
|
-
}
|
|
131
|
-
];
|
|
4
|
+
const COLOR_LABELS = {
|
|
5
|
+
brand: "Brand",
|
|
6
|
+
neutral: "Neutral",
|
|
7
|
+
black: "Black",
|
|
8
|
+
white: "White",
|
|
9
|
+
blue: "Blue",
|
|
10
|
+
green: "Green",
|
|
11
|
+
amber: "Amber",
|
|
12
|
+
violet: "Violet",
|
|
13
|
+
rose: "Rose"
|
|
14
|
+
};
|
|
15
|
+
/** Swatches with the colors of the default dark and light themes. */
|
|
16
|
+
const BOARD_COLORS = BOARD_COLOR_TOKENS.map((id) => ({
|
|
17
|
+
id,
|
|
18
|
+
label: COLOR_LABELS[id],
|
|
19
|
+
dark: { ...BOARD_THEME_DATA.dark.colors[id] },
|
|
20
|
+
light: { ...BOARD_THEME_DATA.light.colors[id] }
|
|
21
|
+
}));
|
|
132
22
|
const DEFAULT_BOARD_COLOR = "brand";
|
|
133
23
|
const COLOR_INDEX = new Map(BOARD_COLORS.map((entry) => [entry.id, entry]));
|
|
134
24
|
function isBoardColorId(value) {
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import { clampBoardFontSize } from "../../protocol/dist/board-layout.js";
|
|
1
|
+
import { BoardTextLayout, clampBoardFontSize } from "../../protocol/dist/board-layout.js";
|
|
2
2
|
import "../../protocol/dist/index.js";
|
|
3
3
|
//#region src/board/model/text-metrics.d.ts
|
|
4
|
-
declare const TEXT_FONT_FAMILY = "Geist";
|
|
4
|
+
declare const TEXT_FONT_FAMILY = "Geist Variable";
|
|
5
5
|
declare const TEXT_FONT_SIZE = 24;
|
|
6
6
|
declare const TEXT_LINE_HEIGHT = 32;
|
|
7
7
|
declare const TEXT_MIN_FONT_SIZE = 2;
|
|
@@ -11,5 +11,10 @@ declare function boardFontFamily(font: string, stacks: {
|
|
|
11
11
|
serif: string;
|
|
12
12
|
mono: string;
|
|
13
13
|
}): string;
|
|
14
|
+
declare const SHAPE_LABEL_PADDING = 8;
|
|
15
|
+
declare function layoutShapeLabel(props: {
|
|
16
|
+
text: string;
|
|
17
|
+
fontSize: number;
|
|
18
|
+
}, width: number): BoardTextLayout;
|
|
14
19
|
//#endregion
|
|
15
|
-
export { TEXT_FONT_FAMILY, TEXT_FONT_SIZE, TEXT_LINE_HEIGHT, TEXT_MAX_FONT_SIZE, TEXT_MIN_FONT_SIZE, boardFontFamily, clampBoardFontSize as clampBoardTextFontSize };
|
|
20
|
+
export { SHAPE_LABEL_PADDING, TEXT_FONT_FAMILY, TEXT_FONT_SIZE, TEXT_LINE_HEIGHT, TEXT_MAX_FONT_SIZE, TEXT_MIN_FONT_SIZE, boardFontFamily, clampBoardFontSize as clampBoardTextFontSize, layoutShapeLabel };
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { BOARD_TEXT_FONT_FAMILY } from "../../protocol/dist/board-constants.js";
|
|
2
|
-
import { clampBoardFontSize } from "../../protocol/dist/board-layout.js";
|
|
2
|
+
import { clampBoardFontSize, layoutBoardText } from "../../protocol/dist/board-layout.js";
|
|
3
3
|
//#region src/board/model/text-metrics.ts
|
|
4
4
|
const TEXT_FONT_FAMILY = BOARD_TEXT_FONT_FAMILY;
|
|
5
5
|
const TEXT_FONT_SIZE = 24;
|
|
@@ -10,5 +10,16 @@ function boardFontFamily(font, stacks) {
|
|
|
10
10
|
if (font === "sans" || font === "serif" || font === "mono") return stacks[font];
|
|
11
11
|
return `"${font.replaceAll("\"", "")}", ${stacks.sans}`;
|
|
12
12
|
}
|
|
13
|
+
const SHAPE_LABEL_PADDING = 8;
|
|
14
|
+
function layoutShapeLabel(props, width) {
|
|
15
|
+
return layoutBoardText({
|
|
16
|
+
text: props.text,
|
|
17
|
+
fontSize: props.fontSize,
|
|
18
|
+
fontWeight: 500,
|
|
19
|
+
font: "sans",
|
|
20
|
+
lineHeight: 1.4,
|
|
21
|
+
width: Math.max(1, width - 16)
|
|
22
|
+
});
|
|
23
|
+
}
|
|
13
24
|
//#endregion
|
|
14
|
-
export { TEXT_FONT_FAMILY, TEXT_FONT_SIZE, TEXT_LINE_HEIGHT, TEXT_MAX_FONT_SIZE, TEXT_MIN_FONT_SIZE, boardFontFamily, clampBoardFontSize as clampBoardTextFontSize };
|
|
25
|
+
export { SHAPE_LABEL_PADDING, TEXT_FONT_FAMILY, TEXT_FONT_SIZE, TEXT_LINE_HEIGHT, TEXT_MAX_FONT_SIZE, TEXT_MIN_FONT_SIZE, boardFontFamily, clampBoardFontSize as clampBoardTextFontSize, layoutShapeLabel };
|