@atlaskit/editor-plugin-base
Version:
Base plugin for @atlaskit/editor-core
83 lines (82 loc) • 3.28 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.createLazyNodeViewDecorationPlugin = createLazyNodeViewDecorationPlugin;
var _lazyNodeView = require("@atlaskit/editor-common/lazy-node-view");
var _safePlugin = require("@atlaskit/editor-common/safe-plugin");
var _view = require("@atlaskit/editor-prosemirror/view");
var LAZY_NODE_VIEW_DECORATION_CLASS = '__lazy-node-view-decoration__';
/**
* Plugin is used to force re-render NodeViews for a specific node type
* when LazyNodeView finishes loading the real NodeView.
*
* This is achieved by applying a decoration to a node.
*
* It's a blessed way that Marijn suggested multiple times in ProseMirror Discuss:
* – https://discuss.prosemirror.net/t/force-nodes-of-specific-type-to-re-render/2480
*/
function createLazyNodeViewDecorationPlugin() {
return new _safePlugin.SafePlugin({
key: _lazyNodeView.lazyNodeViewDecorationPluginKey,
state: {
init: function init() {
return {
decorations: _view.DecorationSet.empty,
nodeTypes: []
};
},
apply: function apply(tr, _oldState, newState) {
var actionPayload = tr.getMeta(_lazyNodeView.lazyNodeViewDecorationPluginKey);
var pluginState = _lazyNodeView.lazyNodeViewDecorationPluginKey.getState(newState);
if ((actionPayload === null || actionPayload === void 0 ? void 0 : actionPayload.type) === 'add' && actionPayload.nodeTypes.size) {
var decorations = [];
tr.doc.nodesBetween(0, tr.doc.nodeSize - 2, function (node, pos) {
if (actionPayload.nodeTypes.has(node.type.name)) {
decorations.push(_view.Decoration.node(pos, pos + node.nodeSize, {
class: LAZY_NODE_VIEW_DECORATION_CLASS
}));
}
});
return {
decorations: _view.DecorationSet.create(tr.doc, decorations)
};
}
if ((actionPayload === null || actionPayload === void 0 ? void 0 : actionPayload.type) === 'clear') {
return {
decorations: _view.DecorationSet.empty
};
}
if (tr.docChanged) {
return {
decorations: pluginState === null || pluginState === void 0 ? void 0 : pluginState.decorations.map(tr.mapping, tr.doc)
};
}
return pluginState;
}
},
props: {
decorations: function decorations(state) {
var _lazyNodeViewDecorati;
return (_lazyNodeViewDecorati = _lazyNodeView.lazyNodeViewDecorationPluginKey.getState(state)) === null || _lazyNodeViewDecorati === void 0 ? void 0 : _lazyNodeViewDecorati.decorations;
}
},
view: function view(editorView) {
return {
update: function update() {
/**
* After view update can clean up decorations...
*/
var pluginState = _lazyNodeView.lazyNodeViewDecorationPluginKey.getState(editorView.state);
if (pluginState.decorations !== _view.DecorationSet.empty) {
var tr = editorView.state.tr;
tr.setMeta(_lazyNodeView.lazyNodeViewDecorationPluginKey, {
type: 'clear'
});
editorView.dispatch(tr);
}
}
};
}
});
}