wordinweb 0.1.5 → 0.1.6

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/index.d.ts CHANGED
@@ -1598,6 +1598,14 @@ interface TextMeasurer {
1598
1598
  ascent: number;
1599
1599
  descent: number;
1600
1600
  } | undefined;
1601
+ /** Ink extents (actualBoundingBox*) of `text` in the RESOLVED paint face,
1602
+ * px above/below the baseline. The radical join needs the √ glyph's real
1603
+ * ink — which face paints it (real Cambria Math vs the STIX substitute)
1604
+ * changes the extents, so a baked table can't cover both. */
1605
+ inkBox?(text: string, font: FontSpec): {
1606
+ ascent: number;
1607
+ descent: number;
1608
+ } | undefined;
1601
1609
  }
1602
1610
 
1603
1611
  interface LayoutOptions {
package/dist/index.js CHANGED
@@ -5157,6 +5157,7 @@ var CanvasMeasurer = class {
5157
5157
  this.widthCache = /* @__PURE__ */ new Map();
5158
5158
  this.metricsCache = /* @__PURE__ */ new Map();
5159
5159
  this.paintBoxCache = /* @__PURE__ */ new Map();
5160
+ this.inkBoxCache = /* @__PURE__ */ new Map();
5160
5161
  this.currentFont = "";
5161
5162
  if (typeof OffscreenCanvas !== "undefined") {
5162
5163
  const c = new OffscreenCanvas(1, 1);
@@ -5200,6 +5201,18 @@ var CanvasMeasurer = class {
5200
5201
  }
5201
5202
  return m ?? void 0;
5202
5203
  }
5204
+ /** Glyph ink extents at 3x (like width()) from the resolved paint face. */
5205
+ inkBox(text, font) {
5206
+ const key = "ink " + fontKey(font) + " " + text;
5207
+ let m = this.inkBoxCache.get(key);
5208
+ if (m === void 0) {
5209
+ this.setFont({ ...font, size: font.size * 3 });
5210
+ const tm = this.ctx.measureText(text);
5211
+ m = tm.actualBoundingBoxAscent !== void 0 && tm.actualBoundingBoxDescent !== void 0 ? { ascent: tm.actualBoundingBoxAscent / 3, descent: tm.actualBoundingBoxDescent / 3 } : null;
5212
+ this.inkBoxCache.set(key, m);
5213
+ }
5214
+ return m ?? void 0;
5215
+ }
5203
5216
  metrics(font) {
5204
5217
  const key = fontKey(font);
5205
5218
  let m = this.metricsCache.get(key);
@@ -5853,14 +5866,12 @@ function flow(nodes, size, dy, box, measurer, tight, display = false, breakDepth
5853
5866
  for (const r of degBox.rules) box.rules.push({ ...r, x1: box.width + r.x1, x2: box.width + r.x2, dy: degDy + r.dy });
5854
5867
  box.width += degBox.width + size * RAD_KERN_AFTER_DEG;
5855
5868
  }
5856
- let grow = Math.max(1, signInkH / (m.ascent + signDesc));
5857
- let signAnchor = -signDesc;
5858
- if (nestedGrown) {
5859
- const inkTopNat = size * RAD_VARIANTS[0].top / 2048;
5860
- const inkBotNat = size * RAD_VARIANTS[0].bot / 2048;
5861
- grow = (paintRuleTop + size * RAD_GROWN_FOOT) / (inkTopNat - inkBotNat);
5862
- signAnchor = (-size * RAD_GROWN_FOOT - inkBotNat * grow) / (1 - grow);
5863
- }
5869
+ const signInk = measurer.inkBox?.("\u221A", font);
5870
+ const inkTopNat = signInk ? signInk.ascent : size * RAD_VARIANTS[0].top / 2048;
5871
+ const inkBotNat = signInk ? -signInk.descent : size * RAD_VARIANTS[0].bot / 2048;
5872
+ const signFoot = nestedGrown ? size * RAD_GROWN_FOOT : signDesc;
5873
+ const grow = (paintRuleTop + signFoot) / (inkTopNat - inkBotNat);
5874
+ const signAnchor = grow === 1 ? 0 : (-signFoot - inkBotNat * grow) / (1 - grow);
5864
5875
  const topLevelDisplay = display && breakDepth === 0 && complexRad;
5865
5876
  const signW = measurer.width("\u221A", font);
5866
5877
  box.pieces.push({
@@ -16310,9 +16321,11 @@ function linearizeMath(nodes) {
16310
16321
  case "frac":
16311
16322
  out += group(n.num) + "/" + group(n.den);
16312
16323
  break;
16313
- case "rad":
16314
- out += "\u221A" + group(n.e);
16324
+ case "rad": {
16325
+ const deg = n.deg && n.deg.length ? linearizeMath(n.deg) : "";
16326
+ out += deg ? "\u221A[" + deg + "]" + group(n.e) : "\u221A" + group(n.e);
16315
16327
  break;
16328
+ }
16316
16329
  case "nary":
16317
16330
  out += n.chr + (n.sub.length ? "_" + group(n.sub) : "") + (n.sup.length ? "^" + group(n.sup) : "") + group(n.e);
16318
16331
  break;
@@ -16442,10 +16455,12 @@ function parseMathLinear(input) {
16442
16455
  const parseUnit = () => {
16443
16456
  const ch = input[i];
16444
16457
  if (ch === "{") return parseGroup();
16445
- if (ch === "\u221A") {
16458
+ if (ch === "\u221A" || ch === "\u221B" || ch === "\u221C") {
16446
16459
  i++;
16460
+ let deg = ch === "\u221B" ? [{ t: "run", text: "3" }] : ch === "\u221C" ? [{ t: "run", text: "4" }] : [];
16461
+ if (ch === "\u221A" && input[i] === "[") deg = parseMathLinear(scanDelim("[", "]"));
16447
16462
  const e = input[i] === "{" ? parseGroup() : parseUnit();
16448
- return [{ t: "rad", e }];
16463
+ return deg.length ? [{ t: "rad", e, deg }] : [{ t: "rad", e }];
16449
16464
  }
16450
16465
  if (NARY_CHRS.has(ch)) return parseNary();
16451
16466
  if (ch in DELIM_CLOSE) return parseDelim(ch);
@@ -16631,7 +16646,11 @@ function ommlToNodes(e) {
16631
16646
  }
16632
16647
  if (ln === "sSup") return [{ t: "sup", base: kids("e"), script: kids("sup") }];
16633
16648
  if (ln === "sSub") return [{ t: "sub", base: kids("e"), script: kids("sub") }];
16634
- if (ln === "rad") return [{ t: "rad", e: kids("e") }];
16649
+ if (ln === "rad") {
16650
+ const hide = chrAttr("radPr", "degHide", "0");
16651
+ const deg = hide === "1" || hide === "true" || hide === "on" ? [] : kids("deg");
16652
+ return deg.length ? [{ t: "rad", e: kids("e"), deg }] : [{ t: "rad", e: kids("e") }];
16653
+ }
16635
16654
  if (ln === "t") return e.text ? [{ t: "run", text: e.text }] : [];
16636
16655
  const out = [];
16637
16656
  for (const c of e.children) {
@@ -16663,9 +16682,11 @@ function sameStructure(a, b) {
16663
16682
  case "frac":
16664
16683
  if (!sameStructure(x.num, y.num) || !sameStructure(x.den, y.den)) return false;
16665
16684
  break;
16666
- case "rad":
16667
- if (!sameStructure(x.e, y.e)) return false;
16685
+ case "rad": {
16686
+ const yy = y;
16687
+ if (!sameStructure(x.e, yy.e) || !sameStructure(x.deg ?? [], yy.deg ?? [])) return false;
16668
16688
  break;
16689
+ }
16669
16690
  case "nary": {
16670
16691
  const yy = y;
16671
16692
  if (x.chr !== yy.chr || !sameStructure(x.sub, yy.sub) || !sameStructure(x.sup, yy.sup) || !sameStructure(x.e, yy.e))
@@ -19676,7 +19697,7 @@ var _DocxEditor = class _DocxEditor {
19676
19697
  row.style.cssText = "display:flex;gap:6px;align-items:center;";
19677
19698
  const input = document.createElement("input");
19678
19699
  input.value = original;
19679
- input.title = "Linear math: x^2, x_i, {a+b}/{2}, \u221A{x}";
19700
+ input.title = "Linear math: x^2, x_i, {a+b}/{2}, \u221A{x}, \u221A[n]{x}";
19680
19701
  input.style.cssText = "width:260px;border:1px solid #dadce0;border-radius:6px;padding:5px 8px;outline:none;font:14px 'Cambria Math','STIX Two Math',serif;transition:border-color .12s,background .12s;";
19681
19702
  const caption = document.createElement("div");
19682
19703
  caption.style.cssText = "font:11px system-ui,sans-serif;color:#5f6368;max-width:300px;";
@@ -19699,7 +19720,7 @@ var _DocxEditor = class _DocxEditor {
19699
19720
  }
19700
19721
  });
19701
19722
  } else {
19702
- caption.textContent = "Linear math: x^2, x_i, {a+b}/{2}, \u221A{x}. Enter to apply.";
19723
+ caption.textContent = "Linear math: x^2, x_i, {a+b}/{2}, \u221A{x}, \u221A[n]{x}. Enter to apply.";
19703
19724
  const apply = document.createElement("button");
19704
19725
  apply.textContent = "Apply";
19705
19726
  apply.style.cssText = "border:1px solid #dadce0;border-radius:14px;padding:3px 12px;cursor:pointer;background:#1a73e8;color:#fff;";