edododraw 0.1.2 → 0.1.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.
- package/dist-lib/chunks/{EdodoDraw-C3Yd1I9B.js → EdodoDraw-BdJowisU.js} +135 -35
- package/dist-lib/chunks/EdodoDraw-BdJowisU.js.map +1 -0
- package/dist-lib/engine/camera/controller.d.ts +5 -0
- package/dist-lib/engine/camera/controller.d.ts.map +1 -1
- package/dist-lib/engine/dsl/compile.d.ts +6 -0
- package/dist-lib/engine/dsl/compile.d.ts.map +1 -1
- package/dist-lib/engine/dsl/index.d.ts +5 -1
- package/dist-lib/engine/dsl/index.d.ts.map +1 -1
- package/dist-lib/engine/render/svgRenderer.d.ts +6 -0
- package/dist-lib/engine/render/svgRenderer.d.ts.map +1 -1
- package/dist-lib/engine/scene/palette.d.ts +8 -0
- package/dist-lib/engine/scene/palette.d.ts.map +1 -1
- package/dist-lib/engine/scene/types.d.ts +4 -0
- package/dist-lib/engine/scene/types.d.ts.map +1 -1
- package/dist-lib/engine/timeline/player.d.ts.map +1 -1
- package/dist-lib/index.js +22 -21
- package/dist-lib/lib/EdodoDraw.d.ts +11 -0
- package/dist-lib/lib/EdodoDraw.d.ts.map +1 -1
- package/dist-lib/lib/react.d.ts +6 -1
- package/dist-lib/lib/react.d.ts.map +1 -1
- package/dist-lib/llms-full.txt +66 -14
- package/dist-lib/react.js +6 -2
- package/dist-lib/react.js.map +1 -1
- package/package.json +1 -1
- package/dist-lib/chunks/EdodoDraw-C3Yd1I9B.js.map +0 -1
|
@@ -252,6 +252,17 @@ const FILL_PALETTE = {
|
|
|
252
252
|
brown: "#e5dbd4",
|
|
253
253
|
white: "#ffffff"
|
|
254
254
|
};
|
|
255
|
+
function isLightColor(color) {
|
|
256
|
+
if (!color) return false;
|
|
257
|
+
const c = color.trim().toLowerCase();
|
|
258
|
+
let hex = c.startsWith("#") ? c.slice(1) : "";
|
|
259
|
+
if (hex.length === 3) hex = hex.replace(/./g, (ch) => ch + ch);
|
|
260
|
+
if (hex.length !== 6 || /[^0-9a-f]/.test(hex)) return true;
|
|
261
|
+
const r2 = parseInt(hex.slice(0, 2), 16);
|
|
262
|
+
const g = parseInt(hex.slice(2, 4), 16);
|
|
263
|
+
const b = parseInt(hex.slice(4, 6), 16);
|
|
264
|
+
return 0.299 * r2 + 0.587 * g + 0.114 * b > 150;
|
|
265
|
+
}
|
|
255
266
|
function resolveStroke(token, fallback) {
|
|
256
267
|
if (!token) return fallback;
|
|
257
268
|
const t = token.trim().toLowerCase();
|
|
@@ -3067,9 +3078,7 @@ class CameraController {
|
|
|
3067
3078
|
};
|
|
3068
3079
|
/** Duration heuristic: further travel + bigger zoom change => longer. */
|
|
3069
3080
|
autoDuration(from, to) {
|
|
3070
|
-
|
|
3071
|
-
const zoomRatio = Math.abs(Math.log(to.zoom / from.zoom));
|
|
3072
|
-
return clamp(420 + dist2 * 0.12 + zoomRatio * 320, 420, 1300);
|
|
3081
|
+
return autoDuration(from, to);
|
|
3073
3082
|
}
|
|
3074
3083
|
// ---- high-level ops -----------------------------------------------------
|
|
3075
3084
|
fitAll(scene, opts = {}) {
|
|
@@ -3109,6 +3118,11 @@ class CameraController {
|
|
|
3109
3118
|
this.setImmediate({ cx: cam.cx - dx / cam.zoom, cy: cam.cy - dy / cam.zoom, zoom: cam.zoom });
|
|
3110
3119
|
}
|
|
3111
3120
|
}
|
|
3121
|
+
function autoDuration(from, to) {
|
|
3122
|
+
const dist2 = Math.hypot(to.cx - from.cx, to.cy - from.cy) * Math.min(from.zoom, to.zoom);
|
|
3123
|
+
const zoomRatio = Math.abs(Math.log(to.zoom / from.zoom));
|
|
3124
|
+
return clamp(420 + dist2 * 0.12 + zoomRatio * 320, 420, 1300);
|
|
3125
|
+
}
|
|
3112
3126
|
function lerp(a, b, t) {
|
|
3113
3127
|
return a + (b - a) * t;
|
|
3114
3128
|
}
|
|
@@ -3352,7 +3366,7 @@ const LIGHT_THEME = {
|
|
|
3352
3366
|
background: "#ffffff",
|
|
3353
3367
|
defaultStroke: STROKE_PALETTE.black,
|
|
3354
3368
|
defaultText: STROKE_PALETTE.black,
|
|
3355
|
-
gridColor: "#
|
|
3369
|
+
gridColor: "#d5d9e0",
|
|
3356
3370
|
mode: "light"
|
|
3357
3371
|
};
|
|
3358
3372
|
const DARK_THEME = {
|
|
@@ -3360,7 +3374,7 @@ const DARK_THEME = {
|
|
|
3360
3374
|
background: "#121212",
|
|
3361
3375
|
defaultStroke: "#e3e3e3",
|
|
3362
3376
|
defaultText: "#e3e3e3",
|
|
3363
|
-
gridColor: "#
|
|
3377
|
+
gridColor: "#2c313a",
|
|
3364
3378
|
mode: "dark"
|
|
3365
3379
|
};
|
|
3366
3380
|
function defaultNodeStyle(seed, mode = "light") {
|
|
@@ -3766,7 +3780,8 @@ function compileProgram(program, opts = {}) {
|
|
|
3766
3780
|
for (const t of themes.get(name).tokens) tokenMap.set(t.name, t.value);
|
|
3767
3781
|
}
|
|
3768
3782
|
}
|
|
3769
|
-
const
|
|
3783
|
+
const derivedMode = themeName?.toLowerCase().includes("dark") ? "dark" : "light";
|
|
3784
|
+
const mode = opts.mode ?? derivedMode;
|
|
3770
3785
|
const classAttrs = (name, seen = /* @__PURE__ */ new Set()) => {
|
|
3771
3786
|
if (seen.has(name) || !styles.has(name)) return { attrs: [] };
|
|
3772
3787
|
seen.add(name);
|
|
@@ -3792,6 +3807,7 @@ function compileProgram(program, opts = {}) {
|
|
|
3792
3807
|
const classes = collectClasses(nd);
|
|
3793
3808
|
const layered = styleFor("node", classes, nd.attrs);
|
|
3794
3809
|
const built = buildNodeStyle(layered, tokenMap);
|
|
3810
|
+
applyDarkInk(built.style, mode);
|
|
3795
3811
|
const shape = mapShape(built.shape ?? nd.shape);
|
|
3796
3812
|
const label = built.label ?? nd.label ?? prettyId(id);
|
|
3797
3813
|
const node = makeNode({
|
|
@@ -3907,6 +3923,15 @@ function collectTags(nd) {
|
|
|
3907
3923
|
}
|
|
3908
3924
|
return tags;
|
|
3909
3925
|
}
|
|
3926
|
+
const DARK_INK = "#1e1e1e";
|
|
3927
|
+
const LIGHT_INK = "#e3e3e3";
|
|
3928
|
+
function applyDarkInk(style, mode) {
|
|
3929
|
+
if (mode !== "dark") return;
|
|
3930
|
+
const solidLightFill = style.fillStyle === "solid" && isLightColor(style.fill ?? null);
|
|
3931
|
+
const ink = solidLightFill ? DARK_INK : LIGHT_INK;
|
|
3932
|
+
if (style.textColor === void 0) style.textColor = ink;
|
|
3933
|
+
if (style.stroke === void 0 && solidLightFill) style.stroke = DARK_INK;
|
|
3934
|
+
}
|
|
3910
3935
|
function buildNodeStyle(attrs, tokens, _mode) {
|
|
3911
3936
|
const style = {};
|
|
3912
3937
|
const out = { style };
|
|
@@ -4104,6 +4129,7 @@ function ensureInline(scene, nd, tokens, mode, styleFor) {
|
|
|
4104
4129
|
if (scene.nodes.some((n) => n.id === nd.id)) return;
|
|
4105
4130
|
const layered = styleFor("node", nd.classes, nd.attrs);
|
|
4106
4131
|
const built = buildNodeStyle(layered, tokens);
|
|
4132
|
+
applyDarkInk(built.style, mode);
|
|
4107
4133
|
scene.nodes.push(
|
|
4108
4134
|
makeNode({
|
|
4109
4135
|
id: nd.id,
|
|
@@ -4276,8 +4302,30 @@ function applyRevealToStep(c, scene, step) {
|
|
|
4276
4302
|
const ids = c.targets.flatMap((t) => resolveTargetIds(t, scene));
|
|
4277
4303
|
if (c.verb === "hide" || c.verb === "fade-out" || c.verb === "remove") {
|
|
4278
4304
|
step.hide.push(...ids);
|
|
4279
|
-
|
|
4280
|
-
|
|
4305
|
+
return;
|
|
4306
|
+
}
|
|
4307
|
+
step.reveal.push(...ids);
|
|
4308
|
+
const effect = revealEffect(c.with ?? (c.verb !== "show" ? c.verb : void 0));
|
|
4309
|
+
if (effect) {
|
|
4310
|
+
step.revealFx = step.revealFx ?? {};
|
|
4311
|
+
for (const id of ids) step.revealFx[id] = effect;
|
|
4312
|
+
}
|
|
4313
|
+
}
|
|
4314
|
+
function revealEffect(raw) {
|
|
4315
|
+
switch (raw) {
|
|
4316
|
+
case "fade-in":
|
|
4317
|
+
case "fade":
|
|
4318
|
+
return "fade";
|
|
4319
|
+
case "pop":
|
|
4320
|
+
case "pop-in":
|
|
4321
|
+
case "emphasize":
|
|
4322
|
+
return "pop";
|
|
4323
|
+
case "draw-on":
|
|
4324
|
+
case "draw":
|
|
4325
|
+
case "sweep":
|
|
4326
|
+
return "sweep";
|
|
4327
|
+
default:
|
|
4328
|
+
return void 0;
|
|
4281
4329
|
}
|
|
4282
4330
|
}
|
|
4283
4331
|
function cameraDirective(cam, scene, _tokens, timelineProps) {
|
|
@@ -4314,9 +4362,9 @@ function normalizeCamOp(op) {
|
|
|
4314
4362
|
return "focus";
|
|
4315
4363
|
}
|
|
4316
4364
|
}
|
|
4317
|
-
function compileEdd(source) {
|
|
4365
|
+
function compileEdd(source, opts = {}) {
|
|
4318
4366
|
const { program, diagnostics } = parse(source);
|
|
4319
|
-
const { scene } = compileProgram(program, { diagnostics });
|
|
4367
|
+
const { scene } = compileProgram(program, { diagnostics, mode: opts.mode });
|
|
4320
4368
|
const report = diagnostics.items.map((d) => formatDiagnostic(d, source));
|
|
4321
4369
|
return { scene, diagnostics, report };
|
|
4322
4370
|
}
|
|
@@ -5149,6 +5197,11 @@ function ensureEngineStyles(doc = document) {
|
|
|
5149
5197
|
injected = true;
|
|
5150
5198
|
}
|
|
5151
5199
|
const SVG_NS = "http://www.w3.org/2000/svg";
|
|
5200
|
+
const REVEAL_EFFECT_CLASS = {
|
|
5201
|
+
fade: "edd-reveal-fade",
|
|
5202
|
+
pop: "edd-reveal-pop",
|
|
5203
|
+
sweep: "edd-reveal-sweep"
|
|
5204
|
+
};
|
|
5152
5205
|
class SvgRenderer {
|
|
5153
5206
|
container;
|
|
5154
5207
|
svg;
|
|
@@ -5268,9 +5321,28 @@ class SvgRenderer {
|
|
|
5268
5321
|
else el.classList.remove("edd-hidden");
|
|
5269
5322
|
});
|
|
5270
5323
|
}
|
|
5324
|
+
/**
|
|
5325
|
+
* Play a per-beat reveal animation (`fade` | `pop` | `sweep`) on the named
|
|
5326
|
+
* element groups. Clears any prior reveal classes first and forces a reflow so
|
|
5327
|
+
* re-entering the same beat restarts the animation. `fx` = id -> effect.
|
|
5328
|
+
*/
|
|
5329
|
+
playReveal(fx) {
|
|
5330
|
+
const classes = ["edd-reveal-fade", "edd-reveal-pop", "edd-reveal-sweep"];
|
|
5331
|
+
const els = this.svg.querySelectorAll("[data-node],[data-edge]");
|
|
5332
|
+
els.forEach((el) => el.classList.remove(...classes));
|
|
5333
|
+
if (!fx || !Object.keys(fx).length) return;
|
|
5334
|
+
void this.svg.getBoundingClientRect();
|
|
5335
|
+
els.forEach((el) => {
|
|
5336
|
+
const id = el.getAttribute("data-node") ?? el.getAttribute("data-edge");
|
|
5337
|
+
const cls = id ? REVEAL_EFFECT_CLASS[fx[id]] : void 0;
|
|
5338
|
+
if (cls) el.classList.add(cls);
|
|
5339
|
+
});
|
|
5340
|
+
}
|
|
5271
5341
|
render(scene) {
|
|
5272
5342
|
this.scene = scene;
|
|
5273
|
-
|
|
5343
|
+
const bgColor = scene.meta.background || scene.theme.background;
|
|
5344
|
+
this.bg.setAttribute("fill", "transparent");
|
|
5345
|
+
this.container.style.backgroundColor = bgColor;
|
|
5274
5346
|
for (const name of ["groups", "edges", "nodes"]) this.layers[name].replaceChildren();
|
|
5275
5347
|
for (const group of scene.groups) {
|
|
5276
5348
|
if (!group.frame) continue;
|
|
@@ -5435,6 +5507,7 @@ class TimelinePlayer {
|
|
|
5435
5507
|
const step = this.steps[i];
|
|
5436
5508
|
const scene = this.scene;
|
|
5437
5509
|
this.renderer.applyVisibility(this.computeHidden(i));
|
|
5510
|
+
if (animate) this.renderer.playReveal(step.revealFx);
|
|
5438
5511
|
this.annotations.render(scene, [...scene.annotations, ...step.annotations], animate);
|
|
5439
5512
|
this.emit();
|
|
5440
5513
|
if (step.camera) {
|
|
@@ -5650,6 +5723,8 @@ class EdodoDraw {
|
|
|
5650
5723
|
listeners = /* @__PURE__ */ new Map();
|
|
5651
5724
|
textInput = null;
|
|
5652
5725
|
closeInput = null;
|
|
5726
|
+
colorScheme = null;
|
|
5727
|
+
hasRendered = false;
|
|
5653
5728
|
cleanup = [];
|
|
5654
5729
|
constructor(container, options = {}) {
|
|
5655
5730
|
this.container = container;
|
|
@@ -5708,7 +5783,7 @@ class EdodoDraw {
|
|
|
5708
5783
|
async render(source) {
|
|
5709
5784
|
this.source = source;
|
|
5710
5785
|
const seq = ++this.renderSeq;
|
|
5711
|
-
const { scene, diagnostics } = compileEdd(source);
|
|
5786
|
+
const { scene, diagnostics } = compileEdd(source, { mode: this.colorScheme ?? void 0 });
|
|
5712
5787
|
let diags = diagnostics.items;
|
|
5713
5788
|
const blocks = extractMermaidBlocks(source);
|
|
5714
5789
|
if (blocks.length) {
|
|
@@ -5725,6 +5800,7 @@ class EdodoDraw {
|
|
|
5725
5800
|
}
|
|
5726
5801
|
if (seq !== this.renderSeq) return { scene, diagnostics: diags };
|
|
5727
5802
|
this.scene = scene;
|
|
5803
|
+
this.hasRendered = true;
|
|
5728
5804
|
this.renderer.render(scene);
|
|
5729
5805
|
this.player.load(scene);
|
|
5730
5806
|
this.renderer.measure();
|
|
@@ -5744,6 +5820,21 @@ class EdodoDraw {
|
|
|
5744
5820
|
getSource() {
|
|
5745
5821
|
return this.source;
|
|
5746
5822
|
}
|
|
5823
|
+
/**
|
|
5824
|
+
* Force light/dark rendering, overriding the diagram's declared theme. Affects
|
|
5825
|
+
* the canvas background, the dotted grid, and the diagram's default ink
|
|
5826
|
+
* (strokes/text adapt for contrast on the dark canvas; explicit colors are
|
|
5827
|
+
* kept). Pass `null` to fall back to the DSL's own theme. Re-renders the
|
|
5828
|
+
* current source. Cheap and idempotent — no-ops if the scheme is unchanged.
|
|
5829
|
+
*/
|
|
5830
|
+
setColorScheme(mode) {
|
|
5831
|
+
if (this.colorScheme === mode) return;
|
|
5832
|
+
this.colorScheme = mode;
|
|
5833
|
+
if (this.hasRendered) void this.render(this.source);
|
|
5834
|
+
}
|
|
5835
|
+
getColorScheme() {
|
|
5836
|
+
return this.colorScheme;
|
|
5837
|
+
}
|
|
5747
5838
|
// ---- camera -------------------------------------------------------------
|
|
5748
5839
|
fit(animate = true) {
|
|
5749
5840
|
this.renderer.measure();
|
|
@@ -5881,7 +5972,8 @@ class EdodoDraw {
|
|
|
5881
5972
|
c.style.backgroundImage = "none";
|
|
5882
5973
|
return;
|
|
5883
5974
|
}
|
|
5884
|
-
|
|
5975
|
+
const dot = this.scene.theme.gridColor;
|
|
5976
|
+
c.style.backgroundImage = `radial-gradient(circle, ${dot} 1px, transparent 1px)`;
|
|
5885
5977
|
c.style.backgroundSize = `${cell}px ${cell}px`;
|
|
5886
5978
|
c.style.backgroundPosition = `${-cam.cx * cam.zoom + w / 2}px ${-cam.cy * cam.zoom + h / 2}px`;
|
|
5887
5979
|
}
|
|
@@ -5965,11 +6057,18 @@ class EdodoDraw {
|
|
|
5965
6057
|
}
|
|
5966
6058
|
/** Inline text editor for renaming a node (double-click / new node). */
|
|
5967
6059
|
showRenameInput(id, current, screen) {
|
|
6060
|
+
const dark = this.scene.theme.mode === "dark";
|
|
5968
6061
|
this.openInlineInput({
|
|
5969
6062
|
value: current,
|
|
5970
6063
|
placeholder: "label…",
|
|
5971
6064
|
screen,
|
|
5972
|
-
style: {
|
|
6065
|
+
style: {
|
|
6066
|
+
background: dark ? "#23262d" : "#ffffff",
|
|
6067
|
+
color: dark ? "#e6e7ea" : "#1e1e1e",
|
|
6068
|
+
textAlign: "center",
|
|
6069
|
+
zIndex: "30",
|
|
6070
|
+
minWidth: "80px"
|
|
6071
|
+
},
|
|
5973
6072
|
onCommit: (v) => this.edit.applyRename(id, v)
|
|
5974
6073
|
});
|
|
5975
6074
|
}
|
|
@@ -6073,26 +6172,27 @@ export {
|
|
|
6073
6172
|
hitTestNode as a3,
|
|
6074
6173
|
injectMermaid as a4,
|
|
6075
6174
|
isEmptyBBox as a5,
|
|
6076
|
-
|
|
6077
|
-
|
|
6078
|
-
|
|
6079
|
-
|
|
6080
|
-
|
|
6081
|
-
|
|
6082
|
-
|
|
6083
|
-
|
|
6084
|
-
|
|
6085
|
-
|
|
6086
|
-
|
|
6087
|
-
|
|
6088
|
-
|
|
6089
|
-
|
|
6090
|
-
|
|
6091
|
-
|
|
6092
|
-
|
|
6093
|
-
|
|
6094
|
-
|
|
6095
|
-
|
|
6175
|
+
isLightColor as a6,
|
|
6176
|
+
lerp$1 as a7,
|
|
6177
|
+
listShapePlugins as a8,
|
|
6178
|
+
makeEdge as a9,
|
|
6179
|
+
makeNode as aa,
|
|
6180
|
+
nodeBBox as ab,
|
|
6181
|
+
nodeRect as ac,
|
|
6182
|
+
nodeRectOf as ad,
|
|
6183
|
+
pairedStrokeForFill as ae,
|
|
6184
|
+
pointInRect as af,
|
|
6185
|
+
rectCenter as ag,
|
|
6186
|
+
rectToBBox as ah,
|
|
6187
|
+
registerShape as ai,
|
|
6188
|
+
renameNode as aj,
|
|
6189
|
+
resolveAnchor as ak,
|
|
6190
|
+
resolveFill as al,
|
|
6191
|
+
resolveMarker as am,
|
|
6192
|
+
resolveStroke as an,
|
|
6193
|
+
sceneBBox as ao,
|
|
6194
|
+
styleNode as ap,
|
|
6195
|
+
writeOverrides as aq,
|
|
6096
6196
|
EditController as b,
|
|
6097
6197
|
EdodoDraw as c,
|
|
6098
6198
|
FONT_FAMILY as d,
|
|
@@ -6119,4 +6219,4 @@ export {
|
|
|
6119
6219
|
deleteElements as y,
|
|
6120
6220
|
dist as z
|
|
6121
6221
|
};
|
|
6122
|
-
//# sourceMappingURL=EdodoDraw-
|
|
6222
|
+
//# sourceMappingURL=EdodoDraw-BdJowisU.js.map
|