azoxjs 1.0.1 → 1.3.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.
@@ -128,6 +128,7 @@ async function go(href, { restore = false } = {}) {
128
128
  // already holds wherever the reader last asked to go.
129
129
  if (location.href !== href) return;
130
130
 
131
+ const previous = currentUrl;
131
132
  const next = new DOMParser().parseFromString(html, 'text/html');
132
133
  const incoming = next.querySelector(ROOT);
133
134
  const target = document.querySelector(ROOT);
@@ -145,6 +146,18 @@ async function go(href, { restore = false } = {}) {
145
146
 
146
147
  currentUrl = href;
147
148
  restoreScroll(restore);
149
+
150
+ // The page's own module is re-run above, but a classic <script> that
151
+ // enhances the markup — syntax highlighting, heading anchors, a
152
+ // table of contents — is not: it ran once on first load and the
153
+ // nodes it worked on have just been replaced. This event is how such
154
+ // a script knows to run again.
155
+ //
156
+ // Dispatched after the swap and after the module, so a listener sees
157
+ // the finished page.
158
+ document.dispatchEvent(
159
+ new CustomEvent('azox:navigate', { detail: { url: href, from: previous } })
160
+ );
148
161
  }
149
162
 
150
163
  // Brings across anything in the new page's head that this one lacks —
@@ -199,13 +212,23 @@ async function runPageModule(next, pageHref) {
199
212
  function restoreScroll(restore) {
200
213
  if (restore) return; // The browser restores the position itself.
201
214
 
202
- const { hash } = location;
203
- const target = hash && document.querySelector(hash);
215
+ const target = elementForHash(location.hash);
204
216
 
205
217
  if (target) target.scrollIntoView();
206
218
  else window.scrollTo(0, 0);
207
219
  }
208
220
 
221
+ // A hash is not always a selector. A page may use it to carry state —
222
+ // "#template=landing" — and handing that to querySelector throws
223
+ // "not a valid selector", which stopped the scroll being restored at
224
+ // all and put an error in every visitor's console.
225
+ function elementForHash(hash) {
226
+ if (!hash || hash.length < 2) return null;
227
+
228
+ // getElementById takes an id, not a selector, so nothing can throw.
229
+ return document.getElementById(decodeURIComponent(hash.slice(1)));
230
+ }
231
+
209
232
  export function currentHref() {
210
233
  return currentUrl;
211
234
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "azoxjs",
3
- "version": "1.0.1",
3
+ "version": "1.3.0",
4
4
  "description": "Azox Framework — The Sound of Future Web",
5
5
  "type": "module",
6
6
  "license": "MIT",
@@ -9,17 +9,26 @@
9
9
  "type": "git",
10
10
  "url": "git+https://github.com/darilpratomo/azox.git"
11
11
  },
12
- "homepage": "https://github.com/darilpratomo/azox#readme",
12
+ "homepage": "https://azox.dev",
13
13
  "bugs": {
14
14
  "url": "https://github.com/darilpratomo/azox/issues"
15
15
  },
16
16
  "bin": {
17
- "azox": "./bin/azox.js"
17
+ "azox": "bin/azox.js"
18
18
  },
19
19
  "exports": {
20
- ".": "./core/index.js",
21
- "./reactivity": "./core/reactivity/signal.js",
22
- "./compiler": "./core/compiler/index.js",
20
+ ".": {
21
+ "types": "./core/index.d.ts",
22
+ "default": "./core/index.js"
23
+ },
24
+ "./reactivity": {
25
+ "types": "./core/reactivity/signal.d.ts",
26
+ "default": "./core/reactivity/signal.js"
27
+ },
28
+ "./compiler": {
29
+ "types": "./core/compiler/index.d.ts",
30
+ "default": "./core/compiler/index.js"
31
+ },
23
32
  "./package.json": "./package.json"
24
33
  },
25
34
  "files": [
@@ -43,5 +52,6 @@
43
52
  "compiler",
44
53
  "ssr",
45
54
  "no-virtual-dom"
46
- ]
55
+ ],
56
+ "types": "./core/index.d.ts"
47
57
  }