@atlaskit/prosemirror-input-rules 3.3.0 → 3.4.0
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 +8 -0
- package/afm-cc/tsconfig.json +24 -18
- package/afm-dev-agents/tsconfig.json +26 -0
- package/afm-jira/tsconfig.json +7 -1
- package/afm-post-office/tsconfig.json +7 -1
- package/afm-rovo-extension/tsconfig.json +26 -0
- package/afm-townsquare/tsconfig.json +26 -0
- package/afm-volt/tsconfig.json +20 -0
- package/build/tsconfig.json +8 -2
- package/dist/cjs/plugin.js +20 -0
- package/dist/cjs/utils.js +6 -2
- package/dist/es2019/plugin.js +22 -0
- package/dist/es2019/utils.js +6 -2
- package/dist/esm/plugin.js +20 -0
- package/dist/esm/utils.js +6 -2
- package/dist/types/plugin.d.ts +2 -0
- package/dist/types/utils.d.ts +9 -0
- package/dist/types-ts4.5/plugin.d.ts +2 -0
- package/dist/types-ts4.5/utils.d.ts +9 -0
- package/package.json +2 -2
- package/src/__tests__/unit/plugin.ts +40 -0
- package/src/plugin.ts +22 -0
- package/src/utils.ts +17 -1
- package/tsconfig.dev.json +7 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,13 @@
|
|
|
1
1
|
# @atlaskit/prosemirror-input-rules
|
|
2
2
|
|
|
3
|
+
## 3.4.0
|
|
4
|
+
|
|
5
|
+
### Minor Changes
|
|
6
|
+
|
|
7
|
+
- [#196046](https://bitbucket.org/atlassian/atlassian-frontend-monorepo/pull-requests/196046)
|
|
8
|
+
[`b0dad85aa7c35`](https://bitbucket.org/atlassian/atlassian-frontend-monorepo/commits/b0dad85aa7c35) -
|
|
9
|
+
[ux] [ED-27974] Allow hyperlink plugin to change text to link on blur
|
|
10
|
+
|
|
3
11
|
## 3.3.0
|
|
4
12
|
|
|
5
13
|
### Minor Changes
|
package/afm-cc/tsconfig.json
CHANGED
|
@@ -1,20 +1,26 @@
|
|
|
1
1
|
{
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
2
|
+
"extends": "../../../../tsconfig.entry-points.confluence.json",
|
|
3
|
+
"compilerOptions": {
|
|
4
|
+
"declaration": true,
|
|
5
|
+
"target": "es5",
|
|
6
|
+
"composite": true,
|
|
7
|
+
"outDir": "../../../../../confluence/tsDist/@atlaskit__prosemirror-input-rules",
|
|
8
|
+
"rootDir": "../"
|
|
9
|
+
},
|
|
10
|
+
"include": [
|
|
11
|
+
"../src/**/*.ts",
|
|
12
|
+
"../src/**/*.tsx"
|
|
13
|
+
],
|
|
14
|
+
"exclude": [
|
|
15
|
+
"../src/**/__tests__/*",
|
|
16
|
+
"../src/**/*.test.*",
|
|
17
|
+
"../src/**/test.*",
|
|
18
|
+
"../src/**/examples.*",
|
|
19
|
+
"../src/**/examples/*",
|
|
20
|
+
"../src/**/examples/**/*",
|
|
21
|
+
"../src/**/*.stories.*",
|
|
22
|
+
"../src/**/stories/*",
|
|
23
|
+
"../src/**/stories/**/*"
|
|
24
|
+
],
|
|
25
|
+
"references": []
|
|
20
26
|
}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
{
|
|
2
|
+
"extends": "../../../../tsconfig.entry-points.dev-agents.json",
|
|
3
|
+
"compilerOptions": {
|
|
4
|
+
"declaration": true,
|
|
5
|
+
"target": "es5",
|
|
6
|
+
"outDir": "../../../../../dev-agents/tsDist/@atlaskit__prosemirror-input-rules/app",
|
|
7
|
+
"rootDir": "../",
|
|
8
|
+
"composite": true
|
|
9
|
+
},
|
|
10
|
+
"include": [
|
|
11
|
+
"../src/**/*.ts",
|
|
12
|
+
"../src/**/*.tsx"
|
|
13
|
+
],
|
|
14
|
+
"exclude": [
|
|
15
|
+
"../src/**/__tests__/*",
|
|
16
|
+
"../src/**/*.test.*",
|
|
17
|
+
"../src/**/test.*",
|
|
18
|
+
"../src/**/examples.*",
|
|
19
|
+
"../src/**/examples/*",
|
|
20
|
+
"../src/**/examples/**/*",
|
|
21
|
+
"../src/**/*.stories.*",
|
|
22
|
+
"../src/**/stories/*",
|
|
23
|
+
"../src/**/stories/**/*"
|
|
24
|
+
],
|
|
25
|
+
"references": []
|
|
26
|
+
}
|
package/afm-jira/tsconfig.json
CHANGED
|
@@ -14,7 +14,13 @@
|
|
|
14
14
|
"exclude": [
|
|
15
15
|
"../src/**/__tests__/*",
|
|
16
16
|
"../src/**/*.test.*",
|
|
17
|
-
"../src/**/test.*"
|
|
17
|
+
"../src/**/test.*",
|
|
18
|
+
"../src/**/examples.*",
|
|
19
|
+
"../src/**/examples/*",
|
|
20
|
+
"../src/**/examples/**/*",
|
|
21
|
+
"../src/**/*.stories.*",
|
|
22
|
+
"../src/**/stories/*",
|
|
23
|
+
"../src/**/stories/**/*"
|
|
18
24
|
],
|
|
19
25
|
"references": []
|
|
20
26
|
}
|
|
@@ -14,7 +14,13 @@
|
|
|
14
14
|
"exclude": [
|
|
15
15
|
"../src/**/__tests__/*",
|
|
16
16
|
"../src/**/*.test.*",
|
|
17
|
-
"../src/**/test.*"
|
|
17
|
+
"../src/**/test.*",
|
|
18
|
+
"../src/**/examples.*",
|
|
19
|
+
"../src/**/examples/*",
|
|
20
|
+
"../src/**/examples/**/*",
|
|
21
|
+
"../src/**/*.stories.*",
|
|
22
|
+
"../src/**/stories/*",
|
|
23
|
+
"../src/**/stories/**/*"
|
|
18
24
|
],
|
|
19
25
|
"references": []
|
|
20
26
|
}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
{
|
|
2
|
+
"extends": "../../../../tsconfig.entry-points.rovo-extension.json",
|
|
3
|
+
"compilerOptions": {
|
|
4
|
+
"declaration": true,
|
|
5
|
+
"target": "es5",
|
|
6
|
+
"outDir": "../../../../../rovo-extension/tsDist/@atlaskit__prosemirror-input-rules/app",
|
|
7
|
+
"rootDir": "../",
|
|
8
|
+
"composite": true
|
|
9
|
+
},
|
|
10
|
+
"include": [
|
|
11
|
+
"../src/**/*.ts",
|
|
12
|
+
"../src/**/*.tsx"
|
|
13
|
+
],
|
|
14
|
+
"exclude": [
|
|
15
|
+
"../src/**/__tests__/*",
|
|
16
|
+
"../src/**/*.test.*",
|
|
17
|
+
"../src/**/test.*",
|
|
18
|
+
"../src/**/examples.*",
|
|
19
|
+
"../src/**/examples/*",
|
|
20
|
+
"../src/**/examples/**/*",
|
|
21
|
+
"../src/**/*.stories.*",
|
|
22
|
+
"../src/**/stories/*",
|
|
23
|
+
"../src/**/stories/**/*"
|
|
24
|
+
],
|
|
25
|
+
"references": []
|
|
26
|
+
}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
{
|
|
2
|
+
"extends": "../../../../tsconfig.entry-points.townsquare.json",
|
|
3
|
+
"compilerOptions": {
|
|
4
|
+
"declaration": true,
|
|
5
|
+
"target": "es5",
|
|
6
|
+
"outDir": "../../../../../townsquare/tsDist/@atlaskit__prosemirror-input-rules/app",
|
|
7
|
+
"rootDir": "../",
|
|
8
|
+
"composite": true
|
|
9
|
+
},
|
|
10
|
+
"include": [
|
|
11
|
+
"../src/**/*.ts",
|
|
12
|
+
"../src/**/*.tsx"
|
|
13
|
+
],
|
|
14
|
+
"exclude": [
|
|
15
|
+
"../src/**/__tests__/*",
|
|
16
|
+
"../src/**/*.test.*",
|
|
17
|
+
"../src/**/test.*",
|
|
18
|
+
"../src/**/examples.*",
|
|
19
|
+
"../src/**/examples/*",
|
|
20
|
+
"../src/**/examples/**/*",
|
|
21
|
+
"../src/**/*.stories.*",
|
|
22
|
+
"../src/**/stories/*",
|
|
23
|
+
"../src/**/stories/**/*"
|
|
24
|
+
],
|
|
25
|
+
"references": []
|
|
26
|
+
}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
{
|
|
2
|
+
"extends": "../../../../tsconfig.entry-points.volt.json",
|
|
3
|
+
"compilerOptions": {
|
|
4
|
+
"declaration": true,
|
|
5
|
+
"target": "es5",
|
|
6
|
+
"outDir": "../../../../../volt/tsDist/@atlaskit__prosemirror-input-rules/app",
|
|
7
|
+
"rootDir": "../",
|
|
8
|
+
"composite": true
|
|
9
|
+
},
|
|
10
|
+
"include": [
|
|
11
|
+
"../src/**/*.ts",
|
|
12
|
+
"../src/**/*.tsx"
|
|
13
|
+
],
|
|
14
|
+
"exclude": [
|
|
15
|
+
"../src/**/__tests__/*",
|
|
16
|
+
"../src/**/*.test.*",
|
|
17
|
+
"../src/**/test.*"
|
|
18
|
+
],
|
|
19
|
+
"references": []
|
|
20
|
+
}
|
package/build/tsconfig.json
CHANGED
|
@@ -12,6 +12,12 @@
|
|
|
12
12
|
"exclude": [
|
|
13
13
|
"../src/**/__tests__/*",
|
|
14
14
|
"../src/**/*.test.*",
|
|
15
|
-
"../src/**/test.*"
|
|
15
|
+
"../src/**/test.*",
|
|
16
|
+
"../src/**/examples.*",
|
|
17
|
+
"../src/**/examples/*",
|
|
18
|
+
"../src/**/examples/**/*",
|
|
19
|
+
"../src/**/*.stories.*",
|
|
20
|
+
"../src/**/stories/*",
|
|
21
|
+
"../src/**/stories/**/*"
|
|
16
22
|
]
|
|
17
|
-
}
|
|
23
|
+
}
|
package/dist/cjs/plugin.js
CHANGED
|
@@ -67,6 +67,26 @@ function createInputRulePlugin(pluginName, rules) {
|
|
|
67
67
|
});
|
|
68
68
|
},
|
|
69
69
|
handleDOMEvents: {
|
|
70
|
+
blur: function blur(view) {
|
|
71
|
+
if (!(options !== null && options !== void 0 && options.checkOnBlur)) {
|
|
72
|
+
return false;
|
|
73
|
+
}
|
|
74
|
+
var selection = view.state.selection;
|
|
75
|
+
if (!(selection instanceof _state.TextSelection)) {
|
|
76
|
+
return;
|
|
77
|
+
}
|
|
78
|
+
var $cursor = selection.$cursor;
|
|
79
|
+
if ($cursor) {
|
|
80
|
+
var _options$appendTextOn;
|
|
81
|
+
inputEvent({
|
|
82
|
+
view: view,
|
|
83
|
+
from: $cursor.pos,
|
|
84
|
+
to: $cursor.pos,
|
|
85
|
+
text: (_options$appendTextOn = options.appendTextOnBlur) !== null && _options$appendTextOn !== void 0 ? _options$appendTextOn : ''
|
|
86
|
+
});
|
|
87
|
+
}
|
|
88
|
+
return false;
|
|
89
|
+
},
|
|
70
90
|
compositionend: function compositionend(view) {
|
|
71
91
|
setTimeout(function () {
|
|
72
92
|
var selection = view.state.selection;
|
package/dist/cjs/utils.js
CHANGED
|
@@ -34,7 +34,9 @@ var createPlugin = exports.createPlugin = function createPlugin(pluginName, rule
|
|
|
34
34
|
var _options$isBlockNodeR = options.isBlockNodeRule,
|
|
35
35
|
isBlockNodeRule = _options$isBlockNodeR === void 0 ? false : _options$isBlockNodeR,
|
|
36
36
|
_options$allowInsertT = options.allowInsertTextOnDocument,
|
|
37
|
-
allowInsertTextOnDocument = _options$allowInsertT === void 0 ? true : _options$allowInsertT
|
|
37
|
+
allowInsertTextOnDocument = _options$allowInsertT === void 0 ? true : _options$allowInsertT,
|
|
38
|
+
checkOnBlur = options.checkOnBlur,
|
|
39
|
+
appendTextOnBlur = options.appendTextOnBlur;
|
|
38
40
|
var onInputEvent = function onInputEvent(_ref) {
|
|
39
41
|
var state = _ref.state,
|
|
40
42
|
from = _ref.from,
|
|
@@ -52,6 +54,8 @@ var createPlugin = exports.createPlugin = function createPlugin(pluginName, rule
|
|
|
52
54
|
onInputEvent: onInputEvent,
|
|
53
55
|
onBeforeRegexMatch: function onBeforeRegexMatch(tr) {
|
|
54
56
|
(0, _history.closeHistory)(tr);
|
|
55
|
-
}
|
|
57
|
+
},
|
|
58
|
+
checkOnBlur: checkOnBlur,
|
|
59
|
+
appendTextOnBlur: appendTextOnBlur
|
|
56
60
|
});
|
|
57
61
|
};
|
package/dist/es2019/plugin.js
CHANGED
|
@@ -62,6 +62,28 @@ export function createInputRulePlugin(pluginName, rules, options = {}) {
|
|
|
62
62
|
});
|
|
63
63
|
},
|
|
64
64
|
handleDOMEvents: {
|
|
65
|
+
blur: view => {
|
|
66
|
+
if (!(options !== null && options !== void 0 && options.checkOnBlur)) {
|
|
67
|
+
return false;
|
|
68
|
+
}
|
|
69
|
+
const selection = view.state.selection;
|
|
70
|
+
if (!(selection instanceof TextSelection)) {
|
|
71
|
+
return;
|
|
72
|
+
}
|
|
73
|
+
const {
|
|
74
|
+
$cursor
|
|
75
|
+
} = selection;
|
|
76
|
+
if ($cursor) {
|
|
77
|
+
var _options$appendTextOn;
|
|
78
|
+
inputEvent({
|
|
79
|
+
view,
|
|
80
|
+
from: $cursor.pos,
|
|
81
|
+
to: $cursor.pos,
|
|
82
|
+
text: (_options$appendTextOn = options.appendTextOnBlur) !== null && _options$appendTextOn !== void 0 ? _options$appendTextOn : ''
|
|
83
|
+
});
|
|
84
|
+
}
|
|
85
|
+
return false;
|
|
86
|
+
},
|
|
65
87
|
compositionend: view => {
|
|
66
88
|
setTimeout(() => {
|
|
67
89
|
const selection = view.state.selection;
|
package/dist/es2019/utils.js
CHANGED
|
@@ -26,7 +26,9 @@ const isCursorInsideUnsupportedMarks = (state, marksNameUnsupported) => {
|
|
|
26
26
|
export const createPlugin = (pluginName, rules, options = {}) => {
|
|
27
27
|
const {
|
|
28
28
|
isBlockNodeRule = false,
|
|
29
|
-
allowInsertTextOnDocument = true
|
|
29
|
+
allowInsertTextOnDocument = true,
|
|
30
|
+
checkOnBlur,
|
|
31
|
+
appendTextOnBlur
|
|
30
32
|
} = options;
|
|
31
33
|
const onInputEvent = ({
|
|
32
34
|
state,
|
|
@@ -46,6 +48,8 @@ export const createPlugin = (pluginName, rules, options = {}) => {
|
|
|
46
48
|
onInputEvent,
|
|
47
49
|
onBeforeRegexMatch: tr => {
|
|
48
50
|
closeHistory(tr);
|
|
49
|
-
}
|
|
51
|
+
},
|
|
52
|
+
checkOnBlur,
|
|
53
|
+
appendTextOnBlur
|
|
50
54
|
});
|
|
51
55
|
};
|
package/dist/esm/plugin.js
CHANGED
|
@@ -61,6 +61,26 @@ export function createInputRulePlugin(pluginName, rules) {
|
|
|
61
61
|
});
|
|
62
62
|
},
|
|
63
63
|
handleDOMEvents: {
|
|
64
|
+
blur: function blur(view) {
|
|
65
|
+
if (!(options !== null && options !== void 0 && options.checkOnBlur)) {
|
|
66
|
+
return false;
|
|
67
|
+
}
|
|
68
|
+
var selection = view.state.selection;
|
|
69
|
+
if (!(selection instanceof TextSelection)) {
|
|
70
|
+
return;
|
|
71
|
+
}
|
|
72
|
+
var $cursor = selection.$cursor;
|
|
73
|
+
if ($cursor) {
|
|
74
|
+
var _options$appendTextOn;
|
|
75
|
+
inputEvent({
|
|
76
|
+
view: view,
|
|
77
|
+
from: $cursor.pos,
|
|
78
|
+
to: $cursor.pos,
|
|
79
|
+
text: (_options$appendTextOn = options.appendTextOnBlur) !== null && _options$appendTextOn !== void 0 ? _options$appendTextOn : ''
|
|
80
|
+
});
|
|
81
|
+
}
|
|
82
|
+
return false;
|
|
83
|
+
},
|
|
64
84
|
compositionend: function compositionend(view) {
|
|
65
85
|
setTimeout(function () {
|
|
66
86
|
var selection = view.state.selection;
|
package/dist/esm/utils.js
CHANGED
|
@@ -28,7 +28,9 @@ export var createPlugin = function createPlugin(pluginName, rules) {
|
|
|
28
28
|
var _options$isBlockNodeR = options.isBlockNodeRule,
|
|
29
29
|
isBlockNodeRule = _options$isBlockNodeR === void 0 ? false : _options$isBlockNodeR,
|
|
30
30
|
_options$allowInsertT = options.allowInsertTextOnDocument,
|
|
31
|
-
allowInsertTextOnDocument = _options$allowInsertT === void 0 ? true : _options$allowInsertT
|
|
31
|
+
allowInsertTextOnDocument = _options$allowInsertT === void 0 ? true : _options$allowInsertT,
|
|
32
|
+
checkOnBlur = options.checkOnBlur,
|
|
33
|
+
appendTextOnBlur = options.appendTextOnBlur;
|
|
32
34
|
var onInputEvent = function onInputEvent(_ref) {
|
|
33
35
|
var state = _ref.state,
|
|
34
36
|
from = _ref.from,
|
|
@@ -46,6 +48,8 @@ export var createPlugin = function createPlugin(pluginName, rules) {
|
|
|
46
48
|
onInputEvent: onInputEvent,
|
|
47
49
|
onBeforeRegexMatch: function onBeforeRegexMatch(tr) {
|
|
48
50
|
closeHistory(tr);
|
|
49
|
-
}
|
|
51
|
+
},
|
|
52
|
+
checkOnBlur: checkOnBlur,
|
|
53
|
+
appendTextOnBlur: appendTextOnBlur
|
|
50
54
|
});
|
|
51
55
|
};
|
package/dist/types/plugin.d.ts
CHANGED
|
@@ -3,6 +3,8 @@ import type { InputRuleWrapper } from './editor-common';
|
|
|
3
3
|
import type { OnBeforeRegexMatch, OnInputEvent } from './types';
|
|
4
4
|
type Options = {
|
|
5
5
|
allowInsertTextOnDocument?: boolean;
|
|
6
|
+
checkOnBlur?: boolean;
|
|
7
|
+
appendTextOnBlur?: string;
|
|
6
8
|
onInputEvent?: OnInputEvent;
|
|
7
9
|
onBeforeRegexMatch?: OnBeforeRegexMatch;
|
|
8
10
|
};
|
package/dist/types/utils.d.ts
CHANGED
|
@@ -3,6 +3,15 @@ import type { InputRuleWrapper } from './editor-common';
|
|
|
3
3
|
type Options = {
|
|
4
4
|
isBlockNodeRule?: boolean;
|
|
5
5
|
allowInsertTextOnDocument?: boolean;
|
|
6
|
+
/**
|
|
7
|
+
* Run checks on blur of the editor as well as during input
|
|
8
|
+
*/
|
|
9
|
+
checkOnBlur?: boolean;
|
|
10
|
+
/**
|
|
11
|
+
* Append text to the checked text on blur. Useful for checks that normally require a trailing
|
|
12
|
+
* space or similar
|
|
13
|
+
*/
|
|
14
|
+
appendTextOnBlur?: string;
|
|
6
15
|
};
|
|
7
16
|
export declare const createPlugin: (pluginName: string, rules: Array<InputRuleWrapper>, options?: Options) => SafePluginSpec;
|
|
8
17
|
export {};
|
|
@@ -3,6 +3,8 @@ import type { InputRuleWrapper } from './editor-common';
|
|
|
3
3
|
import type { OnBeforeRegexMatch, OnInputEvent } from './types';
|
|
4
4
|
type Options = {
|
|
5
5
|
allowInsertTextOnDocument?: boolean;
|
|
6
|
+
checkOnBlur?: boolean;
|
|
7
|
+
appendTextOnBlur?: string;
|
|
6
8
|
onInputEvent?: OnInputEvent;
|
|
7
9
|
onBeforeRegexMatch?: OnBeforeRegexMatch;
|
|
8
10
|
};
|
|
@@ -3,6 +3,15 @@ import type { InputRuleWrapper } from './editor-common';
|
|
|
3
3
|
type Options = {
|
|
4
4
|
isBlockNodeRule?: boolean;
|
|
5
5
|
allowInsertTextOnDocument?: boolean;
|
|
6
|
+
/**
|
|
7
|
+
* Run checks on blur of the editor as well as during input
|
|
8
|
+
*/
|
|
9
|
+
checkOnBlur?: boolean;
|
|
10
|
+
/**
|
|
11
|
+
* Append text to the checked text on blur. Useful for checks that normally require a trailing
|
|
12
|
+
* space or similar
|
|
13
|
+
*/
|
|
14
|
+
appendTextOnBlur?: string;
|
|
6
15
|
};
|
|
7
16
|
export declare const createPlugin: (pluginName: string, rules: Array<InputRuleWrapper>, options?: Options) => SafePluginSpec;
|
|
8
17
|
export {};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@atlaskit/prosemirror-input-rules",
|
|
3
|
-
"version": "3.
|
|
3
|
+
"version": "3.4.0",
|
|
4
4
|
"description": "A package that contains helpers to create autoformatting rules for ProseMirror",
|
|
5
5
|
"publishConfig": {
|
|
6
6
|
"registry": "https://registry.npmjs.org/"
|
|
@@ -31,7 +31,7 @@
|
|
|
31
31
|
"@babel/runtime": "^7.0.0"
|
|
32
32
|
},
|
|
33
33
|
"devDependencies": {
|
|
34
|
-
"@atlaskit/editor-common": "^
|
|
34
|
+
"@atlaskit/editor-common": "^107.17.0"
|
|
35
35
|
},
|
|
36
36
|
"techstack": {
|
|
37
37
|
"@atlassian/frontend": {
|
|
@@ -168,4 +168,44 @@ describe('input-tule/plugin/createInputRulePlugin', () => {
|
|
|
168
168
|
});
|
|
169
169
|
});
|
|
170
170
|
});
|
|
171
|
+
|
|
172
|
+
describe('on blur behaviour', () => {
|
|
173
|
+
let handlerMock: jest.Mock;
|
|
174
|
+
let editorView: EditorView;
|
|
175
|
+
|
|
176
|
+
beforeEach(() => {
|
|
177
|
+
handlerMock = jest.fn().mockImplementation((state: EditorState) => {
|
|
178
|
+
return state.tr;
|
|
179
|
+
});
|
|
180
|
+
|
|
181
|
+
const NAIVE_URL_WITH_SPACE_REGEX = /(\S*)(https?:\/\/[^\s]+\.[^\s]+)\s/u;
|
|
182
|
+
|
|
183
|
+
const myCustomInputRule = new SafePlugin(
|
|
184
|
+
createInputRulePlugin(
|
|
185
|
+
'lol',
|
|
186
|
+
[
|
|
187
|
+
{
|
|
188
|
+
match: NAIVE_URL_WITH_SPACE_REGEX,
|
|
189
|
+
handler: handlerMock,
|
|
190
|
+
},
|
|
191
|
+
],
|
|
192
|
+
{
|
|
193
|
+
checkOnBlur: true,
|
|
194
|
+
appendTextOnBlur: ' ',
|
|
195
|
+
},
|
|
196
|
+
),
|
|
197
|
+
);
|
|
198
|
+
|
|
199
|
+
editorView = createEditorView(doc(p('http://atlassian.net{<>}')), myCustomInputRule);
|
|
200
|
+
});
|
|
201
|
+
|
|
202
|
+
it('should call the handler on blur with appended text', () => {
|
|
203
|
+
jest.spyOn(editorView, 'dispatch').mockImplementation((tr) => {});
|
|
204
|
+
editorView.dom.dispatchEvent(new FocusEvent('blur'));
|
|
205
|
+
|
|
206
|
+
expect(handlerMock).toHaveBeenCalledTimes(1);
|
|
207
|
+
const [, match] = handlerMock.mock.calls[0];
|
|
208
|
+
expect(match[0]).toEqual('http://atlassian.net ');
|
|
209
|
+
});
|
|
210
|
+
});
|
|
171
211
|
});
|
package/src/plugin.ts
CHANGED
|
@@ -8,6 +8,8 @@ import type { InputRulePluginState, OnBeforeRegexMatch, OnInputEvent } from './t
|
|
|
8
8
|
|
|
9
9
|
type Options = {
|
|
10
10
|
allowInsertTextOnDocument?: boolean;
|
|
11
|
+
checkOnBlur?: boolean;
|
|
12
|
+
appendTextOnBlur?: string;
|
|
11
13
|
onInputEvent?: OnInputEvent;
|
|
12
14
|
onBeforeRegexMatch?: OnBeforeRegexMatch;
|
|
13
15
|
};
|
|
@@ -86,6 +88,26 @@ export function createInputRulePlugin(
|
|
|
86
88
|
});
|
|
87
89
|
},
|
|
88
90
|
handleDOMEvents: {
|
|
91
|
+
blur: (view) => {
|
|
92
|
+
if (!options?.checkOnBlur) {
|
|
93
|
+
return false;
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
const selection = view.state.selection;
|
|
97
|
+
if (!(selection instanceof TextSelection)) {
|
|
98
|
+
return;
|
|
99
|
+
}
|
|
100
|
+
const { $cursor } = selection;
|
|
101
|
+
if ($cursor) {
|
|
102
|
+
inputEvent({
|
|
103
|
+
view,
|
|
104
|
+
from: $cursor.pos,
|
|
105
|
+
to: $cursor.pos,
|
|
106
|
+
text: options.appendTextOnBlur ?? '',
|
|
107
|
+
});
|
|
108
|
+
}
|
|
109
|
+
return false;
|
|
110
|
+
},
|
|
89
111
|
compositionend: (view) => {
|
|
90
112
|
setTimeout(() => {
|
|
91
113
|
const selection = view.state.selection;
|
package/src/utils.ts
CHANGED
|
@@ -40,13 +40,27 @@ const isCursorInsideUnsupportedMarks = (
|
|
|
40
40
|
type Options = {
|
|
41
41
|
isBlockNodeRule?: boolean;
|
|
42
42
|
allowInsertTextOnDocument?: boolean;
|
|
43
|
+
/**
|
|
44
|
+
* Run checks on blur of the editor as well as during input
|
|
45
|
+
*/
|
|
46
|
+
checkOnBlur?: boolean;
|
|
47
|
+
/**
|
|
48
|
+
* Append text to the checked text on blur. Useful for checks that normally require a trailing
|
|
49
|
+
* space or similar
|
|
50
|
+
*/
|
|
51
|
+
appendTextOnBlur?: string;
|
|
43
52
|
};
|
|
44
53
|
export const createPlugin = (
|
|
45
54
|
pluginName: string,
|
|
46
55
|
rules: Array<InputRuleWrapper>,
|
|
47
56
|
options: Options = {},
|
|
48
57
|
): SafePluginSpec => {
|
|
49
|
-
const {
|
|
58
|
+
const {
|
|
59
|
+
isBlockNodeRule = false,
|
|
60
|
+
allowInsertTextOnDocument = true,
|
|
61
|
+
checkOnBlur,
|
|
62
|
+
appendTextOnBlur,
|
|
63
|
+
} = options;
|
|
50
64
|
|
|
51
65
|
const onInputEvent: OnInputEvent = ({ state, from, to }) => {
|
|
52
66
|
const unsupportedMarks = isBlockNodeRule ? ['code', 'link', 'typeAheadQuery'] : ['code'];
|
|
@@ -74,5 +88,7 @@ export const createPlugin = (
|
|
|
74
88
|
onBeforeRegexMatch: (tr) => {
|
|
75
89
|
closeHistory(tr);
|
|
76
90
|
},
|
|
91
|
+
checkOnBlur,
|
|
92
|
+
appendTextOnBlur,
|
|
77
93
|
});
|
|
78
94
|
};
|
package/tsconfig.dev.json
CHANGED
|
@@ -23,7 +23,13 @@
|
|
|
23
23
|
"./__mocks__/**/*",
|
|
24
24
|
"**/mock.*",
|
|
25
25
|
"**/codemods/**/*.ts",
|
|
26
|
-
"**/codemods/**/*.tsx"
|
|
26
|
+
"**/codemods/**/*.tsx",
|
|
27
|
+
"**/stories.ts",
|
|
28
|
+
"**/stories.tsx",
|
|
29
|
+
"**/stories/*.ts",
|
|
30
|
+
"**/stories/*.tsx",
|
|
31
|
+
"**/stories/**/*.ts",
|
|
32
|
+
"**/stories/**/*.tsx"
|
|
27
33
|
],
|
|
28
34
|
"exclude": ["./dist/**/*", "./build/**/*", "./node_modules/**/*"],
|
|
29
35
|
"compilerOptions": {
|