526 lines
25 KiB
HTML
526 lines
25 KiB
HTML
<!doctype html>
|
|
<meta charset=utf-8>
|
|
<title>Test that execCommand without editable element</title>
|
|
<script src=../include/implementation.js></script>
|
|
<script>var testsJsLibraryOnly = true</script>
|
|
<script src=../include/tests.js></script>
|
|
<script src=/resources/testharness.js></script>
|
|
<script src=/resources/testharnessreport.js></script>
|
|
<script>
|
|
"use strict";
|
|
|
|
setup({explicit_done: true});
|
|
|
|
// This test calls execCommand() without editable element in the document,
|
|
// but its parent or child document has editable element and it has focus.
|
|
// In most cases, execCommand() should do nothing and return false. However,
|
|
// "cut", "copy", "paste" and "selectall" commands should work without DOM tree
|
|
// modification for making web apps can implement their own editor without
|
|
// editable element.
|
|
async function runTests() {
|
|
let parentWindow = window;
|
|
let parentDocument = document;
|
|
let parentSelection = parentDocument.getSelection();
|
|
let parentEditor = parentDocument.getElementById("editor");
|
|
parentEditor.focus();
|
|
let iframe = document.getElementsByTagName("iframe")[0];
|
|
let childWindow = iframe.contentWindow;
|
|
let childDocument = iframe.contentDocument;
|
|
let childSelection = childDocument.getSelection();
|
|
let childEditor = childDocument.getElementById("editor");
|
|
childEditor.focus();
|
|
|
|
// execCommand() in child document shouldn't affect to focused parent
|
|
// document.
|
|
await doTest(parentWindow, parentDocument, parentSelection, parentEditor,
|
|
childWindow, childDocument, childSelection, childEditor, false);
|
|
// execCommand() in parent document shouldn't affect to focused child
|
|
// document but "cut" and "copy" may affect the focused child document.
|
|
await doTest(childWindow, childDocument, childSelection, childEditor,
|
|
parentWindow, parentDocument, parentSelection, parentEditor, true);
|
|
|
|
done();
|
|
}
|
|
|
|
async function doTest(aFocusWindow, aFocusDocument, aFocusSelection, aFocusEditor,
|
|
aExecWindow, aExecDocument, aExecSelection, aExecEditor,
|
|
aExecInParent) {
|
|
const kTests = [
|
|
/**
|
|
* command: The command which you test.
|
|
* focusContent: Will be set to innerHTML of div#editor element in focused
|
|
* document.
|
|
* execContent: Will be set to innerHTML of div#editor element in the
|
|
* document whose execCommand() will be called.
|
|
* initFunc: [optional] If you need to do something before running the
|
|
* test, you can do it with a function.
|
|
* expectedFocusContent: Expected content and selection in div#editor in
|
|
* focused document after calling execCommand().
|
|
* expectedExecContent: Expected content and selection in div#editor in
|
|
* the document whose execCommand() is called.
|
|
* event: The event which you need to check whether it's fired or not.
|
|
* expectedFiredInFocus: true if the event should be fired on the focused
|
|
* document node.
|
|
* expectedFiredInExec: true if the event should be fired on the document
|
|
* node whose execCommand() is called.
|
|
* expectedResult: Expected result of execCommand().
|
|
*/
|
|
{command: "bold", value: "bold",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "italic", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "underline", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "strikethrough", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "subscript", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "superscript", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
// "cut", "copy" and "paste" command should cause firing corresponding
|
|
// events to make web apps be able to implement their own editor even
|
|
// if there is no editor and selection is collapsed.
|
|
{command: "cut", value: null,
|
|
focusContent: "a[b]c", execContent: "ab[]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "ab[]c",
|
|
event: "cut", expectedFiredInFocus: false, expectedFiredInExec: true,
|
|
expectedResult: false,
|
|
},
|
|
{command: "cut", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "cut", expectedFiredInFocus: false, expectedFiredInExec: true,
|
|
expectedResult: false,
|
|
},
|
|
{command: "copy", value: null,
|
|
focusContent: "a[b]c", execContent: "ab[]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "ab[]c",
|
|
event: "copy", expectedFiredInFocus: false, expectedFiredInExec: true,
|
|
expectedResult: false,
|
|
},
|
|
{command: "copy", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "copy", expectedFiredInFocus: false, expectedFiredInExec: true,
|
|
expectedResult: false,
|
|
},
|
|
{command: "paste", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
initFunc: () => { aFocusDocument.execCommand("copy", false, "b"); },
|
|
event: "paste", expectedFiredInFocus: false, expectedFiredInExec: true,
|
|
expectedResult: false,
|
|
},
|
|
{command: "delete", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "forwarddelete", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
// "selectall" command should be available without editable content.
|
|
{command: "selectall", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: undefined,
|
|
event: "selectionchange", expectedFiredInFocus: false, expectedFiredInExec: true,
|
|
expectedResult: true,
|
|
},
|
|
{command: "undo", value: null,
|
|
focusContent: "a[]c", execContent: "a[b]c",
|
|
initFunc: () => { aFocusDocument.execCommand("insertText", false, "b"); },
|
|
expectedFocusContent: "ab[]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "redo", value: null,
|
|
focusContent: "a[]c", execContent: "a[b]c",
|
|
initFunc: () => {
|
|
aFocusDocument.execCommand("insertText", false, "b");
|
|
aFocusDocument.execCommand("undo", false, null);
|
|
},
|
|
expectedFocusContent: "a[]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "indent", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "outdent", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "backcolor", value: "#000000",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "forecolor", value: "#F0F0F0",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "hilitecolor", value: "#FFFF00",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "fontname", value: "DummyFont",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "fontsize", value: "5",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "increasefontsize", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "decreasefontsize", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "inserthorizontalrule", value: null,
|
|
focusContent: "a[]bc", execContent: "a[]bc",
|
|
expectedFocusContent: "a[]bc", expectedExecContent: "a[]bc",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "createlink", value: "foo.html",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "insertimage", value: "no-image.png",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "inserthtml", value: "<b>inserted</b>",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "inserttext", value: "**inserted**",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "justifyleft", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "justifyright", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "justifycenter", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "justifyfull", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "removeformat", value: null,
|
|
focusContent: "<b>a[b]c</b>", execContent: "<b>a[b]c</b>",
|
|
expectedFocusContent: "<b>a[b]c</b>", expectedExecContent: "<b>a[b]c</b>",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "unlink", value: null,
|
|
focusContent: "<a href=\"foo.html\">a[b]c</a>", execContent: "<a href=\"foo.html\">a[b]c</a>",
|
|
expectedFocusContent: "<a href=\"foo.html\">a[b]c</a>", expectedExecContent: "<a href=\"foo.html\">a[b]c</a>",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "insertorderedlist", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "insertunorderedlist", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "insertparagraph", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "insertlinebreak", value: null,
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "formatblock", value: "div",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "heading", value: "h1",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedFocusContent: "a[b]c", expectedExecContent: "a[b]c",
|
|
event: "input", expectedFiredInFocus: false, expectedFiredInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
/**
|
|
* command: The command which you test.
|
|
* state: The state which is used with execCommand().
|
|
* initState: The state which should be set with execCommand() first.
|
|
* focusContent: Will be set to innerHTML of div#editor element in focused
|
|
* document.
|
|
* execContent: Will be set to innerHTML of div#editor element in the
|
|
* document whose execCommand() will be called.
|
|
* initFunc: [optional] If you need to do something before running the
|
|
* test, you can do it with a function.
|
|
* expectedSetStateInFocus: Expected queryCommandState() result in focused
|
|
* document.
|
|
* expectedSetStateInExec: Expected queryCommandState() result in document
|
|
* whose execCommand() is called.
|
|
* expectedResult: Expected result of execCommand().
|
|
*/
|
|
{command: "styleWithCSS", state: "true", initState: "false",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedSetStateInFocus: false, expectedSetStateInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "contentReadOnly", state: "true", initState: "false",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedSetStateInFocus: false, expectedSetStateInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "insertBrOnReturn", state: "true", initState: "false",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedSetStateInFocus: false, expectedSetStateInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "defaultParagraphSeparator", state: "div", initState: "p",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedSetStateInFocus: false, expectedSetStateInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "defaultParagraphSeparator", state: "p", initState: "div",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedSetStateInFocus: false, expectedSetStateInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "enableObjectResizing", state: "true", initState: "false",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedSetStateInFocus: false, expectedSetStateInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "enableInlineTableEditing", state: "true", initState: "false",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedSetStateInFocus: false, expectedSetStateInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
{command: "enableAbsolutePositionEditing", state: "true", initState: "false",
|
|
focusContent: "a[b]c", execContent: "a[b]c",
|
|
expectedSetStateInFocus: false, expectedSetStateInExec: false,
|
|
expectedResult: false,
|
|
},
|
|
];
|
|
|
|
async function waitForCondition(aCheckFunc) {
|
|
let retry = 60;
|
|
while (retry--) {
|
|
if (aCheckFunc()) {
|
|
return;
|
|
}
|
|
await new Promise(resolve => requestAnimationFrame(resolve));
|
|
}
|
|
}
|
|
|
|
for (const kTest of kTests) {
|
|
// Skip unsupported command since it's not purpose of this tests whether
|
|
// each command is supported on the browser.
|
|
if (!aExecDocument.queryCommandSupported(kTest.command)) {
|
|
continue;
|
|
}
|
|
aExecEditor.removeAttribute("contenteditable"); // Disable commands in the exec document.
|
|
let points = setupDiv(aFocusEditor, kTest.focusContent);
|
|
aFocusSelection.setBaseAndExtent(points[0], points[1], points[2], points[3]);
|
|
points = setupDiv(aExecEditor, kTest.execContent);
|
|
aExecSelection.setBaseAndExtent(points[0], points[1], points[2], points[3]);
|
|
aFocusWindow.focus();
|
|
aFocusEditor.focus();
|
|
if (kTest.initFunc) {
|
|
kTest.initFunc();
|
|
}
|
|
if (kTest.state === undefined) {
|
|
let eventFiredOnFocusDocument = false;
|
|
function handlerOnFocusDocument() {
|
|
eventFiredOnFocusDocument = true;
|
|
}
|
|
aFocusDocument.addEventListener(kTest.event, handlerOnFocusDocument, {capture: true});
|
|
let eventFiredOnExecDocument = false;
|
|
function handlerOnExecDocument() {
|
|
eventFiredOnExecDocument = true;
|
|
}
|
|
aExecDocument.addEventListener(kTest.event, handlerOnExecDocument, {capture: true});
|
|
const kDescription = `${aExecInParent ? "Parent" : "Child"}Document.execCommand(${kTest.command}, false, ${kTest.value}) with ${kTest.execContent}`;
|
|
test(function () {
|
|
let ret = aExecDocument.execCommand(kTest.command, false, kTest.value);
|
|
assert_equals(ret, kTest.expectedResult, `execCommand should return ${kTest.expectedResult}`);
|
|
}, `${kDescription}: calling execCommand`);
|
|
if (kTest.event === "selectionchange") {
|
|
test(function () {
|
|
assert_false(eventFiredOnFocusDocument,
|
|
`"${kTest.event}" event should not be fired synchronously on focused document`);
|
|
assert_false(eventFiredOnExecDocument,
|
|
`"${kTest.event}" event should not be fired synchronously on executed document`);
|
|
}, `${kDescription}: checking unexpected synchronous event`);
|
|
await waitForCondition(() => eventFiredOnFocusDocument && eventFiredOnExecDocument);
|
|
// TODO: Whether select all changes selection in the focused document depends on the
|
|
// implementation of "Select All".
|
|
} else {
|
|
test(function () {
|
|
assert_equals(eventFiredOnFocusDocument, kTest.expectedFiredInFocus,
|
|
`"${kTest.event}" event should${kTest.expectedFiredInFocus ? "" : " not"} be fired`);
|
|
}, `${kDescription}: checking event on focused document`);
|
|
}
|
|
test(function () {
|
|
assert_equals(eventFiredOnExecDocument, kTest.expectedFiredInExec,
|
|
`"${kTest.event}" event should${kTest.expectedFiredInExec ? "" : " not"} be fired`);
|
|
}, `${kDescription}: checking event on executed document`);
|
|
test(function () {
|
|
if (aFocusSelection.rangeCount) {
|
|
addBrackets(aFocusSelection.getRangeAt(0));
|
|
}
|
|
assert_equals(aFocusEditor.innerHTML, kTest.expectedFocusContent);
|
|
}, `${kDescription}: checking result content in focused document`);
|
|
test(function () {
|
|
if (kTest.command === "selectall") {
|
|
assert_true(aExecSelection.rangeCount > 0);
|
|
assert_equals(
|
|
aExecSelection.toString().replace(/[\r\n]/g, ""),
|
|
aExecDocument.body.textContent.replace(/[\r\n]/g, "")
|
|
);
|
|
} else {
|
|
if (aExecSelection.rangeCount) {
|
|
addBrackets(aExecSelection.getRangeAt(0));
|
|
}
|
|
assert_equals(aExecEditor.innerHTML, kTest.expectedExecContent);
|
|
}
|
|
}, `${kDescription}: checking result content in executed document`);
|
|
aFocusDocument.removeEventListener(kTest.event, handlerOnFocusDocument, {capture: true});
|
|
aExecDocument.removeEventListener(kTest.event, handlerOnExecDocument, {capture: true});
|
|
aExecEditor.setAttribute("contenteditable", "");
|
|
} else {
|
|
const kDescription = `${aExecInParent ? "Parent" : "Child"}Document.execCommand(${kTest.command}, false, ${kTest.state})`;
|
|
test(function () {
|
|
let ret = aExecDocument.execCommand(kTest.command, false, kTest.initState);
|
|
assert_equals(ret, kTest.expectedResult, `execCommand should return ${kTest.expectedResult}`);
|
|
}, `${kDescription}: calling execCommand to initialize`);
|
|
let hasSetState = false;
|
|
test(function () {
|
|
hasSetState = aExecDocument.queryCommandState(kTest.command);
|
|
assert_equals(hasSetState, kTest.expectedSetStateInExec, `queryCommandState on executed document should return ${kTest.expectedSetState}`);
|
|
}, `${kDescription}: calling queryCommandState on executed document after initializing`);
|
|
test(function () {
|
|
let ret = aFocusDocument.queryCommandState(kTest.command);
|
|
assert_equals(ret, kTest.expectedSetStateInFocus, `queryCommandState on focus document should return ${kTest.expectedSetState}`);
|
|
}, `${kDescription}: calling queryCommandState on focus document after initializing`);
|
|
if (hasSetState) {
|
|
test(function () {
|
|
let ret = aExecDocument.queryCommandValue(kTest.command);
|
|
assert_equals(ret, kTest.initState, `queryCommandValue on executed document should return ${kTest.initState}`);
|
|
}, `${kDescription}: calling queryCommandValue on executed document after initializing`);
|
|
}
|
|
test(function () {
|
|
let ret = aExecDocument.execCommand(kTest.command, false, kTest.state);
|
|
assert_equals(ret, kTest.expectedResult, `execCommand should return ${kTest.expectedResult}`);
|
|
}, `${kDescription}: calling execCommand to set state`);
|
|
test(function () {
|
|
hasSetState = aExecDocument.queryCommandState(kTest.command);
|
|
assert_equals(hasSetState, kTest.expectedSetStateInExec, `queryCommandState should return ${kTest.expectedSetState}`);
|
|
}, `${kDescription}: calling queryCommandState on executed document`);
|
|
test(function () {
|
|
let ret = aFocusDocument.queryCommandState(kTest.command);
|
|
assert_equals(ret, kTest.expectedSetStateInFocus, `queryCommandState should return ${kTest.expectedSetState}`);
|
|
}, `${kDescription}: calling queryCommandState on focused document`);
|
|
if (hasSetState) {
|
|
test(function () {
|
|
let ret = aExecDocument.queryCommandValue(kTest.command);
|
|
assert_equals(ret, kTest.state, `queryCommandValue should return ${kTest.initState}`);
|
|
}, `${kDescription}: calling queryCommandValue on executed document`);
|
|
}
|
|
aExecEditor.setAttribute("contenteditable", "");
|
|
test(function () {
|
|
let ret = aExecDocument.queryCommandState(kTest.command);
|
|
assert_equals(ret, kTest.expectedSetStateInExec, `queryCommandState should return ${kTest.expectedSetState}`);
|
|
}, `${kDescription}: calling queryCommandState on executed document after making executed document editable`);
|
|
}
|
|
}
|
|
}
|
|
|
|
window.addEventListener("load", runTests, {once: true});
|
|
</script>
|
|
<body>
|
|
<div contenteditable id="editor">abc</div>
|
|
<iframe srcdoc="<div contenteditable id='editor'>def</div><span>ghi</span>"></iframe>
|
|
</body>
|