@atlaskit/editor-plugin-table
Version:
Table plugin for the @atlaskit/editor
80 lines (78 loc) • 2.82 kB
JavaScript
import { SafePlugin } from '@atlaskit/editor-common/safe-plugin';
import { PluginKey } from '@atlaskit/editor-prosemirror/state';
import { Decoration, DecorationSet } from '@atlaskit/editor-prosemirror/view';
import { CellSelection } from '@atlaskit/editor-tables/cell-selection';
import { findCellClosestToPos } from '@atlaskit/editor-tables/utils';
import { TableCssClassName as ClassName } from '../../types';
var EMPTY_STATE = {
cellPos: -1,
decorationSet: DecorationSet.empty
};
export var activeCellHighlightPluginKey = new PluginKey('tableActiveCellHighlight');
/**
* Returns the position of the cell containing the cursor, or -1 if the cursor
* is not in a table cell or the selection is a CellSelection.
*/
var getActiveCellPos = function getActiveCellPos(state) {
if (state.selection instanceof CellSelection) {
return -1;
}
try {
var cell = findCellClosestToPos(state.selection.$from);
return cell ? cell.pos : -1;
} catch (_unused) {
return -1;
}
};
var buildState = function buildState(cellPos, state) {
if (cellPos === -1) {
return EMPTY_STATE;
}
try {
var cell = state.doc.nodeAt(cellPos);
if (!cell) {
return EMPTY_STATE;
}
var decoration = Decoration.node(cellPos, cellPos + cell.nodeSize, {
class: ClassName.ACTIVE_CURSOR_CELL
});
return {
cellPos: cellPos,
decorationSet: DecorationSet.create(state.doc, [decoration])
};
} catch (_unused2) {
return EMPTY_STATE;
}
};
export var createPlugin = function createPlugin() {
return new SafePlugin({
key: activeCellHighlightPluginKey,
state: {
init: function init(_, state) {
return buildState(getActiveCellPos(state), state);
},
apply: function apply(tr, prev, _oldState, newState) {
if (tr.docChanged) {
// Doc changed — always rebuild since positions may have shifted
return buildState(getActiveCellPos(newState), newState);
}
if (!tr.selectionSet) {
// Neither doc nor selection changed — nothing to do
return prev;
}
// Selection changed — only rebuild if cursor moved to a different cell
var nextCellPos = getActiveCellPos(newState);
if (nextCellPos === prev.cellPos) {
return prev;
}
return buildState(nextCellPos, newState);
}
},
props: {
decorations: function decorations(state) {
var _activeCellHighlightP, _activeCellHighlightP2;
return (_activeCellHighlightP = (_activeCellHighlightP2 = activeCellHighlightPluginKey.getState(state)) === null || _activeCellHighlightP2 === void 0 ? void 0 : _activeCellHighlightP2.decorationSet) !== null && _activeCellHighlightP !== void 0 ? _activeCellHighlightP : DecorationSet.empty;
}
}
});
};