markupeditor 0.9.37 → 0.9.39
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/dist/markup-editor.js +29 -23
- package/package.json +1 -1
package/dist/markup-editor.js
CHANGED
|
@@ -35639,34 +35639,32 @@ function insertInternalLink(hTag, index) {
|
|
|
35639
35639
|
function insertInternalLinkCommand(hTag, index) {
|
|
35640
35640
|
const commandAdapter = (state, dispatch, view) => {
|
|
35641
35641
|
// Find the node matching hTag that is index into the nodes matching hTag
|
|
35642
|
-
let {node} = headerMatching(hTag, index, state);
|
|
35642
|
+
let {node, pos} = headerMatching(hTag, index, state);
|
|
35643
35643
|
if (!node) return false
|
|
35644
|
-
// Get the unique id for this header, which
|
|
35644
|
+
// Get the unique id for this header, which it may or may not already have.
|
|
35645
35645
|
let id = idForHeader(node, state);
|
|
35646
|
-
|
|
35647
|
-
|
|
35648
|
-
// Insert the mark (id is always referenced with # at front) and set (or reset) the
|
|
35649
|
-
// id in the header itself. We don't care if it's the same, but we want these changes
|
|
35650
|
-
// to be made in a single transaction so we can undo them if needed.
|
|
35646
|
+
// Same transaction as the mark insertion below, so both land as one undo step.
|
|
35647
|
+
let tr = state.tr.setNodeMarkup(pos, undefined, { ...node.attrs, id });
|
|
35651
35648
|
const selection = state.selection;
|
|
35652
35649
|
const linkMark = state.schema.marks.link.create({ href: '#' + id });
|
|
35653
35650
|
if (selection.empty) {
|
|
35654
|
-
// In case of an empty selection, insert the textContent of the header and then use
|
|
35651
|
+
// In case of an empty selection, insert the textContent of the header and then use
|
|
35655
35652
|
// that to link-to the header
|
|
35656
35653
|
const textNode = state.schema.text(node.textContent, [linkMark]);
|
|
35657
|
-
|
|
35658
|
-
dispatch(
|
|
35654
|
+
tr.replaceSelectionWith(textNode, false);
|
|
35655
|
+
dispatch(tr);
|
|
35659
35656
|
stateChanged(view);
|
|
35660
35657
|
return true;
|
|
35661
35658
|
} else {
|
|
35662
|
-
|
|
35663
|
-
|
|
35664
|
-
|
|
35665
|
-
|
|
35666
|
-
|
|
35667
|
-
|
|
35668
|
-
|
|
35669
|
-
|
|
35659
|
+
// Capture toggleMark's steps rather than let it dispatch, then replay them onto
|
|
35660
|
+
// `tr` (setNodeMarkup doesn't shift positions, so they apply cleanly).
|
|
35661
|
+
let captured = null;
|
|
35662
|
+
toggleMark(linkMark.type, linkMark.attrs)(state, t => { captured = t; });
|
|
35663
|
+
if (!captured) return false;
|
|
35664
|
+
for (const step of captured.steps) tr.step(step);
|
|
35665
|
+
dispatch(tr);
|
|
35666
|
+
stateChanged(view);
|
|
35667
|
+
return true;
|
|
35670
35668
|
}
|
|
35671
35669
|
};
|
|
35672
35670
|
return commandAdapter;
|
|
@@ -35751,11 +35749,17 @@ function headerMatching(hTag, index, state) {
|
|
|
35751
35749
|
}
|
|
35752
35750
|
|
|
35753
35751
|
/**
|
|
35754
|
-
* Return a JSON-stringified array describing every header in the document, in document
|
|
35755
|
-
* within each level. Each entry is `{hTag, index, text}`, where `hTag` and `index` identify
|
|
35756
|
-
* header the same way `insertInternalLink(hTag, index)` and `idForInternalLinkCommand(hTag, index)`
|
|
35752
|
+
* Return a JSON-stringified array describing every non-empty header in the document, in document
|
|
35753
|
+
* order within each level. Each entry is `{hTag, index, text, id}`, where `hTag` and `index` identify
|
|
35754
|
+
* the header the same way `insertInternalLink(hTag, index)` and `idForInternalLinkCommand(hTag, index)`
|
|
35755
|
+
* do, and `id` is the header's current id attribute (null if it hasn't been assigned one yet).
|
|
35756
|
+
*
|
|
35757
|
+
* An empty header is omitted -- it can't form a usable id, so there's nothing to link to -- but
|
|
35758
|
+
* `index` still reflects its true position among ALL headers at that level (empty ones included),
|
|
35759
|
+
* matching what `headerMatching` expects; it's only the reported entries that skip empty headers,
|
|
35760
|
+
* not the numbering.
|
|
35757
35761
|
*
|
|
35758
|
-
* @returns {string} JSON-stringified array of `{hTag, index, text}`
|
|
35762
|
+
* @returns {string} JSON-stringified array of `{hTag, index, text, id}`
|
|
35759
35763
|
*/
|
|
35760
35764
|
function getHeaders() {
|
|
35761
35765
|
const view = activeView();
|
|
@@ -35765,7 +35769,9 @@ function getHeaders() {
|
|
|
35765
35769
|
let hNodes = headersByLevel[level];
|
|
35766
35770
|
if (hNodes) {
|
|
35767
35771
|
hNodes.forEach((h, index) => {
|
|
35768
|
-
|
|
35772
|
+
const text = h.node.textContent;
|
|
35773
|
+
if (text.trim().length === 0) return
|
|
35774
|
+
result.push({hTag: 'H' + level.toString(), index: index, text: text, id: h.node.attrs.id ?? null});
|
|
35769
35775
|
});
|
|
35770
35776
|
}
|
|
35771
35777
|
}
|