@difizen/libro-jupyter 0.1.1 → 0.1.2

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 (100) hide show
  1. package/es/add-between-cell/add-between-cell.d.ts.map +1 -1
  2. package/es/add-between-cell/add-between-cell.js +7 -7
  3. package/es/add-between-cell/index.less +6 -0
  4. package/es/cell/jupyter-code-cell-model.d.ts +2 -2
  5. package/es/cell/jupyter-code-cell-model.d.ts.map +1 -1
  6. package/es/cell/jupyter-code-cell-model.js +7 -3
  7. package/es/cell/jupyter-code-cell-view.d.ts +9 -4
  8. package/es/cell/jupyter-code-cell-view.d.ts.map +1 -1
  9. package/es/cell/jupyter-code-cell-view.js +137 -100
  10. package/es/command/command-contribution.d.ts.map +1 -1
  11. package/es/command/command-contribution.js +9 -9
  12. package/es/components/cell-execution-tip.d.ts.map +1 -1
  13. package/es/components/cell-execution-tip.js +14 -1
  14. package/es/components/cell-input-bottom-blank.d.ts.map +1 -1
  15. package/es/components/cell-input-bottom-blank.js +4 -4
  16. package/es/config/config-contribution.d.ts +2 -2
  17. package/es/config/config-contribution.d.ts.map +1 -1
  18. package/es/config/config-contribution.js +7 -7
  19. package/es/config/config.d.ts +6 -1
  20. package/es/config/config.d.ts.map +1 -1
  21. package/es/config/config.js +15 -1
  22. package/es/config/index.d.ts +1 -0
  23. package/es/config/index.d.ts.map +1 -1
  24. package/es/config/index.js +2 -1
  25. package/es/file/file-command.d.ts.map +1 -1
  26. package/es/file/file-command.js +6 -2
  27. package/es/file/navigatable-view.d.ts +7 -2
  28. package/es/file/navigatable-view.d.ts.map +1 -1
  29. package/es/file/navigatable-view.js +41 -6
  30. package/es/file/open-handler-contribution.js +1 -1
  31. package/es/index.d.ts +17 -15
  32. package/es/index.d.ts.map +1 -1
  33. package/es/index.js +17 -15
  34. package/es/keybind-instructions/index.less +2 -2
  35. package/es/keybind-instructions/keybind-instructions-contribution.js +2 -2
  36. package/es/libro-jupyter-model.d.ts +8 -4
  37. package/es/libro-jupyter-model.d.ts.map +1 -1
  38. package/es/libro-jupyter-model.js +24 -17
  39. package/es/libro-jupyter-protocol.d.ts +4 -0
  40. package/es/libro-jupyter-protocol.d.ts.map +1 -1
  41. package/es/libro-jupyter-protocol.js +2 -1
  42. package/es/libro-jupyter-server-launch-manager.d.ts +3 -1
  43. package/es/libro-jupyter-server-launch-manager.d.ts.map +1 -1
  44. package/es/libro-jupyter-server-launch-manager.js +9 -2
  45. package/es/libro-jupyter-view.d.ts +2 -1
  46. package/es/libro-jupyter-view.d.ts.map +1 -1
  47. package/es/libro-jupyter-view.js +4 -2
  48. package/es/module.d.ts.map +1 -1
  49. package/es/module.js +12 -10
  50. package/es/output/libro-jupyter-outputarea.d.ts +3 -0
  51. package/es/output/libro-jupyter-outputarea.d.ts.map +1 -1
  52. package/es/output/libro-jupyter-outputarea.js +49 -4
  53. package/es/rendermime/index.less +12 -1
  54. package/es/rendermime/plotly-renderers.d.ts +15 -14
  55. package/es/rendermime/plotly-renderers.d.ts.map +1 -1
  56. package/es/rendermime/plotly-renderers.js +1 -3
  57. package/es/toolbar/kernel-selector-dropdown.d.ts.map +1 -1
  58. package/es/toolbar/kernel-selector-dropdown.js +2 -6
  59. package/es/typings/index.d.ts +7 -2
  60. package/package.json +16 -14
  61. package/src/add-between-cell/add-between-cell.tsx +17 -8
  62. package/src/add-between-cell/index.less +6 -0
  63. package/src/cell/jupyter-code-cell-model.ts +6 -4
  64. package/src/cell/jupyter-code-cell-view.tsx +81 -48
  65. package/src/command/command-contribution.ts +13 -9
  66. package/src/components/cell-execution-tip.tsx +8 -2
  67. package/src/components/cell-input-bottom-blank.tsx +10 -5
  68. package/src/config/config-contribution.ts +3 -3
  69. package/src/config/config.ts +17 -2
  70. package/src/config/index.ts +1 -0
  71. package/src/file/file-command.tsx +5 -2
  72. package/src/file/navigatable-view.tsx +39 -1
  73. package/src/file/open-handler-contribution.ts +1 -1
  74. package/src/index.spec.ts +1 -5
  75. package/src/index.ts +17 -16
  76. package/src/keybind-instructions/index.less +2 -2
  77. package/src/keybind-instructions/keybind-instructions-contribution.ts +2 -2
  78. package/src/libro-jupyter-model.ts +34 -20
  79. package/src/libro-jupyter-protocol.ts +5 -0
  80. package/src/libro-jupyter-server-launch-manager.ts +11 -2
  81. package/src/libro-jupyter-view.tsx +4 -1
  82. package/src/module.ts +23 -15
  83. package/src/output/libro-jupyter-outputarea.tsx +31 -3
  84. package/src/rendermime/index.less +12 -1
  85. package/src/rendermime/plotly-render.tsx +1 -1
  86. package/src/rendermime/plotly-renderers.ts +15 -17
  87. package/src/toolbar/kernel-selector-dropdown.tsx +2 -6
  88. package/src/typings/index.d.ts +7 -2
  89. package/es/configuration/index.d.ts +0 -3
  90. package/es/configuration/index.d.ts.map +0 -1
  91. package/es/configuration/index.js +0 -2
  92. package/es/configuration/libro-configuration-contribution.d.ts +0 -5
  93. package/es/configuration/libro-configuration-contribution.d.ts.map +0 -1
  94. package/es/configuration/libro-configuration-contribution.js +0 -24
  95. package/es/configuration/libro-configuration.d.ts +0 -3
  96. package/es/configuration/libro-configuration.d.ts.map +0 -1
  97. package/es/configuration/libro-configuration.js +0 -12
  98. package/src/configuration/index.ts +0 -2
  99. package/src/configuration/libro-configuration-contribution.ts +0 -11
  100. package/src/configuration/libro-configuration.ts +0 -14
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@difizen/libro-jupyter",
3
- "version": "0.1.1",
3
+ "version": "0.1.2",
4
4
  "description": "",
5
5
  "keywords": [
6
6
  "libro"
@@ -31,19 +31,21 @@
31
31
  "src"
32
32
  ],
33
33
  "dependencies": {
34
- "@difizen/libro-code-editor": "^0.1.1",
35
- "@difizen/libro-codemirror": "^0.1.1",
36
- "@difizen/libro-codemirror-code-cell": "^0.1.1",
37
- "@difizen/libro-codemirror-markdown-cell": "^0.1.1",
38
- "@difizen/libro-codemirror-raw-cell": "^0.1.1",
39
- "@difizen/libro-rendermime": "^0.1.1",
40
- "@difizen/libro-common": "^0.1.1",
41
- "@difizen/libro-core": "^0.1.1",
42
- "@difizen/libro-kernel": "^0.1.1",
43
- "@difizen/libro-l10n": "^0.1.1",
44
- "@difizen/libro-output": "^0.1.1",
45
- "@difizen/libro-search": "^0.1.1",
46
- "@difizen/libro-search-codemirror-cell": "^0.1.1",
34
+ "@difizen/libro-cofine-editor": "^0.1.2",
35
+ "@difizen/libro-code-editor": "^0.1.2",
36
+ "@difizen/libro-code-cell": "^0.1.2",
37
+ "@difizen/libro-codemirror": "^0.1.2",
38
+ "@difizen/libro-rendermime": "^0.1.2",
39
+ "@difizen/libro-common": "^0.1.2",
40
+ "@difizen/libro-core": "^0.1.2",
41
+ "@difizen/libro-kernel": "^0.1.2",
42
+ "@difizen/libro-l10n": "^0.1.2",
43
+ "@difizen/libro-output": "^0.1.2",
44
+ "@difizen/libro-search": "^0.1.2",
45
+ "@difizen/libro-search-code-cell": "^0.1.2",
46
+ "@difizen/libro-lsp": "^0.1.2",
47
+ "@difizen/libro-markdown-cell": "^0.1.2",
48
+ "@difizen/libro-raw-cell": "^0.1.2",
47
49
  "@difizen/mana-app": "latest",
48
50
  "@difizen/mana-l10n": "latest",
49
51
  "@ant-design/colors": "^7.0.0",
@@ -1,5 +1,5 @@
1
1
  import { DisplayWrapComponent } from '@difizen/libro-common';
2
- import type { BetweenCellProvider, LibroView } from '@difizen/libro-core';
2
+ import type { BetweenCellProvider, CellOptions, LibroView } from '@difizen/libro-core';
3
3
  import { CellService } from '@difizen/libro-core';
4
4
  import { CommandRegistry, useInject, ViewInstance } from '@difizen/mana-app';
5
5
  import { l10n } from '@difizen/mana-l10n';
@@ -36,8 +36,13 @@ const AddCellOutlined: React.FC = () => (
36
36
 
37
37
  // eslint-disable-next-line @typescript-eslint/no-unused-vars
38
38
  export const LibroCommonBetweenCellContent: BetweenCellProvider = forwardRef(
39
- function LibroCommonBetweenCellContent(props, _ref) {
40
- // eslint-disable-next-line react/prop-types
39
+ function LibroCommonBetweenCellContent(
40
+ props: {
41
+ index: number;
42
+ addCell: (option: CellOptions, position?: number | undefined) => Promise<void>;
43
+ },
44
+ ref,
45
+ ) {
41
46
  const { addCell, index } = props;
42
47
  const { cellsMeta } = useInject<CellService>(CellService);
43
48
  const anchorRef = useRef<HTMLDivElement>(null);
@@ -62,7 +67,7 @@ export const LibroCommonBetweenCellContent: BetweenCellProvider = forwardRef(
62
67
  clearTimeout(delayRef.current);
63
68
  };
64
69
 
65
- const openTooltip = (_nextOpen: boolean, delay = 0.5) => {
70
+ const openTooltip = (nextOpen: boolean, delay = 0.5) => {
66
71
  clearDelay();
67
72
 
68
73
  if (delay === 0) {
@@ -117,7 +122,7 @@ export const LibroCommonBetweenCellContent: BetweenCellProvider = forwardRef(
117
122
  tabIndex={10}
118
123
  className="libro-add-between-cell-anchor"
119
124
  style={{
120
- position: 'fixed',
125
+ position: 'absolute',
121
126
  top: position.top + 5,
122
127
  left: position.left + 5,
123
128
  width: 1,
@@ -153,7 +158,9 @@ export const LibroCommonBetweenCellContent: BetweenCellProvider = forwardRef(
153
158
  closeTooltip();
154
159
  setGutterVisible(true);
155
160
  setMenuVisible(true);
156
- setPosition({ top: e.clientY, left: e.clientX });
161
+
162
+ // TODO: 位置不准确
163
+ setPosition({ top: e.nativeEvent.offsetY, left: e.nativeEvent.offsetX });
157
164
  anchorRef.current?.focus();
158
165
  }}
159
166
  >
@@ -189,8 +196,10 @@ export const LibroCommonBetweenCellContent: BetweenCellProvider = forwardRef(
189
196
  },
190
197
  );
191
198
 
192
- export const LibroWrappedBetweenCellContent: BetweenCellProvider = (props) => {
193
- // eslint-disable-next-line react/prop-types
199
+ export const LibroWrappedBetweenCellContent: BetweenCellProvider = (props: {
200
+ index: number;
201
+ addCell: (option: CellOptions, position?: number | undefined) => Promise<void>;
202
+ }) => {
194
203
  const { index, addCell } = props;
195
204
  const instance = useInject<LibroView>(ViewInstance);
196
205
  return (
@@ -101,3 +101,9 @@
101
101
  outline: none;
102
102
  cursor: pointer;
103
103
  }
104
+
105
+ .ReactVirtualized__List {
106
+ .libro-add-between-cell-area {
107
+ width: calc(100% - 45px);
108
+ }
109
+ }
@@ -1,12 +1,12 @@
1
- import { LibroCodeCellModel } from '@difizen/libro-codemirror-code-cell';
1
+ import { LibroCodeCellModel } from '@difizen/libro-code-cell';
2
2
  import type { ICellMetadata } from '@difizen/libro-common';
3
3
  import { CellOptions } from '@difizen/libro-core';
4
4
  import { inject, transient } from '@difizen/mana-app';
5
5
  import { prop, ViewManager } from '@difizen/mana-app';
6
6
 
7
7
  import type {
8
- ExecutedWithKernelCellModel,
9
8
  CodeCellMetadata,
9
+ ExecutedWithKernelCellModel,
10
10
  } from '../libro-jupyter-protocol.js';
11
11
 
12
12
  @transient()
@@ -24,12 +24,14 @@ export class JupyterCodeCellModel
24
24
  @inject(ViewManager) viewManager: ViewManager,
25
25
  ) {
26
26
  super(options, viewManager);
27
- this.metadata = options.cell?.metadata || {};
27
+ this.metadata = {
28
+ ...options?.cell?.metadata,
29
+ libroFormatter: this.libroFormatType,
30
+ };
28
31
  }
29
32
 
30
33
  override clearExecution = () => {
31
34
  this.executeCount = null;
32
- this.executing = false;
33
35
  this.kernelExecuting = false;
34
36
  this.metadata.execution = {};
35
37
  };
@@ -1,4 +1,5 @@
1
- import { CodeEditorView } from '@difizen/libro-code-editor';
1
+ import { CellEditorMemo, LibroCodeCellView } from '@difizen/libro-code-cell';
2
+ import { CodeEditorManager, CodeEditorSettings } from '@difizen/libro-code-editor';
2
3
  import type {
3
4
  CodeEditorViewOptions,
4
5
  CompletionProvider,
@@ -6,14 +7,14 @@ import type {
6
7
  TooltipProvider,
7
8
  TooltipProviderOption,
8
9
  } from '@difizen/libro-code-editor';
9
- import { codeMirrorEditorFactory } from '@difizen/libro-codemirror';
10
- import { CellEditorMemo, LibroCodeCellView } from '@difizen/libro-codemirror-code-cell';
11
10
  import type { CellViewOptions } from '@difizen/libro-core';
12
11
  import { CellService } from '@difizen/libro-core';
13
12
  import { KernelError } from '@difizen/libro-kernel';
13
+ import type { LSPConnection, LSPProvider } from '@difizen/libro-lsp';
14
+ import { ILSPDocumentConnectionManager } from '@difizen/libro-lsp';
14
15
  import { inject, transient } from '@difizen/mana-app';
15
16
  import { view, ViewInstance, ViewManager, ViewOption } from '@difizen/mana-app';
16
- import { getOrigin, useInject, watch } from '@difizen/mana-app';
17
+ import { getOrigin, useInject } from '@difizen/mana-app';
17
18
  import { l10n } from '@difizen/mana-l10n';
18
19
  import { forwardRef } from 'react';
19
20
 
@@ -23,7 +24,7 @@ import type { ExecutionMeta } from '../libro-jupyter-protocol.js';
23
24
  import type { JupyterCodeCellModel } from './jupyter-code-cell-model.js';
24
25
 
25
26
  const JupyterCodeCellComponent = forwardRef<HTMLDivElement>(
26
- function JupyterCodeCellComponent(_props, ref) {
27
+ function JupyterCodeCellComponent(props, ref) {
27
28
  const instance = useInject<JupyterCodeCellView>(ViewInstance);
28
29
  return (
29
30
  <div
@@ -44,51 +45,79 @@ export class JupyterCodeCellView extends LibroCodeCellView {
44
45
  override view = JupyterCodeCellComponent;
45
46
  declare model: JupyterCodeCellModel;
46
47
 
48
+ protected readonly lspDocumentConnectionManager: ILSPDocumentConnectionManager;
49
+
47
50
  constructor(
48
51
  @inject(ViewOption) options: CellViewOptions,
49
52
  @inject(CellService) cellService: CellService,
50
53
  @inject(ViewManager) viewManager: ViewManager,
54
+ @inject(ILSPDocumentConnectionManager)
55
+ lspDocumentConnectionManager: ILSPDocumentConnectionManager,
56
+ @inject(CodeEditorManager) codeEditorManager: CodeEditorManager,
57
+ @inject(CodeEditorSettings) codeEditorSettings: CodeEditorSettings,
51
58
  ) {
52
- super(options, cellService, viewManager);
59
+ super(options, cellService, viewManager, codeEditorManager, codeEditorSettings);
60
+ this.lspDocumentConnectionManager = lspDocumentConnectionManager;
53
61
  }
54
62
 
55
63
  override clearExecution = () => {
56
64
  this.model.clearExecution();
57
- this.outputArea.clear();
65
+ Promise.resolve()
66
+ .then(() => {
67
+ this.outputArea.clear();
68
+ return;
69
+ })
70
+ .catch(console.error);
58
71
  };
59
72
 
60
- override onViewMount() {
61
- const option: CodeEditorViewOptions = {
62
- ...this.options,
63
- factory: (editorOption) =>
64
- codeMirrorEditorFactory({
65
- ...editorOption,
66
- config: {
67
- ...editorOption.config,
68
- ...{ readOnly: this.parent.model.readOnly },
69
- },
70
- }),
71
- model: this.model,
73
+ protected override getEditorOption(): CodeEditorViewOptions {
74
+ const options = super.getEditorOption();
75
+ return {
76
+ ...options,
72
77
  tooltipProvider: this.tooltipProvider,
73
78
  completionProvider: this.completionProvider,
74
- lspProvider: undefined,
79
+ lspProvider: (this.parent.model as LibroJupyterModel).lspEnabled
80
+ ? this.lspProvider
81
+ : undefined,
75
82
  };
76
- this.viewManager
77
- .getOrCreateView<CodeEditorView, CodeEditorViewOptions>(CodeEditorView, option)
78
- .then((editorView) => {
79
- this.editorView = editorView;
80
- this.editorViewReadyDeferred.resolve();
81
- watch(this.parent.model, 'readOnly', () => {
82
- this.editorView?.editor?.setOption('readOnly', this.parent.model.readOnly);
83
- });
84
- this.editorView.onModalChange((val) => (this.hasModal = val));
85
- return;
86
- })
87
- .catch(() => {
88
- //
89
- });
90
83
  }
91
84
 
85
+ lspProvider: LSPProvider = async () => {
86
+ await this.lspDocumentConnectionManager.ready;
87
+ const adapter = this.lspDocumentConnectionManager.adapters.get(
88
+ this.parent.model.id,
89
+ );
90
+ if (!adapter) {
91
+ throw new Error('no adapter');
92
+ }
93
+
94
+ await adapter.ready;
95
+
96
+ const virtualEditor = adapter.getCellEditor(this);
97
+
98
+ if (!virtualEditor) {
99
+ throw new Error('no virtual editor');
100
+ }
101
+
102
+ // Get the associated virtual document of the opened document
103
+ const virtualDocument = adapter.virtualDocument;
104
+
105
+ if (!virtualDocument) {
106
+ throw new Error('no virtualDocument');
107
+ }
108
+
109
+ // Get the LSP connection of the virtual document.
110
+ const lspConnection = this.lspDocumentConnectionManager.connections.get(
111
+ virtualDocument.uri,
112
+ ) as LSPConnection;
113
+
114
+ return {
115
+ virtualDocument,
116
+ lspConnection,
117
+ editor: virtualEditor,
118
+ };
119
+ };
120
+
92
121
  tooltipProvider: TooltipProvider = async (option: TooltipProviderOption) => {
93
122
  const cellContent = this.model.value;
94
123
  const kernelConnection = getOrigin(
@@ -113,7 +142,7 @@ export class JupyterCodeCellView extends LibroCodeCellView {
113
142
  };
114
143
 
115
144
  completionProvider: CompletionProvider = async (option: CompletionProviderOption) => {
116
- const cellContent = this.model.value;
145
+ const cellContent = this.model.source;
117
146
  const kernelConnection = getOrigin(
118
147
  (this.parent.model as LibroJupyterModel).kernelConnection,
119
148
  );
@@ -157,35 +186,37 @@ export class JupyterCodeCellView extends LibroCodeCellView {
157
186
  }
158
187
 
159
188
  const kernelConnection = getOrigin(libroModel.kernelConnection);
160
- const cellContent = this.model.value;
189
+ const cellContent = this.model.source;
161
190
  const cellModel = this.model;
162
191
 
163
192
  try {
164
- this.clearExecution();
193
+ // if (this.outputArea instanceof LibroOutputArea)
194
+ // this.outputArea.lastOutputContainerHeight =
195
+ // this.outputArea.container?.current?.clientHeight;
196
+ cellModel.executing = true;
165
197
  const future = kernelConnection.requestExecute({
166
198
  code: cellContent,
167
199
  });
168
200
 
169
201
  let startTimeStr = '';
170
- cellModel.executing = true;
171
-
172
- cellModel.metadata['execution'] = {
173
- 'shell.execute_reply.started': '',
174
- 'shell.execute_reply.end': '',
175
- to_execute: new Date().toISOString(),
176
- } as ExecutionMeta;
202
+ this.clearExecution();
177
203
 
178
204
  // Handle iopub messages
179
205
  future.onIOPub = (msg: any) => {
180
- cellModel.msgChangeEmitter.fire(msg);
181
206
  if (msg.header.msg_type === 'execute_input') {
207
+ cellModel.metadata.execution = {
208
+ 'shell.execute_reply.started': '',
209
+ 'shell.execute_reply.end': '',
210
+ to_execute: new Date().toISOString(),
211
+ } as ExecutionMeta;
182
212
  cellModel.kernelExecuting = true;
183
213
  startTimeStr = msg.header.date as string;
184
- const meta = cellModel.metadata['execution'] as ExecutionMeta;
214
+ const meta = cellModel.metadata.execution as ExecutionMeta;
185
215
  if (meta) {
186
216
  meta['shell.execute_reply.started'] = startTimeStr;
187
217
  }
188
218
  }
219
+ cellModel.msgChangeEmitter.fire(msg);
189
220
  };
190
221
  // Handle the execute reply.
191
222
  future.onReply = (msg: any) => {
@@ -199,8 +230,10 @@ export class JupyterCodeCellView extends LibroCodeCellView {
199
230
  startTimeStr = msgPromise.metadata['started'] as string;
200
231
  const endTimeStr = msgPromise.header.date;
201
232
 
202
- cellModel.metadata['execution']['shell.execute_reply.started'] = startTimeStr;
203
- cellModel.metadata['execution']['shell.execute_reply.end'] = endTimeStr;
233
+ (cellModel.metadata.execution as ExecutionMeta)['shell.execute_reply.started'] =
234
+ startTimeStr;
235
+ (cellModel.metadata.execution as ExecutionMeta)['shell.execute_reply.end'] =
236
+ endTimeStr;
204
237
 
205
238
  if (!msgPromise) {
206
239
  return true;
@@ -30,12 +30,12 @@ export class LibroJupyterCommandContribution implements CommandContribution {
30
30
  command,
31
31
  KernelCommands['ShowKernelStatusAndSelector'],
32
32
  {
33
- execute: async (_cell, libro) => {
33
+ execute: async (cell, libro) => {
34
34
  if (!libro || !(libro instanceof LibroView)) {
35
35
  return;
36
36
  }
37
37
  },
38
- isVisible: (_cell, libro, path) => {
38
+ isVisible: (cell, libro, path) => {
39
39
  if (!libro || !(libro instanceof LibroView)) {
40
40
  return false;
41
41
  }
@@ -45,7 +45,7 @@ export class LibroJupyterCommandContribution implements CommandContribution {
45
45
  path === LibroToolbarArea.HeaderLeft
46
46
  );
47
47
  },
48
- isEnabled: (_cell, libro) => {
48
+ isEnabled: (cell, libro) => {
49
49
  if (!libro || !(libro instanceof LibroView)) {
50
50
  return false;
51
51
  }
@@ -79,7 +79,7 @@ export class LibroJupyterCommandContribution implements CommandContribution {
79
79
  }
80
80
  return !!cell;
81
81
  },
82
- isEnabled: (_cell, libro) => {
82
+ isEnabled: (cell, libro) => {
83
83
  if (!libro || !(libro instanceof LibroView)) {
84
84
  return false;
85
85
  }
@@ -113,7 +113,7 @@ export class LibroJupyterCommandContribution implements CommandContribution {
113
113
  path === LibroToolbarArea.CellRight
114
114
  );
115
115
  },
116
- isEnabled: (_cell, libro) => {
116
+ isEnabled: (cell, libro) => {
117
117
  if (!libro || !(libro instanceof LibroView)) {
118
118
  return false;
119
119
  }
@@ -129,7 +129,7 @@ export class LibroJupyterCommandContribution implements CommandContribution {
129
129
  command,
130
130
  NotebookCommands['SelectLastRunCell'],
131
131
  {
132
- execute: async (_cell, libro) => {
132
+ execute: async (cell, libro) => {
133
133
  if (!libro || !(libro instanceof LibroView)) {
134
134
  return;
135
135
  }
@@ -137,13 +137,17 @@ export class LibroJupyterCommandContribution implements CommandContribution {
137
137
  libro.model.findRunningCell();
138
138
  }
139
139
  },
140
- isVisible: (_cell, libro, path) => {
140
+ isVisible: (cell, libro, path) => {
141
141
  if (!libro || !(libro instanceof LibroView)) {
142
142
  return false;
143
143
  }
144
- return path === LibroToolbarArea.HeaderCenter && !libro.model.readOnly;
144
+ return (
145
+ !libro?.model.quickEditMode &&
146
+ path === LibroToolbarArea.HeaderCenter &&
147
+ !libro.model.readOnly
148
+ );
145
149
  },
146
- isEnabled: (_cell, libro) => {
150
+ isEnabled: (cell, libro) => {
147
151
  if (!libro || !(libro instanceof LibroView) || libro.model.readOnly) {
148
152
  return false;
149
153
  }
@@ -8,6 +8,7 @@ import {
8
8
  import { useObserve } from '@difizen/mana-app';
9
9
  import classnames from 'classnames';
10
10
  import moment from 'moment';
11
+ import { useState } from 'react';
11
12
 
12
13
  import type { JupyterCodeCellModel } from '../cell/jupyter-code-cell-model.js';
13
14
  import {
@@ -21,6 +22,7 @@ import { InfoCircle } from './icons.js';
21
22
  import './index.less';
22
23
 
23
24
  export function CellExecutionTip({ cell }: { cell: CellView }) {
25
+ const [, setCurrentTime] = useState<number>();
24
26
  const observableCell = useObserve(cell);
25
27
 
26
28
  if (!ExecutableCellView.is(cell)) {
@@ -32,7 +34,8 @@ export function CellExecutionTip({ cell }: { cell: CellView }) {
32
34
  }
33
35
 
34
36
  const isHidden = observableCell.model.hasOutputHidden;
35
- const kernelExecuting = (cell.model as JupyterCodeCellModel).kernelExecuting;
37
+ const kernelExecuting = (cell.model as unknown as JupyterCodeCellModel)
38
+ .kernelExecuting;
36
39
  const executionInfo = parseExecutionInfoFromModel(cell.model);
37
40
 
38
41
  const output = cell.outputArea.outputs;
@@ -73,6 +76,9 @@ export function CellExecutionTip({ cell }: { cell: CellView }) {
73
76
  </div>
74
77
  );
75
78
  } else if (kernelExecuting) {
79
+ setTimeout(() => {
80
+ setCurrentTime(Date.now());
81
+ }, 100);
76
82
  return (
77
83
  <div
78
84
  className={classnames(
@@ -94,7 +100,7 @@ export function CellExecutionTip({ cell }: { cell: CellView }) {
94
100
  <div
95
101
  className={classnames(
96
102
  `libro-cell-execution-tip`,
97
- waitingExecute && 'libro-cell-execution-tip-without-output',
103
+ !existOutput && 'libro-cell-execution-tip-without-output',
98
104
  )}
99
105
  >
100
106
  <div className="libro-cell-execution-tip-border" />
@@ -1,5 +1,5 @@
1
- import { LibroExecutableCellView } from '@difizen/libro-core';
2
1
  import type { CellView } from '@difizen/libro-core';
2
+ import { LibroExecutableCellView, LibroOutputArea } from '@difizen/libro-core';
3
3
  import { useObserve } from '@difizen/mana-app';
4
4
 
5
5
  import { isWaitingExecute } from '../utils/index.js';
@@ -7,16 +7,21 @@ import { isWaitingExecute } from '../utils/index.js';
7
7
  export function CellInputBottomBlank({ cell }: { cell: CellView }) {
8
8
  const observableCell = useObserve(cell) as LibroExecutableCellView;
9
9
 
10
- if (!(cell instanceof LibroExecutableCellView)) {
10
+ if (
11
+ !(cell instanceof LibroExecutableCellView) ||
12
+ !(observableCell.outputArea instanceof LibroOutputArea)
13
+ ) {
11
14
  return null;
12
15
  }
13
16
 
14
17
  const outputs = observableCell.outputArea.outputs;
15
- const hasNoneOutput =
16
- (!outputs || outputs.length === 0) && observableCell.model.executeCount;
18
+ const hasNoneOutput = !outputs || outputs.length === 0;
17
19
 
18
20
  // 有output时 或者 没有被执行过,不显示input底部的空白
19
- if (hasNoneOutput || isWaitingExecute(observableCell.model)) {
21
+ if (
22
+ hasNoneOutput &&
23
+ (observableCell.model.executeCount || isWaitingExecute(observableCell.model))
24
+ ) {
20
25
  return <div className="libro-cell-bottom-blank" />;
21
26
  }
22
27
 
@@ -3,12 +3,12 @@ import { ConfigurationContribution, ConfigurationService } from '@difizen/mana-a
3
3
  import { ApplicationContribution } from '@difizen/mana-app';
4
4
  import { inject, singleton } from '@difizen/mana-app';
5
5
 
6
- import { LibroAutosaveSetting } from './config.js';
6
+ import { LibroJupyterConfiguration } from './config.js';
7
7
 
8
8
  @singleton({ contrib: ConfigurationContribution })
9
- export class LibroSettingContribution implements ConfigurationContribution {
9
+ export class LibroJupyterSettingContribution implements ConfigurationContribution {
10
10
  registerConfigurations() {
11
- return [LibroAutosaveSetting];
11
+ return [LibroJupyterConfiguration.AutoSave, LibroJupyterConfiguration.OpenSlot];
12
12
  }
13
13
  }
14
14
  @singleton({ contrib: ApplicationContribution })
@@ -1,9 +1,8 @@
1
1
  import type { ConfigurationNode } from '@difizen/mana-app';
2
2
  import { l10n } from '@difizen/mana-l10n';
3
3
 
4
- export const LibroAutosaveSetting: ConfigurationNode<boolean> = {
4
+ export const LibroConfigAutoSave: ConfigurationNode<boolean> = {
5
5
  id: 'libro.autosave',
6
-
7
6
  description: l10n.t('是否自动保存修改'),
8
7
  title: 'checkbox',
9
8
  type: 'checkbox',
@@ -12,3 +11,19 @@ export const LibroAutosaveSetting: ConfigurationNode<boolean> = {
12
11
  type: 'boolean',
13
12
  },
14
13
  };
14
+
15
+ export const LibroConfigOpenSlot: ConfigurationNode<string> = {
16
+ id: 'libro.jupyter.open.slot',
17
+ description: '文件默认打开位置',
18
+ title: '文件默认打开位置',
19
+ type: 'checkbox',
20
+ defaultValue: 'main',
21
+ schema: {
22
+ type: 'string',
23
+ },
24
+ };
25
+
26
+ export const LibroJupyterConfiguration = {
27
+ AutoSave: LibroConfigAutoSave,
28
+ OpenSlot: LibroConfigOpenSlot,
29
+ };
@@ -1 +1,2 @@
1
1
  export * from './config-contribution.js';
2
+ export * from './config.js';
@@ -11,7 +11,6 @@ import { ViewManager } from '@difizen/mana-app';
11
11
  import {
12
12
  CommandContribution,
13
13
  FileStatNode,
14
- FileTreeCommand,
15
14
  inject,
16
15
  MenuContribution,
17
16
  ModalService,
@@ -71,6 +70,10 @@ const FileCommands = {
71
70
  id: 'fileTree.command.refresh',
72
71
  label: '刷新',
73
72
  },
73
+ REMOVE: {
74
+ id: 'fileTree.command.remove',
75
+ label: '删除',
76
+ },
74
77
  };
75
78
  export const FileTreeContextMenuPath: MenuPath = ['file-tree-context-menu'];
76
79
 
@@ -177,7 +180,7 @@ export class FileCommandContribution
177
180
  return FileStatNode.is(node) && node.fileStat.isFile;
178
181
  },
179
182
  });
180
- command.registerHandler(FileTreeCommand.REMOVE.id, {
183
+ command.registerHandler(FileCommands.REMOVE.id, {
181
184
  execute: (node) => {
182
185
  if (FileStatNode.is(node)) {
183
186
  const filePath = node.uri.path.toString();