@atlaskit/editor-plugin-base 0.3.3 → 0.3.4
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/CHANGELOG.md +6 -0
- package/dist/cjs/plugin.js +1 -3
- package/dist/cjs/pm-plugins/scroll-gutter/index.js +5 -5
- package/dist/es2019/plugin.js +1 -3
- package/dist/es2019/pm-plugins/scroll-gutter/index.js +5 -5
- package/dist/esm/plugin.js +1 -3
- package/dist/esm/pm-plugins/scroll-gutter/index.js +5 -5
- package/package.json +2 -8
- package/tsconfig.app.json +0 -3
- package/dist/cjs/pm-plugins/scroll-gutter/plugin-deprecated.js +0 -262
- package/dist/es2019/pm-plugins/scroll-gutter/plugin-deprecated.js +0 -244
- package/dist/esm/pm-plugins/scroll-gutter/plugin-deprecated.js +0 -256
- package/dist/types/pm-plugins/scroll-gutter/plugin-deprecated.d.ts +0 -22
- package/dist/types-ts4.5/pm-plugins/scroll-gutter/plugin-deprecated.d.ts +0 -22
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,11 @@
|
|
|
1
1
|
# @atlaskit/editor-plugin-base
|
|
2
2
|
|
|
3
|
+
## 0.3.4
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- [#67690](https://stash.atlassian.com/projects/CONFCLOUD/repos/confluence-frontend/pull-requests/67690) [`2f7dc1629e1c`](https://stash.atlassian.com/projects/CONFCLOUD/repos/confluence-frontend/commits/2f7dc1629e1c) - Cleanup feature flag for scrolling optimisation.
|
|
8
|
+
|
|
3
9
|
## 0.3.3
|
|
4
10
|
|
|
5
11
|
### Patch Changes
|
package/dist/cjs/plugin.js
CHANGED
|
@@ -11,7 +11,6 @@ var _adfSchema = require("@atlaskit/adf-schema");
|
|
|
11
11
|
var _keymaps = require("@atlaskit/editor-common/keymaps");
|
|
12
12
|
var _commands = require("@atlaskit/editor-prosemirror/commands");
|
|
13
13
|
var _history = require("@atlaskit/editor-prosemirror/history");
|
|
14
|
-
var _platformFeatureFlags = require("@atlaskit/platform-feature-flags");
|
|
15
14
|
var _commands2 = require("./commands");
|
|
16
15
|
var _contextIdentifier = _interopRequireWildcard(require("./pm-plugins/context-identifier"));
|
|
17
16
|
var _disableSpellChecking = _interopRequireDefault(require("./pm-plugins/disable-spell-checking"));
|
|
@@ -20,7 +19,6 @@ var _frozenEditor = _interopRequireDefault(require("./pm-plugins/frozen-editor")
|
|
|
20
19
|
var _inlineCursorTarget = _interopRequireDefault(require("./pm-plugins/inline-cursor-target"));
|
|
21
20
|
var _newlinePreserveMarks = _interopRequireDefault(require("./pm-plugins/newline-preserve-marks"));
|
|
22
21
|
var _scrollGutter = _interopRequireWildcard(require("./pm-plugins/scroll-gutter"));
|
|
23
|
-
var _pluginDeprecated = _interopRequireDefault(require("./pm-plugins/scroll-gutter/plugin-deprecated"));
|
|
24
22
|
function _getRequireWildcardCache(nodeInterop) { if (typeof WeakMap !== "function") return null; var cacheBabelInterop = new WeakMap(); var cacheNodeInterop = new WeakMap(); return (_getRequireWildcardCache = function _getRequireWildcardCache(nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); }
|
|
25
23
|
function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj && obj.__esModule) { return obj; } if (obj === null || _typeof(obj) !== "object" && typeof obj !== "function") { return { default: obj }; } var cache = _getRequireWildcardCache(nodeInterop); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; }
|
|
26
24
|
function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
|
|
@@ -108,7 +106,7 @@ var basePlugin = function basePlugin(_ref) {
|
|
|
108
106
|
plugins.push({
|
|
109
107
|
name: 'scrollGutterPlugin',
|
|
110
108
|
plugin: function plugin() {
|
|
111
|
-
return (0,
|
|
109
|
+
return (0, _scrollGutter.default)(options.allowScrollGutter);
|
|
112
110
|
}
|
|
113
111
|
});
|
|
114
112
|
}
|
|
@@ -216,7 +216,7 @@ var _default = exports.default = function _default() {
|
|
|
216
216
|
gutter.addGutter(editorParentElement);
|
|
217
217
|
}
|
|
218
218
|
};
|
|
219
|
-
var toggleGutter = function toggleGutter(
|
|
219
|
+
var toggleGutter = function toggleGutter(contentSize, threshold) {
|
|
220
220
|
if (pluginOptions.persistScrollGutter) {
|
|
221
221
|
if (!(0, _utils.isEmptyDocument)(view.state.doc)) {
|
|
222
222
|
addAndObserveGutter();
|
|
@@ -229,8 +229,7 @@ var _default = exports.default = function _default() {
|
|
|
229
229
|
// Add or remove the gutter based on whether the content is about to exceed the viewport height.
|
|
230
230
|
// We do this to ensure there is sufficient white space below the last content node in order to
|
|
231
231
|
// see any UI control elements which may sit beneath it.
|
|
232
|
-
|
|
233
|
-
if (contentSize >= gutterThresholdHeight) {
|
|
232
|
+
if (contentSize >= threshold) {
|
|
234
233
|
addAndObserveGutter();
|
|
235
234
|
} else {
|
|
236
235
|
if (gutter.isMounted()) {
|
|
@@ -258,7 +257,7 @@ var _default = exports.default = function _default() {
|
|
|
258
257
|
} finally {
|
|
259
258
|
_iterator.f();
|
|
260
259
|
}
|
|
261
|
-
toggleGutter(
|
|
260
|
+
toggleGutter(contentElementHeight, viewportElementHeight);
|
|
262
261
|
};
|
|
263
262
|
|
|
264
263
|
// Subscribe to updates of the height of the viewport and content elements
|
|
@@ -288,7 +287,8 @@ var _default = exports.default = function _default() {
|
|
|
288
287
|
// No need to recheck if the selected node hasn't changed.
|
|
289
288
|
return;
|
|
290
289
|
}
|
|
291
|
-
|
|
290
|
+
var gutterThresholdHeight = viewportElementHeight - gutterSize;
|
|
291
|
+
toggleGutter(contentElementHeight, gutterThresholdHeight);
|
|
292
292
|
}
|
|
293
293
|
};
|
|
294
294
|
})
|
package/dist/es2019/plugin.js
CHANGED
|
@@ -2,7 +2,6 @@ import { doc, paragraph, text } from '@atlaskit/adf-schema';
|
|
|
2
2
|
import { keymap } from '@atlaskit/editor-common/keymaps';
|
|
3
3
|
import { baseKeymap } from '@atlaskit/editor-prosemirror/commands';
|
|
4
4
|
import { history } from '@atlaskit/editor-prosemirror/history';
|
|
5
|
-
import { getBooleanFF } from '@atlaskit/platform-feature-flags';
|
|
6
5
|
import { setKeyboardHeight } from './commands';
|
|
7
6
|
import contextIdentifierPlugin, { getContextIdentifier } from './pm-plugins/context-identifier';
|
|
8
7
|
import disableSpellcheckingPlugin from './pm-plugins/disable-spell-checking';
|
|
@@ -11,7 +10,6 @@ import frozenEditor from './pm-plugins/frozen-editor';
|
|
|
11
10
|
import inlineCursorTargetPlugin from './pm-plugins/inline-cursor-target';
|
|
12
11
|
import newlinePreserveMarksPlugin from './pm-plugins/newline-preserve-marks';
|
|
13
12
|
import scrollGutter, { getKeyboardHeight } from './pm-plugins/scroll-gutter';
|
|
14
|
-
import deprecatedScrollGutter from './pm-plugins/scroll-gutter/plugin-deprecated';
|
|
15
13
|
const basePlugin = ({
|
|
16
14
|
config: options,
|
|
17
15
|
api
|
|
@@ -85,7 +83,7 @@ const basePlugin = ({
|
|
|
85
83
|
if (options && options.allowScrollGutter) {
|
|
86
84
|
plugins.push({
|
|
87
85
|
name: 'scrollGutterPlugin',
|
|
88
|
-
plugin: () =>
|
|
86
|
+
plugin: () => scrollGutter(options.allowScrollGutter)
|
|
89
87
|
});
|
|
90
88
|
}
|
|
91
89
|
plugins.push({
|
|
@@ -195,7 +195,7 @@ export default ((pluginOptions = {}) => {
|
|
|
195
195
|
gutter.addGutter(editorParentElement);
|
|
196
196
|
}
|
|
197
197
|
};
|
|
198
|
-
const toggleGutter = (
|
|
198
|
+
const toggleGutter = (contentSize, threshold) => {
|
|
199
199
|
if (pluginOptions.persistScrollGutter) {
|
|
200
200
|
if (!isEmptyDocument(view.state.doc)) {
|
|
201
201
|
addAndObserveGutter();
|
|
@@ -208,8 +208,7 @@ export default ((pluginOptions = {}) => {
|
|
|
208
208
|
// Add or remove the gutter based on whether the content is about to exceed the viewport height.
|
|
209
209
|
// We do this to ensure there is sufficient white space below the last content node in order to
|
|
210
210
|
// see any UI control elements which may sit beneath it.
|
|
211
|
-
|
|
212
|
-
if (contentSize >= gutterThresholdHeight) {
|
|
211
|
+
if (contentSize >= threshold) {
|
|
213
212
|
addAndObserveGutter();
|
|
214
213
|
} else {
|
|
215
214
|
if (gutter.isMounted()) {
|
|
@@ -228,7 +227,7 @@ export default ((pluginOptions = {}) => {
|
|
|
228
227
|
contentElementHeight = elementHeight - (gutter.isMounted() ? gutterSize : 0);
|
|
229
228
|
}
|
|
230
229
|
}
|
|
231
|
-
toggleGutter(
|
|
230
|
+
toggleGutter(contentElementHeight, viewportElementHeight);
|
|
232
231
|
};
|
|
233
232
|
|
|
234
233
|
// Subscribe to updates of the height of the viewport and content elements
|
|
@@ -258,7 +257,8 @@ export default ((pluginOptions = {}) => {
|
|
|
258
257
|
// No need to recheck if the selected node hasn't changed.
|
|
259
258
|
return;
|
|
260
259
|
}
|
|
261
|
-
|
|
260
|
+
const gutterThresholdHeight = viewportElementHeight - gutterSize;
|
|
261
|
+
toggleGutter(contentElementHeight, gutterThresholdHeight);
|
|
262
262
|
}
|
|
263
263
|
};
|
|
264
264
|
}
|
package/dist/esm/plugin.js
CHANGED
|
@@ -5,7 +5,6 @@ import { doc, paragraph, text } from '@atlaskit/adf-schema';
|
|
|
5
5
|
import { keymap } from '@atlaskit/editor-common/keymaps';
|
|
6
6
|
import { baseKeymap } from '@atlaskit/editor-prosemirror/commands';
|
|
7
7
|
import { history } from '@atlaskit/editor-prosemirror/history';
|
|
8
|
-
import { getBooleanFF } from '@atlaskit/platform-feature-flags';
|
|
9
8
|
import { setKeyboardHeight } from './commands';
|
|
10
9
|
import contextIdentifierPlugin, { getContextIdentifier } from './pm-plugins/context-identifier';
|
|
11
10
|
import disableSpellcheckingPlugin from './pm-plugins/disable-spell-checking';
|
|
@@ -14,7 +13,6 @@ import frozenEditor from './pm-plugins/frozen-editor';
|
|
|
14
13
|
import inlineCursorTargetPlugin from './pm-plugins/inline-cursor-target';
|
|
15
14
|
import newlinePreserveMarksPlugin from './pm-plugins/newline-preserve-marks';
|
|
16
15
|
import scrollGutter, { getKeyboardHeight } from './pm-plugins/scroll-gutter';
|
|
17
|
-
import deprecatedScrollGutter from './pm-plugins/scroll-gutter/plugin-deprecated';
|
|
18
16
|
var basePlugin = function basePlugin(_ref) {
|
|
19
17
|
var _api$featureFlags;
|
|
20
18
|
var options = _ref.config,
|
|
@@ -98,7 +96,7 @@ var basePlugin = function basePlugin(_ref) {
|
|
|
98
96
|
plugins.push({
|
|
99
97
|
name: 'scrollGutterPlugin',
|
|
100
98
|
plugin: function plugin() {
|
|
101
|
-
return
|
|
99
|
+
return scrollGutter(options.allowScrollGutter);
|
|
102
100
|
}
|
|
103
101
|
});
|
|
104
102
|
}
|
|
@@ -210,7 +210,7 @@ export default (function () {
|
|
|
210
210
|
gutter.addGutter(editorParentElement);
|
|
211
211
|
}
|
|
212
212
|
};
|
|
213
|
-
var toggleGutter = function toggleGutter(
|
|
213
|
+
var toggleGutter = function toggleGutter(contentSize, threshold) {
|
|
214
214
|
if (pluginOptions.persistScrollGutter) {
|
|
215
215
|
if (!isEmptyDocument(view.state.doc)) {
|
|
216
216
|
addAndObserveGutter();
|
|
@@ -223,8 +223,7 @@ export default (function () {
|
|
|
223
223
|
// Add or remove the gutter based on whether the content is about to exceed the viewport height.
|
|
224
224
|
// We do this to ensure there is sufficient white space below the last content node in order to
|
|
225
225
|
// see any UI control elements which may sit beneath it.
|
|
226
|
-
|
|
227
|
-
if (contentSize >= gutterThresholdHeight) {
|
|
226
|
+
if (contentSize >= threshold) {
|
|
228
227
|
addAndObserveGutter();
|
|
229
228
|
} else {
|
|
230
229
|
if (gutter.isMounted()) {
|
|
@@ -252,7 +251,7 @@ export default (function () {
|
|
|
252
251
|
} finally {
|
|
253
252
|
_iterator.f();
|
|
254
253
|
}
|
|
255
|
-
toggleGutter(
|
|
254
|
+
toggleGutter(contentElementHeight, viewportElementHeight);
|
|
256
255
|
};
|
|
257
256
|
|
|
258
257
|
// Subscribe to updates of the height of the viewport and content elements
|
|
@@ -282,7 +281,8 @@ export default (function () {
|
|
|
282
281
|
// No need to recheck if the selected node hasn't changed.
|
|
283
282
|
return;
|
|
284
283
|
}
|
|
285
|
-
|
|
284
|
+
var gutterThresholdHeight = viewportElementHeight - gutterSize;
|
|
285
|
+
toggleGutter(contentElementHeight, gutterThresholdHeight);
|
|
286
286
|
}
|
|
287
287
|
};
|
|
288
288
|
})
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@atlaskit/editor-plugin-base",
|
|
3
|
-
"version": "0.3.
|
|
3
|
+
"version": "0.3.4",
|
|
4
4
|
"description": "Base plugin for @atlaskit/editor-core",
|
|
5
5
|
"author": "Atlassian Pty Ltd",
|
|
6
6
|
"license": "Apache-2.0",
|
|
@@ -36,7 +36,6 @@
|
|
|
36
36
|
"@atlaskit/editor-common": "^77.0.0",
|
|
37
37
|
"@atlaskit/editor-plugin-feature-flags": "^1.0.1",
|
|
38
38
|
"@atlaskit/editor-prosemirror": "1.1.0",
|
|
39
|
-
"@atlaskit/platform-feature-flags": "^0.2.0",
|
|
40
39
|
"@babel/runtime": "^7.0.0"
|
|
41
40
|
},
|
|
42
41
|
"devDependencies": {
|
|
@@ -45,7 +44,7 @@
|
|
|
45
44
|
"@atlaskit/editor-plugin-emoji": "^1.0.0",
|
|
46
45
|
"@atlaskit/editor-plugin-guideline": "^0.5.0",
|
|
47
46
|
"@atlaskit/editor-plugin-selection": "^0.2.0",
|
|
48
|
-
"@atlaskit/editor-plugin-table": "^
|
|
47
|
+
"@atlaskit/editor-plugin-table": "^7.0.0",
|
|
49
48
|
"@atlaskit/editor-plugin-type-ahead": "^0.9.0",
|
|
50
49
|
"@atlaskit/editor-plugin-width": "^0.2.0",
|
|
51
50
|
"@atlaskit/util-data-test": "^17.8.0",
|
|
@@ -86,11 +85,6 @@
|
|
|
86
85
|
}
|
|
87
86
|
},
|
|
88
87
|
"prettier": "@atlassian/atlassian-frontend-prettier-config-1.0.0",
|
|
89
|
-
"platform-feature-flags": {
|
|
90
|
-
"platform.editor.scroll-gutter.reflow-optimisation": {
|
|
91
|
-
"type": "boolean"
|
|
92
|
-
}
|
|
93
|
-
},
|
|
94
88
|
"stricter": {
|
|
95
89
|
"no-unused-dependencies": {
|
|
96
90
|
"checkDevDependencies": true
|
package/tsconfig.app.json
CHANGED
|
@@ -1,262 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
|
|
3
|
-
Object.defineProperty(exports, "__esModule", {
|
|
4
|
-
value: true
|
|
5
|
-
});
|
|
6
|
-
exports.getKeyboardHeight = exports.default = void 0;
|
|
7
|
-
var _safePlugin = require("@atlaskit/editor-common/safe-plugin");
|
|
8
|
-
var _utils = require("@atlaskit/editor-common/utils");
|
|
9
|
-
var _pluginKey = require("./plugin-key");
|
|
10
|
-
var getKeyboardHeight = exports.getKeyboardHeight = function getKeyboardHeight(state) {
|
|
11
|
-
if (state) {
|
|
12
|
-
var scrollGutterPluginState = (0, _pluginKey.getScrollGutterPluginState)(state);
|
|
13
|
-
return scrollGutterPluginState ? scrollGutterPluginState.keyboardHeight : undefined;
|
|
14
|
-
}
|
|
15
|
-
};
|
|
16
|
-
var MIN_TAP_SIZE_IN_PX = 40;
|
|
17
|
-
function supportsIntersectionObserver() {
|
|
18
|
-
if (typeof window !== 'undefined' && 'IntersectionObserver' in window && 'IntersectionObserverEntry' in window && 'intersectionRatio' in
|
|
19
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
20
|
-
window.IntersectionObserverEntry.prototype) {
|
|
21
|
-
return true;
|
|
22
|
-
}
|
|
23
|
-
return false;
|
|
24
|
-
}
|
|
25
|
-
function listenForGutterVisibilityChanges(scrollElement, gutterIsVisible) {
|
|
26
|
-
if (supportsIntersectionObserver()) {
|
|
27
|
-
var observer = new IntersectionObserver(function (entries, _) {
|
|
28
|
-
entries.forEach(function (entry) {
|
|
29
|
-
gutterIsVisible(entry.intersectionRatio > 0);
|
|
30
|
-
});
|
|
31
|
-
}, {
|
|
32
|
-
root: scrollElement,
|
|
33
|
-
rootMargin: '0px',
|
|
34
|
-
threshold: 0
|
|
35
|
-
});
|
|
36
|
-
return observer;
|
|
37
|
-
}
|
|
38
|
-
return undefined;
|
|
39
|
-
}
|
|
40
|
-
|
|
41
|
-
/**
|
|
42
|
-
* Create a gutter element that can be added or removed from the DOM.
|
|
43
|
-
*/
|
|
44
|
-
function createGutter(gutterSize) {
|
|
45
|
-
var gutter = document.createElement('div');
|
|
46
|
-
gutter.style.paddingBottom = "".concat(gutterSize, "px");
|
|
47
|
-
gutter.id = _utils.GUTTER_SELECTOR.substr(1);
|
|
48
|
-
var initialized = false;
|
|
49
|
-
var mounted = false;
|
|
50
|
-
var currentParent = null;
|
|
51
|
-
var observer;
|
|
52
|
-
var isVisible = false;
|
|
53
|
-
return {
|
|
54
|
-
addGutter: function addGutter(parent) {
|
|
55
|
-
if (parent) {
|
|
56
|
-
currentParent = parent;
|
|
57
|
-
parent.appendChild(gutter);
|
|
58
|
-
mounted = true;
|
|
59
|
-
if (observer) {
|
|
60
|
-
observer.observe(gutter);
|
|
61
|
-
}
|
|
62
|
-
}
|
|
63
|
-
},
|
|
64
|
-
removeGutter: function removeGutter() {
|
|
65
|
-
if (currentParent && mounted) {
|
|
66
|
-
mounted = false;
|
|
67
|
-
currentParent.removeChild(gutter);
|
|
68
|
-
if (observer) {
|
|
69
|
-
observer.unobserve(gutter);
|
|
70
|
-
}
|
|
71
|
-
}
|
|
72
|
-
},
|
|
73
|
-
element: function element() {
|
|
74
|
-
return gutter;
|
|
75
|
-
},
|
|
76
|
-
isMounted: function isMounted() {
|
|
77
|
-
return mounted;
|
|
78
|
-
},
|
|
79
|
-
visible: function visible() {
|
|
80
|
-
// If we know whether it's visible we can avoid expensive calculations
|
|
81
|
-
if (observer) {
|
|
82
|
-
return isVisible;
|
|
83
|
-
}
|
|
84
|
-
// Fallback for legacy browsers assumes it's visible (if mounted)
|
|
85
|
-
return mounted;
|
|
86
|
-
},
|
|
87
|
-
observe: function observe(scrollElement) {
|
|
88
|
-
if (!initialized) {
|
|
89
|
-
initialized = true;
|
|
90
|
-
observer = listenForGutterVisibilityChanges(scrollElement, function (visible) {
|
|
91
|
-
return isVisible = visible;
|
|
92
|
-
});
|
|
93
|
-
}
|
|
94
|
-
},
|
|
95
|
-
destroy: function destroy() {
|
|
96
|
-
if (observer) {
|
|
97
|
-
observer.disconnect();
|
|
98
|
-
}
|
|
99
|
-
observer = undefined;
|
|
100
|
-
this.removeGutter();
|
|
101
|
-
initialized = mounted = false;
|
|
102
|
-
}
|
|
103
|
-
};
|
|
104
|
-
}
|
|
105
|
-
|
|
106
|
-
/**
|
|
107
|
-
* Get caret top position given the current selection,
|
|
108
|
-
* use start container position as fallback
|
|
109
|
-
*/
|
|
110
|
-
function getCaretTopPosition() {
|
|
111
|
-
var windowSelection = window.getSelection();
|
|
112
|
-
if (windowSelection && windowSelection.rangeCount > 0) {
|
|
113
|
-
var range = windowSelection.getRangeAt(0);
|
|
114
|
-
if (range) {
|
|
115
|
-
var clientRects = range.getClientRects();
|
|
116
|
-
// Return client rects
|
|
117
|
-
if (clientRects && clientRects.length > 0) {
|
|
118
|
-
return clientRects[0].top;
|
|
119
|
-
}
|
|
120
|
-
|
|
121
|
-
// Return container top
|
|
122
|
-
var container = range.startContainer;
|
|
123
|
-
if (container && container.getBoundingClientRect) {
|
|
124
|
-
return container.getBoundingClientRect().top;
|
|
125
|
-
}
|
|
126
|
-
}
|
|
127
|
-
}
|
|
128
|
-
return;
|
|
129
|
-
}
|
|
130
|
-
function scrollToGutterElement(scrollContainer, gutterElement, gutterSize) {
|
|
131
|
-
var viewportHeight = scrollContainer.offsetHeight;
|
|
132
|
-
var viewportOffsetY = scrollContainer.getBoundingClientRect().top;
|
|
133
|
-
var caretTopPosition = getCaretTopPosition();
|
|
134
|
-
if (!caretTopPosition) {
|
|
135
|
-
return false;
|
|
136
|
-
}
|
|
137
|
-
var caretTopFromContainer = caretTopPosition - viewportOffsetY;
|
|
138
|
-
var gutterThresholdTop = viewportHeight - gutterSize - MIN_TAP_SIZE_IN_PX * 2;
|
|
139
|
-
if (caretTopFromContainer < gutterThresholdTop) {
|
|
140
|
-
return false;
|
|
141
|
-
}
|
|
142
|
-
|
|
143
|
-
// Clamp the scroll position to above the scroll gutter element.
|
|
144
|
-
gutterElement.scrollIntoView(false);
|
|
145
|
-
|
|
146
|
-
// Mark scrolling as handled so that other plugin's don't override our position.
|
|
147
|
-
return true;
|
|
148
|
-
}
|
|
149
|
-
var _default = exports.default = function _default() {
|
|
150
|
-
var pluginOptions = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
|
|
151
|
-
var getScrollElement = pluginOptions.getScrollElement,
|
|
152
|
-
allowCustomScrollHandler = pluginOptions.allowCustomScrollHandler,
|
|
153
|
-
_pluginOptions$gutter = pluginOptions.gutterSize,
|
|
154
|
-
gutterSize = _pluginOptions$gutter === void 0 ? _utils.GUTTER_SIZE_IN_PX : _pluginOptions$gutter;
|
|
155
|
-
if (!getScrollElement) {
|
|
156
|
-
return undefined;
|
|
157
|
-
}
|
|
158
|
-
var gutter = createGutter(gutterSize);
|
|
159
|
-
var scrollElement = null; // | undefined;
|
|
160
|
-
|
|
161
|
-
return new _safePlugin.SafePlugin({
|
|
162
|
-
key: _pluginKey.scrollGutterPluginKey,
|
|
163
|
-
state: {
|
|
164
|
-
init: function init() {
|
|
165
|
-
return {};
|
|
166
|
-
},
|
|
167
|
-
apply: function apply(tr, pluginState) {
|
|
168
|
-
if (tr.getMeta(_pluginKey.scrollGutterPluginKey)) {
|
|
169
|
-
return tr.getMeta(_pluginKey.scrollGutterPluginKey);
|
|
170
|
-
}
|
|
171
|
-
return pluginState;
|
|
172
|
-
}
|
|
173
|
-
},
|
|
174
|
-
props: {
|
|
175
|
-
// Determines the distance (in pixels) between the cursor and the end of the visible viewport at which point,
|
|
176
|
-
// when scrolling the cursor into view, scrolling takes place.
|
|
177
|
-
// Defaults to 0: https://prosemirror.net/docs/ref/#view.EditorProps.scrollThreshold
|
|
178
|
-
scrollThreshold: gutterSize / 2,
|
|
179
|
-
// Determines the extra space (in pixels) that is left above or below the cursor when it is scrolled into view.
|
|
180
|
-
// Defaults to 5: https://prosemirror.net/docs/ref/#view.EditorProps.scrollMargin
|
|
181
|
-
scrollMargin: gutterSize,
|
|
182
|
-
// Called when the view, after updating its state, tries to scroll the selection into view
|
|
183
|
-
// https://prosemirror.net/docs/ref/#view.EditorProps.handleScrollToSelection
|
|
184
|
-
handleScrollToSelection: function handleScrollToSelection() {
|
|
185
|
-
if (allowCustomScrollHandler === false) {
|
|
186
|
-
return false;
|
|
187
|
-
}
|
|
188
|
-
if (!gutter.isMounted() || !gutter.visible() || !scrollElement) {
|
|
189
|
-
// Avoid scrolling until applicable
|
|
190
|
-
return false;
|
|
191
|
-
}
|
|
192
|
-
return scrollToGutterElement(scrollElement, gutter.element(), gutterSize);
|
|
193
|
-
}
|
|
194
|
-
},
|
|
195
|
-
view: function (_view) {
|
|
196
|
-
function view(_x) {
|
|
197
|
-
return _view.apply(this, arguments);
|
|
198
|
-
}
|
|
199
|
-
view.toString = function () {
|
|
200
|
-
return _view.toString();
|
|
201
|
-
};
|
|
202
|
-
return view;
|
|
203
|
-
}(function (view) {
|
|
204
|
-
// Store references to avoid lookups on successive checks.
|
|
205
|
-
scrollElement = getScrollElement(view);
|
|
206
|
-
var editorElement = view.dom;
|
|
207
|
-
var editorParentElement = editorElement.parentElement;
|
|
208
|
-
return {
|
|
209
|
-
destroy: function destroy() {
|
|
210
|
-
// Remove if it's mounted
|
|
211
|
-
gutter.destroy();
|
|
212
|
-
scrollElement = editorParentElement = editorElement = null;
|
|
213
|
-
},
|
|
214
|
-
/**
|
|
215
|
-
* Toggle the Scroll Gutter Element
|
|
216
|
-
*/
|
|
217
|
-
update: function update(view, prevState) {
|
|
218
|
-
var _getKeyboardHeight;
|
|
219
|
-
if (!scrollElement || !editorParentElement) {
|
|
220
|
-
return;
|
|
221
|
-
}
|
|
222
|
-
var state = view.state;
|
|
223
|
-
if (prevState.selection === state.selection) {
|
|
224
|
-
// No need to recheck if the selected node hasn't changed.
|
|
225
|
-
return;
|
|
226
|
-
}
|
|
227
|
-
var gutterMounted = gutter.isMounted();
|
|
228
|
-
var addAndObserveGutter = function addAndObserveGutter() {
|
|
229
|
-
if (!gutterMounted) {
|
|
230
|
-
gutter.observe(scrollElement);
|
|
231
|
-
gutter.addGutter(editorParentElement);
|
|
232
|
-
}
|
|
233
|
-
};
|
|
234
|
-
if (pluginOptions.persistScrollGutter) {
|
|
235
|
-
if (!(0, _utils.isEmptyDocument)(state.doc)) {
|
|
236
|
-
addAndObserveGutter();
|
|
237
|
-
} else {
|
|
238
|
-
gutter.removeGutter();
|
|
239
|
-
}
|
|
240
|
-
return;
|
|
241
|
-
}
|
|
242
|
-
// Determine whether we need to consider Keyboard Height
|
|
243
|
-
var keyboardHeight = (_getKeyboardHeight = getKeyboardHeight(state)) !== null && _getKeyboardHeight !== void 0 ? _getKeyboardHeight : 0;
|
|
244
|
-
var viewportHeight = scrollElement.offsetHeight - keyboardHeight;
|
|
245
|
-
var contentHeight = editorParentElement.offsetHeight - (gutterMounted ? gutterSize : 0);
|
|
246
|
-
|
|
247
|
-
// Add or remove the gutter based on whether the content is about to exceed the viewport height.
|
|
248
|
-
// We do this to ensure there is sufficient white space below the last content node in order to
|
|
249
|
-
// see any UI control elements which may sit beneath it.
|
|
250
|
-
var gutterThresholdHeight = viewportHeight - gutterSize;
|
|
251
|
-
if (contentHeight >= gutterThresholdHeight) {
|
|
252
|
-
addAndObserveGutter();
|
|
253
|
-
} else {
|
|
254
|
-
if (gutterMounted) {
|
|
255
|
-
gutter.removeGutter();
|
|
256
|
-
}
|
|
257
|
-
}
|
|
258
|
-
}
|
|
259
|
-
};
|
|
260
|
-
})
|
|
261
|
-
});
|
|
262
|
-
};
|
|
@@ -1,244 +0,0 @@
|
|
|
1
|
-
import { SafePlugin } from '@atlaskit/editor-common/safe-plugin';
|
|
2
|
-
import { GUTTER_SELECTOR, GUTTER_SIZE_IN_PX, isEmptyDocument } from '@atlaskit/editor-common/utils';
|
|
3
|
-
import { getScrollGutterPluginState, scrollGutterPluginKey } from './plugin-key';
|
|
4
|
-
export const getKeyboardHeight = state => {
|
|
5
|
-
if (state) {
|
|
6
|
-
const scrollGutterPluginState = getScrollGutterPluginState(state);
|
|
7
|
-
return scrollGutterPluginState ? scrollGutterPluginState.keyboardHeight : undefined;
|
|
8
|
-
}
|
|
9
|
-
};
|
|
10
|
-
const MIN_TAP_SIZE_IN_PX = 40;
|
|
11
|
-
function supportsIntersectionObserver() {
|
|
12
|
-
if (typeof window !== 'undefined' && 'IntersectionObserver' in window && 'IntersectionObserverEntry' in window && 'intersectionRatio' in
|
|
13
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
14
|
-
window.IntersectionObserverEntry.prototype) {
|
|
15
|
-
return true;
|
|
16
|
-
}
|
|
17
|
-
return false;
|
|
18
|
-
}
|
|
19
|
-
function listenForGutterVisibilityChanges(scrollElement, gutterIsVisible) {
|
|
20
|
-
if (supportsIntersectionObserver()) {
|
|
21
|
-
const observer = new IntersectionObserver((entries, _) => {
|
|
22
|
-
entries.forEach(entry => {
|
|
23
|
-
gutterIsVisible(entry.intersectionRatio > 0);
|
|
24
|
-
});
|
|
25
|
-
}, {
|
|
26
|
-
root: scrollElement,
|
|
27
|
-
rootMargin: '0px',
|
|
28
|
-
threshold: 0
|
|
29
|
-
});
|
|
30
|
-
return observer;
|
|
31
|
-
}
|
|
32
|
-
return undefined;
|
|
33
|
-
}
|
|
34
|
-
|
|
35
|
-
/**
|
|
36
|
-
* Create a gutter element that can be added or removed from the DOM.
|
|
37
|
-
*/
|
|
38
|
-
function createGutter(gutterSize) {
|
|
39
|
-
const gutter = document.createElement('div');
|
|
40
|
-
gutter.style.paddingBottom = `${gutterSize}px`;
|
|
41
|
-
gutter.id = GUTTER_SELECTOR.substr(1);
|
|
42
|
-
let initialized = false;
|
|
43
|
-
let mounted = false;
|
|
44
|
-
let currentParent = null;
|
|
45
|
-
let observer;
|
|
46
|
-
let isVisible = false;
|
|
47
|
-
return {
|
|
48
|
-
addGutter(parent) {
|
|
49
|
-
if (parent) {
|
|
50
|
-
currentParent = parent;
|
|
51
|
-
parent.appendChild(gutter);
|
|
52
|
-
mounted = true;
|
|
53
|
-
if (observer) {
|
|
54
|
-
observer.observe(gutter);
|
|
55
|
-
}
|
|
56
|
-
}
|
|
57
|
-
},
|
|
58
|
-
removeGutter() {
|
|
59
|
-
if (currentParent && mounted) {
|
|
60
|
-
mounted = false;
|
|
61
|
-
currentParent.removeChild(gutter);
|
|
62
|
-
if (observer) {
|
|
63
|
-
observer.unobserve(gutter);
|
|
64
|
-
}
|
|
65
|
-
}
|
|
66
|
-
},
|
|
67
|
-
element() {
|
|
68
|
-
return gutter;
|
|
69
|
-
},
|
|
70
|
-
isMounted() {
|
|
71
|
-
return mounted;
|
|
72
|
-
},
|
|
73
|
-
visible() {
|
|
74
|
-
// If we know whether it's visible we can avoid expensive calculations
|
|
75
|
-
if (observer) {
|
|
76
|
-
return isVisible;
|
|
77
|
-
}
|
|
78
|
-
// Fallback for legacy browsers assumes it's visible (if mounted)
|
|
79
|
-
return mounted;
|
|
80
|
-
},
|
|
81
|
-
observe(scrollElement) {
|
|
82
|
-
if (!initialized) {
|
|
83
|
-
initialized = true;
|
|
84
|
-
observer = listenForGutterVisibilityChanges(scrollElement, visible => isVisible = visible);
|
|
85
|
-
}
|
|
86
|
-
},
|
|
87
|
-
destroy() {
|
|
88
|
-
if (observer) {
|
|
89
|
-
observer.disconnect();
|
|
90
|
-
}
|
|
91
|
-
observer = undefined;
|
|
92
|
-
this.removeGutter();
|
|
93
|
-
initialized = mounted = false;
|
|
94
|
-
}
|
|
95
|
-
};
|
|
96
|
-
}
|
|
97
|
-
|
|
98
|
-
/**
|
|
99
|
-
* Get caret top position given the current selection,
|
|
100
|
-
* use start container position as fallback
|
|
101
|
-
*/
|
|
102
|
-
function getCaretTopPosition() {
|
|
103
|
-
const windowSelection = window.getSelection();
|
|
104
|
-
if (windowSelection && windowSelection.rangeCount > 0) {
|
|
105
|
-
const range = windowSelection.getRangeAt(0);
|
|
106
|
-
if (range) {
|
|
107
|
-
const clientRects = range.getClientRects();
|
|
108
|
-
// Return client rects
|
|
109
|
-
if (clientRects && clientRects.length > 0) {
|
|
110
|
-
return clientRects[0].top;
|
|
111
|
-
}
|
|
112
|
-
|
|
113
|
-
// Return container top
|
|
114
|
-
const container = range.startContainer;
|
|
115
|
-
if (container && container.getBoundingClientRect) {
|
|
116
|
-
return container.getBoundingClientRect().top;
|
|
117
|
-
}
|
|
118
|
-
}
|
|
119
|
-
}
|
|
120
|
-
return;
|
|
121
|
-
}
|
|
122
|
-
function scrollToGutterElement(scrollContainer, gutterElement, gutterSize) {
|
|
123
|
-
const viewportHeight = scrollContainer.offsetHeight;
|
|
124
|
-
const viewportOffsetY = scrollContainer.getBoundingClientRect().top;
|
|
125
|
-
const caretTopPosition = getCaretTopPosition();
|
|
126
|
-
if (!caretTopPosition) {
|
|
127
|
-
return false;
|
|
128
|
-
}
|
|
129
|
-
const caretTopFromContainer = caretTopPosition - viewportOffsetY;
|
|
130
|
-
const gutterThresholdTop = viewportHeight - gutterSize - MIN_TAP_SIZE_IN_PX * 2;
|
|
131
|
-
if (caretTopFromContainer < gutterThresholdTop) {
|
|
132
|
-
return false;
|
|
133
|
-
}
|
|
134
|
-
|
|
135
|
-
// Clamp the scroll position to above the scroll gutter element.
|
|
136
|
-
gutterElement.scrollIntoView(false);
|
|
137
|
-
|
|
138
|
-
// Mark scrolling as handled so that other plugin's don't override our position.
|
|
139
|
-
return true;
|
|
140
|
-
}
|
|
141
|
-
export default ((pluginOptions = {}) => {
|
|
142
|
-
const {
|
|
143
|
-
getScrollElement,
|
|
144
|
-
allowCustomScrollHandler,
|
|
145
|
-
gutterSize = GUTTER_SIZE_IN_PX
|
|
146
|
-
} = pluginOptions;
|
|
147
|
-
if (!getScrollElement) {
|
|
148
|
-
return undefined;
|
|
149
|
-
}
|
|
150
|
-
const gutter = createGutter(gutterSize);
|
|
151
|
-
let scrollElement = null; // | undefined;
|
|
152
|
-
|
|
153
|
-
return new SafePlugin({
|
|
154
|
-
key: scrollGutterPluginKey,
|
|
155
|
-
state: {
|
|
156
|
-
init: () => ({}),
|
|
157
|
-
apply: (tr, pluginState) => {
|
|
158
|
-
if (tr.getMeta(scrollGutterPluginKey)) {
|
|
159
|
-
return tr.getMeta(scrollGutterPluginKey);
|
|
160
|
-
}
|
|
161
|
-
return pluginState;
|
|
162
|
-
}
|
|
163
|
-
},
|
|
164
|
-
props: {
|
|
165
|
-
// Determines the distance (in pixels) between the cursor and the end of the visible viewport at which point,
|
|
166
|
-
// when scrolling the cursor into view, scrolling takes place.
|
|
167
|
-
// Defaults to 0: https://prosemirror.net/docs/ref/#view.EditorProps.scrollThreshold
|
|
168
|
-
scrollThreshold: gutterSize / 2,
|
|
169
|
-
// Determines the extra space (in pixels) that is left above or below the cursor when it is scrolled into view.
|
|
170
|
-
// Defaults to 5: https://prosemirror.net/docs/ref/#view.EditorProps.scrollMargin
|
|
171
|
-
scrollMargin: gutterSize,
|
|
172
|
-
// Called when the view, after updating its state, tries to scroll the selection into view
|
|
173
|
-
// https://prosemirror.net/docs/ref/#view.EditorProps.handleScrollToSelection
|
|
174
|
-
handleScrollToSelection: () => {
|
|
175
|
-
if (allowCustomScrollHandler === false) {
|
|
176
|
-
return false;
|
|
177
|
-
}
|
|
178
|
-
if (!gutter.isMounted() || !gutter.visible() || !scrollElement) {
|
|
179
|
-
// Avoid scrolling until applicable
|
|
180
|
-
return false;
|
|
181
|
-
}
|
|
182
|
-
return scrollToGutterElement(scrollElement, gutter.element(), gutterSize);
|
|
183
|
-
}
|
|
184
|
-
},
|
|
185
|
-
view(view) {
|
|
186
|
-
// Store references to avoid lookups on successive checks.
|
|
187
|
-
scrollElement = getScrollElement(view);
|
|
188
|
-
let editorElement = view.dom;
|
|
189
|
-
let editorParentElement = editorElement.parentElement;
|
|
190
|
-
return {
|
|
191
|
-
destroy() {
|
|
192
|
-
// Remove if it's mounted
|
|
193
|
-
gutter.destroy();
|
|
194
|
-
scrollElement = editorParentElement = editorElement = null;
|
|
195
|
-
},
|
|
196
|
-
/**
|
|
197
|
-
* Toggle the Scroll Gutter Element
|
|
198
|
-
*/
|
|
199
|
-
update(view, prevState) {
|
|
200
|
-
var _getKeyboardHeight;
|
|
201
|
-
if (!scrollElement || !editorParentElement) {
|
|
202
|
-
return;
|
|
203
|
-
}
|
|
204
|
-
const state = view.state;
|
|
205
|
-
if (prevState.selection === state.selection) {
|
|
206
|
-
// No need to recheck if the selected node hasn't changed.
|
|
207
|
-
return;
|
|
208
|
-
}
|
|
209
|
-
const gutterMounted = gutter.isMounted();
|
|
210
|
-
const addAndObserveGutter = () => {
|
|
211
|
-
if (!gutterMounted) {
|
|
212
|
-
gutter.observe(scrollElement);
|
|
213
|
-
gutter.addGutter(editorParentElement);
|
|
214
|
-
}
|
|
215
|
-
};
|
|
216
|
-
if (pluginOptions.persistScrollGutter) {
|
|
217
|
-
if (!isEmptyDocument(state.doc)) {
|
|
218
|
-
addAndObserveGutter();
|
|
219
|
-
} else {
|
|
220
|
-
gutter.removeGutter();
|
|
221
|
-
}
|
|
222
|
-
return;
|
|
223
|
-
}
|
|
224
|
-
// Determine whether we need to consider Keyboard Height
|
|
225
|
-
const keyboardHeight = (_getKeyboardHeight = getKeyboardHeight(state)) !== null && _getKeyboardHeight !== void 0 ? _getKeyboardHeight : 0;
|
|
226
|
-
const viewportHeight = scrollElement.offsetHeight - keyboardHeight;
|
|
227
|
-
const contentHeight = editorParentElement.offsetHeight - (gutterMounted ? gutterSize : 0);
|
|
228
|
-
|
|
229
|
-
// Add or remove the gutter based on whether the content is about to exceed the viewport height.
|
|
230
|
-
// We do this to ensure there is sufficient white space below the last content node in order to
|
|
231
|
-
// see any UI control elements which may sit beneath it.
|
|
232
|
-
const gutterThresholdHeight = viewportHeight - gutterSize;
|
|
233
|
-
if (contentHeight >= gutterThresholdHeight) {
|
|
234
|
-
addAndObserveGutter();
|
|
235
|
-
} else {
|
|
236
|
-
if (gutterMounted) {
|
|
237
|
-
gutter.removeGutter();
|
|
238
|
-
}
|
|
239
|
-
}
|
|
240
|
-
}
|
|
241
|
-
};
|
|
242
|
-
}
|
|
243
|
-
});
|
|
244
|
-
});
|
|
@@ -1,256 +0,0 @@
|
|
|
1
|
-
import { SafePlugin } from '@atlaskit/editor-common/safe-plugin';
|
|
2
|
-
import { GUTTER_SELECTOR, GUTTER_SIZE_IN_PX, isEmptyDocument } from '@atlaskit/editor-common/utils';
|
|
3
|
-
import { getScrollGutterPluginState, scrollGutterPluginKey } from './plugin-key';
|
|
4
|
-
export var getKeyboardHeight = function getKeyboardHeight(state) {
|
|
5
|
-
if (state) {
|
|
6
|
-
var scrollGutterPluginState = getScrollGutterPluginState(state);
|
|
7
|
-
return scrollGutterPluginState ? scrollGutterPluginState.keyboardHeight : undefined;
|
|
8
|
-
}
|
|
9
|
-
};
|
|
10
|
-
var MIN_TAP_SIZE_IN_PX = 40;
|
|
11
|
-
function supportsIntersectionObserver() {
|
|
12
|
-
if (typeof window !== 'undefined' && 'IntersectionObserver' in window && 'IntersectionObserverEntry' in window && 'intersectionRatio' in
|
|
13
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
14
|
-
window.IntersectionObserverEntry.prototype) {
|
|
15
|
-
return true;
|
|
16
|
-
}
|
|
17
|
-
return false;
|
|
18
|
-
}
|
|
19
|
-
function listenForGutterVisibilityChanges(scrollElement, gutterIsVisible) {
|
|
20
|
-
if (supportsIntersectionObserver()) {
|
|
21
|
-
var observer = new IntersectionObserver(function (entries, _) {
|
|
22
|
-
entries.forEach(function (entry) {
|
|
23
|
-
gutterIsVisible(entry.intersectionRatio > 0);
|
|
24
|
-
});
|
|
25
|
-
}, {
|
|
26
|
-
root: scrollElement,
|
|
27
|
-
rootMargin: '0px',
|
|
28
|
-
threshold: 0
|
|
29
|
-
});
|
|
30
|
-
return observer;
|
|
31
|
-
}
|
|
32
|
-
return undefined;
|
|
33
|
-
}
|
|
34
|
-
|
|
35
|
-
/**
|
|
36
|
-
* Create a gutter element that can be added or removed from the DOM.
|
|
37
|
-
*/
|
|
38
|
-
function createGutter(gutterSize) {
|
|
39
|
-
var gutter = document.createElement('div');
|
|
40
|
-
gutter.style.paddingBottom = "".concat(gutterSize, "px");
|
|
41
|
-
gutter.id = GUTTER_SELECTOR.substr(1);
|
|
42
|
-
var initialized = false;
|
|
43
|
-
var mounted = false;
|
|
44
|
-
var currentParent = null;
|
|
45
|
-
var observer;
|
|
46
|
-
var isVisible = false;
|
|
47
|
-
return {
|
|
48
|
-
addGutter: function addGutter(parent) {
|
|
49
|
-
if (parent) {
|
|
50
|
-
currentParent = parent;
|
|
51
|
-
parent.appendChild(gutter);
|
|
52
|
-
mounted = true;
|
|
53
|
-
if (observer) {
|
|
54
|
-
observer.observe(gutter);
|
|
55
|
-
}
|
|
56
|
-
}
|
|
57
|
-
},
|
|
58
|
-
removeGutter: function removeGutter() {
|
|
59
|
-
if (currentParent && mounted) {
|
|
60
|
-
mounted = false;
|
|
61
|
-
currentParent.removeChild(gutter);
|
|
62
|
-
if (observer) {
|
|
63
|
-
observer.unobserve(gutter);
|
|
64
|
-
}
|
|
65
|
-
}
|
|
66
|
-
},
|
|
67
|
-
element: function element() {
|
|
68
|
-
return gutter;
|
|
69
|
-
},
|
|
70
|
-
isMounted: function isMounted() {
|
|
71
|
-
return mounted;
|
|
72
|
-
},
|
|
73
|
-
visible: function visible() {
|
|
74
|
-
// If we know whether it's visible we can avoid expensive calculations
|
|
75
|
-
if (observer) {
|
|
76
|
-
return isVisible;
|
|
77
|
-
}
|
|
78
|
-
// Fallback for legacy browsers assumes it's visible (if mounted)
|
|
79
|
-
return mounted;
|
|
80
|
-
},
|
|
81
|
-
observe: function observe(scrollElement) {
|
|
82
|
-
if (!initialized) {
|
|
83
|
-
initialized = true;
|
|
84
|
-
observer = listenForGutterVisibilityChanges(scrollElement, function (visible) {
|
|
85
|
-
return isVisible = visible;
|
|
86
|
-
});
|
|
87
|
-
}
|
|
88
|
-
},
|
|
89
|
-
destroy: function destroy() {
|
|
90
|
-
if (observer) {
|
|
91
|
-
observer.disconnect();
|
|
92
|
-
}
|
|
93
|
-
observer = undefined;
|
|
94
|
-
this.removeGutter();
|
|
95
|
-
initialized = mounted = false;
|
|
96
|
-
}
|
|
97
|
-
};
|
|
98
|
-
}
|
|
99
|
-
|
|
100
|
-
/**
|
|
101
|
-
* Get caret top position given the current selection,
|
|
102
|
-
* use start container position as fallback
|
|
103
|
-
*/
|
|
104
|
-
function getCaretTopPosition() {
|
|
105
|
-
var windowSelection = window.getSelection();
|
|
106
|
-
if (windowSelection && windowSelection.rangeCount > 0) {
|
|
107
|
-
var range = windowSelection.getRangeAt(0);
|
|
108
|
-
if (range) {
|
|
109
|
-
var clientRects = range.getClientRects();
|
|
110
|
-
// Return client rects
|
|
111
|
-
if (clientRects && clientRects.length > 0) {
|
|
112
|
-
return clientRects[0].top;
|
|
113
|
-
}
|
|
114
|
-
|
|
115
|
-
// Return container top
|
|
116
|
-
var container = range.startContainer;
|
|
117
|
-
if (container && container.getBoundingClientRect) {
|
|
118
|
-
return container.getBoundingClientRect().top;
|
|
119
|
-
}
|
|
120
|
-
}
|
|
121
|
-
}
|
|
122
|
-
return;
|
|
123
|
-
}
|
|
124
|
-
function scrollToGutterElement(scrollContainer, gutterElement, gutterSize) {
|
|
125
|
-
var viewportHeight = scrollContainer.offsetHeight;
|
|
126
|
-
var viewportOffsetY = scrollContainer.getBoundingClientRect().top;
|
|
127
|
-
var caretTopPosition = getCaretTopPosition();
|
|
128
|
-
if (!caretTopPosition) {
|
|
129
|
-
return false;
|
|
130
|
-
}
|
|
131
|
-
var caretTopFromContainer = caretTopPosition - viewportOffsetY;
|
|
132
|
-
var gutterThresholdTop = viewportHeight - gutterSize - MIN_TAP_SIZE_IN_PX * 2;
|
|
133
|
-
if (caretTopFromContainer < gutterThresholdTop) {
|
|
134
|
-
return false;
|
|
135
|
-
}
|
|
136
|
-
|
|
137
|
-
// Clamp the scroll position to above the scroll gutter element.
|
|
138
|
-
gutterElement.scrollIntoView(false);
|
|
139
|
-
|
|
140
|
-
// Mark scrolling as handled so that other plugin's don't override our position.
|
|
141
|
-
return true;
|
|
142
|
-
}
|
|
143
|
-
export default (function () {
|
|
144
|
-
var pluginOptions = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
|
|
145
|
-
var getScrollElement = pluginOptions.getScrollElement,
|
|
146
|
-
allowCustomScrollHandler = pluginOptions.allowCustomScrollHandler,
|
|
147
|
-
_pluginOptions$gutter = pluginOptions.gutterSize,
|
|
148
|
-
gutterSize = _pluginOptions$gutter === void 0 ? GUTTER_SIZE_IN_PX : _pluginOptions$gutter;
|
|
149
|
-
if (!getScrollElement) {
|
|
150
|
-
return undefined;
|
|
151
|
-
}
|
|
152
|
-
var gutter = createGutter(gutterSize);
|
|
153
|
-
var scrollElement = null; // | undefined;
|
|
154
|
-
|
|
155
|
-
return new SafePlugin({
|
|
156
|
-
key: scrollGutterPluginKey,
|
|
157
|
-
state: {
|
|
158
|
-
init: function init() {
|
|
159
|
-
return {};
|
|
160
|
-
},
|
|
161
|
-
apply: function apply(tr, pluginState) {
|
|
162
|
-
if (tr.getMeta(scrollGutterPluginKey)) {
|
|
163
|
-
return tr.getMeta(scrollGutterPluginKey);
|
|
164
|
-
}
|
|
165
|
-
return pluginState;
|
|
166
|
-
}
|
|
167
|
-
},
|
|
168
|
-
props: {
|
|
169
|
-
// Determines the distance (in pixels) between the cursor and the end of the visible viewport at which point,
|
|
170
|
-
// when scrolling the cursor into view, scrolling takes place.
|
|
171
|
-
// Defaults to 0: https://prosemirror.net/docs/ref/#view.EditorProps.scrollThreshold
|
|
172
|
-
scrollThreshold: gutterSize / 2,
|
|
173
|
-
// Determines the extra space (in pixels) that is left above or below the cursor when it is scrolled into view.
|
|
174
|
-
// Defaults to 5: https://prosemirror.net/docs/ref/#view.EditorProps.scrollMargin
|
|
175
|
-
scrollMargin: gutterSize,
|
|
176
|
-
// Called when the view, after updating its state, tries to scroll the selection into view
|
|
177
|
-
// https://prosemirror.net/docs/ref/#view.EditorProps.handleScrollToSelection
|
|
178
|
-
handleScrollToSelection: function handleScrollToSelection() {
|
|
179
|
-
if (allowCustomScrollHandler === false) {
|
|
180
|
-
return false;
|
|
181
|
-
}
|
|
182
|
-
if (!gutter.isMounted() || !gutter.visible() || !scrollElement) {
|
|
183
|
-
// Avoid scrolling until applicable
|
|
184
|
-
return false;
|
|
185
|
-
}
|
|
186
|
-
return scrollToGutterElement(scrollElement, gutter.element(), gutterSize);
|
|
187
|
-
}
|
|
188
|
-
},
|
|
189
|
-
view: function (_view) {
|
|
190
|
-
function view(_x) {
|
|
191
|
-
return _view.apply(this, arguments);
|
|
192
|
-
}
|
|
193
|
-
view.toString = function () {
|
|
194
|
-
return _view.toString();
|
|
195
|
-
};
|
|
196
|
-
return view;
|
|
197
|
-
}(function (view) {
|
|
198
|
-
// Store references to avoid lookups on successive checks.
|
|
199
|
-
scrollElement = getScrollElement(view);
|
|
200
|
-
var editorElement = view.dom;
|
|
201
|
-
var editorParentElement = editorElement.parentElement;
|
|
202
|
-
return {
|
|
203
|
-
destroy: function destroy() {
|
|
204
|
-
// Remove if it's mounted
|
|
205
|
-
gutter.destroy();
|
|
206
|
-
scrollElement = editorParentElement = editorElement = null;
|
|
207
|
-
},
|
|
208
|
-
/**
|
|
209
|
-
* Toggle the Scroll Gutter Element
|
|
210
|
-
*/
|
|
211
|
-
update: function update(view, prevState) {
|
|
212
|
-
var _getKeyboardHeight;
|
|
213
|
-
if (!scrollElement || !editorParentElement) {
|
|
214
|
-
return;
|
|
215
|
-
}
|
|
216
|
-
var state = view.state;
|
|
217
|
-
if (prevState.selection === state.selection) {
|
|
218
|
-
// No need to recheck if the selected node hasn't changed.
|
|
219
|
-
return;
|
|
220
|
-
}
|
|
221
|
-
var gutterMounted = gutter.isMounted();
|
|
222
|
-
var addAndObserveGutter = function addAndObserveGutter() {
|
|
223
|
-
if (!gutterMounted) {
|
|
224
|
-
gutter.observe(scrollElement);
|
|
225
|
-
gutter.addGutter(editorParentElement);
|
|
226
|
-
}
|
|
227
|
-
};
|
|
228
|
-
if (pluginOptions.persistScrollGutter) {
|
|
229
|
-
if (!isEmptyDocument(state.doc)) {
|
|
230
|
-
addAndObserveGutter();
|
|
231
|
-
} else {
|
|
232
|
-
gutter.removeGutter();
|
|
233
|
-
}
|
|
234
|
-
return;
|
|
235
|
-
}
|
|
236
|
-
// Determine whether we need to consider Keyboard Height
|
|
237
|
-
var keyboardHeight = (_getKeyboardHeight = getKeyboardHeight(state)) !== null && _getKeyboardHeight !== void 0 ? _getKeyboardHeight : 0;
|
|
238
|
-
var viewportHeight = scrollElement.offsetHeight - keyboardHeight;
|
|
239
|
-
var contentHeight = editorParentElement.offsetHeight - (gutterMounted ? gutterSize : 0);
|
|
240
|
-
|
|
241
|
-
// Add or remove the gutter based on whether the content is about to exceed the viewport height.
|
|
242
|
-
// We do this to ensure there is sufficient white space below the last content node in order to
|
|
243
|
-
// see any UI control elements which may sit beneath it.
|
|
244
|
-
var gutterThresholdHeight = viewportHeight - gutterSize;
|
|
245
|
-
if (contentHeight >= gutterThresholdHeight) {
|
|
246
|
-
addAndObserveGutter();
|
|
247
|
-
} else {
|
|
248
|
-
if (gutterMounted) {
|
|
249
|
-
gutter.removeGutter();
|
|
250
|
-
}
|
|
251
|
-
}
|
|
252
|
-
}
|
|
253
|
-
};
|
|
254
|
-
})
|
|
255
|
-
});
|
|
256
|
-
});
|
|
@@ -1,22 +0,0 @@
|
|
|
1
|
-
import { SafePlugin } from '@atlaskit/editor-common/safe-plugin';
|
|
2
|
-
import type { EditorState } from '@atlaskit/editor-prosemirror/state';
|
|
3
|
-
import type { EditorView } from '@atlaskit/editor-prosemirror/view';
|
|
4
|
-
export declare const getKeyboardHeight: (state?: EditorState) => number | undefined;
|
|
5
|
-
export type ScrollGutterPluginOptions = {
|
|
6
|
-
/** Element the page uses for scrolling */
|
|
7
|
-
getScrollElement?: (view: EditorView) => HTMLElement | null;
|
|
8
|
-
/**
|
|
9
|
-
* Whether to allow custom functionality to scroll to gutter element in
|
|
10
|
-
* plugin's handleScrollToSelection function
|
|
11
|
-
* Default is true
|
|
12
|
-
*/
|
|
13
|
-
allowCustomScrollHandler?: boolean;
|
|
14
|
-
/**
|
|
15
|
-
* Persist scroll gutter when the mobile appearance is COMPACT
|
|
16
|
-
* Default is false
|
|
17
|
-
*/
|
|
18
|
-
persistScrollGutter?: boolean;
|
|
19
|
-
gutterSize?: number;
|
|
20
|
-
};
|
|
21
|
-
declare const _default: (pluginOptions?: ScrollGutterPluginOptions) => SafePlugin<{}> | undefined;
|
|
22
|
-
export default _default;
|
|
@@ -1,22 +0,0 @@
|
|
|
1
|
-
import { SafePlugin } from '@atlaskit/editor-common/safe-plugin';
|
|
2
|
-
import type { EditorState } from '@atlaskit/editor-prosemirror/state';
|
|
3
|
-
import type { EditorView } from '@atlaskit/editor-prosemirror/view';
|
|
4
|
-
export declare const getKeyboardHeight: (state?: EditorState) => number | undefined;
|
|
5
|
-
export type ScrollGutterPluginOptions = {
|
|
6
|
-
/** Element the page uses for scrolling */
|
|
7
|
-
getScrollElement?: (view: EditorView) => HTMLElement | null;
|
|
8
|
-
/**
|
|
9
|
-
* Whether to allow custom functionality to scroll to gutter element in
|
|
10
|
-
* plugin's handleScrollToSelection function
|
|
11
|
-
* Default is true
|
|
12
|
-
*/
|
|
13
|
-
allowCustomScrollHandler?: boolean;
|
|
14
|
-
/**
|
|
15
|
-
* Persist scroll gutter when the mobile appearance is COMPACT
|
|
16
|
-
* Default is false
|
|
17
|
-
*/
|
|
18
|
-
persistScrollGutter?: boolean;
|
|
19
|
-
gutterSize?: number;
|
|
20
|
-
};
|
|
21
|
-
declare const _default: (pluginOptions?: ScrollGutterPluginOptions) => SafePlugin<{}> | undefined;
|
|
22
|
-
export default _default;
|