Index: Source/platform/graphics/skia/NativeImageSkia.cpp |
diff --git a/Source/platform/graphics/skia/NativeImageSkia.cpp b/Source/platform/graphics/skia/NativeImageSkia.cpp |
index 344cf729c59a2b2695da75859acba7a6e66294b3..f0db318605e4ca49e68ed556d327cfceab3492e5 100644 |
--- a/Source/platform/graphics/skia/NativeImageSkia.cpp |
+++ b/Source/platform/graphics/skia/NativeImageSkia.cpp |
@@ -46,6 +46,7 @@ |
#include "third_party/skia/include/core/SkScalar.h" |
#include "third_party/skia/include/core/SkShader.h" |
+#include <algorithm> |
#include <math.h> |
#include <limits> |
@@ -56,7 +57,7 @@ static bool nearlyIntegral(float value) |
return fabs(value - floorf(value)) < std::numeric_limits<float>::epsilon(); |
} |
-ResamplingMode NativeImageSkia::computeResamplingMode(const SkMatrix& matrix, float srcWidth, float srcHeight, float destWidth, float destHeight) const |
+InterpolationQuality NativeImageSkia::computeInterpolationQuality(const SkMatrix& matrix, float srcWidth, float srcHeight, float destWidth, float destHeight) const |
{ |
// The percent change below which we will not resample. This usually means |
// an off-by-one error on the web page, and just doing nearest neighbor |
@@ -81,7 +82,7 @@ ResamplingMode NativeImageSkia::computeResamplingMode(const SkMatrix& matrix, fl |
bool heightNearlyEqual = diffHeight < std::numeric_limits<float>::epsilon(); |
// We don't need to resample if the source and destination are the same. |
if (widthNearlyEqual && heightNearlyEqual) |
- return NoResampling; |
+ return InterpolationNone; |
if (srcWidth <= kSmallImageSizeThreshold |
|| srcHeight <= kSmallImageSizeThreshold |
@@ -94,11 +95,11 @@ ResamplingMode NativeImageSkia::computeResamplingMode(const SkMatrix& matrix, fl |
// when the source image is only one pixel wide in that dimension. |
if ((!nearlyIntegral(destWidth) && srcWidth > 1 + std::numeric_limits<float>::epsilon()) |
|| (!nearlyIntegral(destHeight) && srcHeight > 1 + std::numeric_limits<float>::epsilon())) |
- return LinearResampling; |
+ return InterpolationLow; |
// Otherwise, don't resample small images. These are often used for |
// borders and rules (think 1x1 images used to make lines). |
- return NoResampling; |
+ return InterpolationNone; |
} |
if (srcHeight * kLargeStretch <= destHeight || srcWidth * kLargeStretch <= destWidth) { |
@@ -109,11 +110,11 @@ ResamplingMode NativeImageSkia::computeResamplingMode(const SkMatrix& matrix, fl |
// (which might be large) and then is stretching it to fill some part |
// of the page. |
if (widthNearlyEqual || heightNearlyEqual) |
- return NoResampling; |
+ return InterpolationNone; |
// The image is growing a lot and in more than one direction. Resampling |
// is slow and doesn't give us very much when growing a lot. |
- return LinearResampling; |
+ return InterpolationLow; |
} |
if ((diffWidth / srcWidth < kFractionalChangeThreshold) |
@@ -121,59 +122,40 @@ ResamplingMode NativeImageSkia::computeResamplingMode(const SkMatrix& matrix, fl |
// It is disappointingly common on the web for image sizes to be off by |
// one or two pixels. We don't bother resampling if the size difference |
// is a small fraction of the original size. |
- return NoResampling; |
+ return InterpolationNone; |
} |
// When the image is not yet done loading, use linear. We don't cache the |
// partially resampled images, and as they come in incrementally, it causes |
// us to have to resample the whole thing every time. |
if (!isDataComplete()) |
- return LinearResampling; |
+ return InterpolationLow; |
// Everything else gets resampled. |
// High quality interpolation only enabled for scaling and translation. |
if (!(matrix.getType() & (SkMatrix::kAffine_Mask | SkMatrix::kPerspective_Mask))) |
- return AwesomeResampling; |
+ return InterpolationHigh; |
- return LinearResampling; |
+ return InterpolationLow; |
} |
-static ResamplingMode limitResamplingMode(GraphicsContext* context, ResamplingMode resampling) |
+static InterpolationQuality limitInterpolationQuality(GraphicsContext* context, InterpolationQuality resampling) |
{ |
- switch (context->imageInterpolationQuality()) { |
- case InterpolationNone: |
- return NoResampling; |
- case InterpolationMedium: |
- if (resampling == AwesomeResampling) |
- return LinearWithMipmapsResampling; |
- break; |
- case InterpolationLow: |
- if (resampling == AwesomeResampling || resampling == LinearWithMipmapsResampling) |
- return LinearResampling; |
- break; |
- case InterpolationHigh: |
- break; |
- } |
- |
- return resampling; |
+ return std::min(resampling, context->imageInterpolationQuality()); |
} |
-static SkPaint::FilterLevel convertToSkiaFilterLevel(bool useBicubicFilter, ResamplingMode resampling) |
+static SkPaint::FilterLevel convertToSkiaFilterLevel(bool useBicubicFilter, InterpolationQuality resampling) |
{ |
+ // FIXME: If we get rid of this special case, this function can go away entirely. |
if (useBicubicFilter) |
return SkPaint::kHigh_FilterLevel; |
- switch (resampling) { |
- case LinearWithMipmapsResampling: |
- return SkPaint::kMedium_FilterLevel; |
- case LinearResampling: |
- return SkPaint::kLow_FilterLevel; |
- // AwesomeResampling if useBicubicFilter is false means that we do |
+ // InterpolationHigh if useBicubicFilter is false means that we do |
// a manual high quality resampling before drawing to Skia. |
- case AwesomeResampling: |
- default: |
+ if (resampling == InterpolationHigh) |
return SkPaint::kNone_FilterLevel; |
- } |
+ |
+ return static_cast<SkPaint::FilterLevel>(resampling); |
} |
// This function is used to scale an image and extract a scaled fragment. |
@@ -377,13 +359,13 @@ void NativeImageSkia::draw(GraphicsContext* context, const SkRect& srcRect, cons |
bool isLazyDecoded = DeferredImageDecoder::isLazyDecoded(bitmap()); |
- ResamplingMode resampling; |
+ InterpolationQuality resampling; |
if (context->isAccelerated()) { |
- resampling = LinearResampling; |
+ resampling = InterpolationLow; |
} else if (context->printing()) { |
- resampling = NoResampling; |
+ resampling = InterpolationNone; |
} else if (isLazyDecoded) { |
- resampling = AwesomeResampling; |
+ resampling = InterpolationHigh; |
} else { |
// Take into account scale applied to the canvas when computing sampling mode (e.g. CSS scale or page scale). |
SkRect destRectTarget = destRect; |
@@ -391,27 +373,27 @@ void NativeImageSkia::draw(GraphicsContext* context, const SkRect& srcRect, cons |
if (!(totalMatrix.getType() & (SkMatrix::kAffine_Mask | SkMatrix::kPerspective_Mask))) |
totalMatrix.mapRect(&destRectTarget, destRect); |
- resampling = computeResamplingMode(totalMatrix, |
+ resampling = computeInterpolationQuality(totalMatrix, |
SkScalarToFloat(srcRect.width()), SkScalarToFloat(srcRect.height()), |
SkScalarToFloat(destRectTarget.width()), SkScalarToFloat(destRectTarget.height())); |
} |
- if (resampling == NoResampling) { |
+ if (resampling == InterpolationNone) { |
// FIXME: This is to not break tests (it results in the filter bitmap flag |
- // being set to true). We need to decide if we respect NoResampling |
- // being returned from computeResamplingMode. |
- resampling = LinearResampling; |
+ // being set to true). We need to decide if we respect InterpolationNone |
+ // being returned from computeInterpolationQuality. |
+ resampling = InterpolationLow; |
} |
- resampling = limitResamplingMode(context, resampling); |
+ resampling = limitInterpolationQuality(context, resampling); |
// FIXME: Bicubic filtering in Skia is only applied to defer-decoded images |
// as an experiment. Once this filtering code path becomes stable we should |
// turn this on for all cases, including non-defer-decoded images. |
- bool useBicubicFilter = resampling == AwesomeResampling && isLazyDecoded; |
+ bool useBicubicFilter = resampling == InterpolationHigh && isLazyDecoded; |
paint.setFilterLevel(convertToSkiaFilterLevel(useBicubicFilter, resampling)); |
- if (resampling == AwesomeResampling && !useBicubicFilter) { |
+ if (resampling == InterpolationHigh && !useBicubicFilter) { |
// Resample the image and then draw the result to canvas with bilinear |
// filtering. |
drawResampledBitmap(context, paint, srcRect, destRect); |
@@ -475,14 +457,14 @@ void NativeImageSkia::drawPattern( |
bool isLazyDecoded = DeferredImageDecoder::isLazyDecoded(bitmap()); |
// Compute the resampling mode. |
- ResamplingMode resampling; |
+ InterpolationQuality resampling; |
if (context->isAccelerated() || context->printing()) |
- resampling = LinearResampling; |
+ resampling = InterpolationLow; |
else if (isLazyDecoded) |
- resampling = AwesomeResampling; |
+ resampling = InterpolationHigh; |
else |
- resampling = computeResamplingMode(totalMatrix, normSrcRect.width(), normSrcRect.height(), destBitmapWidth, destBitmapHeight); |
- resampling = limitResamplingMode(context, resampling); |
+ resampling = computeInterpolationQuality(totalMatrix, normSrcRect.width(), normSrcRect.height(), destBitmapWidth, destBitmapHeight); |
+ resampling = limitInterpolationQuality(context, resampling); |
SkMatrix localMatrix; |
// We also need to translate it such that the origin of the pattern is the |
@@ -497,9 +479,9 @@ void NativeImageSkia::drawPattern( |
// Bicubic filter is only applied to defer-decoded images, see |
// NativeImageSkia::draw for details. |
- bool useBicubicFilter = resampling == AwesomeResampling && isLazyDecoded; |
+ bool useBicubicFilter = resampling == InterpolationHigh && isLazyDecoded; |
- if (resampling == AwesomeResampling && !useBicubicFilter) { |
+ if (resampling == InterpolationHigh && !useBicubicFilter) { |
// Do nice resampling. |
float scaleX = destBitmapWidth / normSrcRect.width(); |
float scaleY = destBitmapHeight / normSrcRect.height(); |