UNPKG

@jupyterlab/application

Version:
140 lines 5.9 kB
/* * Copyright (c) Jupyter Development Team. * Distributed under the terms of the Modified BSD License. */ import { nullTranslator } from '@jupyterlab/translation'; /** * Add a semantic commands to the application and take care * of setting up the command changed signal. * * @param options Semantic command options */ export function addSemanticCommand(options) { const { id, commands, shell, semanticCommands, default: defaultValues, overrides, trans } = options; commands.addCommand(id, { ...createSemanticCommand({ commands, shell }, semanticCommands, defaultValues !== null && defaultValues !== void 0 ? defaultValues : {}, trans !== null && trans !== void 0 ? trans : nullTranslator.load('jupyterlab')), ...overrides }); const commandList = Array.isArray(semanticCommands) ? semanticCommands : [semanticCommands]; const onCommandChanged = (commands, args) => { if (args.id) { if (args.id === id && args.type === 'removed') { commands.commandChanged.disconnect(onCommandChanged); } else { const commandIds = commandList.reduce((agg, cmd) => agg.concat(cmd.ids), []); if (commandIds.includes(args.id)) { switch (args.type) { case 'changed': case 'many-changed': commands.notifyCommandChanged(id); break; case 'removed': for (const cmd of commandList) { cmd.remove(args.id); } break; } } } } }; commands.commandChanged.connect(onCommandChanged); } /** * Create the command options from the given semantic commands list * and the given default values. * * @param app Jupyter Application * @param semanticCommands Single semantic command or a list of commands * @param defaultValues Default values * @param trans Translation bundle * @returns Command options * * @deprecated Please use {@link addSemanticCommand}. This function will * be removed of the public API in JupyterLab 5. */ export function createSemanticCommand(app, semanticCommands, defaultValues, trans) { const { commands, shell } = app; const commandList = Array.isArray(semanticCommands) ? semanticCommands : [semanticCommands]; return { label: concatenateTexts('label'), caption: concatenateTexts('caption'), isEnabled: () => { var _a; const isEnabled = reduceAttribute('isEnabled'); return ((isEnabled.length > 0 && !isEnabled.some(enabled => enabled === false)) || ((_a = defaultValues.isEnabled) !== null && _a !== void 0 ? _a : false)); }, isToggled: () => { var _a; const isToggled = reduceAttribute('isToggled'); return (isToggled.some(enabled => enabled === true) || ((_a = defaultValues.isToggled) !== null && _a !== void 0 ? _a : false)); }, isVisible: () => { var _a; const isVisible = reduceAttribute('isVisible'); return ((isVisible.length > 0 && !isVisible.some(visible => visible === false)) || ((_a = defaultValues.isVisible) !== null && _a !== void 0 ? _a : true)); }, execute: async () => { const widget = shell.currentWidget; const commandIds = commandList.map(cmd => widget !== null ? cmd.getActiveCommandId(widget) : null); const toExecute = commandIds.filter(commandId => commandId !== null && commands.isEnabled(commandId)); let result = null; if (toExecute.length > 0) { for (const commandId of toExecute) { result = await commands.execute(commandId); if (typeof result === 'boolean' && result === false) { // If a command returns a boolean, assume it is the execution success status // So break if it is false. break; } } } else if (defaultValues.execute) { result = await commands.execute(defaultValues.execute); } return result; } }; function reduceAttribute(attribute) { const widget = shell.currentWidget; const commandIds = commandList.map(cmd => widget !== null ? cmd.getActiveCommandId(widget) : null); const attributes = commandIds .filter(commandId => commandId !== null) .map(commandId => commands[attribute](commandId)); return attributes; } function concatenateTexts(attribute) { return () => { var _a; const texts = reduceAttribute(attribute).map((text, textIndex) => attribute == 'caption' && textIndex > 0 ? text.toLocaleLowerCase() : text); switch (texts.length) { case 0: return (_a = defaultValues[attribute]) !== null && _a !== void 0 ? _a : ''; case 1: return texts[0]; default: { const hasEllipsis = texts.some(l => /…$/.test(l)); const main = texts .slice(undefined, -1) .map(l => l.replace(/…$/, '')) .join(', '); const end = texts.slice(-1)[0].replace(/…$/, '') + (hasEllipsis ? '…' : ''); return trans.__('%1 and %2', main, end); } } }; } } //# sourceMappingURL=utils.js.map