mrmd-editor 0.7.1 → 0.8.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +3 -1
- package/src/commands.js +112 -4
- package/src/comment-syntax.js +364 -39
- package/src/config/handlers.js +1 -2
- package/src/config/schema.js +46 -4
- package/src/document-template.js +2236 -0
- package/src/frontmatter-updater.js +204 -74
- package/src/grammar.js +758 -0
- package/src/index.js +1074 -55
- package/src/keymap.js +11 -2
- package/src/markdown/block-decorations.js +108 -5
- package/src/markdown/facets.js +37 -0
- package/src/markdown/html-inline.js +9 -5
- package/src/markdown/index.js +13 -3
- package/src/markdown/inline-commands.js +256 -0
- package/src/markdown/inline-model.js +578 -0
- package/src/markdown/inline-state.js +103 -0
- package/src/markdown/renderer.js +219 -12
- package/src/markdown/styles.js +290 -3
- package/src/markdown/widgets/alert-title.js +10 -8
- package/src/markdown/widgets/frontmatter.js +0 -6
- package/src/markdown/widgets/index.js +1 -0
- package/src/markdown/widgets/list-marker.js +29 -0
- package/src/markdown/wysiwyg.js +1158 -0
- package/src/mrp-types.js +2 -0
- package/src/output-widget.js +532 -18
- package/src/page-view-pagination.js +127 -0
- package/src/runtime-lsp.js +1757 -150
- package/src/section-controls/commands.js +617 -0
- package/src/section-controls/index.js +63 -0
- package/src/section-controls/plugin.js +165 -0
- package/src/section-controls/widgets.js +936 -0
- package/src/shell/ai-menu.js +11 -0
- package/src/shell/components/context-panel.js +572 -0
- package/src/shell/components/status-bar.js +10 -2
- package/src/shell/layouts/studio.js +206 -14
- package/src/shell/orchestrator-client.js +69 -0
- package/src/spellcheck.js +166 -0
- package/src/tables/README.md +97 -0
- package/src/tables/commands/insert-linked-table.js +122 -0
- package/src/tables/commands/open-table-workspace.js +43 -0
- package/src/tables/index.js +24 -0
- package/src/tables/jobs/client.js +158 -0
- package/src/tables/parsing/anchors.js +82 -0
- package/src/tables/parsing/linked-table-blocks.js +61 -0
- package/src/tables/state/linked-table-state.js +68 -0
- package/src/tables/widgets/linked-table-source-banner.js +77 -0
- package/src/tables/widgets/linked-table-widget.js +256 -0
- package/src/tables/workspace/controller.js +616 -0
- package/src/term-pty-client.js +51 -2
- package/src/term-widget.js +43 -3
- package/src/widgets/theme-utils.js +24 -16
- package/src/widgets/theme.js +1015 -1
- package/src/runtime-codelens/detector.js +0 -279
- package/src/runtime-codelens/index.js +0 -76
- package/src/runtime-codelens/plugin.js +0 -142
- package/src/runtime-codelens/styles.js +0 -184
- package/src/runtime-codelens/widgets.js +0 -216
package/src/markdown/renderer.js
CHANGED
|
@@ -15,6 +15,7 @@
|
|
|
15
15
|
import { ViewPlugin, Decoration, WidgetType } from '@codemirror/view';
|
|
16
16
|
import { Facet } from '@codemirror/state';
|
|
17
17
|
import { syntaxTree } from '@codemirror/language';
|
|
18
|
+
import { sourceModeFacet, wysiwygModeFacet } from './facets.js';
|
|
18
19
|
|
|
19
20
|
// =============================================================================
|
|
20
21
|
// Asset Resolver Facet
|
|
@@ -49,6 +50,7 @@ import {
|
|
|
49
50
|
// Tables handled by StateField (block-decorations.js) - multi-line replace not allowed in ViewPlugin
|
|
50
51
|
import { TaskCheckboxWidget } from './widgets/checkbox.js';
|
|
51
52
|
import { AlertTitleWidget } from './widgets/alert-title.js';
|
|
53
|
+
import { ListMarkerWidget } from './widgets/list-marker.js';
|
|
52
54
|
import {
|
|
53
55
|
InlineMathWidget,
|
|
54
56
|
extractInlineMath,
|
|
@@ -239,6 +241,93 @@ class ImageSpacerWidget extends WidgetType {
|
|
|
239
241
|
}
|
|
240
242
|
}
|
|
241
243
|
|
|
244
|
+
const ALERT_TYPE_MAP = {
|
|
245
|
+
note: 'note',
|
|
246
|
+
tip: 'tip',
|
|
247
|
+
important: 'important',
|
|
248
|
+
warning: 'warning',
|
|
249
|
+
caution: 'caution',
|
|
250
|
+
info: 'note',
|
|
251
|
+
abstract: 'note',
|
|
252
|
+
success: 'tip',
|
|
253
|
+
question: 'important',
|
|
254
|
+
failure: 'caution',
|
|
255
|
+
danger: 'caution',
|
|
256
|
+
bug: 'caution',
|
|
257
|
+
};
|
|
258
|
+
|
|
259
|
+
function toTitleCase(text) {
|
|
260
|
+
if (!text) return '';
|
|
261
|
+
return text
|
|
262
|
+
.replace(/[-_]+/g, ' ')
|
|
263
|
+
.trim()
|
|
264
|
+
.split(/\s+/)
|
|
265
|
+
.map((w) => w.charAt(0).toUpperCase() + w.slice(1).toLowerCase())
|
|
266
|
+
.join(' ');
|
|
267
|
+
}
|
|
268
|
+
|
|
269
|
+
function normalizeAlertType(type) {
|
|
270
|
+
const lower = (type || '').toLowerCase();
|
|
271
|
+
return ALERT_TYPE_MAP[lower] || 'note';
|
|
272
|
+
}
|
|
273
|
+
|
|
274
|
+
/**
|
|
275
|
+
* Find MkDocs-style admonitions:
|
|
276
|
+
*
|
|
277
|
+
* !!! tip
|
|
278
|
+
* indented body
|
|
279
|
+
*/
|
|
280
|
+
function findBangAdmonitions(doc) {
|
|
281
|
+
const ranges = [];
|
|
282
|
+
|
|
283
|
+
for (let i = 1; i <= doc.lines; i++) {
|
|
284
|
+
const startLine = doc.line(i);
|
|
285
|
+
const match = startLine.text.match(/^(\s*)!!!\s+([A-Za-z][\w-]*)(?:\s+"([^"]+)")?\s*$/);
|
|
286
|
+
if (!match) continue;
|
|
287
|
+
|
|
288
|
+
const baseIndent = match[1] || '';
|
|
289
|
+
const bodyIndentSpaces = `${baseIndent} `;
|
|
290
|
+
const bodyIndentTab = `${baseIndent}\t`;
|
|
291
|
+
|
|
292
|
+
let endLine = i;
|
|
293
|
+
let hasBody = false;
|
|
294
|
+
|
|
295
|
+
for (let j = i + 1; j <= doc.lines; j++) {
|
|
296
|
+
const lineText = doc.line(j).text;
|
|
297
|
+
|
|
298
|
+
if (lineText.trim() === '') {
|
|
299
|
+
if (hasBody) {
|
|
300
|
+
endLine = j;
|
|
301
|
+
continue;
|
|
302
|
+
}
|
|
303
|
+
break;
|
|
304
|
+
}
|
|
305
|
+
|
|
306
|
+
if (lineText.startsWith(bodyIndentSpaces) || lineText.startsWith(bodyIndentTab)) {
|
|
307
|
+
hasBody = true;
|
|
308
|
+
endLine = j;
|
|
309
|
+
continue;
|
|
310
|
+
}
|
|
311
|
+
|
|
312
|
+
break;
|
|
313
|
+
}
|
|
314
|
+
|
|
315
|
+
ranges.push({
|
|
316
|
+
startLine: i,
|
|
317
|
+
endLine,
|
|
318
|
+
headerIndent: baseIndent.length,
|
|
319
|
+
bodyIndentSpaces,
|
|
320
|
+
bodyIndentTab,
|
|
321
|
+
alertType: normalizeAlertType(match[2]),
|
|
322
|
+
title: match[3] || toTitleCase(match[2]),
|
|
323
|
+
});
|
|
324
|
+
|
|
325
|
+
i = endLine;
|
|
326
|
+
}
|
|
327
|
+
|
|
328
|
+
return ranges;
|
|
329
|
+
}
|
|
330
|
+
|
|
242
331
|
/**
|
|
243
332
|
* Build decorations for all markdown elements in the viewport.
|
|
244
333
|
*
|
|
@@ -252,6 +341,10 @@ function buildDecorations(view) {
|
|
|
252
341
|
const cursorLine = doc.lineAt(cursorPos).number;
|
|
253
342
|
const frontmatterRange = findFrontmatterRange(doc);
|
|
254
343
|
|
|
344
|
+
// Mode flags
|
|
345
|
+
const isSourceMode = view.state.facet(sourceModeFacet);
|
|
346
|
+
const isWysiwygMode = view.state.facet(wysiwygModeFacet);
|
|
347
|
+
|
|
255
348
|
// Get asset resolver from facet (may be null)
|
|
256
349
|
const assetResolver = view.state.facet(assetResolverFacet);
|
|
257
350
|
|
|
@@ -292,7 +385,7 @@ function buildDecorations(view) {
|
|
|
292
385
|
}
|
|
293
386
|
}
|
|
294
387
|
|
|
295
|
-
const isActiveLine = lineNum === cursorLine;
|
|
388
|
+
const isActiveLine = isSourceMode || (!isWysiwygMode && lineNum === cursorLine);
|
|
296
389
|
|
|
297
390
|
// Marker class: hidden on blur, muted on focus
|
|
298
391
|
const markerClass = isActiveLine ? 'cm-md-marker' : 'cm-md-hidden';
|
|
@@ -386,8 +479,9 @@ function buildDecorations(view) {
|
|
|
386
479
|
// Code backticks (inline only, not fenced code)
|
|
387
480
|
if (node.name === 'CodeMark') {
|
|
388
481
|
const text = doc.sliceString(node.from, node.to);
|
|
389
|
-
//
|
|
390
|
-
|
|
482
|
+
// In normal rendered mode, only hide inline backticks.
|
|
483
|
+
// In WYSIWYG mode, also hide fenced code markers.
|
|
484
|
+
if (text.length < 3 || isWysiwygMode) {
|
|
391
485
|
decorations.push(
|
|
392
486
|
Decoration.mark({ class: markerClass }).range(node.from, node.to)
|
|
393
487
|
);
|
|
@@ -429,7 +523,7 @@ function buildDecorations(view) {
|
|
|
429
523
|
const linkUrl = linkMatch[2];
|
|
430
524
|
|
|
431
525
|
const linkLine = doc.lineAt(node.from).number;
|
|
432
|
-
const isLinkActive = linkLine === cursorLine;
|
|
526
|
+
const isLinkActive = isSourceMode || (!isWysiwygMode && linkLine === cursorLine);
|
|
433
527
|
|
|
434
528
|
if (isLinkActive) {
|
|
435
529
|
// Show raw markdown with styling on active line
|
|
@@ -517,7 +611,7 @@ function buildDecorations(view) {
|
|
|
517
611
|
}
|
|
518
612
|
|
|
519
613
|
// Replace the alert marker [!TYPE] with widget when not on that line
|
|
520
|
-
if (alertType && startLine.number !== cursorLine) {
|
|
614
|
+
if (alertType && !isSourceMode && (isWysiwygMode || startLine.number !== cursorLine)) {
|
|
521
615
|
const markerStart = startLine.from + firstLineText.indexOf('[!');
|
|
522
616
|
const markerEnd = startLine.from + firstLineText.indexOf(']') + 1;
|
|
523
617
|
if (markerStart >= startLine.from && markerEnd > markerStart) {
|
|
@@ -541,9 +635,30 @@ function buildDecorations(view) {
|
|
|
541
635
|
// LISTS
|
|
542
636
|
// =======================================================================
|
|
543
637
|
if (node.name === 'ListMark') {
|
|
544
|
-
|
|
545
|
-
|
|
546
|
-
);
|
|
638
|
+
const line = doc.lineAt(node.from);
|
|
639
|
+
const listMarkText = doc.sliceString(node.from, node.to);
|
|
640
|
+
const isListActive = isSourceMode || (!isWysiwygMode && line.number === cursorLine);
|
|
641
|
+
const isUnordered = /^[-+*]$/.test(listMarkText);
|
|
642
|
+
const textAfterMarker = doc.sliceString(node.to, Math.min(node.to + 6, line.to));
|
|
643
|
+
const isTaskItem = /^\s+\[[ xX]\]/.test(textAfterMarker);
|
|
644
|
+
|
|
645
|
+
if (isListActive) {
|
|
646
|
+
decorations.push(
|
|
647
|
+
Decoration.mark({ class: 'cm-md-marker cm-md-list-marker' }).range(node.from, node.to)
|
|
648
|
+
);
|
|
649
|
+
} else if (isUnordered && !isTaskItem) {
|
|
650
|
+
decorations.push(
|
|
651
|
+
Decoration.replace({ widget: new ListMarkerWidget() }).range(node.from, node.to)
|
|
652
|
+
);
|
|
653
|
+
} else if (isTaskItem) {
|
|
654
|
+
decorations.push(
|
|
655
|
+
Decoration.mark({ class: 'cm-md-hidden' }).range(node.from, node.to)
|
|
656
|
+
);
|
|
657
|
+
} else {
|
|
658
|
+
decorations.push(
|
|
659
|
+
Decoration.mark({ class: 'cm-md-list-marker cm-md-list-number' }).range(node.from, node.to)
|
|
660
|
+
);
|
|
661
|
+
}
|
|
547
662
|
}
|
|
548
663
|
|
|
549
664
|
// Task list checkboxes: - [ ] or - [x]
|
|
@@ -559,7 +674,7 @@ function buildDecorations(view) {
|
|
|
559
674
|
|
|
560
675
|
// Don't render widget if cursor is on this line
|
|
561
676
|
const itemLine = doc.lineAt(node.from);
|
|
562
|
-
if (itemLine.number !== cursorLine) {
|
|
677
|
+
if (!isSourceMode && (isWysiwygMode || itemLine.number !== cursorLine)) {
|
|
563
678
|
// Replace [ ], [x], or [X] with checkbox widget
|
|
564
679
|
decorations.push(
|
|
565
680
|
Decoration.replace({
|
|
@@ -583,6 +698,27 @@ function buildDecorations(view) {
|
|
|
583
698
|
);
|
|
584
699
|
}
|
|
585
700
|
|
|
701
|
+
// =======================================================================
|
|
702
|
+
// PAGE BREAKS (\pagebreak, \newpage)
|
|
703
|
+
// Detected as single-line paragraphs containing only the command.
|
|
704
|
+
// In WYSIWYG mode, rendered as a visual break indicator.
|
|
705
|
+
// =======================================================================
|
|
706
|
+
if (node.name === 'Paragraph' || node.name === 'HTMLBlock') {
|
|
707
|
+
const nodeText = doc.sliceString(node.from, node.to).trim();
|
|
708
|
+
if (/^\\(pagebreak|newpage)$/.test(nodeText) ||
|
|
709
|
+
/^<div\s+style\s*=\s*["']page-break-after:\s*always;?["']\s*>\s*<\/div>$/i.test(nodeText)) {
|
|
710
|
+
const line = doc.lineAt(node.from);
|
|
711
|
+
decorations.push(
|
|
712
|
+
Decoration.line({ class: 'cm-pagebreak-line' }).range(line.from)
|
|
713
|
+
);
|
|
714
|
+
if (!isActiveLine) {
|
|
715
|
+
decorations.push(
|
|
716
|
+
Decoration.mark({ class: 'cm-md-hidden' }).range(node.from, node.to)
|
|
717
|
+
);
|
|
718
|
+
}
|
|
719
|
+
}
|
|
720
|
+
}
|
|
721
|
+
|
|
586
722
|
// =======================================================================
|
|
587
723
|
// IMAGES
|
|
588
724
|
// =======================================================================
|
|
@@ -769,6 +905,72 @@ function buildDecorations(view) {
|
|
|
769
905
|
}
|
|
770
906
|
});
|
|
771
907
|
|
|
908
|
+
// ==========================================================================
|
|
909
|
+
// MKDOCS-STYLE ADMONITIONS: !!! tip / !!! warning / ...
|
|
910
|
+
// ==========================================================================
|
|
911
|
+
const bangAdmonitions = findBangAdmonitions(doc);
|
|
912
|
+
const viewportStartLine = doc.lineAt(view.viewport.from).number;
|
|
913
|
+
const viewportEndLine = doc.lineAt(view.viewport.to).number;
|
|
914
|
+
|
|
915
|
+
for (const admonition of bangAdmonitions) {
|
|
916
|
+
// Skip if out of viewport
|
|
917
|
+
if (admonition.endLine < viewportStartLine || admonition.startLine > viewportEndLine) {
|
|
918
|
+
continue;
|
|
919
|
+
}
|
|
920
|
+
|
|
921
|
+
// Skip if inside frontmatter or fenced code block
|
|
922
|
+
if (
|
|
923
|
+
(frontmatterRange &&
|
|
924
|
+
admonition.startLine >= frontmatterRange.startLine &&
|
|
925
|
+
admonition.startLine <= frontmatterRange.endLine) ||
|
|
926
|
+
codeBlockLines.has(admonition.startLine)
|
|
927
|
+
) {
|
|
928
|
+
continue;
|
|
929
|
+
}
|
|
930
|
+
|
|
931
|
+
const cursorInAdmonition = isSourceMode || (!isWysiwygMode && cursorLine >= admonition.startLine && cursorLine <= admonition.endLine);
|
|
932
|
+
if (cursorInAdmonition) {
|
|
933
|
+
continue;
|
|
934
|
+
}
|
|
935
|
+
|
|
936
|
+
const visibleStart = Math.max(admonition.startLine, viewportStartLine);
|
|
937
|
+
const visibleEnd = Math.min(admonition.endLine, viewportEndLine);
|
|
938
|
+
|
|
939
|
+
for (let lineNum = visibleStart; lineNum <= visibleEnd; lineNum++) {
|
|
940
|
+
const line = doc.line(lineNum);
|
|
941
|
+
const classes = [
|
|
942
|
+
`cm-md-alert-${admonition.alertType}`,
|
|
943
|
+
'cm-md-admonition-line',
|
|
944
|
+
];
|
|
945
|
+
|
|
946
|
+
if (lineNum === admonition.startLine) classes.push('cm-md-admonition-start', 'cm-md-admonition-title-line');
|
|
947
|
+
if (lineNum === admonition.endLine) classes.push('cm-md-admonition-end');
|
|
948
|
+
|
|
949
|
+
decorations.push(
|
|
950
|
+
Decoration.line({ class: classes.join(' ') }).range(line.from)
|
|
951
|
+
);
|
|
952
|
+
|
|
953
|
+
if (lineNum === admonition.startLine) {
|
|
954
|
+
const from = line.from + admonition.headerIndent;
|
|
955
|
+
if (from < line.to) {
|
|
956
|
+
decorations.push(
|
|
957
|
+
Decoration.replace({
|
|
958
|
+
widget: new AlertTitleWidget(admonition.alertType, admonition.title),
|
|
959
|
+
}).range(from, line.to)
|
|
960
|
+
);
|
|
961
|
+
}
|
|
962
|
+
} else if (line.text.startsWith(admonition.bodyIndentSpaces)) {
|
|
963
|
+
decorations.push(
|
|
964
|
+
Decoration.mark({ class: 'cm-md-hidden' }).range(line.from, line.from + admonition.bodyIndentSpaces.length)
|
|
965
|
+
);
|
|
966
|
+
} else if (line.text.startsWith(admonition.bodyIndentTab)) {
|
|
967
|
+
decorations.push(
|
|
968
|
+
Decoration.mark({ class: 'cm-md-hidden' }).range(line.from, line.from + admonition.bodyIndentTab.length)
|
|
969
|
+
);
|
|
970
|
+
}
|
|
971
|
+
}
|
|
972
|
+
}
|
|
973
|
+
|
|
772
974
|
// ==========================================================================
|
|
773
975
|
// INLINE MATH: $...$ (single line only)
|
|
774
976
|
// ==========================================================================
|
|
@@ -776,7 +978,7 @@ function buildDecorations(view) {
|
|
|
776
978
|
// Process line by line in viewport
|
|
777
979
|
for (let i = doc.lineAt(view.viewport.from).number; i <= doc.lineAt(view.viewport.to).number; i++) {
|
|
778
980
|
const line = doc.line(i);
|
|
779
|
-
const isActiveLine = i === cursorLine;
|
|
981
|
+
const isActiveLine = isSourceMode || (!isWysiwygMode && i === cursorLine);
|
|
780
982
|
|
|
781
983
|
// Skip frontmatter lines
|
|
782
984
|
if (frontmatterRange && i >= frontmatterRange.startLine && i <= frontmatterRange.endLine) continue;
|
|
@@ -814,7 +1016,7 @@ function buildDecorations(view) {
|
|
|
814
1016
|
// ==========================================================================
|
|
815
1017
|
for (let i = doc.lineAt(view.viewport.from).number; i <= doc.lineAt(view.viewport.to).number; i++) {
|
|
816
1018
|
const line = doc.line(i);
|
|
817
|
-
const isActiveLine = i === cursorLine;
|
|
1019
|
+
const isActiveLine = isSourceMode || (!isWysiwygMode && i === cursorLine);
|
|
818
1020
|
|
|
819
1021
|
// Skip frontmatter lines
|
|
820
1022
|
if (frontmatterRange && i >= frontmatterRange.startLine && i <= frontmatterRange.endLine) continue;
|
|
@@ -857,7 +1059,7 @@ function buildDecorations(view) {
|
|
|
857
1059
|
|
|
858
1060
|
for (let i = doc.lineAt(view.viewport.from).number; i <= doc.lineAt(view.viewport.to).number; i++) {
|
|
859
1061
|
const line = doc.line(i);
|
|
860
|
-
const isActiveLine = i === cursorLine;
|
|
1062
|
+
const isActiveLine = isSourceMode || (!isWysiwygMode && i === cursorLine);
|
|
861
1063
|
|
|
862
1064
|
// Skip frontmatter lines
|
|
863
1065
|
if (frontmatterRange && i >= frontmatterRange.startLine && i <= frontmatterRange.endLine) continue;
|
|
@@ -868,6 +1070,11 @@ function buildDecorations(view) {
|
|
|
868
1070
|
const htmlElements = extractHtmlElements(line.text);
|
|
869
1071
|
|
|
870
1072
|
for (const el of htmlElements) {
|
|
1073
|
+
// Underline is handled by the shared inline formatting model so it can
|
|
1074
|
+
// participate in semantic toggling like bold/italic instead of being
|
|
1075
|
+
// rendered as an opaque HTML widget.
|
|
1076
|
+
if (el.tag === 'u') continue;
|
|
1077
|
+
|
|
871
1078
|
const from = line.from + el.start;
|
|
872
1079
|
const to = line.from + el.end;
|
|
873
1080
|
|
package/src/markdown/styles.js
CHANGED
|
@@ -102,6 +102,12 @@ export const markdownStyles = `
|
|
|
102
102
|
font-style: italic;
|
|
103
103
|
}
|
|
104
104
|
|
|
105
|
+
.cm-md-underline {
|
|
106
|
+
text-decoration: underline;
|
|
107
|
+
text-decoration-thickness: 1px;
|
|
108
|
+
text-underline-offset: 2px;
|
|
109
|
+
}
|
|
110
|
+
|
|
105
111
|
.cm-md-strikethrough {
|
|
106
112
|
text-decoration: line-through;
|
|
107
113
|
opacity: 0.7;
|
|
@@ -217,22 +223,58 @@ export const markdownStyles = `
|
|
|
217
223
|
|
|
218
224
|
.cm-md-alert-note {
|
|
219
225
|
border-left-color: var(--md-alert-note-color);
|
|
226
|
+
--md-alert-accent: var(--md-alert-note-color);
|
|
220
227
|
}
|
|
221
228
|
|
|
222
229
|
.cm-md-alert-tip {
|
|
223
230
|
border-left-color: var(--md-alert-tip-color);
|
|
231
|
+
--md-alert-accent: var(--md-alert-tip-color);
|
|
224
232
|
}
|
|
225
233
|
|
|
226
234
|
.cm-md-alert-important {
|
|
227
235
|
border-left-color: var(--md-alert-important-color);
|
|
236
|
+
--md-alert-accent: var(--md-alert-important-color);
|
|
228
237
|
}
|
|
229
238
|
|
|
230
239
|
.cm-md-alert-warning {
|
|
231
240
|
border-left-color: var(--md-alert-warning-color);
|
|
241
|
+
--md-alert-accent: var(--md-alert-warning-color);
|
|
232
242
|
}
|
|
233
243
|
|
|
234
244
|
.cm-md-alert-caution {
|
|
235
245
|
border-left-color: var(--md-alert-caution-color);
|
|
246
|
+
--md-alert-accent: var(--md-alert-caution-color);
|
|
247
|
+
}
|
|
248
|
+
|
|
249
|
+
/* MkDocs-style !!! admonitions (card style with title bar) */
|
|
250
|
+
.cm-md-admonition-line {
|
|
251
|
+
border-left: var(--md-admonition-border-width, 1px) solid var(--md-admonition-border-color, color-mix(in srgb, var(--md-alert-accent, var(--widget-border-accent)) 46%, var(--widget-border) 54%));
|
|
252
|
+
border-right: var(--md-admonition-border-width, 1px) solid var(--md-admonition-border-color, color-mix(in srgb, var(--md-alert-accent, var(--widget-border-accent)) 46%, var(--widget-border) 54%));
|
|
253
|
+
background: var(--md-admonition-body-background, var(--md-admonition-background, color-mix(in srgb, var(--md-alert-accent, var(--widget-border-accent)) 5%, var(--editor-background, transparent) 95%)));
|
|
254
|
+
color: var(--md-admonition-text-color, inherit);
|
|
255
|
+
padding-left: var(--md-admonition-padding-x, 0.9em);
|
|
256
|
+
padding-right: var(--md-admonition-padding-x, 0.9em);
|
|
257
|
+
}
|
|
258
|
+
|
|
259
|
+
.cm-md-admonition-start {
|
|
260
|
+
border-top: var(--md-admonition-border-width, 1px) solid var(--md-admonition-border-color, color-mix(in srgb, var(--md-alert-accent, var(--widget-border-accent)) 46%, var(--widget-border) 54%));
|
|
261
|
+
border-top-left-radius: var(--md-admonition-radius, 6px);
|
|
262
|
+
border-top-right-radius: var(--md-admonition-radius, 6px);
|
|
263
|
+
background: var(--md-admonition-title-background, color-mix(in srgb, var(--md-alert-accent, var(--widget-border-accent)) 14%, var(--editor-background, transparent) 86%));
|
|
264
|
+
padding-top: var(--md-admonition-padding-y, 0.35em);
|
|
265
|
+
padding-bottom: var(--md-admonition-padding-y, 0.35em);
|
|
266
|
+
border-bottom: 1px solid color-mix(in srgb, var(--md-admonition-border-color, var(--md-alert-accent, var(--widget-border-accent))) 55%, transparent);
|
|
267
|
+
}
|
|
268
|
+
|
|
269
|
+
.cm-md-admonition-end {
|
|
270
|
+
border-bottom: var(--md-admonition-border-width, 1px) solid var(--md-admonition-border-color, color-mix(in srgb, var(--md-alert-accent, var(--widget-border-accent)) 46%, var(--widget-border) 54%));
|
|
271
|
+
border-bottom-left-radius: var(--md-admonition-radius, 6px);
|
|
272
|
+
border-bottom-right-radius: var(--md-admonition-radius, 6px);
|
|
273
|
+
padding-bottom: calc(var(--md-admonition-padding-y, 0.35em) + 0.05em);
|
|
274
|
+
}
|
|
275
|
+
|
|
276
|
+
.cm-md-admonition-title-line {
|
|
277
|
+
color: var(--md-admonition-title-color, var(--md-alert-accent, var(--widget-text-accent)));
|
|
236
278
|
}
|
|
237
279
|
|
|
238
280
|
/* ==========================================================================
|
|
@@ -241,6 +283,19 @@ export const markdownStyles = `
|
|
|
241
283
|
|
|
242
284
|
.cm-md-list-marker {
|
|
243
285
|
color: var(--md-list-marker-color);
|
|
286
|
+
font-variant-numeric: tabular-nums;
|
|
287
|
+
}
|
|
288
|
+
|
|
289
|
+
.cm-md-list-number {
|
|
290
|
+
font-weight: var(--md-list-number-weight, 600);
|
|
291
|
+
}
|
|
292
|
+
|
|
293
|
+
.cm-md-list-bullet {
|
|
294
|
+
display: inline-block;
|
|
295
|
+
width: var(--md-list-bullet-width, 0.75em);
|
|
296
|
+
color: var(--md-list-marker-color);
|
|
297
|
+
font-weight: var(--md-list-bullet-weight, 700);
|
|
298
|
+
text-align: center;
|
|
244
299
|
}
|
|
245
300
|
|
|
246
301
|
/* ==========================================================================
|
|
@@ -322,6 +377,222 @@ export const markdownStyles = `
|
|
|
322
377
|
padding: 0.5em 0;
|
|
323
378
|
}
|
|
324
379
|
|
|
380
|
+
/* Linked-table wrapper (header chrome + table snapshot) */
|
|
381
|
+
.cm-linked-table-widget {
|
|
382
|
+
display: block;
|
|
383
|
+
margin: 0.35em 0;
|
|
384
|
+
padding: 0.45em 0.6em 0.55em;
|
|
385
|
+
border: 1px solid var(--widget-border, rgba(128, 128, 128, 0.2));
|
|
386
|
+
border-radius: var(--widget-border-radius, 8px);
|
|
387
|
+
background: color-mix(in srgb, var(--md-table-bg, var(--editor-background)) 92%, var(--widget-surface, transparent) 8%);
|
|
388
|
+
}
|
|
389
|
+
|
|
390
|
+
.cm-linked-table-widget .cm-table-widget {
|
|
391
|
+
padding: 0;
|
|
392
|
+
background: transparent;
|
|
393
|
+
}
|
|
394
|
+
|
|
395
|
+
.cm-linked-table-chrome {
|
|
396
|
+
display: flex;
|
|
397
|
+
align-items: center;
|
|
398
|
+
justify-content: space-between;
|
|
399
|
+
gap: 0.75em;
|
|
400
|
+
margin-bottom: 0.45em;
|
|
401
|
+
}
|
|
402
|
+
|
|
403
|
+
.cm-linked-table-chrome-left {
|
|
404
|
+
display: flex;
|
|
405
|
+
align-items: baseline;
|
|
406
|
+
gap: 0.55em;
|
|
407
|
+
min-width: 0;
|
|
408
|
+
flex-wrap: wrap;
|
|
409
|
+
}
|
|
410
|
+
|
|
411
|
+
.cm-linked-table-title {
|
|
412
|
+
font-size: 0.95em;
|
|
413
|
+
font-weight: 600;
|
|
414
|
+
color: var(--widget-text);
|
|
415
|
+
}
|
|
416
|
+
|
|
417
|
+
.cm-linked-table-badges {
|
|
418
|
+
display: inline-flex;
|
|
419
|
+
align-items: center;
|
|
420
|
+
gap: 0.35em;
|
|
421
|
+
flex-wrap: wrap;
|
|
422
|
+
}
|
|
423
|
+
|
|
424
|
+
.cm-linked-table-badge {
|
|
425
|
+
display: inline-flex;
|
|
426
|
+
align-items: center;
|
|
427
|
+
padding: 0.1em 0.45em;
|
|
428
|
+
border-radius: 999px;
|
|
429
|
+
background: var(--widget-surface, rgba(128, 128, 128, 0.12));
|
|
430
|
+
color: var(--widget-text-muted, inherit);
|
|
431
|
+
font-size: 0.75em;
|
|
432
|
+
line-height: 1.25;
|
|
433
|
+
}
|
|
434
|
+
|
|
435
|
+
.cm-linked-table-badge-linked {
|
|
436
|
+
color: var(--md-link-color, var(--widget-text));
|
|
437
|
+
}
|
|
438
|
+
|
|
439
|
+
.cm-linked-table-status-badge {
|
|
440
|
+
border: 1px solid transparent;
|
|
441
|
+
}
|
|
442
|
+
|
|
443
|
+
.cm-linked-table-status-pending,
|
|
444
|
+
.cm-linked-table-status-claimed,
|
|
445
|
+
.cm-linked-table-status-requested {
|
|
446
|
+
background: color-mix(in srgb, var(--widget-surface, rgba(128, 128, 128, 0.12)) 60%, var(--md-link-color, #64748b) 40%);
|
|
447
|
+
color: var(--widget-text);
|
|
448
|
+
}
|
|
449
|
+
|
|
450
|
+
.cm-linked-table-status-running,
|
|
451
|
+
.cm-linked-table-status-writing {
|
|
452
|
+
background: color-mix(in srgb, var(--widget-surface, rgba(128, 128, 128, 0.12)) 45%, var(--mrmd-accent, #2563eb) 55%);
|
|
453
|
+
color: white;
|
|
454
|
+
}
|
|
455
|
+
|
|
456
|
+
.cm-linked-table-status-stale {
|
|
457
|
+
background: color-mix(in srgb, var(--widget-surface, rgba(128, 128, 128, 0.12)) 35%, var(--mrmd-warning, #d97706) 65%);
|
|
458
|
+
color: white;
|
|
459
|
+
}
|
|
460
|
+
|
|
461
|
+
.cm-linked-table-status-error {
|
|
462
|
+
background: color-mix(in srgb, var(--widget-surface, rgba(128, 128, 128, 0.12)) 35%, var(--mrmd-error, #dc2626) 65%);
|
|
463
|
+
color: white;
|
|
464
|
+
}
|
|
465
|
+
|
|
466
|
+
.cm-linked-table-status-fresh {
|
|
467
|
+
border-color: var(--widget-border, rgba(128, 128, 128, 0.2));
|
|
468
|
+
}
|
|
469
|
+
|
|
470
|
+
.cm-linked-table-status-active {
|
|
471
|
+
position: relative;
|
|
472
|
+
}
|
|
473
|
+
|
|
474
|
+
.cm-linked-table-status-active::after {
|
|
475
|
+
content: '';
|
|
476
|
+
width: 0.45em;
|
|
477
|
+
height: 0.45em;
|
|
478
|
+
margin-left: 0.4em;
|
|
479
|
+
border-radius: 999px;
|
|
480
|
+
background: currentColor;
|
|
481
|
+
display: inline-block;
|
|
482
|
+
opacity: 0.75;
|
|
483
|
+
animation: cm-linked-table-pulse 1s ease-in-out infinite;
|
|
484
|
+
}
|
|
485
|
+
|
|
486
|
+
@keyframes cm-linked-table-pulse {
|
|
487
|
+
0%, 100% { opacity: 0.35; transform: scale(0.85); }
|
|
488
|
+
50% { opacity: 0.95; transform: scale(1); }
|
|
489
|
+
}
|
|
490
|
+
|
|
491
|
+
.cm-linked-table-widget[data-job-status="running"],
|
|
492
|
+
.cm-linked-table-widget[data-job-status="writing"],
|
|
493
|
+
.cm-linked-table-widget[data-job-status="requested"],
|
|
494
|
+
.cm-linked-table-widget[data-job-status="claimed"] {
|
|
495
|
+
box-shadow: 0 0 0 1px color-mix(in srgb, var(--mrmd-accent, #2563eb) 35%, transparent 65%);
|
|
496
|
+
}
|
|
497
|
+
|
|
498
|
+
.cm-linked-table-widget[data-job-status="stale"] {
|
|
499
|
+
box-shadow: 0 0 0 1px color-mix(in srgb, var(--mrmd-warning, #d97706) 35%, transparent 65%);
|
|
500
|
+
}
|
|
501
|
+
|
|
502
|
+
.cm-linked-table-widget[data-job-status="error"] {
|
|
503
|
+
box-shadow: 0 0 0 1px color-mix(in srgb, var(--mrmd-error, #dc2626) 35%, transparent 65%);
|
|
504
|
+
}
|
|
505
|
+
|
|
506
|
+
.cm-linked-table-widget[aria-busy="true"] .cm-linked-table-sortable {
|
|
507
|
+
opacity: 0.7;
|
|
508
|
+
}
|
|
509
|
+
|
|
510
|
+
.cm-linked-table-actions {
|
|
511
|
+
display: inline-flex;
|
|
512
|
+
align-items: center;
|
|
513
|
+
gap: 0.35em;
|
|
514
|
+
flex-wrap: wrap;
|
|
515
|
+
}
|
|
516
|
+
|
|
517
|
+
.cm-linked-table-action {
|
|
518
|
+
appearance: none;
|
|
519
|
+
border: 1px solid var(--widget-border, rgba(128, 128, 128, 0.2));
|
|
520
|
+
background: var(--widget-surface, transparent);
|
|
521
|
+
color: var(--widget-text);
|
|
522
|
+
border-radius: 6px;
|
|
523
|
+
padding: 0.18em 0.5em;
|
|
524
|
+
font: inherit;
|
|
525
|
+
font-size: 0.78em;
|
|
526
|
+
cursor: pointer;
|
|
527
|
+
}
|
|
528
|
+
|
|
529
|
+
.cm-linked-table-action:hover {
|
|
530
|
+
background: var(--widget-surface-hover, rgba(128, 128, 128, 0.08));
|
|
531
|
+
}
|
|
532
|
+
|
|
533
|
+
.cm-linked-table-caption {
|
|
534
|
+
font-size: 0.85em;
|
|
535
|
+
color: var(--widget-text-muted);
|
|
536
|
+
font-style: italic;
|
|
537
|
+
line-height: 1.35;
|
|
538
|
+
}
|
|
539
|
+
|
|
540
|
+
.cm-linked-table-caption-above {
|
|
541
|
+
margin: 0 0 0.35em;
|
|
542
|
+
}
|
|
543
|
+
|
|
544
|
+
.cm-linked-table-caption-below {
|
|
545
|
+
margin: 0.45em 0 0;
|
|
546
|
+
}
|
|
547
|
+
|
|
548
|
+
.cm-linked-table-sortable {
|
|
549
|
+
cursor: pointer;
|
|
550
|
+
user-select: none;
|
|
551
|
+
}
|
|
552
|
+
|
|
553
|
+
.cm-linked-table-sortable::after {
|
|
554
|
+
content: ' ↕';
|
|
555
|
+
opacity: 0.35;
|
|
556
|
+
font-size: 0.8em;
|
|
557
|
+
}
|
|
558
|
+
|
|
559
|
+
.cm-linked-table-sortable:hover::after {
|
|
560
|
+
opacity: 0.65;
|
|
561
|
+
}
|
|
562
|
+
|
|
563
|
+
.cm-linked-table-source-banner {
|
|
564
|
+
display: flex;
|
|
565
|
+
align-items: center;
|
|
566
|
+
justify-content: space-between;
|
|
567
|
+
gap: 0.75em;
|
|
568
|
+
margin: 0.25em 0 0.4em;
|
|
569
|
+
padding: 0.35em 0.5em;
|
|
570
|
+
border: 1px dashed var(--widget-border, rgba(128, 128, 128, 0.24));
|
|
571
|
+
border-radius: 8px;
|
|
572
|
+
background: color-mix(in srgb, var(--widget-surface, transparent) 30%, var(--editor-background, transparent) 70%);
|
|
573
|
+
}
|
|
574
|
+
|
|
575
|
+
.cm-linked-table-source-banner-text {
|
|
576
|
+
font-size: 0.82em;
|
|
577
|
+
color: var(--widget-text-muted, inherit);
|
|
578
|
+
}
|
|
579
|
+
|
|
580
|
+
.cm-linked-table-source-banner-action {
|
|
581
|
+
appearance: none;
|
|
582
|
+
border: 1px solid var(--widget-border, rgba(128, 128, 128, 0.24));
|
|
583
|
+
background: var(--widget-surface, transparent);
|
|
584
|
+
color: var(--widget-text, inherit);
|
|
585
|
+
border-radius: 6px;
|
|
586
|
+
padding: 0.16em 0.5em;
|
|
587
|
+
font: inherit;
|
|
588
|
+
font-size: 0.78em;
|
|
589
|
+
cursor: pointer;
|
|
590
|
+
}
|
|
591
|
+
|
|
592
|
+
.cm-linked-table-source-banner-action:hover {
|
|
593
|
+
background: var(--widget-surface-hover, rgba(128, 128, 128, 0.08));
|
|
594
|
+
}
|
|
595
|
+
|
|
325
596
|
/* The table element */
|
|
326
597
|
.cm-table {
|
|
327
598
|
display: table;
|
|
@@ -854,11 +1125,16 @@ export const markdownStyles = `
|
|
|
854
1125
|
.cm-alert-title {
|
|
855
1126
|
display: inline-flex;
|
|
856
1127
|
align-items: center;
|
|
857
|
-
gap: 0.
|
|
858
|
-
font-weight:
|
|
1128
|
+
gap: 0.45em;
|
|
1129
|
+
font-weight: 650;
|
|
859
1130
|
margin-bottom: 0.25em;
|
|
860
1131
|
}
|
|
861
1132
|
|
|
1133
|
+
.cm-md-admonition-title-line .cm-alert-title {
|
|
1134
|
+
margin-bottom: 0;
|
|
1135
|
+
color: var(--md-admonition-title-color, var(--md-alert-accent, var(--widget-text-accent)));
|
|
1136
|
+
}
|
|
1137
|
+
|
|
862
1138
|
.cm-alert-title-note {
|
|
863
1139
|
color: var(--md-alert-note-color);
|
|
864
1140
|
}
|
|
@@ -881,7 +1157,18 @@ export const markdownStyles = `
|
|
|
881
1157
|
|
|
882
1158
|
/* Alert icons */
|
|
883
1159
|
.cm-alert-icon {
|
|
884
|
-
|
|
1160
|
+
width: 1.2em;
|
|
1161
|
+
height: 1.2em;
|
|
1162
|
+
border-radius: 999px;
|
|
1163
|
+
display: inline-flex;
|
|
1164
|
+
align-items: center;
|
|
1165
|
+
justify-content: center;
|
|
1166
|
+
font-size: 0.75em;
|
|
1167
|
+
font-weight: 700;
|
|
1168
|
+
line-height: 1;
|
|
1169
|
+
color: var(--md-admonition-title-color, currentColor);
|
|
1170
|
+
border: 1px solid color-mix(in srgb, currentColor 45%, transparent);
|
|
1171
|
+
background: color-mix(in srgb, currentColor 12%, transparent);
|
|
885
1172
|
}
|
|
886
1173
|
|
|
887
1174
|
/* ==========================================================================
|