| <!DOCTYPE html> | |
| <html> | |
| <head> | |
| <script src="../js/resources/js-test-pre.js"></script> | |
| <style> | |
| #computed-infer-vertical-border-spacing { border-spacing: 11px; } | |
| #computed-infer-vertical-border-spacing-from-negative-horizontal-border-spacing { border-spacing: -11px; } | |
| #computed-explicit-border-spacing { border-spacing: 13px 23px; } | |
| #computed-explicit-negative-border-spacing { border-spacing: -5px -13px; } | |
| #computed-explicit-border-spacing-with-negative-horizontal { border-spacing: -5px 13px; } | |
| #computed-explicit-border-spacing-with-negative-vertical { border-spacing: 5px -13px; } | |
| #missing-stylesheet-border-spacing { border-spacing: } | |
| </style> | |
| <script> | |
| window.onload = runTests; | |
| if (!String.prototype.trim) { | |
| // Assume this script is being executed in Internet Explorer. | |
| String.prototype.trim = function() { | |
| return this.replace(/^\s+/, '').replace(/\s+$/, ''); | |
| } | |
| } | |
| function runTests() | |
| { | |
| debug('Valid values:'); | |
| testInferredVerticalBorderSpacing(); | |
| testExplicitBorderSpacing(); | |
| testComputedInferredVerticalBorderSpacing(); | |
| testComputedExplicitBorderSpacing(); | |
| debug('<br />Negative values:'); | |
| testInferredVerticalBorderSpacingFromNegativeHorizontalSpacing(); | |
| testExplicitNegativeBorderSpacing(); | |
| testExplicitBorderSpacingWithNegativeHorizontal(); | |
| testExplicitBorderSpacingWithNegativeVertical(); | |
| testComputedInferredVerticalBorderSpacingFromNegativeHorizontalSpacing(); | |
| testComputedExplicitNegativeBorderSpacing(); | |
| testComputedExplicitBorderSpacingWithNegativeHorizontal(); | |
| testComputedExplicitBorderSpacingWithNegativeVertical(); | |
| debug('<br />Missing values:'); | |
| testMissingBorderSpacing(); | |
| testMissingStylesheetBorderSpacing(); | |
| document.body.removeChild(document.getElementById("test-container")); | |
| debug('<br /><span class="pass">TEST COMPLETE</span>'); | |
| } | |
| function testInferredVerticalBorderSpacing() | |
| { | |
| var styleAttr = styleAttribute(document.getElementById("infer-vertical-border-spacing")); | |
| shouldBeEqualToString('document.getElementById("infer-vertical-border-spacing").style.borderSpacing', parseCSSTextForPropertyValue(styleAttr, "border-spacing")); | |
| } | |
| function testExplicitBorderSpacing() | |
| { | |
| var styleAttr = styleAttribute(document.getElementById("explicit-border-spacing")); | |
| shouldBeEqualToString('document.getElementById("explicit-border-spacing").style.borderSpacing', parseCSSTextForPropertyValue(styleAttr, "border-spacing")); | |
| } | |
| function testComputedInferredVerticalBorderSpacing() | |
| { | |
| shouldBeEqualToString('computedStyle(document.getElementById("computed-infer-vertical-border-spacing")).borderSpacing', "11px 11px"); | |
| shouldBeEqualToString('cssRule("#computed-infer-vertical-border-spacing").style.borderSpacing', "11px"); // Must match border-spacing for #computed-infer-vertical-border-spacing. | |
| } | |
| function testComputedExplicitBorderSpacing() | |
| { | |
| var expectedResult = "13px 23px"; // Must match border-spacing for #computed-explicit-border-spacing. | |
| shouldBeEqualToString('computedStyle(document.getElementById("computed-explicit-border-spacing")).borderSpacing', expectedResult); | |
| shouldBeEqualToString('cssRule("#computed-explicit-border-spacing").style.borderSpacing', expectedResult); | |
| } | |
| function testInferredVerticalBorderSpacingFromNegativeHorizontalSpacing() | |
| { | |
| // The expected value of the empty string follows from <http://www.w3.org/TR/html5/elements.html#the-style-attribute>, | |
| // <http://www.w3.org/TR/css-style-attr/#syntax>, <http://www.w3.org/TR/CSS21/syndata.html#declaration>, <http://www.w3.org/TR/CSS21/syndata.html#length-units>, | |
| // and the definition of "ignore" <http://www.w3.org/TR/CSS21/syndata.html#ignore>. | |
| shouldBeEqualToString('document.getElementById("infer-vertical-border-spacing-from-negative-horizontal-spacing").style.borderSpacing', ""); | |
| } | |
| function testExplicitNegativeBorderSpacing() | |
| { | |
| // The expected value of the empty string follows from <http://www.w3.org/TR/html5/elements.html#the-style-attribute>, | |
| // <http://www.w3.org/TR/css-style-attr/#syntax>, <http://www.w3.org/TR/CSS21/syndata.html#declaration>, <http://www.w3.org/TR/CSS21/syndata.html#length-units>, | |
| // and the definition of "ignore" <http://www.w3.org/TR/CSS21/syndata.html#ignore>. | |
| shouldBeEqualToString('document.getElementById("explicit-negative-border-spacing").style.borderSpacing', ""); | |
| } | |
| function testExplicitBorderSpacingWithNegativeHorizontal() | |
| { | |
| // The expected value of the empty string follows from <http://www.w3.org/TR/html5/elements.html#the-style-attribute>, | |
| // <http://www.w3.org/TR/css-style-attr/#syntax>, <http://www.w3.org/TR/CSS21/syndata.html#declaration>, <http://www.w3.org/TR/CSS21/syndata.html#length-units>, | |
| // and the definition of "ignore" <http://www.w3.org/TR/CSS21/syndata.html#ignore>. | |
| shouldBeEqualToString('document.getElementById("explicit-border-spacing-with-negative-horizontal").style.borderSpacing', ""); | |
| } | |
| function testExplicitBorderSpacingWithNegativeVertical() | |
| { | |
| // The expected value of the empty string follows from <http://www.w3.org/TR/html5/elements.html#the-style-attribute>, | |
| // <http://www.w3.org/TR/css-style-attr/#syntax>, <http://www.w3.org/TR/CSS21/syndata.html#declaration>, <http://www.w3.org/TR/CSS21/syndata.html#length-units>, | |
| // and the definition of "ignore" <http://www.w3.org/TR/CSS21/syndata.html#ignore>. | |
| shouldBeEqualToString('document.getElementById("explicit-border-spacing-with-negative-vertical").style.borderSpacing', ""); | |
| } | |
| function testComputedInferredVerticalBorderSpacingFromNegativeHorizontalSpacing() | |
| { | |
| // Expected results follow from the explanation given in testInferredVerticalBorderSpacingFromNegativeHorizontalSpacing(). | |
| shouldBeEqualToString('cssRule("#computed-infer-vertical-border-spacing-from-negative-horizontal-border-spacing").style.borderSpacing', ""); | |
| } | |
| function testComputedExplicitNegativeBorderSpacing() | |
| { | |
| // Expected results follow from the explanation given in testExplicitNegativeBorderSpacing(). | |
| shouldBeEqualToString('cssRule("#computed-explicit-negative-border-spacing").style.borderSpacing', ""); | |
| } | |
| function testComputedExplicitBorderSpacingWithNegativeHorizontal() | |
| { | |
| // Expected results follow from the explanation given in testExplicitBorderSpacingWithNegativeHorizontal(). | |
| shouldBeEqualToString('cssRule("#computed-explicit-border-spacing-with-negative-horizontal").style.borderSpacing', ""); | |
| } | |
| function testComputedExplicitBorderSpacingWithNegativeVertical() | |
| { | |
| // Expected results follow from the explanation given in testExplicitBorderSpacingWithNegativeVertical(). | |
| shouldBeEqualToString('cssRule("#computed-explicit-border-spacing-with-negative-vertical").style.borderSpacing', ""); | |
| } | |
| function testMissingBorderSpacing() | |
| { | |
| // Notice, a property with a missing value is considered a malformed declaration by | |
| // <http://www.w3.org/TR/CSS21/syndata.html#parsing-errors>. Hence, we ignore the declaration. | |
| shouldBeEqualToString('document.getElementById("missing-border-spacing").style.borderSpacing', ""); | |
| } | |
| function testMissingStylesheetBorderSpacing() | |
| { | |
| // Expected results follow from the explanation given in testMissingBorderSpacing(). | |
| shouldBeEqualToString('cssRule("#missing-stylesheet-border-spacing").style.borderSpacing', ""); | |
| } | |
| function styleAttribute(element) | |
| { | |
| var result = element.getAttribute("style"); | |
| if (typeof(result) === "object") { | |
| // Assume this script is being executed in Internet Explorer. | |
| result = result.cssText; | |
| } | |
| return result; | |
| } | |
| function computedStyle(element) | |
| { | |
| if (window.getComputedStyle) | |
| return window.getComputedStyle(element, null); | |
| return element.currentStyle; // Assume this script is being executed in Internet Explorer 8 or less. | |
| } | |
| function cssRule(ruleName) | |
| { | |
| if (!ruleName) | |
| return; | |
| if (!document.styleSheets) | |
| return; | |
| var NotFound = -1; // We can't make this "const" since IE (as of 8.0) doesn't support it. | |
| // We normalize the name of the rule to be lowercase since it is case-insensitive by <http://www.w3.org/TR/CSS21/syndata.html#characters>. | |
| var ruleName = ruleName.toLowerCase(); | |
| var lastRuleThatMatchedCriterion; | |
| for (var i = 0; i < document.styleSheets.length; ++i) { | |
| var rules = []; | |
| try { | |
| var rules = document.styleSheets[i].rules || document.styleSheets[i].cssRules; // IE has "rules" property; WebKit and Firefox have "cssRules". | |
| } catch (e) { | |
| // Firefox's same-origin policy for file URLs prevents access to cssRules for stylesheets that aren't within the | |
| // same directory as the web page (e.g. ../js/resources/js-test-style.css). So, we ignore such exceptions that arise. | |
| continue; | |
| } | |
| for (var r = 0; r < rules.length; ++r) { | |
| if (rules[r].selectorText.toLowerCase() !== ruleName) | |
| continue; | |
| lastRuleThatMatchedCriterion = rules[r]; | |
| } | |
| } | |
| return lastRuleThatMatchedCriterion; | |
| } | |
| function parseCSSTextForPropertyValue(cssText, propertyName) | |
| { | |
| if (!cssText) | |
| return String(); | |
| if (!propertyName) | |
| return String(); | |
| // Some constants. We can't use "const" since IE (as of 8.0) doesn't support it. | |
| var Colon = ':'; | |
| var Semicolon = ';'; | |
| var NotFound = -1; | |
| // Note, CSS property names are case-insensitive, but its corresponding value can be case- | |
| // sensitive (e.g. font-family) by section 4.1.3 of the CSS 2.1 spec <http://www.w3.org/TR/CSS21/syndata.html#characters>. | |
| var cssTextLowerCase = cssText.toLowerCase(); | |
| var propertyName = propertyName.toLowerCase(); | |
| var startOfPropertyName = cssTextLowerCase.indexOf(propertyName); | |
| if (startOfPropertyName === NotFound) | |
| return; | |
| var delimiter = cssTextLowerCase.indexOf(Colon, startOfPropertyName); | |
| if (delimiter === NotFound) | |
| return; | |
| if (cssTextLowerCase.substr(startOfPropertyName, delimiter - startOfPropertyName).trim() !== propertyName) | |
| return; | |
| var startOfPropertyValue = delimiter + 1; | |
| var endOfRule = cssTextLowerCase.indexOf(Semicolon, startOfPropertyValue); | |
| return cssText.substr(startOfPropertyValue, endOfRule === NotFound ? cssText.length : endOfRule - startOfPropertyValue).trim(); // Preserve case-sensitivity of the property value. | |
| } | |
| </script> | |
| </head> | |
| <body> | |
| <p id="description"></p> | |
| <div id="test-container"> | |
| <table id="infer-vertical-border-spacing" style="border-spacing: 4px"> | |
| <tr><td>Infer vertical border spacing</td></tr> | |
| </table> | |
| <table id="explicit-border-spacing" style="border-spacing: 4px 5px"> | |
| <tr><td>Explicit horizontal and vertical border spacing</td></tr> | |
| </table> | |
| <table id="computed-infer-vertical-border-spacing"> | |
| <tr><td>Infer vertical border spacing (uses computed style)</td></tr> | |
| </table> | |
| <table id="computed-explicit-border-spacing"> | |
| <tr><td>Explicit horizontal and vertical border spacing (uses computed style)</td></tr> | |
| </table> | |
| <table id="infer-vertical-border-spacing-from-negative-horizontal-spacing" style="border-spacing: -5px"> | |
| <tr><td>Infer vertical border spacing from negative horizontal spacing</td></tr> | |
| </table> | |
| <table id="explicit-negative-border-spacing" style="border-spacing: -5px -13px"> | |
| <tr><td>Explicit negative horizontal and vertical border spacing</td></tr> | |
| </table> | |
| <table id="explicit-border-spacing-with-negative-horizontal" style="border-spacing: -5px 13px"> | |
| <tr><td>Explicit vertical and horizontal border spacing with negative horizontal border spacing</td></tr> | |
| </table> | |
| <table id="explicit-border-spacing-with-negative-vertical" style="border-spacing: 5px -13px"> | |
| <tr><td>Explicit vertical and horizontal border spacing with negative vertical border spacing</td></tr> | |
| </table> | |
| <table id="computed-infer-vertical-border-spacing-from-negative-horizontal-border-spacing"> | |
| <tr><td>Infer vertical border spacing from negative horizontal border spacing (uses computed style)</td></tr> | |
| </table> | |
| <table id="computed-explicit-negative-border-spacing"> | |
| <tr><td>Explicit negative horizontal and vertical border spacing (uses computed style)</td></tr> | |
| </table> | |
| <table id="computed-explicit-border-spacing-with-negative-horizontal"> | |
| <tr><td>Explicit horizontal and vertical border spacing with negative horizontal border spacing (uses computed style)</td></tr> | |
| </table> | |
| <table id="computed-explicit-border-spacing-with-negative-vertical"> | |
| <tr><td>Explicit horizontal and vertical border spacing with negative vertical border spacing (uses computed style)</td></tr> | |
| </table> | |
| <table id="missing-border-spacing" style="border-spacing: "> | |
| <tr><td>Missing border spacing</td></tr> | |
| </table> | |
| <table id="missing-stylesheet-border-spacing"> | |
| <tr><td>Missing border-spacing value in stylesheet</td></tr> | |
| </table> | |
| </div> | |
| <div id="console"></div> | |
| <script> | |
| description("This test checks that style.borderSpacing returns the correct result for valid, negative, and missing border-spacing values."); | |
| </script> | |
| </body> | |
| </html> |