remove SkCanvas::createCompatibleDevice, and add SkCanvas::newSurface

BUG=skia:
R=bsalomon@google.com

Review URL: https://codereview.chromium.org/154163002

git-svn-id: http://skia.googlecode.com/svn/trunk@13319 2bbb7eff-a529-9590-31e7-b0007b416f81
This commit is contained in:
reed@google.com 2014-02-05 15:32:21 +00:00
Родитель cb6adecd4d
Коммит 76f10a3bd9
15 изменённых файлов: 111 добавлений и 61 удалений

Просмотреть файл

@ -35,3 +35,8 @@
# Added by bsalomon for skbug.com/2051, https://codereview.chromium.org/151523005
filltypespersp
# Need to rebaseline all platforms, as the content was changed to remove
# deprecated calling pattern.
# https://codereview.chromium.org/154163002/
extractbitmap

Просмотреть файл

@ -1,15 +1,16 @@
/*
* Copyright 2011 Google Inc.
*
* Use of this source code is governed by a BSD-style license that can be
* found in the LICENSE file.
*/
#include "gm.h"
#include "SkBitmap.h"
#include "SkCanvas.h"
#include "SkDevice.h"
#include "SkString.h"
#include "SkSurface.h"
namespace skiagm {
@ -71,24 +72,6 @@ protected:
canvas->translate(0, SkIntToScalar(bitmap.height() + 20));
canvas->drawBitmap(subset, 0, 0);
}
// Now do the same but with a device bitmap as source image
SkAutoTUnref<SkBaseDevice> secondDevice(canvas->createCompatibleDevice(
SkBitmap::kARGB_8888_Config, bitmap.width(),
bitmap.height(), true));
SkCanvas secondCanvas(secondDevice.get());
secondCanvas.writePixels(bitmap, 0, 0);
SkBitmap deviceBitmap = secondDevice->accessBitmap(false);
SkBitmap deviceSubset;
deviceBitmap.extractSubset(&deviceSubset,
SkIRect::MakeXYWH(x, y, x, y));
canvas->translate(SkIntToScalar(120), SkIntToScalar(0));
canvas->drawBitmap(deviceBitmap, 0, 0);
canvas->drawBitmap(deviceSubset, 0, 0);
}
private:

Просмотреть файл

@ -277,6 +277,8 @@ private:
*/
virtual void flush() SK_OVERRIDE {}
virtual SkSurface* newSurface(const SkImageInfo&) SK_OVERRIDE;
SkBitmap fBitmap;
typedef SkBaseDevice INHERITED;

Просмотреть файл

@ -1,4 +1,3 @@
/*
* Copyright 2006 The Android Open Source Project
*
@ -6,7 +5,6 @@
* found in the LICENSE file.
*/
#ifndef SkCanvas_DEFINED
#define SkCanvas_DEFINED
@ -20,6 +18,8 @@
#include "SkRegion.h"
#include "SkXfermode.h"
//#define SK_SUPPORT_LEGACY_CANVAS_CREATECOMPATIBLEDEVICE
class SkBounder;
class SkBaseDevice;
class SkDraw;
@ -27,6 +27,7 @@ class SkDrawFilter;
class SkMetaData;
class SkPicture;
class SkRRect;
class SkSurface;
class SkSurface_Base;
class GrContext;
@ -112,6 +113,7 @@ public:
*/
SkBaseDevice* getTopDevice(bool updateMatrixClip = false) const;
#ifdef SK_SUPPORT_LEGACY_CANVAS_CREATECOMPATIBLEDEVICE
/**
* Shortcut for getDevice()->createCompatibleDevice(...).
* If getDevice() == NULL, this method does nothing, and returns NULL.
@ -119,6 +121,13 @@ public:
SkBaseDevice* createCompatibleDevice(SkBitmap::Config config,
int width, int height,
bool isOpaque);
#endif
/**
* Create a new surface matching the specified info, one that attempts to
* be maximally compatible when used with this canvas.
*/
SkSurface* newSurface(const SkImageInfo&);
/**
* Return the GPU context of the device that is associated with the canvas.
@ -1019,6 +1028,9 @@ public:
};
protected:
// default impl defers to getDevice()->newSurface(info)
virtual SkSurface* onNewSurface(const SkImageInfo&);
// Returns the canvas to be used by DrawIter. Default implementation
// returns this. Subclasses that encapsulate an indirect canvas may
// need to overload this method. The impl must keep track of this, as it

Просмотреть файл

@ -367,6 +367,9 @@ protected:
static const SkCanvas::Config8888 kPMColorAlias;
protected:
// default impl returns NULL
virtual SkSurface* newSurface(const SkImageInfo&);
/**
* Leaky properties are those which the device should be applying but it isn't.
* These properties will be applied by the draw, when and as it can.
@ -382,6 +385,7 @@ private:
friend class SkDrawIter;
friend class SkDeviceFilteredPaint;
friend class SkDeviceImageFilterProxy;
friend class DeferredDevice; // for newSurface
friend class SkSurface_Raster;

Просмотреть файл

@ -169,6 +169,8 @@ private:
bool isOpaque,
Usage usage) SK_OVERRIDE;
virtual SkSurface* newSurface(const SkImageInfo&) SK_OVERRIDE;
// sets the render target, clip, and matrix on GrContext. Use forceIdenity to override
// SkDraw's matrix and draw in device coords.
void prepareDraw(const SkDraw&, bool forceIdentity);

Просмотреть файл

@ -9,7 +9,7 @@
#include "SkBlurMask.h"
#include "SkBlurMaskFilter.h"
#include "SkCanvas.h"
#include "SkDevice.h"
#include "SkSurface.h"
static SkBitmap make_bitmap() {
SkBitmap bm;
@ -45,7 +45,7 @@ protected:
}
virtual void onDrawContent(SkCanvas* canvas) {
SkIRect srcRect;
SkRect srcRect;
SkRect dstRect;
SkPaint paint;
paint.setFilterLevel(SkPaint::kLow_FilterLevel);
@ -53,54 +53,53 @@ protected:
// Test that bitmap draws from malloc-backed bitmaps respect
// the constrained texture domain.
srcRect.setXYWH(1, 1, 3, 3);
dstRect.setXYWH(5.0f, 5.0f, 305.0f, 305.0f);
canvas->drawBitmapRect(fBM, &srcRect, dstRect, &paint);
dstRect.setXYWH(5, 5, 305, 305);
canvas->drawBitmapRectToRect(fBM, &srcRect, dstRect, &paint);
// Test that bitmap draws across separate devices also respect
// the constrainted texture domain.
// Note: GPU-backed bitmaps follow a different rendering path
// when copying from one GPU device to another.
SkAutoTUnref<SkBaseDevice> secondDevice(canvas->createCompatibleDevice(
SkBitmap::kARGB_8888_Config, 5, 5, true));
SkCanvas secondCanvas(secondDevice.get());
SkImageInfo info = SkImageInfo::MakeN32(5, 5, kOpaque_SkAlphaType);
SkAutoTUnref<SkSurface> surface(canvas->newSurface(info));
srcRect.setXYWH(1, 1, 3, 3);
dstRect.setXYWH(1.0f, 1.0f, 3.0f, 3.0f);
secondCanvas.drawBitmapRect(fBM, &srcRect, dstRect, &paint);
dstRect.setXYWH(1, 1, 3, 3);
surface->getCanvas()->drawBitmapRectToRect(fBM, &srcRect, dstRect,
&paint);
SkBitmap deviceBitmap = secondDevice->accessBitmap(false);
SkAutoTUnref<SkImage> image(surface->newImageSnapshot());
srcRect.setXYWH(1, 1, 3, 3);
dstRect.setXYWH(405.0f, 5.0f, 305.0f, 305.0f);
canvas->drawBitmapRect(deviceBitmap, &srcRect, dstRect, &paint);
dstRect.setXYWH(405, 5, 305, 305);
image->draw(canvas, &srcRect, dstRect, &paint);
// Test that bitmap blurring using a subrect
// renders correctly
srcRect.setXYWH(1, 1, 3, 3);
dstRect.setXYWH(5.0f, 405.0f, 305.0f, 305.0f);
dstRect.setXYWH(5, 405, 305, 305);
SkMaskFilter* mf = SkBlurMaskFilter::Create(
SkBlurMaskFilter::kNormal_BlurStyle,
SkBlurMask::ConvertRadiusToSigma(SkIntToScalar(5)),
SkBlurMaskFilter::kHighQuality_BlurFlag |
SkBlurMaskFilter::kIgnoreTransform_BlurFlag);
paint.setMaskFilter(mf)->unref();
canvas->drawBitmapRect(deviceBitmap, &srcRect, dstRect, &paint);
image->draw(canvas, &srcRect, dstRect, &paint);
// Blur and a rotation + NULL src rect
// This should not trigger the texture domain code
// but it will test a code path in SkGpuDevice::drawBitmap
// that handles blurs with rects transformed to non-
// orthogonal rects. It also tests the NULL src rect handling
mf = SkBlurMaskFilter::Create(
SkBlurMaskFilter::kNormal_BlurStyle,
SkBlurMask::ConvertRadiusToSigma(SkIntToScalar(5)),
SkBlurMaskFilter::kHighQuality_BlurFlag);
mf = SkBlurMaskFilter::Create(SkBlurMaskFilter::kNormal_BlurStyle,
SkBlurMask::ConvertRadiusToSigma(5),
SkBlurMaskFilter::kHighQuality_BlurFlag);
paint.setMaskFilter(mf)->unref();
dstRect.setXYWH(-150.0f, -150.0f, 300.0f, 300.0f);
dstRect.setXYWH(-150, -150, 300, 300);
canvas->translate(550, 550);
canvas->rotate(45);
canvas->drawBitmapRect(fBM, NULL, dstRect, &paint);
canvas->drawBitmapRectToRect(fBM, NULL, dstRect, &paint);
}
private:
typedef SkView INHERITED;

Просмотреть файл

@ -10,6 +10,7 @@
#include "SkDraw.h"
#include "SkRasterClip.h"
#include "SkShader.h"
#include "SkSurface.h"
#define CHECK_FOR_ANNOTATION(paint) \
do { if (paint.getAnnotation()) { return; } } while (0)
@ -381,6 +382,10 @@ void SkBitmapDevice::drawDevice(const SkDraw& draw, SkBaseDevice* device,
draw.drawSprite(src, x, y, paint);
}
SkSurface* SkBitmapDevice::newSurface(const SkImageInfo& info) {
return SkSurface::NewRaster(info);
}
///////////////////////////////////////////////////////////////////////////////
bool SkBitmapDevice::filterTextFlags(const SkPaint& paint, TextFlags* flags) {

Просмотреть файл

@ -832,6 +832,26 @@ int SkCanvas::saveLayer(const SkRect* bounds, const SkPaint* paint,
return this->internalSaveLayer(bounds, paint, flags, false);
}
static SkBaseDevice* createCompatibleDevice(SkCanvas* canvas,
SkBitmap::Config config,
int width, int height,
bool isOpaque) {
SkBaseDevice* device = canvas->getDevice();
if (device) {
return device->createCompatibleDevice(config, width, height, isOpaque);
} else {
return NULL;
}
}
#ifdef SK_SUPPORT_LEGACY_CANVAS_CREATECOMPATIBLEDEVICE
SkBaseDevice* SkCanvas::createCompatibleDevice(SkBitmap::Config config,
int width, int height,
bool isOpaque) {
return createCompatibleDevice(this, config, width, height, isOpaque);
}
#endif
int SkCanvas::internalSaveLayer(const SkRect* bounds, const SkPaint* paint,
SaveFlags flags, bool justForImageFilter) {
// do this before we create the layer. We don't call the public save() since
@ -864,8 +884,8 @@ int SkCanvas::internalSaveLayer(const SkRect* bounds, const SkPaint* paint,
SkBaseDevice* device;
if (paint && paint->getImageFilter()) {
device = this->createCompatibleDevice(config, ir.width(), ir.height(),
isOpaque);
device = createCompatibleDevice(this, config, ir.width(), ir.height(),
isOpaque);
} else {
device = this->createLayerDevice(config, ir.width(), ir.height(),
isOpaque);
@ -964,6 +984,15 @@ bool SkCanvas::isDrawingToLayer() const {
return fSaveLayerCount > 0;
}
SkSurface* SkCanvas::newSurface(const SkImageInfo& info) {
return this->onNewSurface(info);
}
SkSurface* SkCanvas::onNewSurface(const SkImageInfo& info) {
SkBaseDevice* dev = this->getDevice();
return dev ? dev->newSurface(info) : NULL;
}
/////////////////////////////////////////////////////////////////////////////
// can't draw it if its empty, or its too big for a fixed-point width or height
@ -1548,17 +1577,6 @@ SkBaseDevice* SkCanvas::createLayerDevice(SkBitmap::Config config,
}
}
SkBaseDevice* SkCanvas::createCompatibleDevice(SkBitmap::Config config,
int width, int height,
bool isOpaque) {
SkBaseDevice* device = this->getDevice();
if (device) {
return device->createCompatibleDevice(config, width, height, isOpaque);
} else {
return NULL;
}
}
GrContext* SkCanvas::getGrContext() {
#if SK_SUPPORT_GPU
SkBaseDevice* device = this->getTopDevice();

Просмотреть файл

@ -1,4 +1,3 @@
/*
* Copyright 2011 Google Inc.
*
@ -18,6 +17,7 @@
#endif
///////////////////////////////////////////////////////////////////////////////
SkBaseDevice::SkBaseDevice()
: fLeakyProperties(SkDeviceProperties::MakeDefault())
#ifdef SK_DEBUG
@ -115,3 +115,5 @@ bool SkBaseDevice::readPixels(SkBitmap* bitmap, int x, int y,
}
return result;
}
SkSurface* SkBaseDevice::newSurface(const SkImageInfo&) { return NULL; }

Просмотреть файл

@ -1,10 +1,10 @@
/*
* Copyright 2011 Google Inc.
*
* Use of this source code is governed by a BSD-style license that can be
* found in the LICENSE file.
*/
#include "SkPictureRecord.h"
#include "SkTSearch.h"
#include "SkPixelRef.h"
@ -12,6 +12,7 @@
#include "SkBBoxHierarchy.h"
#include "SkDevice.h"
#include "SkPictureStateTree.h"
#include "SkSurface.h"
#define HEAP_BLOCK_SIZE 4096
@ -1316,6 +1317,10 @@ void SkPictureRecord::endCommentGroup() {
///////////////////////////////////////////////////////////////////////////////
SkSurface* SkPictureRecord::onNewSurface(const SkImageInfo& info) {
return SkSurface::NewPicture(info.fWidth, info.fHeight);
}
void SkPictureRecord::addBitmap(const SkBitmap& bitmap) {
const int index = fBitmapHeap->insert(bitmap);
// In debug builds, a bad return value from insert() will crash, allowing for debugging. In

Просмотреть файл

@ -1,10 +1,10 @@
/*
* Copyright 2011 Google Inc.
*
* Use of this source code is governed by a BSD-style license that can be
* found in the LICENSE file.
*/
#ifndef SkPictureRecord_DEFINED
#define SkPictureRecord_DEFINED
@ -215,6 +215,8 @@ public:
#endif
protected:
virtual SkSurface* onNewSurface(const SkImageInfo&) SK_OVERRIDE;
// Return fontmetrics.fTop,fBottom in topbot[0,1], after they have been
// tweaked by paint.computeFastBounds().
static void ComputeFontMetricsTopBottom(const SkPaint& paint, SkScalar topbot[2]);

Просмотреть файл

@ -27,6 +27,7 @@
#include "SkPathEffect.h"
#include "SkRRect.h"
#include "SkStroke.h"
#include "SkSurface.h"
#include "SkTLazy.h"
#include "SkUtils.h"
#include "SkErrorInternals.h"
@ -1913,6 +1914,10 @@ SkBaseDevice* SkGpuDevice::onCreateCompatibleDevice(SkBitmap::Config config,
}
}
SkSurface* SkGpuDevice::newSurface(const SkImageInfo& info) {
return SkSurface::NewRenderTarget(fContext, info, fRenderTarget->numSamples());
}
SkGpuDevice::SkGpuDevice(GrContext* context,
GrTexture* texture,
bool needClear)

Просмотреть файл

@ -173,6 +173,8 @@ public:
virtual void writePixels(const SkBitmap& bitmap, int x, int y,
SkCanvas::Config8888 config8888) SK_OVERRIDE;
virtual SkSurface* newSurface(const SkImageInfo&) SK_OVERRIDE;
protected:
virtual const SkBitmap& onAccessBitmap() SK_OVERRIDE;
virtual bool onReadPixels(const SkBitmap& bitmap,
@ -495,6 +497,10 @@ SkBaseDevice* DeferredDevice::onCreateCompatibleDevice(
return immediateDevice()->createCompatibleDevice(config, width, height, isOpaque);
}
SkSurface* DeferredDevice::newSurface(const SkImageInfo& info) {
return this->immediateDevice()->newSurface(info);
}
bool DeferredDevice::onReadPixels(
const SkBitmap& bitmap, int x, int y, SkCanvas::Config8888 config8888) {
this->flushPendingCommands(kNormal_PlaybackMode);

Просмотреть файл

@ -825,14 +825,14 @@ static void TestDeferredCanvasCreateCompatibleDevice(skiatest::Reporter* reporte
NotificationCounter notificationCounter;
canvas->setNotificationClient(&notificationCounter);
SkAutoTUnref<SkBaseDevice> secondaryDevice(canvas->createCompatibleDevice(
SkBitmap::kARGB_8888_Config, 10, 10, false));
SkCanvas secondaryCanvas(secondaryDevice.get());
SkImageInfo info = SkImageInfo::MakeN32Premul(10, 10);
SkAutoTUnref<SkSurface> secondarySurface(canvas->newSurface(info));
SkRect rect = SkRect::MakeWH(5, 5);
SkPaint paint;
// After spawning a compatible canvas:
// 1) Verify that secondary canvas is usable and does not report to the notification client.
secondaryCanvas.drawRect(rect, paint);
surface->getCanvas()->drawRect(rect, paint);
REPORTER_ASSERT(reporter, notificationCounter.fStorageAllocatedChangedCount == 0);
// 2) Verify that original canvas is usable and still reports to the notification client.
canvas->drawRect(rect, paint);