UNPKG

@atlaskit/editor-core

Version:

A package contains Atlassian editor core functionality

139 lines • 5.49 kB
import { analyticsService } from '../../analytics'; import { PluginKey, TextSelection, Plugin, } from '../../prosemirror'; import { panelNodeView } from '../../nodeviews'; import inputRulePlugin from './input-rules'; export var availablePanelType = [ { panelType: 'info' }, { panelType: 'note' }, { panelType: 'tip' }, { panelType: 'warning' } ]; var PanelState = (function () { function PanelState(state) { this.changeHandlers = []; this.editorFocused = false; this.changeHandlers = []; this.state = state; this.toolbarVisible = false; } PanelState.prototype.updateEditorFocused = function (editorFocused) { this.editorFocused = editorFocused; }; PanelState.prototype.changePanelType = function (view, panelType) { analyticsService.trackEvent("atlassian.editor.format." + panelType.panelType + ".button"); var state = view.state, dispatch = view.dispatch; var tr = state.tr; var panel = state.schema.nodes.panel; var _a = state.selection, $from = _a.$from, $to = _a.$to; var newFrom = tr.doc.resolve($from.start($from.depth - 1)); var newTo = tr.doc.resolve($to.end($to.depth - 1)); var range = newFrom.blockRange(newTo); tr.lift(range, $from.depth - 2); newFrom = tr.doc.resolve(tr.mapping.map(newFrom.pos)); newTo = tr.doc.resolve(tr.mapping.map(newTo.pos)); range = newFrom.blockRange(newTo); tr = tr.wrap(range, [{ type: panel, attrs: panelType }]); dispatch(tr); }; PanelState.prototype.removePanel = function (view) { var dispatch = view.dispatch, state = view.state; var tr = state.tr; var _a = state.selection, $from = _a.$from, $to = _a.$to; var newFrom = tr.doc.resolve($from.start($from.depth - 1)); var newTo = tr.doc.resolve($to.end($to.depth - 1)); var range = newFrom.blockRange(newTo); tr = tr.delete(range.start - 1, range.end + 1); dispatch(tr); }; PanelState.prototype.subscribe = function (cb) { this.changeHandlers.push(cb); cb(this); }; PanelState.prototype.unsubscribe = function (cb) { this.changeHandlers = this.changeHandlers.filter(function (ch) { return ch !== cb; }); }; PanelState.prototype.update = function (state, docView, domEvent) { var _this = this; if (domEvent === void 0) { domEvent = false; } this.state = state; var newPanel = this.getActivePanel(docView); if ((domEvent && newPanel) || this.activeNode !== newPanel) { var newElement = newPanel && this.getDomElement(docView); this.activeNode = newPanel; this.toolbarVisible = this.editorFocused && !!newPanel && (domEvent || this.element !== newElement); this.element = newElement; this.activePanelType = newPanel && newPanel.attrs['panelType']; this.changeHandlers.forEach(function (cb) { return cb(_this); }); } }; PanelState.prototype.getActivePanel = function (docView) { var state = this.state; if (state.selection instanceof TextSelection) { var $from = state.selection.$from; var node = $from.node($from.depth - 1); if (node && node.type === state.schema.nodes.panel) { return node; } } }; PanelState.prototype.getDomElement = function (docView) { var selection = this.state.selection; if (selection instanceof TextSelection) { var node = docView.domFromPos(selection.$from.pos).node; var currentNode = node; while (currentNode) { if (currentNode.attributes && currentNode.attributes['data-panel-type']) { return currentNode; } currentNode = currentNode.parentNode; } } }; return PanelState; }()); export { PanelState }; export var stateKey = new PluginKey('panelPlugin'); var plugin = new Plugin({ state: { init: function (config, state) { return new PanelState(state); }, apply: function (tr, pluginState, oldState, newState) { var stored = tr.getMeta(stateKey); if (stored) { pluginState.update(newState, stored.docView, stored.domEvent); } return pluginState; } }, key: stateKey, view: function (view) { return { update: function (view, prevState) { stateKey.getState(view.state).update(view.state, view.docView); } }; }, props: { nodeViews: { panel: panelNodeView, }, handleClick: function (view, event) { stateKey.getState(view.state).update(view.state, view.docView, true); return false; }, onFocus: function (view, event) { stateKey.getState(view.state).updateEditorFocused(true); }, onBlur: function (view, event) { var pluginState = stateKey.getState(view.state); pluginState.updateEditorFocused(false); pluginState.update(view.state, view.docView, true); }, }, }); var plugins = function (schema) { return [plugin, inputRulePlugin(schema)].filter(function (plugin) { return !!plugin; }); }; export default plugins; //# sourceMappingURL=index.js.map