summaryrefslogtreecommitdiffstats
path: root/libs
diff options
context:
space:
mode:
authorRomain Guy <romainguy@google.com>2011-01-14 15:29:36 -0800
committerAndroid (Google) Code Review <android-gerrit@google.com>2011-01-14 15:29:36 -0800
commit4b26d057665c662c782e3baa5d9ca8287c96ede4 (patch)
treedeacd21fbf60b6d111557c5607e2b1468c970eaa /libs
parent20220dfa428f97e2def04e339ddfbb3a0531d456 (diff)
parent24c00216687ac87fe531dc4d4168ac0c0ca04ea6 (diff)
downloadframeworks_base-4b26d057665c662c782e3baa5d9ca8287c96ede4.zip
frameworks_base-4b26d057665c662c782e3baa5d9ca8287c96ede4.tar.gz
frameworks_base-4b26d057665c662c782e3baa5d9ca8287c96ede4.tar.bz2
Merge "Copy shaders when recording them in display lists." into honeycomb
Diffstat (limited to 'libs')
-rw-r--r--libs/hwui/DisplayListRenderer.cpp22
-rw-r--r--libs/hwui/DisplayListRenderer.h33
-rw-r--r--libs/hwui/SkiaShader.cpp56
-rw-r--r--libs/hwui/SkiaShader.h34
4 files changed, 121 insertions, 24 deletions
diff --git a/libs/hwui/DisplayListRenderer.cpp b/libs/hwui/DisplayListRenderer.cpp
index 75b1671..747543f 100644
--- a/libs/hwui/DisplayListRenderer.cpp
+++ b/libs/hwui/DisplayListRenderer.cpp
@@ -128,10 +128,10 @@ DisplayList::~DisplayList() {
}
mBitmapResources.clear();
- for (size_t i = 0; i < mShaderResources.size(); i++) {
- caches.resourceCache.decrementRefcount(mShaderResources.itemAt(i));
+ for (size_t i = 0; i < mShaders.size(); i++) {
+ delete mShaders.itemAt(i);
}
- mShaderResources.clear();
+ mShaders.clear();
for (size_t i = 0; i < mPaints.size(); i++) {
delete mPaints.itemAt(i);
@@ -179,11 +179,9 @@ void DisplayList::initFromDisplayListRenderer(const DisplayListRenderer& recorde
caches.resourceCache.incrementRefcount(resource);
}
- const Vector<SkiaShader*> &shaderResources = recorder.getShaderResources();
- for (size_t i = 0; i < shaderResources.size(); i++) {
- SkiaShader* resource = shaderResources.itemAt(i);
- mShaderResources.add(resource);
- caches.resourceCache.incrementRefcount(resource);
+ const Vector<SkiaShader*> &shaders = recorder.getShaders();
+ for (size_t i = 0; i < shaders.size(); i++) {
+ mShaders.add(shaders.itemAt(i));
}
const Vector<SkPaint*> &paints = recorder.getPaints();
@@ -407,14 +405,10 @@ void DisplayListRenderer::reset() {
}
mBitmapResources.clear();
- for (size_t i = 0; i < mShaderResources.size(); i++) {
- SkiaShader* resource = mShaderResources.itemAt(i);
- caches.resourceCache.decrementRefcount(resource);
- }
- mShaderResources.clear();
-
mPaints.clear();
mPaintMap.clear();
+ mShaders.clear();
+ mShaderMap.clear();
mMatrices.clear();
}
diff --git a/libs/hwui/DisplayListRenderer.h b/libs/hwui/DisplayListRenderer.h
index cc52309..112e455 100644
--- a/libs/hwui/DisplayListRenderer.h
+++ b/libs/hwui/DisplayListRenderer.h
@@ -206,11 +206,11 @@ private:
PathHeap* mPathHeap;
Vector<SkBitmap*> mBitmapResources;
- Vector<SkiaShader*> mShaderResources;
Vector<SkiaColorFilter*> mFilterResources;
Vector<SkPaint*> mPaints;
Vector<SkMatrix*> mMatrices;
+ Vector<SkiaShader*> mShaders;
mutable SkFlattenableReadBuffer mReader;
@@ -291,8 +291,8 @@ public:
return mBitmapResources;
}
- const Vector<SkiaShader*>& getShaderResources() const {
- return mShaderResources;
+ const Vector<SkiaShader*>& getShaders() const {
+ return mShaders;
}
const Vector<SkPaint*>& getPaints() const {
@@ -366,12 +366,12 @@ private:
}
inline void addPaint(SkPaint* paint) {
- if (paint == NULL) {
+ if (!paint) {
addInt((int) NULL);
return;
}
- SkPaint *paintCopy = mPaintMap.valueFor(paint);
+ SkPaint* paintCopy = mPaintMap.valueFor(paint);
if (paintCopy == NULL || paintCopy->getGenerationID() != paint->getGenerationID()) {
paintCopy = new SkPaint(*paint);
mPaintMap.add(paint, paintCopy);
@@ -406,10 +406,20 @@ private:
}
inline void addShader(SkiaShader* shader) {
- addInt((int) shader);
- mShaderResources.add(shader);
- Caches& caches = Caches::getInstance();
- caches.resourceCache.incrementRefcount(shader);
+ if (!shader) {
+ addInt((int) NULL);
+ return;
+ }
+
+ SkiaShader* shaderCopy = mShaderMap.valueFor(shader);
+ // TODO: We also need to handle generation ID changes in compose shaders
+ if (!shaderCopy || shaderCopy->getGenerationId() != shader->getGenerationId()) {
+ shaderCopy = shader->copy();
+ mShaderMap.add(shader, shaderCopy);
+ mShaders.add(shader);
+ }
+
+ addInt((int) shaderCopy);
}
inline void addColorFilter(SkiaColorFilter* colorFilter) {
@@ -422,11 +432,14 @@ private:
SkChunkAlloc mHeap;
Vector<SkBitmap*> mBitmapResources;
- Vector<SkiaShader*> mShaderResources;
Vector<SkiaColorFilter*> mFilterResources;
Vector<SkPaint*> mPaints;
DefaultKeyedVector<SkPaint*, SkPaint*> mPaintMap;
+
+ Vector<SkiaShader*> mShaders;
+ DefaultKeyedVector<SkiaShader*, SkiaShader*> mShaderMap;
+
Vector<SkMatrix*> mMatrices;
PathHeap* mPathHeap;
diff --git a/libs/hwui/SkiaShader.cpp b/libs/hwui/SkiaShader.cpp
index 590a9d7..a1783df 100644
--- a/libs/hwui/SkiaShader.cpp
+++ b/libs/hwui/SkiaShader.cpp
@@ -47,10 +47,22 @@ static const GLint gTileModes[] = {
// Base shader
///////////////////////////////////////////////////////////////////////////////
+void SkiaShader::copyFrom(const SkiaShader& shader) {
+ mType = shader.mType;
+ mKey = shader.mKey;
+ mTileX = shader.mTileX;
+ mTileY = shader.mTileY;
+ mBlend = shader.mBlend;
+ mUnitMatrix = shader.mUnitMatrix;
+ mShaderMatrix = shader.mShaderMatrix;
+ mGenerationId = shader.mGenerationId;
+}
+
SkiaShader::SkiaShader(Type type, SkShader* key, SkShader::TileMode tileX,
SkShader::TileMode tileY, SkMatrix* matrix, bool blend):
mType(type), mKey(key), mTileX(tileX), mTileY(tileY), mBlend(blend) {
setMatrix(matrix);
+ mGenerationId = 0;
}
SkiaShader::~SkiaShader() {
@@ -90,6 +102,13 @@ SkiaBitmapShader::SkiaBitmapShader(SkBitmap* bitmap, SkShader* key, SkShader::Ti
updateLocalMatrix(matrix);
}
+SkiaShader* SkiaBitmapShader::copy() {
+ SkiaBitmapShader* copy = new SkiaBitmapShader();
+ copy->copyFrom(*this);
+ copy->mBitmap = mBitmap;
+ return copy;
+}
+
void SkiaBitmapShader::describe(ProgramDescription& description, const Extensions& extensions) {
Texture* texture = mTextureCache->get(mBitmap);
if (!texture) return;
@@ -183,6 +202,16 @@ SkiaLinearGradientShader::~SkiaLinearGradientShader() {
delete[] mPositions;
}
+SkiaShader* SkiaLinearGradientShader::copy() {
+ SkiaLinearGradientShader* copy = new SkiaLinearGradientShader();
+ copy->copyFrom(*this);
+ copy->mBounds = mBounds;
+ copy->mColors = mColors;
+ copy->mPositions = mPositions;
+ copy->mCount = mCount;
+ return copy;
+}
+
void SkiaLinearGradientShader::describe(ProgramDescription& description,
const Extensions& extensions) {
description.hasGradient = true;
@@ -238,6 +267,15 @@ SkiaCircularGradientShader::SkiaCircularGradientShader(float x, float y, float r
updateLocalMatrix(matrix);
}
+SkiaShader* SkiaCircularGradientShader::copy() {
+ SkiaCircularGradientShader* copy = new SkiaCircularGradientShader();
+ copy->copyFrom(*this);
+ copy->mColors = mColors;
+ copy->mPositions = mPositions;
+ copy->mCount = mCount;
+ return copy;
+}
+
void SkiaCircularGradientShader::describe(ProgramDescription& description,
const Extensions& extensions) {
description.hasGradient = true;
@@ -276,6 +314,15 @@ SkiaSweepGradientShader::~SkiaSweepGradientShader() {
delete[] mPositions;
}
+SkiaShader* SkiaSweepGradientShader::copy() {
+ SkiaSweepGradientShader* copy = new SkiaSweepGradientShader();
+ copy->copyFrom(*this);
+ copy->mColors = mColors;
+ copy->mPositions = mPositions;
+ copy->mCount = mCount;
+ return copy;
+}
+
void SkiaSweepGradientShader::describe(ProgramDescription& description,
const Extensions& extensions) {
description.hasGradient = true;
@@ -318,6 +365,15 @@ SkiaComposeShader::SkiaComposeShader(SkiaShader* first, SkiaShader* second,
NULL, first->blend() || second->blend()), mFirst(first), mSecond(second), mMode(mode) {
}
+SkiaShader* SkiaComposeShader::copy() {
+ SkiaComposeShader* copy = new SkiaComposeShader();
+ copy->copyFrom(*this);
+ copy->mFirst = mFirst;
+ copy->mSecond = mSecond;
+ copy->mMode = mMode;
+ return copy;
+}
+
void SkiaComposeShader::set(TextureCache* textureCache, GradientCache* gradientCache) {
SkiaShader::set(textureCache, gradientCache);
mFirst->set(textureCache, gradientCache);
diff --git a/libs/hwui/SkiaShader.h b/libs/hwui/SkiaShader.h
index 6702129..1ebde38 100644
--- a/libs/hwui/SkiaShader.h
+++ b/libs/hwui/SkiaShader.h
@@ -56,6 +56,9 @@ struct SkiaShader {
SkMatrix* matrix, bool blend);
virtual ~SkiaShader();
+ virtual SkiaShader* copy() = 0;
+ void copyFrom(const SkiaShader& shader);
+
virtual void describe(ProgramDescription& description, const Extensions& extensions);
virtual void setupProgram(Program* program, const mat4& modelView, const Snapshot& snapshot,
GLuint* textureUnit);
@@ -81,8 +84,13 @@ struct SkiaShader {
const Snapshot& snapshot) {
}
+ uint32_t getGenerationId() {
+ return mGenerationId;
+ }
+
void setMatrix(SkMatrix* matrix) {
updateLocalMatrix(matrix);
+ mGenerationId++;
}
void updateLocalMatrix(const SkMatrix* matrix) {
@@ -97,6 +105,9 @@ struct SkiaShader {
void computeScreenSpaceMatrix(mat4& screenSpace, const mat4& modelView);
protected:
+ SkiaShader() {
+ }
+
/**
* The appropriate texture unit must have been activated prior to invoking
* this method.
@@ -114,6 +125,9 @@ protected:
mat4 mUnitMatrix;
mat4 mShaderMatrix;
+
+private:
+ uint32_t mGenerationId;
}; // struct SkiaShader
@@ -127,6 +141,7 @@ protected:
struct SkiaBitmapShader: public SkiaShader {
SkiaBitmapShader(SkBitmap* bitmap, SkShader* key, SkShader::TileMode tileX,
SkShader::TileMode tileY, SkMatrix* matrix, bool blend);
+ SkiaShader* copy();
void describe(ProgramDescription& description, const Extensions& extensions);
void setupProgram(Program* program, const mat4& modelView, const Snapshot& snapshot,
@@ -134,6 +149,9 @@ struct SkiaBitmapShader: public SkiaShader {
void updateTransforms(Program* program, const mat4& modelView, const Snapshot& snapshot);
private:
+ SkiaBitmapShader() {
+ }
+
/**
* This method does not work for n == 0.
*/
@@ -154,6 +172,7 @@ struct SkiaLinearGradientShader: public SkiaShader {
SkiaLinearGradientShader(float* bounds, uint32_t* colors, float* positions, int count,
SkShader* key, SkShader::TileMode tileMode, SkMatrix* matrix, bool blend);
~SkiaLinearGradientShader();
+ SkiaShader* copy();
void describe(ProgramDescription& description, const Extensions& extensions);
void setupProgram(Program* program, const mat4& modelView, const Snapshot& snapshot,
@@ -161,6 +180,9 @@ struct SkiaLinearGradientShader: public SkiaShader {
void updateTransforms(Program* program, const mat4& modelView, const Snapshot& snapshot);
private:
+ SkiaLinearGradientShader() {
+ }
+
float* mBounds;
uint32_t* mColors;
float* mPositions;
@@ -174,6 +196,7 @@ struct SkiaSweepGradientShader: public SkiaShader {
SkiaSweepGradientShader(float x, float y, uint32_t* colors, float* positions, int count,
SkShader* key, SkMatrix* matrix, bool blend);
~SkiaSweepGradientShader();
+ SkiaShader* copy();
virtual void describe(ProgramDescription& description, const Extensions& extensions);
void setupProgram(Program* program, const mat4& modelView, const Snapshot& snapshot,
@@ -183,6 +206,8 @@ struct SkiaSweepGradientShader: public SkiaShader {
protected:
SkiaSweepGradientShader(Type type, float x, float y, uint32_t* colors, float* positions,
int count, SkShader* key, SkShader::TileMode tileMode, SkMatrix* matrix, bool blend);
+ SkiaSweepGradientShader() {
+ }
uint32_t* mColors;
float* mPositions;
@@ -195,8 +220,13 @@ protected:
struct SkiaCircularGradientShader: public SkiaSweepGradientShader {
SkiaCircularGradientShader(float x, float y, float radius, uint32_t* colors, float* positions,
int count, SkShader* key,SkShader::TileMode tileMode, SkMatrix* matrix, bool blend);
+ SkiaShader* copy();
void describe(ProgramDescription& description, const Extensions& extensions);
+
+private:
+ SkiaCircularGradientShader() {
+ }
}; // struct SkiaCircularGradientShader
/**
@@ -204,6 +234,7 @@ struct SkiaCircularGradientShader: public SkiaSweepGradientShader {
*/
struct SkiaComposeShader: public SkiaShader {
SkiaComposeShader(SkiaShader* first, SkiaShader* second, SkXfermode::Mode mode, SkShader* key);
+ SkiaShader* copy();
void set(TextureCache* textureCache, GradientCache* gradientCache);
@@ -212,6 +243,9 @@ struct SkiaComposeShader: public SkiaShader {
GLuint* textureUnit);
private:
+ SkiaComposeShader() {
+ }
+
SkiaShader* mFirst;
SkiaShader* mSecond;
SkXfermode::Mode mMode;