@jupyterlab/notebook-extension 4.6.0-alpha.3 → 4.6.0-alpha.5

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/lib/index.d.ts CHANGED
@@ -7,6 +7,10 @@ import type { JupyterFrontEndPlugin } from '@jupyterlab/application';
7
7
  * A plugin providing a CommandEdit status item.
8
8
  */
9
9
  export declare const commandEditItem: JupyterFrontEndPlugin<void>;
10
+ /**
11
+ * A plugin providing a current cell/total cells status item.
12
+ */
13
+ export declare const cellCounterItem: JupyterFrontEndPlugin<void>;
10
14
  /**
11
15
  * A plugin that provides a execution indicator item to the status bar.
12
16
  */
package/lib/index.js CHANGED
@@ -19,7 +19,7 @@ import { ILauncher } from '@jupyterlab/launcher';
19
19
  import { ILSPCodeExtractorsManager, ILSPDocumentConnectionManager, ILSPFeatureManager, IWidgetLSPAdapterTracker } from '@jupyterlab/lsp';
20
20
  import { IMainMenu } from '@jupyterlab/mainmenu';
21
21
  import { IMetadataFormProvider } from '@jupyterlab/metadataform';
22
- import { CommandEditStatus, ExecutionIndicator, INotebookCellExecutor, INotebookTools, INotebookTracker, INotebookWidgetFactory, NotebookActions, NotebookAdapter, NotebookModelFactory, NotebookPanel, NotebookSearchProvider, NotebookToCFactory, NotebookTools, NotebookTracker, NotebookTrustStatus, NotebookWidgetFactory, setCellExecutor, StaticNotebook, ToolbarItems } from '@jupyterlab/notebook';
22
+ import { CellCounterStatus, CommandEditStatus, ExecutionIndicator, INotebookCellExecutor, INotebookTools, INotebookTracker, INotebookWidgetFactory, NotebookActions, NotebookAdapter, NotebookModelFactory, NotebookPanel, NotebookSearchProvider, NotebookToCFactory, NotebookTools, NotebookTracker, NotebookTrustStatus, NotebookWidgetFactory, setCellExecutor, StaticNotebook, ToolbarItems } from '@jupyterlab/notebook';
23
23
  import { IPropertyInspectorProvider } from '@jupyterlab/property-inspector';
24
24
  import { IMarkdownParser, IRenderMimeRegistry } from '@jupyterlab/rendermime';
25
25
  import { ISettingRegistry } from '@jupyterlab/settingregistry';
@@ -125,6 +125,7 @@ var CommandIDs;
125
125
  CommandIDs.setSideBySideRatio = 'notebook:set-side-by-side-ratio';
126
126
  CommandIDs.enableOutputScrolling = 'notebook:enable-output-scrolling';
127
127
  CommandIDs.disableOutputScrolling = 'notebook:disable-output-scrolling';
128
+ CommandIDs.toggleOutputScrolling = 'notebook:toggle-output-scrolling';
128
129
  CommandIDs.selectLastRunCell = 'notebook:select-last-run-cell';
129
130
  CommandIDs.replaceSelection = 'notebook:replace-selection';
130
131
  CommandIDs.autoClosingBrackets = 'notebook:toggle-autoclosing-brackets';
@@ -185,11 +186,11 @@ const trackerPlugin = {
185
186
  autoStart: true
186
187
  };
187
188
  /**
188
- * The notebook cell factory provider.
189
+ * The notebook and cell factory provider.
189
190
  */
190
191
  const factory = {
191
192
  id: '@jupyterlab/notebook-extension:factory',
192
- description: 'Provides the notebook cell factory.',
193
+ description: 'Provides the notebook and cell factory.',
193
194
  provides: NotebookPanel.IContentFactory,
194
195
  requires: [IEditorServices],
195
196
  autoStart: true,
@@ -248,6 +249,39 @@ export const commandEditItem = {
248
249
  });
249
250
  }
250
251
  };
252
+ /**
253
+ * A plugin providing a current cell/total cells status item.
254
+ */
255
+ export const cellCounterItem = {
256
+ id: '@jupyterlab/notebook-extension:cell-counter-status',
257
+ description: 'Adds a notebook cell counter status widget.',
258
+ autoStart: true,
259
+ requires: [INotebookTracker, ITranslator],
260
+ optional: [IStatusBar],
261
+ activate: (app, tracker, translator, statusBar) => {
262
+ if (!statusBar) {
263
+ // Automatically disable if statusbar missing
264
+ return;
265
+ }
266
+ const { shell } = app;
267
+ const item = new CellCounterStatus({ translator });
268
+ const updateNotebook = () => {
269
+ const current = tracker.currentWidget;
270
+ item.model.notebook = current && current.content;
271
+ };
272
+ tracker.currentChanged.connect(updateNotebook);
273
+ updateNotebook();
274
+ statusBar.registerStatusItem(cellCounterItem.id, {
275
+ priority: 1,
276
+ item,
277
+ align: 'right',
278
+ rank: 2.5,
279
+ isActive: () => !!shell.currentWidget &&
280
+ !!tracker.currentWidget &&
281
+ shell.currentWidget === tracker.currentWidget
282
+ });
283
+ }
284
+ };
251
285
  /**
252
286
  * A plugin that provides a execution indicator item to the status bar.
253
287
  */
@@ -422,7 +456,8 @@ export const exportPlugin = {
422
456
  // Convert export list to palette and menu items.
423
457
  const formatList = Object.keys(response);
424
458
  formatList.forEach(function (key) {
425
- const capCaseKey = trans.__(key[0].toUpperCase() + key.substr(1));
459
+ const formattedKey = key[0].toLocaleUpperCase() + key.slice(1);
460
+ const capCaseKey = trans.__(formattedKey);
426
461
  const labelStr = formatLabels[key] ? formatLabels[key] : capCaseKey;
427
462
  let args = {
428
463
  format: key,
@@ -689,7 +724,8 @@ const updateRawMimetype = {
689
724
  var _a;
690
725
  const mimetypeExists = ((_a = properties.oneOf) === null || _a === void 0 ? void 0 : _a.filter(value => value.const === key).length) > 0;
691
726
  if (!mimetypeExists) {
692
- const altOption = trans.__(key[0].toUpperCase() + key.substr(1));
727
+ const formattedKey = key[0].toLocaleUpperCase() + key.slice(1);
728
+ const altOption = trans.__(formattedKey);
693
729
  const option = formatLabels[key] ? formatLabels[key] : altOption;
694
730
  const mimeTypeValue = response[key].output_mimetype;
695
731
  properties.oneOf.push({
@@ -825,6 +861,7 @@ const plugins = [
825
861
  executionIndicator,
826
862
  exportPlugin,
827
863
  tools,
864
+ cellCounterItem,
828
865
  commandEditItem,
829
866
  notebookTrustItem,
830
867
  widgetFactoryPlugin,
@@ -1121,7 +1158,6 @@ function activateCodeConsole(app, tracker, translator) {
1121
1158
  let fromFirst = curLine > 0;
1122
1159
  let firstLine = 0;
1123
1160
  let lastLine = firstLine + 1;
1124
- // eslint-disable-next-line
1125
1161
  while (true) {
1126
1162
  code = srcLines.slice(firstLine, lastLine).join('\n');
1127
1163
  const reply = await ((_b = (_a = current.context.sessionContext.session) === null || _a === void 0 ? void 0 : _a.kernel) === null || _b === void 0 ? void 0 : _b.requestIsComplete({
@@ -1425,6 +1461,7 @@ function activateNotebookHandler(app, factory, extensions, executor, palette, de
1425
1461
  var _a, _b, _c;
1426
1462
  // If the notebook panel does not have an ID, assign it one.
1427
1463
  widget.id = widget.id || `notebook-${++id}`;
1464
+ widget.content.node.setAttribute('data-trust-command', CommandIDs.trust);
1428
1465
  // Set up the title icon
1429
1466
  widget.title.icon = ft === null || ft === void 0 ? void 0 : ft.icon;
1430
1467
  widget.title.iconClass = (_a = ft === null || ft === void 0 ? void 0 : ft.iconClass) !== null && _a !== void 0 ? _a : '';
@@ -1759,6 +1796,22 @@ function getCurrent(tracker, shell, args) {
1759
1796
  }
1760
1797
  return widget;
1761
1798
  }
1799
+ // Whether all selected code cells have output scrolling enabled.
1800
+ function isOutputScrollingEnabled(notebook) {
1801
+ if (!notebook.model || !notebook.activeCell) {
1802
+ return false;
1803
+ }
1804
+ let hasCodeCell = false;
1805
+ for (const cell of notebook.widgets) {
1806
+ if (notebook.isSelectedOrActive(cell) && cell.model.type === 'code') {
1807
+ hasCodeCell = true;
1808
+ if (!cell.outputsScrolled) {
1809
+ return false;
1810
+ }
1811
+ }
1812
+ }
1813
+ return hasCodeCell;
1814
+ }
1762
1815
  /**
1763
1816
  * Add the notebook commands to the application's command registry.
1764
1817
  */
@@ -1776,6 +1829,11 @@ function addCommands(app, tracker, translator, sessionDialogs, settings, isEnabl
1776
1829
  cell
1777
1830
  .getHeadings()
1778
1831
  .then(() => {
1832
+ // Heading parsing is async; avoid restoring an outdated collapse
1833
+ // state if the heading has been expanded in the meantime.
1834
+ if (cell.isDisposed || !cell.headingCollapsed) {
1835
+ return;
1836
+ }
1779
1837
  NotebookActions.setHeadingCollapse(cell, true, notebook);
1780
1838
  })
1781
1839
  .catch(error => {
@@ -1833,6 +1891,7 @@ function addCommands(app, tracker, translator, sessionDialogs, settings, isEnabl
1833
1891
  commands.notifyCommandChanged(CommandIDs.runAndInsert);
1834
1892
  });
1835
1893
  tracker.activeCellChanged.connect(() => {
1894
+ commands.notifyCommandChanged(CommandIDs.deleteCell);
1836
1895
  commands.notifyCommandChanged(CommandIDs.moveUp);
1837
1896
  commands.notifyCommandChanged(CommandIDs.moveDown);
1838
1897
  });
@@ -2077,12 +2136,17 @@ function addCommands(app, tracker, translator, sessionDialogs, settings, isEnabl
2077
2136
  });
2078
2137
  commands.addCommand(CommandIDs.trust, {
2079
2138
  label: () => trans.__('Trust Notebook'),
2080
- execute: args => {
2139
+ execute: async (args) => {
2081
2140
  const current = getCurrent(tracker, shell, args);
2082
2141
  if (current) {
2083
2142
  const { context, content } = current;
2084
- return NotebookActions.trust(content).then(() => context.save());
2143
+ const trustResult = await NotebookActions.trust(content);
2144
+ if (trustResult.trusted) {
2145
+ await context.save();
2146
+ }
2147
+ return trustResult;
2085
2148
  }
2149
+ return { trusted: false };
2086
2150
  },
2087
2151
  isEnabled,
2088
2152
  describedBy: {
@@ -2499,7 +2563,16 @@ function addCommands(app, tracker, translator, sessionDialogs, settings, isEnabl
2499
2563
  return NotebookActions.deleteCells(current.content);
2500
2564
  }
2501
2565
  },
2502
- isEnabled: args => (args.toolbar ? true : isEnabled()),
2566
+ isEnabled: args => {
2567
+ var _a;
2568
+ const current = getCurrent(tracker, shell, { ...args, activate: false });
2569
+ if (!current) {
2570
+ return false;
2571
+ }
2572
+ // The 'deletable' metadata is optional, null and undefined values should be made truthy
2573
+ const deletable = ((_a = current.content.activeCell) === null || _a === void 0 ? void 0 : _a.model.getMetadata('deletable')) !== false;
2574
+ return deletable;
2575
+ },
2503
2576
  describedBy: {
2504
2577
  args: {
2505
2578
  type: 'object',
@@ -2521,7 +2594,7 @@ function addCommands(app, tracker, translator, sessionDialogs, settings, isEnabl
2521
2594
  execute: args => {
2522
2595
  const current = getCurrent(tracker, shell, args);
2523
2596
  if (current) {
2524
- return NotebookActions.splitCell(current.content);
2597
+ return NotebookActions.splitCell(current.content, translator);
2525
2598
  }
2526
2599
  },
2527
2600
  isEnabled,
@@ -2539,7 +2612,7 @@ function addCommands(app, tracker, translator, sessionDialogs, settings, isEnabl
2539
2612
  const current = getCurrent(tracker, shell, args);
2540
2613
  if (current) {
2541
2614
  const addExtraLine = (_a = settings === null || settings === void 0 ? void 0 : settings.get('addExtraLineOnCellMerge').composite) !== null && _a !== void 0 ? _a : true;
2542
- return NotebookActions.mergeCells(current.content, false, addExtraLine);
2615
+ return NotebookActions.mergeCells(current.content, false, addExtraLine, translator);
2543
2616
  }
2544
2617
  },
2545
2618
  isEnabled,
@@ -2557,7 +2630,7 @@ function addCommands(app, tracker, translator, sessionDialogs, settings, isEnabl
2557
2630
  const current = getCurrent(tracker, shell, args);
2558
2631
  if (current) {
2559
2632
  const addExtraLine = (_a = settings === null || settings === void 0 ? void 0 : settings.get('addExtraLineOnCellMerge').composite) !== null && _a !== void 0 ? _a : true;
2560
- return NotebookActions.mergeCells(current.content, true, addExtraLine);
2633
+ return NotebookActions.mergeCells(current.content, true, addExtraLine, translator);
2561
2634
  }
2562
2635
  },
2563
2636
  isEnabled,
@@ -2575,7 +2648,7 @@ function addCommands(app, tracker, translator, sessionDialogs, settings, isEnabl
2575
2648
  const current = getCurrent(tracker, shell, args);
2576
2649
  if (current) {
2577
2650
  const addExtraLine = (_a = settings === null || settings === void 0 ? void 0 : settings.get('addExtraLineOnCellMerge').composite) !== null && _a !== void 0 ? _a : true;
2578
- return NotebookActions.mergeCells(current.content, false, addExtraLine);
2651
+ return NotebookActions.mergeCells(current.content, false, addExtraLine, translator);
2579
2652
  }
2580
2653
  },
2581
2654
  isEnabled,
@@ -3410,6 +3483,41 @@ function addCommands(app, tracker, translator, sessionDialogs, settings, isEnabl
3410
3483
  }
3411
3484
  }
3412
3485
  });
3486
+ commands.addCommand(CommandIDs.toggleOutputScrolling, {
3487
+ label: args => args['isMenu'] || args['isPalette']
3488
+ ? trans.__('Enable Scrolling for Outputs')
3489
+ : trans.__('Toggle Scrolling for Outputs'),
3490
+ execute: args => {
3491
+ const current = getCurrent(tracker, shell, args);
3492
+ if (current) {
3493
+ if (isOutputScrollingEnabled(current.content)) {
3494
+ return NotebookActions.disableOutputScrolling(current.content);
3495
+ }
3496
+ return NotebookActions.enableOutputScrolling(current.content);
3497
+ }
3498
+ },
3499
+ isEnabled,
3500
+ isToggled: args => {
3501
+ const current = getCurrent(tracker, shell, { ...args, activate: false });
3502
+ if (current) {
3503
+ return isOutputScrollingEnabled(current.content);
3504
+ }
3505
+ else {
3506
+ return false;
3507
+ }
3508
+ },
3509
+ describedBy: {
3510
+ args: {
3511
+ type: 'object',
3512
+ properties: {
3513
+ isMenu: {
3514
+ type: 'boolean',
3515
+ description: trans.__('Whether the command is called from a menu')
3516
+ }
3517
+ }
3518
+ }
3519
+ }
3520
+ });
3413
3521
  commands.addCommand(CommandIDs.selectLastRunCell, {
3414
3522
  label: trans.__('Select current running or last run cell'),
3415
3523
  execute: args => {
@@ -3892,12 +4000,14 @@ var Private;
3892
4000
  // If the container is not available, append the newly created container
3893
4001
  // to the current notebook panel and set related properties
3894
4002
  if (hiddenAlertContainer.getAttribute('id') !== hiddenAlertContainerId) {
3895
- hiddenAlertContainer.classList.add('sr-only');
3896
4003
  hiddenAlertContainer.setAttribute('id', hiddenAlertContainerId);
3897
- hiddenAlertContainer.setAttribute('role', 'alert');
3898
- hiddenAlertContainer.hidden = true;
3899
4004
  notebookNode.appendChild(hiddenAlertContainer);
3900
4005
  }
4006
+ hiddenAlertContainer.classList.add('jp-sr-only');
4007
+ hiddenAlertContainer.setAttribute('role', 'alert');
4008
+ hiddenAlertContainer.setAttribute('aria-live', 'assertive');
4009
+ hiddenAlertContainer.setAttribute('aria-atomic', 'true');
4010
+ hiddenAlertContainer.hidden = false;
3901
4011
  // Insert/Update alert container with the notification message
3902
4012
  hiddenAlertContainer.innerText = message;
3903
4013
  }
@@ -3914,7 +4024,7 @@ var Private;
3914
4024
  this._index = options.index !== undefined ? options.index : -1;
3915
4025
  this._cell = options.cell || null;
3916
4026
  this.id = `LinkedOutputView-${UUID.uuid4()}`;
3917
- this.title.label = 'Output View';
4027
+ this.title.label = trans.__('Output View');
3918
4028
  this.title.icon = notebookIcon;
3919
4029
  this.title.caption = this._notebook.title.label
3920
4030
  ? trans.__('For Notebook: %1', this._notebook.title.label)