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

Side by Side Diff: src/core/SkCanvas.cpp

Issue 2224163005: Made shadows blurry (thru implementing variance mapping) (Closed) Base URL: https://skia.googlesource.com/skia@master
Patch Set: Moved SkShadowType to SkCanvas Created 4 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
OLDNEW
1 /* 1 /*
2 * Copyright 2008 The Android Open Source Project 2 * Copyright 2008 The Android Open Source Project
3 * 3 *
4 * Use of this source code is governed by a BSD-style license that can be 4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file. 5 * found in the LICENSE file.
6 */ 6 */
7 7
8 #include "SkBitmapDevice.h" 8 #include "SkBitmapDevice.h"
9 #include "SkBitmapProcShader.h"
9 #include "SkCanvas.h" 10 #include "SkCanvas.h"
10 #include "SkCanvasPriv.h" 11 #include "SkCanvasPriv.h"
11 #include "SkClipStack.h" 12 #include "SkClipStack.h"
12 #include "SkColorFilter.h" 13 #include "SkColorFilter.h"
13 #include "SkDraw.h" 14 #include "SkDraw.h"
14 #include "SkDrawable.h" 15 #include "SkDrawable.h"
robertphillips 2016/08/15 23:00:25 Why do we need GrDrawContext ? Or most of these n
vjiaoblack 2016/08/16 14:16:40 Done.
16 #include "GrDrawContext.h"
15 #include "SkDrawFilter.h" 17 #include "SkDrawFilter.h"
16 #include "SkDrawLooper.h" 18 #include "SkDrawLooper.h"
17 #include "SkErrorInternals.h" 19 #include "SkErrorInternals.h"
18 #include "SkImage.h" 20 #include "SkImage.h"
19 #include "SkImage_Base.h" 21 #include "SkImage_Base.h"
20 #include "SkImageFilter.h" 22 #include "SkImageFilter.h"
21 #include "SkImageFilterCache.h" 23 #include "SkImageFilterCache.h"
22 #include "SkLatticeIter.h" 24 #include "SkLatticeIter.h"
25 #include "SkLights.h"
26 #include "SkMatrix.h"
23 #include "SkMatrixUtils.h" 27 #include "SkMatrixUtils.h"
24 #include "SkMetaData.h" 28 #include "SkMetaData.h"
29 #include "SkNormalSource.h"
30 #include "SkPaintFilterCanvas.h"
25 #include "SkPaintPriv.h" 31 #include "SkPaintPriv.h"
26 #include "SkPatchUtils.h" 32 #include "SkPatchUtils.h"
27 #include "SkPicture.h" 33 #include "SkPicture.h"
34 #include "SkPictureRecorder.h"
28 #include "SkRasterClip.h" 35 #include "SkRasterClip.h"
29 #include "SkReadPixelsRec.h" 36 #include "SkReadPixelsRec.h"
30 #include "SkRRect.h" 37 #include "SkRRect.h"
31 #include "SkShadowPaintFilterCanvas.h" 38 #include "SkShadowPaintFilterCanvas.h"
32 #include "SkShadowShader.h" 39 #include "SkShadowShader.h"
33 #include "SkSmallAllocator.h" 40 #include "SkSmallAllocator.h"
34 #include "SkSpecialImage.h" 41 #include "SkSpecialImage.h"
42 #include "SkSurface.h"
35 #include "SkSurface_Base.h" 43 #include "SkSurface_Base.h"
36 #include "SkTextBlob.h" 44 #include "SkTextBlob.h"
37 #include "SkTextFormatParams.h" 45 #include "SkTextFormatParams.h"
38 #include "SkTLazy.h" 46 #include "SkTLazy.h"
39 #include "SkTraceEvent.h" 47 #include "SkTraceEvent.h"
40 48 #include "../../include/effects/SkBlurImageFilter.h"
41 #include <new> 49 #include <new>
42 50
43 #if SK_SUPPORT_GPU 51 #if SK_SUPPORT_GPU
44 #include "GrContext.h" 52 #include "GrContext.h"
45 #include "GrRenderTarget.h" 53 #include "GrRenderTarget.h"
46 #include "SkGrPriv.h" 54 #include "SkGrPriv.h"
55
47 #endif 56 #endif
48 57
49 #define RETURN_ON_NULL(ptr) do { if (nullptr == (ptr)) return; } while (0) 58 #define RETURN_ON_NULL(ptr) do { if (nullptr == (ptr)) return; } while (0)
50 59
51 //#define SK_SUPPORT_PRECHECK_CLIPRECT 60 //#define SK_SUPPORT_PRECHECK_CLIPRECT
52 61
53 /* 62 /*
54 * Return true if the drawing this rect would hit every pixels in the canvas. 63 * Return true if the drawing this rect would hit every pixels in the canvas.
55 * 64 *
56 * Returns false if 65 * Returns false if
(...skipping 2996 matching lines...) Expand 10 before | Expand all | Expand 10 after
3053 } 3062 }
3054 } 3063 }
3055 3064
3056 SkAutoCanvasMatrixPaint acmp(this, matrix, paint, picture->cullRect()); 3065 SkAutoCanvasMatrixPaint acmp(this, matrix, paint, picture->cullRect());
3057 picture->playback(this); 3066 picture->playback(this);
3058 } 3067 }
3059 3068
3060 #ifdef SK_EXPERIMENTAL_SHADOWING 3069 #ifdef SK_EXPERIMENTAL_SHADOWING
3061 void SkCanvas::drawShadowedPicture(const SkPicture* picture, 3070 void SkCanvas::drawShadowedPicture(const SkPicture* picture,
3062 const SkMatrix* matrix, 3071 const SkMatrix* matrix,
3063 const SkPaint* paint) { 3072 const SkPaint* paint,
3073 const SkShadowType& sType) {
3064 RETURN_ON_NULL(picture); 3074 RETURN_ON_NULL(picture);
3065 3075
3066 TRACE_EVENT0("disabled-by-default-skia", "SkCanvas::drawShadowedPicture()"); 3076 TRACE_EVENT0("disabled-by-default-skia", "SkCanvas::drawShadowedPicture()");
3067 3077
3068 this->onDrawShadowedPicture(picture, matrix, paint); 3078 this->onDrawShadowedPicture(picture, matrix, paint, sType);
3069 } 3079 }
3070 3080
3071 void SkCanvas::onDrawShadowedPicture(const SkPicture* picture, 3081 void SkCanvas::onDrawShadowedPicture(const SkPicture* picture,
3072 const SkMatrix* matrix, 3082 const SkMatrix* matrix,
3073 const SkPaint* paint) { 3083 const SkPaint* paint,
3084 const SkShadowType& sType) {
3074 if (!paint || paint->canComputeFastBounds()) { 3085 if (!paint || paint->canComputeFastBounds()) {
3075 SkRect bounds = picture->cullRect(); 3086 SkRect bounds = picture->cullRect();
3076 if (paint) { 3087 if (paint) {
3077 paint->computeFastBounds(bounds, &bounds); 3088 paint->computeFastBounds(bounds, &bounds);
3078 } 3089 }
3079 if (matrix) { 3090 if (matrix) {
3080 matrix->mapRect(&bounds); 3091 matrix->mapRect(&bounds);
3081 } 3092 }
3082 if (this->quickReject(bounds)) { 3093 if (this->quickReject(bounds)) {
3083 return; 3094 return;
3084 } 3095 }
3085 } 3096 }
3086 3097
3087 SkAutoCanvasMatrixPaint acmp(this, matrix, paint, picture->cullRect()); 3098 SkAutoCanvasMatrixPaint acmp(this, matrix, paint, picture->cullRect());
3088 3099
3100 sk_sp<SkImage> povDepthMap;
3101 sk_sp<SkImage> diffuseMap;
3102
3103 // TODO: pass the depth to the shader in vertices, or uniforms
3104 // so we don't have to render depth and color separately
3089 for (int i = 0; i < fLights->numLights(); ++i) { 3105 for (int i = 0; i < fLights->numLights(); ++i) {
3090 // skip over ambient lights; they don't cast shadows 3106 // skip over ambient lights; they don't cast shadows
3091 // lights that have shadow maps do not need updating (because lights are immutable) 3107 // lights that have shadow maps do not need updating (because lights are immutable)
3092 3108
3093 if (SkLights::Light::kAmbient_LightType == fLights->light(i).type() || 3109 if (SkLights::Light::kAmbient_LightType == fLights->light(i).type() ||
3094 fLights->light(i).getShadowMap() != nullptr) { 3110 fLights->light(i).getShadowMap() != nullptr) {
3095 continue; 3111 continue;
3096 } 3112 }
3097 3113
3098 // TODO: compute the correct size of the depth map from the light proper ties 3114 // TODO: compute the correct size of the depth map from the light proper ties
3099 // TODO: maybe add a kDepth_8_SkColorType 3115 // TODO: maybe add a kDepth_8_SkColorType
3100 // TODO: find actual max depth of picture 3116 // TODO: find actual max depth of picture
3101 SkISize shMapSize = SkShadowPaintFilterCanvas::ComputeDepthMapSize( 3117 SkISize shMapSize = SkShadowPaintFilterCanvas::ComputeDepthMapSize(
3102 fLights->light(i), 255, 3118 fLights->light(i), 255,
3103 picture->cullRect().width(), 3119 picture->cullRect().width(),
3104 picture->cullRect().height()); 3120 picture->cullRect().height());
3105 3121
3106 SkImageInfo info = SkImageInfo::Make(shMapSize.fWidth, shMapSize.fHeight , 3122 SkImageInfo info = SkImageInfo::Make(shMapSize.fWidth, shMapSize.fHeight ,
3107 kBGRA_8888_SkColorType, 3123 kBGRA_8888_SkColorType,
3108 kOpaque_SkAlphaType); 3124 kOpaque_SkAlphaType);
3109 3125
3110 // Create a new surface (that matches the backend of canvas) 3126 // Create a new surface (that matches the backend of canvas)
3111 // for each shadow map 3127 // for each shadow map
3112 sk_sp<SkSurface> surf(this->makeSurface(info)); 3128 sk_sp<SkSurface> surf(this->makeSurface(info));
3113 3129
3114 // Wrap another SPFCanvas around the surface 3130 // Wrap another SPFCanvas around the surface
3115 sk_sp<SkShadowPaintFilterCanvas> depthMapCanvas = 3131 sk_sp<SkShadowPaintFilterCanvas> depthMapCanvas =
3116 sk_make_sp<SkShadowPaintFilterCanvas>(surf->getCanvas()); 3132 sk_make_sp<SkShadowPaintFilterCanvas>(surf->getCanvas());
3133 depthMapCanvas->setShadowType(sType);
3117 3134
3118 // set the depth map canvas to have the light we're drawing. 3135 // set the depth map canvas to have the light we're drawing.
3119 SkLights::Builder builder; 3136 SkLights::Builder builder;
3120 builder.add(fLights->light(i)); 3137 builder.add(fLights->light(i));
3121 sk_sp<SkLights> curLight = builder.finish(); 3138 sk_sp<SkLights> curLight = builder.finish();
robertphillips 2016/08/15 23:00:25 why rm the std::move ?
vjiaoblack 2016/08/16 14:16:40 Done.
3139 depthMapCanvas->setLights(curLight);
3122 3140
3123 depthMapCanvas->setLights(std::move(curLight));
3124 depthMapCanvas->drawPicture(picture); 3141 depthMapCanvas->drawPicture(picture);
3142 sk_sp<SkImage> depthMap = surf->makeImageSnapshot();
3125 3143
3126 fLights->light(i).setShadowMap(surf->makeImageSnapshot()); 3144 // we blur the variance map
3145 SkPaint blurPaint;
robertphillips 2016/08/15 23:00:25 For no blur we shouldn't be doing the draw at all
vjiaoblack 2016/08/16 14:16:40 True. Done.
3146 if (sType.fBlurAlgorithm != SkShadowType::kNoBlur_BlurAlgorithm) {
3147 blurPaint.setImageFilter(SkBlurImageFilter::Make(sType.fShadowRadius ,
3148 sType.fShadowRadius , nullptr));
3149 }
3150
3151 SkImageInfo blurInfo = SkImageInfo::Make(shMapSize.fWidth, shMapSize.fHe ight,
3152 kBGRA_8888_SkColorType,
3153 kOpaque_SkAlphaType);
3154
3155 sk_sp<SkSurface> blurSurf(this->makeSurface(blurInfo));
3156 sk_sp<SkCanvas> blurDepthMapCanvas = sk_ref_sp(blurSurf->getCanvas());
3157
3158 blurDepthMapCanvas->drawImage(depthMap, 0, 0, &blurPaint);
3159
3160 fLights->light(i).setShadowMap(blurSurf->makeImageSnapshot());
3127 } 3161 }
3128 3162
3129 sk_sp<SkImage> povDepthMap;
3130 sk_sp<SkImage> diffuseMap;
3131
3132 // TODO: pass the depth to the shader in vertices, or uniforms
3133 // so we don't have to render depth and color separately
3134
3135 // povDepthMap 3163 // povDepthMap
3136 { 3164 {
3137 SkLights::Builder builder; 3165 SkLights::Builder builder;
3138 builder.add(SkLights::Light(SkColor3f::Make(1.0f, 1.0f, 1.0f), 3166 builder.add(SkLights::Light(SkColor3f::Make(1.0f, 1.0f, 1.0f),
3139 SkVector3::Make(0.0f, 0.0f, 1.0f))); 3167 SkVector3::Make(0.0f, 0.0f, 1.0f)));
3140 sk_sp<SkLights> povLight = builder.finish(); 3168 sk_sp<SkLights> povLight = builder.finish();
3141 3169
3142 SkImageInfo info = SkImageInfo::Make(picture->cullRect().width(), 3170 SkImageInfo info = SkImageInfo::Make(picture->cullRect().width(),
3143 picture->cullRect().height(), 3171 picture->cullRect().height(),
3144 kBGRA_8888_SkColorType, 3172 kBGRA_8888_SkColorType,
3145 kOpaque_SkAlphaType); 3173 kOpaque_SkAlphaType);
3146 3174
3147 // Create a new surface (that matches the backend of canvas) 3175 // Create a new surface (that matches the backend of canvas)
3148 // to create the povDepthMap 3176 // to create the povDepthMap
3149 sk_sp<SkSurface> surf(this->makeSurface(info)); 3177 sk_sp<SkSurface> surf(this->makeSurface(info));
3150 3178
3151 // Wrap another SPFCanvas around the surface 3179 // Wrap another SPFCanvas around the surface
3152 sk_sp<SkShadowPaintFilterCanvas> depthMapCanvas = 3180 sk_sp<SkShadowPaintFilterCanvas> depthMapCanvas =
3153 sk_make_sp<SkShadowPaintFilterCanvas>(surf->getCanvas()); 3181 sk_make_sp<SkShadowPaintFilterCanvas>(surf->getCanvas());
3154 3182
3155 // set the depth map canvas to have the light as the user's POV 3183 // set the depth map canvas to have the light as the user's POV
3156 depthMapCanvas->setLights(std::move(povLight)); 3184 depthMapCanvas->setLights(std::move(povLight));
3157 3185
3158 depthMapCanvas->drawPicture(picture); 3186 depthMapCanvas->drawPicture(picture);
3159
3160 povDepthMap = surf->makeImageSnapshot(); 3187 povDepthMap = surf->makeImageSnapshot();
3161 } 3188 }
3162 3189
3163 // diffuseMap 3190 // diffuseMap
3164 { 3191 {
3165 SkImageInfo info = SkImageInfo::Make(picture->cullRect().width(), 3192 SkImageInfo info = SkImageInfo::Make(picture->cullRect().width(),
3166 picture->cullRect().height(), 3193 picture->cullRect().height(),
3167 kBGRA_8888_SkColorType, 3194 kBGRA_8888_SkColorType,
3168 kOpaque_SkAlphaType); 3195 kOpaque_SkAlphaType);
3169 3196
3170 sk_sp<SkSurface> surf(this->makeSurface(info)); 3197 sk_sp<SkSurface> surf(this->makeSurface(info));
3171 surf->getCanvas()->drawPicture(picture); 3198 surf->getCanvas()->drawPicture(picture);
3172 3199
3173 diffuseMap = surf->makeImageSnapshot(); 3200 diffuseMap = surf->makeImageSnapshot();
3174 } 3201 }
3175
3176 SkPaint shadowPaint; 3202 SkPaint shadowPaint;
3177 3203
3178 sk_sp<SkShader> povDepthShader = povDepthMap->makeShader(SkShader::kClamp_Ti leMode, 3204 sk_sp<SkShader> povDepthShader = povDepthMap->makeShader(SkShader::kClamp_Ti leMode,
3179 SkShader::kClamp_Ti leMode); 3205 SkShader::kClamp_Ti leMode);
3180
3181 sk_sp<SkShader> diffuseShader = diffuseMap->makeShader(SkShader::kClamp_Tile Mode, 3206 sk_sp<SkShader> diffuseShader = diffuseMap->makeShader(SkShader::kClamp_Tile Mode,
3182 SkShader::kClamp_Tile Mode); 3207 SkShader::kClamp_Tile Mode);
3183
3184 sk_sp<SkShader> shadowShader = SkShadowShader::Make(std::move(povDepthShader ), 3208 sk_sp<SkShader> shadowShader = SkShadowShader::Make(std::move(povDepthShader ),
3185 std::move(diffuseShader) , 3209 std::move(diffuseShader) ,
3186 std::move(fLights), 3210 std::move(fLights),
3187 diffuseMap->width(), 3211 diffuseMap->width(),
3188 diffuseMap->height()); 3212 diffuseMap->height(),
3213 sType);
3189 3214
3190 shadowPaint.setShader(shadowShader); 3215 shadowPaint.setShader(shadowShader);
3191 3216
3192 this->drawRect(SkRect::MakeIWH(diffuseMap->width(), diffuseMap->height()), s hadowPaint); 3217 this->drawRect(SkRect::MakeIWH(diffuseMap->width(), diffuseMap->height()), s hadowPaint);
3193 } 3218 }
3194 #endif 3219 #endif
3195 3220
3196 /////////////////////////////////////////////////////////////////////////////// 3221 ///////////////////////////////////////////////////////////////////////////////
3197 /////////////////////////////////////////////////////////////////////////////// 3222 ///////////////////////////////////////////////////////////////////////////////
3198 3223
(...skipping 97 matching lines...) Expand 10 before | Expand all | Expand 10 after
3296 3321
3297 SkAutoCanvasMatrixPaint::~SkAutoCanvasMatrixPaint() { 3322 SkAutoCanvasMatrixPaint::~SkAutoCanvasMatrixPaint() {
3298 fCanvas->restoreToCount(fSaveCount); 3323 fCanvas->restoreToCount(fSaveCount);
3299 } 3324 }
3300 3325
3301 #ifdef SK_SUPPORT_LEGACY_NEW_SURFACE_API 3326 #ifdef SK_SUPPORT_LEGACY_NEW_SURFACE_API
3302 SkSurface* SkCanvas::newSurface(const SkImageInfo& info, const SkSurfaceProps* p rops) { 3327 SkSurface* SkCanvas::newSurface(const SkImageInfo& info, const SkSurfaceProps* p rops) {
3303 return this->makeSurface(info, props).release(); 3328 return this->makeSurface(info, props).release();
3304 } 3329 }
3305 #endif 3330 #endif
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698