@dxos/react-ui-editor 0.6.8-main.046e6cf → 0.6.8-staging.77f93a3
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 +290 -293
- package/dist/lib/browser/index.mjs.map +4 -4
- package/dist/lib/browser/meta.json +1 -1
- package/dist/types/src/TextEditor.stories.d.ts +5 -2
- package/dist/types/src/TextEditor.stories.d.ts.map +1 -1
- package/dist/types/src/defaults.d.ts +1 -1
- package/dist/types/src/defaults.d.ts.map +1 -1
- package/dist/types/src/extensions/doc.d.ts +3 -0
- package/dist/types/src/extensions/doc.d.ts.map +1 -1
- package/dist/types/src/extensions/factories.d.ts.map +1 -1
- package/dist/types/src/extensions/folding.d.ts.map +1 -1
- package/dist/types/src/extensions/markdown/bundle.d.ts.map +1 -1
- package/dist/types/src/extensions/markdown/decorate.d.ts.map +1 -1
- package/dist/types/src/extensions/markdown/formatting.d.ts +1 -1
- package/dist/types/src/extensions/markdown/formatting.d.ts.map +1 -1
- package/dist/types/src/extensions/markdown/highlight.d.ts +2 -1
- package/dist/types/src/extensions/markdown/highlight.d.ts.map +1 -1
- package/dist/types/src/extensions/markdown/link-paste.d.ts +3 -0
- package/dist/types/src/extensions/markdown/link-paste.d.ts.map +1 -1
- package/dist/types/src/extensions/markdown/link.d.ts +3 -1
- package/dist/types/src/extensions/markdown/link.d.ts.map +1 -1
- package/dist/types/src/extensions/state.d.ts +14 -14
- package/dist/types/src/extensions/state.d.ts.map +1 -1
- package/dist/types/src/extensions/util/react.d.ts +1 -1
- package/dist/types/src/extensions/util/react.d.ts.map +1 -1
- package/dist/types/src/hooks/useTextEditor.d.ts +5 -3
- package/dist/types/src/hooks/useTextEditor.d.ts.map +1 -1
- package/dist/types/src/styles/markdown.d.ts +7 -17
- package/dist/types/src/styles/markdown.d.ts.map +1 -1
- package/dist/types/src/styles/theme.d.ts +2 -1
- package/dist/types/src/styles/theme.d.ts.map +1 -1
- package/dist/types/src/styles/tokens.d.ts +5 -7
- package/dist/types/src/styles/tokens.d.ts.map +1 -1
- package/package.json +24 -24
- package/src/TextEditor.stories.tsx +40 -27
- package/src/defaults.ts +2 -1
- package/src/extensions/doc.ts +3 -0
- package/src/extensions/factories.ts +3 -2
- package/src/extensions/folding.tsx +5 -7
- package/src/extensions/markdown/bundle.ts +1 -3
- package/src/extensions/markdown/decorate.ts +29 -23
- package/src/extensions/markdown/formatting.ts +3 -1
- package/src/extensions/markdown/highlight.ts +33 -19
- package/src/extensions/markdown/link-paste.ts +3 -0
- package/src/extensions/state.ts +41 -35
- package/src/extensions/util/react.tsx +3 -4
- package/src/hooks/useTextEditor.ts +24 -29
- package/src/styles/markdown.ts +17 -40
- package/src/styles/theme.ts +42 -49
- package/src/styles/tokens.ts +9 -7
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"useTextEditor.d.ts","sourceRoot":"","sources":["../../../../src/hooks/useTextEditor.ts"],"names":[],"mappings":"AAIA,OAAO,EAAe,KAAK,iBAAiB,EAAE,
|
|
1
|
+
{"version":3,"file":"useTextEditor.d.ts","sourceRoot":"","sources":["../../../../src/hooks/useTextEditor.ts"],"names":[],"mappings":"AAIA,OAAO,EAAe,KAAK,iBAAiB,EAAE,MAAM,mBAAmB,CAAC;AACxE,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAC9C,OAAO,EAAE,iBAAiB,EAAE,MAAM,yBAAyB,CAAC;AAC5D,OAAO,EACL,KAAK,cAAc,EACnB,KAAK,oBAAoB,EACzB,KAAK,SAAS,EAMf,MAAM,OAAO,CAAC;AAGf,OAAO,EAAc,KAAK,aAAa,EAAE,MAAM,YAAY,CAAC;AAE5D,OAAO,EAA6D,KAAK,eAAe,EAAE,MAAM,eAAe,CAAC;AAGhH,MAAM,MAAM,aAAa,GAAG;IAC1B,SAAS,EAAE,SAAS,CAAC,cAAc,CAAC,CAAC;IACrC,IAAI,CAAC,EAAE,UAAU,CAAC;IAClB,eAAe,EAAE,UAAU,CAAC,OAAO,iBAAiB,CAAC,GAAG;QACtD,QAAQ,EAAE,CAAC,CAAC;QACZ,OAAO,EAAE,oBAAoB,CAAC,cAAc,CAAC,CAAC;KAC/C,CAAC;CACH,CAAC;AAEF,MAAM,MAAM,UAAU,GAAG;IACvB,IAAI,EAAE,MAAM,CAAC;IACb,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,MAAM,CAAC;IACf,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB,CAAC;AAEF,MAAM,MAAM,kBAAkB,GAAG,IAAI,CAAC,iBAAiB,EAAE,YAAY,CAAC,GAAG;IACvE,EAAE,CAAC,EAAE,MAAM,CAAC;IACZ,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,SAAS,CAAC,EAAE,eAAe,CAAC;IAC5B,eAAe,CAAC,EAAE,OAAO,CAAC;IAC1B,KAAK,CAAC,EAAE,OAAO,CAAC;CACjB,CAAC;AAIF;;GAEG;AACH,eAAO,MAAM,aAAa,WACjB,aAAa,CAAC,kBAAkB,CAAC,SAClC,cAAc,KACnB,aAwHF,CAAC"}
|
|
@@ -1,19 +1,9 @@
|
|
|
1
1
|
export type HeadingLevel = 1 | 2 | 3 | 4 | 5 | 6;
|
|
2
|
-
export declare const
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
export declare const strikethrough = "line-through";
|
|
10
|
-
export declare const code = "font-mono !no-underline text-neutral-700 dark:text-neutral-300";
|
|
11
|
-
export declare const codeMark = "font-mono text-primary-500";
|
|
12
|
-
export declare const codeBlock = "mlb-2 font-mono bg-neutral-500/10 p-3 rounded";
|
|
13
|
-
export declare const inlineUrl: string;
|
|
14
|
-
export declare const blockquote: string;
|
|
15
|
-
export declare const horizontalRule = "flex mlb-4 border-b text-neutral-100 dark:text-neutral-900 border-neutral-200 dark:border-neutral-800";
|
|
16
|
-
export declare const unorderedList = "mlb-2 grid grid-cols-[min-content_1fr] [&>li:before]:content-[attr(marker)] [&>li:before]:mlb-1 [&>li:before]:mie-2";
|
|
17
|
-
export declare const orderedList = "mlb-2 grid grid-cols-[min-content_1fr] [&>li:before]:content-[counters(section,_\".\")_\"._\"] [counter-reset:section] [&>li:before]:mlb-1";
|
|
18
|
-
export declare const listItem = "contents before:[counter-increment:section]";
|
|
2
|
+
export declare const theme: {
|
|
3
|
+
mark: string;
|
|
4
|
+
code: string;
|
|
5
|
+
codeMark: string;
|
|
6
|
+
blockquote: string;
|
|
7
|
+
heading: (level: HeadingLevel) => string;
|
|
8
|
+
};
|
|
19
9
|
//# sourceMappingURL=markdown.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"markdown.d.ts","sourceRoot":"","sources":["../../../../src/styles/markdown.ts"],"names":[],"mappings":"AAMA,MAAM,MAAM,YAAY,GAAG,CAAC,GAAG,CAAC,GAAG,CAAC,GAAG,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC;AAcjD,eAAO,MAAM,
|
|
1
|
+
{"version":3,"file":"markdown.d.ts","sourceRoot":"","sources":["../../../../src/styles/markdown.ts"],"names":[],"mappings":"AAMA,MAAM,MAAM,YAAY,GAAG,CAAC,GAAG,CAAC,GAAG,CAAC,GAAG,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC;AAcjD,eAAO,MAAM,KAAK;;;;;qBAMC,YAAY;CAG9B,CAAC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"theme.d.ts","sourceRoot":"","sources":["../../../../src/styles/theme.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"theme.d.ts","sourceRoot":"","sources":["../../../../src/styles/theme.ts"],"names":[],"mappings":"AAIA,OAAO,EAAE,KAAK,SAAS,EAAE,MAAM,WAAW,CAAC;AAI3C,MAAM,MAAM,WAAW,GAAG,MAAM,CAAC,MAAM,EAAE,SAAS,CAAC,CAAC;AAMpD;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAgCG;AACH,eAAO,MAAM,YAAY,EAAE,WAwP1B,CAAC"}
|
|
@@ -1,8 +1,6 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
export declare const tokens: TailwindConfig['theme'];
|
|
7
|
-
export declare const getToken: (path: string, defaultValue?: any) => any;
|
|
1
|
+
/**
|
|
2
|
+
* @deprecated
|
|
3
|
+
* Replace with CSS vars.
|
|
4
|
+
*/
|
|
5
|
+
export declare const getToken: (path: string, defaultValue?: string | string[]) => string;
|
|
8
6
|
//# sourceMappingURL=tokens.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"tokens.d.ts","sourceRoot":"","sources":["../../../../src/styles/tokens.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"tokens.d.ts","sourceRoot":"","sources":["../../../../src/styles/tokens.ts"],"names":[],"mappings":"AAUA;;;GAGG;AACH,eAAO,MAAM,QAAQ,SAAU,MAAM,iBAAiB,MAAM,GAAG,MAAM,EAAE,KAAG,MAGzE,CAAC"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@dxos/react-ui-editor",
|
|
3
|
-
"version": "0.6.8-
|
|
3
|
+
"version": "0.6.8-staging.77f93a3",
|
|
4
4
|
"description": "Document editing experience within a DXOS shell.",
|
|
5
5
|
"homepage": "https://dxos.org",
|
|
6
6
|
"bugs": "https://github.com/dxos/dxos/issues",
|
|
@@ -46,19 +46,19 @@
|
|
|
46
46
|
"lodash.sortby": "^4.7.0",
|
|
47
47
|
"react-dropzone": "^14.2.3",
|
|
48
48
|
"style-mod": "^4.1.0",
|
|
49
|
-
"@dxos/async": "0.6.8-
|
|
50
|
-
"@dxos/
|
|
51
|
-
"@dxos/automerge": "0.6.8-
|
|
52
|
-
"@dxos/
|
|
53
|
-
"@dxos/echo-schema": "0.6.8-
|
|
54
|
-
"@dxos/
|
|
55
|
-
"@dxos/
|
|
56
|
-
"@dxos/log": "0.6.8-
|
|
57
|
-
"@dxos/protocols": "0.6.8-
|
|
58
|
-
"@dxos/react-
|
|
59
|
-
"@dxos/react-
|
|
60
|
-
"@dxos/
|
|
61
|
-
"@dxos/
|
|
49
|
+
"@dxos/async": "0.6.8-staging.77f93a3",
|
|
50
|
+
"@dxos/context": "0.6.8-staging.77f93a3",
|
|
51
|
+
"@dxos/automerge": "0.6.8-staging.77f93a3",
|
|
52
|
+
"@dxos/debug": "0.6.8-staging.77f93a3",
|
|
53
|
+
"@dxos/echo-schema": "0.6.8-staging.77f93a3",
|
|
54
|
+
"@dxos/display-name": "0.6.8-staging.77f93a3",
|
|
55
|
+
"@dxos/invariant": "0.6.8-staging.77f93a3",
|
|
56
|
+
"@dxos/log": "0.6.8-staging.77f93a3",
|
|
57
|
+
"@dxos/protocols": "0.6.8-staging.77f93a3",
|
|
58
|
+
"@dxos/react-ui": "0.6.8-staging.77f93a3",
|
|
59
|
+
"@dxos/react-async": "0.6.8-staging.77f93a3",
|
|
60
|
+
"@dxos/util": "0.6.8-staging.77f93a3",
|
|
61
|
+
"@dxos/react-ui-theme": "0.6.8-staging.77f93a3"
|
|
62
62
|
},
|
|
63
63
|
"devDependencies": {
|
|
64
64
|
"@phosphor-icons/react": "^2.1.5",
|
|
@@ -83,21 +83,21 @@
|
|
|
83
83
|
"vite-plugin-top-level-await": "^1.4.1",
|
|
84
84
|
"vite-plugin-wasm": "^3.3.0",
|
|
85
85
|
"vitest": "^1.5.0",
|
|
86
|
-
"@dxos/
|
|
87
|
-
"@dxos/
|
|
88
|
-
"@dxos/echo-typegen": "0.6.8-
|
|
89
|
-
"@dxos/echo-signals": "0.6.8-
|
|
90
|
-
"@dxos/keyboard": "0.6.8-
|
|
91
|
-
"@dxos/random": "0.6.8-
|
|
92
|
-
"@dxos/react-client": "0.6.8-
|
|
93
|
-
"@dxos/react-ui": "0.6.8-
|
|
94
|
-
"@dxos/storybook-utils": "0.6.8-
|
|
86
|
+
"@dxos/config": "0.6.8-staging.77f93a3",
|
|
87
|
+
"@dxos/automerge": "0.6.8-staging.77f93a3",
|
|
88
|
+
"@dxos/echo-typegen": "0.6.8-staging.77f93a3",
|
|
89
|
+
"@dxos/echo-signals": "0.6.8-staging.77f93a3",
|
|
90
|
+
"@dxos/keyboard": "0.6.8-staging.77f93a3",
|
|
91
|
+
"@dxos/random": "0.6.8-staging.77f93a3",
|
|
92
|
+
"@dxos/react-client": "0.6.8-staging.77f93a3",
|
|
93
|
+
"@dxos/react-ui": "0.6.8-staging.77f93a3",
|
|
94
|
+
"@dxos/storybook-utils": "0.6.8-staging.77f93a3"
|
|
95
95
|
},
|
|
96
96
|
"peerDependencies": {
|
|
97
97
|
"@phosphor-icons/react": "^2.1.5",
|
|
98
98
|
"react": "^18.0.0",
|
|
99
99
|
"react-dom": "^18.0.0",
|
|
100
|
-
"@dxos/react-client": "0.6.8-
|
|
100
|
+
"@dxos/react-client": "0.6.8-staging.77f93a3"
|
|
101
101
|
},
|
|
102
102
|
"publishConfig": {
|
|
103
103
|
"access": "public"
|
|
@@ -17,11 +17,11 @@ import { PublicKey } from '@dxos/keys';
|
|
|
17
17
|
import { log } from '@dxos/log';
|
|
18
18
|
import { faker } from '@dxos/random';
|
|
19
19
|
import { createDocAccessor, createEchoObject } from '@dxos/react-client/echo';
|
|
20
|
-
import { Button, DensityProvider, Input,
|
|
21
|
-
import { baseSurface,
|
|
20
|
+
import { Button, DensityProvider, Input, useThemeContext } from '@dxos/react-ui';
|
|
21
|
+
import { baseSurface, mx, getSize } from '@dxos/react-ui-theme';
|
|
22
22
|
import { withFullscreen, withTheme } from '@dxos/storybook-utils';
|
|
23
23
|
|
|
24
|
-
import { editorContent } from './defaults';
|
|
24
|
+
import { editorContent, editorGutter } from './defaults';
|
|
25
25
|
import {
|
|
26
26
|
InputModeExtensions,
|
|
27
27
|
annotations,
|
|
@@ -47,11 +47,11 @@ import {
|
|
|
47
47
|
table,
|
|
48
48
|
typewriter,
|
|
49
49
|
type CommandAction,
|
|
50
|
-
type CommandOptions,
|
|
51
50
|
type Comment,
|
|
52
51
|
type CommentsOptions,
|
|
53
|
-
type
|
|
52
|
+
type EditorSelectionState,
|
|
54
53
|
} from './extensions';
|
|
54
|
+
import { renderRoot } from './extensions/util';
|
|
55
55
|
import { useTextEditor, type UseTextEditorProps } from './hooks';
|
|
56
56
|
import translations from './translations';
|
|
57
57
|
|
|
@@ -153,17 +153,19 @@ const content = {
|
|
|
153
153
|
...[1, 2, 3, 4, 5, 6].map((level) => ['#'.repeat(level) + ` Heading ${level}`, faker.lorem.sentences(), '']).flat(),
|
|
154
154
|
),
|
|
155
155
|
|
|
156
|
-
formatting: str('### Formatting', 'This this is **bold**, ~~strikethrough~~, _italic_, and `f(INLINE)`.'),
|
|
156
|
+
formatting: str('### Formatting', '', 'This this is **bold**, ~~strikethrough~~, _italic_, and `f(INLINE)`.', ''),
|
|
157
157
|
|
|
158
158
|
blockquotes: str(
|
|
159
159
|
'### Blockquotes',
|
|
160
|
+
'',
|
|
160
161
|
'> This is a block quote.',
|
|
161
162
|
'',
|
|
162
163
|
'> This is a long wrapping block quote. Neque reiciendis ullam quae error labore sit, at, et, nulla, aut at nostrum omnis quas nostrum, at consectetur vitae eos asperiores non omnis ullam in beatae at vitae deserunt asperiores sapiente.',
|
|
163
164
|
'',
|
|
164
|
-
'> This is',
|
|
165
|
-
'> a multi-line',
|
|
165
|
+
'> This is ...',
|
|
166
|
+
'> ... a multi-line ...',
|
|
166
167
|
'> block quote.',
|
|
168
|
+
'',
|
|
167
169
|
),
|
|
168
170
|
|
|
169
171
|
paragraphs: str(...faker.helpers.multiple(() => [faker.lorem.paragraph(), ''], { count: 3 }).flat()),
|
|
@@ -264,7 +266,7 @@ type StoryProps = {
|
|
|
264
266
|
text?: string;
|
|
265
267
|
readonly?: boolean;
|
|
266
268
|
placeholder?: string;
|
|
267
|
-
} & Pick<UseTextEditorProps, 'selection' | 'extensions'>;
|
|
269
|
+
} & Pick<UseTextEditorProps, 'scrollTo' | 'selection' | 'extensions'>;
|
|
268
270
|
|
|
269
271
|
const Story = ({
|
|
270
272
|
id = 'editor-' + PublicKey.random().toHex().slice(0, 8),
|
|
@@ -272,6 +274,7 @@ const Story = ({
|
|
|
272
274
|
extensions,
|
|
273
275
|
readonly,
|
|
274
276
|
placeholder = 'New document.',
|
|
277
|
+
scrollTo,
|
|
275
278
|
selection,
|
|
276
279
|
}: StoryProps) => {
|
|
277
280
|
const [object] = useState(createEchoObject(create(Expando, { content: text ?? '' })));
|
|
@@ -294,6 +297,7 @@ const Story = ({
|
|
|
294
297
|
}),
|
|
295
298
|
extensions || [],
|
|
296
299
|
],
|
|
300
|
+
scrollTo,
|
|
297
301
|
selection,
|
|
298
302
|
}),
|
|
299
303
|
[object, extensions, themeMode],
|
|
@@ -313,13 +317,25 @@ const defaults = [
|
|
|
313
317
|
autocomplete({
|
|
314
318
|
onSearch: (text) => links.filter(({ label }) => label.toLowerCase().includes(text.toLowerCase())),
|
|
315
319
|
}),
|
|
316
|
-
decorateMarkdown({ renderLinkButton, selectionChangeDelay: 100
|
|
320
|
+
decorateMarkdown({ renderLinkButton, selectionChangeDelay: 100 }),
|
|
317
321
|
formattingKeymap(),
|
|
318
322
|
linkTooltip(renderLinkTooltip),
|
|
319
323
|
];
|
|
320
324
|
|
|
321
325
|
export const Default = {
|
|
322
|
-
render: () => <Story text={text} extensions={defaults} />,
|
|
326
|
+
render: () => <Story text={text} extensions={defaults} selection={{ anchor: 99, head: 110 }} />,
|
|
327
|
+
};
|
|
328
|
+
|
|
329
|
+
export const ScrollTo = {
|
|
330
|
+
render: () => {
|
|
331
|
+
// NOTE: Selection won't appear if text is reformatted.
|
|
332
|
+
const word = 'Scroll to here...';
|
|
333
|
+
const text = str('# Scroll To', longText, '', word, '', longText);
|
|
334
|
+
const idx = text.indexOf(word);
|
|
335
|
+
return (
|
|
336
|
+
<Story text={text} extensions={defaults} scrollTo={idx} selection={{ anchor: idx, head: idx + word.length }} />
|
|
337
|
+
);
|
|
338
|
+
},
|
|
323
339
|
};
|
|
324
340
|
|
|
325
341
|
export const Readonly = {
|
|
@@ -335,10 +351,10 @@ export const NoExtensions = {
|
|
|
335
351
|
};
|
|
336
352
|
|
|
337
353
|
export const Folding = {
|
|
338
|
-
render: () => <Story text={text} extensions={[folding()]} />,
|
|
354
|
+
render: () => <Story text={text} extensions={[editorGutter, folding()]} />,
|
|
339
355
|
};
|
|
340
356
|
|
|
341
|
-
const
|
|
357
|
+
const longText = faker.helpers.multiple(() => faker.lorem.paragraph({ min: 8, max: 16 }), { count: 20 }).join('\n\n');
|
|
342
358
|
|
|
343
359
|
const largeWithImages = faker.helpers
|
|
344
360
|
.multiple(() => [faker.lorem.paragraph({ min: 12, max: 16 }), img], { count: 20 })
|
|
@@ -355,12 +371,12 @@ export const Headings = {
|
|
|
355
371
|
render: () => <Story text={headings} extensions={decorateMarkdown({ numberedHeadings: { from: 2, to: 4 } })} />,
|
|
356
372
|
};
|
|
357
373
|
|
|
358
|
-
const global = new Map<string,
|
|
374
|
+
const global = new Map<string, EditorSelectionState>();
|
|
359
375
|
|
|
360
376
|
export const Scrolling = {
|
|
361
377
|
render: () => (
|
|
362
378
|
<Story
|
|
363
|
-
text={str('# Large Document', '',
|
|
379
|
+
text={str('# Large Document', '', longText)}
|
|
364
380
|
extensions={state({
|
|
365
381
|
setState: (id, state) => global.set(id, state),
|
|
366
382
|
getState: (id) => global.get(id),
|
|
@@ -489,21 +505,18 @@ const CommandDialog: FC<{ onClose: (action?: CommandAction) => void }> = ({ onCl
|
|
|
489
505
|
);
|
|
490
506
|
};
|
|
491
507
|
|
|
492
|
-
const renderCommandDialog: CommandOptions['onRender'] = (el, onClose) => {
|
|
493
|
-
createRoot(el).render(
|
|
494
|
-
<StrictMode>
|
|
495
|
-
<ThemeProvider tx={defaultTx}>
|
|
496
|
-
<CommandDialog onClose={onClose} />
|
|
497
|
-
</ThemeProvider>
|
|
498
|
-
</StrictMode>,
|
|
499
|
-
);
|
|
500
|
-
};
|
|
501
|
-
|
|
502
508
|
export const Command = {
|
|
503
509
|
render: () => (
|
|
504
510
|
<Story
|
|
505
511
|
text={str('# Command', '')}
|
|
506
|
-
extensions={[
|
|
512
|
+
extensions={[
|
|
513
|
+
command({
|
|
514
|
+
onRender: (el, onClose) => {
|
|
515
|
+
renderRoot(el, <CommandDialog onClose={onClose} />);
|
|
516
|
+
},
|
|
517
|
+
onHint: () => 'Press / for commands.',
|
|
518
|
+
}),
|
|
519
|
+
]}
|
|
507
520
|
/>
|
|
508
521
|
),
|
|
509
522
|
};
|
|
@@ -558,7 +571,7 @@ export const Vim = {
|
|
|
558
571
|
};
|
|
559
572
|
|
|
560
573
|
export const Annotations = {
|
|
561
|
-
render: () => <Story text={str('# Annotations', '',
|
|
574
|
+
render: () => <Story text={str('# Annotations', '', longText)} extensions={[annotations({ match: /volup/gi })]} />,
|
|
562
575
|
};
|
|
563
576
|
|
|
564
577
|
export const DND = {
|
package/src/defaults.ts
CHANGED
|
@@ -11,7 +11,7 @@ export { getToken } from './styles';
|
|
|
11
11
|
* 40rem = 640px. Corresponds to initial plank width (Google docs, Stashpad, etc.)
|
|
12
12
|
* 50rem = 800px. Maximum content width for solo mode.
|
|
13
13
|
*/
|
|
14
|
-
export const editorContent = '!mt-[16px] !mli-auto w-full max-w-[min(50rem,100%-4rem)]';
|
|
14
|
+
export const editorContent = '!mt-[16px] !mb-[32px] !mli-auto w-full max-w-[min(50rem,100%-4rem)]';
|
|
15
15
|
|
|
16
16
|
export const editorWithToolbarLayout =
|
|
17
17
|
'grid grid-cols-1 grid-rows-[min-content_1fr] data-[toolbar=disabled]:grid-rows-[1fr] justify-center content-start overflow-hidden';
|
|
@@ -20,6 +20,7 @@ export const editorGutter = EditorView.baseTheme({
|
|
|
20
20
|
'.cm-gutters': {
|
|
21
21
|
// Match margin from content.
|
|
22
22
|
marginTop: '16px',
|
|
23
|
+
marginBottom: '16px',
|
|
23
24
|
// Inside within content margin.
|
|
24
25
|
marginRight: '-32px',
|
|
25
26
|
width: '32px',
|
package/src/extensions/doc.ts
CHANGED
|
@@ -6,6 +6,9 @@ import { Facet } from '@codemirror/state';
|
|
|
6
6
|
|
|
7
7
|
import { invariant } from '@dxos/invariant';
|
|
8
8
|
|
|
9
|
+
/**
|
|
10
|
+
* Currently edited document id as FQ string.
|
|
11
|
+
*/
|
|
9
12
|
export const documentId = Facet.define<string, string>({
|
|
10
13
|
combine: (providers) => {
|
|
11
14
|
invariant(providers.length <= 1);
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
//
|
|
4
4
|
|
|
5
5
|
import { closeBrackets, closeBracketsKeymap } from '@codemirror/autocomplete';
|
|
6
|
-
import { defaultKeymap, history, historyKeymap,
|
|
6
|
+
import { defaultKeymap, history, historyKeymap, standardKeymap } from '@codemirror/commands';
|
|
7
7
|
import { bracketMatching } from '@codemirror/language';
|
|
8
8
|
import { searchKeymap } from '@codemirror/search';
|
|
9
9
|
import { EditorState, type Extension } from '@codemirror/state';
|
|
@@ -109,8 +109,9 @@ export const createBasicExtensions = (_props?: BasicExtensionsOptions): Extensio
|
|
|
109
109
|
keymap.of(
|
|
110
110
|
[
|
|
111
111
|
...((props.keymap && keymaps[props.keymap]) ?? []),
|
|
112
|
+
// NOTE: Tab configured by markdown extension.
|
|
112
113
|
// https://codemirror.net/docs/ref/#commands.indentWithTab
|
|
113
|
-
...(props.indentWithTab ? [indentWithTab] : []),
|
|
114
|
+
// ...(props.indentWithTab ? [indentWithTab] : []),
|
|
114
115
|
// https://codemirror.net/docs/ref/#autocomplete.closeBracketsKeymap
|
|
115
116
|
...(props.closeBrackets ? closeBracketsKeymap : []),
|
|
116
117
|
// https://codemirror.net/docs/ref/#commands.historyKeymap
|
|
@@ -6,8 +6,7 @@ import { codeFolding, foldGutter } from '@codemirror/language';
|
|
|
6
6
|
import { type Extension } from '@codemirror/state';
|
|
7
7
|
import React from 'react';
|
|
8
8
|
|
|
9
|
-
import {
|
|
10
|
-
import { defaultTx, getSize, mx } from '@dxos/react-ui-theme';
|
|
9
|
+
import { getSize, mx } from '@dxos/react-ui-theme';
|
|
11
10
|
|
|
12
11
|
import { renderRoot } from './util';
|
|
13
12
|
|
|
@@ -23,11 +22,10 @@ export const folding = (_props: FoldingOptions = {}): Extension => [
|
|
|
23
22
|
foldGutter({
|
|
24
23
|
markerDOM: (open) => {
|
|
25
24
|
return renderRoot(
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
</ThemeProvider>,
|
|
25
|
+
document.createElement('div'),
|
|
26
|
+
<svg className={mx(getSize(3), 'm-3 cursor-pointer', open && 'rotate-90')}>
|
|
27
|
+
<use href={'/icons.svg#ph--caret-right--regular'} />
|
|
28
|
+
</svg>,
|
|
31
29
|
);
|
|
32
30
|
},
|
|
33
31
|
}),
|
|
@@ -15,7 +15,6 @@ import { keymap } from '@codemirror/view';
|
|
|
15
15
|
import { type ThemeMode } from '@dxos/react-ui';
|
|
16
16
|
|
|
17
17
|
import { markdownHighlightStyle, markdownTagsExtensions } from './highlight';
|
|
18
|
-
import { linkPastePlugin } from './link-paste';
|
|
19
18
|
|
|
20
19
|
export type MarkdownBundleOptions = {
|
|
21
20
|
themeMode?: ThemeMode;
|
|
@@ -58,9 +57,8 @@ export const createMarkdownExtensions = ({ themeMode }: MarkdownBundleOptions =
|
|
|
58
57
|
// Custom styles.
|
|
59
58
|
syntaxHighlighting(markdownHighlightStyle()),
|
|
60
59
|
|
|
61
|
-
linkPastePlugin,
|
|
62
|
-
|
|
63
60
|
keymap.of([
|
|
61
|
+
// TODO(burdon): Indent by 4 if in task list.
|
|
64
62
|
// https://codemirror.net/docs/ref/#commands.indentWithTab
|
|
65
63
|
indentWithTab,
|
|
66
64
|
|
|
@@ -11,8 +11,9 @@ import { invariant } from '@dxos/invariant';
|
|
|
11
11
|
import { mx } from '@dxos/react-ui-theme';
|
|
12
12
|
|
|
13
13
|
import { image } from './image';
|
|
14
|
+
import { linkPastePlugin } from './link-paste';
|
|
14
15
|
import { table } from './table';
|
|
15
|
-
import { getToken,
|
|
16
|
+
import { getToken, theme, type HeadingLevel } from '../../styles';
|
|
16
17
|
import { wrapWithCatch } from '../util';
|
|
17
18
|
|
|
18
19
|
//
|
|
@@ -201,28 +202,34 @@ const buildDecorations = (view: EditorView, options: DecorateOptions, focus: boo
|
|
|
201
202
|
}
|
|
202
203
|
|
|
203
204
|
const editing = editingRange(state, node, focus);
|
|
204
|
-
if (
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
205
|
+
if (editing) {
|
|
206
|
+
break;
|
|
207
|
+
}
|
|
208
|
+
|
|
209
|
+
const mark = node.node.firstChild!;
|
|
210
|
+
if (mark?.name === 'HeaderMark') {
|
|
211
|
+
const { from, to = 6 } = options.numberedHeadings ?? {};
|
|
212
|
+
const text = view.state.sliceDoc(node.from, node.to);
|
|
213
|
+
const len = text.match(/[#\s]+/)![0].length;
|
|
214
|
+
if (!from || level < from || level > to) {
|
|
215
|
+
atomicDeco.add(mark.from, mark.from + len, hide);
|
|
216
|
+
} else {
|
|
217
|
+
// TODO(burdon): Number format/style.
|
|
218
|
+
const num =
|
|
219
|
+
headers
|
|
211
220
|
.slice(from - 1)
|
|
212
221
|
.map((level) => level?.number ?? 0)
|
|
213
|
-
.join('.');
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
222
|
+
.join('.') + ' ';
|
|
223
|
+
|
|
224
|
+
if (num.length) {
|
|
225
|
+
atomicDeco.add(
|
|
226
|
+
mark.from,
|
|
227
|
+
mark.from + len,
|
|
228
|
+
Decoration.replace({
|
|
229
|
+
widget: new TextWidget(num, theme.heading(level)),
|
|
230
|
+
}),
|
|
231
|
+
);
|
|
217
232
|
}
|
|
218
|
-
|
|
219
|
-
deco.add(
|
|
220
|
-
node.from,
|
|
221
|
-
node.to,
|
|
222
|
-
Decoration.replace({
|
|
223
|
-
widget: new TextWidget(text, heading(level)),
|
|
224
|
-
}),
|
|
225
|
-
);
|
|
226
233
|
}
|
|
227
234
|
}
|
|
228
235
|
|
|
@@ -271,7 +278,6 @@ const buildDecorations = (view: EditorView, options: DecorateOptions, focus: boo
|
|
|
271
278
|
// const mark = node.node.firstChild!;
|
|
272
279
|
// console.log(mark?.name);
|
|
273
280
|
// if (mark?.name === 'ListMark') {}
|
|
274
|
-
|
|
275
281
|
break;
|
|
276
282
|
}
|
|
277
283
|
|
|
@@ -515,6 +521,7 @@ export const decorateMarkdown = (options: DecorateOptions = {}) => {
|
|
|
515
521
|
},
|
|
516
522
|
),
|
|
517
523
|
formattingStyles,
|
|
524
|
+
linkPastePlugin,
|
|
518
525
|
image(),
|
|
519
526
|
table(),
|
|
520
527
|
];
|
|
@@ -522,7 +529,7 @@ export const decorateMarkdown = (options: DecorateOptions = {}) => {
|
|
|
522
529
|
|
|
523
530
|
const formattingStyles = EditorView.baseTheme({
|
|
524
531
|
'& .cm-code': {
|
|
525
|
-
fontFamily: getToken('fontFamily.mono'
|
|
532
|
+
fontFamily: getToken('fontFamily.mono'),
|
|
526
533
|
},
|
|
527
534
|
|
|
528
535
|
'& .cm-codeblock-line': {
|
|
@@ -579,7 +586,6 @@ const formattingStyles = EditorView.baseTheme({
|
|
|
579
586
|
'& .cm-list-mark': {
|
|
580
587
|
display: 'inline-block',
|
|
581
588
|
textAlign: 'right',
|
|
582
|
-
color: getToken('extend.colors.neutral.500'),
|
|
583
589
|
fontVariant: 'tabular-nums',
|
|
584
590
|
},
|
|
585
591
|
'& .cm-list-mark-bullet': {
|
|
@@ -3,6 +3,7 @@
|
|
|
3
3
|
//
|
|
4
4
|
|
|
5
5
|
import { snippet } from '@codemirror/autocomplete';
|
|
6
|
+
import { indentWithTab } from '@codemirror/commands';
|
|
6
7
|
import { syntaxTree } from '@codemirror/language';
|
|
7
8
|
import {
|
|
8
9
|
type Extension,
|
|
@@ -1015,8 +1016,9 @@ export const toggleCodeblock: StateCommand = (target) => {
|
|
|
1015
1016
|
//
|
|
1016
1017
|
|
|
1017
1018
|
export type FormattingOptions = {};
|
|
1019
|
+
indentWithTab;
|
|
1018
1020
|
|
|
1019
|
-
export const formattingKeymap = (
|
|
1021
|
+
export const formattingKeymap = (_options: FormattingOptions = {}): Extension => {
|
|
1020
1022
|
return [
|
|
1021
1023
|
keymap.of([
|
|
1022
1024
|
{
|
|
@@ -7,7 +7,7 @@ import { HighlightStyle } from '@codemirror/language';
|
|
|
7
7
|
import { tags, styleTags, Tag } from '@lezer/highlight';
|
|
8
8
|
import { type MarkdownConfig, Table } from '@lezer/markdown';
|
|
9
9
|
|
|
10
|
-
import {
|
|
10
|
+
import { getToken, theme } from '../../styles';
|
|
11
11
|
|
|
12
12
|
/**
|
|
13
13
|
* Custom tags defined and processed by the GFM lezer extension.
|
|
@@ -49,6 +49,8 @@ export const markdownTagsExtensions: MarkdownConfig[] = [
|
|
|
49
49
|
},
|
|
50
50
|
];
|
|
51
51
|
|
|
52
|
+
export type HighlightOptions = {};
|
|
53
|
+
|
|
52
54
|
/**
|
|
53
55
|
* Styling based on `lezer` parser tags.
|
|
54
56
|
* https://codemirror.net/examples/styling
|
|
@@ -60,7 +62,7 @@ export const markdownTagsExtensions: MarkdownConfig[] = [
|
|
|
60
62
|
* - https://github.com/codemirror/language/blob/main/src/highlight.ts#L194
|
|
61
63
|
* - https://github.com/codemirror/theme-one-dark/blob/main/src/one-dark.ts#L115
|
|
62
64
|
*/
|
|
63
|
-
export const markdownHighlightStyle = (
|
|
65
|
+
export const markdownHighlightStyle = (_options: HighlightOptions = {}) => {
|
|
64
66
|
return HighlightStyle.define(
|
|
65
67
|
[
|
|
66
68
|
{
|
|
@@ -99,6 +101,7 @@ export const markdownHighlightStyle = (readonly?: boolean) => {
|
|
|
99
101
|
tags.inserted,
|
|
100
102
|
tags.invalid,
|
|
101
103
|
],
|
|
104
|
+
// TODO(burdon): Explain.
|
|
102
105
|
color: 'inherit !important',
|
|
103
106
|
},
|
|
104
107
|
|
|
@@ -111,38 +114,49 @@ export const markdownHighlightStyle = (readonly?: boolean) => {
|
|
|
111
114
|
markdownTags.LinkReference,
|
|
112
115
|
markdownTags.ListMark,
|
|
113
116
|
],
|
|
114
|
-
class: mark,
|
|
117
|
+
class: theme.mark,
|
|
115
118
|
},
|
|
116
119
|
|
|
117
120
|
// Markdown marks.
|
|
118
121
|
{
|
|
119
|
-
tag: [
|
|
120
|
-
|
|
122
|
+
tag: [
|
|
123
|
+
//
|
|
124
|
+
markdownTags.CodeMark,
|
|
125
|
+
markdownTags.HeaderMark,
|
|
126
|
+
markdownTags.QuoteMark,
|
|
127
|
+
markdownTags.EmphasisMark,
|
|
128
|
+
],
|
|
129
|
+
class: theme.mark,
|
|
121
130
|
},
|
|
122
131
|
|
|
123
132
|
// E.g., code block language (after ```).
|
|
124
133
|
{
|
|
125
|
-
tag: [
|
|
126
|
-
|
|
134
|
+
tag: [
|
|
135
|
+
//
|
|
136
|
+
tags.function(tags.variableName),
|
|
137
|
+
tags.labelName,
|
|
138
|
+
],
|
|
139
|
+
class: theme.codeMark,
|
|
127
140
|
},
|
|
128
141
|
|
|
142
|
+
// Fonts.
|
|
129
143
|
{
|
|
130
144
|
tag: [tags.monospace],
|
|
131
145
|
class: 'font-mono',
|
|
132
146
|
},
|
|
133
147
|
|
|
134
148
|
// Headings.
|
|
135
|
-
{ tag: tags.heading1, class: heading(1) },
|
|
136
|
-
{ tag: tags.heading2, class: heading(2) },
|
|
137
|
-
{ tag: tags.heading3, class: heading(3) },
|
|
138
|
-
{ tag: tags.heading4, class: heading(4) },
|
|
139
|
-
{ tag: tags.heading5, class: heading(5) },
|
|
140
|
-
{ tag: tags.heading6, class: heading(6) },
|
|
149
|
+
{ tag: tags.heading1, class: theme.heading(1) },
|
|
150
|
+
{ tag: tags.heading2, class: theme.heading(2) },
|
|
151
|
+
{ tag: tags.heading3, class: theme.heading(3) },
|
|
152
|
+
{ tag: tags.heading4, class: theme.heading(4) },
|
|
153
|
+
{ tag: tags.heading5, class: theme.heading(5) },
|
|
154
|
+
{ tag: tags.heading6, class: theme.heading(6) },
|
|
141
155
|
|
|
142
156
|
// Emphasis.
|
|
143
|
-
{ tag: tags.emphasis, class: italic },
|
|
144
|
-
{ tag: tags.strong, class: bold },
|
|
145
|
-
{ tag: tags.strikethrough, class:
|
|
157
|
+
{ tag: tags.emphasis, class: 'italic' },
|
|
158
|
+
{ tag: tags.strong, class: 'font-bold' },
|
|
159
|
+
{ tag: tags.strikethrough, class: 'line-through' },
|
|
146
160
|
|
|
147
161
|
// NOTE: The `markdown` extension configures extensions for `lezer` to parse markdown tokens (incl. below).
|
|
148
162
|
// However, since `codeLanguages` is also defined, the `lezer` will not parse fenced code blocks,
|
|
@@ -151,12 +165,12 @@ export const markdownHighlightStyle = (readonly?: boolean) => {
|
|
|
151
165
|
// IMPORTANT: Therefore, the fenced code block will use the base editor font unless changed by an extension.
|
|
152
166
|
{
|
|
153
167
|
tag: [markdownTags.CodeText, markdownTags.InlineCode],
|
|
154
|
-
class: code,
|
|
168
|
+
class: theme.code,
|
|
155
169
|
},
|
|
156
170
|
|
|
157
171
|
{
|
|
158
172
|
tag: [markdownTags.QuoteMark],
|
|
159
|
-
class: blockquote,
|
|
173
|
+
class: theme.blockquote,
|
|
160
174
|
},
|
|
161
175
|
|
|
162
176
|
{
|
|
@@ -167,7 +181,7 @@ export const markdownHighlightStyle = (readonly?: boolean) => {
|
|
|
167
181
|
{
|
|
168
182
|
scope: markdownLanguage,
|
|
169
183
|
all: {
|
|
170
|
-
fontFamily: getToken('fontFamily.body'
|
|
184
|
+
fontFamily: getToken('fontFamily.body'),
|
|
171
185
|
},
|
|
172
186
|
},
|
|
173
187
|
);
|