Merge pull request #1144 from chinmaygarde/master

Use the CTM of the canvas to determine the dimensions of the rasterized image
This commit is contained in:
Chinmay Garde 2015-09-11 15:37:41 -07:00
commit 97489dadec
9 changed files with 46 additions and 56 deletions

View File

@ -32,7 +32,7 @@ void DrawCheckerboard(SkCanvas* canvas, int width, int height) {
// Draw a checkerboard
canvas->clipRect(rect);
DrawCheckerboard(canvas, 0x9900FF00, 0x00000000, 12);
DrawCheckerboard(canvas, 0x4400FF00, 0x00000000, 12);
// Stroke the drawn area
SkPaint debugPaint;

View File

@ -15,9 +15,5 @@ Layer::Layer() {
Layer::~Layer() {
}
SkMatrix Layer::model_view_matrix(const SkMatrix& model_matrix) const {
return model_matrix;
}
} // namespace compositor
} // namespace sky

View File

@ -34,8 +34,6 @@ class Layer {
virtual void Paint(PaintContext::ScopedFrame& frame) = 0;
virtual SkMatrix model_view_matrix(const SkMatrix& model_matrix) const;
ContainerLayer* parent() const { return parent_; }
void set_parent(ContainerLayer* parent) { parent_ = parent; }

View File

@ -14,22 +14,19 @@ PictureLayer::PictureLayer() {
PictureLayer::~PictureLayer() {
}
SkMatrix PictureLayer::model_view_matrix(const SkMatrix& model_matrix) const {
SkMatrix modelView = model_matrix;
modelView.postTranslate(offset_.x(), offset_.y());
return modelView;
}
void PictureLayer::Paint(PaintContext::ScopedFrame& frame) {
DCHECK(picture_);
const SkRect& bounds = paint_bounds();
SkISize size = SkISize::Make(bounds.width(), bounds.height());
RefPtr<SkImage> image =
frame.paint_context().rasterizer().GetCachedImageIfPresent(
frame.paint_context(), frame.gr_context(), picture_.get(), size);
SkCanvas& canvas = frame.canvas();
const SkRect& bounds = paint_bounds();
const SkMatrix& ctm = canvas.getTotalMatrix();
const SkISize physical_size = SkISize::Make(
bounds.width() * ctm.getScaleX(), bounds.height() * ctm.getScaleY());
PictureRasterzier& rasterizer = frame.paint_context().rasterizer();
RefPtr<SkImage> image = rasterizer.GetCachedImageIfPresent(
frame.paint_context(), frame.gr_context(), picture_.get(), physical_size,
ctm);
if (image) {
canvas.drawImage(image.get(), offset_.x(), offset_.y());

View File

@ -19,8 +19,6 @@ class PictureLayer : public Layer {
void set_picture(PassRefPtr<SkPicture> picture) { picture_ = picture; }
SkMatrix model_view_matrix(const SkMatrix& model_matrix) const override;
SkPicture* picture() const { return picture_.get(); }
void Paint(PaintContext::ScopedFrame& frame) override;

View File

@ -38,19 +38,22 @@ PictureRasterzier::Value::Value()
PictureRasterzier::Value::~Value() {
}
RefPtr<SkImage> PictureRasterzier::ImageFromPicture(PaintContext& context,
GrContext* gr_context,
SkPicture* picture,
const SkISize& size) {
RefPtr<SkImage> PictureRasterzier::ImageFromPicture(
PaintContext& context,
GrContext* gr_context,
SkPicture* picture,
const SkISize& physical_size,
const SkMatrix& incoming_ctm) {
// Step 1: Create a texture from the context's texture provider
GrSurfaceDesc desc;
desc.fWidth = size.width();
desc.fHeight = size.height();
desc.fFlags = kRenderTarget_GrSurfaceFlag;
desc.fConfig = kRGBA_8888_GrPixelConfig;
GrSurfaceDesc surfaceDesc;
surfaceDesc.fWidth = physical_size.width();
surfaceDesc.fHeight = physical_size.height();
surfaceDesc.fFlags = kRenderTarget_GrSurfaceFlag;
surfaceDesc.fConfig = kRGBA_8888_GrPixelConfig;
GrTexture* texture = gr_context->textureProvider()->createTexture(desc, true);
GrTexture* texture =
gr_context->textureProvider()->createTexture(surfaceDesc, true);
if (!texture) {
// The texture provider could not allocate a texture backing. Render
@ -61,14 +64,14 @@ RefPtr<SkImage> PictureRasterzier::ImageFromPicture(PaintContext& context,
// Step 2: Create a backend render target description for the created texture
GrBackendTextureDesc backendDesc;
backendDesc.fConfig = desc.fConfig;
backendDesc.fWidth = desc.fWidth;
backendDesc.fHeight = desc.fHeight;
backendDesc.fSampleCnt = desc.fSampleCnt;
backendDesc.fFlags = kRenderTarget_GrBackendTextureFlag;
backendDesc.fConfig = desc.fConfig;
backendDesc.fTextureHandle = texture->getTextureHandle();
GrBackendTextureDesc textureDesc;
textureDesc.fConfig = surfaceDesc.fConfig;
textureDesc.fWidth = physical_size.width() / incoming_ctm.getScaleX();
textureDesc.fHeight = physical_size.height() / incoming_ctm.getScaleY();
textureDesc.fSampleCnt = surfaceDesc.fSampleCnt;
textureDesc.fFlags = kRenderTarget_GrBackendTextureFlag;
textureDesc.fConfig = surfaceDesc.fConfig;
textureDesc.fTextureHandle = texture->getTextureHandle();
// Step 3: Render the picture into the offscreen texture
@ -82,17 +85,19 @@ RefPtr<SkImage> PictureRasterzier::ImageFromPicture(PaintContext& context,
SkCanvas* canvas = surface->getCanvas();
DCHECK(canvas);
canvas->setMatrix(
SkMatrix::MakeScale(incoming_ctm.getScaleX(), incoming_ctm.getScaleY()));
canvas->drawPicture(picture);
if (context.options().isEnabled(
CompositorOptions::Option::HightlightRasterizedImages)) {
DrawCheckerboard(canvas, desc.fWidth, desc.fHeight);
DrawCheckerboard(canvas, textureDesc.fWidth, textureDesc.fHeight);
}
// Step 4: Create an image representation from the texture
RefPtr<SkImage> image = adoptRef(
SkImage::NewFromTexture(gr_context, backendDesc, kPremul_SkAlphaType,
SkImage::NewFromTexture(gr_context, textureDesc, kPremul_SkAlphaType,
&ImageReleaseProc, texture));
if (image) {
@ -106,12 +111,13 @@ RefPtr<SkImage> PictureRasterzier::GetCachedImageIfPresent(
PaintContext& context,
GrContext* gr_context,
SkPicture* picture,
SkISize size) {
if (size.isEmpty() || picture == nullptr || gr_context == nullptr) {
const SkISize& physical_size,
const SkMatrix& incoming_ctm) {
if (physical_size.isEmpty() || picture == nullptr || gr_context == nullptr) {
return nullptr;
}
const Key key(picture->uniqueID(), size);
const Key key(picture->uniqueID(), physical_size);
Value& value = cache_[key];
@ -122,10 +128,11 @@ RefPtr<SkImage> PictureRasterzier::GetCachedImageIfPresent(
value.access_count++;
DCHECK(value.access_count == 1)
<< "Did you forget to call purge_cache between frames?";
<< "Did you forget to call PurgeCache between frames?";
if (!value.image) {
value.image = ImageFromPicture(context, gr_context, picture, size);
value.image = ImageFromPicture(context, gr_context, picture, physical_size,
incoming_ctm);
}
if (value.image) {

View File

@ -28,7 +28,8 @@ class PictureRasterzier {
RefPtr<SkImage> GetCachedImageIfPresent(PaintContext& context,
GrContext* gr_context,
SkPicture* picture,
SkISize size);
const SkISize& physical_size,
const SkMatrix& incoming_ctm);
void PurgeCache();
@ -80,7 +81,8 @@ class PictureRasterzier {
RefPtr<SkImage> ImageFromPicture(PaintContext& context,
GrContext* gr_context,
SkPicture* picture,
const SkISize& size);
const SkISize& physical_size,
const SkMatrix& incomingCTM);
DISALLOW_COPY_AND_ASSIGN(PictureRasterzier);
};

View File

@ -13,12 +13,6 @@ TransformLayer::TransformLayer() {
TransformLayer::~TransformLayer() {
}
SkMatrix TransformLayer::model_view_matrix(const SkMatrix& model_matrix) const {
SkMatrix modelView = model_matrix;
modelView.postConcat(transform_);
return modelView;
}
void TransformLayer::Paint(PaintContext::ScopedFrame& frame) {
SkCanvas& canvas = frame.canvas();
canvas.save();

View File

@ -17,8 +17,6 @@ class TransformLayer : public ContainerLayer {
void set_transform(const SkMatrix& transform) { transform_ = transform; }
SkMatrix model_view_matrix(const SkMatrix& model_matrix) const override;
void Paint(PaintContext::ScopedFrame& frame) override;
private: