aboutsummaryrefslogtreecommitdiffstats
path: root/src/gpu/SkGrTexturePixelRef.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/gpu/SkGrTexturePixelRef.cpp')
-rw-r--r--src/gpu/SkGrTexturePixelRef.cpp118
1 files changed, 98 insertions, 20 deletions
diff --git a/src/gpu/SkGrTexturePixelRef.cpp b/src/gpu/SkGrTexturePixelRef.cpp
index 8becfd4..045ddab 100644
--- a/src/gpu/SkGrTexturePixelRef.cpp
+++ b/src/gpu/SkGrTexturePixelRef.cpp
@@ -1,26 +1,82 @@
+
/*
- Copyright 2010 Google Inc.
+ * Copyright 2010 Google Inc.
+ *
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ */
- Licensed under the Apache License, Version 2.0 (the "License");
- you may not use this file except in compliance with the License.
- You may obtain a copy of the License at
- http://www.apache.org/licenses/LICENSE-2.0
- Unless required by applicable law or agreed to in writing, software
- distributed under the License is distributed on an "AS IS" BASIS,
- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- See the License for the specific language governing permissions and
- limitations under the License.
- */
+#include "SkGrTexturePixelRef.h"
+#include "GrContext.h"
+#include "GrTexture.h"
+#include "SkGr.h"
+#include "SkRect.h"
+// since we call lockPixels recursively on fBitmap, we need a distinct mutex,
+// to avoid deadlock with the default one provided by SkPixelRef.
+static SkMutex gROLockPixelsPixelRefMutex;
-#include "SkGrTexturePixelRef.h"
+SkROLockPixelsPixelRef::SkROLockPixelsPixelRef() : INHERITED(&gROLockPixelsPixelRefMutex) {
+}
-#include "GrTexture.h"
+SkROLockPixelsPixelRef::~SkROLockPixelsPixelRef() {
+}
-#include "SkRect.h"
-#include "SkBitmap.h"
+void* SkROLockPixelsPixelRef::onLockPixels(SkColorTable** ctable) {
+ if (ctable) {
+ *ctable = NULL;
+ }
+ fBitmap.reset();
+// SkDebugf("---------- calling readpixels in support of lockpixels\n");
+ if (!this->onReadPixels(&fBitmap, NULL)) {
+ SkDebugf("SkROLockPixelsPixelRef::onLockPixels failed!\n");
+ return NULL;
+ }
+ fBitmap.lockPixels();
+ return fBitmap.getPixels();
+}
+
+void SkROLockPixelsPixelRef::onUnlockPixels() {
+ fBitmap.unlockPixels();
+}
+
+bool SkROLockPixelsPixelRef::onLockPixelsAreWritable() const {
+ return false;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+
+static SkGrTexturePixelRef* copyToTexturePixelRef(GrTexture* texture,
+ SkBitmap::Config dstConfig) {
+ if (NULL == texture) {
+ return NULL;
+ }
+ GrContext* context = texture->getContext();
+ if (NULL == context) {
+ return NULL;
+ }
+ GrTextureDesc desc;
+
+ desc.fWidth = texture->width();
+ desc.fHeight = texture->height();
+ desc.fFlags = kRenderTarget_GrTextureFlagBit | kNoStencil_GrTextureFlagBit;
+ desc.fConfig = SkGr::BitmapConfig2PixelConfig(dstConfig, false);
+ desc.fAALevel = kNone_GrAALevel;
+
+ GrTexture* dst = context->createUncachedTexture(desc, NULL, 0);
+ if (NULL == dst) {
+ return NULL;
+ }
+
+ context->copyTexture(texture, dst->asRenderTarget());
+ SkGrTexturePixelRef* pixelRef = new SkGrTexturePixelRef(dst);
+ GrSafeUnref(dst);
+ return pixelRef;
+}
+
+///////////////////////////////////////////////////////////////////////////////
SkGrTexturePixelRef::SkGrTexturePixelRef(GrTexture* tex) {
fTexture = tex;
@@ -31,6 +87,14 @@ SkGrTexturePixelRef::~SkGrTexturePixelRef() {
GrSafeUnref(fTexture);
}
+SkGpuTexture* SkGrTexturePixelRef::getTexture() {
+ return (SkGpuTexture*)fTexture;
+}
+
+SkPixelRef* SkGrTexturePixelRef::deepCopy(SkBitmap::Config dstConfig) {
+ return copyToTexturePixelRef(fTexture, dstConfig);
+}
+
bool SkGrTexturePixelRef::onReadPixels(SkBitmap* dst, const SkIRect* subset) {
if (NULL != fTexture && fTexture->isValid()) {
int left, top, width, height;
@@ -50,14 +114,14 @@ bool SkGrTexturePixelRef::onReadPixels(SkBitmap* dst, const SkIRect* subset) {
SkAutoLockPixels al(*dst);
void* buffer = dst->getPixels();
return fTexture->readPixels(left, top, width, height,
- kRGBA_8888_GrPixelConfig,
- buffer);
+ kSkia8888_PM_GrPixelConfig,
+ buffer, dst->rowBytes());
} else {
return false;
}
}
-////////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////
SkGrRenderTargetPixelRef::SkGrRenderTargetPixelRef(GrRenderTarget* rt) {
fRenderTarget = rt;
@@ -75,6 +139,19 @@ SkGpuTexture* SkGrRenderTargetPixelRef::getTexture() {
return NULL;
}
+SkPixelRef* SkGrRenderTargetPixelRef::deepCopy(SkBitmap::Config dstConfig) {
+ if (NULL == fRenderTarget) {
+ return NULL;
+ }
+ // Note that when copying an SkGrRenderTargetPixelRef, we actually
+ // return an SkGrTexturePixelRef instead. This is because
+ // SkGrRenderTargetPixelRef is usually created in conjunction with
+ // GrTexture owned elsewhere (e.g., SkGpuDevice), and cannot live
+ // independently of that texture. SkGrTexturePixelRef, on the other
+ // hand, owns its own GrTexture, and is thus self-contained.
+ return copyToTexturePixelRef(fRenderTarget->asTexture(), dstConfig);
+}
+
bool SkGrRenderTargetPixelRef::onReadPixels(SkBitmap* dst, const SkIRect* subset) {
if (NULL != fRenderTarget && fRenderTarget->isValid()) {
int left, top, width, height;
@@ -94,9 +171,10 @@ bool SkGrRenderTargetPixelRef::onReadPixels(SkBitmap* dst, const SkIRect* subset
SkAutoLockPixels al(*dst);
void* buffer = dst->getPixels();
return fRenderTarget->readPixels(left, top, width, height,
- kRGBA_8888_GrPixelConfig,
- buffer);
+ kSkia8888_PM_GrPixelConfig,
+ buffer, dst->rowBytes());
} else {
return false;
}
}
+