| Index: third_party/WebKit/LayoutTests/fast/canvas/canvas-createImageBitmap-drawImage-flipY.html
|
| diff --git a/third_party/WebKit/LayoutTests/fast/canvas/canvas-createImageBitmap-drawImage-flipY.html b/third_party/WebKit/LayoutTests/fast/canvas/canvas-createImageBitmap-drawImage-flipY.html
|
| new file mode 100644
|
| index 0000000000000000000000000000000000000000..de9d21c32223cb41cbe8c255e08034f2be62936c
|
| --- /dev/null
|
| +++ b/third_party/WebKit/LayoutTests/fast/canvas/canvas-createImageBitmap-drawImage-flipY.html
|
| @@ -0,0 +1,553 @@
|
| +<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML//EN">
|
| +<html>
|
| +<head>
|
| +<script src="../../resources/js-test.js"></script>
|
| +</head>
|
| +<body>
|
| +<script>
|
| +
|
| +description("Ensure correct behavior of drawImage with ImageBitmaps along with flipY option.");
|
| +window.jsTestIsAsync = true;
|
| +
|
| +function jsWrapperClass(node)
|
| +{
|
| + // returns the ClassName of node
|
| + if (!node)
|
| + return "[null]";
|
| + var string = Object.prototype.toString.apply(node);
|
| +
|
| + // string will be of the form [object ClassName]
|
| + return string.substr(8, string.length - 9);
|
| +}
|
| +
|
| +function shouldBeType(expression, className)
|
| +{
|
| + shouldBe("jsWrapperClass(" + expression + ")", "'" + className + "'");
|
| +}
|
| +
|
| +function shouldNotBeCalled() {
|
| + testFailed("createImageBitmap promise rejected.");
|
| + finishJSTest();
|
| +}
|
| +
|
| +function shouldBeRed(x, y) {
|
| + d = ctx.getImageData(x, y, 1, 1).data;
|
| + if (d[0] == 255 && d[1] == 0 && d[2] == 0 && d[3] == 255) {
|
| + testPassed("This pixel is red.");
|
| + return;
|
| + }
|
| + testFailed("This pixel is expected to be red, but it is actually " + d);
|
| +}
|
| +
|
| +function shouldBeGreen(x, y) {
|
| + d = ctx.getImageData(x, y, 1, 1).data;
|
| + if (d[0] == 0 && d[1] == 255 && d[2] == 0 && d[3] == 255) {
|
| + testPassed("This pixel is green.");
|
| + return;
|
| + }
|
| + testFailed("This pixel is expected to be green, but it is actually " + d);
|
| +}
|
| +
|
| +function shouldBeBlue(x, y) {
|
| + d = ctx.getImageData(x, y, 1, 1).data;
|
| + if (d[0] == 0 && d[1] == 0 && d[2] == 255 && d[3] == 255) {
|
| + testPassed("This pixel is blue.");
|
| + return;
|
| + }
|
| + testFailed("This pixel is expected to be blue, but it is actually " + d);
|
| +}
|
| +
|
| +function shouldBeBlack(x, y) {
|
| + d = ctx.getImageData(x, y, 1, 1).data;
|
| + if (d[0] == 0 && d[1] == 0 && d[2] == 0 && d[3] == 255) {
|
| + testPassed("This pixel is black.");
|
| + return;
|
| + }
|
| + testFailed("This pixel is expected to be black, but it is actually " + d);
|
| +}
|
| +
|
| +function shouldBeClear(x, y) {
|
| + // should be transparent black pixels
|
| + d = ctx.getImageData(x, y, 1, 1).data;
|
| + if (d[0] == 0 && d[1] == 0 && d[2] == 0 && d[3] == 0) {
|
| + testPassed("This pixel is transparent black.");
|
| + return;
|
| + }
|
| + testFailed("This pixel is expected to be transparent black, but it is actually " + d);
|
| +}
|
| +
|
| +function drawPattern(ctx) {
|
| + // Draw a four-color pattern
|
| + ctx.beginPath();
|
| + ctx.fillStyle = "rgb(255, 0, 0)";
|
| + ctx.fillRect(0, 0, 10, 10);
|
| + ctx.fillStyle = "rgb(0, 255, 0)";
|
| + ctx.fillRect(10, 0, 10, 10);
|
| + ctx.fillStyle = "rgb(0, 0, 255)";
|
| + ctx.fillRect(0, 10, 10, 10);
|
| + ctx.fillStyle = "rgb(0, 0, 0)";
|
| + ctx.fillRect(10, 10, 10, 10);
|
| +}
|
| +
|
| +function clearContext(context) {
|
| + context.clearRect(0, 0, 50, 50);
|
| +}
|
| +
|
| +var bitmap;
|
| +var image;
|
| +var testBitmap; // this is an ImageBitmap that is uncropped. We use this to test createImageBitmap(testBitmap)
|
| +var d; // image.imageData
|
| +var elements;
|
| +var options;
|
| +
|
| +var imageWidth = 20;
|
| +var imageHeight = 20;
|
| +
|
| +// Draw to an auxillary canvas.
|
| +var aCanvas = document.createElement("canvas");
|
| +aCanvas.width = imageWidth;
|
| +aCanvas.height = imageHeight;
|
| +var aCtx = aCanvas.getContext("2d");
|
| +drawPattern(aCtx);
|
| +
|
| +var canvas = document.createElement("canvas");
|
| +canvas.setAttribute("width", "50");
|
| +canvas.setAttribute("height", "50");
|
| +var ctx = canvas.getContext("2d");
|
| +
|
| +image = new Image();
|
| +image.onload = imageLoaded;
|
| +image.src = aCanvas.toDataURL();
|
| +
|
| +var imageLoaded = false;
|
| +var imageBitmapLoaded = false;
|
| +var blobLoaded = false;
|
| +
|
| +function imageLoaded() {
|
| + createImageBitmap(image).then(imageBitmapLoadedCallback, shouldNotBeCalled);
|
| + d = aCtx.getImageData(0, 0, 20, 20);
|
| + imageLoaded = true;
|
| + loaded();
|
| +}
|
| +
|
| +function imageBitmapLoadedCallback(imageBitmap) {
|
| + testBitmap = imageBitmap;
|
| +
|
| + shouldBe("testBitmap.width", "imageWidth");
|
| + shouldBe("testBitmap.height", "imageHeight");
|
| +
|
| + // width and height are readonly
|
| + testBitmap.width = 42;
|
| + testBitmap.height = 42;
|
| + shouldBe("testBitmap.width", "imageWidth");
|
| + shouldBe("testBitmap.height", "imageHeight");
|
| +
|
| + imageBitmapLoaded = true;
|
| + loaded();
|
| +}
|
| +
|
| +var xhr = new XMLHttpRequest();
|
| +xhr.open("GET", 'resources/pattern.png');
|
| +xhr.responseType = 'blob';
|
| +xhr.send();
|
| +xhr.onload = function() {
|
| + blob = xhr.response;
|
| + blobLoaded = true;
|
| + loaded();
|
| +}
|
| +
|
| +function loaded() {
|
| + if (imageLoaded && imageBitmapLoaded && blobLoaded) {
|
| + // check all elements and all options
|
| + elements = [image, aCanvas, d, testBitmap, blob];
|
| + options = ["none", "flipY"];
|
| + // elements = [image, aCanvas, d, testBitmap, blob];
|
| + // wait for callback to finish before each check to ensure synchronous behavior
|
| + nextCheck(0, 0);
|
| + }
|
| +}
|
| +
|
| +function nextCheck(elementIndex, optionIndex) {
|
| + if (elementIndex == elements.length) {
|
| + finishJSTest();
|
| + return;
|
| + }
|
| + var element = elements[elementIndex];
|
| + imageBitmaps = {};
|
| + debug("Checking " + jsWrapperClass(element) + " with imageOrientation: " + options[optionIndex] + ".");
|
| + var p1 = createImageBitmap(element, {imageOrientation: options[optionIndex]}).then(function (image) { imageBitmaps.noCrop = image });
|
| + var p2 = createImageBitmap(element, 0, 0, 10, 10, {imageOrientation: options[optionIndex]}).then(function (image) { imageBitmaps.crop = image });
|
| + var p3 = createImageBitmap(element, 5, 5, 10, 10, {imageOrientation: options[optionIndex]}).then(function (image) { imageBitmaps.cropCenter = image });
|
| + var p4 = createImageBitmap(element, 10, 10, 10, 10, {imageOrientation: options[optionIndex]}).then(function (image) { imageBitmaps.cropRight = image });
|
| + var p5 = createImageBitmap(element, -10, -10, 60, 60, {imageOrientation: options[optionIndex]}).then(function (image) { imageBitmaps.overCrop = image });
|
| + var p6 = createImageBitmap(element, 10, 10, 50, 50, {imageOrientation: options[optionIndex]}).then(function (image) { imageBitmaps.overCropRight = image });
|
| + var p7 = createImageBitmap(element, 10, 10, -10, -10, {imageOrientation: options[optionIndex]}).then(function (image) { imageBitmaps.negativeCrop = image });
|
| + var p8 = createImageBitmap(element, -30, -30, 30, 30, {imageOrientation: options[optionIndex]}).then(function (image) { imageBitmaps.empty = image });
|
| + var p9 = createImageBitmap(element, 40, 30, 30, 30, {imageOrientation: options[optionIndex]}).then(function (image) { imageBitmaps.emptyTwo = image });
|
| + Promise.all([p1, p2, p3, p4, p5, p6, p7, p8, p9]).then(function() {
|
| + checkNoCrop(imageBitmaps.noCrop, options[optionIndex]);
|
| + checkCrop(imageBitmaps.crop, options[optionIndex]);
|
| + checkCropCenter(imageBitmaps.cropCenter, options[optionIndex]);
|
| + checkCropRight(imageBitmaps.cropRight, options[optionIndex]);
|
| + checkOverCrop(imageBitmaps.overCrop, options[optionIndex]);
|
| + checkOverCropRight(imageBitmaps.overCropRight, options[optionIndex]);
|
| + checkCrop(imageBitmaps.negativeCrop, options[optionIndex]);
|
| + checkEmpty(imageBitmaps.empty, options[optionIndex]);
|
| + checkEmpty(imageBitmaps.emptyTwo, options[optionIndex]);
|
| + if (optionIndex == 3)
|
| + nextCheck(elementIndex + 1, 0);
|
| + else
|
| + nextCheck(elementIndex, optionIndex + 1);
|
| + }, shouldNotBeCalled);
|
| +}
|
| +
|
| +function checkNoCrop(imageBitmap, option) {
|
| + debug("Check no crop.");
|
| + bitmap = imageBitmap;
|
| + shouldBeType("bitmap", "ImageBitmap");
|
| + shouldBe("bitmap.width", "imageWidth");
|
| + shouldBe("bitmap.height", "imageHeight");
|
| +
|
| + clearContext(ctx);
|
| + ctx.drawImage(imageBitmap, 0, 0);
|
| + if (option == "flipY" || option == "bottomLeft") {
|
| + shouldBeBlue(9, 9);
|
| + shouldBeBlack(11, 9);
|
| + shouldBeRed(9, 11);
|
| + shouldBeGreen(11, 11);
|
| + shouldBeGreen(19, 19);
|
| + shouldBeClear(1, 21);
|
| + shouldBeClear(21, 1);
|
| + shouldBeClear(21, 21);
|
| + } else {
|
| + shouldBeRed(9, 9);
|
| + shouldBeGreen(11, 9);
|
| + shouldBeBlue(9, 11);
|
| + shouldBeBlack(11, 11);
|
| + shouldBeBlack(19, 19);
|
| + shouldBeClear(1, 21);
|
| + shouldBeClear(21, 1);
|
| + shouldBeClear(21, 21);
|
| + }
|
| +
|
| + clearContext(ctx);
|
| + ctx.drawImage(imageBitmap, 0, 0, 10, 10);
|
| + if (option == "flipY" || option == "bottomLeft") {
|
| + shouldBeBlue(4, 4);
|
| + shouldBeBlack(6, 4);
|
| + shouldBeRed(4, 6);
|
| + shouldBeGreen(6, 6);
|
| + shouldBeGreen(9, 9);
|
| + shouldBeClear(1, 11);
|
| + shouldBeClear(11, 1);
|
| + shouldBeClear(11, 11);
|
| + } else {
|
| + shouldBeRed(4, 4);
|
| + shouldBeGreen(6, 4);
|
| + shouldBeBlue(4, 6);
|
| + shouldBeBlack(6, 6);
|
| + shouldBeBlack(9, 9);
|
| + shouldBeClear(1, 11);
|
| + shouldBeClear(11, 1);
|
| + shouldBeClear(11, 11);
|
| + }
|
| +
|
| + clearContext(ctx);
|
| + ctx.drawImage(imageBitmap, 10, 10, 10, 10);
|
| + if (option == "flipY" || option == "bottomLeft") {
|
| + shouldBeBlue(14, 14);
|
| + shouldBeBlack(16, 14);
|
| + shouldBeRed(14, 16);
|
| + shouldBeGreen(16, 16);
|
| + shouldBeGreen(19, 19);
|
| + shouldBeClear(11, 21);
|
| + shouldBeClear(21, 11);
|
| + shouldBeClear(21, 21);
|
| + } else {
|
| + shouldBeRed(14, 14);
|
| + shouldBeGreen(16, 14);
|
| + shouldBeBlue(14, 16);
|
| + shouldBeBlack(16, 16);
|
| + shouldBeBlack(19, 19);
|
| + shouldBeClear(11, 21);
|
| + shouldBeClear(21, 11);
|
| + shouldBeClear(21, 21);
|
| + }
|
| +
|
| + clearContext(ctx);
|
| + ctx.drawImage(imageBitmap, 10, 10, 10, 10, 10, 10, 10, 10);
|
| + if (option == "flipY" || option == "bottomLeft") {
|
| + shouldBeClear(9, 9);
|
| + shouldBeGreen(11, 11);
|
| + shouldBeGreen(19, 19);
|
| + shouldBeClear(1, 21);
|
| + shouldBeClear(21, 1);
|
| + shouldBeClear(21, 21);
|
| + } else {
|
| + shouldBeClear(9, 9);
|
| + shouldBeBlack(11, 11);
|
| + shouldBeBlack(19, 19);
|
| + shouldBeClear(1, 21);
|
| + shouldBeClear(21, 1);
|
| + shouldBeClear(21, 21);
|
| + }
|
| +}
|
| +
|
| +function checkCrop(imageBitmap, option) {
|
| + debug("Check crop.");
|
| + bitmap = imageBitmap;
|
| + shouldBeType("bitmap", "ImageBitmap");
|
| + shouldBe("bitmap.width", "10");
|
| + shouldBe("bitmap.height", "10");
|
| +
|
| + clearContext(ctx);
|
| + ctx.drawImage(imageBitmap, 0, 0);
|
| + if (option == "flipY" || option == "bottomLeft") {
|
| + shouldBeRed(1, 1);
|
| + shouldBeRed(9, 9);
|
| + shouldBeClear(12, 12);
|
| + shouldBeClear(1, 12);
|
| + shouldBeClear(12, 1);
|
| + } else {
|
| + shouldBeRed(1, 1);
|
| + shouldBeRed(9, 9);
|
| + shouldBeClear(12, 12);
|
| + shouldBeClear(1, 12);
|
| + shouldBeClear(12, 1);
|
| + }
|
| +
|
| + clearContext(ctx);
|
| + ctx.drawImage(imageBitmap, 0, 0, 20, 20);
|
| + if (option == "flipY" || option == "bottomLeft") {
|
| + shouldBeRed(1, 1);
|
| + shouldBeRed(18, 18);
|
| + shouldBeClear(22, 22);
|
| + shouldBeClear(1, 22);
|
| + shouldBeClear(22, 1);
|
| + } else {
|
| + shouldBeRed(1, 1);
|
| + shouldBeRed(18, 18);
|
| + shouldBeClear(22, 22);
|
| + shouldBeClear(1, 22);
|
| + shouldBeClear(22, 1);
|
| + }
|
| +}
|
| +
|
| +function checkCropCenter(imageBitmap, option) {
|
| + debug("Check crop center.");
|
| + bitmap = imageBitmap;
|
| + shouldBeType("bitmap", "ImageBitmap");
|
| + shouldBe("bitmap.width", "10");
|
| + shouldBe("bitmap.height", "10");
|
| +
|
| + clearContext(ctx);
|
| + ctx.drawImage(imageBitmap, 0, 0);
|
| + if (option == "flipY" || option == "bottomLeft") {
|
| + shouldBeBlue(4, 4);
|
| + shouldBeBlack(6, 4);
|
| + shouldBeRed(4, 6);
|
| + shouldBeGreen(6, 6);
|
| + shouldBeGreen(9, 9);
|
| + shouldBeClear(11, 11);
|
| + shouldBeClear(1, 11);
|
| + shouldBeClear(11, 1);
|
| + } else {
|
| + shouldBeRed(4, 4);
|
| + shouldBeGreen(6, 4);
|
| + shouldBeBlue(4, 6);
|
| + shouldBeBlack(6, 6);
|
| + shouldBeBlack(9, 9);
|
| + shouldBeClear(11, 11);
|
| + shouldBeClear(1, 11);
|
| + shouldBeClear(11, 1);
|
| + }
|
| +
|
| + clearContext(ctx);
|
| + ctx.drawImage(imageBitmap, 0, 0, 20, 20);
|
| + if (option == "flipY" || option == "bottomLeft") {
|
| + shouldBeBlue(8, 8);
|
| + shouldBeBlack(11, 8);
|
| + shouldBeRed(8, 11);
|
| + shouldBeGreen(11, 11);
|
| + shouldBeGreen(18, 18);
|
| + shouldBeClear(22, 22);
|
| + shouldBeClear(1, 21);
|
| + shouldBeClear(21, 1);
|
| + } else {
|
| + shouldBeRed(8, 8);
|
| + shouldBeGreen(11, 8);
|
| + shouldBeBlue(8, 11);
|
| + shouldBeBlack(11, 11);
|
| + shouldBeBlack(18, 18);
|
| + shouldBeClear(22, 22);
|
| + shouldBeClear(1, 21);
|
| + shouldBeClear(21, 1);
|
| + }
|
| +}
|
| +
|
| +function checkCropRight(imageBitmap, option) {
|
| + debug("Check crop right.");
|
| + bitmap = imageBitmap;
|
| + shouldBeType("bitmap", "ImageBitmap");
|
| + shouldBe("bitmap.width", "10");
|
| + shouldBe("bitmap.height", "10");
|
| +
|
| + clearContext(ctx);
|
| + ctx.drawImage(imageBitmap, 0, 0);
|
| + if (option == "flipY" || option == "bottomLeft") {
|
| + shouldBeBlack(1, 1);
|
| + shouldBeBlack(9, 9);
|
| + shouldBeClear(11, 11);
|
| + shouldBeClear(1, 11);
|
| + shouldBeClear(11, 1);
|
| + } else {
|
| + shouldBeBlack(1, 1);
|
| + shouldBeBlack(9, 9);
|
| + shouldBeClear(11, 11);
|
| + shouldBeClear(1, 11);
|
| + shouldBeClear(11, 1);
|
| + }
|
| +}
|
| +
|
| +function checkOverCrop(imageBitmap, option) {
|
| + debug("Check over crop.");
|
| + bitmap = imageBitmap;
|
| + shouldBeType("bitmap", "ImageBitmap");
|
| + shouldBe("bitmap.width", "60");
|
| + shouldBe("bitmap.height", "60");
|
| +
|
| + clearContext(ctx);
|
| + ctx.drawImage(imageBitmap, 0, 0);
|
| + if (option == "flipY" || option == "bottomLeft") {
|
| + shouldBeClear(1, 59);
|
| + shouldBeClear(9, 51);
|
| + shouldBeBlue(10, 30);
|
| + shouldBeBlue(19, 39);
|
| + shouldBeBlack(20, 30);
|
| + shouldBeBlack(29, 39);
|
| + shouldBeRed(10, 40);
|
| + shouldBeRed(19, 49);
|
| + shouldBeGreen(20, 40);
|
| + shouldBeGreen(29, 49);
|
| + shouldBeClear(31, 59);
|
| + shouldBeClear(1, 29);
|
| + shouldBeClear(30, 30);
|
| + } else {
|
| + shouldBeClear(1, 1);
|
| + shouldBeClear(9, 9);
|
| + shouldBeRed(11, 11);
|
| + shouldBeRed(19, 19);
|
| + shouldBeGreen(21, 19);
|
| + shouldBeBlue(19, 21);
|
| + shouldBeBlack(21, 21);
|
| + shouldBeBlack(29, 29);
|
| + shouldBeClear(32, 1);
|
| + shouldBeClear(1, 32);
|
| + shouldBeClear(32, 32);
|
| + }
|
| +
|
| + clearContext(ctx);
|
| + ctx.drawImage(imageBitmap, 0, 0, 30, 30);
|
| + if (option == "flipY" || option == "bottomLeft") {
|
| + shouldBeClear(1, 29);
|
| + shouldBeClear(4, 25);
|
| + shouldBeBlue(5, 15);
|
| + shouldBeBlue(9, 19);
|
| + shouldBeBlack(10, 15);
|
| + shouldBeBlack(14, 19);
|
| + shouldBeRed(5, 21);
|
| + shouldBeRed(9, 24);
|
| + shouldBeGreen(11, 21);
|
| + shouldBeGreen(14, 24);
|
| + shouldBeClear(16, 29);
|
| + shouldBeClear(1, 14);
|
| + shouldBeClear(15, 15);
|
| + } else {
|
| + shouldBeClear(1, 1);
|
| + shouldBeClear(4, 4);
|
| + shouldBeRed(6, 6);
|
| + shouldBeRed(9, 9);
|
| + shouldBeGreen(11, 9);
|
| + shouldBeBlue(9, 11);
|
| + shouldBeBlack(11, 11);
|
| + shouldBeBlack(14, 14);
|
| + shouldBeClear(16, 1);
|
| + shouldBeClear(1, 16);
|
| + shouldBeClear(16, 16);
|
| + }
|
| +}
|
| +
|
| +function checkOverCropRight(imageBitmap, option) {
|
| + debug("Check over crop right.");
|
| + bitmap = imageBitmap;
|
| + shouldBe("bitmap.width", "50");
|
| + shouldBe("bitmap.height", "50");
|
| +
|
| + clearContext(ctx);
|
| + ctx.drawImage(imageBitmap, 0, 0);
|
| + if (option == "flipY" || option == "bottomLeft") {
|
| + shouldBeBlack(1, 40);
|
| + shouldBeBlack(9, 49);
|
| + shouldBeClear(10, 49);
|
| + shouldBeClear(1, 39);
|
| + shouldBeClear(10, 40);
|
| + } else {
|
| + shouldBeBlack(1, 1);
|
| + shouldBeBlack(9, 9);
|
| + shouldBeClear(11, 11);
|
| + shouldBeClear(1, 11);
|
| + shouldBeClear(11, 1);
|
| + }
|
| +
|
| + clearContext(ctx);
|
| + ctx.drawImage(imageBitmap, 0, 0, 20, 20);
|
| + if (option == "flipY" || option == "bottomLeft") {
|
| + shouldBeBlack(0, 16);
|
| + shouldBeBlack(3, 19);
|
| + shouldBeClear(4, 19);
|
| + shouldBeClear(0, 15);
|
| + shouldBeClear(4, 15);
|
| + } else {
|
| + shouldBeBlack(1, 1);
|
| + shouldBeBlack(3, 3);
|
| + shouldBeClear(5, 5);
|
| + shouldBeClear(1, 5);
|
| + shouldBeClear(5, 1);
|
| + }
|
| +
|
| + clearContext(ctx);
|
| + ctx.drawImage(imageBitmap, 10, 10, 20, 20, 0, 0, 20, 20);
|
| + if (option == "flipY" || option == "bottomLeft") {
|
| + shouldBeClear(1, 1);
|
| + shouldBeClear(3, 3);
|
| + shouldBeClear(5, 5);
|
| + shouldBeClear(1, 5);
|
| + shouldBeClear(5, 1);
|
| + } else {
|
| + shouldBeClear(1, 1);
|
| + shouldBeClear(3, 3);
|
| + shouldBeClear(5, 5);
|
| + shouldBeClear(1, 5);
|
| + shouldBeClear(5, 1);
|
| + }
|
| +}
|
| +
|
| +// For an empty image, the orientation doesn't matter
|
| +function checkEmpty(imageBitmap, option) {
|
| + debug("Check empty.");
|
| + bitmap = imageBitmap;
|
| + shouldBeType("bitmap", "ImageBitmap");
|
| + shouldBe("bitmap.width", "30");
|
| + shouldBe("bitmap.height", "30");
|
| +
|
| + // nothing should be drawn
|
| + clearContext(ctx);
|
| + ctx.drawImage(imageBitmap, 0, 0);
|
| + shouldBeClear(1, 1);
|
| + shouldBeClear(9, 9);
|
| + shouldBeClear(11, 11);
|
| + shouldBeClear(22, 22);
|
| +}
|
| +</script>
|
| +</body>
|
| +</html>
|
|
|