add local-matrix to shader::context
BUG=skia: R=scroggo@google.com, dominikg@chromium.org Author: reed@google.com Review URL: https://codereview.chromium.org/263293005 git-svn-id: http://skia.googlecode.com/svn/trunk@14592 2bbb7eff-a529-9590-31e7-b0007b416f81
This commit is contained in:
parent
7418bd8cad
commit
80116dcf1e
@ -123,17 +123,17 @@ public:
|
||||
* ContextRec acts as a parameter bundle for creating Contexts.
|
||||
*/
|
||||
struct ContextRec {
|
||||
ContextRec() : fDevice(NULL), fPaint(NULL), fMatrix(NULL) {}
|
||||
ContextRec(const ContextRec& other)
|
||||
: fDevice(other.fDevice), fPaint(other.fPaint), fMatrix(other.fMatrix) {}
|
||||
ContextRec() : fDevice(NULL), fPaint(NULL), fMatrix(NULL), fLocalMatrix(NULL) {}
|
||||
ContextRec(const SkBitmap& device, const SkPaint& paint, const SkMatrix& matrix)
|
||||
: fDevice(&device)
|
||||
, fPaint(&paint)
|
||||
, fMatrix(&matrix) {}
|
||||
, fMatrix(&matrix)
|
||||
, fLocalMatrix(NULL) {}
|
||||
|
||||
const SkBitmap* fDevice; // the bitmap we are drawing into
|
||||
const SkPaint* fPaint; // the current paint associated with the draw
|
||||
const SkMatrix* fMatrix; // the current matrix in the canvas
|
||||
const SkBitmap* fDevice; // the bitmap we are drawing into
|
||||
const SkPaint* fPaint; // the current paint associated with the draw
|
||||
const SkMatrix* fMatrix; // the current matrix in the canvas
|
||||
const SkMatrix* fLocalMatrix; // optional local matrix
|
||||
};
|
||||
|
||||
class Context : public ::SkNoncopyable {
|
||||
@ -200,14 +200,15 @@ public:
|
||||
};
|
||||
static MatrixClass ComputeMatrixClass(const SkMatrix&);
|
||||
|
||||
uint8_t getPaintAlpha() const { return fPaintAlpha; }
|
||||
const SkMatrix& getTotalInverse() const { return fTotalInverse; }
|
||||
MatrixClass getInverseClass() const { return (MatrixClass)fTotalInverseClass; }
|
||||
|
||||
uint8_t getPaintAlpha() const { return fPaintAlpha; }
|
||||
const SkMatrix& getTotalInverse() const { return fTotalInverse; }
|
||||
MatrixClass getInverseClass() const { return (MatrixClass)fTotalInverseClass; }
|
||||
const SkMatrix& getCTM() const { return fCTM; }
|
||||
private:
|
||||
SkMatrix fTotalInverse;
|
||||
uint8_t fPaintAlpha;
|
||||
uint8_t fTotalInverseClass;
|
||||
SkMatrix fCTM;
|
||||
SkMatrix fTotalInverse;
|
||||
uint8_t fPaintAlpha;
|
||||
uint8_t fTotalInverseClass;
|
||||
|
||||
typedef SkNoncopyable INHERITED;
|
||||
};
|
||||
|
@ -71,10 +71,7 @@ private:
|
||||
// an Sk3DBlitter in SkDraw.cpp
|
||||
// Note that some contexts may contain other contexts (e.g. for compose shaders), but we've not
|
||||
// yet found a situation where the size below isn't big enough.
|
||||
typedef SkSmallAllocator<3, sizeof(SkBitmapProcShader) +
|
||||
sizeof(SkBitmapProcShader::BitmapProcShaderContext) +
|
||||
sizeof(SkBitmapProcState) +
|
||||
sizeof(void*) * 2> SkTBlitterAllocator;
|
||||
typedef SkSmallAllocator<3, 768> SkTBlitterAllocator;
|
||||
|
||||
// If alloc is non-NULL, it will be used to allocate the returned SkShader, and MUST outlive
|
||||
// the SkShader.
|
||||
|
@ -1,4 +1,3 @@
|
||||
|
||||
/*
|
||||
* Copyright 2006 The Android Open Source Project
|
||||
*
|
||||
@ -6,7 +5,6 @@
|
||||
* found in the LICENSE file.
|
||||
*/
|
||||
|
||||
|
||||
#include "SkBlitter.h"
|
||||
#include "SkAntiRun.h"
|
||||
#include "SkColor.h"
|
||||
@ -26,8 +24,7 @@ SkBlitter::~SkBlitter() {}
|
||||
|
||||
bool SkBlitter::isNullBlitter() const { return false; }
|
||||
|
||||
bool SkBlitter::resetShaderContext(const SkBitmap& device, const SkPaint& paint,
|
||||
const SkMatrix& matrix) {
|
||||
bool SkBlitter::resetShaderContext(const SkShader::ContextRec&) {
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -1030,10 +1027,7 @@ SkShaderBlitter::~SkShaderBlitter() {
|
||||
fShader->unref();
|
||||
}
|
||||
|
||||
bool SkShaderBlitter::resetShaderContext(const SkBitmap& device, const SkPaint& paint,
|
||||
const SkMatrix& matrix) {
|
||||
SkShader::ContextRec rec(device, paint, matrix);
|
||||
|
||||
bool SkShaderBlitter::resetShaderContext(const SkShader::ContextRec& rec) {
|
||||
// Only destroy the old context if we have a new one. We need to ensure to have a
|
||||
// live context in fShaderContext because the storage is owned by an SkSmallAllocator
|
||||
// outside of this class.
|
||||
@ -1045,6 +1039,7 @@ bool SkShaderBlitter::resetShaderContext(const SkBitmap& device, const SkPaint&
|
||||
// Need a valid context in fShaderContext's storage, so we can later (or our caller) call
|
||||
// the in-place destructor.
|
||||
SkNEW_PLACEMENT_ARGS(fShaderContext, SkTransparentShaderContext, (*fShader, rec));
|
||||
return false;
|
||||
}
|
||||
return ctx != NULL;
|
||||
return true;
|
||||
}
|
||||
|
@ -64,8 +64,7 @@ public:
|
||||
/**
|
||||
* Special methods for SkShaderBlitter. On all other classes this is a no-op.
|
||||
*/
|
||||
virtual bool resetShaderContext(const SkBitmap& device, const SkPaint& paint,
|
||||
const SkMatrix& matrix);
|
||||
virtual bool resetShaderContext(const SkShader::ContextRec&);
|
||||
virtual SkShader::Context* getShaderContext() const;
|
||||
|
||||
///@name non-virtual helpers
|
||||
|
@ -41,8 +41,7 @@ public:
|
||||
* Will create the context at the same location as the old one (this is safe
|
||||
* because the shader itself is unchanged).
|
||||
*/
|
||||
virtual bool resetShaderContext(const SkBitmap& device, const SkPaint& paint,
|
||||
const SkMatrix& matrix) SK_OVERRIDE;
|
||||
virtual bool resetShaderContext(const SkShader::ContextRec&) SK_OVERRIDE;
|
||||
|
||||
virtual SkShader::Context* getShaderContext() const SK_OVERRIDE { return fShaderContext; }
|
||||
|
||||
|
@ -2403,7 +2403,13 @@ bool SkTriColorShader::TriColorShaderContext::setup(const SkPoint pts[], const S
|
||||
if (!m.invert(&im)) {
|
||||
return false;
|
||||
}
|
||||
fDstToUnit.setConcat(im, this->getTotalInverse());
|
||||
// We can't call getTotalInverse(), because we explicitly don't want to look at the localmatrix
|
||||
// as our interators are intrinsically tied to the vertices, and nothing else.
|
||||
SkMatrix ctmInv;
|
||||
if (!this->getCTM().invert(&ctmInv)) {
|
||||
return false;
|
||||
}
|
||||
fDstToUnit.setConcat(im, ctmInv);
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -2556,18 +2562,13 @@ void SkDraw::drawVertices(SkCanvas::VertexMode vmode, int count,
|
||||
VertState::Proc vertProc = state.chooseProc(vmode);
|
||||
|
||||
if (NULL != textures || NULL != colors) {
|
||||
SkMatrix tempM;
|
||||
SkMatrix savedLocalM;
|
||||
if (shader) {
|
||||
savedLocalM = shader->getLocalMatrix();
|
||||
}
|
||||
|
||||
while (vertProc(&state)) {
|
||||
if (NULL != textures) {
|
||||
SkMatrix tempM;
|
||||
if (texture_to_matrix(state, vertices, textures, &tempM)) {
|
||||
tempM.postConcat(savedLocalM);
|
||||
shader->setLocalMatrix(tempM);
|
||||
if (!blitter->resetShaderContext(*fBitmap, p, *fMatrix)) {
|
||||
SkShader::ContextRec rec(*fBitmap, p, *fMatrix);
|
||||
rec.fLocalMatrix = &tempM;
|
||||
if (!blitter->resetShaderContext(rec)) {
|
||||
continue;
|
||||
}
|
||||
}
|
||||
@ -2603,11 +2604,6 @@ void SkDraw::drawVertices(SkCanvas::VertexMode vmode, int count,
|
||||
};
|
||||
SkScan::FillTriangle(tmp, *fRC, blitter.get());
|
||||
}
|
||||
|
||||
// now restore the shader's original local matrix
|
||||
if (NULL != shader) {
|
||||
shader->setLocalMatrix(savedLocalM);
|
||||
}
|
||||
} else {
|
||||
// no colors[] and no texture
|
||||
HairProc hairProc = ChooseHairProc(paint.isAntiAlias());
|
||||
|
@ -52,7 +52,7 @@ void SkPictureShader::flatten(SkWriteBuffer& buffer) const {
|
||||
fPicture->flatten(buffer);
|
||||
}
|
||||
|
||||
SkShader* SkPictureShader::refBitmapShader(const SkMatrix& matrix) const {
|
||||
SkShader* SkPictureShader::refBitmapShader(const SkMatrix& matrix, const SkMatrix* localM) const {
|
||||
SkASSERT(fPicture && fPicture->width() > 0 && fPicture->height() > 0);
|
||||
|
||||
SkMatrix m;
|
||||
@ -61,6 +61,9 @@ SkShader* SkPictureShader::refBitmapShader(const SkMatrix& matrix) const {
|
||||
} else {
|
||||
m = matrix;
|
||||
}
|
||||
if (localM) {
|
||||
m.preConcat(*localM);
|
||||
}
|
||||
|
||||
// Use a rotation-invariant scale
|
||||
SkPoint scale;
|
||||
@ -115,7 +118,7 @@ size_t SkPictureShader::contextSize() const {
|
||||
}
|
||||
|
||||
SkShader::Context* SkPictureShader::onCreateContext(const ContextRec& rec, void* storage) const {
|
||||
SkAutoTUnref<SkShader> bitmapShader(this->refBitmapShader(*rec.fMatrix));
|
||||
SkAutoTUnref<SkShader> bitmapShader(this->refBitmapShader(*rec.fMatrix, rec.fLocalMatrix));
|
||||
if (NULL == bitmapShader.get()) {
|
||||
return NULL;
|
||||
}
|
||||
@ -190,7 +193,7 @@ void SkPictureShader::toString(SkString* str) const {
|
||||
|
||||
#if SK_SUPPORT_GPU
|
||||
GrEffectRef* SkPictureShader::asNewEffect(GrContext* context, const SkPaint& paint) const {
|
||||
SkAutoTUnref<SkShader> bitmapShader(this->refBitmapShader(context->getMatrix()));
|
||||
SkAutoTUnref<SkShader> bitmapShader(this->refBitmapShader(context->getMatrix(), NULL));
|
||||
if (!bitmapShader) {
|
||||
return NULL;
|
||||
}
|
||||
|
@ -41,7 +41,7 @@ protected:
|
||||
private:
|
||||
SkPictureShader(SkPicture*, TileMode, TileMode, const SkMatrix* = NULL);
|
||||
|
||||
SkShader* refBitmapShader(const SkMatrix&) const;
|
||||
SkShader* refBitmapShader(const SkMatrix&, const SkMatrix* localMatrix) const;
|
||||
|
||||
SkPicture* fPicture;
|
||||
TileMode fTmx, fTmy;
|
||||
|
@ -53,6 +53,10 @@ bool SkShader::computeTotalInverse(const ContextRec& rec, SkMatrix* totalInverse
|
||||
total.setConcat(*m, this->getLocalMatrix());
|
||||
m = &total;
|
||||
}
|
||||
if (rec.fLocalMatrix) {
|
||||
total.setConcat(*m, *rec.fLocalMatrix);
|
||||
m = &total;
|
||||
}
|
||||
return m->invert(totalInverse);
|
||||
}
|
||||
|
||||
@ -63,7 +67,7 @@ SkShader::Context* SkShader::createContext(const ContextRec& rec, void* storage)
|
||||
return this->onCreateContext(rec, storage);
|
||||
}
|
||||
|
||||
SkShader::Context* SkShader::onCreateContext(const ContextRec&, void*) const {
|
||||
SkShader::Context* SkShader::onCreateContext(const ContextRec& rec, void*) const {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@ -72,7 +76,7 @@ size_t SkShader::contextSize() const {
|
||||
}
|
||||
|
||||
SkShader::Context::Context(const SkShader& shader, const ContextRec& rec)
|
||||
: fShader(shader)
|
||||
: fShader(shader), fCTM(*rec.fMatrix)
|
||||
{
|
||||
// Because the context parameters must be valid at this point, we know that the matrix is
|
||||
// invertible.
|
||||
|
Loading…
Reference in New Issue
Block a user