| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright (C) 2006 Samuel Weinig (sam.weinig@gmail.com) | 2 * Copyright (C) 2006 Samuel Weinig (sam.weinig@gmail.com) |
| 3 * Copyright (C) 2004, 2005, 2006 Apple Computer, Inc. All rights reserved. | 3 * Copyright (C) 2004, 2005, 2006 Apple Computer, Inc. All rights reserved. |
| 4 * | 4 * |
| 5 * Redistribution and use in source and binary forms, with or without | 5 * Redistribution and use in source and binary forms, with or without |
| 6 * modification, are permitted provided that the following conditions | 6 * modification, are permitted provided that the following conditions |
| 7 * are met: | 7 * are met: |
| 8 * 1. Redistributions of source code must retain the above copyright | 8 * 1. Redistributions of source code must retain the above copyright |
| 9 * notice, this list of conditions and the following disclaimer. | 9 * notice, this list of conditions and the following disclaimer. |
| 10 * 2. Redistributions in binary form must reproduce the above copyright | 10 * 2. Redistributions in binary form must reproduce the above copyright |
| (...skipping 18 matching lines...) Expand all Loading... |
| 29 #include "platform/Length.h" | 29 #include "platform/Length.h" |
| 30 #include "platform/MIMETypeRegistry.h" | 30 #include "platform/MIMETypeRegistry.h" |
| 31 #include "platform/PlatformInstrumentation.h" | 31 #include "platform/PlatformInstrumentation.h" |
| 32 #include "platform/RuntimeEnabledFeatures.h" | 32 #include "platform/RuntimeEnabledFeatures.h" |
| 33 #include "platform/SharedBuffer.h" | 33 #include "platform/SharedBuffer.h" |
| 34 #include "platform/TraceEvent.h" | 34 #include "platform/TraceEvent.h" |
| 35 #include "platform/geometry/FloatPoint.h" | 35 #include "platform/geometry/FloatPoint.h" |
| 36 #include "platform/geometry/FloatRect.h" | 36 #include "platform/geometry/FloatRect.h" |
| 37 #include "platform/geometry/FloatSize.h" | 37 #include "platform/geometry/FloatSize.h" |
| 38 #include "platform/graphics/BitmapImage.h" | 38 #include "platform/graphics/BitmapImage.h" |
| 39 #include "platform/graphics/ColorSpaceFilter.h" |
| 40 #include "platform/graphics/ColorSpaceProfile.h" |
| 39 #include "platform/graphics/DeferredImageDecoder.h" | 41 #include "platform/graphics/DeferredImageDecoder.h" |
| 40 #include "platform/graphics/GraphicsContext.h" | 42 #include "platform/graphics/GraphicsContext.h" |
| 43 #include "platform/graphics/GraphicsScreen.h" |
| 41 #include "public/platform/Platform.h" | 44 #include "public/platform/Platform.h" |
| 42 #include "public/platform/WebData.h" | 45 #include "public/platform/WebData.h" |
| 43 #include "third_party/skia/include/core/SkCanvas.h" | 46 #include "third_party/skia/include/core/SkCanvas.h" |
| 44 #include "third_party/skia/include/core/SkImage.h" | 47 #include "third_party/skia/include/core/SkImage.h" |
| 45 #include "third_party/skia/include/core/SkPictureRecorder.h" | 48 #include "third_party/skia/include/core/SkPictureRecorder.h" |
| 46 #include "wtf/MainThread.h" | 49 #include "wtf/MainThread.h" |
| 47 #include "wtf/StdLibExtras.h" | 50 #include "wtf/StdLibExtras.h" |
| 48 | 51 |
| 49 #include <math.h> | 52 #include <math.h> |
| 50 | 53 |
| (...skipping 125 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 176 ctxt.setImageInterpolationQuality(InterpolationLow); | 179 ctxt.setImageInterpolationQuality(InterpolationLow); |
| 177 drawPattern(ctxt, srcRect, tileScaleFactor, patternPhase, op, dstRect); | 180 drawPattern(ctxt, srcRect, tileScaleFactor, patternPhase, op, dstRect); |
| 178 ctxt.setImageInterpolationQuality(previousInterpolationQuality); | 181 ctxt.setImageInterpolationQuality(previousInterpolationQuality); |
| 179 } else { | 182 } else { |
| 180 drawPattern(ctxt, srcRect, tileScaleFactor, patternPhase, op, dstRect); | 183 drawPattern(ctxt, srcRect, tileScaleFactor, patternPhase, op, dstRect); |
| 181 } | 184 } |
| 182 | 185 |
| 183 startAnimation(); | 186 startAnimation(); |
| 184 } | 187 } |
| 185 | 188 |
| 186 namespace { | 189 static PassRefPtr<SkShader> createPatternShader(const SkImage* image, SkPaint* p
aint, const SkMatrix& shaderMatrix, const FloatSize& spacing) |
| 187 | |
| 188 PassRefPtr<SkShader> createPatternShader(const SkImage* image, const SkMatrix& s
haderMatrix, | |
| 189 const SkPaint& paint, const FloatSize& spacing) | |
| 190 { | 190 { |
| 191 if (spacing.isZero()) | 191 if (spacing.isZero()) |
| 192 return adoptRef(image->newShader(SkShader::kRepeat_TileMode, SkShader::k
Repeat_TileMode, &shaderMatrix)); | 192 return adoptRef(image->newShader(SkShader::kRepeat_TileMode, SkShader::k
Repeat_TileMode, &shaderMatrix)); |
| 193 | 193 |
| 194 // Arbitrary tiling is currently only supported for SkPictureShader - so we
use it instead | 194 // Arbitrary tiling is currently only supported for SkPictureShader so use i
t, instead |
| 195 // of a plain bitmap shader to implement spacing. | 195 // of a plain bitmap shader, to implement spacing (CSS background-repeat: sp
ace). |
| 196 const SkRect tileRect = SkRect::MakeWH( | 196 SkRect tileRect = SkRect::MakeWH(image->width() + spacing.width(), image->he
ight() + spacing.height()); |
| 197 image->width() + spacing.width(), | |
| 198 image->height() + spacing.height()); | |
| 199 | 197 |
| 200 SkPictureRecorder recorder; | 198 SkPictureRecorder recorder; |
| 201 SkCanvas* canvas = recorder.beginRecording(tileRect); | 199 SkCanvas* canvas = recorder.beginRecording(tileRect); |
| 202 canvas->drawImage(image, 0, 0, &paint); | 200 canvas->drawImage(image, 0, 0, paint); |
| 203 RefPtr<const SkPicture> picture = adoptRef(recorder.endRecordingAsPicture())
; | 201 RefPtr<const SkPicture> picture = adoptRef(recorder.endRecordingAsPicture())
; |
| 204 | 202 |
| 205 return adoptRef(SkShader::CreatePictureShader( | 203 // Remove any color filter from callers paint: it is applied when drawing th
e SkPicture |
| 206 picture.get(), SkShader::kRepeat_TileMode, SkShader::kRepeat_TileMode, &
shaderMatrix, nullptr)); | 204 // shader: clearing it here prevents caller from applying the filter twice. |
| 205 paint->setColorFilter(nullptr); |
| 206 |
| 207 return adoptRef(SkShader::CreatePictureShader(picture.get(), SkShader::kRepe
at_TileMode, SkShader::kRepeat_TileMode, &shaderMatrix, nullptr)); |
| 207 } | 208 } |
| 208 | 209 |
| 209 } // anonymous namespace | |
| 210 | |
| 211 void Image::drawPattern(GraphicsContext& context, const FloatRect& floatSrcRect,
const FloatSize& scale, | 210 void Image::drawPattern(GraphicsContext& context, const FloatRect& floatSrcRect,
const FloatSize& scale, |
| 212 const FloatPoint& phase, SkXfermode::Mode compositeOp, const FloatRect& dest
Rect, const FloatSize& repeatSpacing) | 211 const FloatPoint& phase, SkXfermode::Mode compositeOp, const FloatRect& dest
Rect, const FloatSize& repeatSpacing) |
| 213 { | 212 { |
| 214 TRACE_EVENT0("skia", "Image::drawPattern"); | 213 TRACE_EVENT0("skia", "Image::drawPattern"); |
| 215 | 214 |
| 216 RefPtr<SkImage> image = imageForCurrentFrame(); | 215 RefPtr<SkImage> image = imageForCurrentFrame(); |
| 217 if (!image) | 216 if (!image) |
| 218 return; | 217 return; |
| 219 | 218 |
| 220 FloatRect normSrcRect = floatSrcRect; | 219 FloatRect normSrcRect = floatSrcRect; |
| 221 | |
| 222 normSrcRect.intersect(FloatRect(0, 0, image->width(), image->height())); | 220 normSrcRect.intersect(FloatRect(0, 0, image->width(), image->height())); |
| 223 if (destRect.isEmpty() || normSrcRect.isEmpty()) | 221 if (destRect.isEmpty() || normSrcRect.isEmpty()) |
| 224 return; // nothing to draw | 222 return; // nothing to draw |
| 225 | 223 |
| 226 SkMatrix localMatrix; | 224 SkMatrix localMatrix; |
| 227 // We also need to translate it such that the origin of the pattern is the | 225 // We also need to translate it such that the origin of the pattern is the |
| 228 // origin of the destination rect, which is what WebKit expects. Skia uses | 226 // origin of the destination rect, which is what WebKit expects. Skia uses |
| 229 // the coordinate system origin as the base for the pattern. If WebKit wants | 227 // the coordinate system origin as the base for the pattern. If WebKit wants |
| 230 // a shifted image, it will shift it from there using the localMatrix. | 228 // a shifted image, it will shift it from there using the localMatrix. |
| 231 const float adjustedX = phase.x() + normSrcRect.x() * scale.width(); | 229 const float adjustedX = phase.x() + normSrcRect.x() * scale.width(); |
| 232 const float adjustedY = phase.y() + normSrcRect.y() * scale.height(); | 230 const float adjustedY = phase.y() + normSrcRect.y() * scale.height(); |
| 233 localMatrix.setTranslate(SkFloatToScalar(adjustedX), SkFloatToScalar(adjuste
dY)); | 231 localMatrix.setTranslate(SkFloatToScalar(adjustedX), SkFloatToScalar(adjuste
dY)); |
| 234 | 232 |
| 235 // Because no resizing occurred, the shader transform should be | 233 // Because no resizing occurred, the shader transform should be |
| 236 // set to the pattern's transform, which just includes scale. | 234 // set to the pattern's transform, which just includes scale. |
| 237 localMatrix.preScale(scale.width(), scale.height()); | 235 localMatrix.preScale(scale.width(), scale.height()); |
| 238 | 236 |
| 239 // Fetch this now as subsetting may swap the image. | 237 // Fetch the image ID now since subsetting and/or the application of color |
| 238 // transforms may swap out the image. |
| 240 auto imageID = image->uniqueID(); | 239 auto imageID = image->uniqueID(); |
| 241 | 240 |
| 241 if (imageColorProfilesEnabled() && this->isBitmapImage()) |
| 242 image = toBitmapImage(this)->pictureForCurrentFrame(); |
| 243 |
| 242 image = adoptRef(image->newSubset(enclosingIntRect(normSrcRect))); | 244 image = adoptRef(image->newSubset(enclosingIntRect(normSrcRect))); |
| 243 if (!image) | 245 if (!image) |
| 244 return; | 246 return; |
| 245 | 247 |
| 246 { | 248 SkPaint paint = context.fillPaint(); |
| 247 SkPaint paint = context.fillPaint(); | 249 paint.setColor(SK_ColorBLACK); // FIXME: not color correct. |
| 248 paint.setColor(SK_ColorBLACK); | 250 paint.setXfermodeMode(compositeOp); |
| 249 paint.setXfermodeMode(compositeOp); | 251 paint.setFilterQuality(context.computeFilterQuality(this, destRect, normSrcR
ect)); |
| 250 paint.setFilterQuality(context.computeFilterQuality(this, destRect, norm
SrcRect)); | 252 paint.setAntiAlias(context.shouldAntialias()); |
| 251 paint.setAntiAlias(context.shouldAntialias()); | 253 |
| 252 RefPtr<SkShader> shader = createPatternShader(image.get(), localMatrix,
paint, | 254 FloatSize spacing = FloatSize(repeatSpacing.width() / scale.width(), repeatS
pacing.height() / scale.height()); |
| 253 FloatSize(repeatSpacing.width() / scale.width(), repeatSpacing.heigh
t() / scale.height())); | 255 RefPtr<SkShader> shader = createPatternShader(image.get(), &paint, localMatr
ix, spacing); |
| 254 paint.setShader(shader.get()); | 256 paint.setShader(shader.get()); |
| 255 context.drawRect(destRect, paint); | 257 |
| 256 } | 258 context.drawRect(destRect, paint); |
| 257 | 259 |
| 258 if (currentFrameIsLazyDecoded()) | 260 if (currentFrameIsLazyDecoded()) |
| 259 PlatformInstrumentation::didDrawLazyPixelRef(imageID); | 261 PlatformInstrumentation::didDrawLazyPixelRef(imageID); |
| 260 } | 262 } |
| 261 | 263 |
| 262 void Image::computeIntrinsicDimensions(Length& intrinsicWidth, Length& intrinsic
Height, FloatSize& intrinsicRatio) | 264 void Image::computeIntrinsicDimensions(Length& intrinsicWidth, Length& intrinsic
Height, FloatSize& intrinsicRatio) |
| 263 { | 265 { |
| 264 intrinsicRatio = FloatSize(size()); | 266 intrinsicRatio = FloatSize(size()); |
| 265 intrinsicWidth = Length(intrinsicRatio.width(), Fixed); | 267 intrinsicWidth = Length(intrinsicRatio.width(), Fixed); |
| 266 intrinsicHeight = Length(intrinsicRatio.height(), Fixed); | 268 intrinsicHeight = Length(intrinsicRatio.height(), Fixed); |
| 267 } | 269 } |
| 268 | 270 |
| 269 PassRefPtr<Image> Image::imageForDefaultFrame() | 271 PassRefPtr<Image> Image::imageForDefaultFrame() |
| 270 { | 272 { |
| 271 RefPtr<Image> image(this); | 273 RefPtr<Image> image(this); |
| 272 | 274 |
| 273 return image.release(); | 275 return image.release(); |
| 274 } | 276 } |
| 275 | 277 |
| 276 bool Image::isTextureBacked() | 278 bool Image::isTextureBacked() |
| 277 { | 279 { |
| 278 RefPtr<SkImage> image = imageForCurrentFrame(); | 280 RefPtr<SkImage> image = imageForCurrentFrame(); |
| 279 return image ? image->isTextureBacked() : false; | 281 return image ? image->isTextureBacked() : false; |
| 280 } | 282 } |
| 281 | 283 |
| 282 } // namespace blink | 284 } // namespace blink |
| OLD | NEW |