Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(247)

Unified Diff: src/gpu/GrPictureUtils.cpp

Issue 212933002: Actually identify required saveLayers in SkGpuDevice::EXPERIMENTAL_drawPicture (Closed) Base URL: http://skia.googlecode.com/svn/trunk/
Patch Set: Addressed code review issue Created 6 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « src/gpu/GrPictureUtils.h ('k') | src/gpu/SkGpuDevice.cpp » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/gpu/GrPictureUtils.cpp
===================================================================
--- src/gpu/GrPictureUtils.cpp (revision 0)
+++ src/gpu/GrPictureUtils.cpp (revision 0)
@@ -0,0 +1,247 @@
+/*
+ * Copyright 2014 Google Inc.
+ *
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ */
+
+#include "GrPictureUtils.h"
+#include "SkDevice.h"
+
+// The GrGather device performs GPU-backend-specific preprocessing on
+// a picture. The results are stored in a GPUAccelData.
+//
+// Currently the only interesting work is done in drawDevice (i.e., when a
+// saveLayer is collapsed back into its parent) and, maybe, in onCreateDevice.
+// All the current work could be done much more efficiently by just traversing the
+// raw op codes in the SkPicture (although we would still need to replay all the
+// clip calls).
+class GrGatherDevice : public SkBaseDevice {
+public:
+ SK_DECLARE_INST_COUNT(GrGatherDevice)
+
+ GrGatherDevice(int width, int height, SkPicture* picture, GPUAccelData* accelData) {
+ fPicture = picture;
+ fInfo.fSize.set(width, height);
+ fInfo.fSaveLayerOpID = fPicture->EXPERIMENTAL_curOpID();
+ fInfo.fRestoreOpID = 0;
+ fInfo.fHasNestedLayers = false;
+
+ fEmptyBitmap.setConfig(SkImageInfo::Make(fInfo.fSize.fWidth,
+ fInfo.fSize.fHeight,
+ kUnknown_SkColorType,
+ kIgnore_SkAlphaType));
+ fAccelData = accelData;
+ fAlreadyDrawn = false;
+ }
+
+ virtual ~GrGatherDevice() { }
+
+ virtual int width() const SK_OVERRIDE { return fInfo.fSize.width(); }
+ virtual int height() const SK_OVERRIDE { return fInfo.fSize.height(); }
+ virtual bool isOpaque() const SK_OVERRIDE { return false; }
+ virtual SkBitmap::Config config() const SK_OVERRIDE {
+ return SkBitmap::kNo_Config;
+ }
+ virtual SkImageInfo imageInfo() const SK_OVERRIDE {
+ return fEmptyBitmap.info();
+ }
+
+#ifdef SK_SUPPORT_LEGACY_WRITEPIXELSCONFIG
+ virtual void writePixels(const SkBitmap& bitmap, int x, int y,
+ SkCanvas::Config8888 config8888) SK_OVERRIDE {
+ NotSupported();
+ }
+#endif
+ virtual GrRenderTarget* accessRenderTarget() SK_OVERRIDE { return NULL; }
+
+protected:
+ virtual bool filterTextFlags(const SkPaint& paint, TextFlags*) SK_OVERRIDE {
+ return false;
+ }
+ virtual void clear(SkColor color) SK_OVERRIDE {
+ NothingToDo();
+ }
+ virtual void drawPaint(const SkDraw& draw, const SkPaint& paint) SK_OVERRIDE {
+ }
+ virtual void drawPoints(const SkDraw& draw, SkCanvas::PointMode mode, size_t count,
+ const SkPoint points[], const SkPaint& paint) SK_OVERRIDE {
+ }
+ virtual void drawRect(const SkDraw& draw, const SkRect& rect,
+ const SkPaint& paint) SK_OVERRIDE {
+ }
+ virtual void drawOval(const SkDraw& draw, const SkRect& rect,
+ const SkPaint& paint) SK_OVERRIDE {
+ }
+ virtual void drawRRect(const SkDraw& draw, const SkRRect& rrect,
+ const SkPaint& paint) SK_OVERRIDE {
+ }
+ virtual void drawPath(const SkDraw& draw, const SkPath& path,
+ const SkPaint& paint, const SkMatrix* prePathMatrix,
+ bool pathIsMutable) SK_OVERRIDE {
+ }
+ virtual void drawBitmap(const SkDraw& draw, const SkBitmap& bitmap,
+ const SkMatrix& matrix, const SkPaint& paint) SK_OVERRIDE {
+ }
+ virtual void drawSprite(const SkDraw&, const SkBitmap& bitmap,
+ int x, int y, const SkPaint& paint) SK_OVERRIDE {
+ }
+ virtual void drawBitmapRect(const SkDraw& draw, const SkBitmap& bitmap,
+ const SkRect* srcOrNull, const SkRect& dst,
+ const SkPaint& paint,
+ SkCanvas::DrawBitmapRectFlags flags) SK_OVERRIDE {
+ }
+ virtual void drawText(const SkDraw& draw, const void* text, size_t len,
+ SkScalar x, SkScalar y,
+ const SkPaint& paint) SK_OVERRIDE {
+ }
+ virtual void drawPosText(const SkDraw& draw, const void* text, size_t len,
+ const SkScalar pos[], SkScalar constY,
+ int scalarsPerPos, const SkPaint& paint) SK_OVERRIDE {
+ }
+ virtual void drawTextOnPath(const SkDraw& draw, const void* text, size_t len,
+ const SkPath& path, const SkMatrix* matrix,
+ const SkPaint& paint) SK_OVERRIDE {
+ }
+ virtual void drawVertices(const SkDraw& draw, SkCanvas::VertexMode, int vertexCount,
+ const SkPoint verts[], const SkPoint texs[],
+ const SkColor colors[], SkXfermode* xmode,
+ const uint16_t indices[], int indexCount,
+ const SkPaint& paint) SK_OVERRIDE {
+ }
+ virtual void drawDevice(const SkDraw& draw, SkBaseDevice* deviceIn, int x, int y,
+ const SkPaint&) SK_OVERRIDE {
+ GrGatherDevice* device = static_cast<GrGatherDevice*>(deviceIn);
+
+ if (device->fAlreadyDrawn) {
+ return;
+ }
+
+ device->fInfo.fRestoreOpID = fPicture->EXPERIMENTAL_curOpID();
+ fAccelData->addSaveLayerInfo(device->fInfo);
+ device->fAlreadyDrawn = true;
+ }
+ // TODO: allow this call to return failure, or move to SkBitmapDevice only.
+ virtual const SkBitmap& onAccessBitmap() SK_OVERRIDE {
+ return fEmptyBitmap;
+ }
+#ifdef SK_SUPPORT_LEGACY_READPIXELSCONFIG
+ virtual bool onReadPixels(const SkBitmap& bitmap,
+ int x, int y,
+ SkCanvas::Config8888 config8888) SK_OVERRIDE {
+ NotSupported();
+ return false;
+ }
+#endif
+ virtual void lockPixels() SK_OVERRIDE { NothingToDo(); }
+ virtual void unlockPixels() SK_OVERRIDE { NothingToDo(); }
+ virtual bool allowImageFilter(const SkImageFilter*) SK_OVERRIDE { return false; }
+ virtual bool canHandleImageFilter(const SkImageFilter*) SK_OVERRIDE { return false; }
+ virtual bool filterImage(const SkImageFilter*, const SkBitmap&, const SkImageFilter::Context&,
+ SkBitmap* result, SkIPoint* offset) SK_OVERRIDE {
+ return false;
+ }
+
+private:
+ // The picture being processed
+ SkPicture *fPicture;
+
+ SkBitmap fEmptyBitmap; // legacy -- need to remove
+
+ // All information gathered during the gather process is stored here
+ GPUAccelData* fAccelData;
+
+ // true if this device has already been drawn back to its parent(s) at least
+ // once.
+ bool fAlreadyDrawn;
+
+ // The information regarding the saveLayer call this device represents.
+ GPUAccelData::SaveLayerInfo fInfo;
+
+ virtual void replaceBitmapBackendForRasterSurface(const SkBitmap&) SK_OVERRIDE {
+ NotSupported();
+ }
+
+ virtual SkBaseDevice* onCreateDevice(const SkImageInfo& info, Usage usage) SK_OVERRIDE {
+ // we expect to only get called via savelayer, in which case it is fine.
+ SkASSERT(kSaveLayer_Usage == usage);
+
+ fInfo.fHasNestedLayers = true;
+ return SkNEW_ARGS(GrGatherDevice, (info.width(), info.height(), fPicture, fAccelData));
+ }
+
+ virtual void flush() SK_OVERRIDE {}
+
+ static void NotSupported() {
+ SkDEBUGFAIL("this method should never be called");
+ }
+
+ static void NothingToDo() {}
+
+ typedef SkBaseDevice INHERITED;
+};
+
+// The GrGatherCanvas allows saveLayers but simplifies clipping. It is really
+// only intended to be used as:
+//
+// GrGatherDevice dev(w, h, picture, accelData);
+// GrGatherCanvas canvas(..., picture);
+// canvas.gather();
+//
+// which is all just to fill in 'accelData'
+class SK_API GrGatherCanvas : public SkCanvas {
+public:
+ GrGatherCanvas(GrGatherDevice* device, SkPicture* pict)
+ : INHERITED(device)
+ , fPicture(pict) {
+ }
+
+ void gather() {
+ if (NULL == fPicture || 0 == fPicture->width() || 0 == fPicture->height()) {
+ return;
+ }
+
+ this->clipRect(SkRect::MakeWH(SkIntToScalar(fPicture->width()),
+ SkIntToScalar(fPicture->height())),
+ SkRegion::kIntersect_Op, false);
+ this->drawPicture(*fPicture);
+ }
+
+ virtual void drawPicture(SkPicture& picture) SK_OVERRIDE {
+ picture.draw(this);
+ }
+protected:
+ // disable aa for speed
+ virtual void onClipRect(const SkRect& rect, SkRegion::Op op, ClipEdgeStyle) SK_OVERRIDE {
+ this->INHERITED::onClipRect(rect, op, kHard_ClipEdgeStyle);
+ }
+
+ // for speed, just respect the bounds, and disable AA. May give us a few
+ // false positives and negatives.
+ virtual void onClipPath(const SkPath& path, SkRegion::Op op, ClipEdgeStyle) SK_OVERRIDE {
+ this->updateClipConservativelyUsingBounds(path.getBounds(), op,
+ path.isInverseFillType());
+ }
+ virtual void onClipRRect(const SkRRect& rrect, SkRegion::Op op, ClipEdgeStyle) SK_OVERRIDE {
+ this->updateClipConservativelyUsingBounds(rrect.getBounds(), op, false);
+ }
+
+private:
+ SkPicture* fPicture;
+
+ typedef SkCanvas INHERITED;
+};
+
+// GatherGPUInfo is only intended to be called within the context of SkGpuDevice's
+// EXPERIMENTAL_optimize method.
+void GatherGPUInfo(SkPicture* pict, GPUAccelData* accelData) {
+ if (0 == pict->width() || 0 == pict->height()) {
+ return ;
+ }
+
+ GrGatherDevice device(pict->width(), pict->height(), pict, accelData);
+ GrGatherCanvas canvas(&device, pict);
+
+ canvas.gather();
+}
+
Property changes on: src\gpu\GrPictureUtils.cpp
___________________________________________________________________
Added: svn:eol-style
+ LF
« no previous file with comments | « src/gpu/GrPictureUtils.h ('k') | src/gpu/SkGpuDevice.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698