@mongodb-js/compass-editor 0.6.0 → 0.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (65) hide show
  1. package/dist/ace/aggregation-autocompleter.d.ts +1 -1
  2. package/dist/ace/aggregation-autocompleter.d.ts.map +1 -1
  3. package/dist/ace/aggregation-autocompleter.js +7 -6
  4. package/dist/ace/aggregation-autocompleter.js.map +1 -1
  5. package/dist/actions.d.ts +11 -0
  6. package/dist/actions.d.ts.map +1 -0
  7. package/dist/actions.js +90 -0
  8. package/dist/actions.js.map +1 -0
  9. package/dist/autocompleter.d.ts +10 -7
  10. package/dist/autocompleter.d.ts.map +1 -1
  11. package/dist/autocompleter.js +28 -8
  12. package/dist/autocompleter.js.map +1 -1
  13. package/dist/base-editor.d.ts +1 -1
  14. package/dist/base-editor.d.ts.map +1 -1
  15. package/dist/codemirror/ace-compat-autocompleter.d.ts +26 -0
  16. package/dist/codemirror/ace-compat-autocompleter.d.ts.map +1 -0
  17. package/dist/codemirror/ace-compat-autocompleter.js +67 -0
  18. package/dist/codemirror/ace-compat-autocompleter.js.map +1 -0
  19. package/dist/codemirror/aggregation-autocompleter.d.ts +3 -0
  20. package/dist/codemirror/aggregation-autocompleter.d.ts.map +1 -0
  21. package/dist/codemirror/aggregation-autocompleter.js +58 -0
  22. package/dist/codemirror/aggregation-autocompleter.js.map +1 -0
  23. package/dist/codemirror/document-autocompleter.d.ts +3 -0
  24. package/dist/codemirror/document-autocompleter.d.ts.map +1 -0
  25. package/dist/codemirror/document-autocompleter.js +50 -0
  26. package/dist/codemirror/document-autocompleter.js.map +1 -0
  27. package/dist/codemirror/query-autocompleter.d.ts +4 -0
  28. package/dist/codemirror/query-autocompleter.d.ts.map +1 -0
  29. package/dist/codemirror/query-autocompleter.js +22 -0
  30. package/dist/codemirror/query-autocompleter.js.map +1 -0
  31. package/dist/codemirror/stage-autocompleter.d.ts +6 -0
  32. package/dist/codemirror/stage-autocompleter.d.ts.map +1 -0
  33. package/dist/codemirror/stage-autocompleter.js +58 -0
  34. package/dist/codemirror/stage-autocompleter.js.map +1 -0
  35. package/dist/codemirror/utils.d.ts +14 -0
  36. package/dist/codemirror/utils.d.ts.map +1 -0
  37. package/dist/codemirror/utils.js +80 -0
  38. package/dist/codemirror/utils.js.map +1 -0
  39. package/dist/codemirror/validation-autocompleter.d.ts +4 -0
  40. package/dist/codemirror/validation-autocompleter.d.ts.map +1 -0
  41. package/dist/codemirror/validation-autocompleter.js +123 -0
  42. package/dist/codemirror/validation-autocompleter.js.map +1 -0
  43. package/dist/index.d.ts +9 -4
  44. package/dist/index.d.ts.map +1 -1
  45. package/dist/index.js +13 -2
  46. package/dist/index.js.map +1 -1
  47. package/dist/inline-editor.d.ts +1 -1
  48. package/dist/inline-editor.d.ts.map +1 -1
  49. package/dist/json-editor.d.ts +51 -16
  50. package/dist/json-editor.d.ts.map +1 -1
  51. package/dist/json-editor.js +373 -50
  52. package/dist/json-editor.js.map +1 -1
  53. package/dist/multiline-editor.d.ts +2 -2
  54. package/dist/multiline-editor.d.ts.map +1 -1
  55. package/dist/multiline-editor.js +4 -60
  56. package/dist/multiline-editor.js.map +1 -1
  57. package/dist/prettify.d.ts +1 -1
  58. package/dist/prettify.d.ts.map +1 -1
  59. package/dist/syntax-highlight.d.ts +2 -2
  60. package/dist/syntax-highlight.d.ts.map +1 -1
  61. package/dist/syntax-highlight.js +2 -2
  62. package/dist/syntax-highlight.js.map +1 -1
  63. package/dist/types.d.ts +3 -2
  64. package/dist/types.d.ts.map +1 -1
  65. package/package.json +9 -9
@@ -23,7 +23,7 @@ var __importStar = (this && this.__importStar) || function (mod) {
23
23
  return result;
24
24
  };
25
25
  Object.defineProperty(exports, "__esModule", { value: true });
26
- exports.JSONEditor = void 0;
26
+ exports.CodemirrorMultilineEditor = exports.CodemirrorInlineEditor = exports.BaseEditor = exports.languageName = exports.languages = void 0;
27
27
  const react_1 = __importStar(require("react"));
28
28
  const view_1 = require("@codemirror/view");
29
29
  const language_1 = require("@codemirror/language");
@@ -38,10 +38,30 @@ const language_2 = require("@codemirror/language");
38
38
  const highlight_1 = require("@lezer/highlight");
39
39
  const polished_1 = require("polished");
40
40
  const prettify_1 = require("./prettify");
41
+ const actions_1 = require("./actions");
41
42
  const editorStyle = (0, compass_components_1.css)({
42
43
  fontSize: 13,
43
44
  fontFamily: compass_components_1.fontFamilies.code,
44
45
  });
46
+ const hiddenScrollStyle = (0, compass_components_1.css)({
47
+ '& .cm-scroller': {
48
+ overflow: '-moz-scrollbars-none',
49
+ msOverflowStyle: 'none',
50
+ },
51
+ '& .cm-scroller::-webkit-scrollbar': {
52
+ display: 'none',
53
+ },
54
+ });
55
+ const breakFocusOutBinding = {
56
+ ...commands_1.indentWithTab,
57
+ run({ state, dispatch }) {
58
+ dispatch(state.update(state.replaceSelection('\t'), {
59
+ scrollIntoView: true,
60
+ userEvent: 'input',
61
+ }));
62
+ return true;
63
+ },
64
+ };
45
65
  const editorPalette = {
46
66
  light: {
47
67
  color: compass_components_1.codePalette.light[3],
@@ -59,6 +79,11 @@ const editorPalette = {
59
79
  errorGutterIconColor: encodeURIComponent(compass_components_1.palette.red.base),
60
80
  foldPlaceholderColor: compass_components_1.palette.gray.base,
61
81
  foldPlaceholderBackgroundColor: compass_components_1.palette.gray.light3,
82
+ autocompleteColor: compass_components_1.palette.black,
83
+ autocompleteBackgroundColor: compass_components_1.palette.gray.light3,
84
+ autocompleteBorderColor: compass_components_1.palette.gray.light2,
85
+ autocompleteMatchColor: compass_components_1.palette.green.dark1,
86
+ autocompleteSelectedBackgroundColor: compass_components_1.palette.gray.light2,
62
87
  },
63
88
  dark: {
64
89
  color: compass_components_1.codePalette.dark[3],
@@ -76,6 +101,11 @@ const editorPalette = {
76
101
  errorGutterIconColor: encodeURIComponent(compass_components_1.palette.red.light1),
77
102
  foldPlaceholderColor: compass_components_1.palette.gray.base,
78
103
  foldPlaceholderBackgroundColor: compass_components_1.palette.gray.dark3,
104
+ autocompleteColor: compass_components_1.palette.gray.light1,
105
+ autocompleteBackgroundColor: compass_components_1.palette.gray.dark4,
106
+ autocompleteBorderColor: compass_components_1.palette.gray.dark1,
107
+ autocompleteMatchColor: compass_components_1.palette.gray.light3,
108
+ autocompleteSelectedBackgroundColor: compass_components_1.palette.gray.dark2,
79
109
  },
80
110
  };
81
111
  function getStylesForTheme(theme) {
@@ -83,16 +113,18 @@ function getStylesForTheme(theme) {
83
113
  '&': {
84
114
  color: editorPalette[theme].color,
85
115
  backgroundColor: editorPalette[theme].backgroundColor,
116
+ maxHeight: '100%',
86
117
  },
87
118
  '& .cm-scroller': {
88
119
  fontSize: '13px',
89
120
  fontFamily: compass_components_1.fontFamilies.code,
90
- lineHeight: `${compass_components_1.spacing[3]}px`,
91
121
  },
92
122
  '&.cm-editor.cm-focused': {
93
123
  outline: 'none',
94
124
  },
95
125
  '& .cm-content': {
126
+ paddingTop: `${compass_components_1.spacing[1]}px`,
127
+ paddingBottom: `${compass_components_1.spacing[1]}px`,
96
128
  caretColor: editorPalette[theme].cursorColor,
97
129
  },
98
130
  '& .cm-activeLine': {
@@ -106,14 +138,8 @@ function getStylesForTheme(theme) {
106
138
  backgroundColor: editorPalette[theme].gutterBackgroundColor,
107
139
  border: 'none',
108
140
  },
109
- '& .cm-gutters > .cm-gutter:first-child > .cm-gutterElement': {
110
- paddingLeft: `${compass_components_1.spacing[2]}px`,
111
- },
112
- '& .cm-gutters > .cm-gutter:last-child > .cm-gutterElement': {
113
- paddingRight: `${compass_components_1.spacing[2]}px`,
114
- },
115
141
  '& .cm-gutter-lint': {
116
- width: 'auto',
142
+ width: `${compass_components_1.spacing[3]}px`,
117
143
  },
118
144
  '& .cm-gutter-lint .cm-gutterElement': {
119
145
  padding: '0',
@@ -181,6 +207,45 @@ function getStylesForTheme(theme) {
181
207
  borderColor: editorPalette[theme].cursorColor,
182
208
  marginLeft: '-1px',
183
209
  },
210
+ '& .cm-tooltip': {
211
+ color: editorPalette[theme].autocompleteColor,
212
+ backgroundColor: editorPalette[theme].autocompleteBackgroundColor,
213
+ border: `1px solid ${editorPalette[theme].autocompleteBorderColor}`,
214
+ },
215
+ '& .cm-tooltip.cm-tooltip-autocomplete > ul': {
216
+ fontFamily: compass_components_1.fontFamilies.code,
217
+ },
218
+ '& .cm-tooltip-autocomplete ul li[aria-selected]': {
219
+ color: editorPalette[theme].autocompleteColor,
220
+ backgroundColor: editorPalette[theme].autocompleteSelectedBackgroundColor,
221
+ },
222
+ '& .cm-completionIcon': {
223
+ display: 'none',
224
+ },
225
+ '& .cm-completionDetail': {
226
+ color: (0, polished_1.rgba)(editorPalette[theme].autocompleteColor, 0.5),
227
+ fontStyle: 'normal',
228
+ marginRight: '1em',
229
+ },
230
+ '& .cm-completionMatchedText': {
231
+ color: editorPalette[theme].autocompleteMatchColor,
232
+ fontWeight: 'bold',
233
+ textDecoration: 'none',
234
+ },
235
+ '& .cm-tooltip .completion-info p': {
236
+ margin: 0,
237
+ marginTop: `${compass_components_1.spacing[2]}px`,
238
+ marginBottom: `${compass_components_1.spacing[2]}px`,
239
+ },
240
+ '& .cm-tooltip .completion-info p:first-child': {
241
+ marginTop: 0,
242
+ },
243
+ '& .cm-tooltip .completion-info p:last-child': {
244
+ marginBottom: 0,
245
+ },
246
+ '& .cm-widgetBuffer': {
247
+ verticalAlign: 'top',
248
+ },
184
249
  }, { dark: theme === 'dark' });
185
250
  }
186
251
  const themeStyles = {
@@ -265,13 +330,27 @@ function createFoldGutterExtension() {
265
330
  const javascriptExpression = lang_javascript_1.javascriptLanguage.configure({
266
331
  top: 'SingleExpression',
267
332
  });
268
- const languages = {
333
+ exports.languages = {
269
334
  json: lang_json_1.json,
270
335
  javascript() {
271
336
  return new language_2.LanguageSupport(javascriptExpression);
272
337
  },
273
338
  };
274
- const languageName = state_1.Facet.define({});
339
+ exports.languageName = state_1.Facet.define({});
340
+ function sheduleDispatch(editorView, transactions, signal) {
341
+ if (signal === null || signal === void 0 ? void 0 : signal.aborted) {
342
+ return;
343
+ }
344
+ if (editorView.updateState != 0) {
345
+ setTimeout(() => {
346
+ sheduleDispatch(editorView, transactions, signal);
347
+ });
348
+ }
349
+ else {
350
+ transactions = Array.isArray(transactions) ? transactions : [transactions];
351
+ editorView.dispatch(...transactions);
352
+ }
353
+ }
275
354
  function useCodemirrorExtensionCompartment(fn, value, editorViewRef) {
276
355
  var _a, _b;
277
356
  const extensionCreatorRef = (0, react_1.useRef)(fn);
@@ -281,16 +360,22 @@ function useCodemirrorExtensionCompartment(fn, value, editorViewRef) {
281
360
  const initialExtensionRef = (0, react_1.useRef)();
282
361
  (_b = initialExtensionRef.current) !== null && _b !== void 0 ? _b : (initialExtensionRef.current = compartmentRef.current.of(extensionCreatorRef.current()));
283
362
  (0, compass_components_1.useEffectOnChange)(() => {
284
- var _a, _b;
285
- (_a = editorViewRef.current) === null || _a === void 0 ? void 0 : _a.dispatch({
286
- effects: (_b = compartmentRef.current) === null || _b === void 0 ? void 0 : _b.reconfigure(extensionCreatorRef.current()),
287
- });
363
+ var _a;
364
+ if (!editorViewRef.current) {
365
+ return;
366
+ }
367
+ const controller = new AbortController();
368
+ sheduleDispatch(editorViewRef.current, {
369
+ effects: (_a = compartmentRef.current) === null || _a === void 0 ? void 0 : _a.reconfigure(extensionCreatorRef.current()),
370
+ }, controller.signal);
371
+ return () => {
372
+ controller.abort();
373
+ };
288
374
  }, value);
289
375
  return initialExtensionRef.current;
290
376
  }
291
- const BaseEditor = ({ initialText: _initialText, text, onChangeText = () => {
292
- }, language = 'json', showLineNumbers = true, showFoldGutter = true, annotations = [], completer, darkMode: _darkMode, className, readOnly = false, onLoad = () => {
293
- }, ...props }) => {
377
+ const BaseEditor = react_1.default.forwardRef(function BaseEditor({ initialText: _initialText, text, onChangeText, language = 'json', showLineNumbers = true, showFoldGutter = true, showAnnotationsGutter = true, showScroll = true, highlightActiveLine: shouldHighlightActiveLine = true, annotations, completer, darkMode: _darkMode, className, readOnly = false, onLoad = () => {
378
+ }, minLines, maxLines, lineHeight = 16, placeholder: placeholderString, commands, ...props }, ref) {
294
379
  const darkMode = (0, compass_components_1.useDarkMode)(_darkMode);
295
380
  const onChangeTextRef = (0, react_1.useRef)(onChangeText);
296
381
  const onLoadRef = (0, react_1.useRef)(onLoad);
@@ -298,28 +383,99 @@ const BaseEditor = ({ initialText: _initialText, text, onChangeText = () => {
298
383
  const initialText = (0, react_1.useRef)(_initialText !== null && _initialText !== void 0 ? _initialText : text);
299
384
  const initialLanguage = (0, react_1.useRef)(language);
300
385
  const containerRef = (0, react_1.useRef)(null);
386
+ const editorContainerRef = (0, react_1.useRef)(null);
301
387
  const editorViewRef = (0, react_1.useRef)();
388
+ const [{ height: contentHeight, hasScroll }, setContentHeight] = (0, react_1.useState)({
389
+ height: 0,
390
+ hasScroll: false,
391
+ });
302
392
  onChangeTextRef.current = onChangeText;
303
393
  onLoadRef.current = onLoad;
394
+ (0, react_1.useImperativeHandle)(ref, () => {
395
+ return {
396
+ foldAll() {
397
+ if (!editorViewRef.current) {
398
+ return false;
399
+ }
400
+ return foldAll(editorViewRef.current);
401
+ },
402
+ unfoldAll() {
403
+ if (!editorViewRef.current) {
404
+ return false;
405
+ }
406
+ return (0, language_1.unfoldAll)(editorViewRef.current);
407
+ },
408
+ copyAll() {
409
+ if (!editorViewRef.current) {
410
+ return false;
411
+ }
412
+ return copyAll(editorViewRef.current);
413
+ },
414
+ prettify() {
415
+ if (!editorViewRef.current) {
416
+ return false;
417
+ }
418
+ return prettify(editorViewRef.current);
419
+ },
420
+ applySnippet(template) {
421
+ if (!editorViewRef.current) {
422
+ return false;
423
+ }
424
+ return applySnippet(editorViewRef.current, template);
425
+ },
426
+ focus() {
427
+ if (!editorViewRef.current) {
428
+ return false;
429
+ }
430
+ editorViewRef.current.focus();
431
+ return true;
432
+ },
433
+ get editor() {
434
+ var _a;
435
+ return (_a = editorViewRef.current) !== null && _a !== void 0 ? _a : null;
436
+ },
437
+ };
438
+ }, []);
304
439
  const languageExtension = useCodemirrorExtensionCompartment(() => {
305
- return [languages[language](), languageName.of(language)];
440
+ return [exports.languages[language](), exports.languageName.of(language)];
306
441
  }, language, editorViewRef);
442
+ const activeLineExtension = useCodemirrorExtensionCompartment(() => {
443
+ return !readOnly && shouldHighlightActiveLine
444
+ ? [(0, view_1.highlightActiveLine)(), (0, view_1.highlightActiveLineGutter)()]
445
+ : [];
446
+ }, [readOnly, shouldHighlightActiveLine], editorViewRef);
307
447
  const readOnlyExtension = useCodemirrorExtensionCompartment(() => {
308
- return [state_1.EditorState.readOnly.of(readOnly)].concat(readOnly ? [] : [(0, view_1.highlightActiveLine)(), (0, view_1.highlightActiveLineGutter)()]);
448
+ return state_1.EditorState.readOnly.of(readOnly);
309
449
  }, readOnly, editorViewRef);
310
450
  const themeConfigExtension = useCodemirrorExtensionCompartment(() => {
311
451
  return themeStyles[darkMode ? 'dark' : 'light'];
312
452
  }, darkMode, editorViewRef);
453
+ const lineHeightExtension = useCodemirrorExtensionCompartment(() => {
454
+ return view_1.EditorView.theme({
455
+ '& .cm-scroller': {
456
+ lineHeight: `${lineHeight}px`,
457
+ ...(maxLines && {
458
+ maxHeight: `${maxLines * lineHeight}px`,
459
+ }),
460
+ height: '100%',
461
+ overflowY: 'auto',
462
+ },
463
+ '& .cm-content, & .cm-gutter': {
464
+ ...(minLines && { minHeight: `${minLines * lineHeight}px` }),
465
+ },
466
+ });
467
+ }, [minLines, maxLines, lineHeight], editorViewRef);
313
468
  const lineNumbersExtension = useCodemirrorExtensionCompartment(() => {
314
469
  return showLineNumbers ? (0, view_1.lineNumbers)() : [];
315
470
  }, showLineNumbers, editorViewRef);
316
471
  const foldGutterExtension = useCodemirrorExtensionCompartment(() => {
317
472
  return showFoldGutter ? createFoldGutterExtension() : [];
318
473
  }, showFoldGutter, editorViewRef);
474
+ const shouldShowAnnotationsGutter = showAnnotationsGutter || (annotations && annotations.length === 0);
319
475
  const annotationsGutterExtension = useCodemirrorExtensionCompartment(() => {
320
- return annotations.length === 0 ? [] : (0, lint_1.lintGutter)();
321
- }, annotations.length === 0, editorViewRef);
322
- const autocomletionExtension = useCodemirrorExtensionCompartment(() => {
476
+ return shouldShowAnnotationsGutter ? (0, lint_1.lintGutter)() : [];
477
+ }, shouldShowAnnotationsGutter, editorViewRef);
478
+ const autocompletionExtension = useCodemirrorExtensionCompartment(() => {
323
479
  return completer
324
480
  ? (0, autocomplete_1.autocompletion)({
325
481
  activateOnTyping: true,
@@ -327,28 +483,62 @@ const BaseEditor = ({ initialText: _initialText, text, onChangeText = () => {
327
483
  })
328
484
  : [];
329
485
  }, completer, editorViewRef);
486
+ const placeholderExtension = useCodemirrorExtensionCompartment(() => {
487
+ return placeholderString ? (0, view_1.placeholder)(placeholderString) : [];
488
+ }, placeholderString, editorViewRef);
489
+ const commandsExtension = useCodemirrorExtensionCompartment(() => {
490
+ return commands && commands.length > 0 ? view_1.keymap.of(commands) : [];
491
+ }, commands, editorViewRef);
492
+ const updateEditorContentHeight = (0, react_1.useCallback)(() => {
493
+ var _a;
494
+ (_a = editorViewRef.current) === null || _a === void 0 ? void 0 : _a.requestMeasure({
495
+ read(view) {
496
+ return [
497
+ view.contentHeight,
498
+ view.scrollDOM.scrollWidth > view.scrollDOM.clientWidth,
499
+ ];
500
+ },
501
+ write([height, hasScroll]) {
502
+ setContentHeight((state) => {
503
+ if (height !== state.height || hasScroll !== state.hasScroll) {
504
+ return { height, hasScroll };
505
+ }
506
+ return state;
507
+ });
508
+ },
509
+ });
510
+ }, []);
330
511
  (0, react_1.useLayoutEffect)(() => {
331
- if (!containerRef.current) {
512
+ if (!editorContainerRef.current) {
332
513
  throw new Error("Can't mount editor: DOM node is missing");
333
514
  }
334
- const domNode = containerRef.current;
515
+ const domNode = editorContainerRef.current;
335
516
  const editor = (editorViewRef.current = new view_1.EditorView({
336
517
  doc: initialText.current,
337
518
  extensions: [
519
+ state_1.EditorState.tabSize.of(2),
520
+ annotationsGutterExtension,
338
521
  lineNumbersExtension,
339
- (0, commands_1.history)(),
340
522
  foldGutterExtension,
523
+ (0, commands_1.history)(),
341
524
  (0, view_1.drawSelection)(),
342
525
  (0, language_1.indentOnInput)(),
343
526
  (0, language_1.bracketMatching)(),
344
527
  (0, autocomplete_1.closeBrackets)(),
345
- autocomletionExtension,
346
- annotationsGutterExtension,
528
+ autocompletionExtension,
347
529
  languageExtension,
348
530
  (0, language_2.syntaxHighlighting)(highlightStyles['light']),
349
531
  (0, language_2.syntaxHighlighting)(highlightStyles['dark']),
532
+ activeLineExtension,
533
+ lineHeightExtension,
350
534
  themeConfigExtension,
535
+ placeholderExtension,
536
+ commandsExtension,
351
537
  view_1.keymap.of([
538
+ {
539
+ key: 'Tab',
540
+ run: autocomplete_1.acceptCompletion,
541
+ },
352
542
  {
353
543
  key: 'Ctrl-Shift-b',
354
544
  run: prettify,
@@ -362,14 +552,15 @@ const BaseEditor = ({ initialText: _initialText, text, onChangeText = () => {
362
552
  ...commands_1.historyKeymap,
363
553
  ...language_1.foldKeymap,
364
554
  ...autocomplete_1.completionKeymap,
365
- commands_1.indentWithTab,
555
+ breakFocusOutBinding,
366
556
  ]),
367
557
  readOnlyExtension,
368
558
  view_1.EditorView.updateListener.of((update) => {
369
- var _a;
559
+ var _a, _b;
560
+ updateEditorContentHeight();
370
561
  if (update.docChanged) {
371
562
  const text = (_a = editor.state.sliceDoc()) !== null && _a !== void 0 ? _a : '';
372
- onChangeTextRef.current(text, update);
563
+ (_b = onChangeTextRef.current) === null || _b === void 0 ? void 0 : _b.call(onChangeTextRef, text, update);
373
564
  }
374
565
  }),
375
566
  ],
@@ -387,6 +578,7 @@ const BaseEditor = ({ initialText: _initialText, text, onChangeText = () => {
387
578
  else {
388
579
  }
389
580
  }
581
+ updateEditorContentHeight();
390
582
  return () => {
391
583
  delete domNode._cm;
392
584
  editor.destroy();
@@ -398,32 +590,66 @@ const BaseEditor = ({ initialText: _initialText, text, onChangeText = () => {
398
590
  lineNumbersExtension,
399
591
  readOnlyExtension,
400
592
  themeConfigExtension,
401
- autocomletionExtension,
593
+ autocompletionExtension,
594
+ lineHeightExtension,
595
+ activeLineExtension,
596
+ placeholderExtension,
597
+ commandsExtension,
598
+ updateEditorContentHeight,
402
599
  ]);
403
600
  (0, react_1.useEffect)(() => {
404
- var _a, _b;
601
+ var _a;
405
602
  if (initialTextProvided.current) {
406
603
  return;
407
604
  }
408
- if (text !== ((_a = editorViewRef.current) === null || _a === void 0 ? void 0 : _a.state.sliceDoc())) {
409
- (_b = editorViewRef.current) === null || _b === void 0 ? void 0 : _b.dispatch({
605
+ if (editorViewRef.current &&
606
+ text !== ((_a = editorViewRef.current.state.sliceDoc()) !== null && _a !== void 0 ? _a : '')) {
607
+ const controller = new AbortController();
608
+ sheduleDispatch(editorViewRef.current, {
410
609
  changes: {
411
610
  from: 0,
412
611
  to: editorViewRef.current.state.doc.length,
413
612
  insert: text,
414
613
  },
415
- });
614
+ }, controller.signal);
615
+ return () => {
616
+ controller.abort();
617
+ };
416
618
  }
417
619
  }, [text]);
418
620
  (0, react_1.useEffect)(() => {
419
- var _a;
420
- (_a = editorViewRef.current) === null || _a === void 0 ? void 0 : _a.dispatch({
421
- effects: lint_1.setDiagnosticsEffect.of(annotations),
422
- });
621
+ if (!editorViewRef.current) {
622
+ return;
623
+ }
624
+ const controller = new AbortController();
625
+ sheduleDispatch(editorViewRef.current, {
626
+ effects: lint_1.setDiagnosticsEffect.of(annotations !== null && annotations !== void 0 ? annotations : []),
627
+ }, controller.signal);
628
+ return () => {
629
+ controller.abort();
630
+ };
423
631
  }, [annotations]);
424
- return (react_1.default.createElement("div", { ref: containerRef, className: (0, compass_components_1.cx)(editorStyle, className), "data-codemirror": "true", ...props }));
425
- };
426
- exports.JSONEditor = BaseEditor;
632
+ (0, react_1.useLayoutEffect)(() => {
633
+ if (containerRef.current) {
634
+ const scrollHeight = hasScroll && showScroll ? 10 : 0;
635
+ const height = Math.min(contentHeight, (maxLines !== null && maxLines !== void 0 ? maxLines : Infinity) * lineHeight) +
636
+ scrollHeight;
637
+ containerRef.current.style.height = `${height}px`;
638
+ }
639
+ }, [maxLines, contentHeight, hasScroll, lineHeight, showScroll]);
640
+ return (react_1.default.createElement("div", { ref: containerRef, className: className, style: {
641
+ width: '100%',
642
+ minHeight: Math.max(lineHeight, (minLines !== null && minLines !== void 0 ? minLines : 0) * lineHeight),
643
+ position: 'relative',
644
+ maxHeight: '100%',
645
+ } },
646
+ react_1.default.createElement("div", { ref: editorContainerRef, className: (0, compass_components_1.cx)(editorStyle, !showScroll && hiddenScrollStyle), style: {
647
+ position: 'absolute',
648
+ width: '100%',
649
+ height: '100%',
650
+ }, "data-codemirror": "true", ...props })));
651
+ });
652
+ exports.BaseEditor = BaseEditor;
427
653
  function isTopNode(node) {
428
654
  return !node
429
655
  ? true
@@ -433,6 +659,16 @@ function isTopNode(node) {
433
659
  ? true
434
660
  : isTopNode(node.parent);
435
661
  }
662
+ const applySnippet = (editor, template) => {
663
+ const completion = (0, autocomplete_1.snippetCompletion)(template, { label: template });
664
+ if (typeof completion.apply === 'function') {
665
+ completion.apply(editor, completion, 0, editor.state.doc.length);
666
+ return true;
667
+ }
668
+ else {
669
+ return false;
670
+ }
671
+ };
436
672
  const foldAll = (editor) => {
437
673
  const foldableProperties = [];
438
674
  (0, language_1.syntaxTree)(editor.state).iterate({
@@ -452,7 +688,7 @@ const foldAll = (editor) => {
452
688
  },
453
689
  });
454
690
  if (foldableProperties.length > 0) {
455
- editor.dispatch({
691
+ sheduleDispatch(editor, {
456
692
  effects: foldableProperties.map((range) => {
457
693
  return language_1.foldEffect.of(range);
458
694
  }),
@@ -468,17 +704,18 @@ const prettify = (editorView) => {
468
704
  if (editorView.state.facet(state_1.EditorState.readOnly)) {
469
705
  return false;
470
706
  }
471
- const language = editorView.state.facet(languageName)[0];
707
+ const language = editorView.state.facet(exports.languageName)[0];
472
708
  const doc = editorView.state.sliceDoc();
473
709
  try {
474
710
  const formatted = (0, prettify_1.prettify)(doc, language === 'json' ? 'json' : 'javascript-expression');
475
711
  if (formatted !== doc) {
476
- editorView.dispatch({
712
+ sheduleDispatch(editorView, {
477
713
  changes: {
478
714
  from: 0,
479
715
  to: editorView.state.doc.length,
480
716
  insert: formatted,
481
717
  },
718
+ scrollIntoView: true,
482
719
  });
483
720
  return true;
484
721
  }
@@ -487,8 +724,94 @@ const prettify = (editorView) => {
487
724
  }
488
725
  return false;
489
726
  };
490
- BaseEditor.foldAll = foldAll;
491
- BaseEditor.unfoldAll = language_1.unfoldAll;
492
- BaseEditor.copyAll = copyAll;
493
- BaseEditor.prettify = prettify;
727
+ const inlineStyles = (0, compass_components_1.css)({
728
+ '& .cm-editor': {
729
+ backgroundColor: 'transparent',
730
+ },
731
+ });
732
+ const InlineEditor = react_1.default.forwardRef(function InlineEditor({ className, ...props }, forwardRef) {
733
+ return (react_1.default.createElement(BaseEditor, { ref: forwardRef, maxLines: 10, showFoldGutter: false, showLineNumbers: false, showAnnotationsGutter: false, showScroll: false, highlightActiveLine: false, className: (0, compass_components_1.cx)(inlineStyles, className), language: "javascript", ...props }));
734
+ });
735
+ exports.CodemirrorInlineEditor = InlineEditor;
736
+ const multilineEditorContainerStyle = (0, compass_components_1.css)({
737
+ position: 'relative',
738
+ height: '100%',
739
+ [`&:focus-within > .multiline-editor-actions,
740
+ &:hover > .multiline-editor-actions`]: {
741
+ display: 'flex',
742
+ },
743
+ });
744
+ const actionsContainerStyle = (0, compass_components_1.css)({
745
+ position: 'absolute',
746
+ top: compass_components_1.spacing[1],
747
+ right: compass_components_1.spacing[2],
748
+ display: 'none',
749
+ gap: compass_components_1.spacing[2],
750
+ });
751
+ const MultilineEditor = react_1.default.forwardRef(function MultilineEditor({ customActions, copyable = true, formattable = true, className, editorClassName, actionsClassName, ...props }, ref) {
752
+ const containerRef = (0, react_1.useRef)(null);
753
+ const editorRef = (0, react_1.useRef)(null);
754
+ (0, react_1.useImperativeHandle)(ref, () => {
755
+ return {
756
+ foldAll() {
757
+ var _a, _b;
758
+ return (_b = (_a = editorRef.current) === null || _a === void 0 ? void 0 : _a.foldAll()) !== null && _b !== void 0 ? _b : false;
759
+ },
760
+ unfoldAll() {
761
+ var _a, _b;
762
+ return (_b = (_a = editorRef.current) === null || _a === void 0 ? void 0 : _a.unfoldAll()) !== null && _b !== void 0 ? _b : false;
763
+ },
764
+ copyAll() {
765
+ var _a, _b;
766
+ return (_b = (_a = editorRef.current) === null || _a === void 0 ? void 0 : _a.copyAll()) !== null && _b !== void 0 ? _b : false;
767
+ },
768
+ prettify() {
769
+ var _a, _b;
770
+ return (_b = (_a = editorRef.current) === null || _a === void 0 ? void 0 : _a.prettify()) !== null && _b !== void 0 ? _b : false;
771
+ },
772
+ focus() {
773
+ var _a, _b;
774
+ return (_b = (_a = editorRef.current) === null || _a === void 0 ? void 0 : _a.focus()) !== null && _b !== void 0 ? _b : false;
775
+ },
776
+ applySnippet(template) {
777
+ var _a, _b;
778
+ return (_b = (_a = editorRef.current) === null || _a === void 0 ? void 0 : _a.applySnippet(template)) !== null && _b !== void 0 ? _b : false;
779
+ },
780
+ get editor() {
781
+ var _a, _b;
782
+ return (_b = (_a = editorRef.current) === null || _a === void 0 ? void 0 : _a.editor) !== null && _b !== void 0 ? _b : null;
783
+ },
784
+ };
785
+ }, []);
786
+ const actions = (0, react_1.useMemo)(() => {
787
+ return [
788
+ copyable && (react_1.default.createElement(actions_1.ActionButton, { key: "Copy", label: "Copy", icon: "Copy", onClick: () => {
789
+ var _a, _b;
790
+ return (_b = (_a = editorRef.current) === null || _a === void 0 ? void 0 : _a.copyAll()) !== null && _b !== void 0 ? _b : false;
791
+ } })),
792
+ formattable && (react_1.default.createElement(actions_1.ActionButton, { key: "Format", label: "Format", icon: react_1.default.createElement(actions_1.FormatIcon, { size: 14, role: "presentation" }), onClick: () => {
793
+ var _a, _b;
794
+ return (_b = (_a = editorRef.current) === null || _a === void 0 ? void 0 : _a.prettify()) !== null && _b !== void 0 ? _b : false;
795
+ } })),
796
+ ...(customActions !== null && customActions !== void 0 ? customActions : []).map((action) => {
797
+ return (react_1.default.createElement(actions_1.ActionButton, { key: action.label, icon: action.icon, label: action.label, onClick: () => {
798
+ var _a;
799
+ if (!((_a = editorRef.current) === null || _a === void 0 ? void 0 : _a.editor)) {
800
+ return false;
801
+ }
802
+ return action.action(editorRef.current.editor);
803
+ } }));
804
+ }),
805
+ ];
806
+ }, [copyable, formattable, customActions]);
807
+ return (react_1.default.createElement("div", { ref: containerRef, className: (0, compass_components_1.cx)(multilineEditorContainerStyle, className), onClick: (evt) => {
808
+ var _a;
809
+ if (evt.target === containerRef.current) {
810
+ (_a = editorRef.current) === null || _a === void 0 ? void 0 : _a.focus();
811
+ }
812
+ } },
813
+ react_1.default.createElement(BaseEditor, { ref: editorRef, className: editorClassName, language: "javascript", minLines: 10, ...props }),
814
+ actions.length > 0 && (react_1.default.createElement("div", { className: (0, compass_components_1.cx)('multiline-editor-actions', actionsContainerStyle, actionsClassName) }, actions))));
815
+ });
816
+ exports.CodemirrorMultilineEditor = MultilineEditor;
494
817
  //# sourceMappingURL=json-editor.js.map