Index: src/pipe/SkGPipeWrite.cpp |
diff --git a/src/pipe/SkGPipeWrite.cpp b/src/pipe/SkGPipeWrite.cpp |
index 83e5c57d274b8dd92dafc0ac6bcc4ffbedf1e8a0..2e73be83f11231d9602b0127c55be35ea48763be 100644 |
--- a/src/pipe/SkGPipeWrite.cpp |
+++ b/src/pipe/SkGPipeWrite.cpp |
@@ -272,12 +272,9 @@ protected: |
void onDrawBitmap(const SkBitmap&, SkScalar left, SkScalar top, const SkPaint*) override; |
void onDrawBitmapRect(const SkBitmap&, const SkRect* src, const SkRect& dst, const SkPaint*, |
DrawBitmapRectFlags flags) override; |
-#if 0 |
- // rely on decomposition into bitmap (for now) |
void onDrawImage(const SkImage*, SkScalar left, SkScalar top, const SkPaint*) override; |
void onDrawImageRect(const SkImage*, const SkRect* src, const SkRect& dst, |
const SkPaint*) override; |
-#endif |
void onDrawBitmapNine(const SkBitmap&, const SkIRect& center, const SkRect& dst, |
const SkPaint*) override; |
void onDrawSprite(const SkBitmap&, int left, int top, const SkPaint*) override; |
@@ -300,6 +297,7 @@ private: |
SkNamedFactorySet* fFactorySet; |
SkBitmapHeap* fBitmapHeap; |
+ SkImageHeap* fImageHeap; |
SkGPipeController* fController; |
SkWriter32& fWriter; |
size_t fBlockSize; // amount allocated for writer |
@@ -348,8 +346,8 @@ private: |
// Common code used by drawBitmap*. Behaves differently depending on the |
// type of SkBitmapHeap being used, which is determined by the flags used. |
- bool commonDrawBitmap(const SkBitmap& bm, DrawOps op, unsigned flags, |
- size_t opBytesNeeded, const SkPaint* paint); |
+ bool commonDrawBitmap(const SkBitmap&, DrawOps, unsigned flags, size_t bytes, const SkPaint*); |
+ bool commonDrawImage(const SkImage*, DrawOps, unsigned flags, size_t bytes, const SkPaint*); |
SkPaint fPaint; |
void writePaint(const SkPaint&); |
@@ -462,6 +460,13 @@ SkGPipeCanvas::SkGPipeCanvas(SkGPipeController* controller, |
} |
} |
fFlattenableHeap.setBitmapStorage(fBitmapHeap); |
+ |
+ fImageHeap = SkNEW(SkImageHeap); |
+ if (this->needOpBytes(sizeof(void*))) { |
+ this->writeOp(kShareImageHeap_DrawOp); |
+ fWriter.writePtr(static_cast<void*>(fImageHeap)); |
+ } |
+ |
this->doNotify(); |
} |
@@ -469,6 +474,7 @@ SkGPipeCanvas::~SkGPipeCanvas() { |
this->finish(true); |
SkSafeUnref(fFactorySet); |
SkSafeUnref(fBitmapHeap); |
+ SkSafeUnref(fImageHeap); |
} |
bool SkGPipeCanvas::needOpBytes(size_t needed) { |
@@ -823,6 +829,53 @@ void SkGPipeCanvas::onDrawSprite(const SkBitmap& bm, int left, int top, const Sk |
} |
} |
+bool SkGPipeCanvas::commonDrawImage(const SkImage* image, DrawOps op, unsigned flags, |
+ size_t opBytesNeeded, const SkPaint* paint) { |
+ if (fDone) { |
+ return false; |
+ } |
+ |
+ if (paint != NULL) { |
+ flags |= kDrawBitmap_HasPaint_DrawOpFlag; |
+ this->writePaint(*paint); |
+ } |
+ // This needs to run first so its calls to needOpBytes() and its writes |
+ // don't interlace with the needOpBytes() and write below. |
+ int32_t slot = fImageHeap->insert(image); |
+ SkASSERT(slot != 0); |
+ if (this->needOpBytes(opBytesNeeded)) { |
+ this->writeOp(op, flags, slot); |
+ return true; |
+ } |
+ return false; |
+} |
+ |
+void SkGPipeCanvas::onDrawImage(const SkImage* image, SkScalar x, SkScalar y, |
+ const SkPaint* paint) { |
+ NOTIFY_SETUP(this); |
+ if (this->commonDrawImage(image, kDrawImage_DrawOp, 0, sizeof(SkScalar) * 2, paint)) { |
+ fWriter.writeScalar(x); |
+ fWriter.writeScalar(y); |
+ } |
+} |
+ |
+void SkGPipeCanvas::onDrawImageRect(const SkImage* image, const SkRect* src, const SkRect& dst, |
+ const SkPaint* paint) { |
+ NOTIFY_SETUP(this); |
+ unsigned flags = 0; |
+ size_t opBytesNeeded = sizeof(SkRect); // dst |
+ if (src) { |
+ flags |= kDrawBitmap_HasSrcRect_DrawOpFlag; |
+ opBytesNeeded += sizeof(SkRect); // src |
+ } |
+ if (this->commonDrawImage(image, kDrawImageRect_DrawOp, flags, opBytesNeeded, paint)) { |
+ if (src) { |
+ fWriter.writeRect(*src); |
+ } |
+ fWriter.writeRect(dst); |
+ } |
+} |
+ |
void SkGPipeCanvas::onDrawText(const void* text, size_t byteLength, SkScalar x, SkScalar y, |
const SkPaint& paint) { |
if (byteLength) { |
@@ -1337,3 +1390,34 @@ void BitmapShuttle::removeCanvas() { |
fCanvas->unref(); |
fCanvas = NULL; |
} |
+ |
+/////////////////////////////////////////////////////////////////////////////////////////////////// |
+ |
+SkImageHeap::SkImageHeap() {} |
+ |
+SkImageHeap::~SkImageHeap() { |
+ fArray.unrefAll(); |
+} |
+ |
+const SkImage* SkImageHeap::get(int32_t slot) const { |
+ SkASSERT(slot > 0); |
+ return fArray[slot - 1]; |
+} |
+ |
+int32_t SkImageHeap::find(const SkImage* img) const { |
+ int index = fArray.find(img); |
+ if (index >= 0) { |
+ return index + 1; // found |
+ } |
+ return 0; // not found |
+} |
+ |
+int32_t SkImageHeap::insert(const SkImage* img) { |
+ int32_t slot = this->find(img); |
+ if (slot) { |
+ return slot; |
+ } |
+ *fArray.append() = SkRef(img); |
+ return fArray.count(); // slot is always index+1 |
+} |
+ |