@dxos/react-ui-editor 0.4.7-main.ea67fec → 0.4.7-main.f4b92be
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/lib/browser/index.mjs +1048 -816
- package/dist/lib/browser/index.mjs.map +4 -4
- package/dist/lib/browser/meta.json +1 -1
- package/dist/types/src/components/TextEditor/MarkdownEditor.stories.d.ts +9 -0
- package/dist/types/src/components/TextEditor/MarkdownEditor.stories.d.ts.map +1 -1
- package/dist/types/src/components/TextEditor/TextEditor.d.ts.map +1 -1
- package/dist/types/src/components/TextEditor/TextEditor.stories.d.ts +0 -9
- package/dist/types/src/components/TextEditor/TextEditor.stories.d.ts.map +1 -1
- package/dist/types/src/components/TextEditor/index.d.ts +0 -2
- package/dist/types/src/components/TextEditor/index.d.ts.map +1 -1
- package/dist/types/src/components/Toolbar/Toolbar.stories.d.ts.map +1 -1
- package/dist/types/src/{components/TextEditor → extensions/automerge}/automerge.stories.d.ts +4 -2
- package/dist/types/src/extensions/automerge/automerge.stories.d.ts.map +1 -0
- package/dist/types/src/extensions/command/command.d.ts +10 -0
- package/dist/types/src/extensions/command/command.d.ts.map +1 -0
- package/dist/types/src/extensions/command/hint.d.ts +7 -0
- package/dist/types/src/extensions/command/hint.d.ts.map +1 -0
- package/dist/types/src/extensions/command/index.d.ts +2 -0
- package/dist/types/src/extensions/command/index.d.ts.map +1 -0
- package/dist/types/src/extensions/command/state.d.ts +18 -0
- package/dist/types/src/extensions/command/state.d.ts.map +1 -0
- package/dist/types/src/extensions/cursor-line-margin.d.ts.map +1 -1
- package/dist/types/src/extensions/dnd.d.ts +3 -0
- package/dist/types/src/extensions/dnd.d.ts.map +1 -0
- package/dist/types/src/extensions/index.d.ts +2 -1
- package/dist/types/src/extensions/index.d.ts.map +1 -1
- package/dist/types/src/extensions/listener.d.ts +1 -1
- package/dist/types/src/extensions/listener.d.ts.map +1 -1
- package/dist/types/src/extensions/markdown/bundle.d.ts +2 -2
- package/dist/types/src/extensions/markdown/bundle.d.ts.map +1 -1
- package/dist/types/src/extensions/markdown/decorate.d.ts +3 -0
- package/dist/types/src/extensions/markdown/decorate.d.ts.map +1 -1
- package/dist/types/src/extensions/util/dom.d.ts +15 -0
- package/dist/types/src/extensions/util/dom.d.ts.map +1 -0
- package/dist/types/src/hooks/defs.d.ts +5 -11
- package/dist/types/src/hooks/defs.d.ts.map +1 -1
- package/dist/types/src/hooks/useEditorView.d.ts.map +1 -1
- package/dist/types/src/hooks/useTextEditor.d.ts +20 -5
- package/dist/types/src/hooks/useTextEditor.d.ts.map +1 -1
- package/dist/types/src/{components/TextEditor/hooks.stories.d.ts → hooks/useTextEditor.stories.d.ts} +1 -3
- package/dist/types/src/hooks/useTextEditor.stories.d.ts.map +1 -0
- package/dist/types/src/hooks/useTextModel.d.ts.map +1 -1
- package/dist/types/src/index.d.ts +1 -0
- package/dist/types/src/index.d.ts.map +1 -1
- package/dist/types/src/themes/default.d.ts.map +1 -1
- package/package.json +24 -24
- package/src/components/TextEditor/MarkdownEditor.stories.tsx +95 -8
- package/src/components/TextEditor/TextEditor.stories.tsx +0 -15
- package/src/components/TextEditor/TextEditor.tsx +11 -6
- package/src/components/TextEditor/index.ts +0 -3
- package/src/components/Toolbar/Toolbar.stories.tsx +2 -1
- package/src/{components/TextEditor → extensions/automerge}/automerge.stories.tsx +32 -37
- package/src/extensions/command/command.ts +35 -0
- package/src/extensions/command/hint.ts +76 -0
- package/src/extensions/command/index.ts +5 -0
- package/src/extensions/command/state.ts +106 -0
- package/src/extensions/cursor-line-margin.ts +2 -1
- package/src/extensions/dnd.ts +15 -0
- package/src/extensions/index.ts +2 -1
- package/src/extensions/listener.ts +3 -3
- package/src/extensions/markdown/bundle.ts +4 -14
- package/src/extensions/markdown/decorate.ts +20 -13
- package/src/extensions/util/dom.ts +36 -0
- package/src/hooks/defs.ts +6 -20
- package/src/hooks/useActionHandler.ts +11 -11
- package/src/hooks/useEditorView.ts +0 -1
- package/src/{components/TextEditor/hooks.stories.tsx → hooks/useTextEditor.stories.tsx} +8 -8
- package/src/hooks/useTextEditor.ts +69 -14
- package/src/hooks/useTextModel.ts +6 -13
- package/src/index.ts +2 -0
- package/src/themes/default.ts +1 -0
- package/dist/types/src/components/TextEditor/automerge.stories.d.ts.map +0 -1
- package/dist/types/src/components/TextEditor/hooks.stories.d.ts.map +0 -1
- package/dist/types/src/extensions/basic.d.ts +0 -9
- package/dist/types/src/extensions/basic.d.ts.map +0 -1
- package/src/extensions/basic.ts +0 -41
|
@@ -23,20 +23,19 @@ var translations_default = [
|
|
|
23
23
|
];
|
|
24
24
|
|
|
25
25
|
// packages/ui/react-ui-editor/src/index.ts
|
|
26
|
-
import { keymap as
|
|
26
|
+
import { keymap as keymap9 } from "@codemirror/view";
|
|
27
|
+
import { tags as tags2 } from "@lezer/highlight";
|
|
27
28
|
import { TextKind } from "@dxos/protocols/proto/dxos/echo/model/text";
|
|
28
29
|
import { Doc, YText, YXmlFragment } from "@dxos/text-model";
|
|
29
30
|
|
|
30
|
-
// packages/ui/react-ui-editor/src/components/TextEditor/index.ts
|
|
31
|
-
import { tags as tags2 } from "@lezer/highlight";
|
|
32
|
-
|
|
33
31
|
// packages/ui/react-ui-editor/src/components/TextEditor/TextEditor.tsx
|
|
34
|
-
import { EditorState as
|
|
35
|
-
import { EditorView as
|
|
32
|
+
import { EditorState as EditorState3 } from "@codemirror/state";
|
|
33
|
+
import { EditorView as EditorView17, scrollPastEnd as scrollPastEnd2 } from "@codemirror/view";
|
|
36
34
|
import { useFocusableGroup } from "@fluentui/react-tabster";
|
|
37
|
-
import
|
|
38
|
-
import React, { forwardRef, useCallback, useEffect as
|
|
39
|
-
import {
|
|
35
|
+
import defaultsDeep3 from "lodash.defaultsdeep";
|
|
36
|
+
import React, { forwardRef, useCallback, useEffect as useEffect3, useImperativeHandle, useRef as useRef3, useState as useState5, useMemo as useMemo3 } from "react";
|
|
37
|
+
import { DocAccessor } from "@dxos/echo-schema";
|
|
38
|
+
import { log as log5 } from "@dxos/log";
|
|
40
39
|
import { useThemeContext } from "@dxos/react-ui";
|
|
41
40
|
import { focusRing } from "@dxos/react-ui-theme";
|
|
42
41
|
import { isNotFalsy as isNotFalsy4 } from "@dxos/util";
|
|
@@ -733,28 +732,8 @@ var styles2 = EditorView3.baseTheme({
|
|
|
733
732
|
}
|
|
734
733
|
});
|
|
735
734
|
|
|
736
|
-
// packages/ui/react-ui-editor/src/extensions/basic.ts
|
|
737
|
-
import { closeBrackets } from "@codemirror/autocomplete";
|
|
738
|
-
import { history } from "@codemirror/commands";
|
|
739
|
-
import { bracketMatching, defaultHighlightStyle, syntaxHighlighting } from "@codemirror/language";
|
|
740
|
-
import { oneDarkHighlightStyle } from "@codemirror/theme-one-dark";
|
|
741
|
-
import { drawSelection, EditorView as EditorView4, highlightActiveLine, placeholder } from "@codemirror/view";
|
|
742
|
-
import { isNotFalsy as isNotFalsy2 } from "@dxos/util";
|
|
743
|
-
var createBasicBundle = ({ themeMode, placeholder: _placeholder, lineWrapping = true, bracketMatching: _bracketMatching = true } = {}) => [
|
|
744
|
-
lineWrapping && EditorView4.lineWrapping,
|
|
745
|
-
// https://codemirror.net/docs/ref/#codemirror.minimalSetup
|
|
746
|
-
_bracketMatching && bracketMatching(),
|
|
747
|
-
closeBrackets(),
|
|
748
|
-
drawSelection(),
|
|
749
|
-
highlightActiveLine(),
|
|
750
|
-
history(),
|
|
751
|
-
_placeholder && placeholder(_placeholder),
|
|
752
|
-
// https://github.com/codemirror/theme-one-dark
|
|
753
|
-
themeMode === "dark" ? syntaxHighlighting(oneDarkHighlightStyle) : syntaxHighlighting(defaultHighlightStyle)
|
|
754
|
-
].filter(isNotFalsy2);
|
|
755
|
-
|
|
756
735
|
// packages/ui/react-ui-editor/src/extensions/blast.ts
|
|
757
|
-
import { EditorView as
|
|
736
|
+
import { EditorView as EditorView4, keymap as keymap2 } from "@codemirror/view";
|
|
758
737
|
import defaultsDeep from "lodash.defaultsdeep";
|
|
759
738
|
import { invariant } from "@dxos/invariant";
|
|
760
739
|
var __dxlog_file2 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/extensions/blast.ts";
|
|
@@ -802,7 +781,7 @@ var blast = (options = defaultOptions) => {
|
|
|
802
781
|
};
|
|
803
782
|
return [
|
|
804
783
|
// Cursor moved.
|
|
805
|
-
|
|
784
|
+
EditorView4.updateListener.of((update2) => {
|
|
806
785
|
if (blaster?.node !== update2.view.scrollDOM) {
|
|
807
786
|
if (blaster) {
|
|
808
787
|
blaster.destroy();
|
|
@@ -1063,10 +1042,227 @@ var random = (min, max) => {
|
|
|
1063
1042
|
return min + ~~(Math.random() * (max - min + 1));
|
|
1064
1043
|
};
|
|
1065
1044
|
|
|
1045
|
+
// packages/ui/react-ui-editor/src/extensions/command/command.ts
|
|
1046
|
+
import { EditorView as EditorView6, keymap as keymap3 } from "@codemirror/view";
|
|
1047
|
+
|
|
1048
|
+
// packages/ui/react-ui-editor/src/extensions/command/hint.ts
|
|
1049
|
+
import { RangeSetBuilder } from "@codemirror/state";
|
|
1050
|
+
import { Decoration as Decoration3, EditorView as EditorView5, ViewPlugin as ViewPlugin3, WidgetType as WidgetType2 } from "@codemirror/view";
|
|
1051
|
+
|
|
1052
|
+
// packages/ui/react-ui-editor/src/extensions/command/state.ts
|
|
1053
|
+
import { Facet as Facet3, StateEffect as StateEffect2, StateField as StateField3 } from "@codemirror/state";
|
|
1054
|
+
import { showTooltip } from "@codemirror/view";
|
|
1055
|
+
var commandConfig = Facet3.define({
|
|
1056
|
+
combine: (providers) => providers[0]
|
|
1057
|
+
});
|
|
1058
|
+
var commandState = StateField3.define({
|
|
1059
|
+
create: () => ({}),
|
|
1060
|
+
update: (state, tr) => {
|
|
1061
|
+
for (const effect of tr.effects) {
|
|
1062
|
+
if (effect.is(closeEffect)) {
|
|
1063
|
+
return {};
|
|
1064
|
+
}
|
|
1065
|
+
if (effect.is(openEffect)) {
|
|
1066
|
+
const options = tr.state.facet(commandConfig);
|
|
1067
|
+
const { pos, fullWidth } = effect.value;
|
|
1068
|
+
const tooltip = {
|
|
1069
|
+
pos,
|
|
1070
|
+
above: false,
|
|
1071
|
+
arrow: false,
|
|
1072
|
+
strictSide: true,
|
|
1073
|
+
create: (view) => {
|
|
1074
|
+
const dom = document.createElement("div");
|
|
1075
|
+
const tooltipView = {
|
|
1076
|
+
dom,
|
|
1077
|
+
mount: (view2) => {
|
|
1078
|
+
if (fullWidth) {
|
|
1079
|
+
const parent = dom.parentElement;
|
|
1080
|
+
const { paddingLeft, paddingRight } = window.getComputedStyle(parent);
|
|
1081
|
+
const widthWithoutPadding = parent.clientWidth - parseFloat(paddingLeft) - parseFloat(paddingRight);
|
|
1082
|
+
dom.style.width = `${widthWithoutPadding}px`;
|
|
1083
|
+
}
|
|
1084
|
+
options.onRender(dom, (action) => {
|
|
1085
|
+
view2.dispatch({
|
|
1086
|
+
effects: closeEffect.of(null)
|
|
1087
|
+
});
|
|
1088
|
+
if (action?.insert?.length) {
|
|
1089
|
+
view2.dispatch({
|
|
1090
|
+
changes: {
|
|
1091
|
+
from: pos,
|
|
1092
|
+
insert: action.insert
|
|
1093
|
+
},
|
|
1094
|
+
selection: {
|
|
1095
|
+
anchor: pos + action.insert.length
|
|
1096
|
+
}
|
|
1097
|
+
});
|
|
1098
|
+
}
|
|
1099
|
+
setTimeout(() => view2.focus());
|
|
1100
|
+
});
|
|
1101
|
+
}
|
|
1102
|
+
};
|
|
1103
|
+
return tooltipView;
|
|
1104
|
+
}
|
|
1105
|
+
};
|
|
1106
|
+
return {
|
|
1107
|
+
tooltip
|
|
1108
|
+
};
|
|
1109
|
+
}
|
|
1110
|
+
}
|
|
1111
|
+
return state;
|
|
1112
|
+
},
|
|
1113
|
+
provide: (f) => [
|
|
1114
|
+
showTooltip.from(f, (value) => value.tooltip ?? null)
|
|
1115
|
+
]
|
|
1116
|
+
});
|
|
1117
|
+
var openEffect = StateEffect2.define();
|
|
1118
|
+
var closeEffect = StateEffect2.define();
|
|
1119
|
+
var openCommand = (view) => {
|
|
1120
|
+
if (view.state.field(commandState, false)) {
|
|
1121
|
+
const selection = view.state.selection.main;
|
|
1122
|
+
const line = view.state.doc.lineAt(selection.from);
|
|
1123
|
+
if (line.from === selection.from && line.from === line.to) {
|
|
1124
|
+
view.dispatch({
|
|
1125
|
+
effects: openEffect.of({
|
|
1126
|
+
pos: selection.anchor,
|
|
1127
|
+
fullWidth: true
|
|
1128
|
+
})
|
|
1129
|
+
});
|
|
1130
|
+
return true;
|
|
1131
|
+
}
|
|
1132
|
+
}
|
|
1133
|
+
return false;
|
|
1134
|
+
};
|
|
1135
|
+
var closeCommand = (view) => {
|
|
1136
|
+
if (view.state.field(commandState, false)) {
|
|
1137
|
+
view.dispatch({
|
|
1138
|
+
effects: closeEffect.of(null)
|
|
1139
|
+
});
|
|
1140
|
+
return true;
|
|
1141
|
+
}
|
|
1142
|
+
return false;
|
|
1143
|
+
};
|
|
1144
|
+
var commandKeyBindings = [
|
|
1145
|
+
{
|
|
1146
|
+
key: "/",
|
|
1147
|
+
run: openCommand
|
|
1148
|
+
},
|
|
1149
|
+
{
|
|
1150
|
+
key: "Escape",
|
|
1151
|
+
run: closeCommand
|
|
1152
|
+
}
|
|
1153
|
+
];
|
|
1154
|
+
|
|
1155
|
+
// packages/ui/react-ui-editor/src/extensions/util/dom.ts
|
|
1156
|
+
var flattenRect = (rect, left) => {
|
|
1157
|
+
const x = left ? rect.left : rect.right;
|
|
1158
|
+
return {
|
|
1159
|
+
left: x,
|
|
1160
|
+
right: x,
|
|
1161
|
+
top: rect.top,
|
|
1162
|
+
bottom: rect.bottom
|
|
1163
|
+
};
|
|
1164
|
+
};
|
|
1165
|
+
var scratchRange;
|
|
1166
|
+
var textRange = (node, from, to = from) => {
|
|
1167
|
+
const range = scratchRange || (scratchRange = document.createRange());
|
|
1168
|
+
range.setEnd(node, to);
|
|
1169
|
+
range.setStart(node, from);
|
|
1170
|
+
return range;
|
|
1171
|
+
};
|
|
1172
|
+
var clientRectsFor = (dom) => {
|
|
1173
|
+
if (dom.nodeType === 3) {
|
|
1174
|
+
return textRange(dom, 0, dom.nodeValue.length).getClientRects();
|
|
1175
|
+
} else if (dom.nodeType === 1) {
|
|
1176
|
+
return dom.getClientRects();
|
|
1177
|
+
} else {
|
|
1178
|
+
return [];
|
|
1179
|
+
}
|
|
1180
|
+
};
|
|
1181
|
+
|
|
1182
|
+
// packages/ui/react-ui-editor/src/extensions/command/hint.ts
|
|
1183
|
+
var CommandHint = class extends WidgetType2 {
|
|
1184
|
+
constructor(content) {
|
|
1185
|
+
super();
|
|
1186
|
+
this.content = content;
|
|
1187
|
+
}
|
|
1188
|
+
toDOM() {
|
|
1189
|
+
const wrap = document.createElement("span");
|
|
1190
|
+
wrap.className = "cm-placeholder";
|
|
1191
|
+
wrap.style.pointerEvents = "none";
|
|
1192
|
+
wrap.appendChild(typeof this.content === "string" ? document.createTextNode(this.content) : this.content);
|
|
1193
|
+
if (typeof this.content === "string") {
|
|
1194
|
+
wrap.setAttribute("aria-label", "placeholder " + this.content);
|
|
1195
|
+
} else {
|
|
1196
|
+
wrap.setAttribute("aria-hidden", "true");
|
|
1197
|
+
}
|
|
1198
|
+
return wrap;
|
|
1199
|
+
}
|
|
1200
|
+
coordsAt(dom) {
|
|
1201
|
+
const rects = dom.firstChild ? clientRectsFor(dom.firstChild) : [];
|
|
1202
|
+
if (!rects.length) {
|
|
1203
|
+
return null;
|
|
1204
|
+
}
|
|
1205
|
+
const style = window.getComputedStyle(dom.parentNode);
|
|
1206
|
+
const rect = flattenRect(rects[0], style.direction !== "rtl");
|
|
1207
|
+
const lineHeight = parseInt(style.lineHeight);
|
|
1208
|
+
if (rect.bottom - rect.top > lineHeight * 1.5) {
|
|
1209
|
+
return {
|
|
1210
|
+
left: rect.left,
|
|
1211
|
+
right: rect.right,
|
|
1212
|
+
top: rect.top,
|
|
1213
|
+
bottom: rect.top + lineHeight
|
|
1214
|
+
};
|
|
1215
|
+
}
|
|
1216
|
+
return rect;
|
|
1217
|
+
}
|
|
1218
|
+
ignoreEvent() {
|
|
1219
|
+
return false;
|
|
1220
|
+
}
|
|
1221
|
+
};
|
|
1222
|
+
var hintViewPlugin = ({ onHint }) => ViewPlugin3.fromClass(class {
|
|
1223
|
+
constructor() {
|
|
1224
|
+
this.deco = Decoration3.none;
|
|
1225
|
+
}
|
|
1226
|
+
update(update2) {
|
|
1227
|
+
const builder = new RangeSetBuilder();
|
|
1228
|
+
const cState = update2.view.state.field(commandState, false);
|
|
1229
|
+
if (!cState?.tooltip) {
|
|
1230
|
+
const selection = update2.view.state.selection.main;
|
|
1231
|
+
const line = update2.view.state.doc.lineAt(selection.from);
|
|
1232
|
+
if (selection.from === selection.to && line.from === line.to) {
|
|
1233
|
+
const hint = onHint();
|
|
1234
|
+
if (hint) {
|
|
1235
|
+
builder.add(selection.from, selection.to, Decoration3.widget({
|
|
1236
|
+
widget: new CommandHint(hint)
|
|
1237
|
+
}));
|
|
1238
|
+
}
|
|
1239
|
+
}
|
|
1240
|
+
}
|
|
1241
|
+
this.deco = builder.finish();
|
|
1242
|
+
}
|
|
1243
|
+
}, {
|
|
1244
|
+
provide: (plugin) => [
|
|
1245
|
+
EditorView5.decorations.of((view) => view.plugin(plugin)?.deco ?? Decoration3.none)
|
|
1246
|
+
]
|
|
1247
|
+
});
|
|
1248
|
+
|
|
1249
|
+
// packages/ui/react-ui-editor/src/extensions/command/command.ts
|
|
1250
|
+
var command = (options) => {
|
|
1251
|
+
return [
|
|
1252
|
+
commandConfig.of(options),
|
|
1253
|
+
commandState,
|
|
1254
|
+
keymap3.of(commandKeyBindings),
|
|
1255
|
+
hintViewPlugin(options),
|
|
1256
|
+
EditorView6.focusChangeEffect.of((_, focusing) => {
|
|
1257
|
+
return focusing ? closeEffect.of(null) : null;
|
|
1258
|
+
})
|
|
1259
|
+
];
|
|
1260
|
+
};
|
|
1261
|
+
|
|
1066
1262
|
// packages/ui/react-ui-editor/src/extensions/comments.ts
|
|
1067
1263
|
import { invertedEffects } from "@codemirror/commands";
|
|
1068
|
-
import { Facet as
|
|
1069
|
-
import { hoverTooltip, keymap as
|
|
1264
|
+
import { Facet as Facet4, StateEffect as StateEffect3, StateField as StateField4 } from "@codemirror/state";
|
|
1265
|
+
import { hoverTooltip, keymap as keymap4, Decoration as Decoration4, EditorView as EditorView7 } from "@codemirror/view";
|
|
1070
1266
|
import sortBy from "lodash.sortby";
|
|
1071
1267
|
import { useEffect } from "react";
|
|
1072
1268
|
import { debounce } from "@dxos/async";
|
|
@@ -1142,13 +1338,13 @@ var logChanges = (trs) => {
|
|
|
1142
1338
|
};
|
|
1143
1339
|
|
|
1144
1340
|
// packages/ui/react-ui-editor/src/extensions/comments.ts
|
|
1145
|
-
var documentId =
|
|
1341
|
+
var documentId = Facet4.define({
|
|
1146
1342
|
combine: (values) => values[0]
|
|
1147
1343
|
});
|
|
1148
|
-
var setComments =
|
|
1149
|
-
var setSelection =
|
|
1150
|
-
var setCommentState =
|
|
1151
|
-
var commentsState =
|
|
1344
|
+
var setComments = StateEffect3.define();
|
|
1345
|
+
var setSelection = StateEffect3.define();
|
|
1346
|
+
var setCommentState = StateEffect3.define();
|
|
1347
|
+
var commentsState = StateField4.define({
|
|
1152
1348
|
create: (state) => ({
|
|
1153
1349
|
id: state.facet(documentId),
|
|
1154
1350
|
comments: [],
|
|
@@ -1186,7 +1382,7 @@ var commentsState = StateField3.define({
|
|
|
1186
1382
|
return value;
|
|
1187
1383
|
}
|
|
1188
1384
|
});
|
|
1189
|
-
var styles3 =
|
|
1385
|
+
var styles3 = EditorView7.baseTheme({
|
|
1190
1386
|
"&light .cm-comment, &light .cm-comment-current": {
|
|
1191
1387
|
mixBlendMode: "darken"
|
|
1192
1388
|
},
|
|
@@ -1208,19 +1404,19 @@ var styles3 = EditorView6.baseTheme({
|
|
|
1208
1404
|
backgroundColor: getToken("extend.colors.yellow.950")
|
|
1209
1405
|
}
|
|
1210
1406
|
});
|
|
1211
|
-
var commentMark =
|
|
1407
|
+
var commentMark = Decoration4.mark({
|
|
1212
1408
|
class: "cm-comment",
|
|
1213
1409
|
attributes: {
|
|
1214
1410
|
"data-testid": "cm-comment"
|
|
1215
1411
|
}
|
|
1216
1412
|
});
|
|
1217
|
-
var commentCurrentMark =
|
|
1413
|
+
var commentCurrentMark = Decoration4.mark({
|
|
1218
1414
|
class: "cm-comment-current",
|
|
1219
1415
|
attributes: {
|
|
1220
1416
|
"data-testid": "cm-comment"
|
|
1221
1417
|
}
|
|
1222
1418
|
});
|
|
1223
|
-
var commentsDecorations =
|
|
1419
|
+
var commentsDecorations = EditorView7.decorations.compute([
|
|
1224
1420
|
commentsState
|
|
1225
1421
|
], (state) => {
|
|
1226
1422
|
const { selection: { current }, comments: comments2 } = state.field(commentsState);
|
|
@@ -1236,7 +1432,7 @@ var commentsDecorations = EditorView6.decorations.compute([
|
|
|
1236
1432
|
return commentMark.range(range.from, range.to);
|
|
1237
1433
|
}
|
|
1238
1434
|
}).filter(nonNullable);
|
|
1239
|
-
return
|
|
1435
|
+
return Decoration4.set(decorations);
|
|
1240
1436
|
});
|
|
1241
1437
|
var trackPastedComments = (onUpdate) => {
|
|
1242
1438
|
let tracked = null;
|
|
@@ -1258,7 +1454,7 @@ var trackPastedComments = (onUpdate) => {
|
|
|
1258
1454
|
}
|
|
1259
1455
|
};
|
|
1260
1456
|
return [
|
|
1261
|
-
|
|
1457
|
+
EditorView7.domEventHandlers({
|
|
1262
1458
|
cut: handleTrack,
|
|
1263
1459
|
copy: handleTrack
|
|
1264
1460
|
}),
|
|
@@ -1280,7 +1476,7 @@ var trackPastedComments = (onUpdate) => {
|
|
|
1280
1476
|
return effects;
|
|
1281
1477
|
}),
|
|
1282
1478
|
// Handle paste or the undo of comment deletion.
|
|
1283
|
-
|
|
1479
|
+
EditorView7.updateListener.of((update2) => {
|
|
1284
1480
|
const restore = [];
|
|
1285
1481
|
for (let i = 0; i < update2.transactions.length; i++) {
|
|
1286
1482
|
const tr = update2.transactions[i];
|
|
@@ -1336,7 +1532,7 @@ var mapTrackedComment = (comment, changes) => ({
|
|
|
1336
1532
|
from: changes.mapPos(comment.from, 1),
|
|
1337
1533
|
to: changes.mapPos(comment.to, 1)
|
|
1338
1534
|
});
|
|
1339
|
-
var restoreCommentEffect =
|
|
1535
|
+
var restoreCommentEffect = StateEffect3.define({
|
|
1340
1536
|
map: mapTrackedComment
|
|
1341
1537
|
});
|
|
1342
1538
|
var createComment = (view) => {
|
|
@@ -1377,7 +1573,7 @@ var createComment = (view) => {
|
|
|
1377
1573
|
}
|
|
1378
1574
|
return false;
|
|
1379
1575
|
};
|
|
1380
|
-
var optionsFacet =
|
|
1576
|
+
var optionsFacet = Facet4.define({
|
|
1381
1577
|
combine: (providers) => providers[0]
|
|
1382
1578
|
});
|
|
1383
1579
|
var comments = (options = {}) => {
|
|
@@ -1392,7 +1588,7 @@ var comments = (options = {}) => {
|
|
|
1392
1588
|
//
|
|
1393
1589
|
// Keymap.
|
|
1394
1590
|
//
|
|
1395
|
-
options.onCreate ?
|
|
1591
|
+
options.onCreate ? keymap4.of([
|
|
1396
1592
|
{
|
|
1397
1593
|
key: shortcut,
|
|
1398
1594
|
run: callbackWrapper(createComment)
|
|
@@ -1431,7 +1627,7 @@ var comments = (options = {}) => {
|
|
|
1431
1627
|
//
|
|
1432
1628
|
// Track deleted ranges and update ranges for decorations.
|
|
1433
1629
|
//
|
|
1434
|
-
|
|
1630
|
+
EditorView7.updateListener.of(({ view, state, changes }) => {
|
|
1435
1631
|
let mod = false;
|
|
1436
1632
|
const { comments: comments2, ...value } = state.field(commentsState);
|
|
1437
1633
|
changes.iterChanges((from, to, from2, to2) => {
|
|
@@ -1463,7 +1659,7 @@ var comments = (options = {}) => {
|
|
|
1463
1659
|
//
|
|
1464
1660
|
// Track selection/proximity.
|
|
1465
1661
|
//
|
|
1466
|
-
|
|
1662
|
+
EditorView7.updateListener.of(({ view, state }) => {
|
|
1467
1663
|
let min = Infinity;
|
|
1468
1664
|
const { selection: { current, closest }, comments: comments2 } = state.field(commentsState);
|
|
1469
1665
|
const { head } = state.selection.main;
|
|
@@ -1512,7 +1708,7 @@ var focusComment = (view, id, center = true) => {
|
|
|
1512
1708
|
},
|
|
1513
1709
|
effects: [
|
|
1514
1710
|
//
|
|
1515
|
-
|
|
1711
|
+
EditorView7.scrollIntoView(range.from, center ? {
|
|
1516
1712
|
y: "center"
|
|
1517
1713
|
} : void 0),
|
|
1518
1714
|
setSelection.of({
|
|
@@ -1540,14 +1736,14 @@ var useComments = (view, id, comments2 = []) => {
|
|
|
1540
1736
|
};
|
|
1541
1737
|
|
|
1542
1738
|
// packages/ui/react-ui-editor/src/extensions/cursor-line-margin.ts
|
|
1543
|
-
import { Facet as
|
|
1544
|
-
import { EditorView as
|
|
1545
|
-
var cursorLineMarginFacet =
|
|
1739
|
+
import { Facet as Facet5, Transaction } from "@codemirror/state";
|
|
1740
|
+
import { EditorView as EditorView8 } from "@codemirror/view";
|
|
1741
|
+
var cursorLineMarginFacet = Facet5.define({
|
|
1546
1742
|
combine: (input) => input[0] ?? 3
|
|
1547
1743
|
});
|
|
1548
1744
|
var annotation = "cursorLineMargin";
|
|
1549
1745
|
var lineAtPos = (s, pos) => s.doc.lineAt(pos).number;
|
|
1550
|
-
var cursorLineMargin =
|
|
1746
|
+
var cursorLineMargin = EditorView8.updateListener.of(({ transactions, state, selectionSet, startState, view }) => {
|
|
1551
1747
|
if (transactions.length < 1 || transactions.some((tr) => tr.isUserEvent(annotation))) {
|
|
1552
1748
|
return;
|
|
1553
1749
|
}
|
|
@@ -1583,38 +1779,48 @@ var cursorLineMargin = EditorView7.updateListener.of(({ transactions, state, sel
|
|
|
1583
1779
|
}
|
|
1584
1780
|
view.dispatch({
|
|
1585
1781
|
annotations: Transaction.userEvent.of(annotation),
|
|
1586
|
-
effects:
|
|
1782
|
+
effects: EditorView8.scrollIntoView(s.selection.main.head, {
|
|
1587
1783
|
y: needsScrollTop ? "start" : "end",
|
|
1588
1784
|
yMargin: view.defaultLineHeight * cursorLineMargin2
|
|
1589
1785
|
})
|
|
1590
1786
|
});
|
|
1591
1787
|
});
|
|
1592
1788
|
|
|
1789
|
+
// packages/ui/react-ui-editor/src/extensions/dnd.ts
|
|
1790
|
+
import { EditorView as EditorView9 } from "@codemirror/view";
|
|
1791
|
+
var dnd = () => {
|
|
1792
|
+
return EditorView9.domEventHandlers({
|
|
1793
|
+
drop: (event, view) => {
|
|
1794
|
+
console.log(event);
|
|
1795
|
+
}
|
|
1796
|
+
});
|
|
1797
|
+
};
|
|
1798
|
+
|
|
1593
1799
|
// packages/ui/react-ui-editor/src/extensions/listener.ts
|
|
1594
|
-
import { EditorView as
|
|
1800
|
+
import { EditorView as EditorView10 } from "@codemirror/view";
|
|
1595
1801
|
var listener = ({ onFocus, onChange }) => {
|
|
1596
1802
|
const extensions = [];
|
|
1597
|
-
onFocus && extensions.push(
|
|
1598
|
-
onFocus(
|
|
1803
|
+
onFocus && extensions.push(EditorView10.focusChangeEffect.of((_, focusing) => {
|
|
1804
|
+
onFocus(focusing);
|
|
1599
1805
|
return null;
|
|
1600
1806
|
}));
|
|
1601
|
-
onChange && extensions.push(
|
|
1807
|
+
onChange && extensions.push(EditorView10.updateListener.of((update2) => {
|
|
1602
1808
|
onChange(update2.state.doc.toString());
|
|
1603
1809
|
}));
|
|
1604
1810
|
return extensions;
|
|
1605
1811
|
};
|
|
1606
1812
|
|
|
1607
1813
|
// packages/ui/react-ui-editor/src/extensions/markdown/bundle.ts
|
|
1608
|
-
import { closeBrackets
|
|
1609
|
-
import { history
|
|
1814
|
+
import { closeBrackets, closeBracketsKeymap } from "@codemirror/autocomplete";
|
|
1815
|
+
import { history, historyKeymap, indentWithTab, standardKeymap } from "@codemirror/commands";
|
|
1610
1816
|
import { markdownLanguage as markdownLanguage3, markdown } from "@codemirror/lang-markdown";
|
|
1611
|
-
import { bracketMatching
|
|
1817
|
+
import { bracketMatching, defaultHighlightStyle, indentOnInput, syntaxHighlighting } from "@codemirror/language";
|
|
1612
1818
|
import { languages } from "@codemirror/language-data";
|
|
1613
1819
|
import { searchKeymap } from "@codemirror/search";
|
|
1614
1820
|
import { EditorState } from "@codemirror/state";
|
|
1615
|
-
import { oneDarkHighlightStyle
|
|
1616
|
-
import {
|
|
1617
|
-
import { isNotFalsy as
|
|
1821
|
+
import { oneDarkHighlightStyle } from "@codemirror/theme-one-dark";
|
|
1822
|
+
import { EditorView as EditorView11, drawSelection, dropCursor, keymap as keymap5, placeholder } from "@codemirror/view";
|
|
1823
|
+
import { isNotFalsy as isNotFalsy2 } from "@dxos/util";
|
|
1618
1824
|
|
|
1619
1825
|
// packages/ui/react-ui-editor/src/extensions/markdown/highlight.ts
|
|
1620
1826
|
import { markdownLanguage as markdownLanguage2 } from "@codemirror/lang-markdown";
|
|
@@ -1807,19 +2013,17 @@ var markdownHighlightStyle = (readonly) => {
|
|
|
1807
2013
|
// packages/ui/react-ui-editor/src/extensions/markdown/bundle.ts
|
|
1808
2014
|
var createMarkdownExtensions = ({ themeMode, placeholder: _placeholder, lineWrapping = true } = {}) => {
|
|
1809
2015
|
return [
|
|
1810
|
-
|
|
2016
|
+
// TODO(burdon): Reconcile with createBasicExtensions.
|
|
2017
|
+
lineWrapping && EditorView11.lineWrapping,
|
|
1811
2018
|
EditorState.allowMultipleSelections.of(true),
|
|
1812
2019
|
EditorState.tabSize.of(2),
|
|
1813
|
-
|
|
1814
|
-
|
|
1815
|
-
closeBrackets2(),
|
|
1816
|
-
crosshairCursor(),
|
|
2020
|
+
bracketMatching(),
|
|
2021
|
+
closeBrackets(),
|
|
1817
2022
|
dropCursor(),
|
|
1818
|
-
|
|
1819
|
-
|
|
1820
|
-
history2(),
|
|
2023
|
+
drawSelection(),
|
|
2024
|
+
history(),
|
|
1821
2025
|
indentOnInput(),
|
|
1822
|
-
_placeholder &&
|
|
2026
|
+
_placeholder && placeholder(_placeholder),
|
|
1823
2027
|
// Main extension.
|
|
1824
2028
|
// https://github.com/codemirror/lang-markdown
|
|
1825
2029
|
// https://codemirror.net/5/mode/markdown/index.html (demo).
|
|
@@ -1839,10 +2043,10 @@ var createMarkdownExtensions = ({ themeMode, placeholder: _placeholder, lineWrap
|
|
|
1839
2043
|
]
|
|
1840
2044
|
}),
|
|
1841
2045
|
// https://github.com/codemirror/theme-one-dark
|
|
1842
|
-
themeMode === "dark" ?
|
|
2046
|
+
themeMode === "dark" ? syntaxHighlighting(oneDarkHighlightStyle) : syntaxHighlighting(defaultHighlightStyle),
|
|
1843
2047
|
// Custom styles.
|
|
1844
|
-
|
|
1845
|
-
|
|
2048
|
+
syntaxHighlighting(markdownHighlightStyle()),
|
|
2049
|
+
keymap5.of([
|
|
1846
2050
|
// https://codemirror.net/docs/ref/#commands.indentWithTab
|
|
1847
2051
|
indentWithTab,
|
|
1848
2052
|
// https://codemirror.net/docs/ref/#autocomplete.closeBracketsKeymap
|
|
@@ -1854,22 +2058,22 @@ var createMarkdownExtensions = ({ themeMode, placeholder: _placeholder, lineWrap
|
|
|
1854
2058
|
// https://codemirror.net/docs/ref/#commands.standardKeymap
|
|
1855
2059
|
...standardKeymap
|
|
1856
2060
|
])
|
|
1857
|
-
].filter(
|
|
2061
|
+
].filter(isNotFalsy2);
|
|
1858
2062
|
};
|
|
1859
2063
|
|
|
1860
2064
|
// packages/ui/react-ui-editor/src/extensions/markdown/decorate.ts
|
|
1861
2065
|
import { syntaxTree } from "@codemirror/language";
|
|
1862
|
-
import { RangeSetBuilder, StateEffect as
|
|
1863
|
-
import { EditorView as
|
|
2066
|
+
import { RangeSetBuilder as RangeSetBuilder2, StateEffect as StateEffect4 } from "@codemirror/state";
|
|
2067
|
+
import { EditorView as EditorView12, Decoration as Decoration5, WidgetType as WidgetType3, ViewPlugin as ViewPlugin4 } from "@codemirror/view";
|
|
1864
2068
|
import { mx as mx2 } from "@dxos/react-ui-theme";
|
|
1865
|
-
var HorizontalRuleWidget = class extends
|
|
2069
|
+
var HorizontalRuleWidget = class extends WidgetType3 {
|
|
1866
2070
|
toDOM() {
|
|
1867
2071
|
const el = document.createElement("span");
|
|
1868
2072
|
el.className = "cm-hr";
|
|
1869
2073
|
return el;
|
|
1870
2074
|
}
|
|
1871
2075
|
};
|
|
1872
|
-
var LinkButton = class extends
|
|
2076
|
+
var LinkButton = class extends WidgetType3 {
|
|
1873
2077
|
constructor(url, render) {
|
|
1874
2078
|
super();
|
|
1875
2079
|
this.url = url;
|
|
@@ -1884,7 +2088,7 @@ var LinkButton = class extends WidgetType2 {
|
|
|
1884
2088
|
return el;
|
|
1885
2089
|
}
|
|
1886
2090
|
};
|
|
1887
|
-
var CheckboxWidget = class extends
|
|
2091
|
+
var CheckboxWidget = class extends WidgetType3 {
|
|
1888
2092
|
constructor(_checked) {
|
|
1889
2093
|
super();
|
|
1890
2094
|
this._checked = _checked;
|
|
@@ -1921,23 +2125,23 @@ var CheckboxWidget = class extends WidgetType2 {
|
|
|
1921
2125
|
return false;
|
|
1922
2126
|
}
|
|
1923
2127
|
};
|
|
1924
|
-
var hide =
|
|
1925
|
-
var fencedCodeLine =
|
|
2128
|
+
var hide = Decoration5.replace({});
|
|
2129
|
+
var fencedCodeLine = Decoration5.line({
|
|
1926
2130
|
class: mx2("cm-code cm-codeblock-line")
|
|
1927
2131
|
});
|
|
1928
|
-
var fencedCodeLineFirst =
|
|
2132
|
+
var fencedCodeLineFirst = Decoration5.line({
|
|
1929
2133
|
class: mx2("cm-code cm-codeblock-line", "cm-codeblock-first")
|
|
1930
2134
|
});
|
|
1931
|
-
var fencedCodeLineLast =
|
|
2135
|
+
var fencedCodeLineLast = Decoration5.line({
|
|
1932
2136
|
class: mx2("cm-code cm-codeblock-line", "cm-codeblock-last")
|
|
1933
2137
|
});
|
|
1934
|
-
var horizontalRule =
|
|
2138
|
+
var horizontalRule = Decoration5.replace({
|
|
1935
2139
|
widget: new HorizontalRuleWidget()
|
|
1936
2140
|
});
|
|
1937
|
-
var checkedTask =
|
|
2141
|
+
var checkedTask = Decoration5.replace({
|
|
1938
2142
|
widget: new CheckboxWidget(true)
|
|
1939
2143
|
});
|
|
1940
|
-
var uncheckedTask =
|
|
2144
|
+
var uncheckedTask = Decoration5.replace({
|
|
1941
2145
|
widget: new CheckboxWidget(false)
|
|
1942
2146
|
});
|
|
1943
2147
|
var editingRange = (state, range, focus) => {
|
|
@@ -1952,8 +2156,8 @@ var MarksByParent = /* @__PURE__ */ new Set([
|
|
|
1952
2156
|
"SuperscriptMark"
|
|
1953
2157
|
]);
|
|
1954
2158
|
var buildDecorations = (view, options, focus) => {
|
|
1955
|
-
const deco = new
|
|
1956
|
-
const atomicDeco = new
|
|
2159
|
+
const deco = new RangeSetBuilder2();
|
|
2160
|
+
const atomicDeco = new RangeSetBuilder2();
|
|
1957
2161
|
const { state } = view;
|
|
1958
2162
|
for (const { from, to } of view.visibleRanges) {
|
|
1959
2163
|
syntaxTree(state).iterate({
|
|
@@ -1970,7 +2174,7 @@ var buildDecorations = (view, options, focus) => {
|
|
|
1970
2174
|
break;
|
|
1971
2175
|
}
|
|
1972
2176
|
const first = block.from <= node.from;
|
|
1973
|
-
const last = block.to >= node.to;
|
|
2177
|
+
const last = block.to >= node.to && /^(\s>)*```$/.test(state.doc.sliceString(block.from, block.to));
|
|
1974
2178
|
deco.add(block.from, block.from, first ? fencedCodeLineFirst : last ? fencedCodeLineLast : fencedCodeLine);
|
|
1975
2179
|
if (!editing && (first || last)) {
|
|
1976
2180
|
atomicDeco.add(block.from, block.to, hide);
|
|
@@ -1986,7 +2190,7 @@ var buildDecorations = (view, options, focus) => {
|
|
|
1986
2190
|
if (!editing) {
|
|
1987
2191
|
atomicDeco.add(node.from, marks[0].to, hide);
|
|
1988
2192
|
}
|
|
1989
|
-
deco.add(marks[0].to, marks[1].from,
|
|
2193
|
+
deco.add(marks[0].to, marks[1].from, Decoration5.mark({
|
|
1990
2194
|
tagName: "a",
|
|
1991
2195
|
attributes: {
|
|
1992
2196
|
class: "cm-link",
|
|
@@ -1996,7 +2200,7 @@ var buildDecorations = (view, options, focus) => {
|
|
|
1996
2200
|
}
|
|
1997
2201
|
}));
|
|
1998
2202
|
if (!editing) {
|
|
1999
|
-
atomicDeco.add(marks[1].from, node.to, options.renderLinkButton ?
|
|
2203
|
+
atomicDeco.add(marks[1].from, node.to, options.renderLinkButton ? Decoration5.replace({
|
|
2000
2204
|
widget: new LinkButton(url, options.renderLinkButton)
|
|
2001
2205
|
}) : hide);
|
|
2002
2206
|
}
|
|
@@ -2014,7 +2218,7 @@ var buildDecorations = (view, options, focus) => {
|
|
|
2014
2218
|
} else if (node.name === "TaskMarker") {
|
|
2015
2219
|
if (!editingRange(state, node, focus)) {
|
|
2016
2220
|
const checked = state.doc.sliceString(node.from + 1, node.to - 1) === "x";
|
|
2017
|
-
atomicDeco.add(node.from - 2, node.from - 1,
|
|
2221
|
+
atomicDeco.add(node.from - 2, node.from - 1, Decoration5.mark({
|
|
2018
2222
|
class: "cm-task"
|
|
2019
2223
|
}));
|
|
2020
2224
|
atomicDeco.add(node.from, node.to, checked ? checkedTask : uncheckedTask);
|
|
@@ -2032,50 +2236,51 @@ var buildDecorations = (view, options, focus) => {
|
|
|
2032
2236
|
atomicDeco: atomicDeco.finish()
|
|
2033
2237
|
};
|
|
2034
2238
|
};
|
|
2035
|
-
var forceUpdate =
|
|
2239
|
+
var forceUpdate = StateEffect4.define();
|
|
2036
2240
|
var decorateMarkdown = (options = {}) => {
|
|
2037
2241
|
return [
|
|
2038
|
-
|
|
2242
|
+
ViewPlugin4.fromClass(class {
|
|
2039
2243
|
constructor(view) {
|
|
2040
|
-
this.pendingUpdate = -1;
|
|
2041
2244
|
({ deco: this.deco, atomicDeco: this.atomicDeco } = buildDecorations(view, options, view.hasFocus));
|
|
2042
2245
|
}
|
|
2043
2246
|
update(update2) {
|
|
2044
|
-
if (update2.docChanged || update2.viewportChanged || update2.focusChanged || update2.transactions.some((tr) => tr.effects.some((e) => e.is(forceUpdate)))) {
|
|
2247
|
+
if (update2.docChanged || update2.viewportChanged || update2.focusChanged || update2.transactions.some((tr) => tr.effects.some((e) => e.is(forceUpdate))) || update2.selectionSet && !options.selectionChangeDelay) {
|
|
2045
2248
|
({ deco: this.deco, atomicDeco: this.atomicDeco } = buildDecorations(update2.view, options, update2.view.hasFocus));
|
|
2046
2249
|
this.clearUpdate();
|
|
2047
2250
|
} else if (update2.selectionSet) {
|
|
2048
2251
|
this.scheduleUpdate(update2.view);
|
|
2049
2252
|
}
|
|
2050
2253
|
}
|
|
2051
|
-
|
|
2052
|
-
|
|
2053
|
-
window.clearTimeout(this.pendingUpdate);
|
|
2054
|
-
this.pendingUpdate = -1;
|
|
2055
|
-
}
|
|
2056
|
-
}
|
|
2254
|
+
// TODO(burdon): BUG: If the cursor is at the end of a link at the end of a line,
|
|
2255
|
+
// the cursor will float in space or be in the wrong position after the decoration is applied.
|
|
2057
2256
|
scheduleUpdate(view) {
|
|
2058
2257
|
this.clearUpdate();
|
|
2059
|
-
this.pendingUpdate =
|
|
2258
|
+
this.pendingUpdate = setTimeout(() => {
|
|
2060
2259
|
view.dispatch({
|
|
2061
2260
|
effects: forceUpdate.of(null)
|
|
2062
2261
|
});
|
|
2063
|
-
}, options.selectionChangeDelay
|
|
2262
|
+
}, options.selectionChangeDelay);
|
|
2263
|
+
}
|
|
2264
|
+
clearUpdate() {
|
|
2265
|
+
if (this.pendingUpdate) {
|
|
2266
|
+
clearTimeout(this.pendingUpdate);
|
|
2267
|
+
this.pendingUpdate = void 0;
|
|
2268
|
+
}
|
|
2064
2269
|
}
|
|
2065
2270
|
destroy() {
|
|
2066
2271
|
this.clearUpdate();
|
|
2067
2272
|
}
|
|
2068
2273
|
}, {
|
|
2069
2274
|
provide: (plugin) => [
|
|
2070
|
-
|
|
2071
|
-
|
|
2072
|
-
|
|
2275
|
+
EditorView12.atomicRanges.of((view) => view.plugin(plugin)?.atomicDeco ?? Decoration5.none),
|
|
2276
|
+
EditorView12.decorations.of((view) => view.plugin(plugin)?.atomicDeco ?? Decoration5.none),
|
|
2277
|
+
EditorView12.decorations.of((view) => view.plugin(plugin)?.deco ?? Decoration5.none)
|
|
2073
2278
|
]
|
|
2074
2279
|
}),
|
|
2075
2280
|
formattingStyles
|
|
2076
2281
|
];
|
|
2077
2282
|
};
|
|
2078
|
-
var formattingStyles =
|
|
2283
|
+
var formattingStyles = EditorView12.baseTheme({
|
|
2079
2284
|
"& .cm-code": {
|
|
2080
2285
|
fontFamily: getToken("fontFamily.mono", []).join(",")
|
|
2081
2286
|
},
|
|
@@ -2128,7 +2333,7 @@ var formattingStyles = EditorView10.baseTheme({
|
|
|
2128
2333
|
import { snippet } from "@codemirror/autocomplete";
|
|
2129
2334
|
import { syntaxTree as syntaxTree2 } from "@codemirror/language";
|
|
2130
2335
|
import { EditorSelection } from "@codemirror/state";
|
|
2131
|
-
import { EditorView as
|
|
2336
|
+
import { EditorView as EditorView13, keymap as keymap6 } from "@codemirror/view";
|
|
2132
2337
|
import { useState, useMemo } from "react";
|
|
2133
2338
|
var compareFormatting = (a, b) => a.blockType === b.blockType && a.strong === b.strong && a.emphasis === b.emphasis && a.strikethrough === b.strikethrough && a.code === b.code && a.link === b.link && a.listStyle === b.listStyle && a.blockQuote === b.blockQuote;
|
|
2134
2339
|
var Inline;
|
|
@@ -3000,7 +3205,7 @@ var toggleCodeblock = (target) => {
|
|
|
3000
3205
|
};
|
|
3001
3206
|
var formatting = (options = {}) => {
|
|
3002
3207
|
return [
|
|
3003
|
-
|
|
3208
|
+
keymap6.of([
|
|
3004
3209
|
{
|
|
3005
3210
|
key: "meta-b",
|
|
3006
3211
|
run: toggleStrong
|
|
@@ -3198,7 +3403,7 @@ var getFormatting = (state) => {
|
|
|
3198
3403
|
};
|
|
3199
3404
|
var useFormattingState = () => {
|
|
3200
3405
|
const [state, setState] = useState(null);
|
|
3201
|
-
const observer = useMemo(() =>
|
|
3406
|
+
const observer = useMemo(() => EditorView13.updateListener.of((update2) => {
|
|
3202
3407
|
if (update2.docChanged || update2.selectionSet) {
|
|
3203
3408
|
const newState = getFormatting(update2.state);
|
|
3204
3409
|
if (!state || !compareFormatting(state, newState)) {
|
|
@@ -3214,12 +3419,12 @@ var useFormattingState = () => {
|
|
|
3214
3419
|
|
|
3215
3420
|
// packages/ui/react-ui-editor/src/extensions/markdown/image.ts
|
|
3216
3421
|
import { syntaxTree as syntaxTree3 } from "@codemirror/language";
|
|
3217
|
-
import { StateField as
|
|
3218
|
-
import { Decoration as
|
|
3422
|
+
import { StateField as StateField5 } from "@codemirror/state";
|
|
3423
|
+
import { Decoration as Decoration6, EditorView as EditorView14, WidgetType as WidgetType4 } from "@codemirror/view";
|
|
3219
3424
|
var image = (options = {}) => {
|
|
3220
|
-
return
|
|
3425
|
+
return StateField5.define({
|
|
3221
3426
|
create: (state) => {
|
|
3222
|
-
return
|
|
3427
|
+
return Decoration6.set(buildDecorations2(0, state.doc.length, state));
|
|
3223
3428
|
},
|
|
3224
3429
|
update: (value, tr) => {
|
|
3225
3430
|
if (!tr.docChanged && !tr.selection) {
|
|
@@ -3242,7 +3447,7 @@ var image = (options = {}) => {
|
|
|
3242
3447
|
add: buildDecorations2(from, to, tr.state)
|
|
3243
3448
|
});
|
|
3244
3449
|
},
|
|
3245
|
-
provide: (field) =>
|
|
3450
|
+
provide: (field) => EditorView14.decorations.from(field)
|
|
3246
3451
|
});
|
|
3247
3452
|
};
|
|
3248
3453
|
var preloaded = /* @__PURE__ */ new Set();
|
|
@@ -3264,7 +3469,7 @@ var buildDecorations2 = (from, to, state) => {
|
|
|
3264
3469
|
const hide2 = state.readOnly || cursor < node.from || cursor > node.to;
|
|
3265
3470
|
const url = state.sliceDoc(urlNode.from, urlNode.to);
|
|
3266
3471
|
preloadImage(url);
|
|
3267
|
-
decorations.push(
|
|
3472
|
+
decorations.push(Decoration6.replace({
|
|
3268
3473
|
block: true,
|
|
3269
3474
|
widget: new ImageWidget(url)
|
|
3270
3475
|
}).range(hide2 ? node.from : node.to, node.to));
|
|
@@ -3276,7 +3481,7 @@ var buildDecorations2 = (from, to, state) => {
|
|
|
3276
3481
|
});
|
|
3277
3482
|
return decorations;
|
|
3278
3483
|
};
|
|
3279
|
-
var ImageWidget = class extends
|
|
3484
|
+
var ImageWidget = class extends WidgetType4 {
|
|
3280
3485
|
constructor(_url) {
|
|
3281
3486
|
super();
|
|
3282
3487
|
this._url = _url;
|
|
@@ -3329,17 +3534,17 @@ var linkTooltip = (render) => hoverTooltip2((view, pos, side) => {
|
|
|
3329
3534
|
|
|
3330
3535
|
// packages/ui/react-ui-editor/src/extensions/markdown/table.ts
|
|
3331
3536
|
import { syntaxTree as syntaxTree5 } from "@codemirror/language";
|
|
3332
|
-
import { RangeSetBuilder as
|
|
3333
|
-
import { Decoration as
|
|
3537
|
+
import { RangeSetBuilder as RangeSetBuilder3, StateField as StateField6 } from "@codemirror/state";
|
|
3538
|
+
import { Decoration as Decoration7, EditorView as EditorView15, WidgetType as WidgetType5 } from "@codemirror/view";
|
|
3334
3539
|
var table = (options = {}) => {
|
|
3335
|
-
return
|
|
3540
|
+
return StateField6.define({
|
|
3336
3541
|
create: (state) => update(state, options),
|
|
3337
3542
|
update: (_, tr) => update(tr.state, options),
|
|
3338
|
-
provide: (field) =>
|
|
3543
|
+
provide: (field) => EditorView15.decorations.from(field)
|
|
3339
3544
|
});
|
|
3340
3545
|
};
|
|
3341
3546
|
var update = (state, options) => {
|
|
3342
|
-
const builder = new
|
|
3547
|
+
const builder = new RangeSetBuilder3();
|
|
3343
3548
|
const cursor = state.selection.main.head;
|
|
3344
3549
|
const tables = [];
|
|
3345
3550
|
const getTable = () => tables[tables.length - 1];
|
|
@@ -3379,16 +3584,16 @@ var update = (state, options) => {
|
|
|
3379
3584
|
});
|
|
3380
3585
|
tables.forEach((table2) => {
|
|
3381
3586
|
const hide2 = state.readOnly || cursor < table2.from || cursor > table2.to;
|
|
3382
|
-
hide2 && builder.add(table2.from, table2.to,
|
|
3587
|
+
hide2 && builder.add(table2.from, table2.to, Decoration7.replace({
|
|
3383
3588
|
widget: new TableWidget(table2)
|
|
3384
3589
|
}));
|
|
3385
|
-
builder.add(table2.from, table2.to,
|
|
3590
|
+
builder.add(table2.from, table2.to, Decoration7.mark({
|
|
3386
3591
|
class: "cm-table"
|
|
3387
3592
|
}));
|
|
3388
3593
|
});
|
|
3389
3594
|
return builder.finish();
|
|
3390
3595
|
};
|
|
3391
|
-
var TableWidget = class extends
|
|
3596
|
+
var TableWidget = class extends WidgetType5 {
|
|
3392
3597
|
constructor(_table) {
|
|
3393
3598
|
super();
|
|
3394
3599
|
this._table = _table;
|
|
@@ -3455,10 +3660,10 @@ var mention = ({ onSearch }) => {
|
|
|
3455
3660
|
};
|
|
3456
3661
|
|
|
3457
3662
|
// packages/ui/react-ui-editor/src/extensions/modes.ts
|
|
3458
|
-
import { Facet as
|
|
3459
|
-
import { keymap as
|
|
3663
|
+
import { Facet as Facet6 } from "@codemirror/state";
|
|
3664
|
+
import { keymap as keymap7 } from "@codemirror/view";
|
|
3460
3665
|
import { vim } from "@replit/codemirror-vim";
|
|
3461
|
-
var editorMode =
|
|
3666
|
+
var editorMode = Facet6.define({
|
|
3462
3667
|
combine: (modes) => modes[0] ?? {}
|
|
3463
3668
|
});
|
|
3464
3669
|
var EditorModes = {
|
|
@@ -3469,7 +3674,7 @@ var EditorModes = {
|
|
|
3469
3674
|
type: "vim",
|
|
3470
3675
|
noTabster: true
|
|
3471
3676
|
}),
|
|
3472
|
-
|
|
3677
|
+
keymap7.of([
|
|
3473
3678
|
{
|
|
3474
3679
|
key: "Alt-Escape",
|
|
3475
3680
|
run: (view) => {
|
|
@@ -3489,7 +3694,7 @@ var outliner = (options = {}) => {
|
|
|
3489
3694
|
};
|
|
3490
3695
|
|
|
3491
3696
|
// packages/ui/react-ui-editor/src/extensions/typewriter.ts
|
|
3492
|
-
import { keymap as
|
|
3697
|
+
import { keymap as keymap8 } from "@codemirror/view";
|
|
3493
3698
|
var defaultItems = [
|
|
3494
3699
|
"hello world!",
|
|
3495
3700
|
"this is a test.",
|
|
@@ -3499,7 +3704,7 @@ var typewriter = ({ delay = 75, items = defaultItems } = {}) => {
|
|
|
3499
3704
|
let t;
|
|
3500
3705
|
let idx = 0;
|
|
3501
3706
|
return [
|
|
3502
|
-
|
|
3707
|
+
keymap8.of([
|
|
3503
3708
|
{
|
|
3504
3709
|
// Reset.
|
|
3505
3710
|
key: "alt-meta-'",
|
|
@@ -3545,186 +3750,370 @@ var typewriter = ({ delay = 75, items = defaultItems } = {}) => {
|
|
|
3545
3750
|
];
|
|
3546
3751
|
};
|
|
3547
3752
|
|
|
3548
|
-
// packages/ui/react-ui-editor/src/
|
|
3549
|
-
import
|
|
3550
|
-
|
|
3551
|
-
|
|
3552
|
-
|
|
3553
|
-
|
|
3554
|
-
|
|
3555
|
-
|
|
3556
|
-
|
|
3557
|
-
|
|
3558
|
-
|
|
3559
|
-
|
|
3560
|
-
|
|
3561
|
-
|
|
3562
|
-
|
|
3563
|
-
|
|
3564
|
-
|
|
3565
|
-
|
|
3566
|
-
|
|
3567
|
-
|
|
3568
|
-
|
|
3569
|
-
|
|
3570
|
-
|
|
3571
|
-
|
|
3572
|
-
|
|
3573
|
-
|
|
3574
|
-
|
|
3575
|
-
|
|
3576
|
-
|
|
3577
|
-
|
|
3578
|
-
|
|
3579
|
-
|
|
3580
|
-
|
|
3581
|
-
|
|
3582
|
-
|
|
3583
|
-
|
|
3584
|
-
|
|
3585
|
-
|
|
3586
|
-
|
|
3587
|
-
|
|
3588
|
-
|
|
3589
|
-
|
|
3590
|
-
|
|
3591
|
-
|
|
3592
|
-
|
|
3593
|
-
|
|
3594
|
-
|
|
3595
|
-
|
|
3596
|
-
|
|
3597
|
-
|
|
3598
|
-
|
|
3599
|
-
}
|
|
3600
|
-
|
|
3601
|
-
|
|
3602
|
-
|
|
3603
|
-
|
|
3604
|
-
|
|
3605
|
-
|
|
3606
|
-
|
|
3607
|
-
|
|
3608
|
-
|
|
3609
|
-
|
|
3610
|
-
|
|
3611
|
-
|
|
3612
|
-
|
|
3613
|
-
|
|
3614
|
-
|
|
3615
|
-
|
|
3616
|
-
|
|
3617
|
-
|
|
3618
|
-
|
|
3619
|
-
|
|
3620
|
-
|
|
3621
|
-
|
|
3622
|
-
|
|
3623
|
-
|
|
3624
|
-
|
|
3625
|
-
|
|
3626
|
-
|
|
3627
|
-
|
|
3628
|
-
|
|
3629
|
-
|
|
3630
|
-
|
|
3631
|
-
|
|
3632
|
-
|
|
3633
|
-
|
|
3634
|
-
|
|
3635
|
-
|
|
3636
|
-
|
|
3637
|
-
|
|
3638
|
-
|
|
3639
|
-
|
|
3640
|
-
|
|
3641
|
-
|
|
3642
|
-
|
|
3643
|
-
|
|
3644
|
-
|
|
3645
|
-
|
|
3646
|
-
|
|
3647
|
-
|
|
3648
|
-
|
|
3649
|
-
|
|
3650
|
-
|
|
3651
|
-
|
|
3652
|
-
|
|
3653
|
-
|
|
3654
|
-
|
|
3655
|
-
|
|
3656
|
-
|
|
3657
|
-
|
|
3658
|
-
|
|
3659
|
-
|
|
3660
|
-
|
|
3661
|
-
|
|
3662
|
-
|
|
3663
|
-
|
|
3664
|
-
|
|
3665
|
-
|
|
3666
|
-
|
|
3667
|
-
|
|
3668
|
-
|
|
3669
|
-
|
|
3670
|
-
|
|
3671
|
-
|
|
3672
|
-
|
|
3673
|
-
|
|
3674
|
-
|
|
3675
|
-
|
|
3676
|
-
|
|
3677
|
-
|
|
3678
|
-
|
|
3679
|
-
|
|
3680
|
-
|
|
3681
|
-
|
|
3682
|
-
|
|
3683
|
-
|
|
3684
|
-
|
|
3685
|
-
|
|
3686
|
-
|
|
3687
|
-
|
|
3688
|
-
|
|
3689
|
-
|
|
3753
|
+
// packages/ui/react-ui-editor/src/hooks/awareness-provider.ts
|
|
3754
|
+
import { DeferredTask, Event as Event2, sleep } from "@dxos/async";
|
|
3755
|
+
import { Context as Context2 } from "@dxos/context";
|
|
3756
|
+
import { invariant as invariant2 } from "@dxos/invariant";
|
|
3757
|
+
import { log as log3 } from "@dxos/log";
|
|
3758
|
+
var __dxlog_file4 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/hooks/awareness-provider.ts";
|
|
3759
|
+
var DEBOUNCE_INTERVAL = 100;
|
|
3760
|
+
var SpaceAwarenessProvider = class {
|
|
3761
|
+
constructor(params) {
|
|
3762
|
+
this._remoteStates = /* @__PURE__ */ new Map();
|
|
3763
|
+
this.remoteStateChange = new Event2();
|
|
3764
|
+
this._space = params.space;
|
|
3765
|
+
this._channel = params.channel;
|
|
3766
|
+
this._peerId = params.peerId;
|
|
3767
|
+
this._info = params.info;
|
|
3768
|
+
}
|
|
3769
|
+
open() {
|
|
3770
|
+
this._ctx = new Context2();
|
|
3771
|
+
this._postTask = new DeferredTask(this._ctx, async () => {
|
|
3772
|
+
if (this._localState) {
|
|
3773
|
+
await this._space.postMessage(this._channel, {
|
|
3774
|
+
kind: "post",
|
|
3775
|
+
state: this._localState
|
|
3776
|
+
});
|
|
3777
|
+
await sleep(DEBOUNCE_INTERVAL);
|
|
3778
|
+
}
|
|
3779
|
+
});
|
|
3780
|
+
this._ctx.onDispose(this._space.listen(this._channel, (message) => {
|
|
3781
|
+
switch (message.payload.kind) {
|
|
3782
|
+
case "query": {
|
|
3783
|
+
this._handleQueryMessage();
|
|
3784
|
+
break;
|
|
3785
|
+
}
|
|
3786
|
+
case "post": {
|
|
3787
|
+
this._handlePostMessage(message.payload);
|
|
3788
|
+
break;
|
|
3789
|
+
}
|
|
3790
|
+
}
|
|
3791
|
+
}));
|
|
3792
|
+
void this._space.postMessage(this._channel, {
|
|
3793
|
+
kind: "query"
|
|
3794
|
+
}).catch((err) => {
|
|
3795
|
+
log3.debug("failed to query awareness", {
|
|
3796
|
+
err
|
|
3797
|
+
}, {
|
|
3798
|
+
F: __dxlog_file4,
|
|
3799
|
+
L: 89,
|
|
3800
|
+
S: this,
|
|
3801
|
+
C: (f, a) => f(...a)
|
|
3802
|
+
});
|
|
3803
|
+
});
|
|
3804
|
+
}
|
|
3805
|
+
close() {
|
|
3806
|
+
void this._ctx?.dispose();
|
|
3807
|
+
this._ctx = void 0;
|
|
3808
|
+
this._postTask = void 0;
|
|
3809
|
+
}
|
|
3810
|
+
getRemoteStates() {
|
|
3811
|
+
return Array.from(this._remoteStates.values());
|
|
3812
|
+
}
|
|
3813
|
+
update(position) {
|
|
3814
|
+
invariant2(this._postTask, void 0, {
|
|
3815
|
+
F: __dxlog_file4,
|
|
3816
|
+
L: 104,
|
|
3817
|
+
S: this,
|
|
3818
|
+
A: [
|
|
3819
|
+
"this._postTask",
|
|
3820
|
+
""
|
|
3821
|
+
]
|
|
3822
|
+
});
|
|
3823
|
+
this._localState = {
|
|
3824
|
+
peerId: this._peerId,
|
|
3825
|
+
position,
|
|
3826
|
+
info: this._info
|
|
3827
|
+
};
|
|
3828
|
+
this._postTask.schedule();
|
|
3829
|
+
}
|
|
3830
|
+
_handleQueryMessage() {
|
|
3831
|
+
invariant2(this._postTask, void 0, {
|
|
3832
|
+
F: __dxlog_file4,
|
|
3833
|
+
L: 115,
|
|
3834
|
+
S: this,
|
|
3835
|
+
A: [
|
|
3836
|
+
"this._postTask",
|
|
3837
|
+
""
|
|
3838
|
+
]
|
|
3839
|
+
});
|
|
3840
|
+
this._postTask.schedule();
|
|
3841
|
+
}
|
|
3842
|
+
_handlePostMessage(message) {
|
|
3843
|
+
invariant2(message.kind === "post", void 0, {
|
|
3844
|
+
F: __dxlog_file4,
|
|
3845
|
+
L: 120,
|
|
3846
|
+
S: this,
|
|
3847
|
+
A: [
|
|
3848
|
+
"message.kind === 'post'",
|
|
3849
|
+
""
|
|
3850
|
+
]
|
|
3851
|
+
});
|
|
3852
|
+
this._remoteStates.set(message.state.peerId, message.state);
|
|
3853
|
+
this.remoteStateChange.emit();
|
|
3854
|
+
}
|
|
3855
|
+
};
|
|
3856
|
+
|
|
3857
|
+
// packages/ui/react-ui-editor/src/hooks/useActionHandler.ts
|
|
3858
|
+
var useActionHandler = (view) => {
|
|
3859
|
+
return (action) => {
|
|
3860
|
+
if (!view) {
|
|
3861
|
+
return;
|
|
3862
|
+
}
|
|
3863
|
+
let inlineType, listType;
|
|
3864
|
+
switch (action.type) {
|
|
3865
|
+
case "heading":
|
|
3866
|
+
setHeading(parseInt(action.data))(view);
|
|
3867
|
+
break;
|
|
3868
|
+
case "strong":
|
|
3869
|
+
case "emphasis":
|
|
3870
|
+
case "strikethrough":
|
|
3871
|
+
case "code":
|
|
3872
|
+
inlineType = action.type === "strong" ? Inline.Strong : action.type === "emphasis" ? Inline.Emphasis : action.type === "strikethrough" ? Inline.Strikethrough : Inline.Code;
|
|
3873
|
+
(typeof action.data === "boolean" ? setStyle(inlineType, action.data) : toggleStyle(inlineType))(view);
|
|
3874
|
+
break;
|
|
3875
|
+
case "list-ordered":
|
|
3876
|
+
case "list-bullet":
|
|
3877
|
+
case "list-task":
|
|
3878
|
+
listType = action.type === "list-ordered" ? List.Ordered : action.type === "list-bullet" ? List.Bullet : List.Task;
|
|
3879
|
+
(action.data === false ? removeList(listType) : action.data === true ? addList(listType) : toggleList(listType))(view);
|
|
3880
|
+
break;
|
|
3881
|
+
case "blockquote":
|
|
3882
|
+
(action.data === false ? removeBlockquote : action.data === true ? addBlockquote : toggleBlockquote)(view);
|
|
3883
|
+
break;
|
|
3884
|
+
case "codeblock":
|
|
3885
|
+
(action.data === false ? removeCodeblock : addCodeblock)(view);
|
|
3886
|
+
break;
|
|
3887
|
+
case "table":
|
|
3888
|
+
insertTable(view);
|
|
3889
|
+
break;
|
|
3890
|
+
case "link":
|
|
3891
|
+
(action.data === false ? removeLink : addLink)(view);
|
|
3892
|
+
break;
|
|
3893
|
+
case "comment":
|
|
3894
|
+
createComment(view);
|
|
3895
|
+
break;
|
|
3896
|
+
}
|
|
3897
|
+
setTimeout(() => {
|
|
3898
|
+
if (!view.hasFocus) {
|
|
3899
|
+
view.focus();
|
|
3900
|
+
}
|
|
3901
|
+
});
|
|
3902
|
+
};
|
|
3903
|
+
};
|
|
3904
|
+
|
|
3905
|
+
// packages/ui/react-ui-editor/src/hooks/useEditorView.ts
|
|
3906
|
+
import { useRef, useState as useState2 } from "react";
|
|
3907
|
+
var useEditorView = (id) => {
|
|
3908
|
+
const editorRef = useRef(null);
|
|
3909
|
+
const [prev, setPrev] = useState2([
|
|
3910
|
+
null,
|
|
3911
|
+
""
|
|
3912
|
+
]);
|
|
3913
|
+
if (prev[0] !== editorRef.current) {
|
|
3914
|
+
setPrev([
|
|
3915
|
+
editorRef.current,
|
|
3916
|
+
id
|
|
3917
|
+
]);
|
|
3918
|
+
}
|
|
3919
|
+
return [
|
|
3920
|
+
editorRef,
|
|
3921
|
+
prev[1] !== id
|
|
3922
|
+
];
|
|
3923
|
+
};
|
|
3924
|
+
|
|
3925
|
+
// packages/ui/react-ui-editor/src/hooks/useTextEditor.ts
|
|
3926
|
+
import { closeBrackets as closeBrackets2 } from "@codemirror/autocomplete";
|
|
3927
|
+
import { history as history2 } from "@codemirror/commands";
|
|
3928
|
+
import { bracketMatching as bracketMatching2 } from "@codemirror/language";
|
|
3929
|
+
import { EditorSelection as EditorSelection2, EditorState as EditorState2 } from "@codemirror/state";
|
|
3930
|
+
import { crosshairCursor, drawSelection as drawSelection2, dropCursor as dropCursor2, EditorView as EditorView16, highlightActiveLine, lineNumbers, placeholder as placeholder2, scrollPastEnd } from "@codemirror/view";
|
|
3931
|
+
import defaultsDeep2 from "lodash.defaultsdeep";
|
|
3932
|
+
import { useEffect as useEffect2, useRef as useRef2, useState as useState3 } from "react";
|
|
3933
|
+
import { log as log4 } from "@dxos/log";
|
|
3934
|
+
import { isNotFalsy as isNotFalsy3 } from "@dxos/util";
|
|
3935
|
+
|
|
3936
|
+
// packages/ui/react-ui-editor/src/themes/default.ts
|
|
3937
|
+
import get4 from "lodash.get";
|
|
3938
|
+
var defaultTheme = {
|
|
3690
3939
|
//
|
|
3691
|
-
//
|
|
3940
|
+
// Main layout:
|
|
3941
|
+
// https://codemirror.net/examples/styling
|
|
3692
3942
|
//
|
|
3693
|
-
"
|
|
3694
|
-
|
|
3695
|
-
|
|
3943
|
+
// <div class="cm-editor [cm-focused] [generated classes]">
|
|
3944
|
+
// <div class="cm-scroller">
|
|
3945
|
+
// <div class="cm-gutters">
|
|
3946
|
+
// <div class="cm-gutter [...]">
|
|
3947
|
+
// <div class="cm-gutterElement">...</div>
|
|
3948
|
+
// </div>
|
|
3949
|
+
// </div>
|
|
3950
|
+
// <div class="cm-content" role="textbox" contenteditable="true">
|
|
3951
|
+
// <div class="cm-line"></div>
|
|
3952
|
+
// </div>
|
|
3953
|
+
// <div class="cm-selectionLayer">
|
|
3954
|
+
// <div class="cm-selectionBackground"></div>
|
|
3955
|
+
// </div>
|
|
3956
|
+
// <div class="cm-cursorLayer">
|
|
3957
|
+
// <div class="cm-cursor"></div>
|
|
3958
|
+
// </div>
|
|
3959
|
+
// </div>
|
|
3960
|
+
// </div>
|
|
3961
|
+
//
|
|
3962
|
+
"&": {},
|
|
3963
|
+
"&.cm-focused": {
|
|
3964
|
+
outline: "none"
|
|
3696
3965
|
},
|
|
3697
|
-
|
|
3698
|
-
|
|
3699
|
-
|
|
3700
|
-
|
|
3701
|
-
|
|
3702
|
-
|
|
3966
|
+
// NOTE: See https://codemirror.net/docs/guide (DOM Structure).
|
|
3967
|
+
".cm-scroller": {
|
|
3968
|
+
// TODO(burdon): Reconcile with docs: https://codemirror.net/docs/guide
|
|
3969
|
+
// Inside of that is the scroller element. If the editor has its own scrollbar, this one should be styled with overflow: auto. But it doesn't have to—the editor also supports growing to accomodate its content, or growing up to a certain max-height and then scrolling.
|
|
3970
|
+
overflowY: "auto",
|
|
3971
|
+
fontFamily: get4(tokens, "fontFamily.mono", []).join(","),
|
|
3972
|
+
lineHeight: 1.5
|
|
3703
3973
|
},
|
|
3704
|
-
".cm-
|
|
3705
|
-
|
|
3974
|
+
".cm-content": {
|
|
3975
|
+
// TODO(burdon): Is it possible to remove the padding value from CM's default theme?
|
|
3976
|
+
// padding: 'unset',
|
|
3977
|
+
// NOTE: Base font size (otherwise defined by HTML tag, which might be different for storybook).
|
|
3978
|
+
fontSize: "16px"
|
|
3979
|
+
},
|
|
3980
|
+
"&light .cm-content": {
|
|
3981
|
+
color: get4(tokens, "extend.semanticColors.base.fg.light", "black"),
|
|
3982
|
+
caretColor: "black"
|
|
3983
|
+
},
|
|
3984
|
+
"&dark .cm-content": {
|
|
3985
|
+
color: get4(tokens, "extend.semanticColors.base.fg.dark", "white"),
|
|
3986
|
+
caretColor: "white"
|
|
3706
3987
|
},
|
|
3707
3988
|
//
|
|
3708
|
-
//
|
|
3989
|
+
// Cursor
|
|
3709
3990
|
//
|
|
3710
|
-
".cm-
|
|
3711
|
-
|
|
3712
|
-
height: "0"
|
|
3991
|
+
"&light .cm-cursor, &light .cm-dropCursor": {
|
|
3992
|
+
borderLeft: "2px solid black"
|
|
3713
3993
|
},
|
|
3714
|
-
".cm-
|
|
3715
|
-
|
|
3716
|
-
|
|
3717
|
-
|
|
3994
|
+
"&dark .cm-cursor, &dark .cm-dropCursor": {
|
|
3995
|
+
borderLeft: "2px solid white"
|
|
3996
|
+
},
|
|
3997
|
+
"&light .cm-placeholder": {
|
|
3998
|
+
color: get4(tokens, "extend.semanticColors.description.light", "rgba(0,0,0,.2)")
|
|
3999
|
+
},
|
|
4000
|
+
"&dark .cm-placeholder": {
|
|
4001
|
+
color: get4(tokens, "extend.semanticColors.description.dark", "rgba(255,255,255,.2)")
|
|
3718
4002
|
},
|
|
3719
4003
|
//
|
|
3720
|
-
//
|
|
3721
|
-
// TODO(thure): This appears to be the best or only way to set selection caret heights,
|
|
3722
|
-
// but it's far more verbose than it needs to be.
|
|
3723
|
-
//
|
|
3724
|
-
// ...Object.keys(get(tokens, 'extend.fontSize', {})).reduce((acc: Record<string, any>, fontSize) => {
|
|
3725
|
-
// const height = get(tokens, ['extend', 'fontSize', fontSize, 1, 'lineHeight']);
|
|
4004
|
+
// line
|
|
3726
4005
|
//
|
|
3727
|
-
|
|
4006
|
+
".cm-line": {
|
|
4007
|
+
paddingInline: 0
|
|
4008
|
+
},
|
|
4009
|
+
".cm-activeLine": {
|
|
4010
|
+
background: "transparent"
|
|
4011
|
+
},
|
|
4012
|
+
//
|
|
4013
|
+
// gutter
|
|
4014
|
+
//
|
|
4015
|
+
".cm-gutterElement": {
|
|
4016
|
+
width: "48px"
|
|
4017
|
+
},
|
|
4018
|
+
//
|
|
4019
|
+
// Selection
|
|
4020
|
+
//
|
|
4021
|
+
"&light .cm-selectionBackground": {
|
|
4022
|
+
background: get4(tokens, "extend.colors.primary.100")
|
|
4023
|
+
},
|
|
4024
|
+
"&light.cm-focused > .cm-scroller > .cm-selectionLayer .cm-selectionBackground": {
|
|
4025
|
+
background: get4(tokens, "extend.colors.primary.200")
|
|
4026
|
+
},
|
|
4027
|
+
"&dark .cm-selectionBackground": {
|
|
4028
|
+
background: get4(tokens, "extend.colors.primary.700")
|
|
4029
|
+
},
|
|
4030
|
+
"&dark.cm-focused > .cm-scroller > .cm-selectionLayer .cm-selectionBackground": {
|
|
4031
|
+
background: get4(tokens, "extend.colors.primary.600")
|
|
4032
|
+
},
|
|
4033
|
+
//
|
|
4034
|
+
// Search
|
|
4035
|
+
//
|
|
4036
|
+
"&light .cm-searchMatch": {
|
|
4037
|
+
backgroundColor: get4(tokens, "extend.colors.yellow.100")
|
|
4038
|
+
},
|
|
4039
|
+
"&dark .cm-searchMatch": {
|
|
4040
|
+
backgroundColor: get4(tokens, "extend.colors.yellow.700")
|
|
4041
|
+
},
|
|
4042
|
+
//
|
|
4043
|
+
// link
|
|
4044
|
+
//
|
|
4045
|
+
".cm-link": {
|
|
4046
|
+
color: get4(tokens, "extend.colors.primary.500"),
|
|
4047
|
+
textDecorationLine: "underline",
|
|
4048
|
+
textDecorationThickness: "1px",
|
|
4049
|
+
textUnderlineOffset: "2px",
|
|
4050
|
+
borderRadius: ".125rem",
|
|
4051
|
+
fontFamily: get4(tokens, "fontFamily.body", []).join(",")
|
|
4052
|
+
},
|
|
4053
|
+
//
|
|
4054
|
+
// tooltip
|
|
4055
|
+
//
|
|
4056
|
+
".cm-tooltip": {
|
|
4057
|
+
border: "none",
|
|
4058
|
+
background: "unset"
|
|
4059
|
+
},
|
|
4060
|
+
".cm-tooltip-below": {},
|
|
4061
|
+
//
|
|
4062
|
+
// autocomplete
|
|
4063
|
+
//
|
|
4064
|
+
".cm-tooltip-autocomplete": {
|
|
4065
|
+
marginTop: "4px",
|
|
4066
|
+
marginLeft: "-3px"
|
|
4067
|
+
},
|
|
4068
|
+
".cm-tooltip-autocomplete ul li": {},
|
|
4069
|
+
".cm-tooltip-autocomplete ul li[aria-selected]": {},
|
|
4070
|
+
".cm-completionIcon": {
|
|
4071
|
+
display: "none"
|
|
4072
|
+
},
|
|
4073
|
+
".cm-completionLabel": {
|
|
4074
|
+
fontFamily: get4(tokens, "fontFamily.body", []).join(",")
|
|
4075
|
+
},
|
|
4076
|
+
".cm-completionMatchedText": {
|
|
4077
|
+
textDecoration: "none"
|
|
4078
|
+
},
|
|
4079
|
+
//
|
|
4080
|
+
// table
|
|
4081
|
+
//
|
|
4082
|
+
".cm-table *": {
|
|
4083
|
+
fontFamily: `${get4(tokens, "fontFamily.mono", []).join(",")} !important`,
|
|
4084
|
+
textDecoration: "none !important"
|
|
4085
|
+
},
|
|
4086
|
+
".cm-table-head": {
|
|
4087
|
+
padding: "2px 16px 2px 0px",
|
|
4088
|
+
borderBottom: `1px solid ${get4(tokens, "extend.colors.neutral.500")}`,
|
|
4089
|
+
fontWeight: 100,
|
|
4090
|
+
textAlign: "left",
|
|
4091
|
+
color: get4(tokens, "extend.colors.neutral.500")
|
|
4092
|
+
},
|
|
4093
|
+
".cm-table-cell": {
|
|
4094
|
+
padding: "2px 16px 2px 0px"
|
|
4095
|
+
},
|
|
4096
|
+
//
|
|
4097
|
+
// image
|
|
4098
|
+
//
|
|
4099
|
+
".cm-image": {
|
|
4100
|
+
display: "block",
|
|
4101
|
+
height: "0"
|
|
4102
|
+
},
|
|
4103
|
+
".cm-image.cm-loaded-image": {
|
|
4104
|
+
height: "auto",
|
|
4105
|
+
borderTop: "0.5rem solid transparent",
|
|
4106
|
+
borderBottom: "0.5rem solid transparent"
|
|
4107
|
+
},
|
|
4108
|
+
//
|
|
4109
|
+
// font size
|
|
4110
|
+
// TODO(thure): This appears to be the best or only way to set selection caret heights,
|
|
4111
|
+
// but it's far more verbose than it needs to be.
|
|
4112
|
+
//
|
|
4113
|
+
// ...Object.keys(get(tokens, 'extend.fontSize', {})).reduce((acc: Record<string, any>, fontSize) => {
|
|
4114
|
+
// const height = get(tokens, ['extend', 'fontSize', fontSize, 1, 'lineHeight']);
|
|
4115
|
+
//
|
|
4116
|
+
// acc[`& .text-${fontSize} + .cm-ySelectionCaret`] = { height };
|
|
3728
4117
|
// acc[`& .text-${fontSize} + .cm-ySelection + .cm-ySelectionCaret`] = { height };
|
|
3729
4118
|
// acc[`& .text-${fontSize} + .cm-widgetBuffer + .cm-ySelectionCaret`] = { height };
|
|
3730
4119
|
// return acc;
|
|
@@ -3795,139 +4184,360 @@ var codeTheme = {
|
|
|
3795
4184
|
}
|
|
3796
4185
|
};
|
|
3797
4186
|
|
|
3798
|
-
// packages/ui/react-ui-editor/src/
|
|
3799
|
-
var
|
|
3800
|
-
var
|
|
3801
|
-
const
|
|
3802
|
-
|
|
3803
|
-
|
|
3804
|
-
const { themeMode } = useThemeContext();
|
|
3805
|
-
const rootRef = useRef(null);
|
|
3806
|
-
const [view, setView] = useState2(null);
|
|
3807
|
-
useImperativeHandle(forwardedRef, () => view, [
|
|
3808
|
-
view
|
|
3809
|
-
]);
|
|
3810
|
-
useEffect2(() => {
|
|
3811
|
-
if (autoFocus) {
|
|
3812
|
-
view?.focus();
|
|
3813
|
-
}
|
|
3814
|
-
}, [
|
|
3815
|
-
view,
|
|
3816
|
-
autoFocus
|
|
3817
|
-
]);
|
|
4187
|
+
// packages/ui/react-ui-editor/src/hooks/useTextEditor.ts
|
|
4188
|
+
var __dxlog_file5 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/hooks/useTextEditor.ts";
|
|
4189
|
+
var useTextEditor = ({ autoFocus, scrollTo, debug, doc, selection, extensions } = {}, deps = []) => {
|
|
4190
|
+
const onUpdate = useRef2();
|
|
4191
|
+
const [view, setView] = useState3();
|
|
4192
|
+
const parentRef = useRef2(null);
|
|
3818
4193
|
useEffect2(() => {
|
|
3819
|
-
|
|
3820
|
-
|
|
3821
|
-
|
|
3822
|
-
|
|
3823
|
-
|
|
3824
|
-
|
|
3825
|
-
|
|
3826
|
-
|
|
3827
|
-
|
|
3828
|
-
|
|
3829
|
-
|
|
3830
|
-
|
|
3831
|
-
|
|
3832
|
-
|
|
3833
|
-
})
|
|
3834
|
-
|
|
3835
|
-
|
|
3836
|
-
|
|
3837
|
-
|
|
3838
|
-
|
|
3839
|
-
|
|
3840
|
-
|
|
3841
|
-
|
|
3842
|
-
|
|
3843
|
-
|
|
3844
|
-
|
|
3845
|
-
|
|
3846
|
-
|
|
3847
|
-
|
|
3848
|
-
|
|
3849
|
-
|
|
3850
|
-
|
|
3851
|
-
if (transaction.isUserEvent("focus.container")) {
|
|
3852
|
-
rootRef.current?.focus();
|
|
3853
|
-
}
|
|
3854
|
-
});
|
|
3855
|
-
}),
|
|
3856
|
-
// State.
|
|
3857
|
-
EditorView14.editable.of(!readonly),
|
|
3858
|
-
EditorState2.readOnly.of(!!readonly),
|
|
3859
|
-
// Storage and replication.
|
|
3860
|
-
// NOTE: This must come before user extensions.
|
|
3861
|
-
model.extension,
|
|
3862
|
-
// Custom.
|
|
3863
|
-
...extensions
|
|
3864
|
-
].filter(isNotFalsy4)
|
|
3865
|
-
});
|
|
3866
|
-
const view2 = new EditorView14({
|
|
3867
|
-
state,
|
|
3868
|
-
parent: rootRef.current,
|
|
3869
|
-
scrollTo,
|
|
3870
|
-
// NOTE: Uncomment to debug/monitor all transactions.
|
|
3871
|
-
// https://codemirror.net/docs/ref/#view.EditorView.dispatch
|
|
3872
|
-
dispatchTransactions: (trs, view3) => {
|
|
3873
|
-
if (debug) {
|
|
3874
|
-
logChanges(trs);
|
|
3875
|
-
}
|
|
3876
|
-
view3.update(trs);
|
|
3877
|
-
}
|
|
3878
|
-
});
|
|
3879
|
-
setView(view2);
|
|
3880
|
-
if (moveToEndOfLine) {
|
|
3881
|
-
const { to } = view2.state.doc.lineAt(0);
|
|
3882
|
-
view2?.dispatch({
|
|
3883
|
-
selection: {
|
|
3884
|
-
anchor: to
|
|
4194
|
+
let view2;
|
|
4195
|
+
if (parentRef.current) {
|
|
4196
|
+
const state = EditorState2.create({
|
|
4197
|
+
doc,
|
|
4198
|
+
selection,
|
|
4199
|
+
extensions: [
|
|
4200
|
+
// TODO(burdon): Doesn't catch errors in keymap functions.
|
|
4201
|
+
EditorView16.exceptionSink.of((err) => {
|
|
4202
|
+
log4.catch(err, void 0, {
|
|
4203
|
+
F: __dxlog_file5,
|
|
4204
|
+
L: 70,
|
|
4205
|
+
S: void 0,
|
|
4206
|
+
C: (f, a) => f(...a)
|
|
4207
|
+
});
|
|
4208
|
+
}),
|
|
4209
|
+
extensions,
|
|
4210
|
+
EditorView16.updateListener.of(() => {
|
|
4211
|
+
onUpdate.current?.();
|
|
4212
|
+
})
|
|
4213
|
+
].filter(isNotFalsy3)
|
|
4214
|
+
});
|
|
4215
|
+
view2 = new EditorView16({
|
|
4216
|
+
parent: parentRef.current,
|
|
4217
|
+
scrollTo,
|
|
4218
|
+
state,
|
|
4219
|
+
// NOTE: Uncomment to debug/monitor all transactions.
|
|
4220
|
+
// https://codemirror.net/docs/ref/#view.EditorView.dispatch
|
|
4221
|
+
dispatchTransactions: (trs, view3) => {
|
|
4222
|
+
if (debug) {
|
|
4223
|
+
logChanges(trs);
|
|
4224
|
+
}
|
|
4225
|
+
view3.update(trs);
|
|
3885
4226
|
}
|
|
3886
4227
|
});
|
|
3887
|
-
|
|
3888
|
-
if (state.facet(editorMode).noTabster) {
|
|
3889
|
-
rootRef.current.removeAttribute("data-tabster");
|
|
4228
|
+
setView(view2);
|
|
3890
4229
|
}
|
|
3891
4230
|
return () => {
|
|
3892
4231
|
view2?.destroy();
|
|
3893
|
-
setView(null);
|
|
3894
4232
|
};
|
|
3895
|
-
},
|
|
3896
|
-
|
|
3897
|
-
|
|
3898
|
-
|
|
3899
|
-
|
|
3900
|
-
|
|
3901
|
-
|
|
3902
|
-
|
|
3903
|
-
|
|
3904
|
-
|
|
3905
|
-
|
|
3906
|
-
|
|
3907
|
-
|
|
4233
|
+
}, deps);
|
|
4234
|
+
useEffect2(() => {
|
|
4235
|
+
if (view) {
|
|
4236
|
+
if (!selection && !view.state.selection.main.anchor) {
|
|
4237
|
+
selection = EditorSelection2.single(view.state.doc.line(1).to);
|
|
4238
|
+
}
|
|
4239
|
+
if (selection || scrollTo) {
|
|
4240
|
+
onUpdate.current = () => {
|
|
4241
|
+
onUpdate.current = void 0;
|
|
4242
|
+
view.dispatch({
|
|
4243
|
+
selection,
|
|
4244
|
+
effects: scrollTo && [
|
|
4245
|
+
scrollTo
|
|
4246
|
+
],
|
|
4247
|
+
scrollIntoView: !scrollTo
|
|
4248
|
+
});
|
|
4249
|
+
};
|
|
4250
|
+
}
|
|
4251
|
+
if (autoFocus) {
|
|
4252
|
+
view.focus();
|
|
3908
4253
|
}
|
|
3909
4254
|
}
|
|
3910
4255
|
}, [
|
|
3911
|
-
view
|
|
4256
|
+
view,
|
|
4257
|
+
autoFocus,
|
|
4258
|
+
selection,
|
|
4259
|
+
scrollTo
|
|
3912
4260
|
]);
|
|
3913
|
-
return
|
|
3914
|
-
|
|
3915
|
-
|
|
3916
|
-
|
|
3917
|
-
|
|
3918
|
-
|
|
3919
|
-
|
|
3920
|
-
|
|
3921
|
-
|
|
3922
|
-
|
|
3923
|
-
|
|
3924
|
-
|
|
3925
|
-
|
|
3926
|
-
|
|
3927
|
-
|
|
3928
|
-
|
|
3929
|
-
|
|
3930
|
-
|
|
4261
|
+
return {
|
|
4262
|
+
parentRef,
|
|
4263
|
+
view
|
|
4264
|
+
};
|
|
4265
|
+
};
|
|
4266
|
+
var defaults = {
|
|
4267
|
+
bracketMatching: true,
|
|
4268
|
+
closeBrackets: true,
|
|
4269
|
+
drawSelection: true,
|
|
4270
|
+
editable: true,
|
|
4271
|
+
history: true,
|
|
4272
|
+
lineWrapping: true
|
|
4273
|
+
};
|
|
4274
|
+
var createBasicExtensions = (_props) => {
|
|
4275
|
+
const props = defaultsDeep2({}, _props, defaults);
|
|
4276
|
+
return [
|
|
4277
|
+
// TODO(burdon): Doesn't catch errors in keymap functions.
|
|
4278
|
+
EditorView16.exceptionSink.of((err) => {
|
|
4279
|
+
log4.catch(err, void 0, {
|
|
4280
|
+
F: __dxlog_file5,
|
|
4281
|
+
L: 167,
|
|
4282
|
+
S: void 0,
|
|
4283
|
+
C: (f, a) => f(...a)
|
|
4284
|
+
});
|
|
4285
|
+
}),
|
|
4286
|
+
props.allowMultipleSelections && EditorState2.allowMultipleSelections.of(true),
|
|
4287
|
+
props.bracketMatching && bracketMatching2(),
|
|
4288
|
+
props.closeBrackets && closeBrackets2(),
|
|
4289
|
+
props.crosshairCursor && crosshairCursor(),
|
|
4290
|
+
props.dropCursor && dropCursor2(),
|
|
4291
|
+
props.drawSelection && drawSelection2(),
|
|
4292
|
+
props.highlightActiveLine && highlightActiveLine(),
|
|
4293
|
+
props.history && history2(),
|
|
4294
|
+
props.lineNumbers && lineNumbers(),
|
|
4295
|
+
props.lineWrapping && EditorView16.lineWrapping,
|
|
4296
|
+
props.placeholder && placeholder2(props.placeholder),
|
|
4297
|
+
props.readonly && [
|
|
4298
|
+
EditorState2.readOnly.of(true),
|
|
4299
|
+
EditorView16.editable.of(false)
|
|
4300
|
+
],
|
|
4301
|
+
props.scrollPastEnd && scrollPastEnd(),
|
|
4302
|
+
props.tabSize && EditorState2.tabSize.of(props.tabSize)
|
|
4303
|
+
].filter(isNotFalsy3);
|
|
4304
|
+
};
|
|
4305
|
+
var createThemeExtensions = ({ theme, themeMode, slots } = {}) => {
|
|
4306
|
+
return [
|
|
4307
|
+
EditorView16.baseTheme(defaultTheme),
|
|
4308
|
+
EditorView16.darkTheme.of(themeMode === "dark"),
|
|
4309
|
+
theme && EditorView16.theme(theme),
|
|
4310
|
+
slots?.editor?.className && EditorView16.editorAttributes.of({
|
|
4311
|
+
class: slots.editor.className
|
|
4312
|
+
}),
|
|
4313
|
+
slots?.content?.className && EditorView16.contentAttributes.of({
|
|
4314
|
+
class: slots.content.className
|
|
4315
|
+
})
|
|
4316
|
+
].filter(isNotFalsy3);
|
|
4317
|
+
};
|
|
4318
|
+
|
|
4319
|
+
// packages/ui/react-ui-editor/src/hooks/useTextModel.ts
|
|
4320
|
+
import get5 from "lodash.get";
|
|
4321
|
+
import { useState as useState4, useMemo as useMemo2 } from "react";
|
|
4322
|
+
import { generateName } from "@dxos/display-name";
|
|
4323
|
+
import { getRawDoc } from "@dxos/echo-schema";
|
|
4324
|
+
import { invariant as invariant3 } from "@dxos/invariant";
|
|
4325
|
+
import { isAutomergeObject } from "@dxos/react-client/echo";
|
|
4326
|
+
import { hueTokens } from "@dxos/react-ui-theme";
|
|
4327
|
+
import { hexToHue } from "@dxos/util";
|
|
4328
|
+
var __dxlog_file6 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/hooks/useTextModel.ts";
|
|
4329
|
+
var useTextExtensions = ({ id, text, space, identity }) => {
|
|
4330
|
+
const extensions = [
|
|
4331
|
+
automerge(text)
|
|
4332
|
+
];
|
|
4333
|
+
const peerId = identity?.identityKey.toHex();
|
|
4334
|
+
const { cursorLightValue, cursorDarkValue } = hueTokens[hexToHue(peerId ?? "0")];
|
|
4335
|
+
if (space && identity) {
|
|
4336
|
+
const awarenessProvider2 = new SpaceAwarenessProvider({
|
|
4337
|
+
space,
|
|
4338
|
+
channel: `awareness.${id}`,
|
|
4339
|
+
peerId: identity.identityKey.toHex(),
|
|
4340
|
+
info: {
|
|
4341
|
+
displayName: identity.profile?.displayName ?? generateName(identity.identityKey.toHex()),
|
|
4342
|
+
color: cursorDarkValue,
|
|
4343
|
+
lightColor: cursorLightValue
|
|
4344
|
+
}
|
|
4345
|
+
});
|
|
4346
|
+
extensions.push(awareness(awarenessProvider2));
|
|
4347
|
+
}
|
|
4348
|
+
return extensions;
|
|
4349
|
+
};
|
|
4350
|
+
var useTextModel = (props) => useMemo2(() => createModel(props), Object.values(props));
|
|
4351
|
+
var useInMemoryTextModel = ({ id, defaultContent }) => {
|
|
4352
|
+
const [content, setContent] = useState4(defaultContent ?? "");
|
|
4353
|
+
return {
|
|
4354
|
+
id,
|
|
4355
|
+
content,
|
|
4356
|
+
text: () => content,
|
|
4357
|
+
setContent
|
|
4358
|
+
};
|
|
4359
|
+
};
|
|
4360
|
+
var createModel = ({ space, identity, text }) => {
|
|
4361
|
+
if (!text) {
|
|
4362
|
+
return void 0;
|
|
4363
|
+
}
|
|
4364
|
+
invariant3(isAutomergeObject(text), void 0, {
|
|
4365
|
+
F: __dxlog_file6,
|
|
4366
|
+
L: 88,
|
|
4367
|
+
S: void 0,
|
|
4368
|
+
A: [
|
|
4369
|
+
"isAutomergeObject(text)",
|
|
4370
|
+
""
|
|
4371
|
+
]
|
|
4372
|
+
});
|
|
4373
|
+
const obj = text;
|
|
4374
|
+
const doc = getRawDoc(obj, [
|
|
4375
|
+
obj.field
|
|
4376
|
+
]);
|
|
4377
|
+
const peerId = identity?.identityKey.toHex();
|
|
4378
|
+
const { cursorLightValue, cursorDarkValue } = hueTokens[hexToHue(peerId ?? "0")];
|
|
4379
|
+
const awarenessProvider2 = space && new SpaceAwarenessProvider({
|
|
4380
|
+
space,
|
|
4381
|
+
channel: `automerge.awareness.${obj.id}`,
|
|
4382
|
+
info: {
|
|
4383
|
+
displayName: identity ? identity.profile?.displayName ?? generateName(identity.identityKey.toHex()) : void 0,
|
|
4384
|
+
color: cursorLightValue,
|
|
4385
|
+
lightColor: cursorDarkValue
|
|
4386
|
+
},
|
|
4387
|
+
peerId: identity?.identityKey.toHex() ?? "Anonymous"
|
|
4388
|
+
});
|
|
4389
|
+
const extensions = [
|
|
4390
|
+
automerge({
|
|
4391
|
+
handle: doc.handle,
|
|
4392
|
+
path: doc.path
|
|
4393
|
+
})
|
|
4394
|
+
];
|
|
4395
|
+
if (awarenessProvider2) {
|
|
4396
|
+
extensions.push(awareness(awarenessProvider2));
|
|
4397
|
+
}
|
|
4398
|
+
return {
|
|
4399
|
+
id: obj.id,
|
|
4400
|
+
content: doc,
|
|
4401
|
+
text: () => get5(doc.handle.docSync(), doc.path),
|
|
4402
|
+
extension: extensions
|
|
4403
|
+
};
|
|
4404
|
+
};
|
|
4405
|
+
|
|
4406
|
+
// packages/ui/react-ui-editor/src/components/TextEditor/TextEditor.tsx
|
|
4407
|
+
var __dxlog_file7 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/components/TextEditor/TextEditor.tsx";
|
|
4408
|
+
var BaseTextEditor = /* @__PURE__ */ forwardRef(({ model, readonly, autoFocus, scrollTo = EditorView17.scrollIntoView(0), moveToEndOfLine, selection, theme, slots = defaultSlots, extensions = [], scrollPastEnd: _scrollPastEnd, debug }, forwardedRef) => {
|
|
4409
|
+
const tabsterDOMAttribute = useFocusableGroup({
|
|
4410
|
+
tabBehavior: "limited"
|
|
4411
|
+
});
|
|
4412
|
+
const { themeMode } = useThemeContext();
|
|
4413
|
+
const rootRef = useRef3(null);
|
|
4414
|
+
const [view, setView] = useState5(null);
|
|
4415
|
+
useImperativeHandle(forwardedRef, () => view, [
|
|
4416
|
+
view
|
|
4417
|
+
]);
|
|
4418
|
+
useEffect3(() => {
|
|
4419
|
+
if (autoFocus) {
|
|
4420
|
+
view?.focus();
|
|
4421
|
+
}
|
|
4422
|
+
}, [
|
|
4423
|
+
view,
|
|
4424
|
+
autoFocus
|
|
4425
|
+
]);
|
|
4426
|
+
useEffect3(() => {
|
|
4427
|
+
if (!model || !rootRef.current) {
|
|
4428
|
+
return;
|
|
4429
|
+
}
|
|
4430
|
+
const state = EditorState3.create({
|
|
4431
|
+
doc: typeof model.content === "string" ? model.content : DocAccessor.getValue(model.content),
|
|
4432
|
+
selection,
|
|
4433
|
+
extensions: [
|
|
4434
|
+
// TODO(burdon): Doesn't catch errors in keymap functions.
|
|
4435
|
+
EditorView17.exceptionSink.of((err) => {
|
|
4436
|
+
log5.catch(err, void 0, {
|
|
4437
|
+
F: __dxlog_file7,
|
|
4438
|
+
L: 123,
|
|
4439
|
+
S: void 0,
|
|
4440
|
+
C: (f, a) => f(...a)
|
|
4441
|
+
});
|
|
4442
|
+
}),
|
|
4443
|
+
// Theme.
|
|
4444
|
+
// TODO(burdon): Make base theme configurable.
|
|
4445
|
+
EditorView17.baseTheme(defaultTheme),
|
|
4446
|
+
theme && EditorView17.theme(theme),
|
|
4447
|
+
EditorView17.darkTheme.of(themeMode === "dark"),
|
|
4448
|
+
slots.editor?.className && EditorView17.editorAttributes.of({
|
|
4449
|
+
class: slots.editor.className
|
|
4450
|
+
}),
|
|
4451
|
+
slots.content?.className && EditorView17.contentAttributes.of({
|
|
4452
|
+
class: slots.content.className
|
|
4453
|
+
}),
|
|
4454
|
+
// NOTE: Assumes default line height.
|
|
4455
|
+
_scrollPastEnd && scrollPastEnd2(),
|
|
4456
|
+
// Focus.
|
|
4457
|
+
EditorView17.updateListener.of((update2) => {
|
|
4458
|
+
update2.transactions.forEach((transaction) => {
|
|
4459
|
+
if (transaction.isUserEvent("focus.container")) {
|
|
4460
|
+
rootRef.current?.focus();
|
|
4461
|
+
}
|
|
4462
|
+
});
|
|
4463
|
+
}),
|
|
4464
|
+
// State.
|
|
4465
|
+
EditorView17.editable.of(!readonly),
|
|
4466
|
+
EditorState3.readOnly.of(!!readonly),
|
|
4467
|
+
// Storage and replication.
|
|
4468
|
+
// NOTE: This must come before user extensions.
|
|
4469
|
+
model.extension,
|
|
4470
|
+
// Custom.
|
|
4471
|
+
...extensions
|
|
4472
|
+
].filter(isNotFalsy4)
|
|
4473
|
+
});
|
|
4474
|
+
const view2 = new EditorView17({
|
|
4475
|
+
state,
|
|
4476
|
+
parent: rootRef.current,
|
|
4477
|
+
scrollTo,
|
|
4478
|
+
// NOTE: Uncomment to debug/monitor all transactions.
|
|
4479
|
+
// https://codemirror.net/docs/ref/#view.EditorView.dispatch
|
|
4480
|
+
dispatchTransactions: (trs, view3) => {
|
|
4481
|
+
if (debug) {
|
|
4482
|
+
logChanges(trs);
|
|
4483
|
+
}
|
|
4484
|
+
view3.update(trs);
|
|
4485
|
+
}
|
|
4486
|
+
});
|
|
4487
|
+
setView(view2);
|
|
4488
|
+
if (moveToEndOfLine) {
|
|
4489
|
+
const { to } = view2.state.doc.lineAt(0);
|
|
4490
|
+
view2?.dispatch({
|
|
4491
|
+
selection: {
|
|
4492
|
+
anchor: to
|
|
4493
|
+
}
|
|
4494
|
+
});
|
|
4495
|
+
}
|
|
4496
|
+
if (state.facet(editorMode).noTabster) {
|
|
4497
|
+
rootRef.current.removeAttribute("data-tabster");
|
|
4498
|
+
}
|
|
4499
|
+
return () => {
|
|
4500
|
+
view2?.destroy();
|
|
4501
|
+
setView(null);
|
|
4502
|
+
};
|
|
4503
|
+
}, [
|
|
4504
|
+
rootRef,
|
|
4505
|
+
extensions,
|
|
4506
|
+
model,
|
|
4507
|
+
readonly,
|
|
4508
|
+
themeMode
|
|
4509
|
+
]);
|
|
4510
|
+
const handleKeyUp = useCallback((event) => {
|
|
4511
|
+
const { key } = event;
|
|
4512
|
+
switch (key) {
|
|
4513
|
+
case "Enter": {
|
|
4514
|
+
view?.focus();
|
|
4515
|
+
break;
|
|
4516
|
+
}
|
|
4517
|
+
}
|
|
4518
|
+
}, [
|
|
4519
|
+
view
|
|
4520
|
+
]);
|
|
4521
|
+
return /* @__PURE__ */ React.createElement("div", {
|
|
4522
|
+
role: "none",
|
|
4523
|
+
ref: rootRef,
|
|
4524
|
+
key: model.id,
|
|
4525
|
+
tabIndex: 0,
|
|
4526
|
+
onKeyUp: handleKeyUp,
|
|
4527
|
+
...slots.root,
|
|
4528
|
+
...tabsterDOMAttribute
|
|
4529
|
+
});
|
|
4530
|
+
});
|
|
4531
|
+
var TextEditor = /* @__PURE__ */ forwardRef(({ readonly, placeholder: placeholder3, lineWrapping = true, theme = textTheme, slots, extensions: _extensions, ...props }, forwardedRef) => {
|
|
4532
|
+
const { themeMode } = useThemeContext();
|
|
4533
|
+
const updatedSlots = defaultsDeep3({}, slots, defaultTextSlots);
|
|
4534
|
+
const extensions = useMemo3(() => [
|
|
4535
|
+
createBasicExtensions({
|
|
4536
|
+
lineWrapping,
|
|
4537
|
+
placeholder: placeholder3
|
|
4538
|
+
}),
|
|
4539
|
+
createThemeExtensions({
|
|
4540
|
+
themeMode
|
|
3931
4541
|
}),
|
|
3932
4542
|
..._extensions ?? []
|
|
3933
4543
|
], [
|
|
@@ -3947,8 +4557,8 @@ var TextEditor = /* @__PURE__ */ forwardRef(({ readonly, placeholder: placeholde
|
|
|
3947
4557
|
});
|
|
3948
4558
|
var MarkdownEditor = /* @__PURE__ */ forwardRef(({ readonly, placeholder: placeholder3, theme = markdownTheme, slots, extensions: _extensions, ...props }, forwardedRef) => {
|
|
3949
4559
|
const { themeMode } = useThemeContext();
|
|
3950
|
-
const updatedSlots =
|
|
3951
|
-
const extensions =
|
|
4560
|
+
const updatedSlots = defaultsDeep3({}, slots, defaultMarkdownSlots);
|
|
4561
|
+
const extensions = useMemo3(() => [
|
|
3952
4562
|
createMarkdownExtensions({
|
|
3953
4563
|
themeMode,
|
|
3954
4564
|
placeholder: placeholder3
|
|
@@ -3986,7 +4596,7 @@ var defaultMarkdownSlots = {
|
|
|
3986
4596
|
// packages/ui/react-ui-editor/src/components/Toolbar/Toolbar.tsx
|
|
3987
4597
|
import { ChatText, Code, CodeBlock, Link, ListBullets, ListChecks, ListNumbers, Paragraph, TextStrikethrough, Table as Table2, TextB, TextHOne, TextHTwo, TextHThree, TextHFour, TextHFive, TextHSix, TextItalic, Quotes } from "@phosphor-icons/react";
|
|
3988
4598
|
import { createContext } from "@radix-ui/react-context";
|
|
3989
|
-
import React2, { useRef as
|
|
4599
|
+
import React2, { useRef as useRef4, useState as useState6 } from "react";
|
|
3990
4600
|
import { DensityProvider, ElevationProvider, Select, Toolbar as NaturalToolbar, Tooltip, useTranslation } from "@dxos/react-ui";
|
|
3991
4601
|
import { getSize } from "@dxos/react-ui-theme";
|
|
3992
4602
|
var tooltipProps = {
|
|
@@ -4044,9 +4654,9 @@ var MarkdownHeading = () => {
|
|
|
4044
4654
|
const header = blockType && /heading(\d)/.exec(blockType);
|
|
4045
4655
|
const value = header ? header[1] : blockType === "paragraph" || !blockType ? "0" : void 0;
|
|
4046
4656
|
const HeadingIcon = HeadingIcons[value ?? "0"];
|
|
4047
|
-
const suppressNextTooltip =
|
|
4048
|
-
const [tooltipOpen, setTooltipOpen] =
|
|
4049
|
-
const [selectOpen, setSelectOpen] =
|
|
4657
|
+
const suppressNextTooltip = useRef4(false);
|
|
4658
|
+
const [tooltipOpen, setTooltipOpen] = useState6(false);
|
|
4659
|
+
const [selectOpen, setSelectOpen] = useState6(false);
|
|
4050
4660
|
return /* @__PURE__ */ React2.createElement(Tooltip.Root, {
|
|
4051
4661
|
open: tooltipOpen,
|
|
4052
4662
|
onOpenChange: (nextOpen) => {
|
|
@@ -4249,384 +4859,6 @@ var Toolbar = {
|
|
|
4249
4859
|
Markdown: MarkdownStandard,
|
|
4250
4860
|
Extended: MarkdownExtended
|
|
4251
4861
|
};
|
|
4252
|
-
|
|
4253
|
-
// packages/ui/react-ui-editor/src/hooks/awareness-provider.ts
|
|
4254
|
-
import { DeferredTask, Event as Event2, sleep } from "@dxos/async";
|
|
4255
|
-
import { Context as Context2 } from "@dxos/context";
|
|
4256
|
-
import { invariant as invariant2 } from "@dxos/invariant";
|
|
4257
|
-
import { log as log4 } from "@dxos/log";
|
|
4258
|
-
var __dxlog_file5 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/hooks/awareness-provider.ts";
|
|
4259
|
-
var DEBOUNCE_INTERVAL = 100;
|
|
4260
|
-
var SpaceAwarenessProvider = class {
|
|
4261
|
-
constructor(params) {
|
|
4262
|
-
this._remoteStates = /* @__PURE__ */ new Map();
|
|
4263
|
-
this.remoteStateChange = new Event2();
|
|
4264
|
-
this._space = params.space;
|
|
4265
|
-
this._channel = params.channel;
|
|
4266
|
-
this._peerId = params.peerId;
|
|
4267
|
-
this._info = params.info;
|
|
4268
|
-
}
|
|
4269
|
-
open() {
|
|
4270
|
-
this._ctx = new Context2();
|
|
4271
|
-
this._postTask = new DeferredTask(this._ctx, async () => {
|
|
4272
|
-
if (this._localState) {
|
|
4273
|
-
await this._space.postMessage(this._channel, {
|
|
4274
|
-
kind: "post",
|
|
4275
|
-
state: this._localState
|
|
4276
|
-
});
|
|
4277
|
-
await sleep(DEBOUNCE_INTERVAL);
|
|
4278
|
-
}
|
|
4279
|
-
});
|
|
4280
|
-
this._ctx.onDispose(this._space.listen(this._channel, (message) => {
|
|
4281
|
-
switch (message.payload.kind) {
|
|
4282
|
-
case "query": {
|
|
4283
|
-
this._handleQueryMessage();
|
|
4284
|
-
break;
|
|
4285
|
-
}
|
|
4286
|
-
case "post": {
|
|
4287
|
-
this._handlePostMessage(message.payload);
|
|
4288
|
-
break;
|
|
4289
|
-
}
|
|
4290
|
-
}
|
|
4291
|
-
}));
|
|
4292
|
-
void this._space.postMessage(this._channel, {
|
|
4293
|
-
kind: "query"
|
|
4294
|
-
}).catch((err) => {
|
|
4295
|
-
log4.debug("failed to query awareness", {
|
|
4296
|
-
err
|
|
4297
|
-
}, {
|
|
4298
|
-
F: __dxlog_file5,
|
|
4299
|
-
L: 89,
|
|
4300
|
-
S: this,
|
|
4301
|
-
C: (f, a) => f(...a)
|
|
4302
|
-
});
|
|
4303
|
-
});
|
|
4304
|
-
}
|
|
4305
|
-
close() {
|
|
4306
|
-
void this._ctx?.dispose();
|
|
4307
|
-
this._ctx = void 0;
|
|
4308
|
-
this._postTask = void 0;
|
|
4309
|
-
}
|
|
4310
|
-
getRemoteStates() {
|
|
4311
|
-
return Array.from(this._remoteStates.values());
|
|
4312
|
-
}
|
|
4313
|
-
update(position) {
|
|
4314
|
-
invariant2(this._postTask, void 0, {
|
|
4315
|
-
F: __dxlog_file5,
|
|
4316
|
-
L: 104,
|
|
4317
|
-
S: this,
|
|
4318
|
-
A: [
|
|
4319
|
-
"this._postTask",
|
|
4320
|
-
""
|
|
4321
|
-
]
|
|
4322
|
-
});
|
|
4323
|
-
this._localState = {
|
|
4324
|
-
peerId: this._peerId,
|
|
4325
|
-
position,
|
|
4326
|
-
info: this._info
|
|
4327
|
-
};
|
|
4328
|
-
this._postTask.schedule();
|
|
4329
|
-
}
|
|
4330
|
-
_handleQueryMessage() {
|
|
4331
|
-
invariant2(this._postTask, void 0, {
|
|
4332
|
-
F: __dxlog_file5,
|
|
4333
|
-
L: 115,
|
|
4334
|
-
S: this,
|
|
4335
|
-
A: [
|
|
4336
|
-
"this._postTask",
|
|
4337
|
-
""
|
|
4338
|
-
]
|
|
4339
|
-
});
|
|
4340
|
-
this._postTask.schedule();
|
|
4341
|
-
}
|
|
4342
|
-
_handlePostMessage(message) {
|
|
4343
|
-
invariant2(message.kind === "post", void 0, {
|
|
4344
|
-
F: __dxlog_file5,
|
|
4345
|
-
L: 120,
|
|
4346
|
-
S: this,
|
|
4347
|
-
A: [
|
|
4348
|
-
"message.kind === 'post'",
|
|
4349
|
-
""
|
|
4350
|
-
]
|
|
4351
|
-
});
|
|
4352
|
-
this._remoteStates.set(message.state.peerId, message.state);
|
|
4353
|
-
this.remoteStateChange.emit();
|
|
4354
|
-
}
|
|
4355
|
-
};
|
|
4356
|
-
|
|
4357
|
-
// packages/ui/react-ui-editor/src/hooks/defs.ts
|
|
4358
|
-
import { StateField as StateField6 } from "@codemirror/state";
|
|
4359
|
-
var modelState = StateField6.define({
|
|
4360
|
-
create: () => void 0,
|
|
4361
|
-
update: (model) => model
|
|
4362
|
-
});
|
|
4363
|
-
|
|
4364
|
-
// packages/ui/react-ui-editor/src/hooks/useActionHandler.ts
|
|
4365
|
-
var useActionHandler = (view) => {
|
|
4366
|
-
return (action) => {
|
|
4367
|
-
if (!view) {
|
|
4368
|
-
return;
|
|
4369
|
-
}
|
|
4370
|
-
let inlineType, listType;
|
|
4371
|
-
switch (action.type) {
|
|
4372
|
-
case "heading":
|
|
4373
|
-
setHeading(parseInt(action.data))(view);
|
|
4374
|
-
break;
|
|
4375
|
-
case "strong":
|
|
4376
|
-
case "emphasis":
|
|
4377
|
-
case "strikethrough":
|
|
4378
|
-
case "code":
|
|
4379
|
-
inlineType = action.type === "strong" ? Inline.Strong : action.type === "emphasis" ? Inline.Emphasis : action.type === "strikethrough" ? Inline.Strikethrough : Inline.Code;
|
|
4380
|
-
(typeof action.data === "boolean" ? setStyle(inlineType, action.data) : toggleStyle(inlineType))(view);
|
|
4381
|
-
break;
|
|
4382
|
-
case "list-ordered":
|
|
4383
|
-
case "list-bullet":
|
|
4384
|
-
case "list-task":
|
|
4385
|
-
listType = action.type === "list-ordered" ? List.Ordered : action.type === "list-bullet" ? List.Bullet : List.Task;
|
|
4386
|
-
(action.data === false ? removeList(listType) : action.data === true ? addList(listType) : toggleList(listType))(view);
|
|
4387
|
-
break;
|
|
4388
|
-
case "blockquote":
|
|
4389
|
-
(action.data === false ? removeBlockquote : action.data === true ? addBlockquote : toggleBlockquote)(view);
|
|
4390
|
-
break;
|
|
4391
|
-
case "codeblock":
|
|
4392
|
-
(action.data === false ? removeCodeblock : addCodeblock)(view);
|
|
4393
|
-
break;
|
|
4394
|
-
case "table":
|
|
4395
|
-
insertTable(view);
|
|
4396
|
-
break;
|
|
4397
|
-
case "link":
|
|
4398
|
-
(action.data === false ? removeLink : addLink)(view);
|
|
4399
|
-
break;
|
|
4400
|
-
case "comment":
|
|
4401
|
-
createComment(view);
|
|
4402
|
-
break;
|
|
4403
|
-
}
|
|
4404
|
-
setTimeout(() => {
|
|
4405
|
-
if (!view.hasFocus) {
|
|
4406
|
-
view.focus();
|
|
4407
|
-
}
|
|
4408
|
-
});
|
|
4409
|
-
};
|
|
4410
|
-
};
|
|
4411
|
-
|
|
4412
|
-
// packages/ui/react-ui-editor/src/hooks/useEditorView.ts
|
|
4413
|
-
import { useRef as useRef3, useState as useState4 } from "react";
|
|
4414
|
-
var useEditorView = (id) => {
|
|
4415
|
-
const editorRef = useRef3(null);
|
|
4416
|
-
const [prev, setPrev] = useState4([
|
|
4417
|
-
null,
|
|
4418
|
-
""
|
|
4419
|
-
]);
|
|
4420
|
-
if (prev[0] !== editorRef.current) {
|
|
4421
|
-
setPrev([
|
|
4422
|
-
editorRef.current,
|
|
4423
|
-
id
|
|
4424
|
-
]);
|
|
4425
|
-
}
|
|
4426
|
-
return [
|
|
4427
|
-
editorRef,
|
|
4428
|
-
prev[1] !== id
|
|
4429
|
-
];
|
|
4430
|
-
};
|
|
4431
|
-
|
|
4432
|
-
// packages/ui/react-ui-editor/src/hooks/useTextEditor.ts
|
|
4433
|
-
import { EditorSelection as EditorSelection2, EditorState as EditorState3 } from "@codemirror/state";
|
|
4434
|
-
import { EditorView as EditorView15 } from "@codemirror/view";
|
|
4435
|
-
import { useEffect as useEffect3, useRef as useRef4, useState as useState5 } from "react";
|
|
4436
|
-
import { log as log5 } from "@dxos/log";
|
|
4437
|
-
import { isNotFalsy as isNotFalsy5 } from "@dxos/util";
|
|
4438
|
-
var __dxlog_file6 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/hooks/useTextEditor.ts";
|
|
4439
|
-
var useTextEditor = ({ autoFocus, scrollTo, debug, doc, selection, extensions } = {}, deps) => {
|
|
4440
|
-
const onUpdate = useRef4();
|
|
4441
|
-
const [view, setView] = useState5();
|
|
4442
|
-
const parentRef = useRef4(null);
|
|
4443
|
-
useEffect3(() => {
|
|
4444
|
-
let view2;
|
|
4445
|
-
if (parentRef.current) {
|
|
4446
|
-
const state = EditorState3.create({
|
|
4447
|
-
doc,
|
|
4448
|
-
selection,
|
|
4449
|
-
extensions: [
|
|
4450
|
-
// TODO(burdon): Doesn't catch errors in keymap functions.
|
|
4451
|
-
EditorView15.exceptionSink.of((err) => {
|
|
4452
|
-
log5.catch(err, void 0, {
|
|
4453
|
-
F: __dxlog_file6,
|
|
4454
|
-
L: 57,
|
|
4455
|
-
S: void 0,
|
|
4456
|
-
C: (f, a) => f(...a)
|
|
4457
|
-
});
|
|
4458
|
-
}),
|
|
4459
|
-
extensions,
|
|
4460
|
-
EditorView15.updateListener.of(() => {
|
|
4461
|
-
onUpdate.current?.();
|
|
4462
|
-
})
|
|
4463
|
-
].filter(isNotFalsy5)
|
|
4464
|
-
});
|
|
4465
|
-
view2 = new EditorView15({
|
|
4466
|
-
parent: parentRef.current,
|
|
4467
|
-
scrollTo,
|
|
4468
|
-
state,
|
|
4469
|
-
// NOTE: Uncomment to debug/monitor all transactions.
|
|
4470
|
-
// https://codemirror.net/docs/ref/#view.EditorView.dispatch
|
|
4471
|
-
dispatchTransactions: (trs, view3) => {
|
|
4472
|
-
if (debug) {
|
|
4473
|
-
logChanges(trs);
|
|
4474
|
-
}
|
|
4475
|
-
view3.update(trs);
|
|
4476
|
-
}
|
|
4477
|
-
});
|
|
4478
|
-
setView(view2);
|
|
4479
|
-
}
|
|
4480
|
-
return () => {
|
|
4481
|
-
view2?.destroy();
|
|
4482
|
-
};
|
|
4483
|
-
}, deps);
|
|
4484
|
-
useEffect3(() => {
|
|
4485
|
-
if (view) {
|
|
4486
|
-
if (!selection && !view.state.selection.main.anchor) {
|
|
4487
|
-
selection = EditorSelection2.single(view.state.doc.line(1).to);
|
|
4488
|
-
}
|
|
4489
|
-
if (selection || scrollTo) {
|
|
4490
|
-
onUpdate.current = () => {
|
|
4491
|
-
onUpdate.current = void 0;
|
|
4492
|
-
view.dispatch({
|
|
4493
|
-
selection,
|
|
4494
|
-
effects: scrollTo && [
|
|
4495
|
-
scrollTo
|
|
4496
|
-
],
|
|
4497
|
-
scrollIntoView: !scrollTo
|
|
4498
|
-
});
|
|
4499
|
-
};
|
|
4500
|
-
}
|
|
4501
|
-
if (autoFocus) {
|
|
4502
|
-
view.focus();
|
|
4503
|
-
}
|
|
4504
|
-
}
|
|
4505
|
-
}, [
|
|
4506
|
-
view,
|
|
4507
|
-
autoFocus,
|
|
4508
|
-
selection,
|
|
4509
|
-
scrollTo
|
|
4510
|
-
]);
|
|
4511
|
-
return {
|
|
4512
|
-
parentRef,
|
|
4513
|
-
view
|
|
4514
|
-
};
|
|
4515
|
-
};
|
|
4516
|
-
var createDataExtensions = ({ readonly = false } = {}) => {
|
|
4517
|
-
return [
|
|
4518
|
-
//
|
|
4519
|
-
EditorState3.readOnly.of(readonly),
|
|
4520
|
-
EditorView15.editable.of(!readonly)
|
|
4521
|
-
];
|
|
4522
|
-
};
|
|
4523
|
-
var createThemeExtensions = ({ theme, themeMode, slots } = {}) => {
|
|
4524
|
-
return [
|
|
4525
|
-
//
|
|
4526
|
-
EditorView15.baseTheme(defaultTheme),
|
|
4527
|
-
theme && EditorView15.theme(theme),
|
|
4528
|
-
EditorView15.darkTheme.of(themeMode === "dark"),
|
|
4529
|
-
EditorView15.editorAttributes.of({
|
|
4530
|
-
class: slots?.editor?.className ?? ""
|
|
4531
|
-
}),
|
|
4532
|
-
EditorView15.contentAttributes.of({
|
|
4533
|
-
class: slots?.content?.className ?? ""
|
|
4534
|
-
})
|
|
4535
|
-
].filter(isNotFalsy5);
|
|
4536
|
-
};
|
|
4537
|
-
|
|
4538
|
-
// packages/ui/react-ui-editor/src/hooks/useTextModel.ts
|
|
4539
|
-
import get5 from "lodash.get";
|
|
4540
|
-
import { useState as useState6, useMemo as useMemo3 } from "react";
|
|
4541
|
-
import { generateName } from "@dxos/display-name";
|
|
4542
|
-
import { getRawDoc } from "@dxos/echo-schema";
|
|
4543
|
-
import { invariant as invariant3 } from "@dxos/invariant";
|
|
4544
|
-
import { isAutomergeObject } from "@dxos/react-client/echo";
|
|
4545
|
-
import { hueTokens } from "@dxos/react-ui-theme";
|
|
4546
|
-
import { hexToHue } from "@dxos/util";
|
|
4547
|
-
var __dxlog_file7 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/hooks/useTextModel.ts";
|
|
4548
|
-
var useTextExtensions = ({ id, text, space, identity }) => {
|
|
4549
|
-
const extensions = [
|
|
4550
|
-
automerge(text)
|
|
4551
|
-
];
|
|
4552
|
-
const peerId = identity?.identityKey.toHex();
|
|
4553
|
-
const { cursorLightValue, cursorDarkValue } = hueTokens[hexToHue(peerId ?? "0")];
|
|
4554
|
-
if (space && identity) {
|
|
4555
|
-
const awarenessProvider2 = new SpaceAwarenessProvider({
|
|
4556
|
-
space,
|
|
4557
|
-
channel: `awareness.${id}`,
|
|
4558
|
-
peerId: identity.identityKey.toHex(),
|
|
4559
|
-
info: {
|
|
4560
|
-
displayName: identity.profile?.displayName ?? generateName(identity.identityKey.toHex()),
|
|
4561
|
-
color: cursorDarkValue,
|
|
4562
|
-
lightColor: cursorLightValue
|
|
4563
|
-
}
|
|
4564
|
-
});
|
|
4565
|
-
extensions.push(awareness(awarenessProvider2));
|
|
4566
|
-
}
|
|
4567
|
-
return extensions;
|
|
4568
|
-
};
|
|
4569
|
-
var useTextModel = (props) => useMemo3(() => createModel(props), Object.values(props));
|
|
4570
|
-
var useInMemoryTextModel = ({ id, defaultContent }) => {
|
|
4571
|
-
const [content, setContent] = useState6(defaultContent ?? "");
|
|
4572
|
-
return {
|
|
4573
|
-
id,
|
|
4574
|
-
content,
|
|
4575
|
-
setContent,
|
|
4576
|
-
text: () => content
|
|
4577
|
-
};
|
|
4578
|
-
};
|
|
4579
|
-
var createModel = ({ space, identity, text }) => {
|
|
4580
|
-
if (!text) {
|
|
4581
|
-
return void 0;
|
|
4582
|
-
}
|
|
4583
|
-
invariant3(isAutomergeObject(text), void 0, {
|
|
4584
|
-
F: __dxlog_file7,
|
|
4585
|
-
L: 87,
|
|
4586
|
-
S: void 0,
|
|
4587
|
-
A: [
|
|
4588
|
-
"isAutomergeObject(text)",
|
|
4589
|
-
""
|
|
4590
|
-
]
|
|
4591
|
-
});
|
|
4592
|
-
const obj = text;
|
|
4593
|
-
const doc = getRawDoc(obj, [
|
|
4594
|
-
obj.field
|
|
4595
|
-
]);
|
|
4596
|
-
const peerId = identity?.identityKey.toHex();
|
|
4597
|
-
const { cursorLightValue, cursorDarkValue } = hueTokens[hexToHue(peerId ?? "0")];
|
|
4598
|
-
const awarenessProvider2 = space && new SpaceAwarenessProvider({
|
|
4599
|
-
space,
|
|
4600
|
-
channel: `automerge.awareness.${obj.id}`,
|
|
4601
|
-
info: {
|
|
4602
|
-
displayName: identity ? identity.profile?.displayName ?? generateName(identity.identityKey.toHex()) : void 0,
|
|
4603
|
-
color: cursorLightValue,
|
|
4604
|
-
lightColor: cursorDarkValue
|
|
4605
|
-
},
|
|
4606
|
-
peerId: identity?.identityKey.toHex() ?? "Anonymous"
|
|
4607
|
-
});
|
|
4608
|
-
const extensions = [
|
|
4609
|
-
modelState.init(() => model),
|
|
4610
|
-
automerge({
|
|
4611
|
-
handle: doc.handle,
|
|
4612
|
-
path: doc.path
|
|
4613
|
-
})
|
|
4614
|
-
];
|
|
4615
|
-
if (awarenessProvider2) {
|
|
4616
|
-
extensions.push(awareness(awarenessProvider2));
|
|
4617
|
-
}
|
|
4618
|
-
const model = {
|
|
4619
|
-
id: obj.id,
|
|
4620
|
-
content: doc,
|
|
4621
|
-
text: () => get5(doc.handle.docSync(), doc.path),
|
|
4622
|
-
extension: extensions,
|
|
4623
|
-
peer: identity ? {
|
|
4624
|
-
id: identity.identityKey.toHex(),
|
|
4625
|
-
name: identity.profile?.displayName
|
|
4626
|
-
} : void 0
|
|
4627
|
-
};
|
|
4628
|
-
return model;
|
|
4629
|
-
};
|
|
4630
4862
|
export {
|
|
4631
4863
|
BaseTextEditor,
|
|
4632
4864
|
Cursor,
|
|
@@ -4655,11 +4887,11 @@ export {
|
|
|
4655
4887
|
blast,
|
|
4656
4888
|
callbackWrapper,
|
|
4657
4889
|
codeTheme,
|
|
4890
|
+
command,
|
|
4658
4891
|
comments,
|
|
4659
4892
|
compareFormatting,
|
|
4660
|
-
|
|
4893
|
+
createBasicExtensions,
|
|
4661
4894
|
createComment,
|
|
4662
|
-
createDataExtensions,
|
|
4663
4895
|
createMarkdownExtensions,
|
|
4664
4896
|
createThemeExtensions,
|
|
4665
4897
|
cursorLineMargin,
|
|
@@ -4670,6 +4902,7 @@ export {
|
|
|
4670
4902
|
defaultSlots,
|
|
4671
4903
|
defaultTextSlots,
|
|
4672
4904
|
defaultTheme,
|
|
4905
|
+
dnd,
|
|
4673
4906
|
editorFillLayoutEditor,
|
|
4674
4907
|
editorFillLayoutRoot,
|
|
4675
4908
|
editorMode,
|
|
@@ -4680,7 +4913,7 @@ export {
|
|
|
4680
4913
|
getToken,
|
|
4681
4914
|
image,
|
|
4682
4915
|
insertTable,
|
|
4683
|
-
|
|
4916
|
+
keymap9 as keymap,
|
|
4684
4917
|
linkTooltip,
|
|
4685
4918
|
listener,
|
|
4686
4919
|
logChanges,
|
|
@@ -4689,7 +4922,6 @@ export {
|
|
|
4689
4922
|
markdownTagsExtensions,
|
|
4690
4923
|
markdownTheme,
|
|
4691
4924
|
mention,
|
|
4692
|
-
modelState,
|
|
4693
4925
|
outliner,
|
|
4694
4926
|
removeBlockquote,
|
|
4695
4927
|
removeCodeblock,
|