Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(195)

Side by Side Diff: Source/core/rendering/RenderImage.cpp

Issue 419453003: Show alt text when source image is missing or broken or not found. (Closed) Base URL: https://chromium.googlesource.com/chromium/blink.git@master
Patch Set: Rebaselining virtual layout tests Created 6 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « LayoutTests/fast/forms/002-expected.png ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright (C) 1999 Lars Knoll (knoll@kde.org) 2 * Copyright (C) 1999 Lars Knoll (knoll@kde.org)
3 * (C) 1999 Antti Koivisto (koivisto@kde.org) 3 * (C) 1999 Antti Koivisto (koivisto@kde.org)
4 * (C) 2000 Dirk Mueller (mueller@kde.org) 4 * (C) 2000 Dirk Mueller (mueller@kde.org)
5 * (C) 2006 Allan Sandfeld Jensen (kde@carewolf.com) 5 * (C) 2006 Allan Sandfeld Jensen (kde@carewolf.com)
6 * (C) 2006 Samuel Weinig (sam.weinig@gmail.com) 6 * (C) 2006 Samuel Weinig (sam.weinig@gmail.com)
7 * Copyright (C) 2003, 2004, 2005, 2006, 2008, 2009, 2010, 2011 Apple Inc. All r ights reserved. 7 * Copyright (C) 2003, 2004, 2005, 2006, 2008, 2009, 2010, 2011 Apple Inc. All r ights reserved.
8 * Copyright (C) 2010 Google Inc. All rights reserved. 8 * Copyright (C) 2010 Google Inc. All rights reserved.
9 * Copyright (C) Research In Motion Limited 2011-2012. All rights reserved. 9 * Copyright (C) Research In Motion Limited 2011-2012. All rights reserved.
10 * 10 *
(...skipping 72 matching lines...) Expand 10 before | Expand all | Expand 10 after
83 { 83 {
84 ASSERT(!m_imageResource); 84 ASSERT(!m_imageResource);
85 m_imageResource = imageResource; 85 m_imageResource = imageResource;
86 m_imageResource->initialize(this); 86 m_imageResource->initialize(this);
87 } 87 }
88 88
89 // If we'll be displaying either alt text or an image, add some padding. 89 // If we'll be displaying either alt text or an image, add some padding.
90 static const unsigned short paddingWidth = 4; 90 static const unsigned short paddingWidth = 4;
91 static const unsigned short paddingHeight = 4; 91 static const unsigned short paddingHeight = 4;
92 92
93 // Alt text is restricted to this maximum size, in pixels. These are
94 // signed integers because they are compared with other signed values.
95 static const float maxAltTextWidth = 1024;
96 static const int maxAltTextHeight = 256;
97
98 IntSize RenderImage::imageSizeForError(ImageResource* newImage) const 93 IntSize RenderImage::imageSizeForError(ImageResource* newImage) const
99 { 94 {
100 ASSERT_ARG(newImage, newImage); 95 ASSERT_ARG(newImage, newImage);
101 ASSERT_ARG(newImage, newImage->imageForRenderer(this)); 96 ASSERT_ARG(newImage, newImage->imageForRenderer(this));
102 97
103 IntSize imageSize; 98 IntSize imageSize;
104 if (newImage->willPaintBrokenImage()) { 99 if (newImage->willPaintBrokenImage()) {
105 float deviceScaleFactor = blink::deviceScaleFactor(frame()); 100 float deviceScaleFactor = blink::deviceScaleFactor(frame());
106 pair<Image*, float> brokenImageAndImageScaleFactor = ImageResource::brok enImage(deviceScaleFactor); 101 pair<Image*, float> brokenImageAndImageScaleFactor = ImageResource::brok enImage(deviceScaleFactor);
107 imageSize = brokenImageAndImageScaleFactor.first->size(); 102 imageSize = brokenImageAndImageScaleFactor.first->size();
(...skipping 16 matching lines...) Expand all
124 else if (!m_altText.isEmpty() || newImage) { 119 else if (!m_altText.isEmpty() || newImage) {
125 // If we'll be displaying either text or an image, add a little padding. 120 // If we'll be displaying either text or an image, add a little padding.
126 imageSize = IntSize(paddingWidth, paddingHeight); 121 imageSize = IntSize(paddingWidth, paddingHeight);
127 } 122 }
128 123
129 // we have an alt and the user meant it (its not a text we invented) 124 // we have an alt and the user meant it (its not a text we invented)
130 if (!m_altText.isEmpty()) { 125 if (!m_altText.isEmpty()) {
131 FontCachePurgePreventer fontCachePurgePreventer; 126 FontCachePurgePreventer fontCachePurgePreventer;
132 127
133 const Font& font = style()->font(); 128 const Font& font = style()->font();
134 IntSize paddedTextSize(paddingWidth + std::min(ceilf(font.width(construc tTextRun(this, font, m_altText, style()))), maxAltTextWidth), paddingHeight + st d::min(font.fontMetrics().height(), maxAltTextHeight)); 129 IntSize paddedTextSize(paddingWidth + ceilf(font.width(constructTextRun( this, font, m_altText, style()))), paddingHeight + font.fontMetrics().height());
135 imageSize = imageSize.expandedTo(paddedTextSize); 130 imageSize = imageSize.expandedTo(paddedTextSize);
136 } 131 }
137 132
138 if (imageSize == intrinsicSize()) 133 if (imageSize == intrinsicSize())
139 return false; 134 return false;
140 135
141 setIntrinsicSize(imageSize); 136 setIntrinsicSize(imageSize);
142 return true; 137 return true;
143 } 138 }
144 139
(...skipping 142 matching lines...) Expand 10 before | Expand all | Expand 10 after
287 282
288 if (cWidth > 2 && cHeight > 2) { 283 if (cWidth > 2 && cHeight > 2) {
289 const int borderWidth = 1; 284 const int borderWidth = 1;
290 285
291 // Draw an outline rect where the image should be. 286 // Draw an outline rect where the image should be.
292 context->setStrokeStyle(SolidStroke); 287 context->setStrokeStyle(SolidStroke);
293 context->setStrokeColor(Color::lightGray); 288 context->setStrokeColor(Color::lightGray);
294 context->setFillColor(Color::transparent); 289 context->setFillColor(Color::transparent);
295 context->drawRect(pixelSnappedIntRect(LayoutRect(paintOffset.x() + l eftBorder + leftPad, paintOffset.y() + topBorder + topPad, cWidth, cHeight))); 290 context->drawRect(pixelSnappedIntRect(LayoutRect(paintOffset.x() + l eftBorder + leftPad, paintOffset.y() + topBorder + topPad, cWidth, cHeight)));
296 291
297 bool errorPictureDrawn = false;
298 LayoutSize imageOffset; 292 LayoutSize imageOffset;
299 // When calculating the usable dimensions, exclude the pixels of 293 // When calculating the usable dimensions, exclude the pixels of
300 // the ouline rect so the error image/alt text doesn't draw on it. 294 // the ouline rect so the error image/alt text doesn't draw on it.
301 LayoutUnit usableWidth = cWidth - 2 * borderWidth; 295 LayoutUnit usableWidth = cWidth - 2 * borderWidth;
302 LayoutUnit usableHeight = cHeight - 2 * borderWidth; 296 LayoutUnit usableHeight = cHeight - 2 * borderWidth;
303 297
304 RefPtr<Image> image = m_imageResource->image(); 298 RefPtr<Image> image = m_imageResource->image();
305 299
306 if (m_imageResource->errorOccurred() && !image->isNull() && usableWi dth >= image->width() && usableHeight >= image->height()) { 300 if (m_imageResource->errorOccurred() && !image->isNull() && usableWi dth >= image->width() && usableHeight >= image->height() && m_altText.isEmpty()) {
307 float deviceScaleFactor = blink::deviceScaleFactor(frame()); 301 float deviceScaleFactor = blink::deviceScaleFactor(frame());
308 // Call brokenImage() explicitly to ensure we get the broken ima ge icon at the appropriate resolution. 302 // Call brokenImage() explicitly to ensure we get the broken ima ge icon at the appropriate resolution.
309 pair<Image*, float> brokenImageAndImageScaleFactor = ImageResour ce::brokenImage(deviceScaleFactor); 303 pair<Image*, float> brokenImageAndImageScaleFactor = ImageResour ce::brokenImage(deviceScaleFactor);
310 image = brokenImageAndImageScaleFactor.first; 304 image = brokenImageAndImageScaleFactor.first;
311 IntSize imageSize = image->size(); 305 IntSize imageSize = image->size();
312 imageSize.scale(1 / brokenImageAndImageScaleFactor.second); 306 imageSize.scale(1 / brokenImageAndImageScaleFactor.second);
313 // Center the error image, accounting for border and padding. 307 // Center the error image, accounting for border and padding.
314 LayoutUnit centerX = (usableWidth - imageSize.width()) / 2; 308 LayoutUnit centerX = (usableWidth - imageSize.width()) / 2;
315 if (centerX < 0) 309 if (centerX < 0)
316 centerX = 0; 310 centerX = 0;
317 LayoutUnit centerY = (usableHeight - imageSize.height()) / 2; 311 LayoutUnit centerY = (usableHeight - imageSize.height()) / 2;
318 if (centerY < 0) 312 if (centerY < 0)
319 centerY = 0; 313 centerY = 0;
320 imageOffset = LayoutSize(leftBorder + leftPad + centerX + border Width, topBorder + topPad + centerY + borderWidth); 314 imageOffset = LayoutSize(leftBorder + leftPad + centerX + border Width, topBorder + topPad + centerY + borderWidth);
321 context->drawImage(image.get(), pixelSnappedIntRect(LayoutRect(p aintOffset + imageOffset, imageSize)), CompositeSourceOver, shouldRespectImageOr ientation()); 315 context->drawImage(image.get(), pixelSnappedIntRect(LayoutRect(p aintOffset + imageOffset, imageSize)), CompositeSourceOver, shouldRespectImageOr ientation());
322 errorPictureDrawn = true;
323 } 316 }
324 317
325 if (!m_altText.isEmpty()) { 318 if (!m_altText.isEmpty()) {
326 const Font& font = style()->font(); 319 const Font& font = style()->font();
327 const FontMetrics& fontMetrics = font.fontMetrics(); 320 const FontMetrics& fontMetrics = font.fontMetrics();
328 LayoutUnit ascent = fontMetrics.ascent(); 321 LayoutUnit ascent = fontMetrics.ascent();
329 LayoutPoint textRectOrigin = paintOffset; 322 LayoutPoint textRectOrigin = paintOffset;
330 textRectOrigin.move(leftBorder + leftPad + (paddingWidth / 2) - borderWidth, topBorder + topPad + (paddingHeight / 2) - borderWidth); 323 textRectOrigin.move(leftBorder + leftPad + (paddingWidth / 2) - borderWidth, topBorder + topPad + (paddingHeight / 2) - borderWidth);
331 LayoutPoint textOrigin(textRectOrigin.x(), textRectOrigin.y() + ascent); 324 LayoutPoint textOrigin(textRectOrigin.x(), textRectOrigin.y() + ascent);
332 325
333 // Only draw the alt text if it'll fit within the content box, 326 // Only draw the alt text if it'll fit within the content box,
334 // and only if it fits above the error image. 327 // and only if it fits above the error image.
335 TextRun textRun = constructTextRun(this, font, m_altText, style( ), TextRun::AllowTrailingExpansion | TextRun::ForbidLeadingExpansion, DefaultTex tRunFlags | RespectDirection); 328 TextRun textRun = constructTextRun(this, font, m_altText, style( ), TextRun::AllowTrailingExpansion | TextRun::ForbidLeadingExpansion, DefaultTex tRunFlags | RespectDirection);
336 float textWidth = font.width(textRun); 329 float textWidth = font.width(textRun);
337 TextRunPaintInfo textRunPaintInfo(textRun); 330 TextRunPaintInfo textRunPaintInfo(textRun);
338 textRunPaintInfo.bounds = FloatRect(textRectOrigin, FloatSize(te xtWidth, fontMetrics.height())); 331 textRunPaintInfo.bounds = FloatRect(textRectOrigin, FloatSize(te xtWidth, fontMetrics.height()));
339 context->setFillColor(resolveColor(CSSPropertyColor)); 332 context->setFillColor(resolveColor(CSSPropertyColor));
340 if (textRun.direction() == RTL) { 333 if (textRun.direction() == RTL) {
341 int availableWidth = cWidth - static_cast<int>(paddingWidth) ; 334 int availableWidth = cWidth - static_cast<int>(paddingWidth) ;
342 textOrigin.move(availableWidth - ceilf(textWidth), 0); 335 textOrigin.move(availableWidth - ceilf(textWidth), 0);
343 } 336 }
344 if (errorPictureDrawn) { 337 context->drawBidiText(font, textRunPaintInfo, textOrigin);
esprehn 2014/08/01 13:45:25 This won't wrap the text, so I think you're just g
345 if (usableWidth >= textWidth && fontMetrics.height() <= imag eOffset.height())
346 context->drawBidiText(font, textRunPaintInfo, textOrigin );
347 } else if (usableWidth >= textWidth && usableHeight >= fontMetri cs.height()) {
348 context->drawBidiText(font, textRunPaintInfo, textOrigin);
349 }
350 } 338 }
351 } 339 }
352 } else if (m_imageResource->hasImage() && cWidth > 0 && cHeight > 0) { 340 } else if (m_imageResource->hasImage() && cWidth > 0 && cHeight > 0) {
353 RefPtr<Image> img = m_imageResource->image(cWidth, cHeight); 341 RefPtr<Image> img = m_imageResource->image(cWidth, cHeight);
354 if (!img || img->isNull()) 342 if (!img || img->isNull())
355 return; 343 return;
356 344
357 LayoutRect contentRect = contentBoxRect(); 345 LayoutRect contentRect = contentBoxRect();
358 contentRect.moveBy(paintOffset); 346 contentRect.moveBy(paintOffset);
359 LayoutRect paintRect = replacedContentRect(); 347 LayoutRect paintRect = replacedContentRect();
(...skipping 262 matching lines...) Expand 10 before | Expand all | Expand 10 after
622 return 0; 610 return 0;
623 611
624 ImageResource* cachedImage = m_imageResource->cachedImage(); 612 ImageResource* cachedImage = m_imageResource->cachedImage();
625 if (cachedImage && cachedImage->image() && cachedImage->image()->isSVGImage( )) 613 if (cachedImage && cachedImage->image() && cachedImage->image()->isSVGImage( ))
626 return toSVGImage(cachedImage->image())->embeddedContentBox(); 614 return toSVGImage(cachedImage->image())->embeddedContentBox();
627 615
628 return 0; 616 return 0;
629 } 617 }
630 618
631 } // namespace blink 619 } // namespace blink
OLDNEW
« no previous file with comments | « LayoutTests/fast/forms/002-expected.png ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698