@dxos/react-ui-editor 0.3.10-main.cbe7692 → 0.3.10-main.dcfebef
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 +123 -689
- 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 +1 -19
- package/dist/types/src/components/TextEditor/MarkdownEditor.stories.d.ts.map +1 -1
- package/dist/types/src/components/TextEditor/TextEditor.d.ts +1 -2
- package/dist/types/src/components/TextEditor/TextEditor.d.ts.map +1 -1
- package/dist/types/src/components/TextEditor/extensions/autocomplete.d.ts.map +1 -1
- package/dist/types/src/components/TextEditor/extensions/basic.d.ts +1 -2
- package/dist/types/src/components/TextEditor/extensions/basic.d.ts.map +1 -1
- package/dist/types/src/components/TextEditor/extensions/demo.d.ts +1 -2
- package/dist/types/src/components/TextEditor/extensions/demo.d.ts.map +1 -1
- package/dist/types/src/components/TextEditor/extensions/index.d.ts +0 -4
- package/dist/types/src/components/TextEditor/extensions/index.d.ts.map +1 -1
- package/dist/types/src/components/TextEditor/extensions/link.d.ts.map +1 -1
- package/dist/types/src/components/TextEditor/extensions/listener.d.ts.map +1 -1
- package/dist/types/src/components/TextEditor/extensions/markdown/bundle.d.ts +1 -2
- package/dist/types/src/components/TextEditor/extensions/markdown/bundle.d.ts.map +1 -1
- package/dist/types/src/components/TextEditor/extensions/markdown/highlight.d.ts +2 -6
- package/dist/types/src/components/TextEditor/extensions/markdown/highlight.d.ts.map +1 -1
- package/dist/types/src/components/TextEditor/extensions/tasklist.d.ts +1 -2
- package/dist/types/src/components/TextEditor/extensions/tasklist.d.ts.map +1 -1
- package/dist/types/src/components/TextEditor/themes/default.d.ts +0 -5
- package/dist/types/src/components/TextEditor/themes/default.d.ts.map +1 -1
- package/dist/types/src/{hooks/yjs → components/TextEditor}/yjs.stories.d.ts +1 -1
- package/dist/types/src/components/TextEditor/yjs.stories.d.ts.map +1 -0
- package/dist/types/src/styles/markdown.d.ts +2 -3
- package/dist/types/src/styles/markdown.d.ts.map +1 -1
- package/package.json +20 -20
- package/src/components/TextEditor/MarkdownEditor.stories.tsx +25 -98
- package/src/components/TextEditor/TextEditor.tsx +7 -16
- package/src/components/TextEditor/extensions/autocomplete.ts +20 -5
- package/src/components/TextEditor/extensions/basic.ts +1 -2
- package/src/components/TextEditor/extensions/demo.ts +1 -4
- package/src/components/TextEditor/extensions/index.ts +0 -4
- package/src/components/TextEditor/extensions/link.ts +23 -15
- package/src/components/TextEditor/extensions/listener.ts +3 -3
- package/src/components/TextEditor/extensions/markdown/bundle.ts +5 -10
- package/src/components/TextEditor/extensions/markdown/highlight.ts +104 -118
- package/src/components/TextEditor/extensions/tasklist.ts +20 -34
- package/src/components/TextEditor/themes/default.ts +2 -54
- package/src/{hooks/yjs → components/TextEditor}/yjs.stories.tsx +1 -1
- package/src/styles/markdown.ts +8 -14
- package/dist/types/src/components/TextEditor/extensions/blast.d.ts +0 -25
- package/dist/types/src/components/TextEditor/extensions/blast.d.ts.map +0 -1
- package/dist/types/src/components/TextEditor/extensions/image.d.ts +0 -4
- package/dist/types/src/components/TextEditor/extensions/image.d.ts.map +0 -1
- package/dist/types/src/components/TextEditor/extensions/mention.d.ts +0 -6
- package/dist/types/src/components/TextEditor/extensions/mention.d.ts.map +0 -1
- package/dist/types/src/components/TextEditor/extensions/table.d.ts +0 -8
- package/dist/types/src/components/TextEditor/extensions/table.d.ts.map +0 -1
- package/dist/types/src/hooks/yjs/yjs.stories.d.ts.map +0 -1
- package/src/components/TextEditor/extensions/blast.ts +0 -375
- package/src/components/TextEditor/extensions/image.ts +0 -68
- package/src/components/TextEditor/extensions/mention.ts +0 -31
- package/src/components/TextEditor/extensions/table.ts +0 -123
|
@@ -24,13 +24,13 @@ var autocomplete = ({ onSearch }) => {
|
|
|
24
24
|
// TODO(burdon): Optional decoration via addToOptions
|
|
25
25
|
override: [
|
|
26
26
|
(context) => {
|
|
27
|
-
const
|
|
28
|
-
if (!
|
|
27
|
+
const word = context.matchBefore(/\w*/);
|
|
28
|
+
if (!word || word.from === word.to && !context.explicit) {
|
|
29
29
|
return null;
|
|
30
30
|
}
|
|
31
31
|
return {
|
|
32
|
-
from:
|
|
33
|
-
options: onSearch(
|
|
32
|
+
from: word.from,
|
|
33
|
+
options: onSearch(word.text.toLowerCase())
|
|
34
34
|
};
|
|
35
35
|
}
|
|
36
36
|
]
|
|
@@ -43,7 +43,7 @@ import { closeBrackets } from "@codemirror/autocomplete";
|
|
|
43
43
|
import { bracketMatching, defaultHighlightStyle, syntaxHighlighting } from "@codemirror/language";
|
|
44
44
|
import { oneDarkHighlightStyle } from "@codemirror/theme-one-dark";
|
|
45
45
|
import { EditorView, placeholder } from "@codemirror/view";
|
|
46
|
-
var basicBundle = ({
|
|
46
|
+
var basicBundle = ({ themeMode, placeholder: _placeholder }) => [
|
|
47
47
|
// TODO(burdon): Compare with minimalSetup.
|
|
48
48
|
// https://codemirror.net/docs/ref/#codemirror.minimalSetup
|
|
49
49
|
bracketMatching(),
|
|
@@ -54,324 +54,8 @@ var basicBundle = ({ readonly, themeMode, placeholder: _placeholder }) => [
|
|
|
54
54
|
themeMode === "dark" ? syntaxHighlighting(oneDarkHighlightStyle) : syntaxHighlighting(defaultHighlightStyle)
|
|
55
55
|
].filter(Boolean);
|
|
56
56
|
|
|
57
|
-
// packages/ui/react-ui-editor/src/components/TextEditor/extensions/blast.ts
|
|
58
|
-
import { StateField } from "@codemirror/state";
|
|
59
|
-
import { EditorView as EditorView2, keymap as keymap2 } from "@codemirror/view";
|
|
60
|
-
import defaultsDeep from "lodash.defaultsdeep";
|
|
61
|
-
import { invariant } from "@dxos/invariant";
|
|
62
|
-
var __dxlog_file = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/components/TextEditor/extensions/blast.ts";
|
|
63
|
-
var defaultOptions = {
|
|
64
|
-
maxParticles: 200,
|
|
65
|
-
particleGravity: 0.08,
|
|
66
|
-
particleAlphaFadeout: 0.996,
|
|
67
|
-
particleSize: {
|
|
68
|
-
min: 2,
|
|
69
|
-
max: 8
|
|
70
|
-
},
|
|
71
|
-
particleNumRange: {
|
|
72
|
-
min: 5,
|
|
73
|
-
max: 10
|
|
74
|
-
},
|
|
75
|
-
particleVelocityRange: {
|
|
76
|
-
x: [
|
|
77
|
-
-1,
|
|
78
|
-
1
|
|
79
|
-
],
|
|
80
|
-
y: [
|
|
81
|
-
-3.5,
|
|
82
|
-
-1.5
|
|
83
|
-
]
|
|
84
|
-
},
|
|
85
|
-
particleShrinkRate: 0.95,
|
|
86
|
-
shakeIntensity: 5
|
|
87
|
-
};
|
|
88
|
-
var blast = (options) => {
|
|
89
|
-
let blaster;
|
|
90
|
-
let last = 0;
|
|
91
|
-
const getPoint = (view, pos) => {
|
|
92
|
-
const { left: x = 0, top: y = 0 } = view.coordsForChar(pos) ?? {};
|
|
93
|
-
const element = document.elementFromPoint(x, y);
|
|
94
|
-
const { offsetLeft: left = 0, offsetTop: top = 0 } = view.scrollDOM.parentElement ?? {};
|
|
95
|
-
const point = {
|
|
96
|
-
x: x - left,
|
|
97
|
-
y: y - top
|
|
98
|
-
};
|
|
99
|
-
return {
|
|
100
|
-
element,
|
|
101
|
-
point
|
|
102
|
-
};
|
|
103
|
-
};
|
|
104
|
-
return [
|
|
105
|
-
// Cursor moved.
|
|
106
|
-
EditorView2.updateListener.of((update4) => {
|
|
107
|
-
if (blaster?.node !== update4.view.scrollDOM) {
|
|
108
|
-
if (blaster) {
|
|
109
|
-
blaster.destroy();
|
|
110
|
-
}
|
|
111
|
-
blaster = new Blaster(update4.view.scrollDOM, defaultsDeep({}, options, defaultOptions));
|
|
112
|
-
blaster.initialize();
|
|
113
|
-
blaster.start();
|
|
114
|
-
} else {
|
|
115
|
-
blaster.resize();
|
|
116
|
-
}
|
|
117
|
-
const current = update4.view.state.selection.main.head;
|
|
118
|
-
if (current !== last) {
|
|
119
|
-
last = current;
|
|
120
|
-
const { element, point } = getPoint(update4.view, current);
|
|
121
|
-
if (element && point) {
|
|
122
|
-
blaster.spawn({
|
|
123
|
-
element,
|
|
124
|
-
point
|
|
125
|
-
});
|
|
126
|
-
}
|
|
127
|
-
}
|
|
128
|
-
}),
|
|
129
|
-
// Document changed.
|
|
130
|
-
StateField.define({
|
|
131
|
-
create: () => null,
|
|
132
|
-
update: (_value, transaction) => {
|
|
133
|
-
if (blaster && transaction.docChanged) {
|
|
134
|
-
const view = EditorView2.findFromDOM(blaster.node);
|
|
135
|
-
const { element, point } = getPoint(view, transaction.selection.main.head);
|
|
136
|
-
if (element && point) {
|
|
137
|
-
blaster.spawn({
|
|
138
|
-
element,
|
|
139
|
-
point
|
|
140
|
-
});
|
|
141
|
-
}
|
|
142
|
-
}
|
|
143
|
-
return null;
|
|
144
|
-
}
|
|
145
|
-
}),
|
|
146
|
-
keymap2.of([
|
|
147
|
-
{
|
|
148
|
-
any: (view, event) => {
|
|
149
|
-
if (blaster && event.key === "Enter" && event.shiftKey) {
|
|
150
|
-
blaster.shake({
|
|
151
|
-
time: 0.4
|
|
152
|
-
});
|
|
153
|
-
}
|
|
154
|
-
return false;
|
|
155
|
-
}
|
|
156
|
-
}
|
|
157
|
-
])
|
|
158
|
-
];
|
|
159
|
-
};
|
|
160
|
-
var Blaster = class {
|
|
161
|
-
constructor(_node, _options) {
|
|
162
|
-
this._node = _node;
|
|
163
|
-
this._options = _options;
|
|
164
|
-
this._running = false;
|
|
165
|
-
this._shakeTime = 0;
|
|
166
|
-
this._shakeTimeMax = 0;
|
|
167
|
-
this._particles = [];
|
|
168
|
-
this._particlePointer = 0;
|
|
169
|
-
this._lastPoint = {
|
|
170
|
-
x: 0,
|
|
171
|
-
y: 0
|
|
172
|
-
};
|
|
173
|
-
this.shake = throttle(({ time }) => {
|
|
174
|
-
this._shakeTime = this._shakeTimeMax;
|
|
175
|
-
this._shakeTimeMax = time;
|
|
176
|
-
}, 100);
|
|
177
|
-
this.spawn = throttle(({ element, point }) => {
|
|
178
|
-
const color = getRGBComponents(element, this._options.color);
|
|
179
|
-
const numParticles = random(this._options.particleNumRange.min, this._options.particleNumRange.max);
|
|
180
|
-
const dir = this._lastPoint.x === point.x ? 0 : this._lastPoint.x < point.x ? 1 : -1;
|
|
181
|
-
this._lastPoint = point;
|
|
182
|
-
for (let i = numParticles; i--; i > 0) {
|
|
183
|
-
this._particles[this._particlePointer] = this._effect.create(point.x - dir * 16, point.y, color);
|
|
184
|
-
this._particlePointer = (this._particlePointer + 1) % this._options.maxParticles;
|
|
185
|
-
}
|
|
186
|
-
}, 100);
|
|
187
|
-
this._effect = this._options.effect === 1 ? new Effect1(_options) : new Effect2(_options);
|
|
188
|
-
}
|
|
189
|
-
get node() {
|
|
190
|
-
return this._node;
|
|
191
|
-
}
|
|
192
|
-
initialize() {
|
|
193
|
-
invariant(!this._canvas && !this._ctx, void 0, {
|
|
194
|
-
F: __dxlog_file,
|
|
195
|
-
L: 140,
|
|
196
|
-
S: this,
|
|
197
|
-
A: [
|
|
198
|
-
"!this._canvas && !this._ctx",
|
|
199
|
-
""
|
|
200
|
-
]
|
|
201
|
-
});
|
|
202
|
-
this._canvas = document.createElement("canvas");
|
|
203
|
-
this._canvas.id = "code-blast-canvas";
|
|
204
|
-
this._canvas.style.position = "absolute";
|
|
205
|
-
this._canvas.style.zIndex = "0";
|
|
206
|
-
this._canvas.style.pointerEvents = "none";
|
|
207
|
-
this._ctx = this._canvas.getContext("2d");
|
|
208
|
-
const parent = this._node.parentElement?.parentElement;
|
|
209
|
-
parent?.appendChild(this._canvas);
|
|
210
|
-
this.resize();
|
|
211
|
-
}
|
|
212
|
-
destroy() {
|
|
213
|
-
this.stop();
|
|
214
|
-
if (this._canvas) {
|
|
215
|
-
this._canvas.remove();
|
|
216
|
-
this._canvas = void 0;
|
|
217
|
-
this._ctx = void 0;
|
|
218
|
-
}
|
|
219
|
-
}
|
|
220
|
-
resize() {
|
|
221
|
-
if (this._node.parentElement && this._canvas) {
|
|
222
|
-
const { offsetLeft: x, offsetTop: y, offsetWidth: width, offsetHeight: height } = this._node.parentElement;
|
|
223
|
-
this._canvas.style.top = `${y}px`;
|
|
224
|
-
this._canvas.style.left = `${x}px`;
|
|
225
|
-
this._canvas.width = width;
|
|
226
|
-
this._canvas.height = height;
|
|
227
|
-
}
|
|
228
|
-
}
|
|
229
|
-
start() {
|
|
230
|
-
invariant(this._canvas && this._ctx, void 0, {
|
|
231
|
-
F: __dxlog_file,
|
|
232
|
-
L: 179,
|
|
233
|
-
S: this,
|
|
234
|
-
A: [
|
|
235
|
-
"this._canvas && this._ctx",
|
|
236
|
-
""
|
|
237
|
-
]
|
|
238
|
-
});
|
|
239
|
-
this._running = true;
|
|
240
|
-
this.loop();
|
|
241
|
-
}
|
|
242
|
-
stop() {
|
|
243
|
-
this._running = false;
|
|
244
|
-
this._node.style.transform = "translate(0px, 0px)";
|
|
245
|
-
}
|
|
246
|
-
loop() {
|
|
247
|
-
if (!this._running || !this._canvas || !this._ctx) {
|
|
248
|
-
return;
|
|
249
|
-
}
|
|
250
|
-
this._ctx.clearRect(0, 0, this._canvas.width ?? 0, this._canvas.height ?? 0);
|
|
251
|
-
const now = (/* @__PURE__ */ new Date()).getTime();
|
|
252
|
-
this._lastTime ??= now;
|
|
253
|
-
const dt = (now - this._lastTime) / 1e3;
|
|
254
|
-
this._lastTime = now;
|
|
255
|
-
if (this._shakeTime > 0) {
|
|
256
|
-
this._shakeTime -= dt;
|
|
257
|
-
const magnitude = this._shakeTime / this._shakeTimeMax * this._options.shakeIntensity;
|
|
258
|
-
const shakeX = random(-magnitude, magnitude);
|
|
259
|
-
const shakeY = random(-magnitude, magnitude);
|
|
260
|
-
this._node.style.transform = `translate(${shakeX}px,${shakeY}px)`;
|
|
261
|
-
}
|
|
262
|
-
this.drawParticles();
|
|
263
|
-
requestAnimationFrame(this.loop.bind(this));
|
|
264
|
-
}
|
|
265
|
-
drawParticles() {
|
|
266
|
-
for (let i = this._particles.length; i--; i > 0) {
|
|
267
|
-
const particle = this._particles[i];
|
|
268
|
-
if (!particle) {
|
|
269
|
-
continue;
|
|
270
|
-
}
|
|
271
|
-
if (particle.alpha < 0.01 || particle.size <= 0.5) {
|
|
272
|
-
continue;
|
|
273
|
-
}
|
|
274
|
-
this._effect.update(this._ctx, particle);
|
|
275
|
-
}
|
|
276
|
-
}
|
|
277
|
-
};
|
|
278
|
-
var Effect = class {
|
|
279
|
-
constructor(_options) {
|
|
280
|
-
this._options = _options;
|
|
281
|
-
}
|
|
282
|
-
};
|
|
283
|
-
var Effect1 = class extends Effect {
|
|
284
|
-
create(x, y, color) {
|
|
285
|
-
return {
|
|
286
|
-
x,
|
|
287
|
-
y: y + 10,
|
|
288
|
-
vx: random(this._options.particleVelocityRange.x[0], this._options.particleVelocityRange.x[1]),
|
|
289
|
-
vy: random(this._options.particleVelocityRange.y[0], this._options.particleVelocityRange.y[1]),
|
|
290
|
-
size: random(this._options.particleSize.min, this._options.particleSize.max),
|
|
291
|
-
color,
|
|
292
|
-
alpha: 1
|
|
293
|
-
};
|
|
294
|
-
}
|
|
295
|
-
update(ctx, particle) {
|
|
296
|
-
particle.vy += this._options.particleGravity;
|
|
297
|
-
particle.x += particle.vx;
|
|
298
|
-
particle.y += particle.vy;
|
|
299
|
-
particle.alpha *= this._options.particleAlphaFadeout;
|
|
300
|
-
ctx.fillStyle = `rgba(${particle.color[0]},${particle.color[1]},${particle.color[2]},${particle.alpha})`;
|
|
301
|
-
ctx.fillRect(Math.round(particle.x - 1), Math.round(particle.y - 1), particle.size, particle.size);
|
|
302
|
-
}
|
|
303
|
-
};
|
|
304
|
-
var Effect2 = class extends Effect {
|
|
305
|
-
create(x, y, color) {
|
|
306
|
-
return {
|
|
307
|
-
x,
|
|
308
|
-
y: y + 10,
|
|
309
|
-
vx: random(this._options.particleVelocityRange.x[0], this._options.particleVelocityRange.x[1]),
|
|
310
|
-
vy: random(this._options.particleVelocityRange.y[0], this._options.particleVelocityRange.y[1]),
|
|
311
|
-
size: random(this._options.particleSize.min, this._options.particleSize.max),
|
|
312
|
-
color,
|
|
313
|
-
alpha: 1,
|
|
314
|
-
theta: random(0, 360) * Math.PI / 180,
|
|
315
|
-
drag: 0.92,
|
|
316
|
-
wander: 0.15
|
|
317
|
-
};
|
|
318
|
-
}
|
|
319
|
-
update(ctx, particle) {
|
|
320
|
-
particle.vy += this._options.particleGravity;
|
|
321
|
-
particle.x += particle.vx;
|
|
322
|
-
particle.y += particle.vy;
|
|
323
|
-
particle.vx *= particle.drag;
|
|
324
|
-
particle.vy *= particle.drag;
|
|
325
|
-
particle.theta += random(-0.5, 0.5);
|
|
326
|
-
particle.vx += Math.sin(particle.theta) * 0.1;
|
|
327
|
-
particle.vy += Math.cos(particle.theta) * 0.1;
|
|
328
|
-
particle.size *= this._options.particleShrinkRate;
|
|
329
|
-
particle.alpha *= this._options.particleAlphaFadeout;
|
|
330
|
-
ctx.fillStyle = `rgba(${particle.color[0]},${particle.color[1]},${particle.color[2]},${particle.alpha})`;
|
|
331
|
-
ctx.beginPath();
|
|
332
|
-
ctx.arc(Math.round(particle.x - 1), Math.round(particle.y - 1), particle.size, 0, 2 * Math.PI);
|
|
333
|
-
ctx.fill();
|
|
334
|
-
}
|
|
335
|
-
};
|
|
336
|
-
function throttle(callback, limit) {
|
|
337
|
-
let wait = false;
|
|
338
|
-
return function(...args) {
|
|
339
|
-
if (!wait) {
|
|
340
|
-
callback.apply(this, args);
|
|
341
|
-
wait = true;
|
|
342
|
-
setTimeout(() => {
|
|
343
|
-
wait = false;
|
|
344
|
-
}, limit);
|
|
345
|
-
}
|
|
346
|
-
};
|
|
347
|
-
}
|
|
348
|
-
var getRGBComponents = (node, color) => {
|
|
349
|
-
if (typeof color === "function") {
|
|
350
|
-
return color();
|
|
351
|
-
}
|
|
352
|
-
const bgColor = getComputedStyle(node).color;
|
|
353
|
-
if (bgColor) {
|
|
354
|
-
const x = bgColor.match(/(\d+), (\d+), (\d+)/)?.slice(1);
|
|
355
|
-
if (x) {
|
|
356
|
-
return x;
|
|
357
|
-
}
|
|
358
|
-
}
|
|
359
|
-
return [
|
|
360
|
-
50,
|
|
361
|
-
50,
|
|
362
|
-
50
|
|
363
|
-
];
|
|
364
|
-
};
|
|
365
|
-
var random = (min, max) => {
|
|
366
|
-
if (!max) {
|
|
367
|
-
max = min;
|
|
368
|
-
min = 0;
|
|
369
|
-
}
|
|
370
|
-
return min + ~~(Math.random() * (max - min + 1));
|
|
371
|
-
};
|
|
372
|
-
|
|
373
57
|
// packages/ui/react-ui-editor/src/components/TextEditor/extensions/demo.ts
|
|
374
|
-
import { keymap as
|
|
58
|
+
import { keymap as keymap2 } from "@codemirror/view";
|
|
375
59
|
var defaultItems = [
|
|
376
60
|
"hello world!",
|
|
377
61
|
"this is a test.",
|
|
@@ -381,7 +65,7 @@ var demo = ({ delay = 75, items = defaultItems } = {}) => {
|
|
|
381
65
|
let t;
|
|
382
66
|
let idx = 0;
|
|
383
67
|
return [
|
|
384
|
-
|
|
68
|
+
keymap2.of([
|
|
385
69
|
{
|
|
386
70
|
// Reset.
|
|
387
71
|
key: "alt-meta-'",
|
|
@@ -428,17 +112,17 @@ var demo = ({ delay = 75, items = defaultItems } = {}) => {
|
|
|
428
112
|
};
|
|
429
113
|
|
|
430
114
|
// packages/ui/react-ui-editor/src/components/TextEditor/extensions/comments.ts
|
|
431
|
-
import { keymap as
|
|
115
|
+
import { keymap as keymap3, Decoration, EditorView as EditorView2, MatchDecorator, ViewPlugin, WidgetType } from "@codemirror/view";
|
|
432
116
|
import { debounce } from "@dxos/async";
|
|
433
|
-
import { invariant
|
|
434
|
-
var
|
|
117
|
+
import { invariant } from "@dxos/invariant";
|
|
118
|
+
var __dxlog_file = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/components/TextEditor/extensions/comments.ts";
|
|
435
119
|
var BookmarkWidget = class extends WidgetType {
|
|
436
120
|
constructor(_pos, _id) {
|
|
437
121
|
super();
|
|
438
122
|
this._pos = _pos;
|
|
439
123
|
this._id = _id;
|
|
440
|
-
|
|
441
|
-
F:
|
|
124
|
+
invariant(this._id, void 0, {
|
|
125
|
+
F: __dxlog_file,
|
|
442
126
|
L: 41,
|
|
443
127
|
S: this,
|
|
444
128
|
A: [
|
|
@@ -457,7 +141,7 @@ var BookmarkWidget = class extends WidgetType {
|
|
|
457
141
|
return span;
|
|
458
142
|
}
|
|
459
143
|
};
|
|
460
|
-
var styles =
|
|
144
|
+
var styles = EditorView2.baseTheme({
|
|
461
145
|
"& .cm-bookmark": {
|
|
462
146
|
cursor: "pointer",
|
|
463
147
|
margin: "4px",
|
|
@@ -484,12 +168,12 @@ var comments = (options = {}) => {
|
|
|
484
168
|
constructor(view) {
|
|
485
169
|
this.bookmarks = bookmarkMatcher.createDeco(view);
|
|
486
170
|
}
|
|
487
|
-
update(
|
|
488
|
-
this.bookmarks = bookmarkMatcher.updateDeco(
|
|
171
|
+
update(update2) {
|
|
172
|
+
this.bookmarks = bookmarkMatcher.updateDeco(update2, this.bookmarks);
|
|
489
173
|
}
|
|
490
174
|
}, {
|
|
491
175
|
decorations: (instance) => instance.bookmarks,
|
|
492
|
-
provide: (plugin) =>
|
|
176
|
+
provide: (plugin) => EditorView2.atomicRanges.of((view) => {
|
|
493
177
|
return view.plugin(plugin)?.bookmarks || Decoration.none;
|
|
494
178
|
})
|
|
495
179
|
});
|
|
@@ -497,7 +181,7 @@ var comments = (options = {}) => {
|
|
|
497
181
|
options.onUpdate?.(data);
|
|
498
182
|
}, 200);
|
|
499
183
|
return [
|
|
500
|
-
|
|
184
|
+
keymap3.of([
|
|
501
185
|
{
|
|
502
186
|
key: options?.key ?? "shift-meta-c",
|
|
503
187
|
run: (view) => {
|
|
@@ -522,12 +206,12 @@ var comments = (options = {}) => {
|
|
|
522
206
|
]),
|
|
523
207
|
bookmarks,
|
|
524
208
|
// Monitor cursor movement.
|
|
525
|
-
|
|
209
|
+
EditorView2.updateListener.of((update2) => {
|
|
526
210
|
active = void 0;
|
|
527
211
|
if (!options.onUpdate) {
|
|
528
212
|
return;
|
|
529
213
|
}
|
|
530
|
-
const view =
|
|
214
|
+
const view = update2.view;
|
|
531
215
|
const pos = view.state.selection.main.head;
|
|
532
216
|
const decorations = [];
|
|
533
217
|
const rangeSet = view.plugin(bookmarks)?.bookmarks;
|
|
@@ -563,62 +247,11 @@ var comments = (options = {}) => {
|
|
|
563
247
|
];
|
|
564
248
|
};
|
|
565
249
|
|
|
566
|
-
// packages/ui/react-ui-editor/src/components/TextEditor/extensions/image.ts
|
|
567
|
-
import { syntaxTree } from "@codemirror/language";
|
|
568
|
-
import { RangeSetBuilder, StateField as StateField2 } from "@codemirror/state";
|
|
569
|
-
import { Decoration as Decoration2, EditorView as EditorView4, WidgetType as WidgetType2 } from "@codemirror/view";
|
|
570
|
-
var image = (options = {}) => {
|
|
571
|
-
return StateField2.define({
|
|
572
|
-
create: (state) => update(state, options),
|
|
573
|
-
update: (_, tr) => update(tr.state, options),
|
|
574
|
-
provide: (field) => EditorView4.decorations.from(field)
|
|
575
|
-
});
|
|
576
|
-
};
|
|
577
|
-
var update = (state, options) => {
|
|
578
|
-
const builder = new RangeSetBuilder();
|
|
579
|
-
syntaxTree(state).iterate({
|
|
580
|
-
enter: (node) => {
|
|
581
|
-
if (node.name === "Image") {
|
|
582
|
-
const urlNode = node.node.getChild("URL");
|
|
583
|
-
if (urlNode) {
|
|
584
|
-
const url = state.sliceDoc(urlNode.from, urlNode.to);
|
|
585
|
-
builder.add(state.readOnly ? node.from : node.to, node.to, Decoration2.widget({
|
|
586
|
-
widget: new ImageWidget(url)
|
|
587
|
-
}));
|
|
588
|
-
}
|
|
589
|
-
}
|
|
590
|
-
}
|
|
591
|
-
});
|
|
592
|
-
return builder.finish();
|
|
593
|
-
};
|
|
594
|
-
var ImageWidget = class extends WidgetType2 {
|
|
595
|
-
constructor(_url) {
|
|
596
|
-
super();
|
|
597
|
-
this._url = _url;
|
|
598
|
-
}
|
|
599
|
-
eq(other) {
|
|
600
|
-
return this._url === other?._url;
|
|
601
|
-
}
|
|
602
|
-
toDOM(view) {
|
|
603
|
-
const img = document.createElement("img");
|
|
604
|
-
img.setAttribute("src", this._url);
|
|
605
|
-
img.setAttribute("class", "cm-image");
|
|
606
|
-
return img;
|
|
607
|
-
}
|
|
608
|
-
};
|
|
609
|
-
|
|
610
250
|
// packages/ui/react-ui-editor/src/components/TextEditor/extensions/link.ts
|
|
611
|
-
import { syntaxTree
|
|
612
|
-
import { RangeSetBuilder
|
|
613
|
-
import { Decoration as
|
|
614
|
-
var
|
|
615
|
-
return StateField3.define({
|
|
616
|
-
create: (state) => update2(state, options),
|
|
617
|
-
update: (_, tr) => update2(tr.state, options),
|
|
618
|
-
provide: (field) => EditorView5.decorations.from(field)
|
|
619
|
-
});
|
|
620
|
-
};
|
|
621
|
-
var LinkButton = class extends WidgetType3 {
|
|
251
|
+
import { syntaxTree } from "@codemirror/language";
|
|
252
|
+
import { RangeSetBuilder, StateField } from "@codemirror/state";
|
|
253
|
+
import { Decoration as Decoration2, EditorView as EditorView3, WidgetType as WidgetType2 } from "@codemirror/view";
|
|
254
|
+
var LinkButton = class extends WidgetType2 {
|
|
622
255
|
constructor(_pos, _url, _onAttach) {
|
|
623
256
|
super();
|
|
624
257
|
this._pos = _pos;
|
|
@@ -634,7 +267,7 @@ var LinkButton = class extends WidgetType3 {
|
|
|
634
267
|
return el;
|
|
635
268
|
}
|
|
636
269
|
};
|
|
637
|
-
var LinkText = class extends
|
|
270
|
+
var LinkText = class extends WidgetType2 {
|
|
638
271
|
constructor(_pos, _text, _url) {
|
|
639
272
|
super();
|
|
640
273
|
this._pos = _pos;
|
|
@@ -664,10 +297,10 @@ var LinkText = class extends WidgetType3 {
|
|
|
664
297
|
return link2;
|
|
665
298
|
}
|
|
666
299
|
};
|
|
667
|
-
var
|
|
668
|
-
const builder = new
|
|
300
|
+
var update = (state, options) => {
|
|
301
|
+
const builder = new RangeSetBuilder();
|
|
669
302
|
const cursor = state.selection.main.head;
|
|
670
|
-
|
|
303
|
+
syntaxTree(state).iterate({
|
|
671
304
|
enter: (node) => {
|
|
672
305
|
if (node.name === "Link") {
|
|
673
306
|
const marks = node.node.getChildren("LinkMark");
|
|
@@ -678,12 +311,12 @@ var update2 = (state, options) => {
|
|
|
678
311
|
return false;
|
|
679
312
|
}
|
|
680
313
|
if (cursor < node.from || cursor > node.to) {
|
|
681
|
-
builder.add(node.from, node.to,
|
|
314
|
+
builder.add(node.from, node.to, Decoration2.replace({
|
|
682
315
|
widget: new LinkText(node.from, text, options.link ? url : void 0)
|
|
683
316
|
}));
|
|
684
317
|
}
|
|
685
318
|
if (options.onRender) {
|
|
686
|
-
builder.add(node.to, node.to,
|
|
319
|
+
builder.add(node.to, node.to, Decoration2.replace({
|
|
687
320
|
widget: new LinkButton(node.from, url, options.onRender)
|
|
688
321
|
}));
|
|
689
322
|
}
|
|
@@ -693,20 +326,25 @@ var update2 = (state, options) => {
|
|
|
693
326
|
});
|
|
694
327
|
return builder.finish();
|
|
695
328
|
};
|
|
329
|
+
var link = (options = {}) => {
|
|
330
|
+
return StateField.define({
|
|
331
|
+
create: (state) => update(state, options),
|
|
332
|
+
update: (_, tr) => update(tr.state, options),
|
|
333
|
+
provide: (field) => EditorView3.decorations.from(field)
|
|
334
|
+
});
|
|
335
|
+
};
|
|
696
336
|
|
|
697
337
|
// packages/ui/react-ui-editor/src/components/TextEditor/extensions/listener.ts
|
|
698
|
-
import { StateField as
|
|
699
|
-
var listener = ({ onChange }) => {
|
|
700
|
-
|
|
701
|
-
|
|
702
|
-
|
|
703
|
-
|
|
704
|
-
onChange(transaction.newDoc.toString());
|
|
705
|
-
}
|
|
706
|
-
return null;
|
|
338
|
+
import { StateField as StateField2 } from "@codemirror/state";
|
|
339
|
+
var listener = ({ onChange }) => StateField2.define({
|
|
340
|
+
create: () => null,
|
|
341
|
+
update: (_value, transaction) => {
|
|
342
|
+
if (transaction.docChanged && onChange) {
|
|
343
|
+
onChange(transaction.newDoc.toString());
|
|
707
344
|
}
|
|
708
|
-
|
|
709
|
-
}
|
|
345
|
+
return null;
|
|
346
|
+
}
|
|
347
|
+
});
|
|
710
348
|
|
|
711
349
|
// packages/ui/react-ui-editor/src/components/TextEditor/extensions/markdown/bundle.ts
|
|
712
350
|
import { closeBrackets as closeBrackets2, closeBracketsKeymap } from "@codemirror/autocomplete";
|
|
@@ -717,46 +355,23 @@ import { languages } from "@codemirror/language-data";
|
|
|
717
355
|
import { highlightSelectionMatches, searchKeymap } from "@codemirror/search";
|
|
718
356
|
import { EditorState } from "@codemirror/state";
|
|
719
357
|
import { oneDarkHighlightStyle as oneDarkHighlightStyle2 } from "@codemirror/theme-one-dark";
|
|
720
|
-
import { crosshairCursor, drawSelection, dropCursor, EditorView as
|
|
358
|
+
import { crosshairCursor, drawSelection, dropCursor, EditorView as EditorView4, highlightActiveLine, highlightActiveLineGutter, highlightSpecialChars, keymap as keymap4, placeholder as placeholder2, rectangularSelection } from "@codemirror/view";
|
|
721
359
|
|
|
722
360
|
// packages/ui/react-ui-editor/src/components/TextEditor/extensions/markdown/highlight.ts
|
|
723
361
|
import { markdownLanguage } from "@codemirror/lang-markdown";
|
|
724
362
|
import { HighlightStyle } from "@codemirror/language";
|
|
725
363
|
import { tags, styleTags, Tag } from "@lezer/highlight";
|
|
726
364
|
import get from "lodash.get";
|
|
727
|
-
import { mx as mx2 } from "@dxos/react-ui-theme";
|
|
728
365
|
|
|
729
366
|
// packages/ui/react-ui-editor/src/styles/markdown.ts
|
|
730
367
|
import { mx } from "@dxos/react-ui-theme";
|
|
731
|
-
var
|
|
732
|
-
1:
|
|
733
|
-
|
|
734
|
-
|
|
735
|
-
|
|
736
|
-
|
|
737
|
-
|
|
738
|
-
"-ml-1.5"
|
|
739
|
-
],
|
|
740
|
-
3: [
|
|
741
|
-
"mbs-4 mbe-2 font-medium text-inherit no-underline text-2xl",
|
|
742
|
-
"-ml-1.5"
|
|
743
|
-
],
|
|
744
|
-
4: [
|
|
745
|
-
"mbs-4 mbe-2 font-medium text-inherit no-underline text-xl",
|
|
746
|
-
"-ml-[5px]"
|
|
747
|
-
],
|
|
748
|
-
5: [
|
|
749
|
-
"mbs-4 mbe-2 font-medium text-inherit no-underline text-lg",
|
|
750
|
-
"-ml-[5px]"
|
|
751
|
-
],
|
|
752
|
-
6: [
|
|
753
|
-
"mbs-4 mbe-2 font-medium text-inherit no-underline",
|
|
754
|
-
"-ml-[4px]"
|
|
755
|
-
]
|
|
756
|
-
};
|
|
757
|
-
var heading = (level, readonly) => {
|
|
758
|
-
const [style, offset] = headings[level];
|
|
759
|
-
return mx(style, readonly && offset);
|
|
368
|
+
var heading = {
|
|
369
|
+
1: "mbs-4 mbe-2 font-medium text-inherit no-underline text-4xl",
|
|
370
|
+
2: "mbs-4 mbe-2 font-medium text-inherit no-underline text-3xl",
|
|
371
|
+
3: "mbs-4 mbe-2 font-medium text-inherit no-underline text-2xl",
|
|
372
|
+
4: "mbs-4 mbe-2 font-medium text-inherit no-underline text-xl",
|
|
373
|
+
5: "mbs-4 mbe-2 font-medium text-inherit no-underline text-lg",
|
|
374
|
+
6: "mbs-4 mbe-2 font-medium text-inherit no-underline"
|
|
760
375
|
};
|
|
761
376
|
var light = "text-neutral-200 dark:text-neutral-800";
|
|
762
377
|
var mark = mx("!font-normal !no-underline !text-inherit opacity-40", light);
|
|
@@ -767,7 +382,7 @@ var code = "font-mono !no-underline text-neutral-700 dark:text-neutral-300";
|
|
|
767
382
|
var codeMark = "font-mono text-primary-500";
|
|
768
383
|
var inlineUrl = mx(code, "px-1");
|
|
769
384
|
var blockquote = mx("pl-1 mr-1 border-is-4 border-primary-500/70 dark:border-primary-500/30", light);
|
|
770
|
-
var horizontalRule = "flex mlb-4 border-b text-neutral-100 dark:text-neutral-900 border-neutral-
|
|
385
|
+
var horizontalRule = "flex mlb-4 border-b text-neutral-100 dark:text-neutral-900 border-neutral-500/50";
|
|
771
386
|
|
|
772
387
|
// packages/ui/react-ui-editor/src/styles/tokens.ts
|
|
773
388
|
import { tailwindConfig } from "@dxos/react-ui-theme";
|
|
@@ -793,7 +408,7 @@ var markdownTagsExtension = {
|
|
|
793
408
|
styleTags(markdownTags)
|
|
794
409
|
]
|
|
795
410
|
};
|
|
796
|
-
var markdownHighlightStyle =
|
|
411
|
+
var markdownHighlightStyle = HighlightStyle.define([
|
|
797
412
|
{
|
|
798
413
|
tag: [
|
|
799
414
|
tags.keyword,
|
|
@@ -837,54 +452,40 @@ var markdownHighlightStyle = (readonly) => HighlightStyle.define([
|
|
|
837
452
|
tag: [
|
|
838
453
|
tags.meta,
|
|
839
454
|
tags.processingInstruction,
|
|
455
|
+
markdownTags.CodeMark,
|
|
456
|
+
markdownTags.EmphasisMark,
|
|
457
|
+
markdownTags.HeaderMark,
|
|
840
458
|
markdownTags.LinkLabel,
|
|
841
459
|
markdownTags.LinkReference,
|
|
842
|
-
markdownTags.ListMark
|
|
460
|
+
markdownTags.ListMark,
|
|
461
|
+
markdownTags.QuoteMark
|
|
843
462
|
],
|
|
844
463
|
class: mark
|
|
845
464
|
},
|
|
846
|
-
// Markdown marks.
|
|
847
|
-
{
|
|
848
|
-
tag: [
|
|
849
|
-
markdownTags.CodeMark,
|
|
850
|
-
markdownTags.HeaderMark,
|
|
851
|
-
markdownTags.QuoteMark,
|
|
852
|
-
markdownTags.EmphasisMark
|
|
853
|
-
],
|
|
854
|
-
class: readonly ? "hidden" : mark
|
|
855
|
-
},
|
|
856
|
-
// E.g., code block language (after ```).
|
|
857
|
-
{
|
|
858
|
-
tag: [
|
|
859
|
-
tags.function(tags.variableName),
|
|
860
|
-
tags.labelName
|
|
861
|
-
],
|
|
862
|
-
class: readonly ? "hidden" : codeMark
|
|
863
|
-
},
|
|
864
465
|
// Headings.
|
|
865
466
|
{
|
|
866
467
|
tag: tags.heading1,
|
|
867
|
-
class: heading
|
|
468
|
+
class: heading[1]
|
|
868
469
|
},
|
|
869
470
|
{
|
|
870
471
|
tag: tags.heading2,
|
|
871
|
-
class: heading
|
|
472
|
+
class: heading[2]
|
|
872
473
|
},
|
|
873
474
|
{
|
|
874
475
|
tag: tags.heading3,
|
|
875
|
-
class: heading
|
|
476
|
+
class: heading[3]
|
|
876
477
|
},
|
|
877
478
|
{
|
|
878
479
|
tag: tags.heading4,
|
|
879
|
-
class: heading
|
|
480
|
+
class: heading[4]
|
|
880
481
|
},
|
|
881
482
|
{
|
|
882
483
|
tag: tags.heading5,
|
|
883
|
-
class: heading
|
|
484
|
+
class: heading[5]
|
|
884
485
|
},
|
|
885
486
|
{
|
|
886
487
|
tag: tags.heading6,
|
|
887
|
-
class: heading
|
|
488
|
+
class: heading[6]
|
|
888
489
|
},
|
|
889
490
|
// Emphasis.
|
|
890
491
|
{
|
|
@@ -906,6 +507,14 @@ var markdownHighlightStyle = (readonly) => HighlightStyle.define([
|
|
|
906
507
|
],
|
|
907
508
|
class: inlineUrl
|
|
908
509
|
},
|
|
510
|
+
// E.g., code block language (after ```).
|
|
511
|
+
{
|
|
512
|
+
tag: [
|
|
513
|
+
tags.function(tags.variableName),
|
|
514
|
+
tags.labelName
|
|
515
|
+
],
|
|
516
|
+
class: codeMark
|
|
517
|
+
},
|
|
909
518
|
// NOTE: The `markdown` extension configures extensions for `lezer` to parse markdown tokens (incl. below).
|
|
910
519
|
// However, since `codeLanguages` is also defined, the `lezer` will not parse fenced code blocks,
|
|
911
520
|
// when a language is specified. In this case, the syntax highlighting extensions will colorize
|
|
@@ -928,7 +537,7 @@ var markdownHighlightStyle = (readonly) => HighlightStyle.define([
|
|
|
928
537
|
tag: [
|
|
929
538
|
markdownTags.HorizontalRule
|
|
930
539
|
],
|
|
931
|
-
class:
|
|
540
|
+
class: horizontalRule
|
|
932
541
|
}
|
|
933
542
|
], {
|
|
934
543
|
scope: markdownLanguage,
|
|
@@ -938,13 +547,13 @@ var markdownHighlightStyle = (readonly) => HighlightStyle.define([
|
|
|
938
547
|
});
|
|
939
548
|
|
|
940
549
|
// packages/ui/react-ui-editor/src/components/TextEditor/extensions/markdown/bundle.ts
|
|
941
|
-
var markdownBundle = ({
|
|
550
|
+
var markdownBundle = ({ themeMode, placeholder: _placeholder }) => {
|
|
942
551
|
return [
|
|
943
552
|
bracketMatching2(),
|
|
944
553
|
closeBrackets2(),
|
|
945
554
|
_placeholder && placeholder2(_placeholder),
|
|
946
555
|
EditorState.allowMultipleSelections.of(true),
|
|
947
|
-
|
|
556
|
+
EditorView4.lineWrapping,
|
|
948
557
|
crosshairCursor(),
|
|
949
558
|
dropCursor(),
|
|
950
559
|
drawSelection(),
|
|
@@ -956,7 +565,7 @@ var markdownBundle = ({ readonly, themeMode, placeholder: _placeholder }) => {
|
|
|
956
565
|
indentOnInput(),
|
|
957
566
|
rectangularSelection(),
|
|
958
567
|
// https://codemirror.net/docs/ref/#view.keymap
|
|
959
|
-
|
|
568
|
+
keymap4.of([
|
|
960
569
|
// https://codemirror.net/docs/ref/#commands.defaultKeymap
|
|
961
570
|
...defaultKeymap,
|
|
962
571
|
// https://codemirror.net/docs/ref/#commands.historyKeymap
|
|
@@ -986,132 +595,16 @@ var markdownBundle = ({ readonly, themeMode, placeholder: _placeholder }) => {
|
|
|
986
595
|
markdownTagsExtension
|
|
987
596
|
]
|
|
988
597
|
}),
|
|
989
|
-
// https://github.com/codemirror/theme-one-dark
|
|
990
|
-
themeMode === "dark" ? syntaxHighlighting2(oneDarkHighlightStyle2) : syntaxHighlighting2(defaultHighlightStyle2),
|
|
991
598
|
// Custom styles.
|
|
992
|
-
syntaxHighlighting2(markdownHighlightStyle
|
|
599
|
+
syntaxHighlighting2(markdownHighlightStyle),
|
|
600
|
+
// TODO(thure): All but one rule here apply to both themes; rename or refactor.
|
|
601
|
+
themeMode === "dark" ? syntaxHighlighting2(oneDarkHighlightStyle2) : syntaxHighlighting2(defaultHighlightStyle2)
|
|
993
602
|
].filter(Boolean);
|
|
994
603
|
};
|
|
995
604
|
|
|
996
|
-
// packages/ui/react-ui-editor/src/components/TextEditor/extensions/mention.ts
|
|
997
|
-
import { autocompletion as autocompletion2 } from "@codemirror/autocomplete";
|
|
998
|
-
var mention = ({ onSearch }) => {
|
|
999
|
-
return autocompletion2({
|
|
1000
|
-
closeOnBlur: false,
|
|
1001
|
-
override: [
|
|
1002
|
-
(context) => {
|
|
1003
|
-
const match = context.matchBefore(/@(\w+)?/);
|
|
1004
|
-
if (!match || match.from === match.to && !context.explicit) {
|
|
1005
|
-
return null;
|
|
1006
|
-
}
|
|
1007
|
-
console.log(match);
|
|
1008
|
-
return {
|
|
1009
|
-
from: match.from,
|
|
1010
|
-
options: onSearch(match.text.slice(1).toLowerCase()).map((value) => ({
|
|
1011
|
-
label: `@${value}`
|
|
1012
|
-
}))
|
|
1013
|
-
};
|
|
1014
|
-
}
|
|
1015
|
-
]
|
|
1016
|
-
});
|
|
1017
|
-
};
|
|
1018
|
-
|
|
1019
|
-
// packages/ui/react-ui-editor/src/components/TextEditor/extensions/table.ts
|
|
1020
|
-
import { syntaxTree as syntaxTree3 } from "@codemirror/language";
|
|
1021
|
-
import { RangeSetBuilder as RangeSetBuilder3, StateField as StateField5 } from "@codemirror/state";
|
|
1022
|
-
import { Decoration as Decoration4, EditorView as EditorView7, WidgetType as WidgetType4 } from "@codemirror/view";
|
|
1023
|
-
var table = (options = {}) => {
|
|
1024
|
-
return StateField5.define({
|
|
1025
|
-
create: (state) => update3(state, options),
|
|
1026
|
-
update: (_, tr) => update3(tr.state, options),
|
|
1027
|
-
provide: (field) => EditorView7.decorations.from(field)
|
|
1028
|
-
});
|
|
1029
|
-
};
|
|
1030
|
-
var update3 = (state, options) => {
|
|
1031
|
-
const builder = new RangeSetBuilder3();
|
|
1032
|
-
if (state.readOnly) {
|
|
1033
|
-
const tables = [];
|
|
1034
|
-
const getTable = () => tables[tables.length - 1];
|
|
1035
|
-
const getRow = () => {
|
|
1036
|
-
const table2 = getTable();
|
|
1037
|
-
return table2.rows?.[table2.rows.length - 1];
|
|
1038
|
-
};
|
|
1039
|
-
syntaxTree3(state).iterate({
|
|
1040
|
-
enter: (node) => {
|
|
1041
|
-
switch (node.name) {
|
|
1042
|
-
case "Table": {
|
|
1043
|
-
tables.push({
|
|
1044
|
-
from: node.from
|
|
1045
|
-
});
|
|
1046
|
-
break;
|
|
1047
|
-
}
|
|
1048
|
-
case "TableHeader": {
|
|
1049
|
-
getTable().header = [];
|
|
1050
|
-
break;
|
|
1051
|
-
}
|
|
1052
|
-
case "TableRow": {
|
|
1053
|
-
(getTable().rows ??= []).push([]);
|
|
1054
|
-
break;
|
|
1055
|
-
}
|
|
1056
|
-
case "TableCell": {
|
|
1057
|
-
const row = getRow();
|
|
1058
|
-
if (row) {
|
|
1059
|
-
row.push(state.sliceDoc(node.from, node.to));
|
|
1060
|
-
} else {
|
|
1061
|
-
getTable().header?.push(state.sliceDoc(node.from, node.to));
|
|
1062
|
-
}
|
|
1063
|
-
break;
|
|
1064
|
-
}
|
|
1065
|
-
case "TableDelimiter": {
|
|
1066
|
-
getTable().to = node.to;
|
|
1067
|
-
break;
|
|
1068
|
-
}
|
|
1069
|
-
}
|
|
1070
|
-
}
|
|
1071
|
-
});
|
|
1072
|
-
tables.forEach((table2) => builder.add(table2.from, table2.to, Decoration4.replace({
|
|
1073
|
-
widget: new TableWidget(table2)
|
|
1074
|
-
})));
|
|
1075
|
-
}
|
|
1076
|
-
return builder.finish();
|
|
1077
|
-
};
|
|
1078
|
-
var TableWidget = class extends WidgetType4 {
|
|
1079
|
-
constructor(_table) {
|
|
1080
|
-
super();
|
|
1081
|
-
this._table = _table;
|
|
1082
|
-
}
|
|
1083
|
-
eq(other) {
|
|
1084
|
-
return this._table.from === other?._table?.from;
|
|
1085
|
-
}
|
|
1086
|
-
toDOM(view) {
|
|
1087
|
-
const table2 = document.createElement("table");
|
|
1088
|
-
{
|
|
1089
|
-
const header = table2.appendChild(document.createElement("thead"));
|
|
1090
|
-
const row = header.appendChild(document.createElement("tr"));
|
|
1091
|
-
this._table.header?.forEach((cell) => {
|
|
1092
|
-
const th = document.createElement("th");
|
|
1093
|
-
th.setAttribute("class", "cm-table-head");
|
|
1094
|
-
row.appendChild(th).textContent = cell;
|
|
1095
|
-
});
|
|
1096
|
-
}
|
|
1097
|
-
{
|
|
1098
|
-
const body = table2.appendChild(document.createElement("tbody"));
|
|
1099
|
-
this._table.rows?.forEach((row) => {
|
|
1100
|
-
const tr = body.appendChild(document.createElement("tr"));
|
|
1101
|
-
row.forEach((cell) => {
|
|
1102
|
-
const td = document.createElement("td");
|
|
1103
|
-
td.setAttribute("class", "cm-table-cell");
|
|
1104
|
-
tr.appendChild(td).textContent = cell;
|
|
1105
|
-
});
|
|
1106
|
-
});
|
|
1107
|
-
}
|
|
1108
|
-
return table2;
|
|
1109
|
-
}
|
|
1110
|
-
};
|
|
1111
|
-
|
|
1112
605
|
// packages/ui/react-ui-editor/src/components/TextEditor/extensions/tasklist.ts
|
|
1113
|
-
import { EditorView as
|
|
1114
|
-
var CheckboxWidget = class extends
|
|
606
|
+
import { EditorView as EditorView5, Decoration as Decoration3, WidgetType as WidgetType3, MatchDecorator as MatchDecorator2, ViewPlugin as ViewPlugin2 } from "@codemirror/view";
|
|
607
|
+
var CheckboxWidget = class extends WidgetType3 {
|
|
1115
608
|
constructor(_pos, _checked, _indent, _onCheck) {
|
|
1116
609
|
super();
|
|
1117
610
|
this._pos = _pos;
|
|
@@ -1130,35 +623,30 @@ var CheckboxWidget = class extends WidgetType5 {
|
|
|
1130
623
|
const input = wrap.appendChild(document.createElement("input"));
|
|
1131
624
|
input.type = "checkbox";
|
|
1132
625
|
input.checked = this._checked;
|
|
1133
|
-
|
|
1134
|
-
|
|
1135
|
-
|
|
1136
|
-
|
|
1137
|
-
input.onchange = (event) => {
|
|
1138
|
-
this._onCheck?.(event.target.checked);
|
|
1139
|
-
return true;
|
|
1140
|
-
};
|
|
1141
|
-
}
|
|
626
|
+
input.onchange = (event) => {
|
|
627
|
+
this._onCheck(event.target.checked);
|
|
628
|
+
return true;
|
|
629
|
+
};
|
|
1142
630
|
return wrap;
|
|
1143
631
|
}
|
|
1144
632
|
ignoreEvent() {
|
|
1145
633
|
return false;
|
|
1146
634
|
}
|
|
1147
635
|
};
|
|
1148
|
-
var styles2 =
|
|
636
|
+
var styles2 = EditorView5.baseTheme({
|
|
1149
637
|
"& .cm-task-item": {
|
|
1150
638
|
paddingLeft: "4px",
|
|
1151
639
|
paddingRight: "8px"
|
|
1152
640
|
}
|
|
1153
641
|
});
|
|
1154
|
-
var tasklist = (
|
|
642
|
+
var tasklist = () => {
|
|
1155
643
|
const taskMatcher = new MatchDecorator2({
|
|
1156
644
|
regexp: /^(\s*)- \[([ xX])\]\s/g,
|
|
1157
645
|
decoration: (match, view, pos) => {
|
|
1158
646
|
const indent = Math.floor(match[1].length / 2);
|
|
1159
647
|
const checked = match[2] === "x" || match[2] === "X";
|
|
1160
|
-
return
|
|
1161
|
-
widget: new CheckboxWidget(pos, checked, indent,
|
|
648
|
+
return Decoration3.replace({
|
|
649
|
+
widget: new CheckboxWidget(pos, checked, indent, (checked2) => {
|
|
1162
650
|
const idx = pos + match[0].indexOf("[") + 1;
|
|
1163
651
|
view.dispatch({
|
|
1164
652
|
changes: {
|
|
@@ -1179,13 +667,13 @@ var tasklist = (options = {}) => {
|
|
|
1179
667
|
constructor(view) {
|
|
1180
668
|
this.tasks = taskMatcher.createDeco(view);
|
|
1181
669
|
}
|
|
1182
|
-
update(
|
|
1183
|
-
this.tasks = taskMatcher.updateDeco(
|
|
670
|
+
update(update2) {
|
|
671
|
+
this.tasks = taskMatcher.updateDeco(update2, this.tasks);
|
|
1184
672
|
}
|
|
1185
673
|
}, {
|
|
1186
674
|
decorations: (instance) => instance.tasks,
|
|
1187
|
-
provide: (plugin) =>
|
|
1188
|
-
return view.plugin(plugin)?.tasks ||
|
|
675
|
+
provide: (plugin) => EditorView5.atomicRanges.of((view) => {
|
|
676
|
+
return view.plugin(plugin)?.tasks || Decoration3.none;
|
|
1189
677
|
})
|
|
1190
678
|
});
|
|
1191
679
|
return [
|
|
@@ -1352,51 +840,8 @@ var defaultTheme = {
|
|
|
1352
840
|
"& .cm-tooltip": {
|
|
1353
841
|
border: "none"
|
|
1354
842
|
},
|
|
1355
|
-
|
|
1356
|
-
//
|
|
1357
|
-
// autocomplete
|
|
1358
|
-
//
|
|
1359
|
-
"& .cm-tooltip-autocomplete": {
|
|
1360
|
-
marginTop: "4px",
|
|
1361
|
-
marginLeft: "-3px"
|
|
1362
|
-
},
|
|
1363
|
-
"& .cm-tooltip-autocomplete ul li": {},
|
|
1364
|
-
"& .cm-tooltip-autocomplete ul li[aria-selected]": {},
|
|
1365
|
-
"& .cm-completionIcon": {
|
|
1366
|
-
display: "none"
|
|
1367
|
-
},
|
|
1368
|
-
"& .cm-completionLabel": {
|
|
1369
|
-
fontFamily: get2(tokens, "fontFamily.body", []).join(",")
|
|
1370
|
-
},
|
|
1371
|
-
"& .cm-completionMatchedText": {
|
|
1372
|
-
textDecoration: "none"
|
|
1373
|
-
},
|
|
1374
|
-
//
|
|
1375
|
-
// widgets
|
|
1376
|
-
//
|
|
1377
|
-
"& .cm-widgetBuffer": {
|
|
1378
|
-
display: "none",
|
|
1379
|
-
height: 0
|
|
1380
|
-
},
|
|
1381
|
-
//
|
|
1382
|
-
// table
|
|
1383
|
-
//
|
|
1384
|
-
"& .cm-table-head": {
|
|
1385
|
-
padding: "2px 16px 2px 0px",
|
|
1386
|
-
borderBottom: `1px solid ${get2(tokens, "extend.colors.neutral.500")}`,
|
|
1387
|
-
fontWeight: 100,
|
|
1388
|
-
textAlign: "left",
|
|
1389
|
-
color: get2(tokens, "extend.colors.neutral.500")
|
|
1390
|
-
},
|
|
1391
|
-
"& .cm-table-cell": {
|
|
1392
|
-
padding: "2px 16px 2px 0px"
|
|
1393
|
-
},
|
|
1394
|
-
//
|
|
1395
|
-
// image
|
|
1396
|
-
//
|
|
1397
|
-
"& .cm-image": {
|
|
1398
|
-
margin: "0.5rem 0"
|
|
1399
|
-
},
|
|
843
|
+
// '& .cm-tooltip-below': {},
|
|
844
|
+
// '& .cm-tooltip-autocomplete': {},
|
|
1400
845
|
//
|
|
1401
846
|
// font size
|
|
1402
847
|
// TODO(thure): This appears to be the best or only way to set selection caret heights, but it's far more verbose than it needs to be.
|
|
@@ -1446,19 +891,19 @@ var codeTheme = {
|
|
|
1446
891
|
|
|
1447
892
|
// packages/ui/react-ui-editor/src/components/TextEditor/TextEditor.tsx
|
|
1448
893
|
import { EditorState as EditorState2 } from "@codemirror/state";
|
|
1449
|
-
import { EditorView as
|
|
894
|
+
import { EditorView as EditorView6 } from "@codemirror/view";
|
|
1450
895
|
import { useFocusableGroup } from "@fluentui/react-tabster";
|
|
1451
896
|
import { vim } from "@replit/codemirror-vim";
|
|
1452
|
-
import
|
|
897
|
+
import defaultsDeep from "lodash.defaultsdeep";
|
|
1453
898
|
import React, { forwardRef, useCallback, useEffect, useImperativeHandle, useState } from "react";
|
|
1454
899
|
import { generateName } from "@dxos/display-name";
|
|
1455
900
|
import { useThemeContext } from "@dxos/react-ui";
|
|
1456
|
-
import { getColorForValue, inputSurface, mx as
|
|
901
|
+
import { getColorForValue, inputSurface, mx as mx2 } from "@dxos/react-ui-theme";
|
|
1457
902
|
var EditorModes = [
|
|
1458
903
|
"default",
|
|
1459
904
|
"vim"
|
|
1460
905
|
];
|
|
1461
|
-
var BaseTextEditor = /* @__PURE__ */ forwardRef(({ model,
|
|
906
|
+
var BaseTextEditor = /* @__PURE__ */ forwardRef(({ model, extensions = [], slots = defaultSlots, editorMode }, forwardedRef) => {
|
|
1462
907
|
const { themeMode } = useThemeContext();
|
|
1463
908
|
const tabsterDOMAttribute = useFocusableGroup({
|
|
1464
909
|
tabBehavior: "limited"
|
|
@@ -1503,14 +948,13 @@ var BaseTextEditor = /* @__PURE__ */ forwardRef(({ model, readonly, editorMode,
|
|
|
1503
948
|
const state2 = EditorState2.create({
|
|
1504
949
|
doc: model.text(),
|
|
1505
950
|
extensions: [
|
|
1506
|
-
readonly && EditorState2.readOnly.of(readonly),
|
|
1507
951
|
// TODO(burdon): Factor out VIM mode?
|
|
1508
952
|
editorMode === "vim" && vim(),
|
|
1509
953
|
// Theme.
|
|
1510
|
-
|
|
1511
|
-
|
|
954
|
+
EditorView6.baseTheme(defaultTheme),
|
|
955
|
+
EditorView6.theme(slots?.editor?.theme ?? {}),
|
|
1512
956
|
// TODO(burdon): themeMode doesn't change in storybooks.
|
|
1513
|
-
|
|
957
|
+
EditorView6.darkTheme.of(themeMode === "dark"),
|
|
1514
958
|
// Storage and replication.
|
|
1515
959
|
model.extension,
|
|
1516
960
|
// Custom.
|
|
@@ -1518,7 +962,7 @@ var BaseTextEditor = /* @__PURE__ */ forwardRef(({ model, readonly, editorMode,
|
|
|
1518
962
|
].filter(Boolean)
|
|
1519
963
|
});
|
|
1520
964
|
view?.destroy();
|
|
1521
|
-
setView(new
|
|
965
|
+
setView(new EditorView6({
|
|
1522
966
|
state: state2,
|
|
1523
967
|
parent: root
|
|
1524
968
|
}));
|
|
@@ -1532,7 +976,6 @@ var BaseTextEditor = /* @__PURE__ */ forwardRef(({ model, readonly, editorMode,
|
|
|
1532
976
|
root,
|
|
1533
977
|
model,
|
|
1534
978
|
themeMode,
|
|
1535
|
-
readonly,
|
|
1536
979
|
editorMode
|
|
1537
980
|
]);
|
|
1538
981
|
const handleKeyUp = useCallback((event) => {
|
|
@@ -1569,15 +1012,13 @@ var maybeDebug = () => {
|
|
|
1569
1012
|
}
|
|
1570
1013
|
return [];
|
|
1571
1014
|
};
|
|
1572
|
-
var TextEditor = /* @__PURE__ */ forwardRef(({
|
|
1015
|
+
var TextEditor = /* @__PURE__ */ forwardRef(({ extensions = [], slots: _slots, ...props }, forwardedRef) => {
|
|
1573
1016
|
const { themeMode } = useThemeContext();
|
|
1574
|
-
const slots =
|
|
1017
|
+
const slots = defaultsDeep({}, _slots, defaultTextSlots);
|
|
1575
1018
|
return /* @__PURE__ */ React.createElement(BaseTextEditor, {
|
|
1576
1019
|
ref: forwardedRef,
|
|
1577
|
-
readonly,
|
|
1578
1020
|
extensions: [
|
|
1579
1021
|
basicBundle({
|
|
1580
|
-
readonly,
|
|
1581
1022
|
themeMode,
|
|
1582
1023
|
placeholder: slots?.editor?.placeholder
|
|
1583
1024
|
}),
|
|
@@ -1588,15 +1029,13 @@ var TextEditor = /* @__PURE__ */ forwardRef(({ readonly, extensions = [], slots:
|
|
|
1588
1029
|
...props
|
|
1589
1030
|
});
|
|
1590
1031
|
});
|
|
1591
|
-
var MarkdownEditor = /* @__PURE__ */ forwardRef(({
|
|
1032
|
+
var MarkdownEditor = /* @__PURE__ */ forwardRef(({ extensions = [], slots: _slots, ...props }, forwardedRef) => {
|
|
1592
1033
|
const { themeMode } = useThemeContext();
|
|
1593
|
-
const slots =
|
|
1034
|
+
const slots = defaultsDeep({}, _slots, defaultMarkdownSlots);
|
|
1594
1035
|
return /* @__PURE__ */ React.createElement(BaseTextEditor, {
|
|
1595
1036
|
ref: forwardedRef,
|
|
1596
|
-
readonly,
|
|
1597
1037
|
extensions: [
|
|
1598
1038
|
markdownBundle({
|
|
1599
|
-
readonly,
|
|
1600
1039
|
themeMode,
|
|
1601
1040
|
placeholder: slots?.editor?.placeholder
|
|
1602
1041
|
}),
|
|
@@ -1609,7 +1048,7 @@ var MarkdownEditor = /* @__PURE__ */ forwardRef(({ readonly, extensions = [], sl
|
|
|
1609
1048
|
});
|
|
1610
1049
|
var defaultSlots = {
|
|
1611
1050
|
root: {
|
|
1612
|
-
className:
|
|
1051
|
+
className: mx2("p-2", inputSurface)
|
|
1613
1052
|
}
|
|
1614
1053
|
};
|
|
1615
1054
|
var defaultTextSlots = {
|
|
@@ -1629,11 +1068,11 @@ var defaultMarkdownSlots = {
|
|
|
1629
1068
|
import get3 from "lodash.get";
|
|
1630
1069
|
import { useEffect as useEffect2, useState as useState2 } from "react";
|
|
1631
1070
|
import { yCollab } from "y-codemirror.next";
|
|
1632
|
-
import { invariant as
|
|
1071
|
+
import { invariant as invariant2 } from "@dxos/invariant";
|
|
1633
1072
|
import { getRawDoc, isActualAutomergeObject } from "@dxos/react-client/echo";
|
|
1634
1073
|
|
|
1635
1074
|
// packages/ui/react-ui-editor/src/hooks/automerge/plugin.ts
|
|
1636
|
-
import { Annotation, Facet, StateEffect, StateField as
|
|
1075
|
+
import { Annotation, Facet, StateEffect, StateField as StateField3 } from "@codemirror/state";
|
|
1637
1076
|
import { ViewPlugin as ViewPlugin3 } from "@codemirror/view";
|
|
1638
1077
|
import * as automerge2 from "@dxos/automerge/automerge";
|
|
1639
1078
|
|
|
@@ -1822,7 +1261,7 @@ var semaphoreFacet = Facet.define({
|
|
|
1822
1261
|
combine: (values) => values.at(-1)
|
|
1823
1262
|
});
|
|
1824
1263
|
var automergePlugin = (handle, path) => {
|
|
1825
|
-
const stateField =
|
|
1264
|
+
const stateField = StateField3.define({
|
|
1826
1265
|
create: () => ({
|
|
1827
1266
|
lastHeads: automerge2.getHeads(handle.docSync()),
|
|
1828
1267
|
unreconciledTransactions: [],
|
|
@@ -1860,8 +1299,8 @@ var automergePlugin = (handle, path) => {
|
|
|
1860
1299
|
this._view = view;
|
|
1861
1300
|
handle.addListener("change", this._handleChange);
|
|
1862
1301
|
}
|
|
1863
|
-
update(
|
|
1864
|
-
if (
|
|
1302
|
+
update(update2) {
|
|
1303
|
+
if (update2.transactions.length > 0 && update2.transactions.some((t) => !isReconcileTx(t))) {
|
|
1865
1304
|
queueMicrotask(() => {
|
|
1866
1305
|
this._view.state.facet(semaphoreFacet).reconcile(handle, this._view);
|
|
1867
1306
|
});
|
|
@@ -1883,7 +1322,7 @@ var reconcileAnnotationType = Annotation.define();
|
|
|
1883
1322
|
var isReconcileTx = (tr) => !!tr.annotation(reconcileAnnotationType);
|
|
1884
1323
|
|
|
1885
1324
|
// packages/ui/react-ui-editor/src/hooks/yjs/cursors.ts
|
|
1886
|
-
import * as
|
|
1325
|
+
import * as random from "lib0/random";
|
|
1887
1326
|
var cursorColors = [
|
|
1888
1327
|
{
|
|
1889
1328
|
color: "#30bced",
|
|
@@ -1918,7 +1357,7 @@ var cursorColors = [
|
|
|
1918
1357
|
light: "#1be7ff33"
|
|
1919
1358
|
}
|
|
1920
1359
|
];
|
|
1921
|
-
var cursorColor = cursorColors[
|
|
1360
|
+
var cursorColor = cursorColors[random.uint32() % cursorColors.length];
|
|
1922
1361
|
|
|
1923
1362
|
// packages/ui/react-ui-editor/src/hooks/yjs/space-provider.ts
|
|
1924
1363
|
import * as decoding from "lib0/decoding";
|
|
@@ -1926,7 +1365,7 @@ import * as encoding from "lib0/encoding";
|
|
|
1926
1365
|
import { Observable } from "lib0/observable";
|
|
1927
1366
|
import * as awarenessProtocol from "y-protocols/awareness";
|
|
1928
1367
|
import { log } from "@dxos/log";
|
|
1929
|
-
var
|
|
1368
|
+
var __dxlog_file2 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/hooks/yjs/space-provider.ts";
|
|
1930
1369
|
var messageAwareness = 1;
|
|
1931
1370
|
var messageQueryAwareness = 3;
|
|
1932
1371
|
var SpaceAwarenessProvider = class extends Observable {
|
|
@@ -1963,7 +1402,7 @@ var SpaceAwarenessProvider = class extends Observable {
|
|
|
1963
1402
|
removed,
|
|
1964
1403
|
origin
|
|
1965
1404
|
}, {
|
|
1966
|
-
F:
|
|
1405
|
+
F: __dxlog_file2,
|
|
1967
1406
|
L: 67,
|
|
1968
1407
|
S: this,
|
|
1969
1408
|
C: (f, a) => f(...a)
|
|
@@ -1976,7 +1415,7 @@ var SpaceAwarenessProvider = class extends Observable {
|
|
|
1976
1415
|
}
|
|
1977
1416
|
_handleSpaceMessage({ payload }) {
|
|
1978
1417
|
log("space message", payload, {
|
|
1979
|
-
F:
|
|
1418
|
+
F: __dxlog_file2,
|
|
1980
1419
|
L: 79,
|
|
1981
1420
|
S: this,
|
|
1982
1421
|
C: (f, a) => f(...a)
|
|
@@ -2021,7 +1460,7 @@ var SpaceAwarenessProvider = class extends Observable {
|
|
|
2021
1460
|
};
|
|
2022
1461
|
|
|
2023
1462
|
// packages/ui/react-ui-editor/src/hooks/useTextModel.ts
|
|
2024
|
-
var
|
|
1463
|
+
var __dxlog_file3 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/hooks/useTextModel.ts";
|
|
2025
1464
|
var useTextModel = ({ identity, space, text }) => {
|
|
2026
1465
|
const [model, setModel] = useState2(() => createModel({
|
|
2027
1466
|
identity,
|
|
@@ -2053,8 +1492,8 @@ var createModel = (options) => {
|
|
|
2053
1492
|
}
|
|
2054
1493
|
};
|
|
2055
1494
|
var createYjsModel = ({ identity, space, text }) => {
|
|
2056
|
-
|
|
2057
|
-
F:
|
|
1495
|
+
invariant2(text?.doc && text?.content, void 0, {
|
|
1496
|
+
F: __dxlog_file3,
|
|
2058
1497
|
L: 74,
|
|
2059
1498
|
S: void 0,
|
|
2060
1499
|
A: [
|
|
@@ -2107,17 +1546,14 @@ export {
|
|
|
2107
1546
|
YXmlFragment,
|
|
2108
1547
|
autocomplete,
|
|
2109
1548
|
basicBundle,
|
|
2110
|
-
blast,
|
|
2111
1549
|
codeTheme,
|
|
2112
1550
|
comments,
|
|
2113
1551
|
cursorColor,
|
|
2114
1552
|
defaultMarkdownSlots,
|
|
2115
|
-
defaultOptions,
|
|
2116
1553
|
defaultSlots,
|
|
2117
1554
|
defaultTextSlots,
|
|
2118
1555
|
defaultTheme,
|
|
2119
1556
|
demo,
|
|
2120
|
-
image,
|
|
2121
1557
|
link,
|
|
2122
1558
|
listener,
|
|
2123
1559
|
markdownBundle,
|
|
@@ -2125,8 +1561,6 @@ export {
|
|
|
2125
1561
|
markdownTags,
|
|
2126
1562
|
markdownTagsExtension,
|
|
2127
1563
|
markdownTheme,
|
|
2128
|
-
mention,
|
|
2129
|
-
table,
|
|
2130
1564
|
tags2 as tags,
|
|
2131
1565
|
tasklist,
|
|
2132
1566
|
textTheme,
|