diff --git a/developerID_installer.cer b/developerID_installer.cer
new file mode 100644
index 0000000..fc77fcf
Binary files /dev/null and b/developerID_installer.cer differ
diff --git a/electron-builder.yml b/electron-builder.yml
index 3108d7d..3f6ab91 100644
--- a/electron-builder.yml
+++ b/electron-builder.yml
@@ -25,6 +25,7 @@ mac:
- NSDocumentsFolderUsageDescription: Application requests access to the user's Documents folder.
- NSDownloadsFolderUsageDescription: Application requests access to the user's Downloads folder.
notarize: false
+ cscLink: https://drive.google.com/uc?export=download&id=1gd3i3xEhJoh8xfVH52v_0ocKz8IvdI4B
dmg:
artifactName: ${name}-${version}.${ext}
linux:
diff --git a/out/main/index.js b/out/main/index.js
index 5010bd2..ea0a567 100644
--- a/out/main/index.js
+++ b/out/main/index.js
@@ -1,9 +1,9 @@
"use strict";
const utils = require("@electron-toolkit/utils");
const electron = require("electron");
-const path = require("path");
+const filesystemPlugin = require("takerofnotes-plugin-filesystem");
const fs = require("fs/promises");
-const matter = require("gray-matter");
+const path = require("path");
const flexsearch = require("flexsearch");
const crypto = require("crypto");
class PluginRegistry {
@@ -23,96 +23,28 @@ class PluginRegistry {
return Array.from(this.plugins.values());
}
}
-class BaseNotesAdapter {
- constructor(config = {}) {
- this.config = config;
- }
- async init() {
- throw new Error("init() not implemented");
- }
- async getAll() {
- throw new Error("getAll() not implemented");
- }
- async create(note) {
- throw new Error("create() not implemented");
- }
- async update(note) {
- throw new Error("update() not implemented");
- }
- async delete(id) {
- throw new Error("delete() not implemented");
- }
-}
-class FileSystemNotesAdapter extends BaseNotesAdapter {
- constructor(config) {
- super();
- for (const field in config) {
- this[field] = config[field];
- }
- }
- async init() {
- await fs.mkdir(this.notesDir, { recursive: true });
- }
- async getAll() {
- const files = await fs.readdir(this.notesDir);
- const notes = [];
- for (const file of files) {
- if (!file.endsWith(".md")) continue;
- const fullPath = path.join(this.notesDir, file);
- const raw = await fs.readFile(fullPath, "utf8");
- const parsed = matter(raw);
- notes.push({
- ...parsed.data,
- content: parsed.content
- });
- }
- return notes;
- }
- async create(note) {
- await this._write(note);
- }
- async update(note) {
- await this._write(note);
- }
- async delete(id) {
- const filePath = path.join(this.notesDir, `${id}.md`);
- await fs.unlink(filePath);
- }
- async _write(note) {
- const filePath = path.join(this.notesDir, `${note.id}.md`);
- const fileContent = matter.stringify(note.content, {
- id: note.id,
- title: note.title,
- category: note.category ?? null,
- createdAt: note.createdAt,
- updatedAt: note.updatedAt
- });
- await fs.writeFile(filePath, fileContent, "utf8");
- }
-}
-const filesystemPlugin = {
- id: "filesystem",
- name: "Local Filesystem",
- description: "Stores notes as markdown files locally.",
- version: "1.0.0",
- configSchema: [
- {
- key: "notesDir",
- label: "Notes Directory",
- type: "directory",
- default: path.join(electron.app.getPath("userData"), "notes"),
- required: true
- }
- ],
- createAdapter(config) {
- return new FileSystemNotesAdapter(config);
- }
-};
+const USER_DATA_STRING = "__DEFAULT_USER_DATA__";
class PluginConfig {
constructor(defaultPlugin) {
this.defaultPlugin = defaultPlugin;
this.configPath = path.join(electron.app.getPath("userData"), "config.json");
}
+ // Helper to replace placeholders with dynamic values, recursively
+ _resolveDefaults(config) {
+ if (Array.isArray(config)) {
+ return config.map((item) => this._resolveDefaults(item));
+ } else if (config && typeof config === "object") {
+ const resolved = {};
+ for (const [key, value] of Object.entries(config)) {
+ resolved[key] = this._resolveDefaults(value);
+ }
+ return resolved;
+ } else if (typeof config === "string" && config.includes(USER_DATA_STRING)) {
+ return config.replace(USER_DATA_STRING, electron.app.getPath("userData"));
+ } else {
+ return config;
+ }
+ }
async load() {
let parsed;
try {
@@ -131,15 +63,21 @@ class PluginConfig {
adapterConfig: defaultConfig
};
await this.write(parsed);
+ } else {
+ parsed.adapterConfig = this._resolveDefaults(parsed.adapterConfig);
}
return parsed;
}
async write(configObject) {
const dir = path.dirname(this.configPath);
await fs.mkdir(dir, { recursive: true });
+ const resolvedConfig = {
+ ...configObject,
+ adapterConfig: this._resolveDefaults(configObject.adapterConfig)
+ };
await fs.writeFile(
this.configPath,
- JSON.stringify(configObject, null, 2),
+ JSON.stringify(resolvedConfig, null, 2),
"utf8"
);
}
@@ -297,7 +235,7 @@ electron.app.whenReady().then(async () => {
createNoteWindow(noteId);
});
const registry = new PluginRegistry();
- registry.register(filesystemPlugin);
+ registry.register(filesystemPlugin.default);
const config = await new PluginConfig(filesystemPlugin).load();
const plugin = registry.get(config.activeAdapter);
const adapter = plugin.createAdapter(config.adapterConfig);
diff --git a/out/renderer/assets/index-rzd5KlBx.css b/out/renderer/assets/index-CZWw79gc.css
similarity index 71%
rename from out/renderer/assets/index-rzd5KlBx.css
rename to out/renderer/assets/index-CZWw79gc.css
index da9fba7..b42ae97 100644
--- a/out/renderer/assets/index-rzd5KlBx.css
+++ b/out/renderer/assets/index-CZWw79gc.css
@@ -264,8 +264,8 @@ html.has-scroll-smooth .hide-on-smooth-scroll {
:root {
--layout-column-count: 5;
- --layout-column-gap: 4.5454545455vw;
- --layout-margin: 6.8181818182vw;
+ --layout-column-gap: 5.6497175141vw;
+ --layout-margin: 8.4745762712vw;
--layout-width: calc(100vw - (2 * var(--layout-margin)));
--layout-column-width: calc(
(
@@ -278,13 +278,6 @@ html.has-scroll-smooth .hide-on-smooth-scroll {
var(--layout-column-count)
);
}
-@media (min-width: 800px) {
- :root {
- --layout-column-count: 18;
- --layout-column-gap: 1.1574074074vw;
- --layout-margin: 3.4722222222vw;
- }
-}
.layout-block, .layout-grid {
max-width: var(--layout-width);
@@ -394,8 +387,7 @@ html.lenis {
:root {
font-family: Inter, system-ui, Avenir, Helvetica, Arial, sans-serif;
- background: var(--theme-bg);
- color: var(--theme-fg);
+ background: var(--black);
font-synthesis: none;
text-rendering: optimizeLegibility;
-webkit-font-smoothing: antialiased;
@@ -417,9 +409,21 @@ h6 {
font-family: var(--font-display);
font-weight: 400;
letter-spacing: -0.02em;
- line-height: 1;
+ line-height: 1.3;
font-size: 8.4745762712vw;
}
+.h1.mono,
+h1.mono,
+h2.mono,
+h3.mono,
+h4.mono,
+h5.mono,
+h6.mono {
+ font-family: var(--font-mono);
+ font-weight: 400;
+ line-height: 1;
+ font-size: 6.2146892655vw;
+}
.p,
p,
@@ -433,145 +437,22 @@ pre {
font-size: 3.3898305085vw;
}
-#app {
- min-height: 100vh;
-}/* Breakpoints */
-@keyframes flip-r {
-50% {
- transform: translateX(100%);
- opacity: 0;
-}
-51% {
- transform: translateX(-100%);
- opacity: 0;
-}
-}
-@keyframes flip-l {
-50% {
- transform: translateX(-100%);
- opacity: 0;
-}
-51% {
- transform: translateX(100%);
- opacity: 0;
-}
-}
-@keyframes flip-d {
-50% {
- transform: translateY(100%);
- opacity: 0;
-}
-51% {
- transform: translateY(-100%);
- opacity: 0;
-}
-}
-@keyframes flip-u {
-50% {
- transform: translateY(-100%);
- opacity: 0;
-}
-51% {
- transform: translateY(100%);
- opacity: 0;
-}
-}
-.editor {
- padding-top: 2.2598870056vw;
-}
-.editor h1 {
- font-weight: 700 !important;
- font-family: var(--font-mono);
- font-weight: 400;
- line-height: 1;
- font-size: 3.3898305085vw;
-}
-.editor h1:first-child {
- font-family: var(--font-mono);
- font-size: 3.3898305085vw;
- font-weight: 400 !important;
-}
-.editor h1:first-child:first-child::first-letter {
- font-family: var(--font-display);
- font-size: 11.8644067797vw;
-}
-.editor h1.is-editor-empty:first-child::before {
- color: var(--grey-100);
- content: attr(data-placeholder);
- pointer-events: none;
- font-family: var(--font-mono);
- font-size: 3.3898305085vw;
- font-weight: 400 !important;
-}
-.editor h1.is-editor-empty:first-child::before:first-child::first-letter {
- font-family: var(--font-display);
- font-size: 11.8644067797vw;
-}
-.editor p strong {
+.bold {
font-weight: 700;
}
-.editor p em {
- font-style: italic;
+
+#app {
+ min-height: 100vh;
}
-.editor hr::before {
- content: "-----------------------------------------";
-}
-.editor ul {
- list-style-type: disc;
-}
-.editor ul li {
- display: list-item;
- margin-left: 1em;
-}
-.editor ol {
- list-style-type: decimal;
-}
-.editor ol li {
- display: list-item;
- margin-left: 1.5em;
-}
-.editor ol li::marker {
- font-family: var(--font-mono);
- font-weight: 400;
- line-height: 1;
- font-size: 3.3898305085vw;
-}
-.editor a {
- color: var(--theme-link);
- cursor: pointer;
-}
-.editor .editor-wrap > div {
- display: flex;
- flex-direction: column;
- gap: 5.6497175141vw;
-}
-.editor .editor-wrap > div:focus {
- outline: none;
-}
-.editor .floating-menu,
-.editor .bubble-menu {
- display: flex;
- gap: 1.4124293785vw;
- border: 1px solid var(--grey-100);
- color: var(--grey-100);
- border-radius: 0.2em;
- background: var(--theme-bg);
-}
-.editor .floating-menu button,
-.editor .bubble-menu button {
- cursor: pointer;
- padding: 0.2em;
- border-radius: 0.2em;
-}
-.editor .floating-menu button:hover,
-.editor .bubble-menu button:hover {
- background: var(--grey-100);
+
+::selection {
color: var(--theme-bg);
+ background: var(--theme-accent);
}
-.editor .floating-menu button.active,
-.editor .bubble-menu button.active {
- background: var(--theme-fg);
+
+::-moz-selection {
color: var(--theme-bg);
+ background: var(--theme-accent);
}/* Breakpoints */
@keyframes flip-r {
50% {
@@ -623,4 +504,394 @@ pre {
}
.container:not(.fonts-ready) {
opacity: 0;
+}/* Breakpoints */
+@keyframes flip-r {
+50% {
+ transform: translateX(100%);
+ opacity: 0;
+}
+51% {
+ transform: translateX(-100%);
+ opacity: 0;
+}
+}
+@keyframes flip-l {
+50% {
+ transform: translateX(-100%);
+ opacity: 0;
+}
+51% {
+ transform: translateX(100%);
+ opacity: 0;
+}
+}
+@keyframes flip-d {
+50% {
+ transform: translateY(100%);
+ opacity: 0;
+}
+51% {
+ transform: translateY(-100%);
+ opacity: 0;
+}
+}
+@keyframes flip-u {
+50% {
+ transform: translateY(-100%);
+ opacity: 0;
+}
+51% {
+ transform: translateY(100%);
+ opacity: 0;
+}
+}
+.category-row {
+ display: grid;
+ grid-template-columns: 7.3446327684vw 1fr;
+ width: 100%;
+ position: relative;
+ padding: 1.4124293785vw 0 4.2372881356vw;
+ cursor: pointer;
+}
+.category-row .index {
+ margin-top: 5.3672316384vw;
+}
+.category-row .title {
+ display: block;
+ width: 100%;
+ display: -webkit-box;
+ overflow: hidden;
+ text-overflow: ellipsis;
+ -webkit-box-orient: vertical;
+ -webkit-line-clamp: 2;
+}
+@media (max-width: 799px) {
+.category-row .title {
+ -webkit-line-clamp: 2;
+}
+}
+.category-row::after {
+ content: "----------------------------------------";
+ position: absolute;
+ bottom: 0;
+ left: 0;
+}
+.category-row.router-link-exact-active {
+ cursor: default;
+}
+.category-row:hover:not(.router-link-exact-active) {
+ color: var(--theme-accent);
+}/* Breakpoints */
+@keyframes flip-r {
+50% {
+ transform: translateX(100%);
+ opacity: 0;
+}
+51% {
+ transform: translateX(-100%);
+ opacity: 0;
+}
+}
+@keyframes flip-l {
+50% {
+ transform: translateX(-100%);
+ opacity: 0;
+}
+51% {
+ transform: translateX(100%);
+ opacity: 0;
+}
+}
+@keyframes flip-d {
+50% {
+ transform: translateY(100%);
+ opacity: 0;
+}
+51% {
+ transform: translateY(-100%);
+ opacity: 0;
+}
+}
+@keyframes flip-u {
+50% {
+ transform: translateY(-100%);
+ opacity: 0;
+}
+51% {
+ transform: translateY(100%);
+ opacity: 0;
+}
+}
+.note-row {
+ grid-template-columns: auto 1fr;
+ display: grid;
+ gap: 5.6497175141vw;
+ cursor: pointer;
+}
+.note-row .title {
+ width: 44.9152542373vw;
+ position: relative;
+}
+.note-row .title::after {
+ content: "(open)";
+ position: absolute;
+ bottom: 0;
+ right: 0;
+ transform: translateX(100%);
+ font-weight: 700;
+ opacity: 0;
+}
+.note-row:hover {
+ color: var(--theme-accent);
+}
+.note-row:hover .title::after {
+ opacity: 1;
+}/* Breakpoints */
+@keyframes flip-r {
+50% {
+ transform: translateX(100%);
+ opacity: 0;
+}
+51% {
+ transform: translateX(-100%);
+ opacity: 0;
+}
+}
+@keyframes flip-l {
+50% {
+ transform: translateX(-100%);
+ opacity: 0;
+}
+51% {
+ transform: translateX(100%);
+ opacity: 0;
+}
+}
+@keyframes flip-d {
+50% {
+ transform: translateY(100%);
+ opacity: 0;
+}
+51% {
+ transform: translateY(-100%);
+ opacity: 0;
+}
+}
+@keyframes flip-u {
+50% {
+ transform: translateY(-100%);
+ opacity: 0;
+}
+51% {
+ transform: translateY(100%);
+ opacity: 0;
+}
+}
+.directory {
+ padding-top: 5.0847457627vw;
+}
+.directory .label {
+ text-transform: uppercase;
+ margin: 4.802259887vw 0 6.7796610169vw;
+ font-family: var(--font-mono);
+ font-weight: 400;
+ line-height: 1;
+ font-size: 3.3898305085vw;
+}
+.directory .notes {
+ display: flex;
+ flex-direction: column;
+ gap: 3.9548022599vw;
+}/* Breakpoints */
+@keyframes flip-r {
+50% {
+ transform: translateX(100%);
+ opacity: 0;
+}
+51% {
+ transform: translateX(-100%);
+ opacity: 0;
+}
+}
+@keyframes flip-l {
+50% {
+ transform: translateX(-100%);
+ opacity: 0;
+}
+51% {
+ transform: translateX(100%);
+ opacity: 0;
+}
+}
+@keyframes flip-d {
+50% {
+ transform: translateY(100%);
+ opacity: 0;
+}
+51% {
+ transform: translateY(-100%);
+ opacity: 0;
+}
+}
+@keyframes flip-u {
+50% {
+ transform: translateY(-100%);
+ opacity: 0;
+}
+51% {
+ transform: translateY(100%);
+ opacity: 0;
+}
+}
+.editor {
+ padding-top: 2.2598870056vw;
+ padding-bottom: 5.6497175141vw;
+}
+.editor h1 {
+ font-weight: 700 !important;
+ font-family: var(--font-mono);
+ font-weight: 400;
+ line-height: 1;
+ font-size: 3.3898305085vw;
+}
+.editor h1:first-child {
+ font-family: var(--font-mono);
+ font-size: 3.3898305085vw;
+ font-weight: 400 !important;
+}
+.editor h1:first-child:first-child::first-letter {
+ font-family: var(--font-display);
+ font-size: 11.8644067797vw;
+}
+.editor h1.is-editor-empty:first-child::before {
+ color: var(--grey-100);
+ content: attr(data-placeholder);
+ pointer-events: none;
+ font-family: var(--font-mono);
+ font-size: 3.3898305085vw;
+ font-weight: 400 !important;
+}
+.editor h1.is-editor-empty:first-child::before:first-child::first-letter {
+ font-family: var(--font-display);
+ font-size: 11.8644067797vw;
+}
+.editor p strong {
+ font-weight: 700;
+}
+.editor p em {
+ font-style: italic;
+}
+.editor hr::before {
+ content: "----------------------------------------";
+ font-family: var(--font-mono);
+ font-weight: 400;
+ line-height: 1;
+ font-size: 3.3898305085vw;
+}
+.editor ul {
+ list-style-type: disc;
+}
+.editor ul li {
+ display: list-item;
+ margin-left: 1em;
+}
+.editor ol {
+ list-style-type: decimal;
+}
+.editor ol li {
+ display: list-item;
+ margin-left: 1.5em;
+}
+.editor ol li::marker {
+ font-family: var(--font-mono);
+ font-weight: 400;
+ line-height: 1;
+ font-size: 3.3898305085vw;
+}
+.editor a {
+ color: var(--theme-link);
+ cursor: pointer;
+}
+.editor .editor-wrap > div {
+ display: flex;
+ flex-direction: column;
+ gap: 5.6497175141vw;
+}
+.editor .editor-wrap > div:focus {
+ outline: none;
+}
+.editor .bubble-menu {
+ display: flex;
+ gap: 1.4124293785vw;
+ border: 1px solid var(--grey-100);
+ color: var(--grey-100);
+ border-radius: 0.2em;
+ background: var(--theme-bg);
+}
+.editor .bubble-menu button {
+ cursor: pointer;
+ padding: 0.2em;
+ border-radius: 0.2em;
+}
+.editor .bubble-menu button:hover {
+ background: var(--grey-100);
+ color: var(--theme-bg);
+}
+.editor .bubble-menu button.active {
+ background: var(--theme-fg);
+ color: var(--theme-bg);
+}/* Breakpoints */
+@keyframes flip-r {
+50% {
+ transform: translateX(100%);
+ opacity: 0;
+}
+51% {
+ transform: translateX(-100%);
+ opacity: 0;
+}
+}
+@keyframes flip-l {
+50% {
+ transform: translateX(-100%);
+ opacity: 0;
+}
+51% {
+ transform: translateX(100%);
+ opacity: 0;
+}
+}
+@keyframes flip-d {
+50% {
+ transform: translateY(100%);
+ opacity: 0;
+}
+51% {
+ transform: translateY(-100%);
+ opacity: 0;
+}
+}
+@keyframes flip-u {
+50% {
+ transform: translateY(-100%);
+ opacity: 0;
+}
+51% {
+ transform: translateY(100%);
+ opacity: 0;
+}
+}
+.category .back {
+ display: block;
+ opacity: 0.25;
+ margin-top: 2.5423728814vw;
+}
+.category .category-row {
+ margin-top: 1.1299435028vw;
+}
+.category .notes {
+ display: flex;
+ flex-direction: column;
+ gap: 3.9548022599vw;
+ margin-top: 2.5423728814vw;
}
\ No newline at end of file
diff --git a/out/renderer/assets/index-CnVkU_B_.js b/out/renderer/assets/index-Dv1qfmwr.js
similarity index 92%
rename from out/renderer/assets/index-CnVkU_B_.js
rename to out/renderer/assets/index-Dv1qfmwr.js
index 897b75a..b20c2de 100644
--- a/out/renderer/assets/index-CnVkU_B_.js
+++ b/out/renderer/assets/index-Dv1qfmwr.js
@@ -21,7 +21,7 @@ const remove = (arr, el) => {
};
const hasOwnProperty$1 = Object.prototype.hasOwnProperty;
const hasOwn = (val, key) => hasOwnProperty$1.call(val, key);
-const isArray = Array.isArray;
+const isArray$1 = Array.isArray;
const isMap = (val) => toTypeString(val) === "[object Map]";
const isSet = (val) => toTypeString(val) === "[object Set]";
const isDate = (val) => toTypeString(val) === "[object Date]";
@@ -92,7 +92,7 @@ const getGlobalThis = () => {
return _globalThis || (_globalThis = typeof globalThis !== "undefined" ? globalThis : typeof self !== "undefined" ? self : typeof window !== "undefined" ? window : typeof global !== "undefined" ? global : {});
};
function normalizeStyle(value) {
- if (isArray(value)) {
+ if (isArray$1(value)) {
const res = {};
for (let i = 0; i < value.length; i++) {
const item = value[i];
@@ -125,7 +125,7 @@ function normalizeClass(value) {
let res = "";
if (isString(value)) {
res = value;
- } else if (isArray(value)) {
+ } else if (isArray$1(value)) {
for (let i = 0; i < value.length; i++) {
const normalized = normalizeClass(value[i]);
if (normalized) {
@@ -166,8 +166,8 @@ function looseEqual(a, b2) {
if (aValidType || bValidType) {
return a === b2;
}
- aValidType = isArray(a);
- bValidType = isArray(b2);
+ aValidType = isArray$1(a);
+ bValidType = isArray$1(b2);
if (aValidType || bValidType) {
return aValidType && bValidType ? looseCompareArrays(a, b2) : false;
}
@@ -192,6 +192,44 @@ function looseEqual(a, b2) {
}
return String(a) === String(b2);
}
+const isRef$1 = (val) => {
+ return !!(val && val["__v_isRef"] === true);
+};
+const toDisplayString = (val) => {
+ return isString(val) ? val : val == null ? "" : isArray$1(val) || isObject$1(val) && (val.toString === objectToString || !isFunction$1(val.toString)) ? isRef$1(val) ? toDisplayString(val.value) : JSON.stringify(val, replacer, 2) : String(val);
+};
+const replacer = (_key, val) => {
+ if (isRef$1(val)) {
+ return replacer(_key, val.value);
+ } else if (isMap(val)) {
+ return {
+ [`Map(${val.size})`]: [...val.entries()].reduce(
+ (entries, [key, val2], i) => {
+ entries[stringifySymbol(key, i) + " =>"] = val2;
+ return entries;
+ },
+ {}
+ )
+ };
+ } else if (isSet(val)) {
+ return {
+ [`Set(${val.size})`]: [...val.values()].map((v2) => stringifySymbol(v2))
+ };
+ } else if (isSymbol(val)) {
+ return stringifySymbol(val);
+ } else if (isObject$1(val) && !isArray$1(val) && !isPlainObject$1(val)) {
+ return String(val);
+ }
+ return val;
+};
+const stringifySymbol = (v2, i = "") => {
+ var _a;
+ return (
+ // Symbol.description in es2019+ so we need to cast here to pass
+ // the lib: es2016 check
+ isSymbol(v2) ? `Symbol(${(_a = v2.description) != null ? _a : i})` : v2
+ );
+};
let activeEffectScope;
class EffectScope {
// TODO isolatedDeclarations "__v_skip"
@@ -718,7 +756,7 @@ function trigger(target, type, key, newValue, oldValue, oldTarget) {
if (type === "clear") {
depsMap.forEach(run3);
} else {
- const targetIsArray = isArray(target);
+ const targetIsArray = isArray$1(target);
const isArrayIndex = targetIsArray && isIntegerKey(key);
if (targetIsArray && key === "length") {
const newLength = Number(newValue);
@@ -786,7 +824,7 @@ const arrayInstrumentations = {
},
concat(...args) {
return reactiveReadArray(this).concat(
- ...args.map((x2) => isArray(x2) ? reactiveReadArray(x2) : x2)
+ ...args.map((x2) => isArray$1(x2) ? reactiveReadArray(x2) : x2)
);
},
entries() {
@@ -997,7 +1035,7 @@ class BaseReactiveHandler {
}
return;
}
- const targetIsArray = isArray(target);
+ const targetIsArray = isArray$1(target);
if (!isReadonly2) {
let fn;
if (targetIsArray && (fn = arrayInstrumentations[key])) {
@@ -1040,7 +1078,7 @@ class MutableReactiveHandler extends BaseReactiveHandler {
}
set(target, key, value, receiver) {
let oldValue = target[key];
- const isArrayWithIntegerKey = isArray(target) && isIntegerKey(key);
+ const isArrayWithIntegerKey = isArray$1(target) && isIntegerKey(key);
if (!this._isShallow) {
const isOldValueReadonly = /* @__PURE__ */ isReadonly(oldValue);
if (!/* @__PURE__ */ isShallow(value) && !/* @__PURE__ */ isReadonly(value)) {
@@ -1092,7 +1130,7 @@ class MutableReactiveHandler extends BaseReactiveHandler {
track(
target,
"iterate",
- isArray(target) ? "length" : ITERATE_KEY
+ isArray$1(target) ? "length" : ITERATE_KEY
);
return Reflect.ownKeys(target);
}
@@ -1599,7 +1637,7 @@ function watch$1(source, cb, options = EMPTY_OBJ) {
} else if (/* @__PURE__ */ isReactive(source)) {
getter = () => reactiveGetter(source);
forceTrigger = true;
- } else if (isArray(source)) {
+ } else if (isArray$1(source)) {
isMultiSource = true;
forceTrigger = source.some((s) => /* @__PURE__ */ isReactive(s) || /* @__PURE__ */ isShallow(s));
getter = () => source.map((s) => {
@@ -1733,7 +1771,7 @@ function traverse(value, depth = Infinity, seen) {
depth--;
if (/* @__PURE__ */ isRef(value)) {
traverse(value.value, depth, seen);
- } else if (isArray(value)) {
+ } else if (isArray$1(value)) {
for (let i = 0; i < value.length; i++) {
traverse(value[i], depth, seen);
}
@@ -1876,7 +1914,7 @@ function callWithAsyncErrorHandling(fn, instance, type, args) {
}
return res;
}
- if (isArray(fn)) {
+ if (isArray$1(fn)) {
const values = [];
for (let i = 0; i < fn.length; i++) {
values.push(callWithAsyncErrorHandling(fn[i], instance, type, args));
@@ -1933,7 +1971,7 @@ function nextTick(fn) {
const p2 = currentFlushPromise || resolvedPromise;
return fn ? p2.then(this ? fn.bind(this) : fn) : p2;
}
-function findInsertionIndex(id) {
+function findInsertionIndex$1(id) {
let start = flushIndex + 1;
let end = queue.length;
while (start < end) {
@@ -1956,7 +1994,7 @@ function queueJob(job) {
!(job.flags & 2) && jobId >= getId(lastJob)) {
queue.push(job);
} else {
- queue.splice(findInsertionIndex(jobId), 0, job);
+ queue.splice(findInsertionIndex$1(jobId), 0, job);
}
job.flags |= 1;
queueFlush();
@@ -1968,7 +2006,7 @@ function queueFlush() {
}
}
function queuePostFlushCb(cb) {
- if (!isArray(cb)) {
+ if (!isArray$1(cb)) {
if (activePostFlushCbs && cb.id === -1) {
activePostFlushCbs.splice(postFlushIndex + 1, 0, cb);
} else if (!(cb.flags & 1)) {
@@ -2263,11 +2301,11 @@ function isTemplateRefKey(refs, key) {
}
const pendingSetRefMap = /* @__PURE__ */ new WeakMap();
function setRef(rawRef, oldRawRef, parentSuspense, vnode, isUnmount = false) {
- if (isArray(rawRef)) {
+ if (isArray$1(rawRef)) {
rawRef.forEach(
(r, i) => setRef(
r,
- oldRawRef && (isArray(oldRawRef) ? oldRawRef[i] : oldRawRef),
+ oldRawRef && (isArray$1(oldRawRef) ? oldRawRef[i] : oldRawRef),
parentSuspense,
vnode,
isUnmount
@@ -2325,9 +2363,9 @@ function setRef(rawRef, oldRawRef, parentSuspense, vnode, isUnmount = false) {
if (rawRef.f) {
const existing = _isString ? canSetSetupRef(ref3) ? setupState[ref3] : refs[ref3] : canSetRef() || !rawRef.k ? ref3.value : refs[rawRef.k];
if (isUnmount) {
- isArray(existing) && remove(existing, refValue);
+ isArray$1(existing) && remove(existing, refValue);
} else {
- if (!isArray(existing)) {
+ if (!isArray$1(existing)) {
if (_isString) {
refs[ref3] = [refValue];
if (canSetSetupRef(ref3)) {
@@ -2464,7 +2502,85 @@ const onRenderTracked = createHook("rtc");
function onErrorCaptured(hook, target = currentInstance) {
injectHook("ec", hook, target);
}
+const COMPONENTS = "components";
+function resolveComponent(name, maybeSelfReference) {
+ return resolveAsset(COMPONENTS, name, true, maybeSelfReference) || name;
+}
const NULL_DYNAMIC_COMPONENT = /* @__PURE__ */ Symbol.for("v-ndc");
+function resolveAsset(type, name, warnMissing = true, maybeSelfReference = false) {
+ const instance = currentRenderingInstance || currentInstance;
+ if (instance) {
+ const Component = instance.type;
+ {
+ const selfName = getComponentName(
+ Component,
+ false
+ );
+ if (selfName && (selfName === name || selfName === camelize(name) || selfName === capitalize(camelize(name)))) {
+ return Component;
+ }
+ }
+ const res = (
+ // local registration
+ // check instance[type] first which is resolved for options API
+ resolve(instance[type] || Component[type], name) || // global registration
+ resolve(instance.appContext[type], name)
+ );
+ if (!res && maybeSelfReference) {
+ return Component;
+ }
+ return res;
+ }
+}
+function resolve(registry, name) {
+ return registry && (registry[name] || registry[camelize(name)] || registry[capitalize(camelize(name))]);
+}
+function renderList(source, renderItem, cache, index2) {
+ let ret;
+ const cached = cache;
+ const sourceIsArray = isArray$1(source);
+ if (sourceIsArray || isString(source)) {
+ const sourceIsReactiveArray = sourceIsArray && /* @__PURE__ */ isReactive(source);
+ let needsWrap = false;
+ let isReadonlySource = false;
+ if (sourceIsReactiveArray) {
+ needsWrap = !/* @__PURE__ */ isShallow(source);
+ isReadonlySource = /* @__PURE__ */ isReadonly(source);
+ source = shallowReadArray(source);
+ }
+ ret = new Array(source.length);
+ for (let i = 0, l = source.length; i < l; i++) {
+ ret[i] = renderItem(
+ needsWrap ? isReadonlySource ? toReadonly(toReactive(source[i])) : toReactive(source[i]) : source[i],
+ i,
+ void 0,
+ cached
+ );
+ }
+ } else if (typeof source === "number") {
+ ret = new Array(source);
+ for (let i = 0; i < source; i++) {
+ ret[i] = renderItem(i + 1, i, void 0, cached);
+ }
+ } else if (isObject$1(source)) {
+ if (source[Symbol.iterator]) {
+ ret = Array.from(
+ source,
+ (item, i) => renderItem(item, i, void 0, cached)
+ );
+ } else {
+ const keys2 = Object.keys(source);
+ ret = new Array(keys2.length);
+ for (let i = 0, l = keys2.length; i < l; i++) {
+ const key = keys2[i];
+ ret[i] = renderItem(source[key], key, i, cached);
+ }
+ }
+ } else {
+ ret = [];
+ }
+ return ret;
+}
function renderSlot(slots, name, props = {}, fallback, noSlotted) {
if (currentRenderingInstance.ce || currentRenderingInstance.parent && isAsyncWrapper(currentRenderingInstance.parent) && currentRenderingInstance.parent.ce) {
const hasProps = Object.keys(props).length > 0;
@@ -2634,7 +2750,7 @@ const PublicInstanceProxyHandlers = {
}
};
function normalizePropsOrEmits(props) {
- return isArray(props) ? props.reduce(
+ return isArray$1(props) ? props.reduce(
(normalized, p2) => (normalized[p2] = null, normalized),
{}
) : props;
@@ -2735,7 +2851,7 @@ function applyOptions(instance) {
callHook(created, instance, "c");
}
function registerLifecycleHook(register, hook) {
- if (isArray(hook)) {
+ if (isArray$1(hook)) {
hook.forEach((_hook) => register(_hook.bind(publicThis)));
} else if (hook) {
register(hook.bind(publicThis));
@@ -2753,7 +2869,7 @@ function applyOptions(instance) {
registerLifecycleHook(onBeforeUnmount, beforeUnmount);
registerLifecycleHook(onUnmounted, unmounted);
registerLifecycleHook(onServerPrefetch, serverPrefetch);
- if (isArray(expose)) {
+ if (isArray$1(expose)) {
if (expose.length) {
const exposed = instance.exposed || (instance.exposed = {});
expose.forEach((key) => {
@@ -2780,7 +2896,7 @@ function applyOptions(instance) {
}
}
function resolveInjections(injectOptions, ctx, checkDuplicateProperties = NOOP) {
- if (isArray(injectOptions)) {
+ if (isArray$1(injectOptions)) {
injectOptions = normalizeInject(injectOptions);
}
for (const key in injectOptions) {
@@ -2813,7 +2929,7 @@ function resolveInjections(injectOptions, ctx, checkDuplicateProperties = NOOP)
}
function callHook(hook, instance, type) {
callWithAsyncErrorHandling(
- isArray(hook) ? hook.map((h2) => h2.bind(instance.proxy)) : hook.bind(instance.proxy),
+ isArray$1(hook) ? hook.map((h2) => h2.bind(instance.proxy)) : hook.bind(instance.proxy),
instance,
type
);
@@ -2832,7 +2948,7 @@ function createWatcher(raw, ctx, publicThis, key) {
watch(getter, raw.bind(publicThis));
}
} else if (isObject$1(raw)) {
- if (isArray(raw)) {
+ if (isArray$1(raw)) {
raw.forEach((r) => createWatcher(r, ctx, publicThis, key));
} else {
const handler = isFunction$1(raw.handler) ? raw.handler.bind(publicThis) : ctx[raw.handler];
@@ -2862,24 +2978,24 @@ function resolveMergedOptions(instance) {
resolved = {};
if (globalMixins.length) {
globalMixins.forEach(
- (m2) => mergeOptions(resolved, m2, optionMergeStrategies, true)
+ (m2) => mergeOptions$1(resolved, m2, optionMergeStrategies, true)
);
}
- mergeOptions(resolved, base2, optionMergeStrategies);
+ mergeOptions$1(resolved, base2, optionMergeStrategies);
}
if (isObject$1(base2)) {
cache.set(base2, resolved);
}
return resolved;
}
-function mergeOptions(to, from2, strats, asMixin = false) {
+function mergeOptions$1(to, from2, strats, asMixin = false) {
const { mixins, extends: extendsOptions } = from2;
if (extendsOptions) {
- mergeOptions(to, extendsOptions, strats, true);
+ mergeOptions$1(to, extendsOptions, strats, true);
}
if (mixins) {
mixins.forEach(
- (m2) => mergeOptions(to, m2, strats, true)
+ (m2) => mergeOptions$1(to, m2, strats, true)
);
}
for (const key in from2) {
@@ -2940,7 +3056,7 @@ function mergeInject(to, from2) {
return mergeObjectOptions(normalizeInject(to), normalizeInject(from2));
}
function normalizeInject(raw) {
- if (isArray(raw)) {
+ if (isArray$1(raw)) {
const res = {};
for (let i = 0; i < raw.length; i++) {
res[raw[i]] = raw[i];
@@ -2957,7 +3073,7 @@ function mergeObjectOptions(to, from2) {
}
function mergeEmitsOrPropsOptions(to, from2) {
if (to) {
- if (isArray(to) && isArray(from2)) {
+ if (isArray$1(to) && isArray$1(from2)) {
return [.../* @__PURE__ */ new Set([...to, ...from2])];
}
return extend(
@@ -3012,7 +3128,7 @@ function createAppAPI(render, hydrate) {
const installedPlugins = /* @__PURE__ */ new WeakSet();
const pluginCleanupFns = [];
let isMounted = false;
- const app = context.app = {
+ const app2 = context.app = {
_uid: uid$1++,
_component: rootComponent,
_props: rootProps,
@@ -3029,12 +3145,12 @@ function createAppAPI(render, hydrate) {
if (installedPlugins.has(plugin)) ;
else if (plugin && isFunction$1(plugin.install)) {
installedPlugins.add(plugin);
- plugin.install(app, ...options);
+ plugin.install(app2, ...options);
} else if (isFunction$1(plugin)) {
installedPlugins.add(plugin);
- plugin(app, ...options);
+ plugin(app2, ...options);
} else ;
- return app;
+ return app2;
},
mixin(mixin) {
{
@@ -3042,25 +3158,25 @@ function createAppAPI(render, hydrate) {
context.mixins.push(mixin);
}
}
- return app;
+ return app2;
},
component(name, component) {
if (!component) {
return context.components[name];
}
context.components[name] = component;
- return app;
+ return app2;
},
directive(name, directive) {
if (!directive) {
return context.directives[name];
}
context.directives[name] = directive;
- return app;
+ return app2;
},
mount(rootContainer, isHydrate, namespace) {
if (!isMounted) {
- const vnode = app._ceVNode || createVNode(rootComponent, rootProps);
+ const vnode = app2._ceVNode || createVNode(rootComponent, rootProps);
vnode.appContext = context;
if (namespace === true) {
namespace = "svg";
@@ -3071,8 +3187,8 @@ function createAppAPI(render, hydrate) {
render(vnode, rootContainer, namespace);
}
isMounted = true;
- app._container = rootContainer;
- rootContainer.__vue_app__ = app;
+ app2._container = rootContainer;
+ rootContainer.__vue_app__ = app2;
return getComponentPublicInstance(vnode.component);
}
},
@@ -3083,20 +3199,20 @@ function createAppAPI(render, hydrate) {
if (isMounted) {
callWithAsyncErrorHandling(
pluginCleanupFns,
- app._instance,
+ app2._instance,
16
);
- render(null, app._container);
- delete app._container.__vue_app__;
+ render(null, app2._container);
+ delete app2._container.__vue_app__;
}
},
provide(key, value) {
context.provides[key] = value;
- return app;
+ return app2;
},
runWithContext(fn) {
const lastApp = currentApp;
- currentApp = app;
+ currentApp = app2;
try {
return fn();
} finally {
@@ -3104,7 +3220,7 @@ function createAppAPI(render, hydrate) {
}
}
};
- return app;
+ return app2;
};
}
let currentApp = null;
@@ -3189,7 +3305,7 @@ function normalizeEmitsOptions(comp, appContext, asMixin = false) {
}
return null;
}
- if (isArray(raw)) {
+ if (isArray$1(raw)) {
raw.forEach((key) => normalized[key] = null);
} else {
extend(normalized, raw);
@@ -3636,7 +3752,7 @@ function normalizePropsOptions(comp, appContext, asMixin = false) {
}
return EMPTY_ARR;
}
- if (isArray(raw)) {
+ if (isArray$1(raw)) {
for (let i = 0; i < raw.length; i++) {
const normalizedKey = camelize(raw[i]);
if (validatePropName(normalizedKey)) {
@@ -3648,11 +3764,11 @@ function normalizePropsOptions(comp, appContext, asMixin = false) {
const normalizedKey = camelize(key);
if (validatePropName(normalizedKey)) {
const opt = raw[key];
- const prop = normalized[normalizedKey] = isArray(opt) || isFunction$1(opt) ? { type: opt } : extend({}, opt);
+ const prop = normalized[normalizedKey] = isArray$1(opt) || isFunction$1(opt) ? { type: opt } : extend({}, opt);
const propType = prop.type;
let shouldCast = false;
let shouldCastTrue = true;
- if (isArray(propType)) {
+ if (isArray$1(propType)) {
for (let index2 = 0; index2 < propType.length; ++index2) {
const type = propType[index2];
const typeName = isFunction$1(type) && type.name;
@@ -3693,8 +3809,8 @@ function validatePropName(key) {
return false;
}
const isInternalKey = (key) => key === "_" || key === "_ctx" || key === "$stable";
-const normalizeSlotValue = (value) => isArray(value) ? value.map(normalizeVNode) : [normalizeVNode(value)];
-const normalizeSlot = (key, rawSlot, ctx) => {
+const normalizeSlotValue = (value) => isArray$1(value) ? value.map(normalizeVNode) : [normalizeVNode(value)];
+const normalizeSlot$1 = (key, rawSlot, ctx) => {
if (rawSlot._n) {
return rawSlot;
}
@@ -3711,7 +3827,7 @@ const normalizeObjectSlots = (rawSlots, slots, instance) => {
if (isInternalKey(key)) continue;
const value = rawSlots[key];
if (isFunction$1(value)) {
- slots[key] = normalizeSlot(key, value, ctx);
+ slots[key] = normalizeSlot$1(key, value, ctx);
} else if (value != null) {
const normalized = normalizeSlotValue(value);
slots[key] = () => normalized;
@@ -5049,7 +5165,7 @@ function needTransition(parentSuspense, transition) {
function traverseStaticChildren(n1, n2, shallow = false) {
const ch1 = n1.children;
const ch2 = n2.children;
- if (isArray(ch1) && isArray(ch2)) {
+ if (isArray$1(ch1) && isArray$1(ch2)) {
for (let i = 0; i < ch1.length; i++) {
const c1 = ch1[i];
let c2 = ch2[i];
@@ -5142,7 +5258,7 @@ function resolveAsyncComponentPlaceholder(anchorVnode) {
const isSuspense = (type) => type.__isSuspense;
function queueEffectWithSuspense(fn, suspense) {
if (suspense && suspense.pendingBranch) {
- if (isArray(fn)) {
+ if (isArray$1(fn)) {
suspense.effects.push(...fn);
} else {
suspense.effects.push(fn);
@@ -5307,7 +5423,7 @@ function _createVNode(type, props = null, children = null, patchFlag = 0, dynami
props.class = normalizeClass(klass);
}
if (isObject$1(style2)) {
- if (/* @__PURE__ */ isProxy(style2) && !isArray(style2)) {
+ if (/* @__PURE__ */ isProxy(style2) && !isArray$1(style2)) {
style2 = extend({}, style2);
}
props.style = normalizeStyle(style2);
@@ -5342,7 +5458,7 @@ function cloneVNode(vnode, extraProps, mergeRef = false, cloneTransition = false
// #2078 in the case of
// if the vnode itself already has a ref, cloneVNode will need to merge
// the refs so the single vnode can be set on multiple refs
- mergeRef && ref3 ? isArray(ref3) ? ref3.concat(normalizeRef(extraProps)) : [ref3, normalizeRef(extraProps)] : normalizeRef(extraProps)
+ mergeRef && ref3 ? isArray$1(ref3) ? ref3.concat(normalizeRef(extraProps)) : [ref3, normalizeRef(extraProps)] : normalizeRef(extraProps)
) : ref3,
scopeId: vnode.scopeId,
slotScopeIds: vnode.slotScopeIds,
@@ -5393,7 +5509,7 @@ function createCommentVNode(text = "", asBlock = false) {
function normalizeVNode(child) {
if (child == null || typeof child === "boolean") {
return createVNode(Comment);
- } else if (isArray(child)) {
+ } else if (isArray$1(child)) {
return createVNode(
Fragment$1,
null,
@@ -5414,7 +5530,7 @@ function normalizeChildren(vnode, children) {
const { shapeFlag } = vnode;
if (children == null) {
children = null;
- } else if (isArray(children)) {
+ } else if (isArray$1(children)) {
type = 16;
} else if (typeof children === "object") {
if (shapeFlag & (1 | 64)) {
@@ -5468,7 +5584,7 @@ function mergeProps(...args) {
} else if (isOn(key)) {
const existing = ret[key];
const incoming = toMerge[key];
- if (incoming && existing !== incoming && !(isArray(existing) && existing.includes(incoming))) {
+ if (incoming && existing !== incoming && !(isArray$1(existing) && existing.includes(incoming))) {
ret[key] = existing ? [].concat(existing, incoming) : incoming;
}
} else if (key !== "") {
@@ -5772,7 +5888,7 @@ function h$1(type, propsOrChildren, children) {
setBlockTracking(-1);
const l = arguments.length;
if (l === 2) {
- if (isObject$1(propsOrChildren) && !isArray(propsOrChildren)) {
+ if (isObject$1(propsOrChildren) && !isArray$1(propsOrChildren)) {
if (isVNode(propsOrChildren)) {
return createVNode(type, null, [propsOrChildren]);
}
@@ -5940,7 +6056,7 @@ function patchStyle(el, prev, next) {
}
const importantRE = /\s*!important$/;
function setStyle(style2, name, val) {
- if (isArray(val)) {
+ if (isArray$1(val)) {
val.forEach((v2) => setStyle(style2, name, v2));
} else {
if (val == null) val = "";
@@ -6105,7 +6221,7 @@ function createInvoker(initialValue, instance) {
return invoker;
}
function patchStopImmediatePropagation(e, value) {
- if (isArray(value)) {
+ if (isArray$1(value)) {
const originalStop = e.stopImmediatePropagation;
e.stopImmediatePropagation = () => {
originalStop.call(e);
@@ -6191,12 +6307,12 @@ function ensureRenderer() {
return renderer || (renderer = createRenderer(rendererOptions));
}
const createApp = ((...args) => {
- const app = ensureRenderer().createApp(...args);
- const { mount } = app;
- app.mount = (containerOrSelector) => {
+ const app2 = ensureRenderer().createApp(...args);
+ const { mount } = app2;
+ app2.mount = (containerOrSelector) => {
const container = normalizeContainer(containerOrSelector);
if (!container) return;
- const component = app._component;
+ const component = app2._component;
if (!isFunction$1(component) && !component.render && !component.template) {
component.template = container.innerHTML;
}
@@ -6210,7 +6326,7 @@ const createApp = ((...args) => {
}
return proxy;
};
- return app;
+ return app2;
});
function resolveRootNamespace(container) {
if (container instanceof SVGElement) {
@@ -7555,7 +7671,7 @@ var TempusImpl = class {
}
};
var Tempus = new TempusImpl();
-const _sfc_main$2 = {
+const _sfc_main$6 = {
__name: "Lenis",
props: {
root: {
@@ -8810,6 +8926,1920 @@ function useWindowSize(options = {}) {
height
};
}
+const _sfc_main$5 = {
+ __name: "App",
+ setup(__props) {
+ const { height } = /* @__PURE__ */ useWindowSize();
+ const classes = computed(() => [
+ "container",
+ { "fonts-ready": !fontsLoading.value },
+ "theme-dark"
+ ]);
+ const fontsLoading = /* @__PURE__ */ ref(true);
+ onMounted(async () => {
+ loadFonts([
+ {
+ name: "Leibniz Fraktur",
+ weights: [400]
+ },
+ {
+ name: "Geist Mono",
+ weights: [400, 700]
+ }
+ ]).then(() => {
+ fontsLoading.value = false;
+ }).catch(() => {
+ fontsLoading.value = false;
+ });
+ });
+ const styles = computed(() => ({
+ "--vh": height.value ? height.value / 100 + "px" : "100vh"
+ }));
+ return (_ctx, _cache) => {
+ const _component_router_view = resolveComponent("router-view");
+ return openBlock(), createBlock(_sfc_main$6, {
+ root: "",
+ options: { duration: 1 }
+ }, {
+ default: withCtx(() => [
+ createBaseVNode("div", {
+ class: normalizeClass(classes.value),
+ style: normalizeStyle(styles.value)
+ }, [
+ (openBlock(), createBlock(_component_router_view, {
+ key: _ctx.$route.fullPath
+ }))
+ ], 6)
+ ]),
+ _: 1
+ });
+ };
+ }
+};
+const isBrowser = typeof document !== "undefined";
+function isRouteComponent(component) {
+ return typeof component === "object" || "displayName" in component || "props" in component || "__vccOpts" in component;
+}
+function isESModule(obj) {
+ return obj.__esModule || obj[Symbol.toStringTag] === "Module" || obj.default && isRouteComponent(obj.default);
+}
+const assign$1 = Object.assign;
+function applyToParams(fn, params) {
+ const newParams = {};
+ for (const key in params) {
+ const value = params[key];
+ newParams[key] = isArray(value) ? value.map(fn) : fn(value);
+ }
+ return newParams;
+}
+const noop$1 = () => {
+};
+const isArray = Array.isArray;
+function mergeOptions(defaults2, partialOptions) {
+ const options = {};
+ for (const key in defaults2) options[key] = key in partialOptions ? partialOptions[key] : defaults2[key];
+ return options;
+}
+let ErrorTypes = /* @__PURE__ */ (function(ErrorTypes2) {
+ ErrorTypes2[ErrorTypes2["MATCHER_NOT_FOUND"] = 1] = "MATCHER_NOT_FOUND";
+ ErrorTypes2[ErrorTypes2["NAVIGATION_GUARD_REDIRECT"] = 2] = "NAVIGATION_GUARD_REDIRECT";
+ ErrorTypes2[ErrorTypes2["NAVIGATION_ABORTED"] = 4] = "NAVIGATION_ABORTED";
+ ErrorTypes2[ErrorTypes2["NAVIGATION_CANCELLED"] = 8] = "NAVIGATION_CANCELLED";
+ ErrorTypes2[ErrorTypes2["NAVIGATION_DUPLICATED"] = 16] = "NAVIGATION_DUPLICATED";
+ return ErrorTypes2;
+})({});
+const NavigationFailureSymbol = /* @__PURE__ */ Symbol("");
+({
+ [ErrorTypes.MATCHER_NOT_FOUND]({ location: location2, currentLocation }) {
+ return `No match for
+ ${JSON.stringify(location2)}${currentLocation ? "\nwhile being at\n" + JSON.stringify(currentLocation) : ""}`;
+ },
+ [ErrorTypes.NAVIGATION_GUARD_REDIRECT]({ from: from2, to }) {
+ return `Redirected from "${from2.fullPath}" to "${stringifyRoute(to)}" via a navigation guard.`;
+ },
+ [ErrorTypes.NAVIGATION_ABORTED]({ from: from2, to }) {
+ return `Navigation aborted from "${from2.fullPath}" to "${to.fullPath}" via a navigation guard.`;
+ },
+ [ErrorTypes.NAVIGATION_CANCELLED]({ from: from2, to }) {
+ return `Navigation cancelled from "${from2.fullPath}" to "${to.fullPath}" with a new navigation.`;
+ },
+ [ErrorTypes.NAVIGATION_DUPLICATED]({ from: from2, to }) {
+ return `Avoided redundant navigation to current location: "${from2.fullPath}".`;
+ }
+});
+function createRouterError(type, params) {
+ return assign$1(/* @__PURE__ */ new Error(), {
+ type,
+ [NavigationFailureSymbol]: true
+ }, params);
+}
+function isNavigationFailure(error, type) {
+ return error instanceof Error && NavigationFailureSymbol in error && (type == null || !!(error.type & type));
+}
+const propertiesToLog = [
+ "params",
+ "query",
+ "hash"
+];
+function stringifyRoute(to) {
+ if (typeof to === "string") return to;
+ if (to.path != null) return to.path;
+ const location2 = {};
+ for (const key of propertiesToLog) if (key in to) location2[key] = to[key];
+ return JSON.stringify(location2, null, 2);
+}
+const matchedRouteKey = /* @__PURE__ */ Symbol("");
+const viewDepthKey = /* @__PURE__ */ Symbol("");
+const routerKey = /* @__PURE__ */ Symbol("");
+const routeLocationKey = /* @__PURE__ */ Symbol("");
+const routerViewLocationKey = /* @__PURE__ */ Symbol("");
+function useRouter() {
+ return inject(routerKey);
+}
+function useRoute(_name) {
+ return inject(routeLocationKey);
+}
+const HASH_RE = /#/g;
+const AMPERSAND_RE = /&/g;
+const SLASH_RE = /\//g;
+const EQUAL_RE = /=/g;
+const IM_RE = /\?/g;
+const PLUS_RE = /\+/g;
+const ENC_BRACKET_OPEN_RE = /%5B/g;
+const ENC_BRACKET_CLOSE_RE = /%5D/g;
+const ENC_CARET_RE = /%5E/g;
+const ENC_BACKTICK_RE = /%60/g;
+const ENC_CURLY_OPEN_RE = /%7B/g;
+const ENC_PIPE_RE = /%7C/g;
+const ENC_CURLY_CLOSE_RE = /%7D/g;
+const ENC_SPACE_RE = /%20/g;
+function commonEncode(text) {
+ return text == null ? "" : encodeURI("" + text).replace(ENC_PIPE_RE, "|").replace(ENC_BRACKET_OPEN_RE, "[").replace(ENC_BRACKET_CLOSE_RE, "]");
+}
+function encodeHash(text) {
+ return commonEncode(text).replace(ENC_CURLY_OPEN_RE, "{").replace(ENC_CURLY_CLOSE_RE, "}").replace(ENC_CARET_RE, "^");
+}
+function encodeQueryValue(text) {
+ return commonEncode(text).replace(PLUS_RE, "%2B").replace(ENC_SPACE_RE, "+").replace(HASH_RE, "%23").replace(AMPERSAND_RE, "%26").replace(ENC_BACKTICK_RE, "`").replace(ENC_CURLY_OPEN_RE, "{").replace(ENC_CURLY_CLOSE_RE, "}").replace(ENC_CARET_RE, "^");
+}
+function encodeQueryKey(text) {
+ return encodeQueryValue(text).replace(EQUAL_RE, "%3D");
+}
+function encodePath(text) {
+ return commonEncode(text).replace(HASH_RE, "%23").replace(IM_RE, "%3F");
+}
+function encodeParam(text) {
+ return encodePath(text).replace(SLASH_RE, "%2F");
+}
+function decode(text) {
+ if (text == null) return null;
+ try {
+ return decodeURIComponent("" + text);
+ } catch (err) {
+ }
+ return "" + text;
+}
+const TRAILING_SLASH_RE = /\/$/;
+const removeTrailingSlash = (path) => path.replace(TRAILING_SLASH_RE, "");
+function parseURL(parseQuery2, location2, currentLocation = "/") {
+ let path, query = {}, searchString = "", hash = "";
+ const hashPos = location2.indexOf("#");
+ let searchPos = location2.indexOf("?");
+ searchPos = hashPos >= 0 && searchPos > hashPos ? -1 : searchPos;
+ if (searchPos >= 0) {
+ path = location2.slice(0, searchPos);
+ searchString = location2.slice(searchPos, hashPos > 0 ? hashPos : location2.length);
+ query = parseQuery2(searchString.slice(1));
+ }
+ if (hashPos >= 0) {
+ path = path || location2.slice(0, hashPos);
+ hash = location2.slice(hashPos, location2.length);
+ }
+ path = resolveRelativePath(path != null ? path : location2, currentLocation);
+ return {
+ fullPath: path + searchString + hash,
+ path,
+ query,
+ hash: decode(hash)
+ };
+}
+function stringifyURL(stringifyQuery2, location2) {
+ const query = location2.query ? stringifyQuery2(location2.query) : "";
+ return location2.path + (query && "?") + query + (location2.hash || "");
+}
+function stripBase(pathname, base2) {
+ if (!base2 || !pathname.toLowerCase().startsWith(base2.toLowerCase())) return pathname;
+ return pathname.slice(base2.length) || "/";
+}
+function isSameRouteLocation(stringifyQuery2, a, b2) {
+ const aLastIndex = a.matched.length - 1;
+ const bLastIndex = b2.matched.length - 1;
+ return aLastIndex > -1 && aLastIndex === bLastIndex && isSameRouteRecord(a.matched[aLastIndex], b2.matched[bLastIndex]) && isSameRouteLocationParams(a.params, b2.params) && stringifyQuery2(a.query) === stringifyQuery2(b2.query) && a.hash === b2.hash;
+}
+function isSameRouteRecord(a, b2) {
+ return (a.aliasOf || a) === (b2.aliasOf || b2);
+}
+function isSameRouteLocationParams(a, b2) {
+ if (Object.keys(a).length !== Object.keys(b2).length) return false;
+ for (var key in a) if (!isSameRouteLocationParamsValue(a[key], b2[key])) return false;
+ return true;
+}
+function isSameRouteLocationParamsValue(a, b2) {
+ return isArray(a) ? isEquivalentArray(a, b2) : isArray(b2) ? isEquivalentArray(b2, a) : (a && a.valueOf()) === (b2 && b2.valueOf());
+}
+function isEquivalentArray(a, b2) {
+ return isArray(b2) ? a.length === b2.length && a.every((value, i) => value === b2[i]) : a.length === 1 && a[0] === b2;
+}
+function resolveRelativePath(to, from2) {
+ if (to.startsWith("/")) return to;
+ if (!to) return from2;
+ const fromSegments = from2.split("/");
+ const toSegments = to.split("/");
+ const lastToSegment = toSegments[toSegments.length - 1];
+ if (lastToSegment === ".." || lastToSegment === ".") toSegments.push("");
+ let position = fromSegments.length - 1;
+ let toPosition;
+ let segment;
+ for (toPosition = 0; toPosition < toSegments.length; toPosition++) {
+ segment = toSegments[toPosition];
+ if (segment === ".") continue;
+ if (segment === "..") {
+ if (position > 1) position--;
+ } else break;
+ }
+ return fromSegments.slice(0, position).join("/") + "/" + toSegments.slice(toPosition).join("/");
+}
+const START_LOCATION_NORMALIZED = {
+ path: "/",
+ name: void 0,
+ params: {},
+ query: {},
+ hash: "",
+ fullPath: "/",
+ matched: [],
+ meta: {},
+ redirectedFrom: void 0
+};
+let NavigationType = /* @__PURE__ */ (function(NavigationType2) {
+ NavigationType2["pop"] = "pop";
+ NavigationType2["push"] = "push";
+ return NavigationType2;
+})({});
+let NavigationDirection = /* @__PURE__ */ (function(NavigationDirection2) {
+ NavigationDirection2["back"] = "back";
+ NavigationDirection2["forward"] = "forward";
+ NavigationDirection2["unknown"] = "";
+ return NavigationDirection2;
+})({});
+function normalizeBase(base2) {
+ if (!base2) if (isBrowser) {
+ const baseEl = document.querySelector("base");
+ base2 = baseEl && baseEl.getAttribute("href") || "/";
+ base2 = base2.replace(/^\w+:\/\/[^\/]+/, "");
+ } else base2 = "/";
+ if (base2[0] !== "/" && base2[0] !== "#") base2 = "/" + base2;
+ return removeTrailingSlash(base2);
+}
+const BEFORE_HASH_RE = /^[^#]+#/;
+function createHref(base2, location2) {
+ return base2.replace(BEFORE_HASH_RE, "#") + location2;
+}
+function getElementPosition(el, offset2) {
+ const docRect = document.documentElement.getBoundingClientRect();
+ const elRect = el.getBoundingClientRect();
+ return {
+ behavior: offset2.behavior,
+ left: elRect.left - docRect.left - (offset2.left || 0),
+ top: elRect.top - docRect.top - (offset2.top || 0)
+ };
+}
+const computeScrollPosition = () => ({
+ left: window.scrollX,
+ top: window.scrollY
+});
+function scrollToPosition(position) {
+ let scrollToOptions;
+ if ("el" in position) {
+ const positionEl = position.el;
+ const isIdSelector = typeof positionEl === "string" && positionEl.startsWith("#");
+ const el = typeof positionEl === "string" ? isIdSelector ? document.getElementById(positionEl.slice(1)) : document.querySelector(positionEl) : positionEl;
+ if (!el) {
+ return;
+ }
+ scrollToOptions = getElementPosition(el, position);
+ } else scrollToOptions = position;
+ if ("scrollBehavior" in document.documentElement.style) window.scrollTo(scrollToOptions);
+ else window.scrollTo(scrollToOptions.left != null ? scrollToOptions.left : window.scrollX, scrollToOptions.top != null ? scrollToOptions.top : window.scrollY);
+}
+function getScrollKey(path, delta) {
+ return (history.state ? history.state.position - delta : -1) + path;
+}
+const scrollPositions = /* @__PURE__ */ new Map();
+function saveScrollPosition(key, scrollPosition) {
+ scrollPositions.set(key, scrollPosition);
+}
+function getSavedScrollPosition(key) {
+ const scroll = scrollPositions.get(key);
+ scrollPositions.delete(key);
+ return scroll;
+}
+function isRouteLocation(route) {
+ return typeof route === "string" || route && typeof route === "object";
+}
+function isRouteName(name) {
+ return typeof name === "string" || typeof name === "symbol";
+}
+function parseQuery(search) {
+ const query = {};
+ if (search === "" || search === "?") return query;
+ const searchParams = (search[0] === "?" ? search.slice(1) : search).split("&");
+ for (let i = 0; i < searchParams.length; ++i) {
+ const searchParam = searchParams[i].replace(PLUS_RE, " ");
+ const eqPos = searchParam.indexOf("=");
+ const key = decode(eqPos < 0 ? searchParam : searchParam.slice(0, eqPos));
+ const value = eqPos < 0 ? null : decode(searchParam.slice(eqPos + 1));
+ if (key in query) {
+ let currentValue = query[key];
+ if (!isArray(currentValue)) currentValue = query[key] = [currentValue];
+ currentValue.push(value);
+ } else query[key] = value;
+ }
+ return query;
+}
+function stringifyQuery(query) {
+ let search = "";
+ for (let key in query) {
+ const value = query[key];
+ key = encodeQueryKey(key);
+ if (value == null) {
+ if (value !== void 0) search += (search.length ? "&" : "") + key;
+ continue;
+ }
+ (isArray(value) ? value.map((v2) => v2 && encodeQueryValue(v2)) : [value && encodeQueryValue(value)]).forEach((value2) => {
+ if (value2 !== void 0) {
+ search += (search.length ? "&" : "") + key;
+ if (value2 != null) search += "=" + value2;
+ }
+ });
+ }
+ return search;
+}
+function normalizeQuery(query) {
+ const normalizedQuery = {};
+ for (const key in query) {
+ const value = query[key];
+ if (value !== void 0) normalizedQuery[key] = isArray(value) ? value.map((v2) => v2 == null ? null : "" + v2) : value == null ? value : "" + value;
+ }
+ return normalizedQuery;
+}
+function useCallbacks() {
+ let handlers2 = [];
+ function add(handler) {
+ handlers2.push(handler);
+ return () => {
+ const i = handlers2.indexOf(handler);
+ if (i > -1) handlers2.splice(i, 1);
+ };
+ }
+ function reset2() {
+ handlers2 = [];
+ }
+ return {
+ add,
+ list: () => handlers2.slice(),
+ reset: reset2
+ };
+}
+function guardToPromiseFn(guard, to, from2, record, name, runWithContext = (fn) => fn()) {
+ const enterCallbackArray = record && (record.enterCallbacks[name] = record.enterCallbacks[name] || []);
+ return () => new Promise((resolve2, reject) => {
+ const next = (valid) => {
+ if (valid === false) reject(createRouterError(ErrorTypes.NAVIGATION_ABORTED, {
+ from: from2,
+ to
+ }));
+ else if (valid instanceof Error) reject(valid);
+ else if (isRouteLocation(valid)) reject(createRouterError(ErrorTypes.NAVIGATION_GUARD_REDIRECT, {
+ from: to,
+ to: valid
+ }));
+ else {
+ if (enterCallbackArray && record.enterCallbacks[name] === enterCallbackArray && typeof valid === "function") enterCallbackArray.push(valid);
+ resolve2();
+ }
+ };
+ const guardReturn = runWithContext(() => guard.call(record && record.instances[name], to, from2, next));
+ let guardCall = Promise.resolve(guardReturn);
+ if (guard.length < 3) guardCall = guardCall.then(next);
+ guardCall.catch((err) => reject(err));
+ });
+}
+function extractComponentsGuards(matched, guardType, to, from2, runWithContext = (fn) => fn()) {
+ const guards = [];
+ for (const record of matched) {
+ for (const name in record.components) {
+ let rawComponent = record.components[name];
+ if (guardType !== "beforeRouteEnter" && !record.instances[name]) continue;
+ if (isRouteComponent(rawComponent)) {
+ const guard = (rawComponent.__vccOpts || rawComponent)[guardType];
+ guard && guards.push(guardToPromiseFn(guard, to, from2, record, name, runWithContext));
+ } else {
+ let componentPromise = rawComponent();
+ guards.push(() => componentPromise.then((resolved) => {
+ if (!resolved) throw new Error(`Couldn't resolve component "${name}" at "${record.path}"`);
+ const resolvedComponent = isESModule(resolved) ? resolved.default : resolved;
+ record.mods[name] = resolved;
+ record.components[name] = resolvedComponent;
+ const guard = (resolvedComponent.__vccOpts || resolvedComponent)[guardType];
+ return guard && guardToPromiseFn(guard, to, from2, record, name, runWithContext)();
+ }));
+ }
+ }
+ }
+ return guards;
+}
+function extractChangingRecords(to, from2) {
+ const leavingRecords = [];
+ const updatingRecords = [];
+ const enteringRecords = [];
+ const len = Math.max(from2.matched.length, to.matched.length);
+ for (let i = 0; i < len; i++) {
+ const recordFrom = from2.matched[i];
+ if (recordFrom) if (to.matched.find((record) => isSameRouteRecord(record, recordFrom))) updatingRecords.push(recordFrom);
+ else leavingRecords.push(recordFrom);
+ const recordTo = to.matched[i];
+ if (recordTo) {
+ if (!from2.matched.find((record) => isSameRouteRecord(record, recordTo))) enteringRecords.push(recordTo);
+ }
+ }
+ return [
+ leavingRecords,
+ updatingRecords,
+ enteringRecords
+ ];
+}
+let createBaseLocation = () => location.protocol + "//" + location.host;
+function createCurrentLocation(base2, location2) {
+ const { pathname, search, hash } = location2;
+ const hashPos = base2.indexOf("#");
+ if (hashPos > -1) {
+ let slicePos = hash.includes(base2.slice(hashPos)) ? base2.slice(hashPos).length : 1;
+ let pathFromHash = hash.slice(slicePos);
+ if (pathFromHash[0] !== "/") pathFromHash = "/" + pathFromHash;
+ return stripBase(pathFromHash, "");
+ }
+ return stripBase(pathname, base2) + search + hash;
+}
+function useHistoryListeners(base2, historyState, currentLocation, replace2) {
+ let listeners = [];
+ let teardowns = [];
+ let pauseState = null;
+ const popStateHandler = ({ state }) => {
+ const to = createCurrentLocation(base2, location);
+ const from2 = currentLocation.value;
+ const fromState = historyState.value;
+ let delta = 0;
+ if (state) {
+ currentLocation.value = to;
+ historyState.value = state;
+ if (pauseState && pauseState === from2) {
+ pauseState = null;
+ return;
+ }
+ delta = fromState ? state.position - fromState.position : 0;
+ } else replace2(to);
+ listeners.forEach((listener) => {
+ listener(currentLocation.value, from2, {
+ delta,
+ type: NavigationType.pop,
+ direction: delta ? delta > 0 ? NavigationDirection.forward : NavigationDirection.back : NavigationDirection.unknown
+ });
+ });
+ };
+ function pauseListeners() {
+ pauseState = currentLocation.value;
+ }
+ function listen(callback) {
+ listeners.push(callback);
+ const teardown = () => {
+ const index2 = listeners.indexOf(callback);
+ if (index2 > -1) listeners.splice(index2, 1);
+ };
+ teardowns.push(teardown);
+ return teardown;
+ }
+ function beforeUnloadListener() {
+ if (document.visibilityState === "hidden") {
+ const { history: history2 } = window;
+ if (!history2.state) return;
+ history2.replaceState(assign$1({}, history2.state, { scroll: computeScrollPosition() }), "");
+ }
+ }
+ function destroy() {
+ for (const teardown of teardowns) teardown();
+ teardowns = [];
+ window.removeEventListener("popstate", popStateHandler);
+ window.removeEventListener("pagehide", beforeUnloadListener);
+ document.removeEventListener("visibilitychange", beforeUnloadListener);
+ }
+ window.addEventListener("popstate", popStateHandler);
+ window.addEventListener("pagehide", beforeUnloadListener);
+ document.addEventListener("visibilitychange", beforeUnloadListener);
+ return {
+ pauseListeners,
+ listen,
+ destroy
+ };
+}
+function buildState(back, current, forward, replaced = false, computeScroll = false) {
+ return {
+ back,
+ current,
+ forward,
+ replaced,
+ position: window.history.length,
+ scroll: computeScroll ? computeScrollPosition() : null
+ };
+}
+function useHistoryStateNavigation(base2) {
+ const { history: history2, location: location2 } = window;
+ const currentLocation = { value: createCurrentLocation(base2, location2) };
+ const historyState = { value: history2.state };
+ if (!historyState.value) changeLocation(currentLocation.value, {
+ back: null,
+ current: currentLocation.value,
+ forward: null,
+ position: history2.length - 1,
+ replaced: true,
+ scroll: null
+ }, true);
+ function changeLocation(to, state, replace22) {
+ const hashIndex = base2.indexOf("#");
+ const url = hashIndex > -1 ? (location2.host && document.querySelector("base") ? base2 : base2.slice(hashIndex)) + to : createBaseLocation() + base2 + to;
+ try {
+ history2[replace22 ? "replaceState" : "pushState"](state, "", url);
+ historyState.value = state;
+ } catch (err) {
+ console.error(err);
+ location2[replace22 ? "replace" : "assign"](url);
+ }
+ }
+ function replace2(to, data) {
+ changeLocation(to, assign$1({}, history2.state, buildState(historyState.value.back, to, historyState.value.forward, true), data, { position: historyState.value.position }), true);
+ currentLocation.value = to;
+ }
+ function push(to, data) {
+ const currentState = assign$1({}, historyState.value, history2.state, {
+ forward: to,
+ scroll: computeScrollPosition()
+ });
+ changeLocation(currentState.current, currentState, true);
+ changeLocation(to, assign$1({}, buildState(currentLocation.value, to, null), { position: currentState.position + 1 }, data), false);
+ currentLocation.value = to;
+ }
+ return {
+ location: currentLocation,
+ state: historyState,
+ push,
+ replace: replace2
+ };
+}
+function createWebHistory(base2) {
+ base2 = normalizeBase(base2);
+ const historyNavigation = useHistoryStateNavigation(base2);
+ const historyListeners = useHistoryListeners(base2, historyNavigation.state, historyNavigation.location, historyNavigation.replace);
+ function go(delta, triggerListeners = true) {
+ if (!triggerListeners) historyListeners.pauseListeners();
+ history.go(delta);
+ }
+ const routerHistory = assign$1({
+ location: "",
+ base: base2,
+ go,
+ createHref: createHref.bind(null, base2)
+ }, historyNavigation, historyListeners);
+ Object.defineProperty(routerHistory, "location", {
+ enumerable: true,
+ get: () => historyNavigation.location.value
+ });
+ Object.defineProperty(routerHistory, "state", {
+ enumerable: true,
+ get: () => historyNavigation.state.value
+ });
+ return routerHistory;
+}
+let TokenType = /* @__PURE__ */ (function(TokenType2) {
+ TokenType2[TokenType2["Static"] = 0] = "Static";
+ TokenType2[TokenType2["Param"] = 1] = "Param";
+ TokenType2[TokenType2["Group"] = 2] = "Group";
+ return TokenType2;
+})({});
+var TokenizerState = /* @__PURE__ */ (function(TokenizerState2) {
+ TokenizerState2[TokenizerState2["Static"] = 0] = "Static";
+ TokenizerState2[TokenizerState2["Param"] = 1] = "Param";
+ TokenizerState2[TokenizerState2["ParamRegExp"] = 2] = "ParamRegExp";
+ TokenizerState2[TokenizerState2["ParamRegExpEnd"] = 3] = "ParamRegExpEnd";
+ TokenizerState2[TokenizerState2["EscapeNext"] = 4] = "EscapeNext";
+ return TokenizerState2;
+})(TokenizerState || {});
+const ROOT_TOKEN = {
+ type: TokenType.Static,
+ value: ""
+};
+const VALID_PARAM_RE = /[a-zA-Z0-9_]/;
+function tokenizePath(path) {
+ if (!path) return [[]];
+ if (path === "/") return [[ROOT_TOKEN]];
+ if (!path.startsWith("/")) throw new Error(`Invalid path "${path}"`);
+ function crash(message) {
+ throw new Error(`ERR (${state})/"${buffer}": ${message}`);
+ }
+ let state = TokenizerState.Static;
+ let previousState = state;
+ const tokens = [];
+ let segment;
+ function finalizeSegment() {
+ if (segment) tokens.push(segment);
+ segment = [];
+ }
+ let i = 0;
+ let char;
+ let buffer = "";
+ let customRe = "";
+ function consumeBuffer() {
+ if (!buffer) return;
+ if (state === TokenizerState.Static) segment.push({
+ type: TokenType.Static,
+ value: buffer
+ });
+ else if (state === TokenizerState.Param || state === TokenizerState.ParamRegExp || state === TokenizerState.ParamRegExpEnd) {
+ if (segment.length > 1 && (char === "*" || char === "+")) crash(`A repeatable param (${buffer}) must be alone in its segment. eg: '/:ids+.`);
+ segment.push({
+ type: TokenType.Param,
+ value: buffer,
+ regexp: customRe,
+ repeatable: char === "*" || char === "+",
+ optional: char === "*" || char === "?"
+ });
+ } else crash("Invalid state to consume buffer");
+ buffer = "";
+ }
+ function addCharToBuffer() {
+ buffer += char;
+ }
+ while (i < path.length) {
+ char = path[i++];
+ if (char === "\\" && state !== TokenizerState.ParamRegExp) {
+ previousState = state;
+ state = TokenizerState.EscapeNext;
+ continue;
+ }
+ switch (state) {
+ case TokenizerState.Static:
+ if (char === "/") {
+ if (buffer) consumeBuffer();
+ finalizeSegment();
+ } else if (char === ":") {
+ consumeBuffer();
+ state = TokenizerState.Param;
+ } else addCharToBuffer();
+ break;
+ case TokenizerState.EscapeNext:
+ addCharToBuffer();
+ state = previousState;
+ break;
+ case TokenizerState.Param:
+ if (char === "(") state = TokenizerState.ParamRegExp;
+ else if (VALID_PARAM_RE.test(char)) addCharToBuffer();
+ else {
+ consumeBuffer();
+ state = TokenizerState.Static;
+ if (char !== "*" && char !== "?" && char !== "+") i--;
+ }
+ break;
+ case TokenizerState.ParamRegExp:
+ if (char === ")") if (customRe[customRe.length - 1] == "\\") customRe = customRe.slice(0, -1) + char;
+ else state = TokenizerState.ParamRegExpEnd;
+ else customRe += char;
+ break;
+ case TokenizerState.ParamRegExpEnd:
+ consumeBuffer();
+ state = TokenizerState.Static;
+ if (char !== "*" && char !== "?" && char !== "+") i--;
+ customRe = "";
+ break;
+ default:
+ crash("Unknown state");
+ break;
+ }
+ }
+ if (state === TokenizerState.ParamRegExp) crash(`Unfinished custom RegExp for param "${buffer}"`);
+ consumeBuffer();
+ finalizeSegment();
+ return tokens;
+}
+const BASE_PARAM_PATTERN = "[^/]+?";
+const BASE_PATH_PARSER_OPTIONS = {
+ sensitive: false,
+ strict: false,
+ start: true,
+ end: true
+};
+var PathScore = /* @__PURE__ */ (function(PathScore2) {
+ PathScore2[PathScore2["_multiplier"] = 10] = "_multiplier";
+ PathScore2[PathScore2["Root"] = 90] = "Root";
+ PathScore2[PathScore2["Segment"] = 40] = "Segment";
+ PathScore2[PathScore2["SubSegment"] = 30] = "SubSegment";
+ PathScore2[PathScore2["Static"] = 40] = "Static";
+ PathScore2[PathScore2["Dynamic"] = 20] = "Dynamic";
+ PathScore2[PathScore2["BonusCustomRegExp"] = 10] = "BonusCustomRegExp";
+ PathScore2[PathScore2["BonusWildcard"] = -50] = "BonusWildcard";
+ PathScore2[PathScore2["BonusRepeatable"] = -20] = "BonusRepeatable";
+ PathScore2[PathScore2["BonusOptional"] = -8] = "BonusOptional";
+ PathScore2[PathScore2["BonusStrict"] = 0.7000000000000001] = "BonusStrict";
+ PathScore2[PathScore2["BonusCaseSensitive"] = 0.25] = "BonusCaseSensitive";
+ return PathScore2;
+})(PathScore || {});
+const REGEX_CHARS_RE = /[.+*?^${}()[\]/\\]/g;
+function tokensToParser(segments, extraOptions) {
+ const options = assign$1({}, BASE_PATH_PARSER_OPTIONS, extraOptions);
+ const score = [];
+ let pattern = options.start ? "^" : "";
+ const keys2 = [];
+ for (const segment of segments) {
+ const segmentScores = segment.length ? [] : [PathScore.Root];
+ if (options.strict && !segment.length) pattern += "/";
+ for (let tokenIndex = 0; tokenIndex < segment.length; tokenIndex++) {
+ const token2 = segment[tokenIndex];
+ let subSegmentScore = PathScore.Segment + (options.sensitive ? PathScore.BonusCaseSensitive : 0);
+ if (token2.type === TokenType.Static) {
+ if (!tokenIndex) pattern += "/";
+ pattern += token2.value.replace(REGEX_CHARS_RE, "\\$&");
+ subSegmentScore += PathScore.Static;
+ } else if (token2.type === TokenType.Param) {
+ const { value, repeatable, optional, regexp } = token2;
+ keys2.push({
+ name: value,
+ repeatable,
+ optional
+ });
+ const re22 = regexp ? regexp : BASE_PARAM_PATTERN;
+ if (re22 !== BASE_PARAM_PATTERN) {
+ subSegmentScore += PathScore.BonusCustomRegExp;
+ try {
+ new RegExp(`(${re22})`);
+ } catch (err) {
+ throw new Error(`Invalid custom RegExp for param "${value}" (${re22}): ` + err.message);
+ }
+ }
+ let subPattern = repeatable ? `((?:${re22})(?:/(?:${re22}))*)` : `(${re22})`;
+ if (!tokenIndex) subPattern = optional && segment.length < 2 ? `(?:/${subPattern})` : "/" + subPattern;
+ if (optional) subPattern += "?";
+ pattern += subPattern;
+ subSegmentScore += PathScore.Dynamic;
+ if (optional) subSegmentScore += PathScore.BonusOptional;
+ if (repeatable) subSegmentScore += PathScore.BonusRepeatable;
+ if (re22 === ".*") subSegmentScore += PathScore.BonusWildcard;
+ }
+ segmentScores.push(subSegmentScore);
+ }
+ score.push(segmentScores);
+ }
+ if (options.strict && options.end) {
+ const i = score.length - 1;
+ score[i][score[i].length - 1] += PathScore.BonusStrict;
+ }
+ if (!options.strict) pattern += "/?";
+ if (options.end) pattern += "$";
+ else if (options.strict && !pattern.endsWith("/")) pattern += "(?:/|$)";
+ const re2 = new RegExp(pattern, options.sensitive ? "" : "i");
+ function parse(path) {
+ const match = path.match(re2);
+ const params = {};
+ if (!match) return null;
+ for (let i = 1; i < match.length; i++) {
+ const value = match[i] || "";
+ const key = keys2[i - 1];
+ params[key.name] = value && key.repeatable ? value.split("/") : value;
+ }
+ return params;
+ }
+ function stringify(params) {
+ let path = "";
+ let avoidDuplicatedSlash = false;
+ for (const segment of segments) {
+ if (!avoidDuplicatedSlash || !path.endsWith("/")) path += "/";
+ avoidDuplicatedSlash = false;
+ for (const token2 of segment) if (token2.type === TokenType.Static) path += token2.value;
+ else if (token2.type === TokenType.Param) {
+ const { value, repeatable, optional } = token2;
+ const param = value in params ? params[value] : "";
+ if (isArray(param) && !repeatable) throw new Error(`Provided param "${value}" is an array but it is not repeatable (* or + modifiers)`);
+ const text = isArray(param) ? param.join("/") : param;
+ if (!text) if (optional) {
+ if (segment.length < 2) if (path.endsWith("/")) path = path.slice(0, -1);
+ else avoidDuplicatedSlash = true;
+ } else throw new Error(`Missing required param "${value}"`);
+ path += text;
+ }
+ }
+ return path || "/";
+ }
+ return {
+ re: re2,
+ score,
+ keys: keys2,
+ parse,
+ stringify
+ };
+}
+function compareScoreArray(a, b2) {
+ let i = 0;
+ while (i < a.length && i < b2.length) {
+ const diff = b2[i] - a[i];
+ if (diff) return diff;
+ i++;
+ }
+ if (a.length < b2.length) return a.length === 1 && a[0] === PathScore.Static + PathScore.Segment ? -1 : 1;
+ else if (a.length > b2.length) return b2.length === 1 && b2[0] === PathScore.Static + PathScore.Segment ? 1 : -1;
+ return 0;
+}
+function comparePathParserScore(a, b2) {
+ let i = 0;
+ const aScore = a.score;
+ const bScore = b2.score;
+ while (i < aScore.length && i < bScore.length) {
+ const comp = compareScoreArray(aScore[i], bScore[i]);
+ if (comp) return comp;
+ i++;
+ }
+ if (Math.abs(bScore.length - aScore.length) === 1) {
+ if (isLastScoreNegative(aScore)) return 1;
+ if (isLastScoreNegative(bScore)) return -1;
+ }
+ return bScore.length - aScore.length;
+}
+function isLastScoreNegative(score) {
+ const last = score[score.length - 1];
+ return score.length > 0 && last[last.length - 1] < 0;
+}
+const PATH_PARSER_OPTIONS_DEFAULTS = {
+ strict: false,
+ end: true,
+ sensitive: false
+};
+function createRouteRecordMatcher(record, parent, options) {
+ const parser = tokensToParser(tokenizePath(record.path), options);
+ const matcher = assign$1(parser, {
+ record,
+ parent,
+ children: [],
+ alias: []
+ });
+ if (parent) {
+ if (!matcher.record.aliasOf === !parent.record.aliasOf) parent.children.push(matcher);
+ }
+ return matcher;
+}
+function createRouterMatcher(routes2, globalOptions) {
+ const matchers = [];
+ const matcherMap = /* @__PURE__ */ new Map();
+ globalOptions = mergeOptions(PATH_PARSER_OPTIONS_DEFAULTS, globalOptions);
+ function getRecordMatcher(name) {
+ return matcherMap.get(name);
+ }
+ function addRoute(record, parent, originalRecord) {
+ const isRootAdd = !originalRecord;
+ const mainNormalizedRecord = normalizeRouteRecord(record);
+ mainNormalizedRecord.aliasOf = originalRecord && originalRecord.record;
+ const options = mergeOptions(globalOptions, record);
+ const normalizedRecords = [mainNormalizedRecord];
+ if ("alias" in record) {
+ const aliases = typeof record.alias === "string" ? [record.alias] : record.alias;
+ for (const alias of aliases) normalizedRecords.push(normalizeRouteRecord(assign$1({}, mainNormalizedRecord, {
+ components: originalRecord ? originalRecord.record.components : mainNormalizedRecord.components,
+ path: alias,
+ aliasOf: originalRecord ? originalRecord.record : mainNormalizedRecord
+ })));
+ }
+ let matcher;
+ let originalMatcher;
+ for (const normalizedRecord of normalizedRecords) {
+ const { path } = normalizedRecord;
+ if (parent && path[0] !== "/") {
+ const parentPath = parent.record.path;
+ const connectingSlash = parentPath[parentPath.length - 1] === "/" ? "" : "/";
+ normalizedRecord.path = parent.record.path + (path && connectingSlash + path);
+ }
+ matcher = createRouteRecordMatcher(normalizedRecord, parent, options);
+ if (originalRecord) {
+ originalRecord.alias.push(matcher);
+ } else {
+ originalMatcher = originalMatcher || matcher;
+ if (originalMatcher !== matcher) originalMatcher.alias.push(matcher);
+ if (isRootAdd && record.name && !isAliasRecord(matcher)) {
+ removeRoute(record.name);
+ }
+ }
+ if (isMatchable(matcher)) insertMatcher(matcher);
+ if (mainNormalizedRecord.children) {
+ const children = mainNormalizedRecord.children;
+ for (let i = 0; i < children.length; i++) addRoute(children[i], matcher, originalRecord && originalRecord.children[i]);
+ }
+ originalRecord = originalRecord || matcher;
+ }
+ return originalMatcher ? () => {
+ removeRoute(originalMatcher);
+ } : noop$1;
+ }
+ function removeRoute(matcherRef) {
+ if (isRouteName(matcherRef)) {
+ const matcher = matcherMap.get(matcherRef);
+ if (matcher) {
+ matcherMap.delete(matcherRef);
+ matchers.splice(matchers.indexOf(matcher), 1);
+ matcher.children.forEach(removeRoute);
+ matcher.alias.forEach(removeRoute);
+ }
+ } else {
+ const index2 = matchers.indexOf(matcherRef);
+ if (index2 > -1) {
+ matchers.splice(index2, 1);
+ if (matcherRef.record.name) matcherMap.delete(matcherRef.record.name);
+ matcherRef.children.forEach(removeRoute);
+ matcherRef.alias.forEach(removeRoute);
+ }
+ }
+ }
+ function getRoutes() {
+ return matchers;
+ }
+ function insertMatcher(matcher) {
+ const index2 = findInsertionIndex(matcher, matchers);
+ matchers.splice(index2, 0, matcher);
+ if (matcher.record.name && !isAliasRecord(matcher)) matcherMap.set(matcher.record.name, matcher);
+ }
+ function resolve2(location2, currentLocation) {
+ let matcher;
+ let params = {};
+ let path;
+ let name;
+ if ("name" in location2 && location2.name) {
+ matcher = matcherMap.get(location2.name);
+ if (!matcher) throw createRouterError(ErrorTypes.MATCHER_NOT_FOUND, { location: location2 });
+ name = matcher.record.name;
+ params = assign$1(pickParams(currentLocation.params, matcher.keys.filter((k2) => !k2.optional).concat(matcher.parent ? matcher.parent.keys.filter((k2) => k2.optional) : []).map((k2) => k2.name)), location2.params && pickParams(location2.params, matcher.keys.map((k2) => k2.name)));
+ path = matcher.stringify(params);
+ } else if (location2.path != null) {
+ path = location2.path;
+ matcher = matchers.find((m2) => m2.re.test(path));
+ if (matcher) {
+ params = matcher.parse(path);
+ name = matcher.record.name;
+ }
+ } else {
+ matcher = currentLocation.name ? matcherMap.get(currentLocation.name) : matchers.find((m2) => m2.re.test(currentLocation.path));
+ if (!matcher) throw createRouterError(ErrorTypes.MATCHER_NOT_FOUND, {
+ location: location2,
+ currentLocation
+ });
+ name = matcher.record.name;
+ params = assign$1({}, currentLocation.params, location2.params);
+ path = matcher.stringify(params);
+ }
+ const matched = [];
+ let parentMatcher = matcher;
+ while (parentMatcher) {
+ matched.unshift(parentMatcher.record);
+ parentMatcher = parentMatcher.parent;
+ }
+ return {
+ name,
+ path,
+ params,
+ matched,
+ meta: mergeMetaFields(matched)
+ };
+ }
+ routes2.forEach((route) => addRoute(route));
+ function clearRoutes() {
+ matchers.length = 0;
+ matcherMap.clear();
+ }
+ return {
+ addRoute,
+ resolve: resolve2,
+ removeRoute,
+ clearRoutes,
+ getRoutes,
+ getRecordMatcher
+ };
+}
+function pickParams(params, keys2) {
+ const newParams = {};
+ for (const key of keys2) if (key in params) newParams[key] = params[key];
+ return newParams;
+}
+function normalizeRouteRecord(record) {
+ const normalized = {
+ path: record.path,
+ redirect: record.redirect,
+ name: record.name,
+ meta: record.meta || {},
+ aliasOf: record.aliasOf,
+ beforeEnter: record.beforeEnter,
+ props: normalizeRecordProps(record),
+ children: record.children || [],
+ instances: {},
+ leaveGuards: /* @__PURE__ */ new Set(),
+ updateGuards: /* @__PURE__ */ new Set(),
+ enterCallbacks: {},
+ components: "components" in record ? record.components || null : record.component && { default: record.component }
+ };
+ Object.defineProperty(normalized, "mods", { value: {} });
+ return normalized;
+}
+function normalizeRecordProps(record) {
+ const propsObject = {};
+ const props = record.props || false;
+ if ("component" in record) propsObject.default = props;
+ else for (const name in record.components) propsObject[name] = typeof props === "object" ? props[name] : props;
+ return propsObject;
+}
+function isAliasRecord(record) {
+ while (record) {
+ if (record.record.aliasOf) return true;
+ record = record.parent;
+ }
+ return false;
+}
+function mergeMetaFields(matched) {
+ return matched.reduce((meta, record) => assign$1(meta, record.meta), {});
+}
+function findInsertionIndex(matcher, matchers) {
+ let lower = 0;
+ let upper = matchers.length;
+ while (lower !== upper) {
+ const mid = lower + upper >> 1;
+ if (comparePathParserScore(matcher, matchers[mid]) < 0) upper = mid;
+ else lower = mid + 1;
+ }
+ const insertionAncestor = getInsertionAncestor(matcher);
+ if (insertionAncestor) {
+ upper = matchers.lastIndexOf(insertionAncestor, upper - 1);
+ }
+ return upper;
+}
+function getInsertionAncestor(matcher) {
+ let ancestor = matcher;
+ while (ancestor = ancestor.parent) if (isMatchable(ancestor) && comparePathParserScore(matcher, ancestor) === 0) return ancestor;
+}
+function isMatchable({ record }) {
+ return !!(record.name || record.components && Object.keys(record.components).length || record.redirect);
+}
+function useLink(props) {
+ const router2 = inject(routerKey);
+ const currentRoute = inject(routeLocationKey);
+ const route = computed(() => {
+ const to = unref(props.to);
+ return router2.resolve(to);
+ });
+ const activeRecordIndex = computed(() => {
+ const { matched } = route.value;
+ const { length } = matched;
+ const routeMatched = matched[length - 1];
+ const currentMatched = currentRoute.matched;
+ if (!routeMatched || !currentMatched.length) return -1;
+ const index2 = currentMatched.findIndex(isSameRouteRecord.bind(null, routeMatched));
+ if (index2 > -1) return index2;
+ const parentRecordPath = getOriginalPath(matched[length - 2]);
+ return length > 1 && getOriginalPath(routeMatched) === parentRecordPath && currentMatched[currentMatched.length - 1].path !== parentRecordPath ? currentMatched.findIndex(isSameRouteRecord.bind(null, matched[length - 2])) : index2;
+ });
+ const isActive2 = computed(() => activeRecordIndex.value > -1 && includesParams(currentRoute.params, route.value.params));
+ const isExactActive = computed(() => activeRecordIndex.value > -1 && activeRecordIndex.value === currentRoute.matched.length - 1 && isSameRouteLocationParams(currentRoute.params, route.value.params));
+ function navigate(e = {}) {
+ if (guardEvent(e)) {
+ const p2 = router2[unref(props.replace) ? "replace" : "push"](unref(props.to)).catch(noop$1);
+ if (props.viewTransition && typeof document !== "undefined" && "startViewTransition" in document) document.startViewTransition(() => p2);
+ return p2;
+ }
+ return Promise.resolve();
+ }
+ return {
+ route,
+ href: computed(() => route.value.href),
+ isActive: isActive2,
+ isExactActive,
+ navigate
+ };
+}
+function preferSingleVNode(vnodes) {
+ return vnodes.length === 1 ? vnodes[0] : vnodes;
+}
+const RouterLinkImpl = /* @__PURE__ */ defineComponent({
+ name: "RouterLink",
+ compatConfig: { MODE: 3 },
+ props: {
+ to: {
+ type: [String, Object],
+ required: true
+ },
+ replace: Boolean,
+ activeClass: String,
+ exactActiveClass: String,
+ custom: Boolean,
+ ariaCurrentValue: {
+ type: String,
+ default: "page"
+ },
+ viewTransition: Boolean
+ },
+ useLink,
+ setup(props, { slots }) {
+ const link = /* @__PURE__ */ reactive(useLink(props));
+ const { options } = inject(routerKey);
+ const elClass = computed(() => ({
+ [getLinkClass(props.activeClass, options.linkActiveClass, "router-link-active")]: link.isActive,
+ [getLinkClass(props.exactActiveClass, options.linkExactActiveClass, "router-link-exact-active")]: link.isExactActive
+ }));
+ return () => {
+ const children = slots.default && preferSingleVNode(slots.default(link));
+ return props.custom ? children : h$1("a", {
+ "aria-current": link.isExactActive ? props.ariaCurrentValue : null,
+ href: link.href,
+ onClick: link.navigate,
+ class: elClass.value
+ }, children);
+ };
+ }
+});
+const RouterLink = RouterLinkImpl;
+function guardEvent(e) {
+ if (e.metaKey || e.altKey || e.ctrlKey || e.shiftKey) return;
+ if (e.defaultPrevented) return;
+ if (e.button !== void 0 && e.button !== 0) return;
+ if (e.currentTarget && e.currentTarget.getAttribute) {
+ const target = e.currentTarget.getAttribute("target");
+ if (/\b_blank\b/i.test(target)) return;
+ }
+ if (e.preventDefault) e.preventDefault();
+ return true;
+}
+function includesParams(outer, inner) {
+ for (const key in inner) {
+ const innerValue = inner[key];
+ const outerValue = outer[key];
+ if (typeof innerValue === "string") {
+ if (innerValue !== outerValue) return false;
+ } else if (!isArray(outerValue) || outerValue.length !== innerValue.length || innerValue.some((value, i) => value.valueOf() !== outerValue[i].valueOf())) return false;
+ }
+ return true;
+}
+function getOriginalPath(record) {
+ return record ? record.aliasOf ? record.aliasOf.path : record.path : "";
+}
+const getLinkClass = (propClass, globalClass, defaultClass) => propClass != null ? propClass : globalClass != null ? globalClass : defaultClass;
+const RouterViewImpl = /* @__PURE__ */ defineComponent({
+ name: "RouterView",
+ inheritAttrs: false,
+ props: {
+ name: {
+ type: String,
+ default: "default"
+ },
+ route: Object
+ },
+ compatConfig: { MODE: 3 },
+ setup(props, { attrs, slots }) {
+ const injectedRoute = inject(routerViewLocationKey);
+ const routeToDisplay = computed(() => props.route || injectedRoute.value);
+ const injectedDepth = inject(viewDepthKey, 0);
+ const depth = computed(() => {
+ let initialDepth = unref(injectedDepth);
+ const { matched } = routeToDisplay.value;
+ let matchedRoute;
+ while ((matchedRoute = matched[initialDepth]) && !matchedRoute.components) initialDepth++;
+ return initialDepth;
+ });
+ const matchedRouteRef = computed(() => routeToDisplay.value.matched[depth.value]);
+ provide(viewDepthKey, computed(() => depth.value + 1));
+ provide(matchedRouteKey, matchedRouteRef);
+ provide(routerViewLocationKey, routeToDisplay);
+ const viewRef = /* @__PURE__ */ ref();
+ watch(() => [
+ viewRef.value,
+ matchedRouteRef.value,
+ props.name
+ ], ([instance, to, name], [oldInstance, from2, oldName]) => {
+ if (to) {
+ to.instances[name] = instance;
+ if (from2 && from2 !== to && instance && instance === oldInstance) {
+ if (!to.leaveGuards.size) to.leaveGuards = from2.leaveGuards;
+ if (!to.updateGuards.size) to.updateGuards = from2.updateGuards;
+ }
+ }
+ if (instance && to && (!from2 || !isSameRouteRecord(to, from2) || !oldInstance)) (to.enterCallbacks[name] || []).forEach((callback) => callback(instance));
+ }, { flush: "post" });
+ return () => {
+ const route = routeToDisplay.value;
+ const currentName = props.name;
+ const matchedRoute = matchedRouteRef.value;
+ const ViewComponent = matchedRoute && matchedRoute.components[currentName];
+ if (!ViewComponent) return normalizeSlot(slots.default, {
+ Component: ViewComponent,
+ route
+ });
+ const routePropsOption = matchedRoute.props[currentName];
+ const routeProps = routePropsOption ? routePropsOption === true ? route.params : typeof routePropsOption === "function" ? routePropsOption(route) : routePropsOption : null;
+ const onVnodeUnmounted = (vnode) => {
+ if (vnode.component.isUnmounted) matchedRoute.instances[currentName] = null;
+ };
+ const component = h$1(ViewComponent, assign$1({}, routeProps, attrs, {
+ onVnodeUnmounted,
+ ref: viewRef
+ }));
+ return normalizeSlot(slots.default, {
+ Component: component,
+ route
+ }) || component;
+ };
+ }
+});
+function normalizeSlot(slot, data) {
+ if (!slot) return null;
+ const slotContent = slot(data);
+ return slotContent.length === 1 ? slotContent[0] : slotContent;
+}
+const RouterView = RouterViewImpl;
+function createRouter(options) {
+ const matcher = createRouterMatcher(options.routes, options);
+ const parseQuery$1 = options.parseQuery || parseQuery;
+ const stringifyQuery$1 = options.stringifyQuery || stringifyQuery;
+ const routerHistory = options.history;
+ const beforeGuards = useCallbacks();
+ const beforeResolveGuards = useCallbacks();
+ const afterGuards = useCallbacks();
+ const currentRoute = /* @__PURE__ */ shallowRef(START_LOCATION_NORMALIZED);
+ let pendingLocation = START_LOCATION_NORMALIZED;
+ if (isBrowser && options.scrollBehavior && "scrollRestoration" in history) history.scrollRestoration = "manual";
+ const normalizeParams = applyToParams.bind(null, (paramValue) => "" + paramValue);
+ const encodeParams = applyToParams.bind(null, encodeParam);
+ const decodeParams = applyToParams.bind(null, decode);
+ function addRoute(parentOrRoute, route) {
+ let parent;
+ let record;
+ if (isRouteName(parentOrRoute)) {
+ parent = matcher.getRecordMatcher(parentOrRoute);
+ record = route;
+ } else record = parentOrRoute;
+ return matcher.addRoute(record, parent);
+ }
+ function removeRoute(name) {
+ const recordMatcher = matcher.getRecordMatcher(name);
+ if (recordMatcher) matcher.removeRoute(recordMatcher);
+ }
+ function getRoutes() {
+ return matcher.getRoutes().map((routeMatcher) => routeMatcher.record);
+ }
+ function hasRoute(name) {
+ return !!matcher.getRecordMatcher(name);
+ }
+ function resolve2(rawLocation, currentLocation) {
+ currentLocation = assign$1({}, currentLocation || currentRoute.value);
+ if (typeof rawLocation === "string") {
+ const locationNormalized = parseURL(parseQuery$1, rawLocation, currentLocation.path);
+ const matchedRoute2 = matcher.resolve({ path: locationNormalized.path }, currentLocation);
+ const href2 = routerHistory.createHref(locationNormalized.fullPath);
+ return assign$1(locationNormalized, matchedRoute2, {
+ params: decodeParams(matchedRoute2.params),
+ hash: decode(locationNormalized.hash),
+ redirectedFrom: void 0,
+ href: href2
+ });
+ }
+ let matcherLocation;
+ if (rawLocation.path != null) {
+ matcherLocation = assign$1({}, rawLocation, { path: parseURL(parseQuery$1, rawLocation.path, currentLocation.path).path });
+ } else {
+ const targetParams = assign$1({}, rawLocation.params);
+ for (const key in targetParams) if (targetParams[key] == null) delete targetParams[key];
+ matcherLocation = assign$1({}, rawLocation, { params: encodeParams(targetParams) });
+ currentLocation.params = encodeParams(currentLocation.params);
+ }
+ const matchedRoute = matcher.resolve(matcherLocation, currentLocation);
+ const hash = rawLocation.hash || "";
+ matchedRoute.params = normalizeParams(decodeParams(matchedRoute.params));
+ const fullPath = stringifyURL(stringifyQuery$1, assign$1({}, rawLocation, {
+ hash: encodeHash(hash),
+ path: matchedRoute.path
+ }));
+ const href = routerHistory.createHref(fullPath);
+ return assign$1({
+ fullPath,
+ hash,
+ query: stringifyQuery$1 === stringifyQuery ? normalizeQuery(rawLocation.query) : rawLocation.query || {}
+ }, matchedRoute, {
+ redirectedFrom: void 0,
+ href
+ });
+ }
+ function locationAsObject(to) {
+ return typeof to === "string" ? parseURL(parseQuery$1, to, currentRoute.value.path) : assign$1({}, to);
+ }
+ function checkCanceledNavigation(to, from2) {
+ if (pendingLocation !== to) return createRouterError(ErrorTypes.NAVIGATION_CANCELLED, {
+ from: from2,
+ to
+ });
+ }
+ function push(to) {
+ return pushWithRedirect(to);
+ }
+ function replace2(to) {
+ return push(assign$1(locationAsObject(to), { replace: true }));
+ }
+ function handleRedirectRecord(to, from2) {
+ const lastMatched = to.matched[to.matched.length - 1];
+ if (lastMatched && lastMatched.redirect) {
+ const { redirect } = lastMatched;
+ let newTargetLocation = typeof redirect === "function" ? redirect(to, from2) : redirect;
+ if (typeof newTargetLocation === "string") {
+ newTargetLocation = newTargetLocation.includes("?") || newTargetLocation.includes("#") ? newTargetLocation = locationAsObject(newTargetLocation) : { path: newTargetLocation };
+ newTargetLocation.params = {};
+ }
+ return assign$1({
+ query: to.query,
+ hash: to.hash,
+ params: newTargetLocation.path != null ? {} : to.params
+ }, newTargetLocation);
+ }
+ }
+ function pushWithRedirect(to, redirectedFrom) {
+ const targetLocation = pendingLocation = resolve2(to);
+ const from2 = currentRoute.value;
+ const data = to.state;
+ const force = to.force;
+ const replace22 = to.replace === true;
+ const shouldRedirect = handleRedirectRecord(targetLocation, from2);
+ if (shouldRedirect) return pushWithRedirect(assign$1(locationAsObject(shouldRedirect), {
+ state: typeof shouldRedirect === "object" ? assign$1({}, data, shouldRedirect.state) : data,
+ force,
+ replace: replace22
+ }), redirectedFrom || targetLocation);
+ const toLocation = targetLocation;
+ toLocation.redirectedFrom = redirectedFrom;
+ let failure;
+ if (!force && isSameRouteLocation(stringifyQuery$1, from2, targetLocation)) {
+ failure = createRouterError(ErrorTypes.NAVIGATION_DUPLICATED, {
+ to: toLocation,
+ from: from2
+ });
+ handleScroll(from2, from2, true, false);
+ }
+ return (failure ? Promise.resolve(failure) : navigate(toLocation, from2)).catch((error) => isNavigationFailure(error) ? isNavigationFailure(error, ErrorTypes.NAVIGATION_GUARD_REDIRECT) ? error : markAsReady(error) : triggerError(error, toLocation, from2)).then((failure2) => {
+ if (failure2) {
+ if (isNavigationFailure(failure2, ErrorTypes.NAVIGATION_GUARD_REDIRECT)) {
+ return pushWithRedirect(assign$1({ replace: replace22 }, locationAsObject(failure2.to), {
+ state: typeof failure2.to === "object" ? assign$1({}, data, failure2.to.state) : data,
+ force
+ }), redirectedFrom || toLocation);
+ }
+ } else failure2 = finalizeNavigation(toLocation, from2, true, replace22, data);
+ triggerAfterEach(toLocation, from2, failure2);
+ return failure2;
+ });
+ }
+ function checkCanceledNavigationAndReject(to, from2) {
+ const error = checkCanceledNavigation(to, from2);
+ return error ? Promise.reject(error) : Promise.resolve();
+ }
+ function runWithContext(fn) {
+ const app2 = installedApps.values().next().value;
+ return app2 && typeof app2.runWithContext === "function" ? app2.runWithContext(fn) : fn();
+ }
+ function navigate(to, from2) {
+ let guards;
+ const [leavingRecords, updatingRecords, enteringRecords] = extractChangingRecords(to, from2);
+ guards = extractComponentsGuards(leavingRecords.reverse(), "beforeRouteLeave", to, from2);
+ for (const record of leavingRecords) record.leaveGuards.forEach((guard) => {
+ guards.push(guardToPromiseFn(guard, to, from2));
+ });
+ const canceledNavigationCheck = checkCanceledNavigationAndReject.bind(null, to, from2);
+ guards.push(canceledNavigationCheck);
+ return runGuardQueue(guards).then(() => {
+ guards = [];
+ for (const guard of beforeGuards.list()) guards.push(guardToPromiseFn(guard, to, from2));
+ guards.push(canceledNavigationCheck);
+ return runGuardQueue(guards);
+ }).then(() => {
+ guards = extractComponentsGuards(updatingRecords, "beforeRouteUpdate", to, from2);
+ for (const record of updatingRecords) record.updateGuards.forEach((guard) => {
+ guards.push(guardToPromiseFn(guard, to, from2));
+ });
+ guards.push(canceledNavigationCheck);
+ return runGuardQueue(guards);
+ }).then(() => {
+ guards = [];
+ for (const record of enteringRecords) if (record.beforeEnter) if (isArray(record.beforeEnter)) for (const beforeEnter of record.beforeEnter) guards.push(guardToPromiseFn(beforeEnter, to, from2));
+ else guards.push(guardToPromiseFn(record.beforeEnter, to, from2));
+ guards.push(canceledNavigationCheck);
+ return runGuardQueue(guards);
+ }).then(() => {
+ to.matched.forEach((record) => record.enterCallbacks = {});
+ guards = extractComponentsGuards(enteringRecords, "beforeRouteEnter", to, from2, runWithContext);
+ guards.push(canceledNavigationCheck);
+ return runGuardQueue(guards);
+ }).then(() => {
+ guards = [];
+ for (const guard of beforeResolveGuards.list()) guards.push(guardToPromiseFn(guard, to, from2));
+ guards.push(canceledNavigationCheck);
+ return runGuardQueue(guards);
+ }).catch((err) => isNavigationFailure(err, ErrorTypes.NAVIGATION_CANCELLED) ? err : Promise.reject(err));
+ }
+ function triggerAfterEach(to, from2, failure) {
+ afterGuards.list().forEach((guard) => runWithContext(() => guard(to, from2, failure)));
+ }
+ function finalizeNavigation(toLocation, from2, isPush, replace22, data) {
+ const error = checkCanceledNavigation(toLocation, from2);
+ if (error) return error;
+ const isFirstNavigation = from2 === START_LOCATION_NORMALIZED;
+ const state = !isBrowser ? {} : history.state;
+ if (isPush) if (replace22 || isFirstNavigation) routerHistory.replace(toLocation.fullPath, assign$1({ scroll: isFirstNavigation && state && state.scroll }, data));
+ else routerHistory.push(toLocation.fullPath, data);
+ currentRoute.value = toLocation;
+ handleScroll(toLocation, from2, isPush, isFirstNavigation);
+ markAsReady();
+ }
+ let removeHistoryListener;
+ function setupListeners() {
+ if (removeHistoryListener) return;
+ removeHistoryListener = routerHistory.listen((to, _from, info) => {
+ if (!router2.listening) return;
+ const toLocation = resolve2(to);
+ const shouldRedirect = handleRedirectRecord(toLocation, router2.currentRoute.value);
+ if (shouldRedirect) {
+ pushWithRedirect(assign$1(shouldRedirect, {
+ replace: true,
+ force: true
+ }), toLocation).catch(noop$1);
+ return;
+ }
+ pendingLocation = toLocation;
+ const from2 = currentRoute.value;
+ if (isBrowser) saveScrollPosition(getScrollKey(from2.fullPath, info.delta), computeScrollPosition());
+ navigate(toLocation, from2).catch((error) => {
+ if (isNavigationFailure(error, ErrorTypes.NAVIGATION_ABORTED | ErrorTypes.NAVIGATION_CANCELLED)) return error;
+ if (isNavigationFailure(error, ErrorTypes.NAVIGATION_GUARD_REDIRECT)) {
+ pushWithRedirect(assign$1(locationAsObject(error.to), { force: true }), toLocation).then((failure) => {
+ if (isNavigationFailure(failure, ErrorTypes.NAVIGATION_ABORTED | ErrorTypes.NAVIGATION_DUPLICATED) && !info.delta && info.type === NavigationType.pop) routerHistory.go(-1, false);
+ }).catch(noop$1);
+ return Promise.reject();
+ }
+ if (info.delta) routerHistory.go(-info.delta, false);
+ return triggerError(error, toLocation, from2);
+ }).then((failure) => {
+ failure = failure || finalizeNavigation(toLocation, from2, false);
+ if (failure) {
+ if (info.delta && !isNavigationFailure(failure, ErrorTypes.NAVIGATION_CANCELLED)) routerHistory.go(-info.delta, false);
+ else if (info.type === NavigationType.pop && isNavigationFailure(failure, ErrorTypes.NAVIGATION_ABORTED | ErrorTypes.NAVIGATION_DUPLICATED)) routerHistory.go(-1, false);
+ }
+ triggerAfterEach(toLocation, from2, failure);
+ }).catch(noop$1);
+ });
+ }
+ let readyHandlers = useCallbacks();
+ let errorListeners = useCallbacks();
+ let ready;
+ function triggerError(error, to, from2) {
+ markAsReady(error);
+ const list = errorListeners.list();
+ if (list.length) list.forEach((handler) => handler(error, to, from2));
+ else {
+ console.error(error);
+ }
+ return Promise.reject(error);
+ }
+ function isReady() {
+ if (ready && currentRoute.value !== START_LOCATION_NORMALIZED) return Promise.resolve();
+ return new Promise((resolve22, reject) => {
+ readyHandlers.add([resolve22, reject]);
+ });
+ }
+ function markAsReady(err) {
+ if (!ready) {
+ ready = !err;
+ setupListeners();
+ readyHandlers.list().forEach(([resolve22, reject]) => err ? reject(err) : resolve22());
+ readyHandlers.reset();
+ }
+ return err;
+ }
+ function handleScroll(to, from2, isPush, isFirstNavigation) {
+ const { scrollBehavior } = options;
+ if (!isBrowser || !scrollBehavior) return Promise.resolve();
+ const scrollPosition = !isPush && getSavedScrollPosition(getScrollKey(to.fullPath, 0)) || (isFirstNavigation || !isPush) && history.state && history.state.scroll || null;
+ return nextTick().then(() => scrollBehavior(to, from2, scrollPosition)).then((position) => position && scrollToPosition(position)).catch((err) => triggerError(err, to, from2));
+ }
+ const go = (delta) => routerHistory.go(delta);
+ let started;
+ const installedApps = /* @__PURE__ */ new Set();
+ const router2 = {
+ currentRoute,
+ listening: true,
+ addRoute,
+ removeRoute,
+ clearRoutes: matcher.clearRoutes,
+ hasRoute,
+ getRoutes,
+ resolve: resolve2,
+ options,
+ push,
+ replace: replace2,
+ go,
+ back: () => go(-1),
+ forward: () => go(1),
+ beforeEach: beforeGuards.add,
+ beforeResolve: beforeResolveGuards.add,
+ afterEach: afterGuards.add,
+ onError: errorListeners.add,
+ isReady,
+ install(app2) {
+ app2.component("RouterLink", RouterLink);
+ app2.component("RouterView", RouterView);
+ app2.config.globalProperties.$router = router2;
+ Object.defineProperty(app2.config.globalProperties, "$route", {
+ enumerable: true,
+ get: () => unref(currentRoute)
+ });
+ if (isBrowser && !started && currentRoute.value === START_LOCATION_NORMALIZED) {
+ started = true;
+ push(routerHistory.location).catch((err) => {
+ });
+ }
+ const reactiveRoute = {};
+ for (const key in START_LOCATION_NORMALIZED) Object.defineProperty(reactiveRoute, key, {
+ get: () => currentRoute.value[key],
+ enumerable: true
+ });
+ app2.provide(routerKey, router2);
+ app2.provide(routeLocationKey, /* @__PURE__ */ shallowReactive(reactiveRoute));
+ app2.provide(routerViewLocationKey, currentRoute);
+ const unmountApp = app2.unmount;
+ installedApps.add(app2);
+ app2.unmount = function() {
+ installedApps.delete(app2);
+ if (installedApps.size < 1) {
+ pendingLocation = START_LOCATION_NORMALIZED;
+ removeHistoryListener && removeHistoryListener();
+ removeHistoryListener = null;
+ currentRoute.value = START_LOCATION_NORMALIZED;
+ started = false;
+ ready = false;
+ }
+ unmountApp();
+ };
+ }
+ };
+ function runGuardQueue(guards) {
+ return guards.reduce((promise, guard) => promise.then(() => runWithContext(guard)), Promise.resolve());
+ }
+ return router2;
+}
+const categories = /* @__PURE__ */ ref([]);
+const searchResults = /* @__PURE__ */ ref([]);
+const useNotes = () => {
+ async function loadCategories() {
+ categories.value = await window.notesAPI.call("getCategories");
+ }
+ async function loadCategoryNotes(category = null) {
+ return await window.notesAPI.call("getCategoryNotes", category);
+ }
+ async function loadNote(id) {
+ return await window.notesAPI.call("getNote", id);
+ }
+ async function createNote(metadata, content) {
+ const note = await window.notesAPI.call("createNote", metadata, content);
+ await loadCategories();
+ return note;
+ }
+ async function updateNoteContent(id, content) {
+ const note = await window.notesAPI.call("updateNote", id, content);
+ return note;
+ }
+ async function updateNoteMetadata(id, updates) {
+ const note = await window.notesAPI.call(
+ "updateNoteMetadata",
+ id,
+ updates
+ );
+ await loadCategories();
+ return note;
+ }
+ async function search(query) {
+ if (!query) {
+ searchResults.value = [];
+ return;
+ }
+ searchResults.value = await window.notesAPI.call("search", query);
+ }
+ return {
+ categories,
+ searchResults,
+ loadCategories,
+ loadCategoryNotes,
+ loadNote,
+ createNote,
+ updateNoteContent,
+ updateNoteMetadata,
+ search
+ };
+};
+const _hoisted_1$4 = { class: "index" };
+const _hoisted_2$4 = { class: "title h1" };
+const _sfc_main$4 = {
+ __name: "CategoryRow",
+ props: { index: Number, category: String },
+ setup(__props) {
+ return (_ctx, _cache) => {
+ const _component_router_link = resolveComponent("router-link");
+ return openBlock(), createBlock(_component_router_link, {
+ class: "category-row",
+ to: `/category/${__props.category}`
+ }, {
+ default: withCtx(() => [
+ createBaseVNode("span", _hoisted_1$4, toDisplayString(String(__props.index + 1).padStart(2, "0")) + ".", 1),
+ createBaseVNode("span", _hoisted_2$4, toDisplayString(__props.category), 1)
+ ]),
+ _: 1
+ }, 8, ["to"]);
+ };
+ }
+};
+const useOpenNote = () => {
+ const router2 = useRouter();
+ function openNote(noteId, options = {}) {
+ const { newWindow = true } = options;
+ const isElectron = typeof window !== "undefined" && window.api && typeof window.api.openNoteWindow === "function";
+ if (newWindow && isElectron) {
+ window.api.openNoteWindow(noteId);
+ return;
+ }
+ router2.push(`/note/${noteId}`);
+ }
+ return {
+ openNote
+ };
+};
+var token = /d{1,4}|M{1,4}|YY(?:YY)?|S{1,3}|Do|ZZ|Z|([HhMsDm])\1?|[aA]|"[^"]*"|'[^']*'/g;
+var literal = /\[([^]*?)\]/gm;
+function shorten(arr, sLen) {
+ var newArr = [];
+ for (var i = 0, len = arr.length; i < len; i++) {
+ newArr.push(arr[i].substr(0, sLen));
+ }
+ return newArr;
+}
+function assign(origObj) {
+ var args = [];
+ for (var _i = 1; _i < arguments.length; _i++) {
+ args[_i - 1] = arguments[_i];
+ }
+ for (var _a = 0, args_1 = args; _a < args_1.length; _a++) {
+ var obj = args_1[_a];
+ for (var key in obj) {
+ origObj[key] = obj[key];
+ }
+ }
+ return origObj;
+}
+var dayNames = [
+ "Sunday",
+ "Monday",
+ "Tuesday",
+ "Wednesday",
+ "Thursday",
+ "Friday",
+ "Saturday"
+];
+var monthNames = [
+ "January",
+ "February",
+ "March",
+ "April",
+ "May",
+ "June",
+ "July",
+ "August",
+ "September",
+ "October",
+ "November",
+ "December"
+];
+var monthNamesShort = shorten(monthNames, 3);
+var dayNamesShort = shorten(dayNames, 3);
+var defaultI18n = {
+ dayNamesShort,
+ dayNames,
+ monthNamesShort,
+ monthNames,
+ amPm: ["am", "pm"],
+ DoFn: function(dayOfMonth) {
+ return dayOfMonth + ["th", "st", "nd", "rd"][dayOfMonth % 10 > 3 ? 0 : (dayOfMonth - dayOfMonth % 10 !== 10 ? 1 : 0) * dayOfMonth % 10];
+ }
+};
+var globalI18n = assign({}, defaultI18n);
+var pad = function(val, len) {
+ if (len === void 0) {
+ len = 2;
+ }
+ val = String(val);
+ while (val.length < len) {
+ val = "0" + val;
+ }
+ return val;
+};
+var formatFlags = {
+ D: function(dateObj) {
+ return String(dateObj.getDate());
+ },
+ DD: function(dateObj) {
+ return pad(dateObj.getDate());
+ },
+ Do: function(dateObj, i18n) {
+ return i18n.DoFn(dateObj.getDate());
+ },
+ d: function(dateObj) {
+ return String(dateObj.getDay());
+ },
+ dd: function(dateObj) {
+ return pad(dateObj.getDay());
+ },
+ ddd: function(dateObj, i18n) {
+ return i18n.dayNamesShort[dateObj.getDay()];
+ },
+ dddd: function(dateObj, i18n) {
+ return i18n.dayNames[dateObj.getDay()];
+ },
+ M: function(dateObj) {
+ return String(dateObj.getMonth() + 1);
+ },
+ MM: function(dateObj) {
+ return pad(dateObj.getMonth() + 1);
+ },
+ MMM: function(dateObj, i18n) {
+ return i18n.monthNamesShort[dateObj.getMonth()];
+ },
+ MMMM: function(dateObj, i18n) {
+ return i18n.monthNames[dateObj.getMonth()];
+ },
+ YY: function(dateObj) {
+ return pad(String(dateObj.getFullYear()), 4).substr(2);
+ },
+ YYYY: function(dateObj) {
+ return pad(dateObj.getFullYear(), 4);
+ },
+ h: function(dateObj) {
+ return String(dateObj.getHours() % 12 || 12);
+ },
+ hh: function(dateObj) {
+ return pad(dateObj.getHours() % 12 || 12);
+ },
+ H: function(dateObj) {
+ return String(dateObj.getHours());
+ },
+ HH: function(dateObj) {
+ return pad(dateObj.getHours());
+ },
+ m: function(dateObj) {
+ return String(dateObj.getMinutes());
+ },
+ mm: function(dateObj) {
+ return pad(dateObj.getMinutes());
+ },
+ s: function(dateObj) {
+ return String(dateObj.getSeconds());
+ },
+ ss: function(dateObj) {
+ return pad(dateObj.getSeconds());
+ },
+ S: function(dateObj) {
+ return String(Math.round(dateObj.getMilliseconds() / 100));
+ },
+ SS: function(dateObj) {
+ return pad(Math.round(dateObj.getMilliseconds() / 10), 2);
+ },
+ SSS: function(dateObj) {
+ return pad(dateObj.getMilliseconds(), 3);
+ },
+ a: function(dateObj, i18n) {
+ return dateObj.getHours() < 12 ? i18n.amPm[0] : i18n.amPm[1];
+ },
+ A: function(dateObj, i18n) {
+ return dateObj.getHours() < 12 ? i18n.amPm[0].toUpperCase() : i18n.amPm[1].toUpperCase();
+ },
+ ZZ: function(dateObj) {
+ var offset2 = dateObj.getTimezoneOffset();
+ return (offset2 > 0 ? "-" : "+") + pad(Math.floor(Math.abs(offset2) / 60) * 100 + Math.abs(offset2) % 60, 4);
+ },
+ Z: function(dateObj) {
+ var offset2 = dateObj.getTimezoneOffset();
+ return (offset2 > 0 ? "-" : "+") + pad(Math.floor(Math.abs(offset2) / 60), 2) + ":" + pad(Math.abs(offset2) % 60, 2);
+ }
+};
+var globalMasks = {
+ default: "ddd MMM DD YYYY HH:mm:ss",
+ shortDate: "M/D/YY",
+ mediumDate: "MMM D, YYYY",
+ longDate: "MMMM D, YYYY",
+ fullDate: "dddd, MMMM D, YYYY",
+ isoDate: "YYYY-MM-DD",
+ isoDateTime: "YYYY-MM-DDTHH:mm:ssZ",
+ shortTime: "HH:mm",
+ mediumTime: "HH:mm:ss",
+ longTime: "HH:mm:ss.SSS"
+};
+var format = function(dateObj, mask, i18n) {
+ if (mask === void 0) {
+ mask = globalMasks["default"];
+ }
+ if (i18n === void 0) {
+ i18n = {};
+ }
+ if (typeof dateObj === "number") {
+ dateObj = new Date(dateObj);
+ }
+ if (Object.prototype.toString.call(dateObj) !== "[object Date]" || isNaN(dateObj.getTime())) {
+ throw new Error("Invalid Date pass to format");
+ }
+ mask = globalMasks[mask] || mask;
+ var literals = [];
+ mask = mask.replace(literal, function($0, $1) {
+ literals.push($1);
+ return "@@@";
+ });
+ var combinedI18nSettings = assign(assign({}, globalI18n), i18n);
+ mask = mask.replace(token, function($0) {
+ return formatFlags[$0](dateObj, combinedI18nSettings);
+ });
+ return mask.replace(/@@@/g, function() {
+ return literals.shift();
+ });
+};
+const _hoisted_1$3 = { class: "date" };
+const _hoisted_2$3 = { class: "title bold" };
+const _sfc_main$3 = {
+ __name: "NoteRow",
+ props: { note: Object },
+ setup(__props) {
+ const { openNote } = useOpenNote();
+ const formatDate = (date) => {
+ const d = new Date(date);
+ return format(d, "MM/DD/YYYY");
+ };
+ return (_ctx, _cache) => {
+ return openBlock(), createElementBlock("button", {
+ class: "note-row",
+ onClick: _cache[0] || (_cache[0] = ($event) => unref(openNote)(__props.note.id))
+ }, [
+ createBaseVNode("span", _hoisted_1$3, toDisplayString(formatDate(__props.note.createdAt)), 1),
+ createBaseVNode("span", _hoisted_2$3, toDisplayString(__props.note.title), 1)
+ ]);
+ };
+ }
+};
+const _hoisted_1$2 = { class: "directory layout-block" };
+const _hoisted_2$2 = { class: "notes" };
+const _sfc_main$2 = {
+ __name: "Directory",
+ setup(__props) {
+ const { categories: categories2, loadCategories, loadCategoryNotes } = useNotes();
+ const notes = /* @__PURE__ */ ref();
+ onMounted(async () => {
+ await loadCategories();
+ notes.value = await loadCategoryNotes();
+ });
+ return (_ctx, _cache) => {
+ return openBlock(), createElementBlock("main", _hoisted_1$2, [
+ (openBlock(true), createElementBlock(Fragment$1, null, renderList(unref(categories2), (category, i) => {
+ return openBlock(), createBlock(_sfc_main$4, {
+ index: i,
+ category,
+ key: category
+ }, null, 8, ["index", "category"]);
+ }), 128)),
+ _cache[0] || (_cache[0] = createBaseVNode("h2", { class: "label" }, "Summarium", -1)),
+ createBaseVNode("div", _hoisted_2$2, [
+ (openBlock(true), createElementBlock(Fragment$1, null, renderList(notes.value, (note) => {
+ return openBlock(), createBlock(_sfc_main$3, {
+ note,
+ key: note.id
+ }, null, 8, ["note"]);
+ }), 128))
+ ])
+ ]);
+ };
+ }
+};
function OrderedMap(content) {
this.content = content;
}
@@ -26176,8 +28206,8 @@ function createAtomBlockMarkdownSpec(options) {
return filtered;
};
return {
- parseMarkdown: (token, h2) => {
- const attrs = { ...defaultAttributes, ...token.attributes };
+ parseMarkdown: (token2, h2) => {
+ const attrs = { ...defaultAttributes, ...token2.attributes };
return h2.createNode(nodeName, attrs, []);
},
markdownTokenizer: {
@@ -26241,17 +28271,17 @@ function createBlockMarkdownSpec(options) {
return filtered;
};
return {
- parseMarkdown: (token, h2) => {
+ parseMarkdown: (token2, h2) => {
let nodeContent;
if (getContent) {
- const contentResult = getContent(token);
+ const contentResult = getContent(token2);
nodeContent = typeof contentResult === "string" ? [{ type: "text", text: contentResult }] : contentResult;
} else if (content === "block") {
- nodeContent = h2.parseChildren(token.tokens || []);
+ nodeContent = h2.parseChildren(token2.tokens || []);
} else {
- nodeContent = h2.parseInline(token.tokens || []);
+ nodeContent = h2.parseInline(token2.tokens || []);
}
- const attrs = { ...defaultAttributes, ...token.attributes };
+ const attrs = { ...defaultAttributes, ...token2.attributes };
return h2.createNode(nodeName, attrs, nodeContent);
},
markdownTokenizer: {
@@ -26300,9 +28330,9 @@ function createBlockMarkdownSpec(options) {
if (matchedContent) {
if (content === "block") {
contentTokens = lexer.blockTokens(rawContent);
- contentTokens.forEach((token) => {
- if (token.text && (!token.tokens || token.tokens.length === 0)) {
- token.tokens = lexer.inlineTokens(token.text);
+ contentTokens.forEach((token2) => {
+ if (token2.text && (!token2.tokens || token2.tokens.length === 0)) {
+ token2.tokens = lexer.inlineTokens(token2.text);
}
});
while (contentTokens.length > 0) {
@@ -26392,12 +28422,12 @@ function createInlineMarkdownSpec(options) {
};
const escapedShortcode = shortcode.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
return {
- parseMarkdown: (token, h2) => {
- const attrs = { ...defaultAttributes, ...token.attributes };
+ parseMarkdown: (token2, h2) => {
+ const attrs = { ...defaultAttributes, ...token2.attributes };
if (selfClosing) {
return h2.createNode(nodeName, attrs);
}
- const content = getContent ? getContent(token) : token.content || "";
+ const content = getContent ? getContent(token2) : token2.content || "";
if (content) {
return h2.createNode(nodeName, attrs, [h2.createTextNode(content)]);
}
@@ -26523,8 +28553,8 @@ function parseIndentedBlocks(src, config, lexer) {
}
}
}
- const token = config.createToken(itemData, nestedTokens);
- items.push(token);
+ const token2 = config.createToken(itemData, nestedTokens);
+ items.push(token2);
}
if (items.length === 0) {
return void 0;
@@ -28170,25 +30200,25 @@ var MarkdownManager = class {
* Convert an array of marked tokens into Tiptap JSON nodes using registered extension handlers.
*/
parseTokens(tokens) {
- return tokens.map((token) => this.parseToken(token)).filter((parsed) => parsed !== null).flatMap((parsed) => Array.isArray(parsed) ? parsed : [parsed]);
+ return tokens.map((token2) => this.parseToken(token2)).filter((parsed) => parsed !== null).flatMap((parsed) => Array.isArray(parsed) ? parsed : [parsed]);
}
/**
* Parse a single token into Tiptap JSON using the appropriate registered handler.
*/
- parseToken(token) {
- if (!token.type) {
+ parseToken(token2) {
+ if (!token2.type) {
return null;
}
- if (token.type === "list") {
- return this.parseListToken(token);
+ if (token2.type === "list") {
+ return this.parseListToken(token2);
}
- const handlers2 = this.getHandlersForToken(token.type);
+ const handlers2 = this.getHandlersForToken(token2.type);
const helpers = this.createParseHelpers();
const result = handlers2.find((handler) => {
if (!handler.parseMarkdown) {
return false;
}
- const parseResult = handler.parseMarkdown(token, helpers);
+ const parseResult = handler.parseMarkdown(token2, helpers);
const normalized = this.normalizeParseResult(parseResult);
if (normalized && (!Array.isArray(normalized) || normalized.length > 0)) {
this.lastParseResult = normalized;
@@ -28201,7 +30231,7 @@ var MarkdownManager = class {
this.lastParseResult = null;
return toReturn;
}
- return this.parseFallbackToken(token);
+ return this.parseFallbackToken(token2);
}
/**
* Parse a list token, handling mixed bullet and task list items by splitting them into separate lists.
@@ -28210,20 +30240,20 @@ var MarkdownManager = class {
* @param token The list token to parse
* @returns Array of parsed list nodes, or null if parsing fails
*/
- parseListToken(token) {
- if (!token.items || token.items.length === 0) {
- return this.parseTokenWithHandlers(token);
+ parseListToken(token2) {
+ if (!token2.items || token2.items.length === 0) {
+ return this.parseTokenWithHandlers(token2);
}
- const hasTask = token.items.some((item) => isTaskItem(item).isTask);
- const hasNonTask = token.items.some((item) => !isTaskItem(item).isTask);
+ const hasTask = token2.items.some((item) => isTaskItem(item).isTask);
+ const hasNonTask = token2.items.some((item) => !isTaskItem(item).isTask);
if (!hasTask || !hasNonTask || this.getHandlersForToken("taskList").length === 0) {
- return this.parseTokenWithHandlers(token);
+ return this.parseTokenWithHandlers(token2);
}
const groups = [];
let currentGroup = [];
let currentType = null;
- for (let i = 0; i < token.items.length; i += 1) {
- const item = token.items[i];
+ for (let i = 0; i < token2.items.length; i += 1) {
+ const item = token2.items[i];
const { isTask, checked, indentLevel } = isTaskItem(item);
let processedItem = item;
if (isTask) {
@@ -28281,7 +30311,7 @@ var MarkdownManager = class {
const results = [];
for (let i = 0; i < groups.length; i += 1) {
const group = groups[i];
- const subToken = { ...token, type: group.type, items: group.items };
+ const subToken = { ...token2, type: group.type, items: group.items };
const parsed = this.parseToken(subToken);
if (parsed) {
if (Array.isArray(parsed)) {
@@ -28296,17 +30326,17 @@ var MarkdownManager = class {
/**
* Parse a token using registered handlers (extracted for reuse).
*/
- parseTokenWithHandlers(token) {
- if (!token.type) {
+ parseTokenWithHandlers(token2) {
+ if (!token2.type) {
return null;
}
- const handlers2 = this.getHandlersForToken(token.type);
+ const handlers2 = this.getHandlersForToken(token2.type);
const helpers = this.createParseHelpers();
const result = handlers2.find((handler) => {
if (!handler.parseMarkdown) {
return false;
}
- const parseResult = handler.parseMarkdown(token, helpers);
+ const parseResult = handler.parseMarkdown(token2, helpers);
const normalized = this.normalizeParseResult(parseResult);
if (normalized && (!Array.isArray(normalized) || normalized.length > 0)) {
this.lastParseResult = normalized;
@@ -28319,7 +30349,7 @@ var MarkdownManager = class {
this.lastParseResult = null;
return toReturn;
}
- return this.parseFallbackToken(token);
+ return this.parseFallbackToken(token2);
}
/**
* Creates helper functions for parsing markdown tokens.
@@ -28369,14 +30399,14 @@ var MarkdownManager = class {
var _a, _b, _c, _d;
const result = [];
for (let i = 0; i < tokens.length; i += 1) {
- const token = tokens[i];
- if (token.type === "text") {
+ const token2 = tokens[i];
+ if (token2.type === "text") {
result.push({
type: "text",
- text: token.text || ""
+ text: token2.text || ""
});
- } else if (token.type === "html") {
- const raw = ((_b = (_a = token.raw) != null ? _a : token.text) != null ? _b : "").toString();
+ } else if (token2.type === "html") {
+ const raw = ((_b = (_a = token2.raw) != null ? _a : token2.text) != null ? _b : "").toString();
const isClosing = /^<\/[\s]*[\w-]+/i.test(raw);
const openMatch = raw.match(/^<[\s]*([\w-]+)(\s|>|\/|$)/i);
if (!isClosing && openMatch && !/\/>$/.test(raw)) {
@@ -28415,7 +30445,7 @@ var MarkdownManager = class {
continue;
}
}
- const parsedSingle = this.parseHTMLToken(token);
+ const parsedSingle = this.parseHTMLToken(token2);
if (parsedSingle) {
const normalized = this.normalizeParseResult(parsedSingle);
if (Array.isArray(normalized)) {
@@ -28424,11 +30454,11 @@ var MarkdownManager = class {
result.push(normalized);
}
}
- } else if (token.type) {
- const markHandler = this.getHandlerForToken(token.type);
+ } else if (token2.type) {
+ const markHandler = this.getHandlerForToken(token2.type);
if (markHandler && markHandler.parseMarkdown) {
const helpers = this.createParseHelpers();
- const parsed = markHandler.parseMarkdown(token, helpers);
+ const parsed = markHandler.parseMarkdown(token2, helpers);
if (this.isMarkResult(parsed)) {
const markedContent = this.applyMarkToContent(parsed.mark, parsed.content, parsed.attrs);
result.push(...markedContent);
@@ -28440,8 +30470,8 @@ var MarkdownManager = class {
result.push(normalized);
}
}
- } else if (token.tokens) {
- result.push(...this.parseInlineTokens(token.tokens));
+ } else if (token2.tokens) {
+ result.push(...this.parseInlineTokens(token2.tokens));
}
}
}
@@ -28487,31 +30517,31 @@ var MarkdownManager = class {
/**
* Fallback parsing for common tokens when no specific handler is registered.
*/
- parseFallbackToken(token) {
- switch (token.type) {
+ parseFallbackToken(token2) {
+ switch (token2.type) {
case "paragraph":
return {
type: "paragraph",
- content: token.tokens ? this.parseInlineTokens(token.tokens) : []
+ content: token2.tokens ? this.parseInlineTokens(token2.tokens) : []
};
case "heading":
return {
type: "heading",
- attrs: { level: token.depth || 1 },
- content: token.tokens ? this.parseInlineTokens(token.tokens) : []
+ attrs: { level: token2.depth || 1 },
+ content: token2.tokens ? this.parseInlineTokens(token2.tokens) : []
};
case "text":
return {
type: "text",
- text: token.text || ""
+ text: token2.text || ""
};
case "html":
- return this.parseHTMLToken(token);
+ return this.parseHTMLToken(token2);
case "space":
return null;
default:
- if (token.tokens) {
- return this.parseTokens(token.tokens);
+ if (token2.tokens) {
+ return this.parseTokens(token2.tokens);
}
return null;
}
@@ -28520,13 +30550,13 @@ var MarkdownManager = class {
* Parse HTML tokens using extensions' parseHTML methods.
* This allows HTML within markdown to be parsed according to extension rules.
*/
- parseHTMLToken(token) {
- const html = token.text || token.raw || "";
+ parseHTMLToken(token2) {
+ const html = token2.text || token2.raw || "";
if (!html.trim()) {
return null;
}
if (typeof window === "undefined") {
- if (token.block) {
+ if (token2.block) {
return {
type: "paragraph",
content: [
@@ -28545,7 +30575,7 @@ var MarkdownManager = class {
try {
const parsed = generateJSON(html, this.baseExtensions);
if (parsed.type === "doc" && parsed.content) {
- if (token.block) {
+ if (token2.block) {
return parsed.content;
}
if (parsed.content.length === 1 && parsed.content[0].type === "paragraph" && parsed.content[0].content) {
@@ -28910,11 +30940,11 @@ var Image = Node3.create({
renderHTML({ HTMLAttributes }) {
return ["img", mergeAttributes(this.options.HTMLAttributes, HTMLAttributes)];
},
- parseMarkdown: (token, helpers) => {
+ parseMarkdown: (token2, helpers) => {
return helpers.createNode("image", {
- src: token.href,
- title: token.title,
- alt: token.text
+ src: token2.href,
+ title: token2.title,
+ alt: token2.text
});
},
renderMarkdown: (node) => {
@@ -29850,7 +31880,7 @@ function mustPreserveItems(state) {
}
const historyKey = new PluginKey("history");
const closeHistoryKey = new PluginKey("closeHistory");
-function history(config = {}) {
+function history$1(config = {}) {
config = {
depth: config.depth || 100,
newGroupDelay: config.newGroupDelay || 500
@@ -30235,7 +32265,7 @@ var UndoRedo = Extension.create({
};
},
addProseMirrorPlugins() {
- return [history(this.options)];
+ return [history$1(this.options)];
},
addKeyboardShortcuts() {
return {
@@ -30278,8 +32308,8 @@ var Blockquote = Node3.create({
renderHTML({ HTMLAttributes }) {
return /* @__PURE__ */ h("blockquote", { ...mergeAttributes(this.options.HTMLAttributes, HTMLAttributes), children: /* @__PURE__ */ h("slot", {}) });
},
- parseMarkdown: (token, helpers) => {
- return helpers.createNode("blockquote", void 0, helpers.parseChildren(token.tokens || []));
+ parseMarkdown: (token2, helpers) => {
+ return helpers.createNode("blockquote", void 0, helpers.parseChildren(token2.tokens || []));
},
renderMarkdown: (node, h2) => {
if (!node.content) {
@@ -30363,8 +32393,8 @@ var Bold = Mark2.create({
return /* @__PURE__ */ h("strong", { ...mergeAttributes(this.options.HTMLAttributes, HTMLAttributes), children: /* @__PURE__ */ h("slot", {}) });
},
markdownTokenName: "strong",
- parseMarkdown: (token, helpers) => {
- return helpers.applyMark("bold", helpers.parseInline(token.tokens || []));
+ parseMarkdown: (token2, helpers) => {
+ return helpers.applyMark("bold", helpers.parseInline(token2.tokens || []));
},
renderMarkdown: (node, h2) => {
return `**${h2.renderChildren(node)}**`;
@@ -30432,8 +32462,8 @@ var Code = Mark2.create({
return ["code", mergeAttributes(this.options.HTMLAttributes, HTMLAttributes), 0];
},
markdownTokenName: "codespan",
- parseMarkdown: (token, helpers) => {
- return helpers.applyMark("code", [{ type: "text", text: token.text || "" }]);
+ parseMarkdown: (token2, helpers) => {
+ return helpers.applyMark("code", [{ type: "text", text: token2.text || "" }]);
},
renderMarkdown: (node, h2) => {
if (!node.content) {
@@ -30541,15 +32571,15 @@ var CodeBlock = Node3.create({
];
},
markdownTokenName: "code",
- parseMarkdown: (token, helpers) => {
+ parseMarkdown: (token2, helpers) => {
var _a;
- if (((_a = token.raw) == null ? void 0 : _a.startsWith("```")) === false && token.codeBlockStyle !== "indented") {
+ if (((_a = token2.raw) == null ? void 0 : _a.startsWith("```")) === false && token2.codeBlockStyle !== "indented") {
return [];
}
return helpers.createNode(
"codeBlock",
- { language: token.lang || null },
- token.text ? [helpers.createTextNode(token.text)] : []
+ { language: token2.lang || null },
+ token2.text ? [helpers.createTextNode(token2.text)] : []
);
},
renderMarkdown: (node, h2) => {
@@ -30876,8 +32906,8 @@ var Heading = Node3.create({
const level = hasLevel ? node.attrs.level : this.options.levels[0];
return [`h${level}`, mergeAttributes(this.options.HTMLAttributes, HTMLAttributes), 0];
},
- parseMarkdown: (token, helpers) => {
- return helpers.createNode("heading", { level: token.depth || 1 }, helpers.parseInline(token.tokens || []));
+ parseMarkdown: (token2, helpers) => {
+ return helpers.createNode("heading", { level: token2.depth || 1 }, helpers.parseInline(token2.tokens || []));
},
renderMarkdown: (node, h2) => {
var _a;
@@ -30943,7 +32973,7 @@ var HorizontalRule = Node3.create({
return ["hr", mergeAttributes(this.options.HTMLAttributes, HTMLAttributes)];
},
markdownTokenName: "hr",
- parseMarkdown: (token, helpers) => {
+ parseMarkdown: (token2, helpers) => {
return helpers.createNode("horizontalRule");
},
renderMarkdown: () => {
@@ -31047,8 +33077,8 @@ var Italic = Mark2.create({
};
},
markdownTokenName: "em",
- parseMarkdown: (token, helpers) => {
- return helpers.applyMark("italic", helpers.parseInline(token.tokens || []));
+ parseMarkdown: (token2, helpers) => {
+ return helpers.applyMark("italic", helpers.parseInline(token2.tokens || []));
},
renderMarkdown: (node, h2) => {
return `*${h2.renderChildren(node)}*`;
@@ -31139,11 +33169,11 @@ function flagsForToken(t, groups) {
}
return result;
}
-function State(token = null) {
+function State(token2 = null) {
this.j = {};
this.jr = [];
this.jd = null;
- this.t = token;
+ this.t = token2;
}
State.groups = {};
State.prototype = {
@@ -31738,8 +33768,8 @@ Options.prototype = {
* @param {MultiToken} token
* @returns {boolean}
*/
- check(token) {
- return this.get("validate", token.toString(), token);
+ check(token2) {
+ return this.get("validate", token2.toString(), token2);
},
// Private methods
/**
@@ -31753,19 +33783,19 @@ Options.prototype = {
* @param {MultiToken} [token] The token from linkify.tokenize
* @returns {Opts[K] | any}
*/
- get(key, operator, token) {
+ get(key, operator, token2) {
const isCallable = operator != null;
let option = this.o[key];
if (!option) {
return option;
}
if (typeof option === "object") {
- option = token.t in option ? option[token.t] : defaults[key];
+ option = token2.t in option ? option[token2.t] : defaults[key];
if (typeof option === "function" && isCallable) {
- option = option(operator, token);
+ option = option(operator, token2);
}
} else if (typeof option === "function" && isCallable) {
- option = option(operator, token.t, token);
+ option = option(operator, token2.t, token2);
}
return option;
},
@@ -31776,10 +33806,10 @@ Options.prototype = {
* @param {MultiToken} [token]
* @returns {Opts[L] | any}
*/
- getObj(key, operator, token) {
+ getObj(key, operator, token2) {
let obj = this.o[key];
if (typeof obj === "function" && operator != null) {
- obj = obj(operator, token.t, token);
+ obj = obj(operator, token2.t, token2);
}
return obj;
},
@@ -31790,10 +33820,10 @@ Options.prototype = {
* @returns {any} Render result; e.g., HTML string, DOM element, React
* Component, etc.
*/
- render(token) {
- const ir = token.render(this);
- const renderFn = this.get("render", null, token) || this.defaultRender;
- return renderFn(ir, token.t, token);
+ render(token2) {
+ const ir = token2.render(this);
+ const renderFn = this.get("render", null, token2) || this.defaultRender;
+ return renderFn(ir, token2.t, token2);
}
};
function noop(val) {
@@ -31901,17 +33931,17 @@ MultiToken.prototype = {
* @param {Options} options Formattinng options
*/
render(options) {
- const token = this;
+ const token2 = this;
const href = this.toHref(options.get("defaultProtocol"));
const formattedHref = options.get("formatHref", href, this);
- const tagName = options.get("tagName", href, token);
+ const tagName = options.get("tagName", href, token2);
const content = this.toFormattedString(options);
const attributes = {};
- const className = options.get("className", href, token);
- const target = options.get("target", href, token);
- const rel = options.get("rel", href, token);
- const attrs = options.getObj("attributes", href, token);
- const eventListeners = options.getObj("events", href, token);
+ const className = options.get("className", href, token2);
+ const target = options.get("target", href, token2);
+ const rel = options.get("rel", href, token2);
+ const attrs = options.getObj("attributes", href, token2);
+ const eventListeners = options.getObj("events", href, token2);
attributes.href = formattedHref;
if (className) {
attributes.class = className;
@@ -32223,9 +34253,9 @@ function find(str, type = null, opts = null) {
const tokens = tokenize(str);
const filtered = [];
for (let i = 0; i < tokens.length; i++) {
- const token = tokens[i];
- if (token.isLink && (!type || token.t === type) && options.check(token)) {
- filtered.push(token.toFormattedObject(options));
+ const token2 = tokens[i];
+ if (token2.isLink && (!type || token2.t === type) && options.check(token2)) {
+ filtered.push(token2.toFormattedObject(options));
}
}
return filtered;
@@ -32522,10 +34552,10 @@ var Link2 = Mark2.create({
return ["a", mergeAttributes(this.options.HTMLAttributes, HTMLAttributes), 0];
},
markdownTokenName: "link",
- parseMarkdown: (token, helpers) => {
- return helpers.applyMark("link", helpers.parseInline(token.tokens || []), {
- href: token.href,
- title: token.title || null
+ parseMarkdown: (token2, helpers) => {
+ return helpers.applyMark("link", helpers.parseInline(token2.tokens || []), {
+ href: token2.href,
+ title: token2.title || null
});
},
renderMarkdown: (node, h2) => {
@@ -32672,13 +34702,13 @@ var BulletList = Node3.create({
return ["ul", mergeAttributes(this.options.HTMLAttributes, HTMLAttributes), 0];
},
markdownTokenName: "list",
- parseMarkdown: (token, helpers) => {
- if (token.type !== "list" || token.ordered) {
+ parseMarkdown: (token2, helpers) => {
+ if (token2.type !== "list" || token2.ordered) {
return [];
}
return {
type: "bulletList",
- content: token.items ? helpers.parseChildren(token.items) : []
+ content: token2.items ? helpers.parseChildren(token2.items) : []
};
},
renderMarkdown: (node, h2) => {
@@ -32747,17 +34777,17 @@ var ListItem = Node3.create({
return ["li", mergeAttributes(this.options.HTMLAttributes, HTMLAttributes), 0];
},
markdownTokenName: "list_item",
- parseMarkdown: (token, helpers) => {
- if (token.type !== "list_item") {
+ parseMarkdown: (token2, helpers) => {
+ if (token2.type !== "list_item") {
return [];
}
let content = [];
- if (token.tokens && token.tokens.length > 0) {
- const hasParagraphTokens = token.tokens.some((t) => t.type === "paragraph");
+ if (token2.tokens && token2.tokens.length > 0) {
+ const hasParagraphTokens = token2.tokens.some((t) => t.type === "paragraph");
if (hasParagraphTokens) {
- content = helpers.parseChildren(token.tokens);
+ content = helpers.parseChildren(token2.tokens);
} else {
- const firstToken = token.tokens[0];
+ const firstToken = token2.tokens[0];
if (firstToken && firstToken.type === "text" && firstToken.tokens && firstToken.tokens.length > 0) {
const inlineContent = helpers.parseInline(firstToken.tokens);
content = [
@@ -32766,13 +34796,13 @@ var ListItem = Node3.create({
content: inlineContent
}
];
- if (token.tokens.length > 1) {
- const remainingTokens = token.tokens.slice(1);
+ if (token2.tokens.length > 1) {
+ const remainingTokens = token2.tokens.slice(1);
const additionalContent = helpers.parseChildren(remainingTokens);
content.push(...additionalContent);
}
} else {
- content = helpers.parseChildren(token.tokens);
+ content = helpers.parseChildren(token2.tokens);
}
}
}
@@ -33226,12 +35256,12 @@ var OrderedList = Node3.create({
return start === 1 ? ["ol", mergeAttributes(this.options.HTMLAttributes, attributesWithoutStart), 0] : ["ol", mergeAttributes(this.options.HTMLAttributes, HTMLAttributes), 0];
},
markdownTokenName: "list",
- parseMarkdown: (token, helpers) => {
- if (token.type !== "list" || !token.ordered) {
+ parseMarkdown: (token2, helpers) => {
+ if (token2.type !== "list" || !token2.ordered) {
return [];
}
- const startValue = token.start || 1;
- const content = token.items ? parseListItems(token.items, helpers) : [];
+ const startValue = token2.start || 1;
+ const content = token2.items ? parseListItems(token2.items, helpers) : [];
if (startValue !== 1) {
return {
type: "orderedList",
@@ -33376,20 +35406,20 @@ var TaskItem = Node3.create({
["div", 0]
];
},
- parseMarkdown: (token, h2) => {
+ parseMarkdown: (token2, h2) => {
const content = [];
- if (token.tokens && token.tokens.length > 0) {
- content.push(h2.createNode("paragraph", {}, h2.parseInline(token.tokens)));
- } else if (token.text) {
- content.push(h2.createNode("paragraph", {}, [h2.createNode("text", { text: token.text })]));
+ if (token2.tokens && token2.tokens.length > 0) {
+ content.push(h2.createNode("paragraph", {}, h2.parseInline(token2.tokens)));
+ } else if (token2.text) {
+ content.push(h2.createNode("paragraph", {}, [h2.createNode("text", { text: token2.text })]));
} else {
content.push(h2.createNode("paragraph", {}, []));
}
- if (token.nestedTokens && token.nestedTokens.length > 0) {
- const nestedContent = h2.parseChildren(token.nestedTokens);
+ if (token2.nestedTokens && token2.nestedTokens.length > 0) {
+ const nestedContent = h2.parseChildren(token2.nestedTokens);
content.push(...nestedContent);
}
- return h2.createNode("taskItem", { checked: token.checked || false }, content);
+ return h2.createNode("taskItem", { checked: token2.checked || false }, content);
},
renderMarkdown: (node, h2) => {
var _a;
@@ -33537,8 +35567,8 @@ var TaskList = Node3.create({
renderHTML({ HTMLAttributes }) {
return ["ul", mergeAttributes(this.options.HTMLAttributes, HTMLAttributes, { "data-type": this.name }), 0];
},
- parseMarkdown: (token, h2) => {
- return h2.createNode("taskList", {}, h2.parseChildren(token.items || []));
+ parseMarkdown: (token2, h2) => {
+ return h2.createNode("taskList", {}, h2.parseChildren(token2.items || []));
},
renderMarkdown: (node, h2) => {
if (!node.content) {
@@ -33684,8 +35714,8 @@ var Paragraph = Node3.create({
renderHTML({ HTMLAttributes }) {
return ["p", mergeAttributes(this.options.HTMLAttributes, HTMLAttributes), 0];
},
- parseMarkdown: (token, helpers) => {
- const tokens = token.tokens || [];
+ parseMarkdown: (token2, helpers) => {
+ const tokens = token2.tokens || [];
if (tokens.length === 1 && tokens[0].type === "image") {
return helpers.parseChildren([tokens[0]]);
}
@@ -33749,8 +35779,8 @@ var Strike = Mark2.create({
return ["s", mergeAttributes(this.options.HTMLAttributes, HTMLAttributes), 0];
},
markdownTokenName: "del",
- parseMarkdown: (token, helpers) => {
- return helpers.applyMark("strike", helpers.parseInline(token.tokens || []));
+ parseMarkdown: (token2, helpers) => {
+ return helpers.applyMark("strike", helpers.parseInline(token2.tokens || []));
},
renderMarkdown: (node, h2) => {
return `~~${h2.renderChildren(node)}~~`;
@@ -33793,10 +35823,10 @@ var Strike = Mark2.create({
var Text = Node3.create({
name: "text",
group: "inline",
- parseMarkdown: (token) => {
+ parseMarkdown: (token2) => {
return {
type: "text",
- text: token.text || ""
+ text: token2.text || ""
};
},
renderMarkdown: (node) => node.text || ""
@@ -33823,8 +35853,8 @@ var Underline = Mark2.create({
renderHTML({ HTMLAttributes }) {
return ["u", mergeAttributes(this.options.HTMLAttributes, HTMLAttributes), 0];
},
- parseMarkdown(token, helpers) {
- return helpers.applyMark(this.name || "underline", helpers.parseInline(token.tokens || []));
+ parseMarkdown(token2, helpers) {
+ return helpers.applyMark(this.name || "underline", helpers.parseInline(token2.tokens || []));
},
renderMarkdown(node, helpers) {
return `++${helpers.renderChildren(node)}++`;
@@ -36635,496 +38665,334 @@ var BubbleMenu = /* @__PURE__ */ defineComponent({
};
}
});
-var FloatingMenuView = class {
- constructor({
- editor,
- element,
- view,
- updateDelay = 250,
- resizeDelay = 60,
- options,
- appendTo,
- shouldShow
- }) {
- this.preventHide = false;
- this.isVisible = false;
- this.scrollTarget = window;
- this.shouldShow = ({ view: view2, state }) => {
- const { selection } = state;
- const { $anchor, empty: empty2 } = selection;
- const isRootDepth = $anchor.depth === 1;
- const isEmptyTextBlock = $anchor.parent.isTextblock && !$anchor.parent.type.spec.code && !$anchor.parent.textContent && $anchor.parent.childCount === 0 && !this.getTextContent($anchor.parent);
- if (!view2.hasFocus() || !empty2 || !isRootDepth || !isEmptyTextBlock || !this.editor.isEditable) {
- return false;
- }
- return true;
- };
- this.floatingUIOptions = {
- strategy: "absolute",
- placement: "right",
- offset: 8,
- flip: {},
- shift: {},
- arrow: false,
- size: false,
- autoPlacement: false,
- hide: false,
- inline: false
- };
- this.updateHandler = (view2, selectionChanged, docChanged, oldState) => {
- const { composing } = view2;
- const isSame = !selectionChanged && !docChanged;
- if (composing || isSame) {
- return;
- }
- const shouldShow2 = this.getShouldShow(oldState);
- if (!shouldShow2) {
- this.hide();
- return;
- }
- this.updatePosition();
- this.show();
- };
- this.mousedownHandler = () => {
- this.preventHide = true;
- };
- this.focusHandler = () => {
- setTimeout(() => this.update(this.editor.view));
- };
- this.blurHandler = ({ event }) => {
- var _a2;
- if (this.preventHide) {
- this.preventHide = false;
- return;
- }
- if ((event == null ? void 0 : event.relatedTarget) && ((_a2 = this.element.parentNode) == null ? void 0 : _a2.contains(event.relatedTarget))) {
- return;
- }
- if ((event == null ? void 0 : event.relatedTarget) === this.editor.view.dom) {
- return;
- }
- this.hide();
- };
- this.transactionHandler = ({ transaction: tr2 }) => {
- const meta = tr2.getMeta("floatingMenu");
- if (meta === "updatePosition") {
- this.updatePosition();
- } else if (meta && typeof meta === "object" && meta.type === "updateOptions") {
- this.updateOptions(meta.options);
- }
- };
- this.resizeHandler = () => {
- if (this.resizeDebounceTimer) {
- clearTimeout(this.resizeDebounceTimer);
- }
- this.resizeDebounceTimer = window.setTimeout(() => {
- this.updatePosition();
- }, this.resizeDelay);
- };
- var _a;
- this.editor = editor;
- this.element = element;
- this.view = view;
- this.updateDelay = updateDelay;
- this.resizeDelay = resizeDelay;
- this.appendTo = appendTo;
- this.scrollTarget = (_a = options == null ? void 0 : options.scrollTarget) != null ? _a : window;
- this.floatingUIOptions = {
- ...this.floatingUIOptions,
- ...options
- };
- this.element.tabIndex = 0;
- if (shouldShow) {
- this.shouldShow = shouldShow;
- }
- this.element.addEventListener("mousedown", this.mousedownHandler, { capture: true });
- this.editor.on("focus", this.focusHandler);
- this.editor.on("blur", this.blurHandler);
- this.editor.on("transaction", this.transactionHandler);
- window.addEventListener("resize", this.resizeHandler);
- this.scrollTarget.addEventListener("scroll", this.resizeHandler);
- this.update(view, view.state);
- if (this.getShouldShow()) {
- this.show();
- this.updatePosition();
+var now_1;
+var hasRequiredNow;
+function requireNow() {
+ if (hasRequiredNow) return now_1;
+ hasRequiredNow = 1;
+ var root = require_root();
+ var now = function() {
+ return root.Date.now();
+ };
+ now_1 = now;
+ return now_1;
+}
+var _trimmedEndIndex;
+var hasRequired_trimmedEndIndex;
+function require_trimmedEndIndex() {
+ if (hasRequired_trimmedEndIndex) return _trimmedEndIndex;
+ hasRequired_trimmedEndIndex = 1;
+ var reWhitespace = /\s/;
+ function trimmedEndIndex(string) {
+ var index2 = string.length;
+ while (index2-- && reWhitespace.test(string.charAt(index2))) {
}
+ return index2;
}
- getTextContent(node) {
- return getText(node, { textSerializers: getTextSerializersFromSchema(this.editor.schema) });
+ _trimmedEndIndex = trimmedEndIndex;
+ return _trimmedEndIndex;
+}
+var _baseTrim;
+var hasRequired_baseTrim;
+function require_baseTrim() {
+ if (hasRequired_baseTrim) return _baseTrim;
+ hasRequired_baseTrim = 1;
+ var trimmedEndIndex = require_trimmedEndIndex();
+ var reTrimStart = /^\s+/;
+ function baseTrim(string) {
+ return string ? string.slice(0, trimmedEndIndex(string) + 1).replace(reTrimStart, "") : string;
}
- get middlewares() {
- const middlewares = [];
- if (this.floatingUIOptions.flip) {
- middlewares.push(flip(typeof this.floatingUIOptions.flip !== "boolean" ? this.floatingUIOptions.flip : void 0));
- }
- if (this.floatingUIOptions.shift) {
- middlewares.push(
- shift(typeof this.floatingUIOptions.shift !== "boolean" ? this.floatingUIOptions.shift : void 0)
- );
- }
- if (this.floatingUIOptions.offset) {
- middlewares.push(
- offset(typeof this.floatingUIOptions.offset !== "boolean" ? this.floatingUIOptions.offset : void 0)
- );
- }
- if (this.floatingUIOptions.arrow) {
- middlewares.push(arrow$1(this.floatingUIOptions.arrow));
- }
- if (this.floatingUIOptions.size) {
- middlewares.push(size(typeof this.floatingUIOptions.size !== "boolean" ? this.floatingUIOptions.size : void 0));
- }
- if (this.floatingUIOptions.autoPlacement) {
- middlewares.push(
- autoPlacement(
- typeof this.floatingUIOptions.autoPlacement !== "boolean" ? this.floatingUIOptions.autoPlacement : void 0
- )
- );
- }
- if (this.floatingUIOptions.hide) {
- middlewares.push(hide(typeof this.floatingUIOptions.hide !== "boolean" ? this.floatingUIOptions.hide : void 0));
- }
- if (this.floatingUIOptions.inline) {
- middlewares.push(
- inline(typeof this.floatingUIOptions.inline !== "boolean" ? this.floatingUIOptions.inline : void 0)
- );
- }
- return middlewares;
+ _baseTrim = baseTrim;
+ return _baseTrim;
+}
+var isObjectLike_1;
+var hasRequiredIsObjectLike;
+function requireIsObjectLike() {
+ if (hasRequiredIsObjectLike) return isObjectLike_1;
+ hasRequiredIsObjectLike = 1;
+ function isObjectLike(value) {
+ return value != null && typeof value == "object";
}
- getShouldShow(oldState) {
- var _a;
- const { state } = this.view;
- const { selection } = state;
- const { ranges } = selection;
- const from2 = Math.min(...ranges.map((range) => range.$from.pos));
- const to = Math.max(...ranges.map((range) => range.$to.pos));
- const shouldShow = (_a = this.shouldShow) == null ? void 0 : _a.call(this, {
- editor: this.editor,
- view: this.view,
- state,
- oldState,
- from: from2,
- to
- });
- return shouldShow;
+ isObjectLike_1 = isObjectLike;
+ return isObjectLike_1;
+}
+var isSymbol_1;
+var hasRequiredIsSymbol;
+function requireIsSymbol() {
+ if (hasRequiredIsSymbol) return isSymbol_1;
+ hasRequiredIsSymbol = 1;
+ var baseGetTag = require_baseGetTag(), isObjectLike = requireIsObjectLike();
+ var symbolTag = "[object Symbol]";
+ function isSymbol2(value) {
+ return typeof value == "symbol" || isObjectLike(value) && baseGetTag(value) == symbolTag;
}
- updateOptions(newProps) {
- var _a;
- if (newProps.updateDelay !== void 0) {
- this.updateDelay = newProps.updateDelay;
+ isSymbol_1 = isSymbol2;
+ return isSymbol_1;
+}
+var toNumber_1;
+var hasRequiredToNumber;
+function requireToNumber() {
+ if (hasRequiredToNumber) return toNumber_1;
+ hasRequiredToNumber = 1;
+ var baseTrim = require_baseTrim(), isObject2 = requireIsObject(), isSymbol2 = requireIsSymbol();
+ var NAN = 0 / 0;
+ var reIsBadHex = /^[-+]0x[0-9a-f]+$/i;
+ var reIsBinary = /^0b[01]+$/i;
+ var reIsOctal = /^0o[0-7]+$/i;
+ var freeParseInt = parseInt;
+ function toNumber(value) {
+ if (typeof value == "number") {
+ return value;
}
- if (newProps.resizeDelay !== void 0) {
- this.resizeDelay = newProps.resizeDelay;
+ if (isSymbol2(value)) {
+ return NAN;
}
- if (newProps.appendTo !== void 0) {
- this.appendTo = newProps.appendTo;
+ if (isObject2(value)) {
+ var other = typeof value.valueOf == "function" ? value.valueOf() : value;
+ value = isObject2(other) ? other + "" : other;
}
- if (newProps.shouldShow !== void 0) {
- if (newProps.shouldShow) {
- this.shouldShow = newProps.shouldShow;
+ if (typeof value != "string") {
+ return value === 0 ? value : +value;
+ }
+ value = baseTrim(value);
+ var isBinary = reIsBinary.test(value);
+ return isBinary || reIsOctal.test(value) ? freeParseInt(value.slice(2), isBinary ? 2 : 8) : reIsBadHex.test(value) ? NAN : +value;
+ }
+ toNumber_1 = toNumber;
+ return toNumber_1;
+}
+var debounce_1;
+var hasRequiredDebounce;
+function requireDebounce() {
+ if (hasRequiredDebounce) return debounce_1;
+ hasRequiredDebounce = 1;
+ var isObject2 = requireIsObject(), now = requireNow(), toNumber = requireToNumber();
+ var FUNC_ERROR_TEXT = "Expected a function";
+ var nativeMax = Math.max, nativeMin = Math.min;
+ function debounce2(func, wait, options) {
+ var lastArgs, lastThis, maxWait, result, timerId, lastCallTime, lastInvokeTime = 0, leading = false, maxing = false, trailing = true;
+ if (typeof func != "function") {
+ throw new TypeError(FUNC_ERROR_TEXT);
+ }
+ wait = toNumber(wait) || 0;
+ if (isObject2(options)) {
+ leading = !!options.leading;
+ maxing = "maxWait" in options;
+ maxWait = maxing ? nativeMax(toNumber(options.maxWait) || 0, wait) : maxWait;
+ trailing = "trailing" in options ? !!options.trailing : trailing;
+ }
+ function invokeFunc(time) {
+ var args = lastArgs, thisArg = lastThis;
+ lastArgs = lastThis = void 0;
+ lastInvokeTime = time;
+ result = func.apply(thisArg, args);
+ return result;
+ }
+ function leadingEdge(time) {
+ lastInvokeTime = time;
+ timerId = setTimeout(timerExpired, wait);
+ return leading ? invokeFunc(time) : result;
+ }
+ function remainingWait(time) {
+ var timeSinceLastCall = time - lastCallTime, timeSinceLastInvoke = time - lastInvokeTime, timeWaiting = wait - timeSinceLastCall;
+ return maxing ? nativeMin(timeWaiting, maxWait - timeSinceLastInvoke) : timeWaiting;
+ }
+ function shouldInvoke(time) {
+ var timeSinceLastCall = time - lastCallTime, timeSinceLastInvoke = time - lastInvokeTime;
+ return lastCallTime === void 0 || timeSinceLastCall >= wait || timeSinceLastCall < 0 || maxing && timeSinceLastInvoke >= maxWait;
+ }
+ function timerExpired() {
+ var time = now();
+ if (shouldInvoke(time)) {
+ return trailingEdge(time);
}
+ timerId = setTimeout(timerExpired, remainingWait(time));
}
- if (newProps.options !== void 0) {
- const newScrollTarget = (_a = newProps.options.scrollTarget) != null ? _a : window;
- if (newScrollTarget !== this.scrollTarget) {
- this.scrollTarget.removeEventListener("scroll", this.resizeHandler);
- this.scrollTarget = newScrollTarget;
- this.scrollTarget.addEventListener("scroll", this.resizeHandler);
+ function trailingEdge(time) {
+ timerId = void 0;
+ if (trailing && lastArgs) {
+ return invokeFunc(time);
}
- this.floatingUIOptions = {
- ...this.floatingUIOptions,
- ...newProps.options
- };
+ lastArgs = lastThis = void 0;
+ return result;
}
- }
- updatePosition() {
- const { selection } = this.editor.state;
- const domRect = posToDOMRect(this.view, selection.from, selection.to);
- const virtualElement = {
- getBoundingClientRect: () => domRect,
- getClientRects: () => [domRect]
- };
- computePosition(virtualElement, this.element, {
- placement: this.floatingUIOptions.placement,
- strategy: this.floatingUIOptions.strategy,
- middleware: this.middlewares
- }).then(({ x: x2, y: y2, strategy, middlewareData }) => {
- var _a, _b;
- if (((_a = middlewareData.hide) == null ? void 0 : _a.referenceHidden) || ((_b = middlewareData.hide) == null ? void 0 : _b.escaped)) {
- this.element.style.visibility = "hidden";
- return;
+ function cancel() {
+ if (timerId !== void 0) {
+ clearTimeout(timerId);
}
- this.element.style.visibility = "visible";
- this.element.style.width = "max-content";
- this.element.style.position = strategy;
- this.element.style.left = `${x2}px`;
- this.element.style.top = `${y2}px`;
- if (this.isVisible && this.floatingUIOptions.onUpdate) {
- this.floatingUIOptions.onUpdate();
+ lastInvokeTime = 0;
+ lastArgs = lastCallTime = lastThis = timerId = void 0;
+ }
+ function flush() {
+ return timerId === void 0 ? result : trailingEdge(now());
+ }
+ function debounced() {
+ var time = now(), isInvoking = shouldInvoke(time);
+ lastArgs = arguments;
+ lastThis = this;
+ lastCallTime = time;
+ if (isInvoking) {
+ if (timerId === void 0) {
+ return leadingEdge(lastCallTime);
+ }
+ if (maxing) {
+ clearTimeout(timerId);
+ timerId = setTimeout(timerExpired, wait);
+ return invokeFunc(lastCallTime);
+ }
}
- });
- }
- update(view, oldState) {
- const selectionChanged = !(oldState == null ? void 0 : oldState.selection.eq(view.state.selection));
- const docChanged = !(oldState == null ? void 0 : oldState.doc.eq(view.state.doc));
- this.updateHandler(view, selectionChanged, docChanged, oldState);
- }
- show() {
- var _a;
- if (this.isVisible) {
- return;
- }
- this.element.style.visibility = "visible";
- this.element.style.opacity = "1";
- const appendToElement = typeof this.appendTo === "function" ? this.appendTo() : this.appendTo;
- (_a = appendToElement != null ? appendToElement : this.view.dom.parentElement) == null ? void 0 : _a.appendChild(this.element);
- if (this.floatingUIOptions.onShow) {
- this.floatingUIOptions.onShow();
- }
- this.isVisible = true;
- }
- hide() {
- if (!this.isVisible) {
- return;
- }
- this.element.style.visibility = "hidden";
- this.element.style.opacity = "0";
- this.element.remove();
- if (this.floatingUIOptions.onHide) {
- this.floatingUIOptions.onHide();
- }
- this.isVisible = false;
- }
- destroy() {
- this.hide();
- this.element.removeEventListener("mousedown", this.mousedownHandler, { capture: true });
- window.removeEventListener("resize", this.resizeHandler);
- this.scrollTarget.removeEventListener("scroll", this.resizeHandler);
- this.editor.off("focus", this.focusHandler);
- this.editor.off("blur", this.blurHandler);
- this.editor.off("transaction", this.transactionHandler);
- if (this.floatingUIOptions.onDestroy) {
- this.floatingUIOptions.onDestroy();
- }
- }
-};
-var FloatingMenuPlugin = (options) => {
- return new Plugin({
- key: typeof options.pluginKey === "string" ? new PluginKey(options.pluginKey) : options.pluginKey,
- view: (view) => new FloatingMenuView({ view, ...options })
- });
-};
-var FloatingMenu = /* @__PURE__ */ defineComponent({
- name: "FloatingMenu",
- inheritAttrs: false,
- props: {
- pluginKey: {
- // TODO: TypeScript breaks :(
- // type: [String, Object as PropType>],
- type: null,
- default: "floatingMenu"
- },
- editor: {
- type: Object,
- required: true
- },
- updateDelay: {
- type: Number,
- default: void 0
- },
- resizeDelay: {
- type: Number,
- default: void 0
- },
- options: {
- type: Object,
- default: () => ({})
- },
- appendTo: {
- type: [Object, Function],
- default: void 0
- },
- shouldShow: {
- type: Function,
- default: null
- }
- },
- setup(props, { slots, attrs }) {
- const root = /* @__PURE__ */ ref(null);
- onMounted(() => {
- const { pluginKey, editor, updateDelay, resizeDelay, options, appendTo, shouldShow } = props;
- const el = root.value;
- if (!el) {
- return;
+ if (timerId === void 0) {
+ timerId = setTimeout(timerExpired, wait);
}
- el.style.visibility = "hidden";
- el.style.position = "absolute";
- el.remove();
- editor.registerPlugin(
- FloatingMenuPlugin({
- pluginKey,
- editor,
- element: el,
- updateDelay,
- resizeDelay,
- options,
- appendTo,
- shouldShow
- })
- );
- });
- onBeforeUnmount(() => {
- const { pluginKey, editor } = props;
- editor.unregisterPlugin(pluginKey);
- });
- return () => {
- var _a;
- return h$1("div", { ref: root, ...attrs }, (_a = slots.default) == null ? void 0 : _a.call(slots));
- };
+ return result;
+ }
+ debounced.cancel = cancel;
+ debounced.flush = flush;
+ return debounced;
}
-});
-const _hoisted_1 = {
+ debounce_1 = debounce2;
+ return debounce_1;
+}
+var debounceExports = requireDebounce();
+const _debounce = /* @__PURE__ */ getDefaultExportFromCjs(debounceExports);
+const _hoisted_1$1 = {
key: 0,
class: "editor layout-block"
};
-const _hoisted_2 = { class: "bubble-menu" };
-const _hoisted_3 = { class: "floating-menu" };
-const initialMarkdown = `# My Document
-
-This is a paragraph.
-
-# Section
-
-- Item one
-- Item two
-
----
-# Header Three
-
-[Link](https://google.com)
-`;
+const _hoisted_2$1 = { class: "bubble-menu" };
const _sfc_main$1 = {
- __name: "Index",
+ __name: "Editor",
setup(__props) {
+ const route = useRoute();
+ const id = route.params.id;
+ const { loadNote, updateNoteContent, updateNoteMetadata } = useNotes();
const CustomDocument = index_default$1.extend({
content: "heading block*"
});
- const editor = new Editor2({
- extensions: [
- CustomDocument,
- index_default.configure({
- document: false,
- heading: { levels: [1] },
- trailingNode: {
- node: "paragraph"
- }
- }),
- Placeholder.configure({
- placeholder: ({ node }) => {
- if (node.type.name === "heading") {
- return "Title";
+ const editor = /* @__PURE__ */ shallowRef();
+ const updateNote = _debounce(async ({ editor: editor2 }) => {
+ const markdown = editor2.getMarkdown();
+ await updateNoteContent(id, markdown);
+ updateTitle(editor2);
+ }, 300);
+ let lastTitle;
+ const updateTitle = _debounce(async (editor2) => {
+ const doc2 = editor2.state.doc;
+ const firstNode = doc2.firstChild;
+ if (!firstNode || firstNode.type.name !== "heading") return;
+ const newTitle = firstNode.textContent.trim() || "Untitled";
+ if (newTitle === lastTitle) return;
+ lastTitle = newTitle;
+ await updateNoteMetadata(id, { title: newTitle });
+ }, 300);
+ onMounted(async () => {
+ const note = await loadNote(id);
+ lastTitle = note.title;
+ editor.value = new Editor2({
+ extensions: [
+ CustomDocument,
+ index_default.configure({
+ document: false,
+ heading: { levels: [1] },
+ trailingNode: {
+ node: "paragraph"
}
- }
- }),
- Markdown,
- index_default$2
- ],
- content: initialMarkdown,
- contentType: "markdown"
+ }),
+ Placeholder.configure({
+ placeholder: ({ node }) => {
+ if (node.type.name === "heading") {
+ return "Title";
+ }
+ }
+ }),
+ Markdown,
+ index_default$2
+ ],
+ content: note.content,
+ contentType: "markdown",
+ onUpdate: updateNote
+ });
});
onBeforeUnmount(() => {
- editor.destroy();
+ editor.value?.destroy?.();
});
return (_ctx, _cache) => {
- return unref(editor) ? (openBlock(), createElementBlock("div", _hoisted_1, [
- createVNode(unref(BubbleMenu), { editor: unref(editor) }, {
+ return editor.value ? (openBlock(), createElementBlock("div", _hoisted_1$1, [
+ createVNode(unref(BubbleMenu), { editor: editor.value }, {
default: withCtx(() => [
- createBaseVNode("div", _hoisted_2, [
+ createBaseVNode("div", _hoisted_2$1, [
createBaseVNode("button", {
- onClick: _cache[0] || (_cache[0] = ($event) => unref(editor).chain().focus().toggleBold().run()),
- class: normalizeClass({ active: unref(editor).isActive("bold") })
+ onClick: _cache[0] || (_cache[0] = ($event) => editor.value.chain().focus().toggleBold().run()),
+ class: normalizeClass({ active: editor.value.isActive("bold") })
}, " Bold ", 2),
createBaseVNode("button", {
- onClick: _cache[1] || (_cache[1] = ($event) => unref(editor).chain().focus().toggleItalic().run()),
- class: normalizeClass({ active: unref(editor).isActive("italic") })
+ onClick: _cache[1] || (_cache[1] = ($event) => editor.value.chain().focus().toggleItalic().run()),
+ class: normalizeClass({ active: editor.value.isActive("italic") })
}, " Italic ", 2)
])
]),
_: 1
}, 8, ["editor"]),
- createVNode(unref(FloatingMenu), { editor: unref(editor) }, {
- default: withCtx(() => [
- createBaseVNode("div", _hoisted_3, [
- createBaseVNode("button", {
- onClick: _cache[2] || (_cache[2] = ($event) => unref(editor).chain().focus().toggleHeading({ level: 1 }).run()),
- class: normalizeClass({
- active: unref(editor).isActive("heading", { level: 1 })
- })
- }, " H1 ", 2),
- createBaseVNode("button", {
- onClick: _cache[3] || (_cache[3] = ($event) => unref(editor).chain().focus().toggleBulletList().run()),
- class: normalizeClass({ active: unref(editor).isActive("bulletList") })
- }, " Bullet List ", 2),
- createBaseVNode("button", {
- onClick: _cache[4] || (_cache[4] = ($event) => unref(editor).chain().focus().toggleOrderedList().run()),
- class: normalizeClass({ active: unref(editor).isActive("orderedlist") })
- }, " Number List ", 2)
- ])
- ]),
- _: 1
- }, 8, ["editor"]),
createVNode(unref(EditorContent), {
- editor: unref(editor),
+ editor: editor.value,
class: "editor-wrap"
}, null, 8, ["editor"])
])) : createCommentVNode("", true);
};
}
};
+const _hoisted_1 = { class: "category layout-block" };
+const _hoisted_2 = { class: "notes" };
const _sfc_main = {
- __name: "App",
+ __name: "Category",
setup(__props) {
- const { height } = /* @__PURE__ */ useWindowSize();
- const classes = computed(() => [
- "container",
- { "fonts-ready": !fontsLoading.value },
- "theme-dark"
- ]);
- const fontsLoading = /* @__PURE__ */ ref(true);
+ const route = useRoute();
+ const id = route.params.id;
+ const { categories: categories2, loadCategoryNotes } = useNotes();
+ const notes = /* @__PURE__ */ ref();
onMounted(async () => {
- loadFonts([
- {
- name: "Leibniz Fraktur",
- weights: [400]
- },
- {
- name: "Geist Mono",
- weights: [400, 700]
- }
- ]).then(() => {
- fontsLoading.value = false;
- }).catch(() => {
- fontsLoading.value = false;
- });
+ notes.value = await loadCategoryNotes(id);
+ });
+ const categoryIndex = computed(() => {
+ return categories2.value?.findIndex((category) => category === id) || 0;
});
- const styles = computed(() => ({
- "--vh": height.value ? height.value / 100 + "px" : "100vh"
- }));
return (_ctx, _cache) => {
- return openBlock(), createBlock(_sfc_main$2, {
- root: "",
- options: { duration: 1 }
- }, {
- default: withCtx(() => [
- createBaseVNode("div", {
- class: normalizeClass(classes.value),
- style: normalizeStyle(styles.value)
- }, [
- createVNode(_sfc_main$1)
- ], 6)
- ]),
- _: 1
- });
+ const _component_router_link = resolveComponent("router-link");
+ return openBlock(), createElementBlock("main", _hoisted_1, [
+ createVNode(_component_router_link, {
+ class: "back",
+ to: "/"
+ }, {
+ default: withCtx(() => [..._cache[0] || (_cache[0] = [
+ createTextVNode("<- Go Back", -1)
+ ])]),
+ _: 1
+ }),
+ createVNode(_sfc_main$4, {
+ index: categoryIndex.value,
+ category: unref(id)
+ }, null, 8, ["index", "category"]),
+ createBaseVNode("div", _hoisted_2, [
+ (openBlock(true), createElementBlock(Fragment$1, null, renderList(notes.value, (note) => {
+ return openBlock(), createBlock(_sfc_main$3, {
+ note,
+ key: note.id
+ }, null, 8, ["note"]);
+ }), 128))
+ ])
+ ]);
};
}
};
-createApp(_sfc_main).mount("#app");
+const routes = [
+ { path: "/", name: "directory", component: _sfc_main$2 },
+ { path: "/note/:id", name: "note", component: _sfc_main$1 },
+ { path: "/category/:id", name: "category", component: _sfc_main }
+];
+const router = createRouter({
+ history: createWebHistory(),
+ routes
+});
+const app = createApp(_sfc_main$5);
+app.use(router);
+app.mount("#app");
diff --git a/out/renderer/index.html b/out/renderer/index.html
index 92f623c..9180e4d 100644
--- a/out/renderer/index.html
+++ b/out/renderer/index.html
@@ -8,8 +8,8 @@
http-equiv="Content-Security-Policy"
content="default-src 'self'; script-src 'self'; style-src 'self' 'unsafe-inline'; img-src 'self' data:"
/>
-
-
+
+
diff --git a/package-lock.json b/package-lock.json
index 170dcbf..6597b72 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -22,12 +22,12 @@
"electron-updater": "^6.3.9",
"fecha": "^4.2.3",
"flexsearch": "^0.8.212",
- "gray-matter": "^4.0.3",
"gsap": "^3.14.2",
"lenis": "^1.3.17",
"lodash": "^4.17.23",
"sass": "^1.97.3",
"sass-embedded": "^1.97.3",
+ "takerofnotes-plugin-filesystem": "^1.6.0",
"tempus": "^1.0.0-dev.17",
"uuid": "^13.0.0",
"vue-router": "^5.0.3"
@@ -8314,6 +8314,25 @@
"node": ">=16.0.0"
}
},
+ "node_modules/takerofnotes-plugin-filesystem": {
+ "version": "1.6.0",
+ "resolved": "https://registry.npmjs.org/takerofnotes-plugin-filesystem/-/takerofnotes-plugin-filesystem-1.6.0.tgz",
+ "integrity": "sha512-wUcH8lV6ges9zkEU7b7h1SkDcvgoJ+TLfogqRirLg38fdJ/LGat6BBfItO3QlalkYobsb4wglEfd7wg4f4erJA==",
+ "license": "MIT",
+ "dependencies": {
+ "gray-matter": "^4.0.3",
+ "takerofnotes-plugin-sdk": "^0.4.0"
+ }
+ },
+ "node_modules/takerofnotes-plugin-sdk": {
+ "version": "0.4.0",
+ "resolved": "https://registry.npmjs.org/takerofnotes-plugin-sdk/-/takerofnotes-plugin-sdk-0.4.0.tgz",
+ "integrity": "sha512-C1bXun19Zh603Aq/7sEI4c3dZ8QEUiz51ikDPJm5g+JWoQkH77OH6AY19SN+eOKnqEmY1yw3JYEVd//mJ06UAA==",
+ "license": "MIT",
+ "dependencies": {
+ "zod": "^4.3.6"
+ }
+ },
"node_modules/tar": {
"version": "7.5.9",
"resolved": "https://registry.npmjs.org/tar/-/tar-7.5.9.tgz",
@@ -9535,6 +9554,15 @@
"funding": {
"url": "https://github.com/sponsors/sindresorhus"
}
+ },
+ "node_modules/zod": {
+ "version": "4.3.6",
+ "resolved": "https://registry.npmjs.org/zod/-/zod-4.3.6.tgz",
+ "integrity": "sha512-rftlrkhHZOcjDwkGlnUtZZkvaPHCsDATp4pGpuOOMDaTdDDXF91wuVDJoWoPsKX/3YPQ5fHuF3STjcYyKr+Qhg==",
+ "license": "MIT",
+ "funding": {
+ "url": "https://github.com/sponsors/colinhacks"
+ }
}
}
}
diff --git a/package.json b/package.json
index 800bdb7..bf7fccf 100644
--- a/package.json
+++ b/package.json
@@ -37,12 +37,12 @@
"electron-updater": "^6.3.9",
"fecha": "^4.2.3",
"flexsearch": "^0.8.212",
- "gray-matter": "^4.0.3",
"gsap": "^3.14.2",
"lenis": "^1.3.17",
"lodash": "^4.17.23",
"sass": "^1.97.3",
"sass-embedded": "^1.97.3",
+ "takerofnotes-plugin-filesystem": "^1.6.0",
"tempus": "^1.0.0-dev.17",
"uuid": "^13.0.0",
"vue-router": "^5.0.3"
diff --git a/src/main/core/BaseNotesAdapter.js b/src/main/core/BaseNotesAdapter.js
deleted file mode 100644
index be74ed8..0000000
--- a/src/main/core/BaseNotesAdapter.js
+++ /dev/null
@@ -1,25 +0,0 @@
-export default class BaseNotesAdapter {
- constructor(config = {}) {
- this.config = config
- }
-
- async init() {
- throw new Error('init() not implemented')
- }
-
- async getAll() {
- throw new Error('getAll() not implemented')
- }
-
- async create(note) {
- throw new Error('create() not implemented')
- }
-
- async update(note) {
- throw new Error('update() not implemented')
- }
-
- async delete(id) {
- throw new Error('delete() not implemented')
- }
-}
diff --git a/src/main/core/PluginConfig.js b/src/main/core/PluginConfig.js
index 7b804cf..810dfc4 100644
--- a/src/main/core/PluginConfig.js
+++ b/src/main/core/PluginConfig.js
@@ -2,13 +2,34 @@ import fs from 'fs/promises'
import path from 'path'
import { app } from 'electron'
+const USER_DATA_STRING = '__DEFAULT_USER_DATA__'
+
export default class PluginConfig {
constructor(defaultPlugin) {
this.defaultPlugin = defaultPlugin
-
this.configPath = path.join(app.getPath('userData'), 'config.json')
}
+ // Helper to replace placeholders with dynamic values, recursively
+ _resolveDefaults(config) {
+ if (Array.isArray(config)) {
+ return config.map((item) => this._resolveDefaults(item))
+ } else if (config && typeof config === 'object') {
+ const resolved = {}
+ for (const [key, value] of Object.entries(config)) {
+ resolved[key] = this._resolveDefaults(value)
+ }
+ return resolved
+ } else if (
+ typeof config === 'string' &&
+ config.includes(USER_DATA_STRING)
+ ) {
+ return config.replace(USER_DATA_STRING, app.getPath('userData'))
+ } else {
+ return config
+ }
+ }
+
async load() {
let parsed
@@ -32,6 +53,9 @@ export default class PluginConfig {
}
await this.write(parsed)
+ } else {
+ // Ensure any "__DEFAULT_USER_DATA__" values are resolved on load
+ parsed.adapterConfig = this._resolveDefaults(parsed.adapterConfig)
}
return parsed
@@ -43,9 +67,15 @@ export default class PluginConfig {
// Ensure directory exists
await fs.mkdir(dir, { recursive: true })
+ // Resolve defaults before writing
+ const resolvedConfig = {
+ ...configObject,
+ adapterConfig: this._resolveDefaults(configObject.adapterConfig),
+ }
+
await fs.writeFile(
this.configPath,
- JSON.stringify(configObject, null, 2),
+ JSON.stringify(resolvedConfig, null, 2),
'utf8',
)
}
diff --git a/src/main/index.js b/src/main/index.js
index b3ce091..e36c037 100644
--- a/src/main/index.js
+++ b/src/main/index.js
@@ -1,7 +1,7 @@
import { electronApp, optimizer, is } from '@electron-toolkit/utils'
import { app, shell, BrowserWindow, ipcMain } from 'electron'
+import filesystemPlugin from 'takerofnotes-plugin-filesystem'
import PluginRegistry from './core/PluginRegistry.js'
-import filesystemPlugin from './plugins/filesystem'
import PluginConfig from './core/PluginConfig.js'
import NotesAPI from './core/NotesAPI.js'
import { join } from 'path'
@@ -84,7 +84,8 @@ app.whenReady().then(async () => {
const registry = new PluginRegistry()
// Register built-in plugins
- registry.register(filesystemPlugin)
+ // TODO figure out why export is under default
+ registry.register(filesystemPlugin.default)
// Pull plugin config
const config = await new PluginConfig(filesystemPlugin).load()
diff --git a/src/main/notesAPI.js b/src/main/notesAPI.js
deleted file mode 100644
index 5951f00..0000000
--- a/src/main/notesAPI.js
+++ /dev/null
@@ -1,159 +0,0 @@
-import fs from 'fs/promises'
-import path from 'path'
-import { app } from 'electron'
-import matter from 'gray-matter'
-import { Index } from 'flexsearch'
-import crypto from 'crypto'
-
-export default class NotesAPI {
- constructor() {
- this.notesDir = path.join(app.getPath('userData'), 'notes')
- this.notesCache = new Map()
-
- this.index = new Index({
- tokenize: 'tolerant',
- resolution: 9,
- })
- }
-
- async init() {
- await fs.mkdir(this.notesDir, { recursive: true })
- await this._loadAllNotes()
- }
-
- async _loadAllNotes() {
- const files = await fs.readdir(this.notesDir)
-
- for (const file of files) {
- if (!file.endsWith('.md')) continue
-
- const fullPath = path.join(this.notesDir, file)
- const raw = await fs.readFile(fullPath, 'utf8')
- const parsed = matter(raw)
-
- const note = {
- ...parsed.data,
- content: parsed.content,
- }
-
- this.notesCache.set(note.id, note)
- this.index.add(note.id, note.title + note.content)
- }
- }
-
- async _writeNoteFile(note) {
- const filePath = path.join(this.notesDir, `${note.id}.md`)
-
- const fileContent = matter.stringify(note.content, {
- id: note.id,
- title: note.title,
- category: note.category ?? null,
- createdAt: note.createdAt,
- updatedAt: note.updatedAt,
- })
-
- await fs.writeFile(filePath, fileContent, 'utf8')
- }
-
- /* -----------------------
- Public API
- ------------------------*/
- getCategories() {
- const categories = new Set()
-
- for (const note of this.notesCache.values()) {
- if (note.category) {
- categories.add(note.category)
- }
- }
-
- return Array.from(categories).sort()
- }
-
- getCategoryNotes(categoryName) {
- return Array.from(this.notesCache.values())
- .filter((n) => n.category === categoryName)
- .sort((a, b) => new Date(b.updatedAt) - new Date(a.updatedAt))
- }
-
- getNote(id) {
- return this.notesCache.get(id) ?? null
- }
-
- async createNote(metadata = {}, content = '') {
- const id = crypto.randomUUID()
- const now = new Date().toISOString()
-
- const note = {
- id,
- title: metadata.title || 'Untitled',
- category: metadata.category || null,
- createdAt: now,
- updatedAt: now,
- content,
- }
-
- console.log(note)
-
- this.notesCache.set(id, note)
- this.index.add(id, note.title + '\n' + content)
-
- await this._writeNoteFile(note)
-
- return note
- }
-
- async deleteNote(id) {
- const filePath = path.join(this.notesDir, `${id}.md`)
- await fs.unlink(filePath)
- this.notesCache.delete(id)
- this.index.remove(id)
- }
-
- async updateNote(id, content) {
- const note = this.notesCache.get(id)
- if (!note) throw new Error('Note not found')
-
- note.content = content
- note.updatedAt = new Date().toISOString()
-
- this.index.update(id, note.title + '\n' + content)
-
- await this._writeNoteFile(note)
-
- return note
- }
-
- async updateNoteMetadata(id, updates = {}) {
- const note = this.notesCache.get(id)
- if (!note) throw new Error('Note not found')
-
- const allowedFields = ['title', 'category']
- for (const key of Object.keys(updates)) {
- if (!allowedFields.includes(key)) {
- throw new Error(`Invalid metadata field: ${key}`)
- }
- }
-
- if (updates.title !== undefined) {
- note.title = updates.title
- }
-
- if (updates.category !== undefined) {
- note.category = updates.category
- }
-
- note.updatedAt = new Date().toISOString()
-
- this.index.update(id, note.title + '\n' + note.content)
-
- await this._writeNoteFile(note)
-
- return note
- }
-
- search(query) {
- const ids = this.index.search(query)
- return ids.map((id) => this.notesCache.get(id))
- }
-}
diff --git a/src/main/plugins/filesystem/FileSystemAdapter.js b/src/main/plugins/filesystem/FileSystemAdapter.js
deleted file mode 100644
index 2c1d1a2..0000000
--- a/src/main/plugins/filesystem/FileSystemAdapter.js
+++ /dev/null
@@ -1,65 +0,0 @@
-import BaseNotesAdapter from '../../core/BaseNotesAdapter.js'
-import matter from 'gray-matter'
-import fs from 'fs/promises'
-import path from 'path'
-
-export default class FileSystemNotesAdapter extends BaseNotesAdapter {
- constructor(config) {
- super()
-
- for (const field in config) {
- this[field] = config[field]
- }
- }
-
- async init() {
- await fs.mkdir(this.notesDir, { recursive: true })
- }
-
- async getAll() {
- const files = await fs.readdir(this.notesDir)
- const notes = []
-
- for (const file of files) {
- if (!file.endsWith('.md')) continue
-
- const fullPath = path.join(this.notesDir, file)
- const raw = await fs.readFile(fullPath, 'utf8')
- const parsed = matter(raw)
-
- notes.push({
- ...parsed.data,
- content: parsed.content,
- })
- }
-
- return notes
- }
-
- async create(note) {
- await this._write(note)
- }
-
- async update(note) {
- await this._write(note)
- }
-
- async delete(id) {
- const filePath = path.join(this.notesDir, `${id}.md`)
- await fs.unlink(filePath)
- }
-
- async _write(note) {
- const filePath = path.join(this.notesDir, `${note.id}.md`)
-
- const fileContent = matter.stringify(note.content, {
- id: note.id,
- title: note.title,
- category: note.category ?? null,
- createdAt: note.createdAt,
- updatedAt: note.updatedAt,
- })
-
- await fs.writeFile(filePath, fileContent, 'utf8')
- }
-}
diff --git a/src/main/plugins/filesystem/index.js b/src/main/plugins/filesystem/index.js
deleted file mode 100644
index 3b246c5..0000000
--- a/src/main/plugins/filesystem/index.js
+++ /dev/null
@@ -1,24 +0,0 @@
-import path from 'path'
-import { app } from 'electron'
-import FileSystemAdapter from './FileSystemAdapter.js'
-
-export default {
- id: 'filesystem',
- name: 'Local Filesystem',
- description: 'Stores notes as markdown files locally.',
- version: '1.0.0',
-
- configSchema: [
- {
- key: 'notesDir',
- label: 'Notes Directory',
- type: 'directory',
- default: path.join(app.getPath('userData'), 'notes'),
- required: true,
- },
- ],
-
- createAdapter(config) {
- return new FileSystemAdapter(config)
- },
-}