Properly handle extracted bitmaps in cross process/shared addr space SkGPipe.
Use the pixel ref which we have already copied and the appropriate pixel ref
offset.
Turn SampleDrawBitmap into a GM to test this functionality.
Review URL: https://codereview.appspot.com/6348059
git-svn-id: http://skia.googlecode.com/svn/trunk@4417 2bbb7eff-a529-9590-31e7-b0007b416f81
diff --git a/samplecode/SampleDrawBitmap.cpp b/gm/extractbitmap.cpp
similarity index 76%
rename from samplecode/SampleDrawBitmap.cpp
rename to gm/extractbitmap.cpp
index aaf1123..5002f1b 100644
--- a/samplecode/SampleDrawBitmap.cpp
+++ b/gm/extractbitmap.cpp
@@ -5,12 +5,13 @@
* Use of this source code is governed by a BSD-style license that can be
* found in the LICENSE file.
*/
-#include "SampleCode.h"
-#include "SkView.h"
+#include "gm.h"
+#include "SkBitmap.h"
#include "SkCanvas.h"
-#include "SkShader.h"
-#include "SkUtils.h"
#include "SkDevice.h"
+#include "SkString.h"
+
+namespace skiagm {
static void create_bitmap(SkBitmap* bitmap) {
const int W = 100;
@@ -25,22 +26,21 @@
canvas.drawCircle(SkIntToScalar(W)/2, SkIntToScalar(H)/2, SkIntToScalar(W)/2, paint);
}
-class DrawBitmapView : public SampleView {
- SkPath fPath;
+class ExtractBitmapGM : public GM {
public:
- DrawBitmapView() {}
+ ExtractBitmapGM() {}
protected:
// overrides from SkEventSink
- virtual bool onQuery(SkEvent* evt) {
- if (SampleCode::TitleQ(*evt)) {
- SampleCode::TitleR(evt, "DrawBitmap");
- return true;
- }
- return this->INHERITED::onQuery(evt);
+ virtual SkString onShortName() SK_OVERRIDE {
+ return SkString("extractbitmap");
}
-
- virtual void onDrawContent(SkCanvas* canvas) {
+
+ virtual SkISize onISize() SK_OVERRIDE {
+ return make_isize(600, 600);
+ }
+
+ virtual void onDraw(SkCanvas* canvas) SK_OVERRIDE {
SkBitmap bitmap;
create_bitmap(&bitmap);
int x = bitmap.width() / 2;
@@ -75,10 +75,12 @@
}
private:
- typedef SampleView INHERITED;
+ typedef GM INHERITED;
};
//////////////////////////////////////////////////////////////////////////////
-static SkView* MyFactory() { return new DrawBitmapView; }
-static SkViewRegister reg(MyFactory);
+static GM* MyFactory(void*) { return new ExtractBitmapGM; }
+static GMRegistry reg(MyFactory);
+
+}
diff --git a/gyp/SampleApp.gyp b/gyp/SampleApp.gyp
index 4f0ad51..bc128be 100644
--- a/gyp/SampleApp.gyp
+++ b/gyp/SampleApp.gyp
@@ -48,7 +48,6 @@
'../samplecode/SampleDegenerateTwoPtRadials.cpp',
'../samplecode/SampleDither.cpp',
'../samplecode/SampleDitherBitmap.cpp',
- '../samplecode/SampleDrawBitmap.cpp',
'../samplecode/SampleDrawLooper.cpp',
'../samplecode/SampleEffects.cpp',
'../samplecode/SampleEmboss.cpp',
diff --git a/gyp/gmslides.gypi b/gyp/gmslides.gypi
index 7c64844..45dab51 100644
--- a/gyp/gmslides.gypi
+++ b/gyp/gmslides.gypi
@@ -20,6 +20,7 @@
'../gm/degeneratesegments.cpp',
'../gm/dashing.cpp',
'../gm/drawbitmaprect.cpp',
+ '../gm/extractbitmap.cpp',
'../gm/emptypath.cpp',
'../gm/filltypes.cpp',
'../gm/filltypespersp.cpp',
diff --git a/src/pipe/SkGPipeWrite.cpp b/src/pipe/SkGPipeWrite.cpp
index 6b48bca..066159f 100644
--- a/src/pipe/SkGPipeWrite.cpp
+++ b/src/pipe/SkGPipeWrite.cpp
@@ -81,10 +81,19 @@
* @return void* Pointer to the heap's copy of the bitmap. If NULL,
* the bitmap could not be copied.
*/
- const SkBitmap* addBitmap(const SkBitmap& bm) {
- const uint32_t genID = bm.getGenerationID();
+ const SkBitmap* addBitmap(const SkBitmap& orig) {
+ const uint32_t genID = orig.getGenerationID();
+ SkPixelRef* sharedPixelRef = NULL;
for (int i = fBitmaps.count() - 1; i >= 0; i--) {
if (genID == fBitmaps[i].fGenID) {
+ if (orig.pixelRefOffset() != fBitmaps[i].fBitmap->pixelRefOffset()) {
+ // In this case, the bitmaps share a pixelRef, but have
+ // different offsets. Keep track of the other bitmap so that
+ // instead of making another copy of the pixelRef we can use
+ // the copy we already made.
+ sharedPixelRef = fBitmaps[i].fBitmap->pixelRef();
+ break;
+ }
return fBitmaps[i].fBitmap;
}
}
@@ -92,13 +101,21 @@
// If the bitmap is mutable, we still need to do a deep copy, since the
// caller may modify it afterwards. That said, if the bitmap is mutable,
// but has no pixelRef, the copy constructor actually does a deep copy.
- if (fCanDoShallowCopies && (bm.isImmutable() || !bm.pixelRef())) {
- copy = new SkBitmap(bm);
+ if (fCanDoShallowCopies && (orig.isImmutable() || !orig.pixelRef())) {
+ copy = new SkBitmap(orig);
} else {
- copy = new SkBitmap();
- if (!bm.copyTo(copy, bm.getConfig())) {
- delete copy;
- return NULL;
+ if (sharedPixelRef != NULL) {
+ // Do a shallow copy of the bitmap to get the width, height, etc
+ copy = new SkBitmap(orig);
+ // Replace the pixelRef with the copy that was already made, and
+ // use the appropriate offset.
+ copy->setPixelRef(sharedPixelRef, orig.pixelRefOffset());
+ } else {
+ copy = new SkBitmap();
+ if (!orig.copyTo(copy, orig.getConfig())) {
+ delete copy;
+ return NULL;
+ }
}
}
BitmapInfo* info = fBitmaps.append();