• Home
  • History
  • Annotate
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2014 Google Inc.
3  *
4  * Use of this source code is governed by a BSD-style license that can be
5  * found in the LICENSE file.
6  */
7 
8 #include "SkPaint.h"
9 #include "SkPathEffect.h"
10 #include "SkPictureContentInfo.h"
11 
suitableForGpuRasterization(GrContext * context,const char ** reason,int sampleCount) const12 bool SkPictureContentInfo::suitableForGpuRasterization(GrContext* context, const char **reason,
13                                                        int sampleCount) const {
14     // TODO: the heuristic used here needs to be refined
15     static const int kNumPaintWithPathEffectUsesTol = 1;
16     static const int kNumAAConcavePaths = 5;
17 
18     SkASSERT(fNumAAHairlineConcavePaths <= fNumAAConcavePaths);
19 
20     int numNonDashedPathEffects = fNumPaintWithPathEffectUses -
21                                   fNumFastPathDashEffects;
22 
23     bool suitableForDash = (0 == fNumPaintWithPathEffectUses) ||
24                            (numNonDashedPathEffects < kNumPaintWithPathEffectUsesTol
25                             && 0 == sampleCount);
26 
27     bool ret = suitableForDash &&
28                     (fNumAAConcavePaths - fNumAAHairlineConcavePaths)
29                     < kNumAAConcavePaths;
30     if (!ret && reason) {
31         if (!suitableForDash) {
32             if (0 != sampleCount) {
33                 *reason = "Can't use multisample on dash effect.";
34             } else {
35                 *reason = "Too many non dashed path effects.";
36             }
37         } else if ((fNumAAConcavePaths - fNumAAHairlineConcavePaths)
38                     >= kNumAAConcavePaths) {
39             *reason = "Too many anti-aliased concave paths.";
40         } else {
41             *reason = "Unknown reason for GPU unsuitability.";
42         }
43     }
44     return ret;
45 }
46 
onDrawPoints(size_t count,const SkPaint & paint)47 void SkPictureContentInfo::onDrawPoints(size_t count, const SkPaint& paint) {
48     if (paint.getPathEffect() != NULL) {
49         SkPathEffect::DashInfo info;
50         SkPathEffect::DashType dashType = paint.getPathEffect()->asADash(&info);
51         if (2 == count && SkPaint::kRound_Cap != paint.getStrokeCap() &&
52             SkPathEffect::kDash_DashType == dashType && 2 == info.fCount) {
53             ++fNumFastPathDashEffects;
54         }
55     }
56 }
57 
onDrawPath(const SkPath & path,const SkPaint & paint)58 void SkPictureContentInfo::onDrawPath(const SkPath& path, const SkPaint& paint) {
59     if (paint.isAntiAlias() && !path.isConvex()) {
60         ++fNumAAConcavePaths;
61 
62         if (SkPaint::kStroke_Style == paint.getStyle() && 0 == paint.getStrokeWidth()) {
63             ++fNumAAHairlineConcavePaths;
64         }
65     }
66 }
67 
onAddPaintPtr(const SkPaint * paint)68 void SkPictureContentInfo::onAddPaintPtr(const SkPaint* paint) {
69     if (paint && paint->getPathEffect()) {
70         ++fNumPaintWithPathEffectUses;
71     }
72 }
73 
onSaveLayer()74 void SkPictureContentInfo::onSaveLayer() {
75     *fSaveStack.append() = kSaveLayer_Flag;
76 }
77 
onSave()78 void SkPictureContentInfo::onSave() {
79     *fSaveStack.append() = kSave_Flag;
80 }
81 
onRestore()82 void SkPictureContentInfo::onRestore() {
83     SkASSERT(fSaveStack.count() > 0);
84 
85     bool containedSaveLayer = fSaveStack.top() & kContainedSaveLayer_Flag;
86 
87     if (fSaveStack.top() & kSaveLayer_Flag) {
88         ++fNumLayers;
89         if (containedSaveLayer) {
90             ++fNumInteriorLayers;
91         } else {
92             ++fNumLeafLayers;
93         }
94         containedSaveLayer = true;
95     }
96 
97     fSaveStack.pop();
98 
99     if (containedSaveLayer && fSaveStack.count() > 0) {
100         fSaveStack.top() |= kContainedSaveLayer_Flag;
101     }
102 }
103 
rescindLastSave()104 void SkPictureContentInfo::rescindLastSave() {
105     SkASSERT(fSaveStack.count() > 0);
106     SkASSERT(fSaveStack.top() & kSave_Flag);
107 
108     bool containedSaveLayer = fSaveStack.top() & kContainedSaveLayer_Flag;
109 
110     fSaveStack.pop();
111 
112     if (containedSaveLayer && fSaveStack.count() > 0) {
113         fSaveStack.top() |= kContainedSaveLayer_Flag;
114     }
115 }
116 
rescindLastSaveLayer()117 void SkPictureContentInfo::rescindLastSaveLayer() {
118     SkASSERT(fSaveStack.count() > 0);
119     SkASSERT(fSaveStack.top() & kSaveLayer_Flag);
120 
121     bool containedSaveLayer = fSaveStack.top() & kContainedSaveLayer_Flag;
122 
123     fSaveStack.pop();
124 
125     if (containedSaveLayer && fSaveStack.count() > 0) {
126         fSaveStack.top() |= kContainedSaveLayer_Flag;
127     }
128 }
129 
set(const SkPictureContentInfo & src)130 void SkPictureContentInfo::set(const SkPictureContentInfo& src) {
131     fNumOperations = src.fNumOperations;
132     fNumTexts = src.fNumTexts;
133     fNumPaintWithPathEffectUses = src.fNumPaintWithPathEffectUses;
134     fNumFastPathDashEffects = src.fNumFastPathDashEffects;
135     fNumAAConcavePaths = src.fNumAAConcavePaths;
136     fNumAAHairlineConcavePaths = src.fNumAAHairlineConcavePaths;
137     fNumLayers = src.fNumLayers;
138     fNumInteriorLayers = src.fNumInteriorLayers;
139     fNumLeafLayers = src.fNumLeafLayers;
140     fSaveStack = src.fSaveStack;
141 }
142 
reset()143 void SkPictureContentInfo::reset() {
144     fNumOperations = 0;
145     fNumTexts = 0;
146     fNumPaintWithPathEffectUses = 0;
147     fNumFastPathDashEffects = 0;
148     fNumAAConcavePaths = 0;
149     fNumAAHairlineConcavePaths = 0;
150     fNumLayers = 0;
151     fNumInteriorLayers = 0;
152     fNumLeafLayers = 0;
153     fSaveStack.rewind();
154 }
155 
swap(SkPictureContentInfo * other)156 void SkPictureContentInfo::swap(SkPictureContentInfo* other) {
157     SkTSwap(fNumOperations, other->fNumOperations);
158     SkTSwap(fNumTexts, other->fNumTexts);
159     SkTSwap(fNumPaintWithPathEffectUses, other->fNumPaintWithPathEffectUses);
160     SkTSwap(fNumFastPathDashEffects, other->fNumFastPathDashEffects);
161     SkTSwap(fNumAAConcavePaths, other->fNumAAConcavePaths);
162     SkTSwap(fNumAAHairlineConcavePaths, other->fNumAAHairlineConcavePaths);
163     SkTSwap(fNumLayers, other->fNumLayers);
164     SkTSwap(fNumInteriorLayers, other->fNumInteriorLayers);
165     SkTSwap(fNumLeafLayers, other->fNumLeafLayers);
166     fSaveStack.swap(other->fSaveStack);
167 }
168