Change TextContext handling of stages and draw targets; this allows us to

assert in GrContext::setPaint() that all stages are disabled every time
the paint is set.

Watch for possible performance implications.

http://codereview.appspot.com/6347043/



git-svn-id: http://skia.googlecode.com/svn/trunk@4531 2bbb7eff-a529-9590-31e7-b0007b416f81
This commit is contained in:
tomhudson@google.com 2012-07-11 14:41:19 +00:00
parent 96dde45518
commit cb325ceda1
3 changed files with 91 additions and 13 deletions

View File

@ -8,6 +8,7 @@
#include "gm.h"
#include "SkCanvas.h"
#include "SkGradientShader.h"
#include "SkTypeface.h"
// test shader w/ transparency
static SkShader* make_grad(SkScalar width) {
@ -27,8 +28,77 @@ static SkShader* make_grad2(SkScalar width) {
SkShader::kMirror_TileMode);
}
static SkShader* make_chrome_solid() {
SkColor colors[] = { SK_ColorGREEN, SK_ColorGREEN };
SkPoint pts[] = { { 0, 0 }, { 1, 0 } };
return SkGradientShader::CreateLinear(pts, colors, NULL, 2,
SkShader::kClamp_TileMode);
}
namespace skiagm {
// Replicate chrome layout test - clipped pathed gradient-shaded text
class ChromeGradTextGM1 : public GM {
public:
ChromeGradTextGM1() { }
protected:
virtual SkString onShortName() { return SkString("chrome_gradtext1"); }
virtual SkISize onISize() { return make_isize(500, 480); }
virtual void onDraw(SkCanvas* canvas) {
SkPaint paint;
const SkISize& size = this->getISize();
SkRect r = SkRect::MakeWH(SkIntToScalar(100), SkIntToScalar(100));
canvas->clipRect(r);
paint.setColor(SK_ColorRED);
canvas->drawRect(r, paint);
// Minimal repro doesn't require AA, LCD, or a nondefault typeface
paint.setShader(make_chrome_solid())->unref();
paint.setTextSize(SkIntToScalar(500));
canvas->drawText("I", 1, 0, 100, paint);
}
private:
typedef GM INHERITED;
};
// Replicate chrome layout test - switching between solid & gadient text
class ChromeGradTextGM2 : public GM {
public:
ChromeGradTextGM2() { }
protected:
virtual SkString onShortName() { return SkString("chrome_gradtext2"); }
virtual SkISize onISize() { return make_isize(500, 480); }
virtual void onDraw(SkCanvas* canvas) {
SkPaint paint;
const SkISize& size = this->getISize();
SkRect r = SkRect::MakeWH(SkIntToScalar(100), SkIntToScalar(100));
paint.setStyle(SkPaint::kFill_Style);
canvas->drawText("Normal Fill Text", 16, 0, 50, paint);
paint.setStyle(SkPaint::kStroke_Style);
canvas->drawText("Normal Stroke Text", 18, 0, 100, paint);
// Minimal repro doesn't require AA, LCD, or a nondefault typeface
paint.setShader(make_chrome_solid())->unref();
paint.setStyle(SkPaint::kFill_Style);
canvas->drawText("Gradient Fill Text", 18, 0, 150, paint);
paint.setStyle(SkPaint::kStroke_Style);
canvas->drawText("Gradient Stroke Text", 20, 0, 200, paint);
}
private:
typedef GM INHERITED;
};
class GradTextGM : public GM {
public:
GradTextGM () {}
@ -91,7 +161,11 @@ private:
//////////////////////////////////////////////////////////////////////////////
static GM* MyFactory(void*) { return new GradTextGM; }
static GMRegistry reg(MyFactory);
static GM* CMyFactory(void*) { return new ChromeGradTextGM1; }
static GM* CMyFactory2(void*) { return new ChromeGradTextGM2; }
static GMRegistry reg(MyFactory);
static GMRegistry Creg(CMyFactory);
static GMRegistry Creg2(CMyFactory2);
}

View File

@ -1589,8 +1589,7 @@ void GrContext::internalWriteRenderTargetPixels(GrRenderTarget* target,
////////////////////////////////////////////////////////////////////////////////
void GrContext::setPaint(const GrPaint& paint) {
// TODO: reenable this once we've cleaned up text state management
//GrAssert(fDrawState->stagesDisabled());
GrAssert(fDrawState->stagesDisabled());
for (int i = 0; i < GrPaint::kMaxTextures; ++i) {
int s = i + GrPaint::kFirstTextureStage;

View File

@ -23,8 +23,11 @@ enum {
};
void GrTextContext::flushGlyphs() {
if (NULL == fDrawTarget) {
return;
}
GrDrawState* drawState = fDrawTarget->drawState();
if (fCurrVertex > 0) {
GrDrawState* drawState = fDrawTarget->drawState();
// setup our sampler state for our text texture/atlas
GrSamplerState::Filter filter;
if (fExtMatrix.isIdentity()) {
@ -68,8 +71,9 @@ void GrTextContext::flushGlyphs() {
fMaxVertices = 0;
fCurrVertex = 0;
GrSafeSetNull(fCurrTexture);
drawState->disableStage(kGlyphMaskStage);
}
drawState->disableStages();
fDrawTarget = NULL;
}
GrTextContext::GrTextContext(GrContext* context,
@ -134,7 +138,7 @@ GrTextContext::GrTextContext(GrContext* context,
}
}
fDrawTarget = fContext->getTextTarget(fPaint);
fDrawTarget = NULL;
fVertices = NULL;
fMaxVertices = 0;
@ -246,19 +250,20 @@ HAS_ATLAS:
// If we need to reserve vertices allow the draw target to suggest
// a number of verts to reserve and whether to perform a flush.
fMaxVertices = kMinRequestedVerts;
bool flush = fDrawTarget->geometryHints(fVertexLayout,
bool flush = (NULL != fDrawTarget) &&
fDrawTarget->geometryHints(fVertexLayout,
&fMaxVertices,
NULL);
if (flush) {
this->flushGlyphs();
fContext->flush();
fDrawTarget = fContext->getTextTarget(fPaint);
fMaxVertices = kDefaultRequestedVerts;
// ignore return, no point in flushing again.
fDrawTarget->geometryHints(fVertexLayout,
&fMaxVertices,
NULL);
}
fDrawTarget = fContext->getTextTarget(fPaint);
fMaxVertices = kDefaultRequestedVerts;
// ignore return, no point in flushing again.
fDrawTarget->geometryHints(fVertexLayout,
&fMaxVertices,
NULL);
int maxQuadVertices = 4 * fContext->getQuadIndexBuffer()->maxQuads();
if (fMaxVertices < kMinRequestedVerts) {