4 <script src=
"../../resources/js-test.js"></script>
5 <script src=
"../editing.js"></script>
6 <script src=
"resources/util.js"></script>
16 <pre id=
"description"></pre>
17 <pre id=
"console"></pre>
19 <div id=
"source">zz zz zz
</textarea>
21 <div id=
"container"></div>
23 <div id=
"move-target"></div>
27 "Test for asynchronous spellchecking in case DOM mutation happens. " +
28 "This test checks crash won't happen if DOM mutations happened."
31 var jsTestIsAsync
= true;
33 if (window
.internals
) {
34 internals
.settings
.setAsynchronousSpellCheckingEnabled(true);
35 internals
.settings
.setUnifiedTextCheckerEnabled(true);
38 var sourceIds
= ['source'];
39 var destElems
= ['textarea', 'input', 'contenteditable'];
40 var tweaks
= ['delete', 'move', 'mutate'];
43 for (var i
= 0; i
< sourceIds
.length
; ++i
) {
44 for (var j
= 0; j
< destElems
.length
; ++j
) {
45 for (var k
= 0; k
< tweaks
.length
; ++k
) {
47 sourceId
: sourceIds
[i
],
48 destElem
: destElems
[j
],
55 var sel
= window
.getSelection();
57 function removeAllChildren(elem
) {
58 while (elem
.firstChild
)
59 elem
.removeChild(elem
.firstChild
);
63 function doTestIfAny() {
65 removeAllChildren(document
.getElementById('container'));
66 removeAllChildren(document
.getElementById('move-target'));
68 var next
= testData
.shift();
70 return window
.setTimeout(function(){ doTest(++testNo
, next
); }, 0);
72 // No more tests. Tear down.
73 removeAllChildren(document
.getElementById('container'));
74 removeAllChildren(document
.getElementById('move-target'));
76 if (window
.testRunner
)
82 function doTest(testNo
, testData
) {
83 function createElement(kind
) {
84 if (kind
== 'textarea' || kind
== 'input')
85 return document
.createElement(kind
);
87 var div
= document
.createElement('div');
88 div
.setAttribute('contenteditable', true);
93 debug("Test Start: " + testNo
);
95 var source
= document
.getElementById(testData
.sourceId
);
96 var destination
= createElement(testData
.destElem
);
97 document
.getElementById('container').appendChild(destination
);
100 lastRequestId
= internals
.lastSpellCheckRequestSequence(document
);
102 // A spellcheck request will be invoked.
103 doCopyAndPaste(source
, destination
);
105 setTimeout(function() {
106 if (window
.internals
)
107 requestId
= internals
.lastSpellCheckRequestSequence(document
);
108 shouldBeGreaterThanOrEqual('requestId', 'lastRequestId + 1');
111 tweak(destination
, testData
.tweak
);
113 waitForSpellCheckRequestDone(requestId
, destination
, testData
.tweak
, 10, 1);
117 function doCopyAndPaste(source
, dest
) {
118 function focusOn(elem
) {
119 if (elem
instanceof HTMLInputElement
|| elem
instanceof HTMLTextAreaElement
)
122 sel
.selectAllChildren(elem
);
125 sel
.selectAllChildren(source
);
126 document
.execCommand("Copy");
129 document
.execCommand("Paste");
132 function tweak(elem
, kind
) {
135 elem
.parentNode
.removeChild(elem
);
138 var target
= document
.getElementById('move-target');
139 target
.appendChild(elem
);
142 if (elem
instanceof HTMLInputElement
|| elem
instanceof HTMLTextAreaElement
)
145 elem
.innerHTML
= 'zzz';
148 testFailed('Unknown kind of tweak');
153 function waitForSpellCheckRequestDone(requestId
, destination
, tweakKind
, restTry
, nsleep
) {
156 testFailed('Failed verification');
157 setTimeout(doTestIfAny
, 0);
161 if (window
.internals
)
162 var lastProcessedId
= internals
.lastSpellCheckProcessedSequence(document
);
164 if (requestId
!= lastProcessedId
) {
165 setTimeout(function() {
166 waitForSpellCheckRequestDone(requestId
, destination
, tweakKind
, restTry
- 1, nsleep
* 2);
171 if (verifyExistenceOfMarkers(destination
, tweakKind
)) {
172 testPassed('Request has been processed.');
174 testFailed('Request has been processed but we detected unexpected marker location.');
177 setTimeout(doTestIfAny
, 0);
180 function verifyExistenceOfMarkers(elem
, tweakKind
) {
181 if (!window
.internals
)
188 // In move, marker should be there. However since markers are removed when unfocusing
189 // an input if it's the input what's moved and it's not focused return true right away.
190 if (elem
instanceof HTMLInputElement
&& elem
!= document
.activeElement
)
192 var markerNum
= internals
.markerCountForNode(findFirstTextNode(elem
), "spelling");
195 for (var i
= 0; i
< 3; ++i
) {
196 var range
= internals
.markerRangeForNode(findFirstTextNode(elem
), "spelling", i
);
197 if (range
.toString() != "zz")
202 // In mutation, there aren't markers.
203 return internals
.markerCountForNode(findFirstTextNode(elem
), "spelling") == 0;
205 testFailed('Unknown kind of tweak');
212 var successfullyParsed
= true;