Index: third_party/WebKit/Source/core/html/HTMLImageFallbackHelper.cpp |
diff --git a/third_party/WebKit/Source/core/html/HTMLImageFallbackHelper.cpp b/third_party/WebKit/Source/core/html/HTMLImageFallbackHelper.cpp |
index bc2f7718bf9fb6816e763795da395201f5ea9294..b34507f2e16637512119ee6fbe18f281194a1c9f 100644 |
--- a/third_party/WebKit/Source/core/html/HTMLImageFallbackHelper.cpp |
+++ b/third_party/WebKit/Source/core/html/HTMLImageFallbackHelper.cpp |
@@ -9,11 +9,11 @@ |
#include "core/dom/ElementRareData.h" |
#include "core/dom/Text.h" |
#include "core/dom/shadow/ShadowRoot.h" |
-#include "core/html/HTMLDivElement.h" |
#include "core/html/HTMLElement.h" |
#include "core/html/HTMLImageElement.h" |
#include "core/html/HTMLImageLoader.h" |
#include "core/html/HTMLInputElement.h" |
+#include "core/html/HTMLSpanElement.h" |
#include "core/html/HTMLStyleElement.h" |
#include "wtf/text/StringBuilder.h" |
@@ -21,31 +21,24 @@ namespace blink { |
using namespace HTMLNames; |
-static bool noImageSourceSpecified(const Element& element) { |
- bool noSrcSpecified = !element.hasAttribute(srcAttr) || |
- element.getAttribute(srcAttr).isNull() || |
- element.getAttribute(srcAttr).isEmpty(); |
- bool noSrcsetSpecified = !element.hasAttribute(srcsetAttr) || |
- element.getAttribute(srcsetAttr).isNull() || |
- element.getAttribute(srcsetAttr).isEmpty(); |
- return noSrcSpecified && noSrcsetSpecified; |
+static bool imageSmallerThanAltImage(int pixelsForAltImage, |
+ const Length width, |
+ const Length height) { |
+ // We don't have a layout tree so can't compute the size of an image |
+ // relative dimensions - so we just assume we should display the alt image. |
+ if (!width.isFixed() && !height.isFixed()) |
+ return false; |
+ if (height.isFixed()) |
+ return height.value() < pixelsForAltImage; |
+ return width.value() < pixelsForAltImage; |
} |
void HTMLImageFallbackHelper::createAltTextShadowTree(Element& element) { |
ShadowRoot& root = element.ensureUserAgentShadowRoot(); |
- HTMLDivElement* container = HTMLDivElement::create(element.document()); |
+ HTMLSpanElement* container = HTMLSpanElement::create(element.document()); |
root.appendChild(container); |
container->setAttribute(idAttr, AtomicString("alttext-container")); |
- container->setInlineStyleProperty(CSSPropertyOverflow, CSSValueHidden); |
- container->setInlineStyleProperty(CSSPropertyBorderWidth, 1, |
- CSSPrimitiveValue::UnitType::Pixels); |
- container->setInlineStyleProperty(CSSPropertyBorderStyle, CSSValueSolid); |
- container->setInlineStyleProperty(CSSPropertyBorderColor, CSSValueSilver); |
- container->setInlineStyleProperty(CSSPropertyDisplay, CSSValueInlineBlock); |
- container->setInlineStyleProperty(CSSPropertyBoxSizing, CSSValueBorderBox); |
- container->setInlineStyleProperty(CSSPropertyPadding, 1, |
- CSSPrimitiveValue::UnitType::Pixels); |
HTMLImageElement* brokenImage = HTMLImageElement::create(element.document()); |
container->appendChild(brokenImage); |
@@ -57,11 +50,9 @@ void HTMLImageFallbackHelper::createAltTextShadowTree(Element& element) { |
brokenImage->setInlineStyleProperty(CSSPropertyMargin, 0, |
CSSPrimitiveValue::UnitType::Pixels); |
- HTMLDivElement* altText = HTMLDivElement::create(element.document()); |
+ HTMLSpanElement* altText = HTMLSpanElement::create(element.document()); |
container->appendChild(altText); |
altText->setAttribute(idAttr, AtomicString("alttext")); |
- altText->setInlineStyleProperty(CSSPropertyOverflow, CSSValueHidden); |
pdr.
2017/03/24 02:12:50
The change to LayoutTests/tables/mozilla_expected_
|
- altText->setInlineStyleProperty(CSSPropertyDisplay, CSSValueBlock); |
Text* text = |
Text::create(element.document(), toHTMLElement(element).altText()); |
@@ -102,36 +93,68 @@ PassRefPtr<ComputedStyle> HTMLImageFallbackHelper::customStyleForAltText( |
} |
} |
- // If the image has specified dimensions allow the alt-text container expand |
- // to fill them. |
- if (newStyle->width().isSpecifiedOrIntrinsic() && |
- newStyle->height().isSpecifiedOrIntrinsic()) { |
- placeHolder->setInlineStyleProperty( |
- CSSPropertyWidth, 100, CSSPrimitiveValue::UnitType::Percentage); |
- placeHolder->setInlineStyleProperty( |
- CSSPropertyHeight, 100, CSSPrimitiveValue::UnitType::Percentage); |
- } |
- |
- // Make sure the broken image icon appears on the appropriate side of the |
- // image for the element's writing direction. |
- brokenImage->setInlineStyleProperty( |
- CSSPropertyFloat, |
- AtomicString(newStyle->direction() == TextDirection::kLtr ? "left" |
- : "right")); |
- |
- // This is an <img> with no attributes, so don't display anything. |
- if (noImageSourceSpecified(element) && |
- !newStyle->width().isSpecifiedOrIntrinsic() && |
- !newStyle->height().isSpecifiedOrIntrinsic() && |
- toHTMLElement(element).altText().isEmpty()) |
- newStyle->setDisplay(EDisplay::kNone); |
- |
- // This preserves legacy behaviour originally defined when alt-text was |
- // managed by LayoutImage. |
- if (noImageSourceSpecified(element)) |
- brokenImage->setInlineStyleProperty(CSSPropertyDisplay, CSSValueNone); |
- else |
+ bool imageHasIntrinsicDimensions = |
+ newStyle->width().isSpecifiedOrIntrinsic() && |
+ newStyle->height().isSpecifiedOrIntrinsic(); |
+ bool imageHasNoAltAttribute = toHTMLElement(element).altText().isNull(); |
+ bool treatAsReplaced = |
+ imageHasIntrinsicDimensions && |
+ (element.document().inQuirksMode() || imageHasNoAltAttribute); |
+ // 16px for the image and 2px for its border/padding offset. |
+ int pixelsForAltImage = 18; |
pdr.
2017/03/24 02:15:45
Should this be 1 + 1 + 16 + 1 + 1 = 20 to account
|
+ if (treatAsReplaced && |
+ !imageSmallerThanAltImage(pixelsForAltImage, newStyle->width(), |
+ newStyle->height())) { |
+ // https://html.spec.whatwg.org/multipage/rendering.html#images-3: |
+ // "If the element does not represent an image, but the element already has |
+ // intrinsic dimensions (e.g. from the dimension attributes or CSS rules), |
+ // and either: the user agent has reason to believe that the image will |
+ // become available and be rendered in due course, or the element has no alt |
+ // attribute, or the Document is in quirks mode The user agent is expected |
+ // to treat the element as a replaced element whose content is the text that |
+ // the element represents, if any." |
+ placeHolder->setInlineStyleProperty(CSSPropertyDisplay, |
+ CSSValueInlineBlock); |
+ placeHolder->setInlineStyleProperty(CSSPropertyBorderWidth, 1, |
+ CSSPrimitiveValue::UnitType::Pixels); |
+ placeHolder->setInlineStyleProperty(CSSPropertyBorderStyle, CSSValueSolid); |
+ placeHolder->setInlineStyleProperty(CSSPropertyBorderColor, CSSValueSilver); |
+ placeHolder->setInlineStyleProperty(CSSPropertyPadding, 1, |
+ CSSPrimitiveValue::UnitType::Pixels); |
+ placeHolder->setInlineStyleProperty(CSSPropertyBoxSizing, |
+ CSSValueBorderBox); |
+ CSSPrimitiveValue::UnitType unit = |
+ newStyle->height().isPercent() ? CSSPrimitiveValue::UnitType::Percentage |
+ : CSSPrimitiveValue::UnitType::Pixels; |
+ placeHolder->setInlineStyleProperty(CSSPropertyHeight, |
+ newStyle->height().value(), unit); |
+ placeHolder->setInlineStyleProperty(CSSPropertyWidth, |
+ newStyle->width().value(), unit); |
brokenImage->setInlineStyleProperty(CSSPropertyDisplay, CSSValueInline); |
+ // Make sure the broken image icon appears on the appropriate side of the |
+ // image for the element's writing direction. |
+ brokenImage->setInlineStyleProperty( |
+ CSSPropertyFloat, |
+ AtomicString(newStyle->direction() == TextDirection::kLtr ? "left" |
+ : "right")); |
+ } else { |
+ // "If the element is an img element that represents nothing and the user |
+ // agent does not expect this to change the user agent is expected to treat |
+ // the element as an empty inline element." |
+ // - We achieve this by hiding the broken image so that the span is empty. |
+ // "If the element is an img element that represents some text and the user |
+ // agent does not expect this to change the user agent is expected to treat |
+ // the element as a non-replaced phrasing element whose content is the text, |
+ // optionally with an icon indicating that an image is missing, so that the |
+ // user can request the image be displayed or investigate why it is not |
+ // rendering." |
+ // - We opt not to display an icon, like Firefox. |
+ if (!treatAsReplaced && newStyle->display() == EDisplay::kInline) { |
+ newStyle->setWidth(Length()); |
+ newStyle->setHeight(Length()); |
pdr.
2017/03/24 02:12:49
In tables/mozilla/bugs/bug56201.html it looks like
|
+ } |
+ brokenImage->setInlineStyleProperty(CSSPropertyDisplay, CSSValueNone); |
+ } |
return newStyle; |
} |