@panda-lingo/goldendict 0.1.1 → 0.1.3

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 CHANGED
@@ -28,6 +28,24 @@ scrollable, unwraps common floated wiki panels on narrow screens, and keeps
28
28
  article headers usable with coarse pointers. The pinned GoldenDict-ng CSS stays
29
29
  unchanged so upstream updates remain straightforward.
30
30
 
31
+ For GoldenDict-compatible article geometry, select the fidelity layout. This
32
+ omits the browser override layer so the upstream body margin, content-box model,
33
+ dictionary header flow, and dictionary-authored CSS cascade remain intact.
34
+ Script permission is independent: a dictionary may require both fidelity layout
35
+ and sandboxed sidecar JavaScript.
36
+
37
+ ```ts
38
+ view.layoutMode = "fidelity";
39
+ view.scriptPolicy = "sandboxed";
40
+ ```
41
+
42
+ The default `layoutMode` is `"responsive"`; the bundled demo deliberately uses
43
+ `"fidelity"` so it can be compared directly with GoldenDict-ng. Consumers can
44
+ also set `layout-mode="fidelity"` on the custom element.
45
+
46
+ Compare at the same CSS viewport, device scale, and GoldenDict zoom: those host
47
+ browser settings still affect physical pixel size and line wrapping.
48
+
31
49
  ```css
32
50
  .dictionary-column {
33
51
  min-width: 0;
@@ -59,10 +77,11 @@ explicit `"sandboxed"` policy retains them inside the iframe, which never gets
59
77
  `allow-same-origin`. Lookup, media, and external-link events are cancelable so a
60
78
  host application can replace the default navigation behavior.
61
79
 
62
- The bundled demo deliberately selects `"sandboxed"` for locally mounted
63
- dictionaries so script-dependent formats such as OALDPE render with their full
64
- GoldenDict typography and interactions. This demo choice does not change the
65
- component's safer `"none"` default for consumers.
80
+ The bundled demo deliberately selects `"sandboxed"` scripts and `"fidelity"`
81
+ layout for locally mounted dictionaries so script-dependent formats such as
82
+ OALDPE render with their GoldenDict typography, geometry, and interactions.
83
+ These demo choices do not change the component defaults (`"none"` scripts and
84
+ `"responsive"` layout) for consumers.
66
85
 
67
86
  In sandboxed mode, external sidecars such as `bres://.../Dictionary-UI.js` are
68
87
  routed through the article's `resourceBaseUrl` without changing filename case.
@@ -1,5 +1,5 @@
1
1
  import { DictionaryClient } from "../client/dictionary-client";
2
- import type { DictionaryClientOptions, GoldenDictTheme, LookupResponse, ScriptPolicy, ViewState } from "../types";
2
+ import type { ArticleLayoutMode, DictionaryClientOptions, GoldenDictTheme, LookupResponse, ScriptPolicy, ViewState } from "../types";
3
3
  export declare class GoldenDictView extends HTMLElement {
4
4
  static readonly observedAttributes: string[];
5
5
  readonly instanceId: string;
@@ -30,6 +30,8 @@ export declare class GoldenDictView extends HTMLElement {
30
30
  set theme(value: GoldenDictTheme);
31
31
  get scriptPolicy(): ScriptPolicy;
32
32
  set scriptPolicy(value: ScriptPolicy);
33
+ get layoutMode(): ArticleLayoutMode;
34
+ set layoutMode(value: ArticleLayoutMode);
33
35
  get dictionaryIds(): readonly string[];
34
36
  set dictionaryIds(value: readonly string[]);
35
37
  get state(): ViewState;
@@ -1 +1 @@
1
- {"version":3,"file":"goldendict-view.d.ts","sourceRoot":"","sources":["../../src/element/goldendict-view.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"goldendict-view.d.ts","sourceRoot":"","sources":["../../src/element/goldendict-view.ts"],"names":[],"mappings":"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"}
package/dist/index.js CHANGED
@@ -311,7 +311,7 @@ const M = `<?xml version="1.0" encoding="UTF-8" standalone="no"?>
311
311
  x="1.1215118e-09"
312
312
  y="4.9718442"
313
313
  ry="0.64957041" /></svg>
314
- `, R = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAACXBIWXMAAATrAAAE6wHYKlsNAAAAGXRFWHRTb2Z0d2FyZQB3d3cuaW5rc2NhcGUub3Jnm+48GgAAAcRJREFUOI2lkztvE0EQgL8Z7/rB2T5fCixhQQc00FAjJCRkiTYV/JH0adIgfgJVGn4CKRBUSIjCHYiOBimK7KA4ORw/dofC3Ck2dhpGGu1r5pvZmV0xM/5HXDEZDAbf2u12BkiM0UIImBlmRoyxHBeLBaPRaNzv9++tAJIkyVS1673HzBCRUtfFzEo/d/VAVRERzvf2uDw6AqB6eMhlt1va9Hq9FWgJiDEiIqgqcTwmnp4CUPeearu9EmRjDYp7qiqVNEV3dgCYx8hlniMimBlZlm0GFN0QERoHB7j9/bIGVUDiHCrVfzLQqwDvPSLCZDIhz3MuLi6YTye4eY58fkOnUbkeUERMkoRWq0WaptRqDaYfXvPr3StmP75cX4PZbIb3HoDx6TmttImveZoPn9N+0KfWvbsdYGY45xARvn76zvu3H8m6GS/2dpnefLRsb4Bb2wAhBJxbLoc/hwCcDc9QqVCvuzLy+uPa2IUnu4+p36hz5/5tGkmdxWKBc45Op0MIYXsNClAzTXj28imquqKFzUbA8fHxbzMbi0glhKBmpsuEREQkqmpU1Sgi8eTkJC/8ZNN3FhEHNIHG360pkJvZdN32D0SOwDehr1HXAAAAAElFTkSuQmCC", N = `<?xml version="1.0" encoding="UTF-8" standalone="no"?>
314
+ `, R = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAACXBIWXMAAATrAAAE6wHYKlsNAAAAGXRFWHRTb2Z0d2FyZQB3d3cuaW5rc2NhcGUub3Jnm+48GgAAAcRJREFUOI2lkztvE0EQgL8Z7/rB2T5fCixhQQc00FAjJCRkiTYV/JH0adIgfgJVGn4CKRBUSIjCHYiOBimK7KA4ORw/dofC3Ck2dhpGGu1r5pvZmV0xM/5HXDEZDAbf2u12BkiM0UIImBlmRoyxHBeLBaPRaNzv9++tAJIkyVS1673HzBCRUtfFzEo/d/VAVRERzvf2uDw6AqB6eMhlt1va9Hq9FWgJiDEiIqgqcTwmnp4CUPeearu9EmRjDYp7qiqVNEV3dgCYx8hlniMimBlZlm0GFN0QERoHB7j9/bIGVUDiHCrVfzLQqwDvPSLCZDIhz3MuLi6YTye4eY58fkOnUbkeUERMkoRWq0WaptRqDaYfXvPr3StmP75cX4PZbIb3HoDx6TmttImveZoPn9N+0KfWvbsdYGY45xARvn76zvu3H8m6GS/2dpnefLRsb4Bb2wAhBJxbLoc/hwCcDc9QqVCvuzLy+uPa2IUnu4+p36hz5/5tGkmdxWKBc45Op0MIYXsNClAzTXj28imquqKFzUbA8fHxbzMbi0glhKBmpsuEREQkqmpU1Sgi8eTkJC/8ZNN3FhEHNIHG360pkJvZdN32D0SOwDehr1HXAAAAAElFTkSuQmCC", G = `<?xml version="1.0" encoding="UTF-8" standalone="no"?>
315
315
  <!-- Created with Inkscape (http://www.inkscape.org/) -->
316
316
 
317
317
  <svg
@@ -357,7 +357,7 @@ const M = `<?xml version="1.0" encoding="UTF-8" standalone="no"?>
357
357
  sodipodi:nodetypes="cccc" />
358
358
  </g>
359
359
  </svg>
360
- `, G = `<?xml version="1.0" encoding="UTF-8" standalone="no"?>
360
+ `, N = `<?xml version="1.0" encoding="UTF-8" standalone="no"?>
361
361
  <!-- Created with Inkscape (http://www.inkscape.org/) -->
362
362
 
363
363
  <svg
@@ -731,9 +731,9 @@ const u = {
731
731
  "collapse_article_hovered.svg": s($),
732
732
  "collapse_opt.svg": s(P),
733
733
  "document.png": R,
734
- "downarrow.svg": s(N),
734
+ "downarrow.svg": s(G),
735
735
  "expand_article.svg": s(O),
736
- "expand_article_hovered.svg": s(G),
736
+ "expand_article_hovered.svg": s(N),
737
737
  "expand_opt.svg": s(V),
738
738
  "old-arrow.svg": s(H),
739
739
  "old-downarrow.svg": s(W),
@@ -8076,8 +8076,8 @@ function p(i, e) {
8076
8076
  try {
8077
8077
  t = new URL(i);
8078
8078
  } catch {
8079
- const l = S(e);
8080
- return l ? pe(i, l) : i;
8079
+ const d = S(e);
8080
+ return d ? pe(i, d) : i;
8081
8081
  }
8082
8082
  const n = t.protocol.slice(0, -1).toLowerCase();
8083
8083
  if (!T.has(n))
@@ -8088,7 +8088,7 @@ function p(i, e) {
8088
8088
  ...e,
8089
8089
  iconUrl: void 0
8090
8090
  }) : A("qrc:///icons/document.png") ?? "";
8091
- const r = me(t), d = `${e.apiBaseUrl.replace(/\/+$/, "")}/dictionaries/${encodeURIComponent(a)}/resources`, m = I(S(e) ?? d, r);
8091
+ const r = me(t), l = `${e.apiBaseUrl.replace(/\/+$/, "")}/dictionaries/${encodeURIComponent(a)}/resources`, m = I(S(e) ?? l, r);
8092
8092
  return t.hash ? `${m}${t.hash}` : m;
8093
8093
  }
8094
8094
  function ge(i) {
@@ -8103,8 +8103,8 @@ function ge(i) {
8103
8103
  const r = new URL(i);
8104
8104
  t = r.searchParams.get("word") ?? r.pathname.replace(/^\/+/, ""), n = r.searchParams.get("gdanchor") ?? (r.hash.slice(1) || void 0), a = r.searchParams.get("dictionaries")?.split(",").filter(Boolean), !t && (o === "bword" || o === "entry") && (t = r.hostname);
8105
8105
  } catch {
8106
- const r = e[2]?.replace(/^\/{0,2}/, "") ?? "", [d, m] = r.split("#", 2), [l, w] = (d ?? "").split("?", 2);
8107
- t = l ?? "", n = new URLSearchParams(w ?? "").get("gdanchor") ?? (m || void 0);
8106
+ const r = e[2]?.replace(/^\/{0,2}/, "") ?? "", [l, m] = r.split("#", 2), [d, w] = (l ?? "").split("?", 2);
8107
+ t = d ?? "", n = new URLSearchParams(w ?? "").get("gdanchor") ?? (m || void 0);
8108
8108
  }
8109
8109
  return t = f(t.replace(/^\/+/, "")), t ? {
8110
8110
  kind: "lookup",
@@ -8154,10 +8154,10 @@ function fe(i, e, o) {
8154
8154
  ];
8155
8155
  for (const [a, r] of t)
8156
8156
  if (i.hasAttribute(a)) {
8157
- const d = i.getAttribute(a)?.trim();
8157
+ const l = i.getAttribute(a)?.trim();
8158
8158
  return {
8159
8159
  kind: r,
8160
- url: p(d || e, o)
8160
+ url: p(l || e, o)
8161
8161
  };
8162
8162
  }
8163
8163
  const n = i.getAttribute("data-gd-action")?.trim().toLowerCase();
@@ -8170,8 +8170,8 @@ function fe(i, e, o) {
8170
8170
  const r = D(e, o);
8171
8171
  if (r.kind === "lookup")
8172
8172
  return r;
8173
- const d = i.getAttribute("data-gd-word")?.trim();
8174
- return d ? { kind: "lookup", word: d } : { kind: "unsafe" };
8173
+ const l = i.getAttribute("data-gd-word")?.trim();
8174
+ return l ? { kind: "lookup", word: l } : { kind: "unsafe" };
8175
8175
  }
8176
8176
  if (n === "unsafe")
8177
8177
  return { kind: "unsafe" };
@@ -8243,25 +8243,25 @@ function ue(i, e, o) {
8243
8243
  }), o === "none" && a.querySelectorAll("script").forEach((r) => r.remove());
8244
8244
  for (const r of a.querySelectorAll("*")) {
8245
8245
  if (ke(r), o === "none")
8246
- for (const l of [...r.attributes])
8247
- (/^on/i.test(l.name) || l.name.toLowerCase() === "srcdoc") && r.removeAttribute(l.name);
8246
+ for (const d of [...r.attributes])
8247
+ (/^on/i.test(d.name) || d.name.toLowerCase() === "srcdoc") && r.removeAttribute(d.name);
8248
8248
  if (r instanceof HTMLAnchorElement || r.tagName === "AREA") {
8249
- const l = r.getAttribute("href");
8250
- l !== null && we(
8249
+ const d = r.getAttribute("href");
8250
+ d !== null && we(
8251
8251
  r,
8252
- fe(r, l, t) ?? D(l, t),
8252
+ fe(r, d, t) ?? D(d, t),
8253
8253
  i.dictionaryId
8254
8254
  );
8255
8255
  } else if (r.hasAttribute("href")) {
8256
- const l = r.getAttribute("href") ?? "";
8257
- x(l) || r.setAttribute("href", p(l, t));
8256
+ const d = r.getAttribute("href") ?? "";
8257
+ x(d) || r.setAttribute("href", p(d, t));
8258
8258
  }
8259
- for (const l of he) {
8260
- const w = r.getAttribute(l);
8261
- w === null || x(w) || (/^(?:javascript|vbscript|file):/i.test(w) ? r.removeAttribute(l) : r.setAttribute(l, p(w, t)));
8259
+ for (const d of he) {
8260
+ const w = r.getAttribute(d);
8261
+ w === null || x(w) || (/^(?:javascript|vbscript|file):/i.test(w) ? r.removeAttribute(d) : r.setAttribute(d, p(w, t)));
8262
8262
  }
8263
- const d = r.getAttribute("srcset");
8264
- d && r.setAttribute("srcset", be(d, t));
8263
+ const l = r.getAttribute("srcset");
8264
+ l && r.setAttribute("srcset", be(l, t));
8265
8265
  const m = r.getAttribute("style");
8266
8266
  m && r.setAttribute(
8267
8267
  "style",
@@ -8362,7 +8362,7 @@ function Ae(i, e) {
8362
8362
  }) : u["document.png"];
8363
8363
  }
8364
8364
  function Se(i, e, o) {
8365
- const t = g(i.dictionaryId), n = _e(i.dictionaryId), a = ue(i, e, o), r = ze(i.sourceLanguage), d = g(i.targetLanguage ?? ""), m = g(Ae(i, e));
8365
+ const t = g(i.dictionaryId), n = _e(i.dictionaryId), a = ue(i, e, o), r = ze(i.sourceLanguage), l = g(i.targetLanguage ?? ""), m = g(Ae(i, e));
8366
8366
  return `
8367
8367
  <article class="gdarticle" id="gdfrom-${n}" data-gd-id="${t}">
8368
8368
  <gd-dict-header class="gddictname" id="gddictname-${n}"
@@ -8375,9 +8375,9 @@ function Se(i, e, o) {
8375
8375
  </span>
8376
8376
  </gd-dict-header>
8377
8377
  <section class="gdarticlebody gdlangfrom-${r}"
8378
- lang="${d}" id="gd-${n}">${a}</section>
8378
+ lang="${l}" style="display:block" id="gd-${n}">${a}</section>
8379
8379
  </article>
8380
- <div class="gdclear" aria-hidden="true"></div>
8380
+ <div style="clear:both;" aria-hidden="true"></div>
8381
8381
  <span class="gdarticleseparator"></span>`;
8382
8382
  }
8383
8383
  function Ce(i) {
@@ -8564,25 +8564,29 @@ function Ie(i, e) {
8564
8564
  "base-uri 'none'"
8565
8565
  ].join("; ");
8566
8566
  }
8567
- function De(i, e) {
8568
- const o = e.theme ?? {}, t = E(o.mode), n = e.instanceId.replace(/[^a-zA-Z0-9_-]/g, ""), a = i.articles.map(
8569
- (m) => Se(m, e.apiBaseUrl, e.scriptPolicy)
8570
- ).join(""), r = a ? `${a}<div class="empty-space" aria-hidden="true"></div>` : `<div class="gdnotfound"><p>No translation for <b>${g(i.word)}</b> was found.</p></div>`, d = o.brandName ? `${i.word} — ${o.brandName}` : i.word;
8567
+ function De() {
8568
+ return 'globalThis.__DICT__={name:"GoldenDict",version:"web"};';
8569
+ }
8570
+ function Ee(i, e) {
8571
+ const o = e.theme ?? {}, t = E(o.mode), n = e.layoutMode ?? "responsive", a = e.instanceId.replace(/[^a-zA-Z0-9_-]/g, ""), r = i.articles.map(
8572
+ (d) => Se(d, e.apiBaseUrl, e.scriptPolicy)
8573
+ ).join(""), l = r ? `${r}<div class="empty-space" aria-hidden="true"></div>` : `<div class="gdnotfound"><p>No translation for <b>${g(i.word)}</b> was found.</p></div>`, m = o.brandName ? `${i.word} — ${o.brandName}` : i.word;
8571
8574
  return `<!doctype html>
8572
- <html data-gd-theme="${t}" data-darkreader-scheme="${t}"><head>
8575
+ <html data-gd-theme="${t}" data-gd-layout="${n}" data-darkreader-scheme="${t}"><head>
8573
8576
  <meta charset="utf-8">
8574
8577
  <meta name="viewport" content="width=device-width,initial-scale=1">
8575
- <meta http-equiv="Content-Security-Policy" content="${g(Ie(e.scriptPolicy, n))}">
8576
- <title>${g(d)}</title>
8578
+ <meta http-equiv="Content-Security-Policy" content="${g(Ie(e.scriptPolicy, a))}">
8579
+ <title>${g(m)}</title>
8580
+ <script nonce="${a}" data-gd-runtime="compatibility">${De()}<\/script>
8577
8581
  <style>${k(re)}</style>
8578
8582
  <style>${k(de(o.preset))}</style>
8579
- <style data-gd-style="responsive">${k(le)}</style>
8583
+ ${n === "responsive" ? `<style data-gd-style="responsive">${k(le)}</style>` : ""}
8580
8584
  <style>${ve(o)}</style>
8581
8585
  <style media="print">${k(ae)}</style>
8582
8586
  </head><body>
8583
- ${r}
8587
+ ${l}
8584
8588
  ${Ce(i.suggestions)}
8585
- <script nonce="${n}">${Te(e.instanceId, t).replace(/<\/script/gi, "<\\/script")}<\/script>
8589
+ <script nonce="${a}">${Te(e.instanceId, t).replace(/<\/script/gi, "<\\/script")}<\/script>
8586
8590
  </body></html>`;
8587
8591
  }
8588
8592
  const b = {
@@ -8592,7 +8596,7 @@ const b = {
8592
8596
  mediaRequest: "goldendict-media-request",
8593
8597
  externalLink: "goldendict-external-link",
8594
8598
  stateChange: "goldendict-state-change"
8595
- }, Ee = `
8599
+ }, qe = `
8596
8600
  :host{display:block;box-sizing:border-box;width:100%;min-width:0;max-width:100%;color:#222;font-family:system-ui,sans-serif;container:goldendict-view / inline-size}
8597
8601
  .shell{position:relative;box-sizing:border-box;width:100%;min-width:0;max-width:100%;min-height:8rem;border-radius:var(--gd-host-radius,8px);overflow:hidden;background:var(--gd-host-background,#fff)}
8598
8602
  .brand{display:flex;align-items:center;gap:.65rem;min-width:0;padding:.65rem .9rem;border-bottom:1px solid var(--gd-host-border,#e3e3e3);background:var(--gd-host-surface,#f7f9fb);font-weight:650}
@@ -8610,10 +8614,10 @@ const b = {
8610
8614
  @container goldendict-view (max-width:30rem){.brand{gap:.5rem;padding:.55rem .65rem}.status{padding:1rem .75rem}}
8611
8615
  @media (prefers-reduced-motion:reduce){.spinner{animation:none}}
8612
8616
  `;
8613
- function qe() {
8617
+ function Le() {
8614
8618
  return globalThis.crypto?.randomUUID?.() ?? `gd-${Date.now().toString(36)}-${Math.random().toString(36).slice(2)}`;
8615
8619
  }
8616
- function Le(i) {
8620
+ function Be(i) {
8617
8621
  return (i instanceof DOMException || i instanceof Error) && i.name === "AbortError";
8618
8622
  }
8619
8623
  class _ extends HTMLElement {
@@ -8622,9 +8626,10 @@ class _ extends HTMLElement {
8622
8626
  "word",
8623
8627
  "preset",
8624
8628
  "theme-mode",
8625
- "script-policy"
8629
+ "script-policy",
8630
+ "layout-mode"
8626
8631
  ];
8627
- instanceId = qe();
8632
+ instanceId = Le();
8628
8633
  frame;
8629
8634
  statusElement;
8630
8635
  brandElement;
@@ -8643,7 +8648,7 @@ class _ extends HTMLElement {
8643
8648
  constructor() {
8644
8649
  super();
8645
8650
  const e = this.attachShadow({ mode: "open" });
8646
- e.innerHTML = `<style>${Ee}</style>
8651
+ e.innerHTML = `<style>${qe}</style>
8647
8652
  <section class="shell" part="container">
8648
8653
  <div class="brand" part="brand" hidden>
8649
8654
  <img alt="" hidden><span></span>
@@ -8668,7 +8673,7 @@ class _ extends HTMLElement {
8668
8673
  } : e === "theme-mode" ? this.theme = {
8669
8674
  ...this.themeValue,
8670
8675
  mode: t || "light"
8671
- } : e === "script-policy" && this.responseValue && this.renderResponse(this.responseValue));
8676
+ } : (e === "script-policy" || e === "layout-mode") && this.responseValue && this.renderResponse(this.responseValue));
8672
8677
  }
8673
8678
  get apiBase() {
8674
8679
  return this.getAttribute("api-base")?.trim() || "/api/v1";
@@ -8694,6 +8699,12 @@ class _ extends HTMLElement {
8694
8699
  set scriptPolicy(e) {
8695
8700
  this.setAttribute("script-policy", e);
8696
8701
  }
8702
+ get layoutMode() {
8703
+ return this.getAttribute("layout-mode") === "fidelity" ? "fidelity" : "responsive";
8704
+ }
8705
+ set layoutMode(e) {
8706
+ this.setAttribute("layout-mode", e);
8707
+ }
8697
8708
  get dictionaryIds() {
8698
8709
  return this.dictionaryIdsValue;
8699
8710
  }
@@ -8727,10 +8738,10 @@ class _ extends HTMLElement {
8727
8738
  return;
8728
8739
  this.setLookupResponse(r);
8729
8740
  } catch (r) {
8730
- if (n !== this.requestSequence || Le(r))
8741
+ if (n !== this.requestSequence || Be(r))
8731
8742
  return;
8732
- const d = r instanceof Error ? r : new Error(String(r));
8733
- this.responseValue = void 0, this.resetFrame(), this.setState("error", { word: t, error: d });
8743
+ const l = r instanceof Error ? r : new Error(String(r));
8744
+ this.responseValue = void 0, this.resetFrame(), this.setState("error", { word: t, error: l });
8734
8745
  } finally {
8735
8746
  n === this.requestSequence && (this.requestController = void 0);
8736
8747
  }
@@ -8752,10 +8763,11 @@ class _ extends HTMLElement {
8752
8763
  this.activeBridgeInstanceId = t;
8753
8764
  const n = this.replaceFrame(!1);
8754
8765
  n.title = e.word ? `Dictionary results for ${e.word}` : "Dictionary article";
8755
- const a = De(e, {
8766
+ const a = Ee(e, {
8756
8767
  apiBaseUrl: this.clientValue.baseUrl,
8757
8768
  instanceId: t,
8758
8769
  scriptPolicy: this.scriptPolicy,
8770
+ layoutMode: this.layoutMode,
8759
8771
  theme: this.themeValue
8760
8772
  });
8761
8773
  requestAnimationFrame(() => {
@@ -8885,13 +8897,13 @@ class _ extends HTMLElement {
8885
8897
  return this.dispatchEvent(n), n;
8886
8898
  }
8887
8899
  }
8888
- function Be(i = "goldendict-view") {
8900
+ function Me(i = "goldendict-view") {
8889
8901
  if (!globalThis.customElements)
8890
8902
  return _;
8891
8903
  const e = globalThis.customElements.get(i);
8892
8904
  return e || (globalThis.customElements.define(i, _), _);
8893
8905
  }
8894
- Be();
8906
+ Me();
8895
8907
  export {
8896
8908
  ye as DARK_THEME_TOKENS,
8897
8909
  q as DictionaryApiError,
@@ -8901,7 +8913,7 @@ export {
8901
8913
  _ as GoldenDictView,
8902
8914
  xe as LIGHT_THEME_TOKENS,
8903
8915
  D as classifyArticleLink,
8904
- Be as defineGoldendictView,
8916
+ Me as defineGoldendictView,
8905
8917
  k as escapeStyleText,
8906
8918
  p as resolveResourceUrl,
8907
8919
  E as resolveThemeMode,