@progress/kendo-editor-common 1.8.2-dev.202204011319 → 1.9.0-dev.202204060830
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/dist/cdn/js/kendo-editor-common.js +2 -2
- package/dist/cdn/main.js +1 -1
- package/dist/es/config/constants.js +4 -0
- package/dist/es/config/schema.js +9 -5
- package/dist/es/main.js +1 -0
- package/dist/es/plugins/image-resize.js +4 -3
- package/dist/es/plugins/table-resize/column-resize.js +294 -0
- package/dist/es/plugins/table-resize/index.js +8 -0
- package/dist/es/plugins/table-resize/row-resize.js +244 -0
- package/dist/es/plugins/table-resize/table-resize.js +281 -0
- package/dist/es/plugins/table-resize/table-view.js +87 -0
- package/dist/es/plugins/table-resize/utils.js +53 -0
- package/dist/es2015/config/constants.js +4 -0
- package/dist/es2015/config/schema.js +11 -8
- package/dist/es2015/main.js +1 -0
- package/dist/es2015/plugins/image-resize.js +4 -3
- package/dist/es2015/plugins/table-resize/column-resize.js +290 -0
- package/dist/es2015/plugins/table-resize/index.js +8 -0
- package/dist/es2015/plugins/table-resize/row-resize.js +240 -0
- package/dist/es2015/plugins/table-resize/table-resize.js +277 -0
- package/dist/es2015/plugins/table-resize/table-view.js +84 -0
- package/dist/es2015/plugins/table-resize/utils.js +51 -0
- package/dist/npm/config/constants.d.ts +4 -0
- package/dist/npm/config/constants.js +4 -0
- package/dist/npm/config/schema.d.ts +1 -0
- package/dist/npm/config/schema.js +8 -4
- package/dist/npm/main.d.ts +1 -0
- package/dist/npm/main.js +2 -0
- package/dist/npm/plugins/image-resize.js +4 -3
- package/dist/npm/plugins/table-resize/column-resize.d.ts +2 -0
- package/dist/npm/plugins/table-resize/column-resize.js +297 -0
- package/dist/npm/plugins/table-resize/index.d.ts +1 -0
- package/dist/npm/plugins/table-resize/index.js +10 -0
- package/dist/npm/plugins/table-resize/row-resize.d.ts +2 -0
- package/dist/npm/plugins/table-resize/row-resize.js +247 -0
- package/dist/npm/plugins/table-resize/table-resize.d.ts +6 -0
- package/dist/npm/plugins/table-resize/table-resize.js +283 -0
- package/dist/npm/plugins/table-resize/table-view.d.ts +17 -0
- package/dist/npm/plugins/table-resize/table-view.js +89 -0
- package/dist/npm/plugins/table-resize/utils.d.ts +12 -0
- package/dist/npm/plugins/table-resize/utils.js +59 -0
- package/dist/systemjs/kendo-editor-common.js +1 -1
- package/package.json +2 -2
|
@@ -1,2 +1,6 @@
|
|
|
1
1
|
export var rowTypeAttr = 'k-parent-node';
|
|
2
2
|
export var colgroupAttr = 'k-colgroup-data';
|
|
3
|
+
export var resizableAttr = 'resizable-node';
|
|
4
|
+
export var resizableWrap = 'k-editor-resize-wrap-element';
|
|
5
|
+
export var resizeHandle = 'k-editor-resize-handle';
|
|
6
|
+
export var dataDirection = 'data-direction';
|
package/dist/es/config/schema.js
CHANGED
|
@@ -2,7 +2,7 @@ import * as tslib_1 from "tslib";
|
|
|
2
2
|
import { Schema } from 'prosemirror-model';
|
|
3
3
|
import { tableNodes } from 'prosemirror-tables';
|
|
4
4
|
import { domToPmDoc, htmlToFragment, pmDocToFragment } from '../source';
|
|
5
|
-
import { rowTypeAttr, colgroupAttr } from './constants';
|
|
5
|
+
import { rowTypeAttr, colgroupAttr, resizableAttr } from './constants';
|
|
6
6
|
var hole = 0;
|
|
7
7
|
var blockquoteDOM = ['blockquote', hole], hrDOM = ['hr'], preDOM = ['pre', ['code', hole]];
|
|
8
8
|
var olDOM = ['ol', 0], ulDOM = ['ul', 0], liDOM = ['li', 0];
|
|
@@ -109,18 +109,22 @@ var shouldSkipColgroup = function (node) {
|
|
|
109
109
|
}
|
|
110
110
|
return shouldSkip;
|
|
111
111
|
};
|
|
112
|
+
export var parseStrColgroup = function (colgroup) {
|
|
113
|
+
var doc = domToPmDoc(htmlToFragment(colgroup), colgroupSchema, { preserveWhitespace: false });
|
|
114
|
+
var fragment = pmDocToFragment(doc);
|
|
115
|
+
var colgroupEl = fragment.firstChild;
|
|
116
|
+
return colgroupEl;
|
|
117
|
+
};
|
|
112
118
|
var tNodes = tableNodes({ tableGroup: 'block', cellContent: 'block+', cellAttributes: cellAttributes });
|
|
113
119
|
tNodes.table_row.attrs = tslib_1.__assign({}, tNodes.table_row.attrs, defaultAttrs([rowTypeAttr, 'style', 'class', 'id']));
|
|
114
120
|
tNodes.table_row.toDOM = function (node) { return ['tr', pmAttributes(node.attrs), 0]; };
|
|
115
121
|
tNodes.table_row.parseDOM = [{ tag: 'tr', getAttrs: domAttributes }];
|
|
116
|
-
tNodes.table.attrs = tslib_1.__assign({}, tNodes.table.attrs, defaultAttrs(['style', 'class', 'id', colgroupAttr]));
|
|
122
|
+
tNodes.table.attrs = tslib_1.__assign({}, tNodes.table.attrs, defaultAttrs(['style', 'class', 'id', colgroupAttr, resizableAttr]));
|
|
117
123
|
tNodes.table.toDOM = function (node) {
|
|
118
124
|
var tableAttrs = hasAttrs(node.attrs) ? pmAttributes(node.attrs, colgroupAttr) : {};
|
|
119
125
|
var colgroup = null;
|
|
120
126
|
if (node.attrs[colgroupAttr] && !shouldSkipColgroup(node)) {
|
|
121
|
-
var
|
|
122
|
-
var fragment = pmDocToFragment(doc);
|
|
123
|
-
var colgroupEl = fragment.firstChild;
|
|
127
|
+
var colgroupEl = parseStrColgroup(node.attrs[colgroupAttr]);
|
|
124
128
|
if (colgroupEl) {
|
|
125
129
|
var cols = Array.from(colgroupEl.children).map(function (c) { return ['col', domAttributes(c)]; });
|
|
126
130
|
colgroup = [
|
package/dist/es/main.js
CHANGED
|
@@ -24,6 +24,7 @@ export { spacesFix } from './plugins/spaces-fix';
|
|
|
24
24
|
export { textHighlight, textHighlightKey } from './plugins/highlight';
|
|
25
25
|
export { imageResizing, imageResizeKey } from './plugins/image-resize';
|
|
26
26
|
export { caretColor, caretColorKey } from './plugins/caret-color';
|
|
27
|
+
export { tableResizing } from './plugins/table-resize';
|
|
27
28
|
// ProseMirror re-exports
|
|
28
29
|
export * from 'prosemirror-commands';
|
|
29
30
|
export * from 'prosemirror-dropcursor';
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import * as tslib_1 from "tslib";
|
|
2
2
|
import { NodeSelection, Plugin, PluginKey } from "prosemirror-state";
|
|
3
3
|
import { Decoration, DecorationSet } from "prosemirror-view";
|
|
4
|
+
import { dataDirection, resizeHandle } from "../config/constants";
|
|
4
5
|
import { changeStylesString } from "../utils";
|
|
5
6
|
export var imageResizeKey = new PluginKey('image-resize');
|
|
6
7
|
var directions = {
|
|
@@ -109,7 +110,7 @@ var handleMouseUp = function (view) {
|
|
|
109
110
|
};
|
|
110
111
|
var handleMouseDown = function (view, event, options) {
|
|
111
112
|
var target = event.target;
|
|
112
|
-
var activeHandle = target.getAttribute(
|
|
113
|
+
var activeHandle = target.getAttribute(dataDirection);
|
|
113
114
|
if (!activeHandle) {
|
|
114
115
|
return false;
|
|
115
116
|
}
|
|
@@ -221,8 +222,8 @@ export var imageResizing = function (options) {
|
|
|
221
222
|
wrapper.style.left = rect.left + 'px';
|
|
222
223
|
for (var i = 0; i < handles.length; i++) {
|
|
223
224
|
var dom = document.createElement('div');
|
|
224
|
-
dom.className = '
|
|
225
|
-
dom.setAttribute(
|
|
225
|
+
dom.className = resizeHandle + ' ' + handles[i];
|
|
226
|
+
dom.setAttribute(dataDirection, handles[i]);
|
|
226
227
|
wrapper.appendChild(dom);
|
|
227
228
|
}
|
|
228
229
|
return DecorationSet.create(state.doc, [Decoration.widget(state.selection.from + 1, wrapper)]);
|
|
@@ -0,0 +1,294 @@
|
|
|
1
|
+
import * as tslib_1 from "tslib";
|
|
2
|
+
import { Plugin } from 'prosemirror-state';
|
|
3
|
+
import { tableNodeTypes, TableMap } from 'prosemirror-tables';
|
|
4
|
+
import { Decoration, DecorationSet } from 'prosemirror-view';
|
|
5
|
+
import { colgroupAttr } from '../../config/constants';
|
|
6
|
+
import { TableView } from './table-view';
|
|
7
|
+
import { otherResizeHandle, otherResizing, parseStyle, setNodeStyle, tableColumnResizing as key } from './utils';
|
|
8
|
+
export function columnResizing() {
|
|
9
|
+
// tslint:disable-next-line:variable-name
|
|
10
|
+
var View = TableView, lastColumnResizable = true, handleWidth = 5, cellMinWidth = 25;
|
|
11
|
+
var plugin = new Plugin({
|
|
12
|
+
key: key,
|
|
13
|
+
state: {
|
|
14
|
+
init: function (_, state) {
|
|
15
|
+
this.spec.props.nodeViews[tableNodeTypes(state.schema).table.name] = function (node, view) { return new View(node, view); };
|
|
16
|
+
return new ResizeState(-1, null);
|
|
17
|
+
},
|
|
18
|
+
apply: function (tr, prev) {
|
|
19
|
+
return prev.apply(tr);
|
|
20
|
+
}
|
|
21
|
+
},
|
|
22
|
+
props: {
|
|
23
|
+
attributes: function (state) {
|
|
24
|
+
if (otherResizeHandle(key, state)) {
|
|
25
|
+
return null;
|
|
26
|
+
}
|
|
27
|
+
var pluginState = key.getState(state);
|
|
28
|
+
return pluginState.activeHandle > -1 ? { class: 'resize-cursor' } : null;
|
|
29
|
+
},
|
|
30
|
+
handleDOMEvents: {
|
|
31
|
+
mousemove: function (view, event) {
|
|
32
|
+
if (!otherResizing(key, view.state)) {
|
|
33
|
+
handleMouseMove(view, event, handleWidth, cellMinWidth, lastColumnResizable);
|
|
34
|
+
}
|
|
35
|
+
return false;
|
|
36
|
+
},
|
|
37
|
+
mouseleave: function (view) {
|
|
38
|
+
handleMouseLeave(view);
|
|
39
|
+
return false;
|
|
40
|
+
},
|
|
41
|
+
mousedown: function (view, event) {
|
|
42
|
+
return handleMouseDown(view, event, cellMinWidth);
|
|
43
|
+
}
|
|
44
|
+
},
|
|
45
|
+
decorations: function (state) {
|
|
46
|
+
if (otherResizing(key, state)) {
|
|
47
|
+
return DecorationSet.empty;
|
|
48
|
+
}
|
|
49
|
+
var pluginState = key.getState(state);
|
|
50
|
+
if (pluginState.activeHandle > -1) {
|
|
51
|
+
return handleDecorations(state, pluginState.activeHandle);
|
|
52
|
+
}
|
|
53
|
+
},
|
|
54
|
+
nodeViews: {}
|
|
55
|
+
}
|
|
56
|
+
});
|
|
57
|
+
return plugin;
|
|
58
|
+
}
|
|
59
|
+
function cellAround($pos) {
|
|
60
|
+
for (var d = $pos.depth - 1; d > 0; d--) {
|
|
61
|
+
if ($pos.node(d).type.spec.tableRole === 'row') {
|
|
62
|
+
return $pos.node(0).resolve($pos.before(d + 1));
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
return null;
|
|
66
|
+
}
|
|
67
|
+
function pointsAtCell($pos) {
|
|
68
|
+
return $pos.parent.type.spec.tableRole === 'row' && $pos.nodeAfter;
|
|
69
|
+
}
|
|
70
|
+
var ResizeState = /** @class */ (function () {
|
|
71
|
+
function ResizeState(activeHandle, dragging) {
|
|
72
|
+
this.activeHandle = activeHandle;
|
|
73
|
+
this.dragging = dragging;
|
|
74
|
+
}
|
|
75
|
+
ResizeState.prototype.apply = function (tr) {
|
|
76
|
+
var state = this, action = tr.getMeta(key);
|
|
77
|
+
if (action && action.setHandle != null) {
|
|
78
|
+
return new ResizeState(action.setHandle, null);
|
|
79
|
+
}
|
|
80
|
+
if (action && action.setDragging !== undefined) {
|
|
81
|
+
return new ResizeState(state.activeHandle, action.setDragging);
|
|
82
|
+
}
|
|
83
|
+
if (state.activeHandle > -1 && tr.docChanged) {
|
|
84
|
+
var handle = tr.mapping.map(state.activeHandle, -1);
|
|
85
|
+
if (!pointsAtCell(tr.doc.resolve(handle))) {
|
|
86
|
+
handle = null;
|
|
87
|
+
}
|
|
88
|
+
state = new ResizeState(handle, state.dragging);
|
|
89
|
+
}
|
|
90
|
+
return state;
|
|
91
|
+
};
|
|
92
|
+
return ResizeState;
|
|
93
|
+
}());
|
|
94
|
+
function handleMouseMove(view, event, handleWidth, _cellMinWidth, lastColumnResizable) {
|
|
95
|
+
var pluginState = key.getState(view.state);
|
|
96
|
+
if (!pluginState.dragging) {
|
|
97
|
+
var target = domCellAround(event.target), cell = -1;
|
|
98
|
+
if (target) {
|
|
99
|
+
var _a = target.getBoundingClientRect(), left = _a.left, right = _a.right;
|
|
100
|
+
if (event.clientX - left <= handleWidth) {
|
|
101
|
+
cell = edgeCell(view, event, 'left');
|
|
102
|
+
}
|
|
103
|
+
else if (right - event.clientX <= handleWidth) {
|
|
104
|
+
cell = edgeCell(view, event, 'right');
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
if (cell !== pluginState.activeHandle) {
|
|
108
|
+
if (!lastColumnResizable && cell !== -1) {
|
|
109
|
+
var $cell = view.state.doc.resolve(cell);
|
|
110
|
+
var table = $cell.node(-1), map = TableMap.get(table), start = $cell.start(-1);
|
|
111
|
+
var col = map.colCount($cell.pos - start) + $cell.nodeAfter.attrs.colspan - 1;
|
|
112
|
+
if (col === map.width - 1) {
|
|
113
|
+
return;
|
|
114
|
+
}
|
|
115
|
+
}
|
|
116
|
+
updateHandle(view, cell);
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
}
|
|
120
|
+
function handleMouseLeave(view) {
|
|
121
|
+
var pluginState = key.getState(view.state);
|
|
122
|
+
if (pluginState.activeHandle > -1 && !pluginState.dragging) {
|
|
123
|
+
updateHandle(view, -1);
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
function handleMouseDown(view, event, cellMinWidth) {
|
|
127
|
+
var _a;
|
|
128
|
+
var pluginState = key.getState(view.state);
|
|
129
|
+
if (pluginState.activeHandle === -1 || pluginState.dragging) {
|
|
130
|
+
return false;
|
|
131
|
+
}
|
|
132
|
+
var $cell = view.state.doc.resolve(pluginState.activeHandle);
|
|
133
|
+
var row = $cell.parent;
|
|
134
|
+
var cellIndex = $cell.index();
|
|
135
|
+
var colSpan = 0;
|
|
136
|
+
for (var i = 0; i <= cellIndex; i++) {
|
|
137
|
+
colSpan += row.child(i).attrs.colspan;
|
|
138
|
+
}
|
|
139
|
+
var tableNode = $cell.node($cell.depth - 1);
|
|
140
|
+
var dom = view.domAtPos(pluginState.activeHandle);
|
|
141
|
+
var domCell = dom.node.childNodes[dom.offset];
|
|
142
|
+
var tableDom = domCell.closest('table');
|
|
143
|
+
var col, tableAttrs;
|
|
144
|
+
if (tableNode.attrs[colgroupAttr]) {
|
|
145
|
+
var colgroup = tableDom.firstChild;
|
|
146
|
+
col = colgroup.children[colSpan - 1];
|
|
147
|
+
if (!col.style.width) {
|
|
148
|
+
col.style.width = col.offsetWidth + 'px';
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
else {
|
|
152
|
+
var total = 0;
|
|
153
|
+
for (var i = 0; i < row.childCount; i++) {
|
|
154
|
+
total += row.child(i).attrs.colspan;
|
|
155
|
+
}
|
|
156
|
+
var colgroup = document.createElement('colgroup');
|
|
157
|
+
var cols = new Array(total);
|
|
158
|
+
for (var i = 0; i < total; i++) {
|
|
159
|
+
cols[i] = document.createElement('col');
|
|
160
|
+
colgroup.appendChild(cols[i]);
|
|
161
|
+
}
|
|
162
|
+
tableDom.insertBefore(colgroup, tableDom.firstChild);
|
|
163
|
+
col = cols[cellIndex];
|
|
164
|
+
col.style.width = col.offsetWidth + 'px';
|
|
165
|
+
tableAttrs = tslib_1.__assign({}, tableNode.attrs, (_a = {}, _a[colgroupAttr] = '<colgroup>' + cols.reduce(function (acc, cur) { return acc + cur.outerHTML; }, '') + '</colgroup>', _a));
|
|
166
|
+
}
|
|
167
|
+
var width = parseFloat(col.style.width);
|
|
168
|
+
var tr = view.state.tr.setMeta(key, { setDragging: { startX: event.clientX, startWidth: width } });
|
|
169
|
+
if (!tableDom.style.width) {
|
|
170
|
+
var widths = Array.from(col.parentNode.children).map(function (c) { return c.style.width; });
|
|
171
|
+
if (widths.every(Boolean)) {
|
|
172
|
+
var sum = widths.reduce(function (acc, cur) { return acc + parseFloat(cur); }, 0);
|
|
173
|
+
tableAttrs = setNodeStyle(tableNode.attrs, 'width', sum + 'px');
|
|
174
|
+
}
|
|
175
|
+
}
|
|
176
|
+
if (tableAttrs) {
|
|
177
|
+
var tablePos = $cell.posAtIndex(0, $cell.depth - 1) - 1;
|
|
178
|
+
tr.setNodeMarkup(tablePos, null, tableAttrs);
|
|
179
|
+
}
|
|
180
|
+
view.dispatch(tr);
|
|
181
|
+
function finish(ev) {
|
|
182
|
+
ev.view.removeEventListener('mouseup', finish);
|
|
183
|
+
ev.view.removeEventListener('mousemove', move);
|
|
184
|
+
var curPluginState = key.getState(view.state);
|
|
185
|
+
if (curPluginState.dragging) {
|
|
186
|
+
updateColumnWidth(view, curPluginState.activeHandle, draggedWidth(curPluginState.dragging, ev, cellMinWidth));
|
|
187
|
+
view.dispatch(view.state.tr.setMeta(key, { setDragging: null }));
|
|
188
|
+
}
|
|
189
|
+
}
|
|
190
|
+
function move(ev) {
|
|
191
|
+
if (!ev.which) {
|
|
192
|
+
return finish(ev);
|
|
193
|
+
}
|
|
194
|
+
var curPluginState = key.getState(view.state);
|
|
195
|
+
var dragged = draggedWidth(curPluginState.dragging, ev, cellMinWidth);
|
|
196
|
+
displayColumnWidth(view, curPluginState.activeHandle, dragged, cellMinWidth);
|
|
197
|
+
}
|
|
198
|
+
event.view.addEventListener('mouseup', finish);
|
|
199
|
+
event.view.addEventListener('mousemove', move);
|
|
200
|
+
event.preventDefault();
|
|
201
|
+
return true;
|
|
202
|
+
}
|
|
203
|
+
function domCellAround(target) {
|
|
204
|
+
while (target && target.nodeName !== 'TD' && target.nodeName !== 'TH') {
|
|
205
|
+
target = target.classList.contains('ProseMirror') ? null : target.parentNode;
|
|
206
|
+
}
|
|
207
|
+
return target;
|
|
208
|
+
}
|
|
209
|
+
function edgeCell(view, event, side) {
|
|
210
|
+
var found = view.posAtCoords({ left: event.clientX, top: event.clientY });
|
|
211
|
+
if (!found) {
|
|
212
|
+
return -1;
|
|
213
|
+
}
|
|
214
|
+
var pos = found.pos;
|
|
215
|
+
var $cell = cellAround(view.state.doc.resolve(pos));
|
|
216
|
+
if (!$cell) {
|
|
217
|
+
return -1;
|
|
218
|
+
}
|
|
219
|
+
if (side === 'right') {
|
|
220
|
+
return $cell.pos;
|
|
221
|
+
}
|
|
222
|
+
var map = TableMap.get($cell.node(-1)), start = $cell.start(-1);
|
|
223
|
+
var index = map.map.indexOf($cell.pos - start);
|
|
224
|
+
return index % map.width === 0 ? -1 : start + map.map[index - 1];
|
|
225
|
+
}
|
|
226
|
+
function draggedWidth(dragging, event, cellMinWidth) {
|
|
227
|
+
var offset = event.clientX - dragging.startX;
|
|
228
|
+
return Math.max(cellMinWidth, dragging.startWidth + offset);
|
|
229
|
+
}
|
|
230
|
+
function updateHandle(view, value) {
|
|
231
|
+
view.dispatch(view.state.tr.setMeta(key, { setHandle: value }));
|
|
232
|
+
}
|
|
233
|
+
function updateColumnWidth(view, cell, _width) {
|
|
234
|
+
var _a;
|
|
235
|
+
var $cell = view.state.doc.resolve(cell);
|
|
236
|
+
var tableNode = $cell.node(-1), start = $cell.start(-1);
|
|
237
|
+
var tr = view.state.tr;
|
|
238
|
+
var tablePos = $cell.posAtIndex(0, $cell.depth - 1) - 1;
|
|
239
|
+
var tableDom = view.nodeDOM(start).closest('table');
|
|
240
|
+
var attrs = tableNode.attrs;
|
|
241
|
+
if (tableNode && attrs[colgroupAttr]) {
|
|
242
|
+
var colgroup = tableDom.firstChild;
|
|
243
|
+
attrs = tslib_1.__assign({}, attrs, (_a = {}, _a[colgroupAttr] = colgroup.outerHTML, _a));
|
|
244
|
+
}
|
|
245
|
+
var tableDomWidth = tableDom.style.width;
|
|
246
|
+
if (tableDom && tableDomWidth && parseStyle(attrs.style).width !== tableDomWidth) {
|
|
247
|
+
attrs = setNodeStyle(attrs, 'width', tableDomWidth);
|
|
248
|
+
tr.setNodeMarkup(tablePos, null, attrs);
|
|
249
|
+
}
|
|
250
|
+
if (tr.docChanged) {
|
|
251
|
+
view.dispatch(tr);
|
|
252
|
+
}
|
|
253
|
+
}
|
|
254
|
+
function displayColumnWidth(view, cell, width, _cellMinWidth) {
|
|
255
|
+
var $cell = view.state.doc.resolve(cell);
|
|
256
|
+
var table = $cell.node(-1), start = $cell.start(-1);
|
|
257
|
+
var col = TableMap.get(table).colCount($cell.pos - start) + $cell.nodeAfter.attrs.colspan - 1;
|
|
258
|
+
var dom = view.domAtPos($cell.start(-1)).node;
|
|
259
|
+
if (dom.nodeName !== 'TABLE') {
|
|
260
|
+
dom = dom.closest('table');
|
|
261
|
+
}
|
|
262
|
+
var tableDom = dom;
|
|
263
|
+
var colgroup = tableDom.firstChild;
|
|
264
|
+
var cols = Array.from(colgroup.children);
|
|
265
|
+
cols[col].style.width = width + 'px';
|
|
266
|
+
if (tableDom.style.width) {
|
|
267
|
+
var widths = cols.map(function (c) { return c.style.width; });
|
|
268
|
+
if (widths.every(Boolean)) {
|
|
269
|
+
var sum = widths.reduce(function (acc, cur) { return acc + parseFloat(cur); }, 0);
|
|
270
|
+
tableDom.style.width = sum + 'px';
|
|
271
|
+
}
|
|
272
|
+
}
|
|
273
|
+
}
|
|
274
|
+
function handleDecorations(state, cell) {
|
|
275
|
+
var decorations = [];
|
|
276
|
+
var $cell = state.doc.resolve(cell);
|
|
277
|
+
var table = $cell.node(-1), map = TableMap.get(table), start = $cell.start(-1);
|
|
278
|
+
var col = map.colCount($cell.pos - start) + $cell.nodeAfter.attrs.colspan;
|
|
279
|
+
for (var row = 0; row < map.height; row++) {
|
|
280
|
+
var index = col + row * map.width - 1;
|
|
281
|
+
// For positions that are have either a different cell or the end
|
|
282
|
+
// of the table to their right, and either the top of the table or
|
|
283
|
+
// a different cell above them, add a decoration
|
|
284
|
+
if ((col === map.width || map.map[index] !== map.map[index + 1]) &&
|
|
285
|
+
(row === 0 || map.map[index - 1] !== map.map[index - 1 - map.width])) {
|
|
286
|
+
var cellPos = map.map[index];
|
|
287
|
+
var pos = start + cellPos + table.nodeAt(cellPos).nodeSize - 1;
|
|
288
|
+
var dom = document.createElement('div');
|
|
289
|
+
dom.className = 'column-resize-handle';
|
|
290
|
+
decorations.push(Decoration.widget(pos, dom));
|
|
291
|
+
}
|
|
292
|
+
}
|
|
293
|
+
return DecorationSet.create(state.doc, decorations);
|
|
294
|
+
}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import { columnResizing } from './column-resize';
|
|
2
|
+
import { tableResizing as tableResize } from './table-resize';
|
|
3
|
+
import { rowResizing } from './row-resize';
|
|
4
|
+
export var tableResizing = function () { return [
|
|
5
|
+
tableResize(),
|
|
6
|
+
columnResizing(),
|
|
7
|
+
rowResizing()
|
|
8
|
+
]; };
|
|
@@ -0,0 +1,244 @@
|
|
|
1
|
+
import { Plugin } from 'prosemirror-state';
|
|
2
|
+
import { TableMap, tableNodeTypes } from 'prosemirror-tables';
|
|
3
|
+
import { Decoration, DecorationSet } from 'prosemirror-view';
|
|
4
|
+
import { otherResizeHandle, otherResizing, parseStyle, setNodeStyle, tableRowResizing as key } from './utils';
|
|
5
|
+
var TableRowView = /** @class */ (function () {
|
|
6
|
+
function TableRowView() {
|
|
7
|
+
}
|
|
8
|
+
TableRowView.prototype.ignoreMutation = function (record) {
|
|
9
|
+
return record.type === 'attributes' && record.attributeName === 'style' && record.target.nodeName === 'TR';
|
|
10
|
+
};
|
|
11
|
+
return TableRowView;
|
|
12
|
+
}());
|
|
13
|
+
export function rowResizing() {
|
|
14
|
+
var handleWidth = 5, rowMinHeight = 25, lastRowResizable = true;
|
|
15
|
+
var plugin = new Plugin({
|
|
16
|
+
key: key,
|
|
17
|
+
state: {
|
|
18
|
+
init: function (_, state) {
|
|
19
|
+
this.spec.props.nodeViews[tableNodeTypes(state.schema).row.name] = function (_node, _view) { return new TableRowView(); };
|
|
20
|
+
return new ResizeState(-1, null);
|
|
21
|
+
},
|
|
22
|
+
apply: function (tr, prev) {
|
|
23
|
+
return prev.apply(tr);
|
|
24
|
+
}
|
|
25
|
+
},
|
|
26
|
+
props: {
|
|
27
|
+
attributes: function (state) {
|
|
28
|
+
if (otherResizeHandle(key, state)) {
|
|
29
|
+
return null;
|
|
30
|
+
}
|
|
31
|
+
var pluginState = key.getState(state);
|
|
32
|
+
return pluginState.activeHandle > -1 ? { class: 'resize-cursor-vertical' } : null;
|
|
33
|
+
},
|
|
34
|
+
handleDOMEvents: {
|
|
35
|
+
mousemove: function (view, event) {
|
|
36
|
+
if (!otherResizing(key, view.state)) {
|
|
37
|
+
handleMouseMove(view, event, handleWidth, rowMinHeight, lastRowResizable);
|
|
38
|
+
}
|
|
39
|
+
return false;
|
|
40
|
+
},
|
|
41
|
+
mouseleave: function (view) {
|
|
42
|
+
handleMouseLeave(view);
|
|
43
|
+
return false;
|
|
44
|
+
},
|
|
45
|
+
mousedown: function (view, event) {
|
|
46
|
+
return handleMouseDown(view, event, rowMinHeight);
|
|
47
|
+
}
|
|
48
|
+
},
|
|
49
|
+
decorations: function (state) {
|
|
50
|
+
if (otherResizing(key, state)) {
|
|
51
|
+
return DecorationSet.empty;
|
|
52
|
+
}
|
|
53
|
+
var pluginState = key.getState(state);
|
|
54
|
+
if (pluginState.activeHandle > -1) {
|
|
55
|
+
return handleDecorations(state, pluginState.activeHandle);
|
|
56
|
+
}
|
|
57
|
+
},
|
|
58
|
+
nodeViews: {}
|
|
59
|
+
}
|
|
60
|
+
});
|
|
61
|
+
return plugin;
|
|
62
|
+
}
|
|
63
|
+
function pointsAtCell($pos) {
|
|
64
|
+
return $pos.parent.type.spec.tableRole === 'row' && $pos.nodeAfter;
|
|
65
|
+
}
|
|
66
|
+
var ResizeState = /** @class */ (function () {
|
|
67
|
+
function ResizeState(activeHandle, dragging) {
|
|
68
|
+
this.activeHandle = activeHandle;
|
|
69
|
+
this.dragging = dragging;
|
|
70
|
+
}
|
|
71
|
+
ResizeState.prototype.apply = function (tr) {
|
|
72
|
+
var state = this, action = tr.getMeta(key);
|
|
73
|
+
if (action && action.setHandle != null) {
|
|
74
|
+
return new ResizeState(action.setHandle, null);
|
|
75
|
+
}
|
|
76
|
+
if (action && action.setDragging !== undefined) {
|
|
77
|
+
return new ResizeState(state.activeHandle, action.setDragging);
|
|
78
|
+
}
|
|
79
|
+
if (state.activeHandle > -1) { // && tr.docChanged
|
|
80
|
+
var handle = tr.mapping.map(state.activeHandle, -1);
|
|
81
|
+
if (!pointsAtCell(tr.doc.resolve(handle))) {
|
|
82
|
+
handle = null;
|
|
83
|
+
}
|
|
84
|
+
state = new ResizeState(handle, state.dragging);
|
|
85
|
+
}
|
|
86
|
+
return state;
|
|
87
|
+
};
|
|
88
|
+
return ResizeState;
|
|
89
|
+
}());
|
|
90
|
+
function handleMouseMove(view, event, handleWidth, _rowMinHeight, lastRowResizable) {
|
|
91
|
+
var pluginState = key.getState(view.state);
|
|
92
|
+
if (!pluginState.dragging) {
|
|
93
|
+
var target = domCellAround(event.target), cell = -1;
|
|
94
|
+
if (target) {
|
|
95
|
+
var rowDom = target.parentNode;
|
|
96
|
+
var domRect = rowDom.getBoundingClientRect();
|
|
97
|
+
if (event.clientY - domRect.top <= handleWidth) {
|
|
98
|
+
cell = edgeCell(view, event, 'up');
|
|
99
|
+
}
|
|
100
|
+
else if (domRect.bottom - event.clientY <= handleWidth) {
|
|
101
|
+
cell = edgeCell(view, event, 'down');
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
if (cell !== pluginState.activeHandle) {
|
|
105
|
+
if (!lastRowResizable && cell !== -1) {
|
|
106
|
+
// let $cell = view.state.doc.resolve(cell);
|
|
107
|
+
// let table = $cell.node(-1), map = TableMap.get(table), start = $cell.start(-1);
|
|
108
|
+
// let col = map.colCount($cell.pos - start) + $cell.nodeAfter.attrs.colspan - 1;
|
|
109
|
+
// if (col === map.width - 1) {
|
|
110
|
+
// return;
|
|
111
|
+
// }
|
|
112
|
+
}
|
|
113
|
+
updateHandle(view, cell);
|
|
114
|
+
}
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
function handleMouseLeave(view) {
|
|
118
|
+
var pluginState = key.getState(view.state);
|
|
119
|
+
if (pluginState.activeHandle > -1 && !pluginState.dragging) {
|
|
120
|
+
updateHandle(view, -1);
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
function handleMouseDown(view, event, rowMinHeight) {
|
|
124
|
+
var pluginState = key.getState(view.state);
|
|
125
|
+
if (pluginState.activeHandle === -1 || pluginState.dragging) {
|
|
126
|
+
return false;
|
|
127
|
+
}
|
|
128
|
+
var doc = view.state.doc;
|
|
129
|
+
var $pos = doc.resolve(pluginState.activeHandle);
|
|
130
|
+
var row = doc.nodeAt(pluginState.activeHandle);
|
|
131
|
+
var table = $pos.parent;
|
|
132
|
+
var rowHeightStr = parseStyle(row.attrs.style).height;
|
|
133
|
+
var tableHeight = parseStyle(table.attrs.style).height;
|
|
134
|
+
var rowHeight = rowHeightStr ? parseFloat(rowHeightStr) : 0;
|
|
135
|
+
if (!rowHeightStr) {
|
|
136
|
+
var tr = view.nodeDOM(pluginState.activeHandle);
|
|
137
|
+
rowHeight = tr.offsetHeight;
|
|
138
|
+
}
|
|
139
|
+
view.dispatch(view.state.tr.setMeta(key, {
|
|
140
|
+
setDragging: {
|
|
141
|
+
startY: event.clientY,
|
|
142
|
+
startHeight: { rowHeight: rowHeight, tableHeight: tableHeight }
|
|
143
|
+
}
|
|
144
|
+
}));
|
|
145
|
+
function finish(ev) {
|
|
146
|
+
ev.view.removeEventListener('mouseup', finish);
|
|
147
|
+
ev.view.removeEventListener('mousemove', move);
|
|
148
|
+
var curPluginState = key.getState(view.state);
|
|
149
|
+
if (curPluginState.dragging) {
|
|
150
|
+
var tr = view.state.tr.setMeta(key, { setDragging: null });
|
|
151
|
+
updateRowHeight(view, tr, curPluginState.activeHandle, draggedHeight(curPluginState.dragging, ev, rowMinHeight));
|
|
152
|
+
view.dispatch(tr);
|
|
153
|
+
}
|
|
154
|
+
}
|
|
155
|
+
function move(ev) {
|
|
156
|
+
if (!ev.which) {
|
|
157
|
+
return finish(ev);
|
|
158
|
+
}
|
|
159
|
+
var curPluginState = key.getState(view.state);
|
|
160
|
+
var dragged = draggedHeight(curPluginState.dragging, ev, rowMinHeight);
|
|
161
|
+
var offset = ev.clientY - curPluginState.dragging.startY;
|
|
162
|
+
displayRowHeight(view, curPluginState.activeHandle, dragged, rowMinHeight, offset, tableHeight);
|
|
163
|
+
}
|
|
164
|
+
event.view.addEventListener('mouseup', finish);
|
|
165
|
+
event.view.addEventListener('mousemove', move);
|
|
166
|
+
event.preventDefault();
|
|
167
|
+
return true;
|
|
168
|
+
}
|
|
169
|
+
function domCellAround(target) {
|
|
170
|
+
while (target && target.nodeName !== 'TD' && target.nodeName !== 'TH') {
|
|
171
|
+
target = target.classList.contains('ProseMirror') ? null : target.parentNode;
|
|
172
|
+
}
|
|
173
|
+
return target;
|
|
174
|
+
}
|
|
175
|
+
function edgeCell(view, event, side) {
|
|
176
|
+
var found = view.posAtCoords({ left: event.clientX, top: event.clientY });
|
|
177
|
+
if (!found) {
|
|
178
|
+
return -1;
|
|
179
|
+
}
|
|
180
|
+
var pos = found.pos;
|
|
181
|
+
var doc = view.state.doc;
|
|
182
|
+
var $pos = doc.resolve(pos);
|
|
183
|
+
var rowDepth = new Array($pos.depth + 1).fill(0).findIndex(function (_, i) { return $pos.node(i).type.spec.tableRole === 'row'; });
|
|
184
|
+
if (rowDepth === -1) {
|
|
185
|
+
return -1;
|
|
186
|
+
}
|
|
187
|
+
var tableDepth = rowDepth - 1;
|
|
188
|
+
var rowIndex = $pos.index(tableDepth);
|
|
189
|
+
rowIndex += side === 'up' ? -1 : 0;
|
|
190
|
+
if (rowIndex < 0) {
|
|
191
|
+
return -1;
|
|
192
|
+
}
|
|
193
|
+
var rowPos = $pos.posAtIndex(rowIndex, tableDepth);
|
|
194
|
+
return rowPos;
|
|
195
|
+
}
|
|
196
|
+
function draggedHeight(dragging, event, rowMinHeight) {
|
|
197
|
+
var offset = event.clientY - dragging.startY;
|
|
198
|
+
return Math.max(rowMinHeight, dragging.startHeight.rowHeight + offset);
|
|
199
|
+
}
|
|
200
|
+
function updateHandle(view, value) {
|
|
201
|
+
view.dispatch(view.state.tr.setMeta(key, { setHandle: value }));
|
|
202
|
+
}
|
|
203
|
+
function updateRowHeight(view, tr, rowPos, height) {
|
|
204
|
+
var doc = view.state.doc;
|
|
205
|
+
var row = doc.nodeAt(rowPos);
|
|
206
|
+
tr.setNodeMarkup(rowPos, null, setNodeStyle(row.attrs, 'height', height + 'px'));
|
|
207
|
+
var dom = view.nodeDOM(rowPos);
|
|
208
|
+
var table = dom && dom.closest('table');
|
|
209
|
+
var tableHeight = table && table.style.height;
|
|
210
|
+
if (tableHeight) {
|
|
211
|
+
var $pos = doc.resolve(rowPos);
|
|
212
|
+
var tablePos = $pos.start($pos.depth) - 1;
|
|
213
|
+
tr.setNodeMarkup(tablePos, null, setNodeStyle($pos.parent.attrs, 'height', tableHeight));
|
|
214
|
+
}
|
|
215
|
+
}
|
|
216
|
+
// tslint:disable-next-line:max-line-length
|
|
217
|
+
function displayRowHeight(view, rowPos, height, rowMinHeight, offset, tableHeight) {
|
|
218
|
+
var dom = view.nodeDOM(rowPos);
|
|
219
|
+
if (dom) {
|
|
220
|
+
dom.style.height = Math.max(height, rowMinHeight) + 'px';
|
|
221
|
+
var table = dom.closest('table');
|
|
222
|
+
var newHeight = (parseFloat(tableHeight) + offset) + 'px';
|
|
223
|
+
var current = table && table.style.height;
|
|
224
|
+
if (current && current !== newHeight) {
|
|
225
|
+
table.style.height = (parseFloat(tableHeight) + offset) + 'px';
|
|
226
|
+
}
|
|
227
|
+
}
|
|
228
|
+
}
|
|
229
|
+
function handleDecorations(state, pos) {
|
|
230
|
+
var decorations = [];
|
|
231
|
+
if (typeof pos !== 'number') {
|
|
232
|
+
return;
|
|
233
|
+
}
|
|
234
|
+
var $row = state.doc.resolve(pos), table = $row.parent, map = TableMap.get(table), rowIndex = $row.index($row.depth), start = $row.start($row.depth);
|
|
235
|
+
for (var col = 0; col < map.width; col++) {
|
|
236
|
+
var index = col + rowIndex * map.width;
|
|
237
|
+
var cellPos = map.map[index];
|
|
238
|
+
var widgetPos = start + cellPos + table.nodeAt(cellPos).nodeSize - 1;
|
|
239
|
+
var dom = document.createElement('div');
|
|
240
|
+
dom.className = 'row-resize-handle';
|
|
241
|
+
decorations.push(Decoration.widget(widgetPos, dom));
|
|
242
|
+
}
|
|
243
|
+
return DecorationSet.create(state.doc, decorations);
|
|
244
|
+
}
|