1 /*
2  * Copyright (C) 2016 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #pragma once
18 
19 #include <SkSurface.h>
20 #include "Lighting.h"
21 #include "hwui/AnimatedImageDrawable.h"
22 #include "renderthread/CanvasContext.h"
23 #include "renderthread/IRenderPipeline.h"
24 
25 class SkPictureRecorder;
26 
27 namespace android {
28 namespace uirenderer {
29 namespace skiapipeline {
30 
31 class SkiaPipeline : public renderthread::IRenderPipeline {
32 public:
33     explicit SkiaPipeline(renderthread::RenderThread& thread);
34     virtual ~SkiaPipeline();
35 
36     void onDestroyHardwareResources() override;
37 
38     bool pinImages(std::vector<SkImage*>& mutableImages) override;
pinImages(LsaVector<sk_sp<Bitmap>> & images)39     bool pinImages(LsaVector<sk_sp<Bitmap>>& images) override { return false; }
40     void unpinImages() override;
41     void onPrepareTree() override;
42 
43     void renderLayers(const LightGeometry& lightGeometry, LayerUpdateQueue* layerUpdateQueue,
44                       bool opaque, const LightInfo& lightInfo) override;
45 
46     bool createOrUpdateLayer(RenderNode* node, const DamageAccumulator& damageAccumulator,
47                              ErrorHandler* errorHandler) override;
48 
getSurfaceColorType()49     SkColorType getSurfaceColorType() const override { return mSurfaceColorType; }
getSurfaceColorSpace()50     sk_sp<SkColorSpace> getSurfaceColorSpace() override { return mSurfaceColorSpace; }
51 
52     void renderFrame(const LayerUpdateQueue& layers, const SkRect& clip,
53                      const std::vector<sp<RenderNode>>& nodes, bool opaque,
54                      const Rect& contentDrawBounds, sk_sp<SkSurface> surface,
55                      const SkMatrix& preTransform);
56 
getVectorDrawables()57     std::vector<VectorDrawableRoot*>* getVectorDrawables() { return &mVectorDrawables; }
58 
59     static void prepareToDraw(const renderthread::RenderThread& thread, Bitmap* bitmap);
60 
61     void renderLayersImpl(const LayerUpdateQueue& layers, bool opaque);
62 
getLightRadius()63     static float getLightRadius() {
64         if (CC_UNLIKELY(Properties::overrideLightRadius > 0)) {
65             return Properties::overrideLightRadius;
66         }
67         return mLightRadius;
68     }
69 
getAmbientShadowAlpha()70     static uint8_t getAmbientShadowAlpha() {
71         if (CC_UNLIKELY(Properties::overrideAmbientShadowStrength >= 0)) {
72             return Properties::overrideAmbientShadowStrength;
73         }
74         return mAmbientShadowAlpha;
75     }
76 
getSpotShadowAlpha()77     static uint8_t getSpotShadowAlpha() {
78         if (CC_UNLIKELY(Properties::overrideSpotShadowStrength >= 0)) {
79             return Properties::overrideSpotShadowStrength;
80         }
81         return mSpotShadowAlpha;
82     }
83 
getLightCenter()84     static Vector3 getLightCenter() {
85         if (CC_UNLIKELY(Properties::overrideLightPosY > 0 || Properties::overrideLightPosZ > 0)) {
86             Vector3 adjustedLightCenter = mLightCenter;
87             if (CC_UNLIKELY(Properties::overrideLightPosY > 0)) {
88                 // negated since this shifts up
89                 adjustedLightCenter.y = -Properties::overrideLightPosY;
90             }
91             if (CC_UNLIKELY(Properties::overrideLightPosZ > 0)) {
92                 adjustedLightCenter.z = Properties::overrideLightPosZ;
93             }
94             return adjustedLightCenter;
95         }
96         return mLightCenter;
97     }
98 
updateLighting(const LightGeometry & lightGeometry,const LightInfo & lightInfo)99     static void updateLighting(const LightGeometry& lightGeometry, const LightInfo& lightInfo) {
100         mLightRadius = lightGeometry.radius;
101         mAmbientShadowAlpha = lightInfo.ambientShadowAlpha;
102         mSpotShadowAlpha = lightInfo.spotShadowAlpha;
103         mLightCenter = lightGeometry.center;
104     }
105 
setPictureCapturedCallback(const std::function<void (sk_sp<SkPicture> &&)> & callback)106     void setPictureCapturedCallback(
107             const std::function<void(sk_sp<SkPicture>&&)>& callback) override {
108         mPictureCapturedCallback = callback;
109     }
110 
111 protected:
112     void dumpResourceCacheUsage() const;
113     void setSurfaceColorProperties(renderthread::ColorMode colorMode);
114 
115     renderthread::RenderThread& mRenderThread;
116     SkColorType mSurfaceColorType;
117     sk_sp<SkColorSpace> mSurfaceColorSpace;
118 
119 private:
120     void renderFrameImpl(const LayerUpdateQueue& layers, const SkRect& clip,
121                          const std::vector<sp<RenderNode>>& nodes, bool opaque,
122                          const Rect& contentDrawBounds, SkCanvas* canvas,
123                          const SkMatrix& preTransform);
124 
125     /**
126      *  Debugging feature.  Draws a semi-transparent overlay on each pixel, indicating
127      *  how many times it has been drawn.
128      */
129     void renderOverdraw(const LayerUpdateQueue& layers, const SkRect& clip,
130                         const std::vector<sp<RenderNode>>& nodes, const Rect& contentDrawBounds,
131                         sk_sp<SkSurface> surface, const SkMatrix& preTransform);
132 
133     /**
134      *  Render mVectorDrawables into offscreen buffers.
135      */
136     void renderVectorDrawableCache();
137 
138     SkCanvas* tryCapture(SkSurface* surface);
139     void endCapture(SkSurface* surface);
140 
141     std::vector<sk_sp<SkImage>> mPinnedImages;
142 
143     /**
144      *  populated by prepareTree with dirty VDs
145      */
146     std::vector<VectorDrawableRoot*> mVectorDrawables;
147 
148     // Block of properties used only for debugging to record a SkPicture and save it in a file.
149     /**
150      * mCapturedFile is used to enforce we don't capture more than once for a given name (cause
151      * permissions don't allow to reset a property from render thread).
152      */
153     std::string mCapturedFile;
154     /**
155      *  mCaptureSequence counts how many frames are left to take in the sequence.
156      */
157     int mCaptureSequence = 0;
158 
159     /**
160      *  mRecorder holds the current picture recorder. We could store it on the stack to support
161      *  parallel tryCapture calls (not really needed).
162      */
163     std::unique_ptr<SkPictureRecorder> mRecorder;
164     std::unique_ptr<SkNWayCanvas> mNwayCanvas;
165     std::function<void(sk_sp<SkPicture>&&)> mPictureCapturedCallback;
166 
167     static float mLightRadius;
168     static uint8_t mAmbientShadowAlpha;
169     static uint8_t mSpotShadowAlpha;
170     static Vector3 mLightCenter;
171 };
172 
173 } /* namespace skiapipeline */
174 } /* namespace uirenderer */
175 } /* namespace android */
176