OLD | NEW |
---|---|
(Empty) | |
1 /* | |
2 * Copyright 2016 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 "SkCanvas.h" | |
9 #include "SkSpecialImage.h" | |
10 #include "SkSpecialSurface.h" | |
11 | |
12 /////////////////////////////////////////////////////////////////////////////// | |
13 class SkSpecialImage_Base : public SkSpecialImage { | |
14 public: | |
15 SkSpecialImage_Base(const SkIRect& subset) : INHERITED(subset) { } | |
16 virtual ~SkSpecialImage_Base() { } | |
17 | |
18 virtual void onDraw(SkCanvas*, int x, int y, const SkPaint*) const = 0; | |
19 | |
20 virtual bool onPeekPixels(SkPixmap*) const { return false; } | |
21 | |
22 virtual GrTexture* onPeekTexture() const { return nullptr; } | |
23 | |
24 virtual SkSpecialSurface* onNewSurface(const SkImageInfo& info) const { retu rn nullptr; } | |
25 | |
26 private: | |
27 typedef SkSpecialImage INHERITED; | |
28 }; | |
29 | |
30 /////////////////////////////////////////////////////////////////////////////// | |
31 static inline const SkSpecialImage_Base* as_IB(const SkSpecialImage* image) { | |
32 return static_cast<const SkSpecialImage_Base*>(image); | |
33 } | |
34 | |
35 void SkSpecialImage::draw(SkCanvas* canvas, int x, int y, const SkPaint* paint) const { | |
36 return as_IB(this)->onDraw(canvas, x, y, paint); | |
37 } | |
38 | |
39 bool SkSpecialImage::peekPixels(SkPixmap* pixmap) const { | |
40 return as_IB(this)->onPeekPixels(pixmap); | |
41 } | |
42 | |
43 GrTexture* SkSpecialImage::peekTexture() const { | |
44 return as_IB(this)->onPeekTexture(); | |
45 } | |
46 | |
47 SkSpecialSurface* SkSpecialImage::newSurface(const SkImageInfo& info) const { | |
48 return as_IB(this)->onNewSurface(info); | |
49 } | |
50 | |
51 /////////////////////////////////////////////////////////////////////////////// | |
52 #include "SkImage.h" | |
53 #if SK_SUPPORT_GPU | |
54 #include "SkGr.h" | |
55 #include "SkGrPriv.h" | |
56 #endif | |
57 | |
58 class SkSpecialImage_Image : public SkSpecialImage_Base { | |
59 public: | |
60 SkSpecialImage_Image(const SkIRect& subset, const SkImage* image) | |
61 : INHERITED(subset) | |
62 , fImage(SkRef(image)) { | |
63 } | |
64 | |
65 ~SkSpecialImage_Image() override { } | |
66 | |
67 void onDraw(SkCanvas* canvas, int x, int y, const SkPaint* paint) const over ride { | |
68 SkRect dst = SkRect::MakeXYWH(x, y, this->subset().width(), this->subset ().height()); | |
69 | |
70 canvas->drawImageRect(fImage, this->subset(), | |
71 dst, paint, SkCanvas::kStrict_SrcRectConstraint); | |
72 } | |
73 | |
74 bool onPeekPixels(SkPixmap* pixmap) const override { | |
75 return fImage->peekPixels(pixmap); | |
76 } | |
77 | |
78 GrTexture* onPeekTexture() const override { return fImage->getTexture(); } | |
79 | |
80 SkSpecialSurface* onNewSurface(const SkImageInfo& info) const override { | |
81 #if SK_SUPPORT_GPU | |
82 GrTexture* texture = fImage->getTexture(); | |
bsalomon
2016/01/19 16:29:47
Wondering about sample counts.. what do filters do
robertphillips
2016/02/04 17:20:44
So we may have to add a 'sampleCnt' parameter to t
| |
83 if (texture) { | |
84 GrSurfaceDesc desc = GrImageInfoToSurfaceDesc(info); | |
85 desc.fFlags = kRenderTarget_GrSurfaceFlag; | |
86 | |
87 return SkSpecialSurface::NewRenderTarget(texture->getContext(), desc ); | |
88 } | |
89 #endif | |
90 return SkSpecialSurface::NewRaster(info, nullptr); | |
91 } | |
92 | |
93 private: | |
94 SkAutoTUnref<const SkImage> fImage; | |
95 | |
96 typedef SkSpecialImage_Base INHERITED; | |
97 }; | |
98 | |
99 static bool rect_fits(const SkIRect& rect, int width, int height) { | |
100 return rect.fLeft >= 0 && rect.fLeft < width && rect.fLeft < rect.fRight && | |
101 rect.fRight >= 0 && rect.fRight <= width && | |
102 rect.fTop >= 0 && rect.fTop < height && rect.fTop < rect.fBottom && | |
103 rect.fBottom >= 0 && rect.fBottom <= height; | |
104 } | |
105 | |
106 SkSpecialImage* SkSpecialImage::NewFromImage(const SkIRect& subset, const SkImag e* image) { | |
107 SkASSERT(rect_fits(subset, image->width(), image->height())); | |
108 return new SkSpecialImage_Image(subset, image); | |
109 } | |
110 | |
111 /////////////////////////////////////////////////////////////////////////////// | |
112 #include "SkBitmap.h" | |
113 #include "SkImageInfo.h" | |
114 #include "SkPixelRef.h" | |
115 | |
116 class SkSpecialImage_Raster : public SkSpecialImage_Base { | |
117 public: | |
118 SkSpecialImage_Raster(const SkIRect& subset, const SkBitmap& bm) | |
119 : INHERITED(subset) | |
120 , fBitmap(bm) { | |
121 if (bm.pixelRef()->isPreLocked()) { | |
122 // we only preemptively lock if there is no chance of triggering som ething expensive | |
123 // like a lazy decode or imagegenerator. PreLocked means it is flat pixels already. | |
124 fBitmap.lockPixels(); | |
125 } | |
126 } | |
127 | |
128 ~SkSpecialImage_Raster() override { } | |
129 | |
130 void onDraw(SkCanvas* canvas, int x, int y, const SkPaint* paint) const over ride { | |
131 SkRect dst = SkRect::MakeXYWH(x, y, | |
132 this->subset().width(), this->subset().hei ght()); | |
133 | |
134 canvas->drawBitmapRect(fBitmap, this->subset(), | |
135 dst, paint, SkCanvas::kStrict_SrcRectConstraint); | |
136 } | |
137 | |
138 bool onPeekPixels(SkPixmap* pixmap) const override { | |
139 const SkImageInfo info = fBitmap.info(); | |
140 if ((kUnknown_SkColorType == info.colorType()) || !fBitmap.getPixels()) { | |
141 return false; | |
142 } | |
143 const void* pixels = fBitmap.getPixels(); | |
144 if (pixels) { | |
145 if (pixmap) { | |
146 pixmap->reset(info, pixels, fBitmap.rowBytes()); | |
147 } | |
148 return true; | |
149 } | |
150 return false; | |
151 } | |
152 | |
153 SkSpecialSurface* onNewSurface(const SkImageInfo& info) const override { | |
154 return SkSpecialSurface::NewRaster(info, nullptr); | |
155 } | |
156 | |
157 private: | |
158 SkBitmap fBitmap; | |
159 | |
160 typedef SkSpecialImage_Base INHERITED; | |
161 }; | |
162 | |
163 SkSpecialImage* SkSpecialImage::NewFromRaster(const SkIRect& subset, const SkBit map& bm) { | |
164 SkASSERT(nullptr == bm.getTexture()); | |
165 SkASSERT(rect_fits(subset, bm.width(), bm.height())); | |
166 return new SkSpecialImage_Raster(subset, bm); | |
167 } | |
168 | |
169 #if SK_SUPPORT_GPU | |
170 /////////////////////////////////////////////////////////////////////////////// | |
171 #include "GrTexture.h" | |
172 | |
173 class SkSpecialImage_Gpu : public SkSpecialImage_Base { | |
174 public: | |
175 SkSpecialImage_Gpu(const SkIRect& subset, GrTexture* tex) | |
176 : INHERITED(subset) | |
177 , fTexture(SkRef(tex)) { | |
178 } | |
179 | |
180 ~SkSpecialImage_Gpu() override { } | |
181 | |
182 void onDraw(SkCanvas* canvas, int x, int y, const SkPaint* paint) const over ride { | |
183 SkRect dst = SkRect::MakeXYWH(x, y, | |
184 this->subset().width(), this->subset().hei ght()); | |
185 | |
186 SkBitmap bm; | |
187 | |
188 static const bool kUnknownOpacity = false; | |
189 GrWrapTextureInBitmap(fTexture, | |
190 fTexture->width(), fTexture->height(), kUnknownOpa city, &bm); | |
191 | |
192 canvas->drawBitmapRect(bm, this->subset(), | |
193 dst, paint, SkCanvas::kStrict_SrcRectConstraint); | |
194 } | |
195 | |
196 GrTexture* onPeekTexture() const override { return fTexture; } | |
197 | |
198 SkSpecialSurface* onNewSurface(const SkImageInfo& info) const override { | |
199 GrSurfaceDesc desc = GrImageInfoToSurfaceDesc(info); | |
200 desc.fFlags = kRenderTarget_GrSurfaceFlag; | |
201 | |
202 return SkSpecialSurface::NewRenderTarget(fTexture->getContext(), desc); | |
203 } | |
204 | |
205 private: | |
206 SkAutoTUnref<GrTexture> fTexture; | |
207 | |
208 typedef SkSpecialImage_Base INHERITED; | |
209 }; | |
210 | |
211 SkSpecialImage* SkSpecialImage::NewFromGpu(const SkIRect& subset, GrTexture* tex ) { | |
212 SkASSERT(rect_fits(subset, tex->width(), tex->height())); | |
213 return new SkSpecialImage_Gpu(subset, tex); | |
214 } | |
215 | |
216 #else | |
217 | |
218 SkSpecialImage* SkSpecialImage::NewGpu(const SkIRect& subset, GrTexture* tex) { | |
219 return nullptr; | |
220 } | |
221 | |
222 #endif | |
OLD | NEW |