@faith-tools/bible-sdk 0.0.0-stage → 0.7.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/LICENSE.md +21 -0
- package/README.md +584 -2
- package/dist/bible-sdk.js +261 -0
- package/dist/data/effect.js +66 -0
- package/dist/data.js +16 -0
- package/dist/index.js +946 -0
- package/dist/providers/api-bible.js +221 -0
- package/dist/providers/fetch-bible.js +254 -0
- package/dist/providers/helloao.js +1 -0
- package/dist/providers/youversion.js +1 -0
- package/dist/providers-Ci0Bdu9f.js +431 -0
- package/dist/runtime-CVlBLU4v.js +229 -0
- package/dist/scripture-inline.js +261 -0
- package/dist/types/card.d.ts +20 -0
- package/dist/types/data-effect.d.ts +206 -0
- package/dist/types/data-helpers.d.ts +21 -0
- package/dist/types/data-types.d.ts +125 -0
- package/dist/types/data.d.ts +102 -0
- package/dist/types/dom-runtime.d.ts +5 -0
- package/dist/types/find.d.ts +12 -0
- package/dist/types/index.d.ts +31 -0
- package/dist/types/passage-input.d.ts +57 -0
- package/dist/types/providers/api-bible.d.ts +37 -0
- package/dist/types/providers/fetch-bible.d.ts +14 -0
- package/dist/types/providers/helloao.d.ts +1 -0
- package/dist/types/providers/youversion.d.ts +1 -0
- package/dist/types/providers.d.ts +62 -0
- package/dist/types/runtime.d.ts +18 -0
- package/dist/types/scan.d.ts +8 -0
- package/dist/types/scripture-passage.d.ts +61 -0
- package/dist/types/version-input.d.ts +64 -0
- package/package.json +84 -3
package/dist/index.js
ADDED
|
@@ -0,0 +1,946 @@
|
|
|
1
|
+
import { a as e, c as t, i as n, l as r, n as i, o as a, r as o, s } from "./providers-Ci0Bdu9f.js";
|
|
2
|
+
import { OSIS_BOOK_CODES as c, OSIS_BOOK_NAMES as l, autocompletePassage as u, formatPassageForDisplay as d, getChapterCount as f, getVerseCount as p, parsePassage as m, parseToResolverUrl as h, resolveBookAlias as g, tryParsePassage as _ } from "grab-bcv";
|
|
3
|
+
import { Effect as v, Exit as y, Scope as b } from "effect";
|
|
4
|
+
// src/dom-runtime.ts
|
|
5
|
+
var x = (e, t, n, r) => v.acquireRelease(v.sync(() => e.addEventListener(t, n, r)), () => v.sync(() => e.removeEventListener(t, n, r))), S = v.callback((e) => {
|
|
6
|
+
let t = requestAnimationFrame(() => e(v.void));
|
|
7
|
+
return v.sync(() => cancelAnimationFrame(t));
|
|
8
|
+
}), C = (e, t) => v.callback((n) => {
|
|
9
|
+
let r = () => n(v.void);
|
|
10
|
+
for (let n of t) e.addEventListener(n, r);
|
|
11
|
+
return v.sync(() => {
|
|
12
|
+
for (let n of t) e.removeEventListener(n, r);
|
|
13
|
+
});
|
|
14
|
+
}), w = "si-passage", T = "bible-sk-passage", E = {
|
|
15
|
+
"font-sans": "\"Inter\",sans-serif",
|
|
16
|
+
"font-serif": "\"Source Serif 4\",serif",
|
|
17
|
+
"font-mono": "ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,\"Liberation Mono\",\"Courier New\",monospace",
|
|
18
|
+
"color-black": "#000",
|
|
19
|
+
"color-white": "#fff",
|
|
20
|
+
spacing: ".25rem",
|
|
21
|
+
"container-sm": "24rem",
|
|
22
|
+
"container-md": "28rem",
|
|
23
|
+
"container-lg": "32rem",
|
|
24
|
+
"text-xs": ".75rem",
|
|
25
|
+
"text-xs--line-height": "calc(1/.75)",
|
|
26
|
+
"text-sm": ".875rem",
|
|
27
|
+
"text-sm--line-height": "calc(1.25/.875)",
|
|
28
|
+
"text-base": "1rem",
|
|
29
|
+
"text-base--line-height": "calc(1.5/1)",
|
|
30
|
+
"text-lg": "1.125rem",
|
|
31
|
+
"text-lg--line-height": "calc(1.75/1.125)",
|
|
32
|
+
"text-xl": "1.25rem",
|
|
33
|
+
"text-xl--line-height": "calc(1.75/1.25)",
|
|
34
|
+
"text-2xl": "1.5rem",
|
|
35
|
+
"text-2xl--line-height": "calc(2/1.5)",
|
|
36
|
+
"text-3xl": "1.875rem",
|
|
37
|
+
"text-3xl--line-height": "calc(2.25/1.875)",
|
|
38
|
+
"font-weight-normal": "400",
|
|
39
|
+
"font-weight-medium": "500",
|
|
40
|
+
"font-weight-bold": "700",
|
|
41
|
+
"tracking-widest": ".1em",
|
|
42
|
+
"leading-tight": "1.25",
|
|
43
|
+
"leading-snug": "1.375",
|
|
44
|
+
"leading-normal": "1.5",
|
|
45
|
+
"radius-2xl": "1rem",
|
|
46
|
+
"radius-3xl": "1.5rem",
|
|
47
|
+
"ease-out": "cubic-bezier(0,0,.2,1)",
|
|
48
|
+
"animate-spin": "spin 1s linear infinite",
|
|
49
|
+
"animate-pulse": "pulse 2s cubic-bezier(.4,0,.6,1)infinite",
|
|
50
|
+
"blur-sm": "8px",
|
|
51
|
+
"default-transition-duration": ".15s",
|
|
52
|
+
"default-transition-timing-function": "cubic-bezier(.4,0,.2,1)"
|
|
53
|
+
}, D = Object.keys(E), O = `
|
|
54
|
+
/* flow-root keeps the passage's margins inside, so its layout is identical during and after the grow.
|
|
55
|
+
The host takes bible.css's tokens from the page when it sets them, and the wrapper uses them. */
|
|
56
|
+
:host {
|
|
57
|
+
display: flow-root;
|
|
58
|
+
position: relative;
|
|
59
|
+
${D.map((e) => `--yv-${e}: inherit; --si-${e}: var(--yv-${e}, ${E[e]});`).join("\n ")}
|
|
60
|
+
}
|
|
61
|
+
.scripture-root {
|
|
62
|
+
all: initial;
|
|
63
|
+
display: block;
|
|
64
|
+
color: inherit;
|
|
65
|
+
${D.map((e) => `--yv-${e}: var(--si-${e});`).join("\n ")}
|
|
66
|
+
}
|
|
67
|
+
.scripture-root { --scripture-muted: #666; --scripture-red: #a52424; }
|
|
68
|
+
.scripture-root[data-theme="dark"] { --scripture-muted: #aaa; --scripture-red: #ff9090; }
|
|
69
|
+
.scripture-bible {
|
|
70
|
+
font: var(--scripture-font-size, 20px)/var(--scripture-line-height, 1.625) var(--scripture-font-family, Georgia, serif);
|
|
71
|
+
max-width: var(--scripture-max-width, 32rem);
|
|
72
|
+
overflow-wrap: break-word;
|
|
73
|
+
}
|
|
74
|
+
.scripture-bible .scripture-verse-number, .fetch-bible sup[data-v] { font: 0.65em/1 system-ui, sans-serif; color: var(--scripture-muted); }
|
|
75
|
+
.fetch-bible sup[data-v] { padding-inline-end: 0.3em; }
|
|
76
|
+
.scripture-bible.fetch-bible .fb-wj { color: var(--scripture-red); }
|
|
77
|
+
.scripture-bible .scripture-heading { display: block; margin: 1em 0 0.5em; font: 600 0.85em/1.5 system-ui, sans-serif; }
|
|
78
|
+
.scripture-bible > .scripture-heading:first-child { margin-top: 0; }
|
|
79
|
+
.scripture-bible .scripture-jesus { color: var(--scripture-red); }
|
|
80
|
+
.scripture-bible .scripture-poetry { display: block; padding-inline-start: calc(var(--indent) * 1em); }
|
|
81
|
+
.scripture-bible .scripture-subtitle { margin: 0 0 0.5em; font-style: italic; }
|
|
82
|
+
:host([verse-numbers="hide"]) .scripture-verse-number { display: none; }
|
|
83
|
+
:host([red-letter="off"]) .scripture-jesus { color: inherit; }
|
|
84
|
+
:host([headings="hide"]) .scripture-heading { display: none; }
|
|
85
|
+
:host([verse-numbers="hide"]) .fetch-bible sup[data-v] { display: none; }
|
|
86
|
+
:host([red-letter="off"]) .fetch-bible .fb-wj { color: inherit; }
|
|
87
|
+
:host([headings="hide"]) .fetch-bible :is(.fb-ms, .fb-ms1, .fb-ms2, .fb-ms3, .fb-ms4, .fb-mr, .fb-s, .fb-s1, .fb-s2, .fb-s3, .fb-s4, .fb-sr, .fb-r, .fb-sp, .fb-qa) { display: none; }
|
|
88
|
+
/* Typography comes from --scripture-* properties, which pages set like any CSS. The fallbacks
|
|
89
|
+
are bible.css's own values, except the font: Untitled Serif is YouVersion's Bible typeface,
|
|
90
|
+
but bible.css defaults to Source Serif 4. */
|
|
91
|
+
[data-slot="yv-bible-renderer"] {
|
|
92
|
+
--yv-reader-font-family: var(--scripture-font-family, "Untitled Serif", "Source Serif 4", serif);
|
|
93
|
+
--yv-reader-font-size: var(--scripture-font-size, 20px);
|
|
94
|
+
--yv-reader-line-height: var(--scripture-line-height, 1.625);
|
|
95
|
+
--yv-reader-max-width: var(--scripture-max-width, 65ch);
|
|
96
|
+
/* bible.css caps each paragraph at this width. */
|
|
97
|
+
--yv-container-lg: var(--scripture-max-width, 32rem);
|
|
98
|
+
}
|
|
99
|
+
/* Content switches. CSS alone applies them, so toggling one never refetches or re-renders. */
|
|
100
|
+
:host([verse-numbers="hide"]) .yv-vlbl { display: none; }
|
|
101
|
+
:host([red-letter="off"]) .wj { color: inherit; }
|
|
102
|
+
/* .yv-h marks editorial headings. Psalm titles (.d) are Scripture, so they stay. */
|
|
103
|
+
:host([headings="hide"]) .yv-h { display: none; }
|
|
104
|
+
/* Translators' added words read as italic, as in print Bibles. bible.css also bolds them,
|
|
105
|
+
which stresses the words the original text does not contain. */
|
|
106
|
+
[data-slot="yv-bible-renderer"] .add { font-weight: inherit; }
|
|
107
|
+
/* Page frameworks (Sensible UI, Pico) draw their own spinner on [aria-busy]; this element has one.
|
|
108
|
+
!important in a shadow root beats the page's rules for the host. */
|
|
109
|
+
:host([aria-busy])::before, :host([aria-busy])::after { content: none !important; }
|
|
110
|
+
.scripture-loading { display: flex; padding: 0.75rem 0; opacity: 0.5; }
|
|
111
|
+
.scripture-stage { position: absolute; inset: 0 0 auto; height: 0; overflow: hidden; visibility: hidden; }
|
|
112
|
+
.scripture-loading > svg { animation: scripture-spin 0.8s linear infinite; }
|
|
113
|
+
@keyframes scripture-spin { to { transform: rotate(360deg); } }
|
|
114
|
+
[role="alert"] { margin: 0; opacity: 0.7; font-family: var(--yv-font-sans, system-ui, sans-serif); }
|
|
115
|
+
/* Every layout uses the same citation; only its place changes. */
|
|
116
|
+
.scripture-citation {
|
|
117
|
+
all: unset;
|
|
118
|
+
display: block;
|
|
119
|
+
/* Match the width bible.css gives the text. */
|
|
120
|
+
max-width: var(--scripture-max-width, 32rem);
|
|
121
|
+
margin-block-start: 1rem;
|
|
122
|
+
font: calc(var(--scripture-font-size, 20px) * 0.8)/1.5 var(--yv-font-sans, system-ui, sans-serif);
|
|
123
|
+
color: var(--yv-foreground);
|
|
124
|
+
}
|
|
125
|
+
.scripture-root > .scripture-citation:first-child { margin-block: 0 1rem; }
|
|
126
|
+
.scripture-citation > .scripture-version { color: var(--yv-muted-foreground, var(--scripture-muted)); }
|
|
127
|
+
/* The attribution always comes after the text, right under a citation when one follows it. */
|
|
128
|
+
.scripture-attribution {
|
|
129
|
+
all: unset;
|
|
130
|
+
display: block;
|
|
131
|
+
max-width: var(--scripture-max-width, 32rem);
|
|
132
|
+
margin-block-start: 1rem;
|
|
133
|
+
font: 0.75rem/1.5 var(--yv-font-sans, system-ui, sans-serif);
|
|
134
|
+
color: var(--yv-muted-foreground, var(--scripture-muted));
|
|
135
|
+
}
|
|
136
|
+
.scripture-root .scripture-attribution a { color: inherit; text-decoration: none; text-underline-offset: 0.15em; }
|
|
137
|
+
.scripture-root .scripture-attribution a:focus-visible { outline: 2px solid currentColor; outline-offset: 2px; }
|
|
138
|
+
@media (hover: hover) and (pointer: fine) {
|
|
139
|
+
.scripture-root .scripture-attribution a:hover { text-decoration: underline; }
|
|
140
|
+
}
|
|
141
|
+
.scripture-citation + .scripture-attribution { margin-block-start: 0; }
|
|
142
|
+
.scripture-quote {
|
|
143
|
+
all: unset;
|
|
144
|
+
display: block;
|
|
145
|
+
padding-inline-start: 1rem;
|
|
146
|
+
border-inline-start: 2px solid color-mix(in srgb, currentColor 18%, transparent);
|
|
147
|
+
}
|
|
148
|
+
@media (prefers-reduced-motion: reduce) { .scripture-loading > svg { animation-duration: 2.4s; } }`, k = "<svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><path d=\"M21 12a9 9 0 1 1-6.219-8.56\"/></svg>", A = matchMedia("(prefers-reduced-motion: reduce)"), j = [
|
|
149
|
+
"heading",
|
|
150
|
+
"citation",
|
|
151
|
+
"quote",
|
|
152
|
+
"none"
|
|
153
|
+
], M = class extends HTMLElement {
|
|
154
|
+
static observedAttributes = [
|
|
155
|
+
"provider",
|
|
156
|
+
"bible-version-id",
|
|
157
|
+
"yvp-public-app-key",
|
|
158
|
+
"yvp-api-host",
|
|
159
|
+
"yvp-bible-version-id",
|
|
160
|
+
"passage-id",
|
|
161
|
+
"theme",
|
|
162
|
+
"reference",
|
|
163
|
+
"direction"
|
|
164
|
+
];
|
|
165
|
+
providerOverride;
|
|
166
|
+
get bibleProvider() {
|
|
167
|
+
return this.providerOverride;
|
|
168
|
+
}
|
|
169
|
+
set bibleProvider(e) {
|
|
170
|
+
this.providerOverride = e, this.isConnected && this.scheduleLoad();
|
|
171
|
+
}
|
|
172
|
+
generation = 0;
|
|
173
|
+
loaded = null;
|
|
174
|
+
scheduled = !1;
|
|
175
|
+
cancelLoad;
|
|
176
|
+
cancelTheme;
|
|
177
|
+
cancelAnimation;
|
|
178
|
+
systemDark = matchMedia("(prefers-color-scheme: dark)");
|
|
179
|
+
onSystemTheme = () => this.applyTheme();
|
|
180
|
+
root = document.createElement("div");
|
|
181
|
+
constructor() {
|
|
182
|
+
super();
|
|
183
|
+
let e = this.attachShadow({ mode: "open" }), t = document.createElement("style");
|
|
184
|
+
t.textContent = O, this.root.className = "scripture-root", e.append(t, this.root);
|
|
185
|
+
}
|
|
186
|
+
connectedCallback() {
|
|
187
|
+
this.cancelTheme = v.runCallback(x(this.systemDark, "change", this.onSystemTheme).pipe(v.andThen(v.never), v.scoped)), this.root.childElementCount || this.showLoading(), this.scheduleLoad();
|
|
188
|
+
}
|
|
189
|
+
disconnectedCallback() {
|
|
190
|
+
this.cancelTheme?.(), this.cancelAnimation?.(), this.generation += 1, this.cancelLoad?.();
|
|
191
|
+
}
|
|
192
|
+
attributeChangedCallback(e, t, n) {
|
|
193
|
+
t !== n && this.isConnected && (e === "theme" ? this.applyTheme() : e === "reference" || e === "direction" ? this.relayout() : this.scheduleLoad());
|
|
194
|
+
}
|
|
195
|
+
scheduleLoad() {
|
|
196
|
+
this.generation += 1, this.cancelLoad?.(), this.cancelAnimation?.(), this.scheduled || (this.scheduled = !0, queueMicrotask(() => {
|
|
197
|
+
this.scheduled = !1, this.isConnected && (this.cancelLoad = v.runCallback(this.load(this.generation).pipe(v.catch((e) => v.sync(() => {
|
|
198
|
+
this.showError("Unable to display Bible text. Check the provider, version, and passage."), this.dispatchEvent(new CustomEvent("scripture-error", { detail: e }));
|
|
199
|
+
})), v.scoped)));
|
|
200
|
+
}));
|
|
201
|
+
}
|
|
202
|
+
applyTheme() {
|
|
203
|
+
let e = this.getAttribute("theme"), t = e === "dark" || e === "auto" && this.systemDark.matches ? "dark" : "light";
|
|
204
|
+
this.root.dataset.theme = t;
|
|
205
|
+
for (let e of this.root.querySelectorAll("[data-yv-sdk]")) e.setAttribute("data-yv-theme", t);
|
|
206
|
+
}
|
|
207
|
+
get referenceLayout() {
|
|
208
|
+
let e = this.getAttribute("reference");
|
|
209
|
+
return e && j.includes(e) ? e : "heading";
|
|
210
|
+
}
|
|
211
|
+
relayout() {
|
|
212
|
+
this.loaded && !this.getAttribute("aria-busy") && (this.root.replaceChildren(...this.compose(this.loaded.display, this.loaded.passageId)), this.applyTheme());
|
|
213
|
+
}
|
|
214
|
+
compose(e, t) {
|
|
215
|
+
let n = this.ownerDocument, r = (e, t, r, i) => {
|
|
216
|
+
let a = n.createElement(e);
|
|
217
|
+
return a.className = t, a.setAttribute("part", r), i !== void 0 && (a.textContent = i), a;
|
|
218
|
+
}, i = _(t), a = i.ok ? d(i.value) : t, o = n.createElement("section");
|
|
219
|
+
o.setAttribute("part", "text");
|
|
220
|
+
for (let [t, n] of Object.entries(e.containerAttributes ?? {})) o.setAttribute(t, n);
|
|
221
|
+
let s = this.getAttribute("direction");
|
|
222
|
+
o.setAttribute("dir", s === "ltr" || s === "rtl" ? s : e.direction ?? "auto"), o.innerHTML = e.html;
|
|
223
|
+
let c = r("p", "scripture-citation", "citation");
|
|
224
|
+
e.yvpBibleVersion && c.setAttribute("data-yv-sdk", ""), c.append(a, " ", r("span", "scripture-version", "version", e.version.abbreviation));
|
|
225
|
+
let l = r("p", "scripture-attribution", "attribution");
|
|
226
|
+
e.yvpBibleVersion && l.setAttribute("data-yv-sdk", "");
|
|
227
|
+
let u = n.createElement("bdi");
|
|
228
|
+
switch (u.setAttribute("dir", "auto"), e.attributionHtml === void 0 ? u.textContent = e.attribution : u.innerHTML = e.attributionHtml, l.append(u), this.referenceLayout) {
|
|
229
|
+
case "heading": return [
|
|
230
|
+
c,
|
|
231
|
+
o,
|
|
232
|
+
l
|
|
233
|
+
];
|
|
234
|
+
case "citation": return [
|
|
235
|
+
o,
|
|
236
|
+
c,
|
|
237
|
+
l
|
|
238
|
+
];
|
|
239
|
+
case "quote": {
|
|
240
|
+
let e = r("blockquote", "scripture-quote", "quote");
|
|
241
|
+
return e.append(o, c, l), [e];
|
|
242
|
+
}
|
|
243
|
+
case "none": return [o, l];
|
|
244
|
+
}
|
|
245
|
+
}
|
|
246
|
+
showLoading() {
|
|
247
|
+
this.setAttribute("aria-busy", "true");
|
|
248
|
+
let e = this.ownerDocument.createElement("div");
|
|
249
|
+
e.className = "scripture-loading", e.setAttribute("part", "loader"), e.setAttribute("role", "status"), e.setAttribute("aria-label", "Loading Bible text"), e.innerHTML = k, this.root.replaceChildren(e);
|
|
250
|
+
}
|
|
251
|
+
showError(e) {
|
|
252
|
+
let t = this.ownerDocument.createElement("p");
|
|
253
|
+
t.setAttribute("role", "alert"), t.setAttribute("part", "error"), t.textContent = e, this.removeAttribute("aria-busy"), this.root.replaceChildren(t);
|
|
254
|
+
}
|
|
255
|
+
load = v.fn("scripture.passage.load")(function* (e) {
|
|
256
|
+
this.loaded = null;
|
|
257
|
+
let n = this.getAttribute("passage-id")?.trim();
|
|
258
|
+
if (!n) {
|
|
259
|
+
this.showError("Set passage-id to display Bible text.");
|
|
260
|
+
return;
|
|
261
|
+
}
|
|
262
|
+
this.root.querySelector(":scope > .scripture-loading") || this.showLoading();
|
|
263
|
+
let i = !1;
|
|
264
|
+
yield* S.pipe(v.andThen(v.sync(() => {
|
|
265
|
+
i = !0;
|
|
266
|
+
})), v.forkScoped);
|
|
267
|
+
let a = yield* r({
|
|
268
|
+
...s,
|
|
269
|
+
provider: this.getAttribute("provider") || this.providerOverride || s.provider,
|
|
270
|
+
yvpPublicAppKey: this.getAttribute("yvp-public-app-key")?.trim() || s.yvpPublicAppKey,
|
|
271
|
+
yvpApiHost: this.getAttribute("yvp-api-host") || s.yvpApiHost
|
|
272
|
+
}), c = a === t(s) ? s.bibleVersionId ?? (a.id === "youversion" ? s.yvpBibleVersionId?.toString() : void 0) : void 0, l = this.getAttribute("bible-version-id") || (a.id === "youversion" ? this.getAttribute("yvp-bible-version-id") : void 0) || c || a.defaultVersionId, u = yield* o(a, l, n);
|
|
273
|
+
if (!this.isConnected || e !== this.generation || (yield* this.installStylesheets(u), !this.isConnected || e !== this.generation)) return;
|
|
274
|
+
let d = this.compose(u, n), f = this.ownerDocument.createElement("div");
|
|
275
|
+
if (f.className = "scripture-stage", f.setAttribute("aria-hidden", "true"), f.append(...d), this.root.append(f), yield* v.addFinalizer(() => v.sync(() => f.remove())), f.offsetHeight, yield* v.promise(() => this.ownerDocument.fonts.ready).pipe(v.timeoutOrElse({
|
|
276
|
+
duration: "3 seconds",
|
|
277
|
+
orElse: () => v.void
|
|
278
|
+
})), !this.isConnected || e !== this.generation) return;
|
|
279
|
+
let p = this.offsetHeight;
|
|
280
|
+
this.root.replaceChildren(...d), this.loaded = {
|
|
281
|
+
display: u,
|
|
282
|
+
passageId: n
|
|
283
|
+
}, this.applyTheme(), i && this.growFrom(p), this.removeAttribute("aria-busy"), this.dispatchEvent(new CustomEvent("scripture-load", { detail: {
|
|
284
|
+
provider: a.id,
|
|
285
|
+
bibleVersionId: l,
|
|
286
|
+
passageId: n,
|
|
287
|
+
bibleVersion: u.version,
|
|
288
|
+
...u.yvpBibleVersion ? {
|
|
289
|
+
yvpBibleVersionId: Number(l),
|
|
290
|
+
yvpBibleVersion: u.yvpBibleVersion
|
|
291
|
+
} : {}
|
|
292
|
+
} }));
|
|
293
|
+
});
|
|
294
|
+
installStylesheets(e) {
|
|
295
|
+
return v.forEach(e.stylesheets ?? [], ({ kind: e, href: t }) => v.suspend(() => {
|
|
296
|
+
let n = e === "font" ? this.ownerDocument.head : this.shadowRoot, r = n.querySelectorAll("link[rel=\"stylesheet\"]"), i = Array.from(r).find((e) => e.href === t);
|
|
297
|
+
if (!i) i = this.ownerDocument.createElement("link"), i.rel = "stylesheet", i.href = t, n.append(i);
|
|
298
|
+
else if (i.sheet || i.dataset.scriptureLoaded) return v.void;
|
|
299
|
+
let a = i;
|
|
300
|
+
return C(a, ["load", "error"]).pipe(v.tap(() => v.sync(() => {
|
|
301
|
+
a.dataset.scriptureLoaded = "";
|
|
302
|
+
})), v.timeoutOrElse({
|
|
303
|
+
duration: "5 seconds",
|
|
304
|
+
orElse: () => v.void
|
|
305
|
+
}));
|
|
306
|
+
}), {
|
|
307
|
+
concurrency: "unbounded",
|
|
308
|
+
discard: !0
|
|
309
|
+
});
|
|
310
|
+
}
|
|
311
|
+
growFrom(e) {
|
|
312
|
+
let t = this.offsetHeight, n = "cubic-bezier(0.23, 1, 0.32, 1)", r = Array.from(this.root.children), i = this;
|
|
313
|
+
this.cancelAnimation = v.runCallback(v.gen(function* () {
|
|
314
|
+
let a = yield* v.acquireRelease(v.sync(() => {
|
|
315
|
+
if (A.matches) return r.map((e) => e.animate({ opacity: [0, 1] }, {
|
|
316
|
+
duration: 200,
|
|
317
|
+
easing: n
|
|
318
|
+
}));
|
|
319
|
+
let a = [];
|
|
320
|
+
return e !== t && (i.style.overflow = "hidden", a.push(i.animate({ height: [`${e}px`, `${t}px`] }, {
|
|
321
|
+
duration: 280,
|
|
322
|
+
easing: n
|
|
323
|
+
}))), a.push(...r.map((e) => e.animate({
|
|
324
|
+
opacity: [0, 1],
|
|
325
|
+
filter: ["blur(4px)", "blur(0)"]
|
|
326
|
+
}, {
|
|
327
|
+
duration: 280,
|
|
328
|
+
easing: n
|
|
329
|
+
}))), a;
|
|
330
|
+
}), (e) => v.sync(() => {
|
|
331
|
+
for (let t of e) t.cancel();
|
|
332
|
+
i.style.overflow = "";
|
|
333
|
+
}));
|
|
334
|
+
yield* v.forEach(a, (e) => v.tryPromise(() => e.finished).pipe(v.ignore), {
|
|
335
|
+
concurrency: "unbounded",
|
|
336
|
+
discard: !0
|
|
337
|
+
});
|
|
338
|
+
}).pipe(v.scoped));
|
|
339
|
+
}
|
|
340
|
+
};
|
|
341
|
+
function N(e = {}) {
|
|
342
|
+
Object.assign(s, e), customElements.get("si-passage") || customElements.define(w, M), customElements.get("bible-sk-passage") || customElements.define(T, class extends M {});
|
|
343
|
+
}
|
|
344
|
+
// src/card.css?inline
|
|
345
|
+
var P = ":host{all:initial;--scripture-font-size:17px;--scripture-line-height:1.6;pointer-events:none;z-index:2147483000;position:fixed;inset:0}.card{--bg:#fff;--fg:#1c1917;--muted:#78716c;--border:#1c19171a;--accent:#b91c1c;--hover:#f0eeed;--yv-font-sans:ui-sans-serif, system-ui, -apple-system, \"Segoe UI\", sans-serif;box-sizing:border-box;width:min(380px,100vw - 16px);max-height:min(440px, 70vh, var(--space,100vh));pointer-events:auto;background:var(--bg);color:var(--fg);border:1px solid var(--border);font:14px/1.4 var(--yv-font-sans);--ease-out:cubic-bezier(.23, 1, .32, 1);opacity:0;transform:translateY(var(--enter-shift,4px)) scale(.97);transform-origin:var(--origin-x,50%) var(--origin-y,100%);transition:opacity .18s var(--ease-out), transform .18s var(--ease-out);border-radius:14px;outline:none;flex-direction:column;display:flex;position:absolute;box-shadow:0 1px 2px #0000000f,0 12px 32px -8px #00000038}.card[data-state=open]{opacity:1;transform:none}.card[data-state=closing]{transition-duration:.14s}@media (prefers-color-scheme:dark){.card{--bg:#1f1d1c;--fg:#f5f5f4;--muted:#a8a29e;--border:#ffffff1a;--accent:#f87171;--hover:#2c2a29}}@media (prefers-reduced-motion:reduce){.card{transition:opacity .12s linear;transform:none}}.close{all:unset;z-index:1;width:28px;height:28px;color:var(--muted);cursor:pointer;transition:background-color .15s ease, color .15s ease, transform .16s var(--ease-out);border-radius:8px;place-items:center;display:grid;position:absolute;top:12px;right:12px}@media (hover:hover) and (pointer:fine){.close:hover{background:var(--hover);color:var(--fg)}}.close:active{transform:scale(.95)}.close:focus-visible{outline:2px solid var(--accent);outline-offset:2px}.body{overscroll-behavior:contain;padding:16px;overflow-y:auto}.body>:not([reference=citation],[reference=quote],[reference=none])::part(citation){padding-inline-end:36px}.body>:is([reference=citation],[reference=none])::part(text),.body>[reference=quote]::part(quote),.body>*::part(error){margin-block-start:28px}", F = 8, I = 8;
|
|
346
|
+
function L({ reference: e, ...n }) {
|
|
347
|
+
N();
|
|
348
|
+
let r = t(n), i = n.bibleVersionId || (r.id === "youversion" && n.yvpBibleVersionId ? String(n.yvpBibleVersionId) : r.defaultVersionId), a = document.createElement("scripture-card"), o = a.attachShadow({ mode: "open" }), s = document.createElement("style");
|
|
349
|
+
s.textContent = P, o.append(s);
|
|
350
|
+
let c = null, l = null, u = !1, f, p, h = b.makeUnsafe();
|
|
351
|
+
function g() {
|
|
352
|
+
if (!c || !l) return;
|
|
353
|
+
let e = l.getBoundingClientRect();
|
|
354
|
+
c.style.removeProperty("--space");
|
|
355
|
+
let t = c.offsetWidth, n = parseFloat(getComputedStyle(c).maxHeight), r = e.top - F - I, i = innerHeight - e.bottom - F - I, a = n <= r || n > i && r > i;
|
|
356
|
+
c.style.setProperty("--space", `${Math.max(a ? r : i, 120)}px`);
|
|
357
|
+
let o = Math.min(Math.max(I, e.left + e.width / 2 - t / 2), innerWidth - I - t);
|
|
358
|
+
c.style.top = a ? "" : `${e.bottom + F}px`, c.style.bottom = a ? `${innerHeight - e.top + F}px` : "", c.style.left = `${o}px`, c.style.setProperty("--origin-x", `${e.left + e.width / 2 - o}px`), c.style.setProperty("--origin-y", a ? "100%" : "0%"), c.style.setProperty("--enter-shift", a ? "4px" : "-4px");
|
|
359
|
+
}
|
|
360
|
+
function _(e = !1) {
|
|
361
|
+
f?.();
|
|
362
|
+
let t = c;
|
|
363
|
+
if (!t) return;
|
|
364
|
+
let n = l;
|
|
365
|
+
c = null, l = null, A(), e ? t.remove() : (t.dataset.state = "closing", v.runSync(C(t, ["transitionend"]).pipe(v.timeoutOrElse({
|
|
366
|
+
duration: "250 millis",
|
|
367
|
+
orElse: () => v.void
|
|
368
|
+
}), v.ensuring(v.sync(() => t.remove())), v.forkIn(h))), n && o.activeElement && n.focus());
|
|
369
|
+
}
|
|
370
|
+
function T(t, n = !1) {
|
|
371
|
+
let s = c !== null;
|
|
372
|
+
_(s), u = n;
|
|
373
|
+
let p = t.dataset.passage, y = d(m(p));
|
|
374
|
+
a.isConnected || document.body.append(a), c = document.createElement("div"), c.className = "card", s && (c.dataset.state = "open"), c.tabIndex = -1, c.setAttribute("role", "dialog"), c.setAttribute("aria-label", y), c.innerHTML = "\n <button class=\"close\" type=\"button\" aria-label=\"Close\">\n <svg width=\"14\" height=\"14\" viewBox=\"0 0 14 14\" aria-hidden=\"true\">\n <path d=\"M3 3l8 8M11 3l-8 8\" stroke=\"currentColor\" stroke-width=\"1.6\" stroke-linecap=\"round\" />\n </svg>\n </button>\n <div class=\"body\" aria-live=\"polite\"></div>";
|
|
375
|
+
let b = document.createElement(w);
|
|
376
|
+
if (b.bibleProvider = r, b.setAttribute("bible-version-id", i), b.setAttribute("passage-id", p), b.setAttribute("theme", "auto"), b.setAttribute("reference", e), b.addEventListener("scripture-error", (e) => console.error("[scripture-inline]", e.detail)), c.querySelector(".body").append(b), c.querySelector(".close").addEventListener("click", () => _()), c.addEventListener("pointerenter", () => f?.()), c.addEventListener("pointerleave", M), o.append(c), l = t, g(), k(), n || c.focus({ preventScroll: !0 }), !s) {
|
|
377
|
+
c.getBoundingClientRect();
|
|
378
|
+
let e = c;
|
|
379
|
+
v.runSync(S.pipe(v.andThen(v.sync(() => {
|
|
380
|
+
c === e && (e.dataset.state = "open");
|
|
381
|
+
})), v.forkIn(h)));
|
|
382
|
+
}
|
|
383
|
+
}
|
|
384
|
+
let E = (e) => e.key === "Escape" && _(), D = (e) => {
|
|
385
|
+
let t = e.composedPath();
|
|
386
|
+
c && !t.includes(c) && !(l && t.includes(l)) && _();
|
|
387
|
+
}, O = () => v.runSync(S.pipe(v.andThen(v.sync(g)), v.forkIn(h)));
|
|
388
|
+
function k() {
|
|
389
|
+
p = v.runCallback(v.gen(function* () {
|
|
390
|
+
yield* x(document, "keydown", E), yield* x(document, "pointerdown", D, !0), yield* x(window, "scroll", O, {
|
|
391
|
+
capture: !0,
|
|
392
|
+
passive: !0
|
|
393
|
+
}), yield* x(window, "resize", O, { passive: !0 }), yield* v.never;
|
|
394
|
+
}).pipe(v.scoped));
|
|
395
|
+
}
|
|
396
|
+
function A() {
|
|
397
|
+
p?.();
|
|
398
|
+
}
|
|
399
|
+
function j(e) {
|
|
400
|
+
f?.(), l !== e && (!c || u) && (f = v.runCallback(v.sleep(c ? 150 : 350).pipe(v.andThen(v.sync(() => T(e, !0))), v.withSpan("scripture.card.hover"))));
|
|
401
|
+
}
|
|
402
|
+
function M(e) {
|
|
403
|
+
e && e.pointerType !== "mouse" || (f?.(), c && u && (f = v.runCallback(v.sleep(250).pipe(v.andThen(v.sync(() => _())), v.withSpan("scripture.card.unhover")))));
|
|
404
|
+
}
|
|
405
|
+
return {
|
|
406
|
+
toggle(e) {
|
|
407
|
+
l === e && u ? (f?.(), u = !1, c.focus({ preventScroll: !0 })) : l === e ? _() : T(e);
|
|
408
|
+
},
|
|
409
|
+
hover: j,
|
|
410
|
+
unhover: M,
|
|
411
|
+
close: _,
|
|
412
|
+
closeIfDetached() {
|
|
413
|
+
l && !l.isConnected && _(!0);
|
|
414
|
+
},
|
|
415
|
+
destroy() {
|
|
416
|
+
_(!0), v.runSync(b.close(h, y.void)), a.remove();
|
|
417
|
+
}
|
|
418
|
+
};
|
|
419
|
+
}
|
|
420
|
+
// src/find.ts
|
|
421
|
+
var ee = /(?<![\w:.])(?:[1-3]\s?)?[A-Za-z]{2,}\.?(?:\s+of\s+[A-Za-z]+)?\s+\d{1,3}(?:[:.]\d{1,3})?(?:\s?[-\u2010-\u2015]\s?\d{1,3}(?:[:.]\d{1,3})?)?(?![\w:])/g;
|
|
422
|
+
function R(e) {
|
|
423
|
+
let t = [], n = new RegExp(ee), r;
|
|
424
|
+
for (; r = n.exec(e);) {
|
|
425
|
+
let e = _(r[0]);
|
|
426
|
+
e.ok ? t.push({
|
|
427
|
+
start: r.index,
|
|
428
|
+
end: r.index + r[0].length,
|
|
429
|
+
text: r[0],
|
|
430
|
+
passage: e.value
|
|
431
|
+
}) : n.lastIndex = r.index + 1;
|
|
432
|
+
}
|
|
433
|
+
return t;
|
|
434
|
+
}
|
|
435
|
+
// src/scan.ts
|
|
436
|
+
var z = "scripture-inline-ref", B = "a,button,script,style,noscript,template,textarea,input,select,option,code,pre,kbd,samp,svg,math,[contenteditable],si-passage,si-passage-input,bible-sk-passage,bible-sk-passage-input,[data-scripture-inline-ignore]";
|
|
437
|
+
function V(e) {
|
|
438
|
+
let t = e.ownerDocument ?? e, n = t.createTreeWalker(e, NodeFilter.SHOW_TEXT, { acceptNode: (e) => e.parentElement && !e.parentElement.closest(B) && /\d/.test(e.nodeValue ?? "") ? NodeFilter.FILTER_ACCEPT : NodeFilter.FILTER_REJECT }), r = [];
|
|
439
|
+
for (; n.nextNode();) r.push(n.currentNode);
|
|
440
|
+
let i = [];
|
|
441
|
+
for (let e of r) {
|
|
442
|
+
let n = e.nodeValue ?? "", r = R(n);
|
|
443
|
+
if (r.length === 0) continue;
|
|
444
|
+
let a = t.createDocumentFragment(), o = 0;
|
|
445
|
+
for (let e of r) {
|
|
446
|
+
a.append(n.slice(o, e.start));
|
|
447
|
+
let r = t.createElement("a");
|
|
448
|
+
r.className = z, r.href = h("https://route.bible", e.passage.canonical), r.target = "_blank", r.rel = "noopener", r.dataset.passage = e.passage.canonical, r.textContent = e.text, a.append(r), i.push(r), o = e.end;
|
|
449
|
+
}
|
|
450
|
+
a.append(n.slice(o)), e.replaceWith(a);
|
|
451
|
+
}
|
|
452
|
+
return i;
|
|
453
|
+
}
|
|
454
|
+
function H(e) {
|
|
455
|
+
for (let t of e) {
|
|
456
|
+
let e = t.parentNode;
|
|
457
|
+
e && (t.replaceWith(t.textContent ?? ""), e.normalize());
|
|
458
|
+
}
|
|
459
|
+
}
|
|
460
|
+
// src/passage-input.ts
|
|
461
|
+
var U = "si-passage-input", W = "bible-sk-passage-input", te = "\n:host { display: block; position: relative; }\n.root { all: initial; display: block; position: relative; color: inherit; font: 0.875rem/1.5 var(--font-sans, system-ui, sans-serif); }\ninput {\n box-sizing: border-box;\n width: 100%;\n height: 2.25rem;\n margin: 0;\n padding: 0.25rem 0.75rem;\n font: inherit;\n color: inherit;\n background: none;\n border: 1px solid var(--input, color-mix(in srgb, currentColor 20%, transparent));\n border-radius: calc(var(--radius, 0.625rem) - 2px);\n box-shadow: 0 1px 2px #0000000d;\n outline: none;\n transition: color 0.15s, box-shadow 0.15s;\n}\n/* iOS Safari zooms the page into a focused field whose text is under 16px. */\n@media (pointer: coarse) { input { font-size: 16px; } }\ninput:focus-visible {\n border-color: var(--ring, Highlight);\n box-shadow: 0 0 0 3px color-mix(in oklab, var(--ring, Highlight) 50%, transparent);\n}\ninput[aria-invalid=\"true\"] { border-color: var(--destructive, #dc2626); }\ninput:disabled { cursor: not-allowed; opacity: 0.5; }\n[role=\"listbox\"] {\n position: absolute;\n inset: calc(100% + 4px) 0 auto;\n z-index: 50;\n box-sizing: border-box;\n max-height: 16rem;\n margin: 0;\n padding: 4px;\n overflow-y: auto;\n list-style: none;\n color: var(--popover-foreground, inherit);\n background: var(--popover, Canvas);\n border: 1px solid var(--border, color-mix(in srgb, currentColor 15%, transparent));\n border-radius: var(--radius, 0.625rem);\n box-shadow: 0 8px 24px -8px rgb(0 0 0 / 0.2);\n}\n[role=\"listbox\"][hidden] { display: none; }\n[role=\"option\"] > .si-passage-count {\n /* The label wraps before the count does. */\n flex-shrink: 0;\n white-space: nowrap;\n margin-inline-start: auto;\n font-size: 0.75rem;\n color: var(--muted-foreground, color-mix(in srgb, currentColor 60%, transparent));\n}\n[role=\"option\"] {\n /* Baseline alignment keeps the smaller count on the label's line. */\n display: flex;\n align-items: baseline;\n gap: 1rem;\n padding: 0.375rem 0.5rem;\n border-radius: calc(var(--radius, 0.625rem) - 4px);\n cursor: default;\n}\n[role=\"option\"][aria-selected=\"true\"] {\n color: var(--accent-foreground, inherit);\n background: var(--accent, color-mix(in srgb, currentColor 10%, transparent));\n}\n[role=\"option\"][aria-disabled=\"true\"] {\n color: var(--muted-foreground, color-mix(in srgb, currentColor 60%, transparent));\n}\n@media (hover: hover) and (pointer: fine) {\n [role=\"option\"]:not([aria-disabled]):hover {\n background: var(--accent, color-mix(in srgb, currentColor 10%, transparent));\n }\n}", ne = 0, G = (e, t) => `${e} ${t}${e === 1 ? "" : "s"}`, re = [...c].sort((e, t) => l[e].localeCompare(l[t], void 0, { numeric: !0 }));
|
|
462
|
+
function K(e) {
|
|
463
|
+
return (e === "alphabetical" ? re : c).map((e) => ({
|
|
464
|
+
kind: "book",
|
|
465
|
+
canonical: e,
|
|
466
|
+
label: l[e],
|
|
467
|
+
insertText: l[e]
|
|
468
|
+
}));
|
|
469
|
+
}
|
|
470
|
+
function q(e) {
|
|
471
|
+
return /^\s*(\d\s*)?[^\d:;,\-–—]+$/.test(e) ? g(e) : null;
|
|
472
|
+
}
|
|
473
|
+
function ie(e, t, n) {
|
|
474
|
+
let r = p(e, t) ?? 0;
|
|
475
|
+
return Array.from({ length: Math.max(r - n, 0) }, (r, i) => {
|
|
476
|
+
let a = `${l[e]} ${t}:${n}-${n + i + 1}`;
|
|
477
|
+
return {
|
|
478
|
+
kind: "range",
|
|
479
|
+
canonical: `${e}.${t}.${n}-${n + i + 1}`,
|
|
480
|
+
label: a,
|
|
481
|
+
insertText: a
|
|
482
|
+
};
|
|
483
|
+
});
|
|
484
|
+
}
|
|
485
|
+
var ae = (e) => e.replace(/^(\d) /, "$1\xA0").replace(/ (?=[\d:-]+$)/, "\xA0");
|
|
486
|
+
function oe(e, t) {
|
|
487
|
+
return Array.from({ length: p(e, t) ?? 0 }, (n, r) => {
|
|
488
|
+
let i = `${l[e]} ${t}:${r + 1}`;
|
|
489
|
+
return {
|
|
490
|
+
kind: "verse",
|
|
491
|
+
canonical: `${e}.${t}.${r + 1}`,
|
|
492
|
+
label: i,
|
|
493
|
+
insertText: i
|
|
494
|
+
};
|
|
495
|
+
});
|
|
496
|
+
}
|
|
497
|
+
function J(e) {
|
|
498
|
+
return Array.from({ length: f(e) }, (t, n) => {
|
|
499
|
+
let r = `${l[e]} ${n + 1}`;
|
|
500
|
+
return {
|
|
501
|
+
kind: "chapter",
|
|
502
|
+
canonical: `${e}.${n + 1}`,
|
|
503
|
+
label: r,
|
|
504
|
+
insertText: r
|
|
505
|
+
};
|
|
506
|
+
});
|
|
507
|
+
}
|
|
508
|
+
function se({ kind: e, canonical: t }) {
|
|
509
|
+
let [n, r] = t.split(".");
|
|
510
|
+
if (e === "book") return G(f(n), "chapter");
|
|
511
|
+
if (e === "chapter") {
|
|
512
|
+
let e = p(n, Number(r));
|
|
513
|
+
return e ? G(e, "verse") : "";
|
|
514
|
+
}
|
|
515
|
+
return "";
|
|
516
|
+
}
|
|
517
|
+
var Y = class extends HTMLElement {
|
|
518
|
+
static formAssociated = !0;
|
|
519
|
+
static observedAttributes = [
|
|
520
|
+
"value",
|
|
521
|
+
"placeholder",
|
|
522
|
+
"disabled",
|
|
523
|
+
"book-order"
|
|
524
|
+
];
|
|
525
|
+
internals = this.attachInternals();
|
|
526
|
+
input = document.createElement("input");
|
|
527
|
+
list = document.createElement("ul");
|
|
528
|
+
suggestions = [];
|
|
529
|
+
active = -1;
|
|
530
|
+
committed = "";
|
|
531
|
+
constructor() {
|
|
532
|
+
super();
|
|
533
|
+
let e = document.createElement("div");
|
|
534
|
+
e.className = "root";
|
|
535
|
+
let t = document.createElement("style");
|
|
536
|
+
t.textContent = te, e.append(this.input, this.list), this.attachShadow({ mode: "open" }).append(t, e), this.input.setAttribute("part", "input"), this.list.setAttribute("part", "listbox");
|
|
537
|
+
let n = `${U}-${++ne}`;
|
|
538
|
+
Object.assign(this.input, {
|
|
539
|
+
type: "text",
|
|
540
|
+
autocomplete: "off",
|
|
541
|
+
spellcheck: !1
|
|
542
|
+
}), this.input.setAttribute("role", "combobox"), this.input.setAttribute("aria-autocomplete", "list"), this.input.setAttribute("aria-expanded", "false"), this.input.setAttribute("aria-controls", `${n}-list`), this.list.id = `${n}-list`, this.list.setAttribute("role", "listbox"), this.list.hidden = !0, this.input.addEventListener("input", () => {
|
|
543
|
+
this.input.removeAttribute("aria-invalid"), this.internals.setValidity({}), this.suggest();
|
|
544
|
+
}), this.input.addEventListener("keydown", (e) => this.onKeydown(e)), this.input.addEventListener("focus", () => this.suggest()), this.input.addEventListener("click", () => this.list.hidden && this.suggest()), this.input.addEventListener("change", (e) => e.stopPropagation()), this.input.addEventListener("blur", () => {
|
|
545
|
+
this.close(), this.commit(this.input.value);
|
|
546
|
+
}), this.list.addEventListener("pointerdown", (e) => e.preventDefault());
|
|
547
|
+
let r = (e) => {
|
|
548
|
+
let t = e.target.closest("[role=option]:not([aria-disabled])");
|
|
549
|
+
t && this.accept(this.suggestions[Number(t.dataset.index)]);
|
|
550
|
+
};
|
|
551
|
+
this.list.addEventListener("click", r);
|
|
552
|
+
let i;
|
|
553
|
+
this.list.addEventListener("touchstart", (e) => i = e.touches[0], { passive: !0 }), this.list.addEventListener("touchend", (e) => {
|
|
554
|
+
let t = e.changedTouches[0];
|
|
555
|
+
!i || !t || Math.hypot(t.clientX - i.clientX, t.clientY - i.clientY) > 10 || (e.preventDefault(), r(e));
|
|
556
|
+
}), this.addEventListener("click", (e) => e.composedPath()[0] === this && this.input.focus());
|
|
557
|
+
}
|
|
558
|
+
connectedCallback() {
|
|
559
|
+
let e = this.getAttribute("aria-label") ?? [...this.internals.labels].map((e) => e.textContent?.trim()).join(" ");
|
|
560
|
+
e && this.input.setAttribute("aria-label", e);
|
|
561
|
+
}
|
|
562
|
+
attributeChangedCallback(e, t, n) {
|
|
563
|
+
e === "value" ? this.commit(n ?? "", !1) : e === "placeholder" ? this.input.placeholder = n ?? "" : e === "disabled" ? this.input.disabled = n !== null : this.list.hidden || this.suggest();
|
|
564
|
+
}
|
|
565
|
+
get value() {
|
|
566
|
+
return this.committed;
|
|
567
|
+
}
|
|
568
|
+
set value(e) {
|
|
569
|
+
this.commit(e, !1);
|
|
570
|
+
}
|
|
571
|
+
get form() {
|
|
572
|
+
return this.internals.form;
|
|
573
|
+
}
|
|
574
|
+
get validity() {
|
|
575
|
+
return this.internals.validity;
|
|
576
|
+
}
|
|
577
|
+
get validationMessage() {
|
|
578
|
+
return this.internals.validationMessage;
|
|
579
|
+
}
|
|
580
|
+
checkValidity() {
|
|
581
|
+
return this.internals.checkValidity();
|
|
582
|
+
}
|
|
583
|
+
reportValidity() {
|
|
584
|
+
return this.internals.reportValidity();
|
|
585
|
+
}
|
|
586
|
+
focus(e) {
|
|
587
|
+
this.input.focus(e);
|
|
588
|
+
}
|
|
589
|
+
formResetCallback() {
|
|
590
|
+
this.commit(this.getAttribute("value") ?? "", !1);
|
|
591
|
+
}
|
|
592
|
+
formDisabledCallback(e) {
|
|
593
|
+
this.input.disabled = e;
|
|
594
|
+
}
|
|
595
|
+
commit(e, t = !0) {
|
|
596
|
+
let n = e.trim(), r = n ? _(n) : null, i = r?.ok && (r.value.start.book !== r.value.end.book || r.value.start.chapter !== r.value.end.chapter);
|
|
597
|
+
if (r && !r.ok || i) {
|
|
598
|
+
let t = i ? "Choose verses within one chapter." : "Enter a Bible passage, such as Romans 8.";
|
|
599
|
+
this.input.value = e, this.input.setAttribute("aria-invalid", "true"), this.internals.setValidity({ customError: !0 }, t, this.input);
|
|
600
|
+
return;
|
|
601
|
+
}
|
|
602
|
+
this.input.removeAttribute("aria-invalid"), this.internals.setValidity({});
|
|
603
|
+
let a = r?.value.canonical ?? "", o = r ? d(r.value) : "";
|
|
604
|
+
this.input.value = o, a !== this.committed && (this.committed = a, this.internals.setFormValue(a || null), t && this.dispatchEvent(new CustomEvent("change", {
|
|
605
|
+
bubbles: !0,
|
|
606
|
+
detail: {
|
|
607
|
+
passageId: a,
|
|
608
|
+
label: o
|
|
609
|
+
}
|
|
610
|
+
})));
|
|
611
|
+
}
|
|
612
|
+
get bookOrder() {
|
|
613
|
+
return this.getAttribute("book-order") === "alphabetical" ? "alphabetical" : "canonical";
|
|
614
|
+
}
|
|
615
|
+
options(e) {
|
|
616
|
+
if (!e) return K(this.bookOrder);
|
|
617
|
+
let t = /^(.+?)\s*(\d+)\s*:\s*(\d+)\s*[-–—]\s*(\d*)$/.exec(e), n = t && q(t[1]);
|
|
618
|
+
if (n) {
|
|
619
|
+
let e = t[4];
|
|
620
|
+
return ie(n, Number(t[2]), Number(t[3])).filter((t) => t.canonical.split("-")[1].startsWith(e));
|
|
621
|
+
}
|
|
622
|
+
let r = /^(.+?)\s*(\d+)\s*:\s*(\d*)$/.exec(e), i = r && q(r[1]);
|
|
623
|
+
if (i) return oe(i, Number(r[2])).filter((e) => e.canonical.split(".")[2].startsWith(r[3]));
|
|
624
|
+
let a = /^(.+?)\s*(\d+)$/.exec(e), o = a && q(a[1]);
|
|
625
|
+
if (o) return J(o).filter((e) => e.canonical.split(".")[1].startsWith(a[2]));
|
|
626
|
+
let s = u(e, { limit: 200 }).filter((e) => e.kind === "book"), c = K(this.bookOrder).map((e) => e.canonical);
|
|
627
|
+
s.sort((e, t) => c.indexOf(e.canonical) - c.indexOf(t.canonical));
|
|
628
|
+
let l = q(e), f = s.find((t) => t.insertText.toLowerCase() === e.toLowerCase());
|
|
629
|
+
if (l && (f || !s.length)) return J(l);
|
|
630
|
+
if (s.length) return s;
|
|
631
|
+
let p = _(e);
|
|
632
|
+
if (!p.ok) return [];
|
|
633
|
+
let { start: m, end: h, canonical: g, rangeType: v } = p.value;
|
|
634
|
+
if (m.book !== h.book || m.chapter !== h.chapter) return [];
|
|
635
|
+
let y = d(p.value);
|
|
636
|
+
return [{
|
|
637
|
+
kind: v === "chapter" ? "chapter" : v === "single" ? "verse" : "range",
|
|
638
|
+
canonical: g,
|
|
639
|
+
label: y,
|
|
640
|
+
insertText: y
|
|
641
|
+
}];
|
|
642
|
+
}
|
|
643
|
+
suggest() {
|
|
644
|
+
if (this.suggestions = this.options(this.input.value.trim()), this.active = -1, this.list.replaceChildren(...this.suggestions.map((e, t) => {
|
|
645
|
+
let n = document.createElement("li");
|
|
646
|
+
n.id = `${this.list.id}-${t}`, n.dataset.index = String(t), n.setAttribute("role", "option"), n.setAttribute("part", "option"), n.setAttribute("aria-selected", "false"), n.textContent = ae(e.label);
|
|
647
|
+
let r = se(e);
|
|
648
|
+
if (r) {
|
|
649
|
+
let e = document.createElement("span");
|
|
650
|
+
e.className = "si-passage-count", e.setAttribute("part", "count"), e.textContent = r, n.append(e);
|
|
651
|
+
}
|
|
652
|
+
return n;
|
|
653
|
+
})), !this.suggestions.length && this.input.value.trim()) {
|
|
654
|
+
let e = document.createElement("li");
|
|
655
|
+
e.setAttribute("role", "option"), e.setAttribute("part", "option"), e.setAttribute("aria-disabled", "true"), e.textContent = "No passage matches", this.list.append(e);
|
|
656
|
+
}
|
|
657
|
+
this.list.hidden = !this.list.childElementCount, this.input.setAttribute("aria-expanded", String(!this.list.hidden)), this.input.removeAttribute("aria-activedescendant");
|
|
658
|
+
}
|
|
659
|
+
highlight(e) {
|
|
660
|
+
this.active = e;
|
|
661
|
+
for (let t of this.list.children) t.setAttribute("aria-selected", String(t.id === `${this.list.id}-${e}`));
|
|
662
|
+
let t = this.list.children[e];
|
|
663
|
+
t ? (this.input.setAttribute("aria-activedescendant", t.id), t.scrollIntoView({ block: "nearest" })) : this.input.removeAttribute("aria-activedescendant");
|
|
664
|
+
}
|
|
665
|
+
close() {
|
|
666
|
+
this.list.hidden = !0, this.input.setAttribute("aria-expanded", "false"), this.input.removeAttribute("aria-activedescendant"), this.active = -1;
|
|
667
|
+
}
|
|
668
|
+
accept(e) {
|
|
669
|
+
e.kind === "book" ? (this.input.value = `${e.insertText} `, this.suggest()) : (this.close(), this.commit(e.insertText));
|
|
670
|
+
}
|
|
671
|
+
onKeydown(e) {
|
|
672
|
+
let t = !this.list.hidden, n = this.suggestions.length;
|
|
673
|
+
switch (e.key) {
|
|
674
|
+
case "ArrowDown":
|
|
675
|
+
case "ArrowUp": {
|
|
676
|
+
if (e.preventDefault(), !t) return this.suggest();
|
|
677
|
+
let r = this.active + (e.key === "ArrowDown" ? 1 : -1);
|
|
678
|
+
this.highlight(r >= n ? -1 : r < -1 ? n - 1 : r);
|
|
679
|
+
return;
|
|
680
|
+
}
|
|
681
|
+
case "Enter": {
|
|
682
|
+
let r = _(this.input.value.trim());
|
|
683
|
+
return t && e.preventDefault(), !this.input.value.trim() && this.active < 0 ? (this.close(), this.commit("")) : this.active >= 0 ? this.accept(this.suggestions[this.active]) : r.ok || !n ? (this.close(), this.commit(this.input.value)) : this.accept(this.suggestions[0]);
|
|
684
|
+
}
|
|
685
|
+
case "Tab":
|
|
686
|
+
if (n && !e.shiftKey && this.input.value.trim()) {
|
|
687
|
+
let t = this.suggestions[Math.max(this.active, 0)];
|
|
688
|
+
t.kind === "book" && `${t.insertText} ` !== this.input.value && (e.preventDefault(), this.accept(t));
|
|
689
|
+
}
|
|
690
|
+
return;
|
|
691
|
+
case "Escape":
|
|
692
|
+
t ? (e.preventDefault(), this.close()) : this.commit(this.committed, !1);
|
|
693
|
+
return;
|
|
694
|
+
}
|
|
695
|
+
}
|
|
696
|
+
};
|
|
697
|
+
function ce() {
|
|
698
|
+
customElements.get("si-passage-input") || customElements.define(U, Y), customElements.get("bible-sk-passage-input") || customElements.define(W, class extends Y {});
|
|
699
|
+
}
|
|
700
|
+
// src/version-input.ts
|
|
701
|
+
var X = "si-version-input", Z = "bible-sk-version-input", le = "\n:host { display: block; position: relative; min-width: 0; }\n.root { all: initial; display: grid; gap: 0.375rem; color: inherit; font: 0.875rem/1.5 var(--font-sans, system-ui, sans-serif); }\ninput, select, button { box-sizing: border-box; font: inherit; color: inherit; }\ninput, select {\n width: 100%; min-width: 0; height: 2.25rem; margin: 0; padding: 0.25rem 0.75rem;\n background: none; border: 1px solid var(--input, color-mix(in srgb, currentColor 20%, transparent));\n border-radius: calc(var(--radius, 0.625rem) - 2px); outline: none; box-shadow: 0 1px 2px #0000000d;\n transition: color 0.15s, box-shadow 0.15s;\n}\ninput:focus-visible, select:focus-visible {\n border-color: var(--ring, Highlight);\n box-shadow: 0 0 0 3px color-mix(in oklab, var(--ring, Highlight) 50%, transparent);\n}\nbutton:focus-visible { outline: 2px solid var(--ring, Highlight); outline-offset: 2px; }\ninput:disabled, select:disabled { opacity: 0.5; cursor: not-allowed; }\ninput[aria-invalid=\"true\"] { border-color: var(--destructive, #dc2626); }\n.language { position: relative; }\n.language select { appearance: none; padding-inline-end: 2.5rem; }\n.language svg { position: absolute; inset-inline-end: 0.75rem; top: 50%; transform: translateY(-50%); pointer-events: none; }\n.language select:disabled + svg { opacity: 0.5; }\n.search { position: relative; }\n[role=\"listbox\"] {\n position: absolute; inset: calc(100% + 4px) 0 auto; z-index: 50; box-sizing: border-box;\n max-height: 16rem; margin: 0; padding: 4px; overflow-y: auto; list-style: none;\n color: var(--popover-foreground, inherit); background: var(--popover, Canvas);\n border: 1px solid var(--border, color-mix(in srgb, currentColor 15%, transparent));\n border-radius: var(--radius, 0.625rem); box-shadow: 0 8px 24px -8px #0003;\n}\n[hidden] { display: none !important; }\n[role=\"option\"] { padding: 0.5rem; border-radius: calc(var(--radius, 0.625rem) - 4px); overflow-wrap: anywhere; cursor: default; }\n[role=\"option\"][aria-selected=\"true\"] { color: var(--accent-foreground, inherit); background: var(--accent, color-mix(in srgb, currentColor 10%, transparent)); }\n.language-name { display: block; font-size: 0.75rem; opacity: 0.7; }\n.feedback { display: flex; align-items: center; gap: 0.5rem; min-height: 1.5rem; font-size: 0.75rem; }\n[role=\"status\"] { display: flex; align-items: center; gap: 0.375rem; }\nsvg { flex: none; }\n[role=\"status\"] svg { animation: spin 0.8s linear infinite; }\nbutton { border: 0; padding: 0; background: none; text-decoration: underline; cursor: pointer; }\n@keyframes spin { to { transform: rotate(360deg); } }\n@media (pointer: coarse) { input, select { font-size: 16px; } }\n@media (prefers-reduced-motion: reduce) { [role=\"status\"] svg { animation-duration: 2.4s; } }\n@media (hover: hover) and (pointer: fine) { [role=\"option\"]:hover { background: var(--accent, color-mix(in srgb, currentColor 10%, transparent)); } }\n", ue = 0, Q = (e) => `${e.title} (${e.abbreviation})`, $ = class extends HTMLElement {
|
|
702
|
+
static formAssociated = !0;
|
|
703
|
+
static observedAttributes = [
|
|
704
|
+
"value",
|
|
705
|
+
"language",
|
|
706
|
+
"provider",
|
|
707
|
+
"yvp-public-app-key",
|
|
708
|
+
"yvp-api-host",
|
|
709
|
+
"placeholder",
|
|
710
|
+
"disabled"
|
|
711
|
+
];
|
|
712
|
+
internals = this.attachInternals();
|
|
713
|
+
input = document.createElement("input");
|
|
714
|
+
language = document.createElement("select");
|
|
715
|
+
list = document.createElement("ul");
|
|
716
|
+
status = document.createElement("span");
|
|
717
|
+
retry = document.createElement("button");
|
|
718
|
+
versions = [];
|
|
719
|
+
filtered = [];
|
|
720
|
+
selected;
|
|
721
|
+
pendingValue;
|
|
722
|
+
provider;
|
|
723
|
+
override;
|
|
724
|
+
active = -1;
|
|
725
|
+
generation = 0;
|
|
726
|
+
scheduled = !1;
|
|
727
|
+
cancelLoad;
|
|
728
|
+
loading = !1;
|
|
729
|
+
failed = !1;
|
|
730
|
+
formDisabled = !1;
|
|
731
|
+
constructor() {
|
|
732
|
+
super();
|
|
733
|
+
let e = document.createElement("style");
|
|
734
|
+
e.textContent = le;
|
|
735
|
+
let t = document.createElement("div");
|
|
736
|
+
t.className = "root";
|
|
737
|
+
let n = document.createElement("div");
|
|
738
|
+
n.className = "language", n.append(this.language), n.insertAdjacentHTML("beforeend", "<svg width=\"16\" height=\"16\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><path d=\"m6 9 6 6 6-6\"/></svg>");
|
|
739
|
+
let r = document.createElement("div");
|
|
740
|
+
r.className = "search", r.append(this.input, this.list);
|
|
741
|
+
let i = document.createElement("div");
|
|
742
|
+
i.className = "feedback", i.append(this.status, this.retry), t.append(n, r, i), this.attachShadow({ mode: "open" }).append(e, t), this.input.type = "text", this.input.autocomplete = "off", this.input.spellcheck = !1, this.input.placeholder = "Search translations", this.input.setAttribute("part", "input"), this.input.setAttribute("role", "combobox"), this.input.setAttribute("aria-autocomplete", "list"), this.input.setAttribute("aria-expanded", "false"), this.list.id = `${X}-${++ue}`, this.list.setAttribute("part", "listbox"), this.list.setAttribute("role", "listbox"), this.list.setAttribute("aria-label", "Bible translations"), this.list.hidden = !0, this.input.setAttribute("aria-controls", this.list.id), this.language.setAttribute("part", "language"), this.language.setAttribute("aria-label", "Translation language"), this.status.setAttribute("role", "status"), this.status.setAttribute("part", "status"), this.retry.type = "button", this.retry.textContent = "Retry", this.retry.setAttribute("part", "retry"), this.retry.hidden = !0, this.retry.addEventListener("click", () => this.scheduleLoad()), this.input.addEventListener("input", () => this.suggest()), this.input.addEventListener("focus", () => {
|
|
743
|
+
this.input.select(), this.suggest();
|
|
744
|
+
}), this.input.addEventListener("click", () => this.list.hidden && this.suggest()), this.input.addEventListener("change", (e) => e.stopPropagation()), this.input.addEventListener("blur", () => {
|
|
745
|
+
this.input.value = this.selected ? Q(this.selected) : "", this.close();
|
|
746
|
+
}), this.language.addEventListener("change", (e) => {
|
|
747
|
+
e.stopPropagation(), this.input.focus(), this.suggest();
|
|
748
|
+
}), this.input.addEventListener("keydown", (e) => {
|
|
749
|
+
e.key === "Escape" ? (this.close(), this.input.value = this.selected ? Q(this.selected) : "") : e.key === "ArrowDown" || e.key === "ArrowUp" ? (e.preventDefault(), this.list.hidden ? this.suggest() : this.highlight(Math.max(0, Math.min(this.filtered.length - 1, this.active + (e.key === "ArrowDown" ? 1 : -1))))) : e.key === "Enter" && !this.list.hidden && (e.preventDefault(), this.filtered[this.active] && this.commit(this.filtered[this.active].id, !0));
|
|
750
|
+
}), this.list.addEventListener("pointerdown", (e) => e.preventDefault());
|
|
751
|
+
let a = (e) => {
|
|
752
|
+
let t = e.target.closest("[role=option]");
|
|
753
|
+
t && this.commit(this.filtered[Number(t.dataset.index)].id, !0);
|
|
754
|
+
};
|
|
755
|
+
this.list.addEventListener("click", a);
|
|
756
|
+
let o;
|
|
757
|
+
this.list.addEventListener("touchstart", (e) => {
|
|
758
|
+
o = e.touches[0];
|
|
759
|
+
}, { passive: !0 }), this.list.addEventListener("touchend", (e) => {
|
|
760
|
+
let t = e.changedTouches[0];
|
|
761
|
+
!o || !t || Math.hypot(t.clientX - o.clientX, t.clientY - o.clientY) > 10 || (e.preventDefault(), a(e));
|
|
762
|
+
}), this.addEventListener("click", (e) => e.composedPath()[0] === this && this.input.focus());
|
|
763
|
+
}
|
|
764
|
+
connectedCallback() {
|
|
765
|
+
this.input.setAttribute("aria-label", this.getAttribute("aria-label") || [...this.internals.labels].map((e) => e.textContent?.trim()).join(" ") || "Bible translation"), this.scheduleLoad();
|
|
766
|
+
}
|
|
767
|
+
disconnectedCallback() {
|
|
768
|
+
this.generation++, this.cancelLoad?.(), this.close();
|
|
769
|
+
}
|
|
770
|
+
attributeChangedCallback(e, t, n) {
|
|
771
|
+
t !== n && (e === "value" ? (this.pendingValue = n ?? "", this.loading || this.commit(this.pendingValue, !1)) : e === "placeholder" ? this.input.placeholder = n ?? "Search translations" : e === "disabled" ? this.updateDisabled() : e === "language" ? (this.language.value = n ?? "all", this.close()) : this.isConnected && this.scheduleLoad());
|
|
772
|
+
}
|
|
773
|
+
get value() {
|
|
774
|
+
return this.selected?.id ?? "";
|
|
775
|
+
}
|
|
776
|
+
set value(e) {
|
|
777
|
+
this.pendingValue = e, this.loading || this.commit(e, !1);
|
|
778
|
+
}
|
|
779
|
+
get bibleProvider() {
|
|
780
|
+
return this.override;
|
|
781
|
+
}
|
|
782
|
+
set bibleProvider(e) {
|
|
783
|
+
this.override = e, this.isConnected && this.scheduleLoad();
|
|
784
|
+
}
|
|
785
|
+
get form() {
|
|
786
|
+
return this.internals.form;
|
|
787
|
+
}
|
|
788
|
+
get validity() {
|
|
789
|
+
return this.internals.validity;
|
|
790
|
+
}
|
|
791
|
+
get validationMessage() {
|
|
792
|
+
return this.internals.validationMessage;
|
|
793
|
+
}
|
|
794
|
+
checkValidity() {
|
|
795
|
+
return this.internals.checkValidity();
|
|
796
|
+
}
|
|
797
|
+
reportValidity() {
|
|
798
|
+
return this.internals.reportValidity();
|
|
799
|
+
}
|
|
800
|
+
focus(e) {
|
|
801
|
+
this.input.focus(e);
|
|
802
|
+
}
|
|
803
|
+
formResetCallback() {
|
|
804
|
+
this.value = this.defaultValue(this.provider ?? t(s));
|
|
805
|
+
}
|
|
806
|
+
formDisabledCallback(e) {
|
|
807
|
+
this.formDisabled = e, this.updateDisabled();
|
|
808
|
+
}
|
|
809
|
+
defaultValue(e) {
|
|
810
|
+
let n = e === t(s) ? s.bibleVersionId ?? (e.id === "youversion" ? s.yvpBibleVersionId?.toString() : void 0) : void 0;
|
|
811
|
+
return this.getAttribute("value") ?? n ?? e.defaultVersionId;
|
|
812
|
+
}
|
|
813
|
+
updateDisabled() {
|
|
814
|
+
let e = this.loading || this.failed || this.formDisabled || this.hasAttribute("disabled");
|
|
815
|
+
this.input.disabled = e, this.language.disabled = e, this.retry.disabled = this.formDisabled || this.hasAttribute("disabled"), e && this.close();
|
|
816
|
+
}
|
|
817
|
+
close() {
|
|
818
|
+
this.list.hidden = !0, this.input.setAttribute("aria-expanded", "false"), this.input.removeAttribute("aria-activedescendant");
|
|
819
|
+
}
|
|
820
|
+
highlight(e) {
|
|
821
|
+
this.active = e, [...this.list.children].forEach((t, n) => t.setAttribute("aria-selected", String(n === e)));
|
|
822
|
+
let t = this.list.children[e];
|
|
823
|
+
t ? (this.input.setAttribute("aria-activedescendant", t.id), t.offsetTop < this.list.scrollTop ? this.list.scrollTop = t.offsetTop : t.offsetTop + t.offsetHeight > this.list.scrollTop + this.list.clientHeight && (this.list.scrollTop = t.offsetTop + t.offsetHeight - this.list.clientHeight)) : this.input.removeAttribute("aria-activedescendant");
|
|
824
|
+
}
|
|
825
|
+
suggest() {
|
|
826
|
+
if (this.input.disabled) return;
|
|
827
|
+
let e = this.selected && this.input.value === Q(this.selected) ? "" : this.input.value.trim().toLocaleLowerCase();
|
|
828
|
+
this.filtered = this.versions.filter((t) => (!this.language.value || this.language.value === "all" || t.language === this.language.value) && `${t.title} ${t.abbreviation} ${t.languageName ?? ""}`.toLocaleLowerCase().includes(e)), this.list.replaceChildren(...this.filtered.map((e, t) => {
|
|
829
|
+
let n = document.createElement("li");
|
|
830
|
+
if (n.id = `${this.list.id}-${t}`, n.dataset.index = String(t), n.setAttribute("role", "option"), n.setAttribute("part", "option"), n.textContent = Q(e), this.language.value === "all" && e.languageName) {
|
|
831
|
+
let t = document.createElement("span");
|
|
832
|
+
t.className = "language-name", t.textContent = e.languageName, n.append(t);
|
|
833
|
+
}
|
|
834
|
+
return n;
|
|
835
|
+
})), this.status.textContent = this.filtered.length ? `${this.filtered.length} translations` : "No matching translations. Try another search or language.", this.list.hidden = !this.filtered.length, this.input.setAttribute("aria-expanded", String(!this.list.hidden)), this.highlight(Math.max(0, this.filtered.findIndex((e) => e.id === this.value)));
|
|
836
|
+
}
|
|
837
|
+
commit(e, t) {
|
|
838
|
+
let n = this.value;
|
|
839
|
+
this.selected = this.versions.find((t) => t.id === e), this.input.value = this.selected ? Q(this.selected) : "", this.internals.setFormValue(this.selected?.id ?? null);
|
|
840
|
+
let r = !!(e && !this.selected && this.provider);
|
|
841
|
+
this.internals.setValidity(r ? { customError: !0 } : {}, r ? "This translation is not available from the selected provider." : "", this.input), this.input.setAttribute("aria-invalid", String(r)), r ? this.status.textContent = "This translation is not available from the selected provider." : this.status.textContent = `${this.versions.filter((e) => !this.language.value || this.language.value === "all" || e.language === this.language.value).length} translations available`, this.close(), t && n !== this.value && (this.pendingValue = this.value, this.dispatchEvent(new CustomEvent("change", {
|
|
842
|
+
bubbles: !0,
|
|
843
|
+
detail: {
|
|
844
|
+
provider: this.provider.id,
|
|
845
|
+
bibleVersionId: this.value,
|
|
846
|
+
bibleVersion: this.selected ?? null
|
|
847
|
+
}
|
|
848
|
+
})));
|
|
849
|
+
}
|
|
850
|
+
scheduleLoad() {
|
|
851
|
+
this.generation++, this.cancelLoad?.(), this.scheduled || (this.scheduled = !0, queueMicrotask(() => {
|
|
852
|
+
this.scheduled = !1, this.isConnected && (this.cancelLoad = v.runCallback(this.load(this.generation).pipe(v.catch((e) => v.sync(() => {
|
|
853
|
+
this.selected = void 0, this.versions = [], this.input.value = "", this.status.textContent = "Unable to load translations.", this.internals.setValidity({ customError: !0 }, "Unable to load translations.", this.input), this.input.setAttribute("aria-invalid", "true"), this.loading = !1, this.failed = !0, this.updateDisabled(), this.retry.hidden = !1, this.dispatchEvent(new CustomEvent("scripture-error", { detail: e }));
|
|
854
|
+
})))));
|
|
855
|
+
}));
|
|
856
|
+
}
|
|
857
|
+
load = v.fn("scripture.versionInput.load")(function* (e) {
|
|
858
|
+
let t = this.pendingValue ?? this.selected?.id;
|
|
859
|
+
this.loading = !0, this.failed = !1, this.updateDisabled(), this.retry.hidden = !0, this.status.innerHTML = "<svg width=\"16\" height=\"16\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" aria-hidden=\"true\"><path d=\"M21 12a9 9 0 1 1-6.219-8.56\"/></svg>Loading translations", this.internals.setFormValue(null), this.internals.setValidity({}), this.input.setAttribute("aria-invalid", "false");
|
|
860
|
+
let n = yield* r({
|
|
861
|
+
...s,
|
|
862
|
+
provider: this.getAttribute("provider") || this.override || s.provider,
|
|
863
|
+
yvpPublicAppKey: this.getAttribute("yvp-public-app-key") || s.yvpPublicAppKey,
|
|
864
|
+
yvpApiHost: this.getAttribute("yvp-api-host") || s.yvpApiHost
|
|
865
|
+
}), i = yield* a({ provider: n });
|
|
866
|
+
if (!this.isConnected || e !== this.generation) return;
|
|
867
|
+
this.provider = n, this.versions = [...i].sort((e, t) => e.title.localeCompare(t.title));
|
|
868
|
+
let o = /* @__PURE__ */ new Map();
|
|
869
|
+
for (let e of i) e.language && o.set(e.language, e.languageName || e.language);
|
|
870
|
+
this.language.replaceChildren(new Option("All languages", "all"), ...[...o].sort((e, t) => e[1].localeCompare(t[1])).map(([e, t]) => new Option(t, e)));
|
|
871
|
+
let c = this.pendingValue ?? t ?? this.defaultValue(n), l = i.find((e) => e.id === c), u = this.getAttribute("language") || l?.language || new Intl.Locale(navigator.language).language;
|
|
872
|
+
this.language.value = o.has(u) ? u : "all", this.commit(c, !1), this.pendingValue = void 0, this.loading = !1, this.updateDisabled(), this.dispatchEvent(new CustomEvent("scripture-versions-load", { detail: {
|
|
873
|
+
provider: n.id,
|
|
874
|
+
versions: i
|
|
875
|
+
} }));
|
|
876
|
+
});
|
|
877
|
+
};
|
|
878
|
+
function de(e = {}) {
|
|
879
|
+
Object.assign(s, e), customElements.get("si-version-input") || customElements.define(X, $), customElements.get("bible-sk-version-input") || customElements.define(Z, class extends $ {});
|
|
880
|
+
}
|
|
881
|
+
// src/index.ts
|
|
882
|
+
var fe = `
|
|
883
|
+
.${z} {
|
|
884
|
+
/* Lay out exactly like the text it replaced, whatever the host styles links as,
|
|
885
|
+
so linking a reference never reflows the line. Only paint-only styles below. */
|
|
886
|
+
display: inline !important;
|
|
887
|
+
font: inherit !important;
|
|
888
|
+
letter-spacing: inherit !important;
|
|
889
|
+
word-spacing: inherit !important;
|
|
890
|
+
margin: 0 !important;
|
|
891
|
+
padding: 0 !important;
|
|
892
|
+
border: 0 !important;
|
|
893
|
+
color: inherit;
|
|
894
|
+
text-decoration: underline dotted;
|
|
895
|
+
text-decoration-thickness: 1.5px;
|
|
896
|
+
text-underline-offset: 0.2em;
|
|
897
|
+
cursor: pointer;
|
|
898
|
+
}
|
|
899
|
+
.${z}:hover { text-decoration-style: solid; }`;
|
|
900
|
+
function pe({ mode: e = "card", trigger: t = "click", reference: n = "heading", root: r, watch: i = !0, ...a } = {}) {
|
|
901
|
+
if (!document.getElementById("scripture-inline-styles")) {
|
|
902
|
+
let e = document.createElement("style");
|
|
903
|
+
e.id = "scripture-inline-styles", e.textContent = fe, document.head.append(e);
|
|
904
|
+
}
|
|
905
|
+
let o = V(r ?? document.body), s = new AbortController(), { signal: c } = s, l = null, u = r ?? document, d = new MutationObserver((e) => {
|
|
906
|
+
for (let t of e) for (let e of t.addedNodes) {
|
|
907
|
+
if (!e.isConnected || !r && !document.body?.contains(e)) continue;
|
|
908
|
+
let t = e.nodeType === Node.TEXT_NODE ? e.parentNode : e;
|
|
909
|
+
if (t && (o.push(...V(t)), t instanceof Element)) for (let e of t.querySelectorAll(`a.${z}`)) o.includes(e) || o.push(e);
|
|
910
|
+
}
|
|
911
|
+
d.takeRecords();
|
|
912
|
+
for (let e = o.length - 1; e >= 0; e--) o[e].isConnected || o.splice(e, 1);
|
|
913
|
+
l?.closeIfDetached();
|
|
914
|
+
});
|
|
915
|
+
if (e === "card") {
|
|
916
|
+
let e = l = L({
|
|
917
|
+
...a,
|
|
918
|
+
reference: n
|
|
919
|
+
}), r = (e) => e.target.closest?.(`a.${z}`);
|
|
920
|
+
u.addEventListener("click", (t) => {
|
|
921
|
+
let n = t;
|
|
922
|
+
if (n.metaKey || n.ctrlKey || n.shiftKey || n.altKey || n.button !== 0) return;
|
|
923
|
+
let i = r(t);
|
|
924
|
+
i && (t.preventDefault(), e.toggle(i));
|
|
925
|
+
}, { signal: c }), t === "hover" && (u.addEventListener("pointerover", (t) => {
|
|
926
|
+
let n = r(t);
|
|
927
|
+
n && t.pointerType === "mouse" && e.hover(n);
|
|
928
|
+
}, { signal: c }), u.addEventListener("pointerout", (t) => {
|
|
929
|
+
r(t) && e.unhover(t);
|
|
930
|
+
}, { signal: c }));
|
|
931
|
+
}
|
|
932
|
+
return {
|
|
933
|
+
links: o,
|
|
934
|
+
stop: v.runCallback(v.gen(function* () {
|
|
935
|
+
yield* v.acquireRelease(v.sync(() => {
|
|
936
|
+
i && d.observe(r ?? document.documentElement, {
|
|
937
|
+
childList: !0,
|
|
938
|
+
subtree: !0
|
|
939
|
+
});
|
|
940
|
+
}), () => v.sync(() => {
|
|
941
|
+
d.disconnect(), s.abort(), l?.destroy(), H(o);
|
|
942
|
+
})), yield* v.never;
|
|
943
|
+
}).pipe(v.scoped, v.withSpan("scripture.references.watch")))
|
|
944
|
+
};
|
|
945
|
+
}
|
|
946
|
+
export { W as BIBLE_PASSAGE_INPUT_TAG, T as BIBLE_PASSAGE_TAG, Z as BIBLE_VERSION_INPUT_TAG, U as PASSAGE_INPUT_TAG, w as SCRIPTURE_PASSAGE_TAG, M as ScripturePassage, Y as ScripturePassageInput, $ as ScriptureVersionInput, X as VERSION_INPUT_TAG, L as createScriptureCard, i as createYouVersionProvider, ce as definePassageInput, N as defineScripturePassage, de as defineVersionInput, R as findReferences, n as helloaoProvider, e as listBibleVersions, pe as scriptureInline, H as unwrapReferences, V as wrapReferences };
|