@dskripchenko/markdown-editor 0.1.0 → 0.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +12 -0
- package/dist/index.cjs +58 -16
- package/dist/index.d.ts +23 -4
- package/dist/index.mjs +58 -17
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,17 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## 0.2.1
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- dc2c5a0: `image-base` without a scheme (`/media/`): pictures shown from it are saved back relative as well.
|
|
8
|
+
|
|
9
|
+
## 0.2.0
|
|
10
|
+
|
|
11
|
+
### Minor Changes
|
|
12
|
+
|
|
13
|
+
- 127c7b2: `image-base` and `link-base`: a document's relative pictures show from its folder in the visual editor and the preview and are saved back as written (`img/a.png`, `../a.png`); relative links of the preview resolve against `link-base`. `fromMarkdown`, `toMarkdown` and `normalize` take `{ imageBase }`; `relativeTo` is exported.
|
|
14
|
+
|
|
3
15
|
## 0.1.0
|
|
4
16
|
|
|
5
17
|
### Minor Changes
|
package/dist/index.cjs
CHANGED
|
@@ -122,12 +122,36 @@ function splitBlocks(markdown) {
|
|
|
122
122
|
function escapeHtml(text) {
|
|
123
123
|
return text.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">");
|
|
124
124
|
}
|
|
125
|
+
/**
|
|
126
|
+
* A URL back to a path relative to `base`, when both share the origin:
|
|
127
|
+
* `<base>img/a.png` → `img/a.png`, `<base's parent>up.png` → `../up.png`.
|
|
128
|
+
* Anything else stays as it is.
|
|
129
|
+
*/
|
|
130
|
+
function relativeTo(url, base) {
|
|
131
|
+
const PLACEHOLDER = "http://base.invalid/";
|
|
132
|
+
let u;
|
|
133
|
+
let b;
|
|
134
|
+
try {
|
|
135
|
+
b = new URL(base, PLACEHOLDER);
|
|
136
|
+
u = new URL(url, b);
|
|
137
|
+
} catch {
|
|
138
|
+
return url;
|
|
139
|
+
}
|
|
140
|
+
if (u.protocol !== b.protocol || u.host !== b.host) return url;
|
|
141
|
+
const from = b.pathname.split("/").slice(0, -1);
|
|
142
|
+
const to = u.pathname.split("/");
|
|
143
|
+
let i = 0;
|
|
144
|
+
while (i < from.length && i < to.length - 1 && from[i] === to[i]) i++;
|
|
145
|
+
if (i === 0 && from.length > 1) return url;
|
|
146
|
+
const rel = [...Array(from.length - i).fill(".."), ...to.slice(i)].join("/");
|
|
147
|
+
return decodeURI(rel) + u.search + u.hash;
|
|
148
|
+
}
|
|
125
149
|
/** Markdown → the HTML the editor edits; source blocks become code blocks of {@link SOURCE_LANG}. */
|
|
126
|
-
function fromMarkdown(markdown) {
|
|
150
|
+
function fromMarkdown(markdown, options = {}) {
|
|
127
151
|
const out = [];
|
|
128
152
|
let pending = [];
|
|
129
153
|
const flush = () => {
|
|
130
|
-
if (pending.length) out.push((0, _dskripchenko_ui.renderMarkdown)(pending.join("\n\n")));
|
|
154
|
+
if (pending.length) out.push((0, _dskripchenko_ui.renderMarkdown)(pending.join("\n\n"), options.imageBase ? { imageBase: options.imageBase } : {}));
|
|
131
155
|
pending = [];
|
|
132
156
|
};
|
|
133
157
|
for (const block of splitBlocks(markdown)) {
|
|
@@ -142,14 +166,18 @@ function fromMarkdown(markdown) {
|
|
|
142
166
|
return out.join("\n");
|
|
143
167
|
}
|
|
144
168
|
var SOURCE_FENCE = new RegExp(`^(\`{3,})${SOURCE_LANG}\\n([\\s\\S]*?)\\n\\1$`, "gm");
|
|
145
|
-
/** The editor's HTML → Markdown; source blocks come back as written. */
|
|
146
|
-
function toMarkdown(html) {
|
|
147
|
-
const
|
|
169
|
+
/** The editor's HTML → Markdown; source blocks come back as written, pictures by their relative paths. */
|
|
170
|
+
function toMarkdown(html, options = {}) {
|
|
171
|
+
const base = options.imageBase;
|
|
172
|
+
const relative = base ? html.replace(/(<img\b[^>]*?\ssrc=")([^"]*)(")/gi, (_m, head, src, tail) => {
|
|
173
|
+
return head + relativeTo(src.replace(/&/g, "&"), base).replace(/&/g, "&") + tail;
|
|
174
|
+
}) : html;
|
|
175
|
+
const md = (0, _dskripchenko_wysiwyg.htmlToMarkdown)(relative).replace(SOURCE_FENCE, (_m, _fence, text) => text);
|
|
148
176
|
return md === "" ? "" : `${md}\n`;
|
|
149
177
|
}
|
|
150
178
|
/** One round: what saving a document unchanged in the editor gives. */
|
|
151
|
-
function normalize(markdown) {
|
|
152
|
-
return toMarkdown(fromMarkdown(markdown));
|
|
179
|
+
function normalize(markdown, options = {}) {
|
|
180
|
+
return toMarkdown(fromMarkdown(markdown, options), options);
|
|
153
181
|
}
|
|
154
182
|
// src/locale.ts
|
|
155
183
|
var en = {
|
|
@@ -211,7 +239,9 @@ var MarkdownEditor_default = /* @__PURE__ */ (0, vue.defineComponent)({
|
|
|
211
239
|
toolbarItems: { default: void 0 },
|
|
212
240
|
slashCommands: { default: void 0 },
|
|
213
241
|
locale: { default: void 0 },
|
|
214
|
-
labels: { default: void 0 }
|
|
242
|
+
labels: { default: void 0 },
|
|
243
|
+
imageBase: { default: void 0 },
|
|
244
|
+
linkBase: { default: void 0 }
|
|
215
245
|
}, {
|
|
216
246
|
"mode": { default: "visual" },
|
|
217
247
|
"modeModifiers": {}
|
|
@@ -226,14 +256,18 @@ var MarkdownEditor_default = /* @__PURE__ */ (0, vue.defineComponent)({
|
|
|
226
256
|
...labelsFor(props.locale ?? kitLocale.value.code),
|
|
227
257
|
...props.labels
|
|
228
258
|
}));
|
|
259
|
+
const options = (0, vue.computed)(() => ({ imageBase: props.imageBase ?? null }));
|
|
229
260
|
const markdown = (0, vue.ref)(props.modelValue);
|
|
230
|
-
const html = (0, vue.ref)(fromMarkdown(props.modelValue));
|
|
261
|
+
const html = (0, vue.ref)(fromMarkdown(props.modelValue, options.value));
|
|
231
262
|
const wysiwyg = (0, vue.ref)(null);
|
|
232
263
|
const area = (0, vue.ref)(null);
|
|
233
264
|
(0, vue.watch)(() => props.modelValue, (next) => {
|
|
234
265
|
if (next === markdown.value) return;
|
|
235
266
|
markdown.value = next;
|
|
236
|
-
html.value = fromMarkdown(next);
|
|
267
|
+
html.value = fromMarkdown(next, options.value);
|
|
268
|
+
});
|
|
269
|
+
(0, vue.watch)(() => props.imageBase, () => {
|
|
270
|
+
html.value = fromMarkdown(markdown.value, options.value);
|
|
237
271
|
});
|
|
238
272
|
function commit(next) {
|
|
239
273
|
if (next === markdown.value) return;
|
|
@@ -243,14 +277,14 @@ var MarkdownEditor_default = /* @__PURE__ */ (0, vue.defineComponent)({
|
|
|
243
277
|
}
|
|
244
278
|
function onHtml(next) {
|
|
245
279
|
html.value = next;
|
|
246
|
-
commit(toMarkdown(next));
|
|
280
|
+
commit(toMarkdown(next, options.value));
|
|
247
281
|
}
|
|
248
282
|
function onSource(event) {
|
|
249
283
|
commit(event.target.value);
|
|
250
284
|
}
|
|
251
285
|
function setMode(next) {
|
|
252
286
|
if (next === mode.value) return;
|
|
253
|
-
if (next === "visual") html.value = fromMarkdown(markdown.value);
|
|
287
|
+
if (next === "visual") html.value = fromMarkdown(markdown.value, options.value);
|
|
254
288
|
mode.value = next;
|
|
255
289
|
}
|
|
256
290
|
/** Text that reads as Markdown: pasted into the visual editor, it arrives formatted. */
|
|
@@ -263,7 +297,7 @@ var MarkdownEditor_default = /* @__PURE__ */ (0, vue.defineComponent)({
|
|
|
263
297
|
if (!text || !MARKDOWN_HINT.test(text)) return;
|
|
264
298
|
event.preventDefault();
|
|
265
299
|
event.stopPropagation();
|
|
266
|
-
document.execCommand("insertHTML", false, fromMarkdown(text));
|
|
300
|
+
document.execCommand("insertHTML", false, fromMarkdown(text, options.value));
|
|
267
301
|
}
|
|
268
302
|
function onTab(event) {
|
|
269
303
|
if (event.key !== "Tab" || event.shiftKey || event.ctrlKey || event.metaKey || event.altKey) return;
|
|
@@ -281,7 +315,7 @@ var MarkdownEditor_default = /* @__PURE__ */ (0, vue.defineComponent)({
|
|
|
281
315
|
function insert(text) {
|
|
282
316
|
if (mode.value === "visual") {
|
|
283
317
|
focus();
|
|
284
|
-
document.execCommand("insertHTML", false, fromMarkdown(text));
|
|
318
|
+
document.execCommand("insertHTML", false, fromMarkdown(text, options.value));
|
|
285
319
|
return;
|
|
286
320
|
}
|
|
287
321
|
const el = area.value;
|
|
@@ -362,8 +396,15 @@ var MarkdownEditor_default = /* @__PURE__ */ (0, vue.defineComponent)({
|
|
|
362
396
|
"aria-label": t.value.preview
|
|
363
397
|
}, [(0, vue.createVNode)((0, vue.unref)(_dskripchenko_ui.UidMarkdown), {
|
|
364
398
|
source: markdown.value,
|
|
365
|
-
"block-renderers": __props.blockRenderers
|
|
366
|
-
|
|
399
|
+
"block-renderers": __props.blockRenderers,
|
|
400
|
+
"image-base": __props.imageBase,
|
|
401
|
+
"link-base": __props.linkBase
|
|
402
|
+
}, null, 8, [
|
|
403
|
+
"source",
|
|
404
|
+
"block-renderers",
|
|
405
|
+
"image-base",
|
|
406
|
+
"link-base"
|
|
407
|
+
])], 8, _hoisted_6)) : (0, vue.createCommentVNode)("", true)]))], 6);
|
|
367
408
|
};
|
|
368
409
|
}
|
|
369
410
|
});
|
|
@@ -373,6 +414,7 @@ exports.fromMarkdown = fromMarkdown;
|
|
|
373
414
|
exports.labelsFor = labelsFor;
|
|
374
415
|
exports.markdownEditorLocales = markdownEditorLocales;
|
|
375
416
|
exports.normalize = normalize;
|
|
417
|
+
exports.relativeTo = relativeTo;
|
|
376
418
|
exports.splitBlocks = splitBlocks;
|
|
377
419
|
exports.toMarkdown = toMarkdown;
|
|
378
420
|
|
package/dist/index.d.ts
CHANGED
|
@@ -20,6 +20,7 @@ declare const __VLS_export: DefineComponent<__VLS_PublicProps, {
|
|
|
20
20
|
onChange?: ((markdown: string) => any) | undefined;
|
|
21
21
|
"onUpdate:mode"?: ((value: MarkdownEditorMode) => any) | undefined;
|
|
22
22
|
}>, {
|
|
23
|
+
imageBase: string;
|
|
23
24
|
modelValue: string;
|
|
24
25
|
placeholder: string;
|
|
25
26
|
toolbarItems: ToolbarItem[];
|
|
@@ -31,6 +32,7 @@ declare const __VLS_export: DefineComponent<__VLS_PublicProps, {
|
|
|
31
32
|
locale: MarkdownEditorLocale;
|
|
32
33
|
labels: Partial<MarkdownEditorLabels>;
|
|
33
34
|
modes: MarkdownEditorMode[];
|
|
35
|
+
linkBase: string;
|
|
34
36
|
}, {}, {}, {}, string, ComponentProvideOptions, false, {}, any>;
|
|
35
37
|
|
|
36
38
|
declare type __VLS_ModelProps = {
|
|
@@ -49,17 +51,27 @@ declare type __VLS_Props = {
|
|
|
49
51
|
slashCommands?: SlashCommands;
|
|
50
52
|
locale?: MarkdownEditorLocale;
|
|
51
53
|
labels?: Partial<MarkdownEditorLabels>;
|
|
54
|
+
/** The folder relative pictures resolve against (a URL ending in `/`); saved back relative. */
|
|
55
|
+
imageBase?: string;
|
|
56
|
+
/** The base of relative links in the preview. */
|
|
57
|
+
linkBase?: string;
|
|
52
58
|
};
|
|
53
59
|
|
|
54
60
|
declare type __VLS_PublicProps = __VLS_Props & __VLS_ModelProps;
|
|
55
61
|
|
|
56
62
|
declare type BlockRenderers = InstanceType<typeof DskWysiwyg>['$props']['blockRenderers'];
|
|
57
63
|
|
|
64
|
+
/** Where the document's relative pictures resolve while it is edited. */
|
|
65
|
+
export declare interface ConvertOptions {
|
|
66
|
+
/** A folder URL (ending in `/`): `img/a.png` shows as `<imageBase>img/a.png` and is saved back as `img/a.png`. */
|
|
67
|
+
imageBase?: string | null;
|
|
68
|
+
}
|
|
69
|
+
|
|
58
70
|
/** Focus the editor of the current mode. */
|
|
59
71
|
declare function focus_2(): void;
|
|
60
72
|
|
|
61
73
|
/** Markdown → the HTML the editor edits; source blocks become code blocks of {@link SOURCE_LANG}. */
|
|
62
|
-
export declare function fromMarkdown(markdown: string): string;
|
|
74
|
+
export declare function fromMarkdown(markdown: string, options?: ConvertOptions): string;
|
|
63
75
|
|
|
64
76
|
/** Insert Markdown at the caret (the source's caret in the Markdown modes). */
|
|
65
77
|
declare function insert(text: string): void;
|
|
@@ -90,7 +102,14 @@ export declare const markdownEditorLocales: Record<MarkdownEditorLocale, Markdow
|
|
|
90
102
|
export declare type MarkdownEditorMode = 'visual' | 'source' | 'split';
|
|
91
103
|
|
|
92
104
|
/** One round: what saving a document unchanged in the editor gives. */
|
|
93
|
-
export declare function normalize(markdown: string): string;
|
|
105
|
+
export declare function normalize(markdown: string, options?: ConvertOptions): string;
|
|
106
|
+
|
|
107
|
+
/**
|
|
108
|
+
* A URL back to a path relative to `base`, when both share the origin:
|
|
109
|
+
* `<base>img/a.png` → `img/a.png`, `<base's parent>up.png` → `../up.png`.
|
|
110
|
+
* Anything else stays as it is.
|
|
111
|
+
*/
|
|
112
|
+
export declare function relativeTo(url: string, base: string): string;
|
|
94
113
|
|
|
95
114
|
declare type SlashCommands = InstanceType<typeof DskWysiwyg>['$props']['slashCommands'];
|
|
96
115
|
|
|
@@ -103,8 +122,8 @@ export declare const SOURCE_LANG = "x-markdown";
|
|
|
103
122
|
*/
|
|
104
123
|
export declare function splitBlocks(markdown: string): MarkdownBlock[];
|
|
105
124
|
|
|
106
|
-
/** The editor's HTML → Markdown; source blocks come back as written. */
|
|
107
|
-
export declare function toMarkdown(html: string): string;
|
|
125
|
+
/** The editor's HTML → Markdown; source blocks come back as written, pictures by their relative paths. */
|
|
126
|
+
export declare function toMarkdown(html: string, options?: ConvertOptions): string;
|
|
108
127
|
|
|
109
128
|
declare type ToolbarItems = InstanceType<typeof DskWysiwyg>['$props']['toolbarItems'];
|
|
110
129
|
|
package/dist/index.mjs
CHANGED
|
@@ -121,12 +121,36 @@ function splitBlocks(markdown) {
|
|
|
121
121
|
function escapeHtml(text) {
|
|
122
122
|
return text.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">");
|
|
123
123
|
}
|
|
124
|
+
/**
|
|
125
|
+
* A URL back to a path relative to `base`, when both share the origin:
|
|
126
|
+
* `<base>img/a.png` → `img/a.png`, `<base's parent>up.png` → `../up.png`.
|
|
127
|
+
* Anything else stays as it is.
|
|
128
|
+
*/
|
|
129
|
+
function relativeTo(url, base) {
|
|
130
|
+
const PLACEHOLDER = "http://base.invalid/";
|
|
131
|
+
let u;
|
|
132
|
+
let b;
|
|
133
|
+
try {
|
|
134
|
+
b = new URL(base, PLACEHOLDER);
|
|
135
|
+
u = new URL(url, b);
|
|
136
|
+
} catch {
|
|
137
|
+
return url;
|
|
138
|
+
}
|
|
139
|
+
if (u.protocol !== b.protocol || u.host !== b.host) return url;
|
|
140
|
+
const from = b.pathname.split("/").slice(0, -1);
|
|
141
|
+
const to = u.pathname.split("/");
|
|
142
|
+
let i = 0;
|
|
143
|
+
while (i < from.length && i < to.length - 1 && from[i] === to[i]) i++;
|
|
144
|
+
if (i === 0 && from.length > 1) return url;
|
|
145
|
+
const rel = [...Array(from.length - i).fill(".."), ...to.slice(i)].join("/");
|
|
146
|
+
return decodeURI(rel) + u.search + u.hash;
|
|
147
|
+
}
|
|
124
148
|
/** Markdown → the HTML the editor edits; source blocks become code blocks of {@link SOURCE_LANG}. */
|
|
125
|
-
function fromMarkdown(markdown) {
|
|
149
|
+
function fromMarkdown(markdown, options = {}) {
|
|
126
150
|
const out = [];
|
|
127
151
|
let pending = [];
|
|
128
152
|
const flush = () => {
|
|
129
|
-
if (pending.length) out.push(renderMarkdown(pending.join("\n\n")));
|
|
153
|
+
if (pending.length) out.push(renderMarkdown(pending.join("\n\n"), options.imageBase ? { imageBase: options.imageBase } : {}));
|
|
130
154
|
pending = [];
|
|
131
155
|
};
|
|
132
156
|
for (const block of splitBlocks(markdown)) {
|
|
@@ -141,14 +165,18 @@ function fromMarkdown(markdown) {
|
|
|
141
165
|
return out.join("\n");
|
|
142
166
|
}
|
|
143
167
|
var SOURCE_FENCE = new RegExp(`^(\`{3,})${SOURCE_LANG}\\n([\\s\\S]*?)\\n\\1$`, "gm");
|
|
144
|
-
/** The editor's HTML → Markdown; source blocks come back as written. */
|
|
145
|
-
function toMarkdown(html) {
|
|
146
|
-
const
|
|
168
|
+
/** The editor's HTML → Markdown; source blocks come back as written, pictures by their relative paths. */
|
|
169
|
+
function toMarkdown(html, options = {}) {
|
|
170
|
+
const base = options.imageBase;
|
|
171
|
+
const relative = base ? html.replace(/(<img\b[^>]*?\ssrc=")([^"]*)(")/gi, (_m, head, src, tail) => {
|
|
172
|
+
return head + relativeTo(src.replace(/&/g, "&"), base).replace(/&/g, "&") + tail;
|
|
173
|
+
}) : html;
|
|
174
|
+
const md = htmlToMarkdown(relative).replace(SOURCE_FENCE, (_m, _fence, text) => text);
|
|
147
175
|
return md === "" ? "" : `${md}\n`;
|
|
148
176
|
}
|
|
149
177
|
/** One round: what saving a document unchanged in the editor gives. */
|
|
150
|
-
function normalize(markdown) {
|
|
151
|
-
return toMarkdown(fromMarkdown(markdown));
|
|
178
|
+
function normalize(markdown, options = {}) {
|
|
179
|
+
return toMarkdown(fromMarkdown(markdown, options), options);
|
|
152
180
|
}
|
|
153
181
|
// src/locale.ts
|
|
154
182
|
var en = {
|
|
@@ -210,7 +238,9 @@ var MarkdownEditor_default = /* @__PURE__ */ defineComponent({
|
|
|
210
238
|
toolbarItems: { default: void 0 },
|
|
211
239
|
slashCommands: { default: void 0 },
|
|
212
240
|
locale: { default: void 0 },
|
|
213
|
-
labels: { default: void 0 }
|
|
241
|
+
labels: { default: void 0 },
|
|
242
|
+
imageBase: { default: void 0 },
|
|
243
|
+
linkBase: { default: void 0 }
|
|
214
244
|
}, {
|
|
215
245
|
"mode": { default: "visual" },
|
|
216
246
|
"modeModifiers": {}
|
|
@@ -225,14 +255,18 @@ var MarkdownEditor_default = /* @__PURE__ */ defineComponent({
|
|
|
225
255
|
...labelsFor(props.locale ?? kitLocale.value.code),
|
|
226
256
|
...props.labels
|
|
227
257
|
}));
|
|
258
|
+
const options = computed(() => ({ imageBase: props.imageBase ?? null }));
|
|
228
259
|
const markdown = ref(props.modelValue);
|
|
229
|
-
const html = ref(fromMarkdown(props.modelValue));
|
|
260
|
+
const html = ref(fromMarkdown(props.modelValue, options.value));
|
|
230
261
|
const wysiwyg = ref(null);
|
|
231
262
|
const area = ref(null);
|
|
232
263
|
watch(() => props.modelValue, (next) => {
|
|
233
264
|
if (next === markdown.value) return;
|
|
234
265
|
markdown.value = next;
|
|
235
|
-
html.value = fromMarkdown(next);
|
|
266
|
+
html.value = fromMarkdown(next, options.value);
|
|
267
|
+
});
|
|
268
|
+
watch(() => props.imageBase, () => {
|
|
269
|
+
html.value = fromMarkdown(markdown.value, options.value);
|
|
236
270
|
});
|
|
237
271
|
function commit(next) {
|
|
238
272
|
if (next === markdown.value) return;
|
|
@@ -242,14 +276,14 @@ var MarkdownEditor_default = /* @__PURE__ */ defineComponent({
|
|
|
242
276
|
}
|
|
243
277
|
function onHtml(next) {
|
|
244
278
|
html.value = next;
|
|
245
|
-
commit(toMarkdown(next));
|
|
279
|
+
commit(toMarkdown(next, options.value));
|
|
246
280
|
}
|
|
247
281
|
function onSource(event) {
|
|
248
282
|
commit(event.target.value);
|
|
249
283
|
}
|
|
250
284
|
function setMode(next) {
|
|
251
285
|
if (next === mode.value) return;
|
|
252
|
-
if (next === "visual") html.value = fromMarkdown(markdown.value);
|
|
286
|
+
if (next === "visual") html.value = fromMarkdown(markdown.value, options.value);
|
|
253
287
|
mode.value = next;
|
|
254
288
|
}
|
|
255
289
|
/** Text that reads as Markdown: pasted into the visual editor, it arrives formatted. */
|
|
@@ -262,7 +296,7 @@ var MarkdownEditor_default = /* @__PURE__ */ defineComponent({
|
|
|
262
296
|
if (!text || !MARKDOWN_HINT.test(text)) return;
|
|
263
297
|
event.preventDefault();
|
|
264
298
|
event.stopPropagation();
|
|
265
|
-
document.execCommand("insertHTML", false, fromMarkdown(text));
|
|
299
|
+
document.execCommand("insertHTML", false, fromMarkdown(text, options.value));
|
|
266
300
|
}
|
|
267
301
|
function onTab(event) {
|
|
268
302
|
if (event.key !== "Tab" || event.shiftKey || event.ctrlKey || event.metaKey || event.altKey) return;
|
|
@@ -280,7 +314,7 @@ var MarkdownEditor_default = /* @__PURE__ */ defineComponent({
|
|
|
280
314
|
function insert(text) {
|
|
281
315
|
if (mode.value === "visual") {
|
|
282
316
|
focus();
|
|
283
|
-
document.execCommand("insertHTML", false, fromMarkdown(text));
|
|
317
|
+
document.execCommand("insertHTML", false, fromMarkdown(text, options.value));
|
|
284
318
|
return;
|
|
285
319
|
}
|
|
286
320
|
const el = area.value;
|
|
@@ -361,11 +395,18 @@ var MarkdownEditor_default = /* @__PURE__ */ defineComponent({
|
|
|
361
395
|
"aria-label": t.value.preview
|
|
362
396
|
}, [createVNode(unref(UidMarkdown), {
|
|
363
397
|
source: markdown.value,
|
|
364
|
-
"block-renderers": __props.blockRenderers
|
|
365
|
-
|
|
398
|
+
"block-renderers": __props.blockRenderers,
|
|
399
|
+
"image-base": __props.imageBase,
|
|
400
|
+
"link-base": __props.linkBase
|
|
401
|
+
}, null, 8, [
|
|
402
|
+
"source",
|
|
403
|
+
"block-renderers",
|
|
404
|
+
"image-base",
|
|
405
|
+
"link-base"
|
|
406
|
+
])], 8, _hoisted_6)) : createCommentVNode("", true)]))], 6);
|
|
366
407
|
};
|
|
367
408
|
}
|
|
368
409
|
});
|
|
369
|
-
export { MarkdownEditor_default as MarkdownEditor, SOURCE_LANG, fromMarkdown, labelsFor, markdownEditorLocales, normalize, splitBlocks, toMarkdown };
|
|
410
|
+
export { MarkdownEditor_default as MarkdownEditor, SOURCE_LANG, fromMarkdown, labelsFor, markdownEditorLocales, normalize, relativeTo, splitBlocks, toMarkdown };
|
|
370
411
|
|
|
371
412
|
//# sourceMappingURL=index.mjs.map
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@dskripchenko/markdown-editor",
|
|
3
|
-
"version": "0.1
|
|
3
|
+
"version": "0.2.1",
|
|
4
4
|
"description": "A Markdown editor for Vue 3 that edits like a word processor: the value is Markdown, the editing is the @dskripchenko/wysiwyg engine — its toolbar, slash menu, shortcuts and live blocks — with source and side-by-side modes, and a lossless round trip",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"markdown",
|