Merge "Implement support for drawBitmapMesh's colors array"
This commit is contained in:
@ -901,9 +901,9 @@ class GLES20Canvas extends HardwareCanvas {
|
||||
final int count = (meshWidth + 1) * (meshHeight + 1);
|
||||
checkRange(verts.length, vertOffset, count * 2);
|
||||
|
||||
// TODO: Colors are ignored for now
|
||||
colors = null;
|
||||
colorOffset = 0;
|
||||
if (colors != null) {
|
||||
checkRange(colors.length, colorOffset, count);
|
||||
}
|
||||
|
||||
int modifiers = paint != null ? setupModifiers(bitmap, paint) : MODIFIER_NONE;
|
||||
try {
|
||||
|
@ -365,11 +365,12 @@ void Caches::bindPositionVertexPointer(bool force, GLvoid* vertices, GLsizei str
|
||||
}
|
||||
}
|
||||
|
||||
void Caches::bindTexCoordsVertexPointer(bool force, GLvoid* vertices) {
|
||||
if (force || vertices != mCurrentTexCoordsPointer) {
|
||||
void Caches::bindTexCoordsVertexPointer(bool force, GLvoid* vertices, GLsizei stride) {
|
||||
if (force || vertices != mCurrentTexCoordsPointer || stride != mCurrentTexCoordsStride) {
|
||||
GLuint slot = currentProgram->texCoords;
|
||||
glVertexAttribPointer(slot, 2, GL_FLOAT, GL_FALSE, gMeshStride, vertices);
|
||||
glVertexAttribPointer(slot, 2, GL_FLOAT, GL_FALSE, stride, vertices);
|
||||
mCurrentTexCoordsPointer = vertices;
|
||||
mCurrentTexCoordsStride = stride;
|
||||
}
|
||||
}
|
||||
|
||||
@ -390,7 +391,7 @@ void Caches::enableTexCoordsVertexArray() {
|
||||
}
|
||||
}
|
||||
|
||||
void Caches::disbaleTexCoordsVertexArray() {
|
||||
void Caches::disableTexCoordsVertexArray() {
|
||||
if (mTexCoordsArrayEnabled) {
|
||||
glDisableVertexAttribArray(Program::kBindingTexCoords);
|
||||
mTexCoordsArrayEnabled = false;
|
||||
|
@ -183,7 +183,7 @@ public:
|
||||
* Binds an attrib to the specified float vertex pointer.
|
||||
* Assumes a stride of gMeshStride and a size of 2.
|
||||
*/
|
||||
void bindTexCoordsVertexPointer(bool force, GLvoid* vertices);
|
||||
void bindTexCoordsVertexPointer(bool force, GLvoid* vertices, GLsizei stride = gMeshStride);
|
||||
|
||||
/**
|
||||
* Resets the vertex pointers.
|
||||
@ -192,7 +192,7 @@ public:
|
||||
void resetTexCoordsVertexPointer();
|
||||
|
||||
void enableTexCoordsVertexArray();
|
||||
void disbaleTexCoordsVertexArray();
|
||||
void disableTexCoordsVertexArray();
|
||||
|
||||
/**
|
||||
* Activate the specified texture unit. The texture unit must
|
||||
@ -299,6 +299,7 @@ private:
|
||||
void* mCurrentPositionPointer;
|
||||
GLsizei mCurrentPositionStride;
|
||||
void* mCurrentTexCoordsPointer;
|
||||
GLsizei mCurrentTexCoordsStride;
|
||||
|
||||
bool mTexCoordsArrayEnabled;
|
||||
|
||||
|
@ -317,7 +317,7 @@ void OpenGLRenderer::interrupt() {
|
||||
mCaches.unbindMeshBuffer();
|
||||
mCaches.unbindIndicesBuffer();
|
||||
mCaches.resetVertexPointers();
|
||||
mCaches.disbaleTexCoordsVertexArray();
|
||||
mCaches.disableTexCoordsVertexArray();
|
||||
debugOverdraw(false, false);
|
||||
}
|
||||
|
||||
@ -1469,12 +1469,18 @@ void OpenGLRenderer::setupDrawWithTexture(bool isAlpha8) {
|
||||
mDescription.hasAlpha8Texture = isAlpha8;
|
||||
}
|
||||
|
||||
void OpenGLRenderer::setupDrawWithTextureAndColor(bool isAlpha8) {
|
||||
mDescription.hasTexture = true;
|
||||
mDescription.hasColors = true;
|
||||
mDescription.hasAlpha8Texture = isAlpha8;
|
||||
}
|
||||
|
||||
void OpenGLRenderer::setupDrawWithExternalTexture() {
|
||||
mDescription.hasExternalTexture = true;
|
||||
}
|
||||
|
||||
void OpenGLRenderer::setupDrawNoTexture() {
|
||||
mCaches.disbaleTexCoordsVertexArray();
|
||||
mCaches.disableTexCoordsVertexArray();
|
||||
}
|
||||
|
||||
void OpenGLRenderer::setupDrawAA() {
|
||||
@ -1682,6 +1688,23 @@ void OpenGLRenderer::setupDrawMesh(GLvoid* vertices, GLvoid* texCoords, GLuint v
|
||||
mCaches.unbindIndicesBuffer();
|
||||
}
|
||||
|
||||
void OpenGLRenderer::setupDrawMesh(GLvoid* vertices, GLvoid* texCoords, GLvoid* colors) {
|
||||
bool force = mCaches.unbindMeshBuffer();
|
||||
GLsizei stride = sizeof(ColorTextureVertex);
|
||||
|
||||
mCaches.bindPositionVertexPointer(force, vertices, stride);
|
||||
if (mCaches.currentProgram->texCoords >= 0) {
|
||||
mCaches.bindTexCoordsVertexPointer(force, texCoords, stride);
|
||||
}
|
||||
int slot = mCaches.currentProgram->getAttrib("colors");
|
||||
if (slot >= 0) {
|
||||
glEnableVertexAttribArray(slot);
|
||||
glVertexAttribPointer(slot, 4, GL_FLOAT, GL_FALSE, stride, colors);
|
||||
}
|
||||
|
||||
mCaches.unbindIndicesBuffer();
|
||||
}
|
||||
|
||||
void OpenGLRenderer::setupDrawMeshIndices(GLvoid* vertices, GLvoid* texCoords) {
|
||||
bool force = mCaches.unbindMeshBuffer();
|
||||
mCaches.bindPositionVertexPointer(force, vertices);
|
||||
@ -1833,9 +1856,16 @@ status_t OpenGLRenderer::drawBitmapMesh(SkBitmap* bitmap, int meshWidth, int mes
|
||||
|
||||
const uint32_t count = meshWidth * meshHeight * 6;
|
||||
|
||||
// TODO: Support the colors array
|
||||
TextureVertex mesh[count];
|
||||
TextureVertex* vertex = mesh;
|
||||
ColorTextureVertex mesh[count];
|
||||
ColorTextureVertex* vertex = mesh;
|
||||
|
||||
bool cleanupColors = false;
|
||||
if (!colors) {
|
||||
uint32_t colorsCount = (meshWidth + 1) * (meshHeight + 1);
|
||||
colors = new int[colorsCount];
|
||||
memset(colors, 0xff, colorsCount * sizeof(int));
|
||||
cleanupColors = true;
|
||||
}
|
||||
|
||||
for (int32_t y = 0; y < meshHeight; y++) {
|
||||
for (int32_t x = 0; x < meshWidth; x++) {
|
||||
@ -1855,13 +1885,13 @@ status_t OpenGLRenderer::drawBitmapMesh(SkBitmap* bitmap, int meshWidth, int mes
|
||||
int dx = i + (meshWidth + 1) * 2 + 2;
|
||||
int dy = dx + 1;
|
||||
|
||||
TextureVertex::set(vertex++, vertices[ax], vertices[ay], u1, v2);
|
||||
TextureVertex::set(vertex++, vertices[bx], vertices[by], u1, v1);
|
||||
TextureVertex::set(vertex++, vertices[cx], vertices[cy], u2, v1);
|
||||
ColorTextureVertex::set(vertex++, vertices[dx], vertices[dy], u2, v2, colors[dx / 2]);
|
||||
ColorTextureVertex::set(vertex++, vertices[ax], vertices[ay], u1, v2, colors[ax / 2]);
|
||||
ColorTextureVertex::set(vertex++, vertices[bx], vertices[by], u1, v1, colors[bx / 2]);
|
||||
|
||||
TextureVertex::set(vertex++, vertices[ax], vertices[ay], u1, v2);
|
||||
TextureVertex::set(vertex++, vertices[cx], vertices[cy], u2, v1);
|
||||
TextureVertex::set(vertex++, vertices[dx], vertices[dy], u2, v2);
|
||||
ColorTextureVertex::set(vertex++, vertices[dx], vertices[dy], u2, v2, colors[dx / 2]);
|
||||
ColorTextureVertex::set(vertex++, vertices[bx], vertices[by], u1, v1, colors[bx / 2]);
|
||||
ColorTextureVertex::set(vertex++, vertices[cx], vertices[cy], u2, v1, colors[cx / 2]);
|
||||
|
||||
left = fminf(left, fminf(vertices[ax], fminf(vertices[bx], vertices[cx])));
|
||||
top = fminf(top, fminf(vertices[ay], fminf(vertices[by], vertices[cy])));
|
||||
@ -1871,12 +1901,16 @@ status_t OpenGLRenderer::drawBitmapMesh(SkBitmap* bitmap, int meshWidth, int mes
|
||||
}
|
||||
|
||||
if (quickReject(left, top, right, bottom)) {
|
||||
if (cleanupColors) delete[] colors;
|
||||
return DrawGlInfo::kStatusDone;
|
||||
}
|
||||
|
||||
mCaches.activeTexture(0);
|
||||
Texture* texture = mCaches.textureCache.get(bitmap);
|
||||
if (!texture) return DrawGlInfo::kStatusDone;
|
||||
if (!texture) {
|
||||
if (cleanupColors) delete[] colors;
|
||||
return DrawGlInfo::kStatusDone;
|
||||
}
|
||||
const AutoTexture autoCleanup(texture);
|
||||
|
||||
texture->setWrap(GL_CLAMP_TO_EDGE, true);
|
||||
@ -1886,13 +1920,35 @@ status_t OpenGLRenderer::drawBitmapMesh(SkBitmap* bitmap, int meshWidth, int mes
|
||||
SkXfermode::Mode mode;
|
||||
getAlphaAndMode(paint, &alpha, &mode);
|
||||
|
||||
float a = alpha / 255.0f;
|
||||
|
||||
if (hasLayer()) {
|
||||
dirtyLayer(left, top, right, bottom, *mSnapshot->transform);
|
||||
}
|
||||
|
||||
drawTextureMesh(0.0f, 0.0f, 1.0f, 1.0f, texture->id, alpha / 255.0f,
|
||||
mode, texture->blend, &mesh[0].position[0], &mesh[0].texture[0],
|
||||
GL_TRIANGLES, count, false, false, 0, false, false);
|
||||
setupDraw();
|
||||
setupDrawWithTextureAndColor();
|
||||
setupDrawColor(a, a, a, a);
|
||||
setupDrawColorFilter();
|
||||
setupDrawBlending(true, mode, false);
|
||||
setupDrawProgram();
|
||||
setupDrawDirtyRegionsDisabled();
|
||||
setupDrawModelView(0.0f, 0.0f, 1.0f, 1.0f, false);
|
||||
setupDrawTexture(texture->id);
|
||||
setupDrawPureColorUniforms();
|
||||
setupDrawColorFilterUniforms();
|
||||
setupDrawMesh(&mesh[0].position[0], &mesh[0].texture[0], &mesh[0].color[0]);
|
||||
|
||||
glDrawArrays(GL_TRIANGLES, 0, count);
|
||||
|
||||
finishDrawTexture();
|
||||
|
||||
int slot = mCaches.currentProgram->getAttrib("colors");
|
||||
if (slot >= 0) {
|
||||
glDisableVertexAttribArray(slot);
|
||||
}
|
||||
|
||||
if (cleanupColors) delete[] colors;
|
||||
|
||||
return DrawGlInfo::kStatusDrew;
|
||||
}
|
||||
|
@ -777,6 +777,7 @@ private:
|
||||
* Various methods to setup OpenGL rendering.
|
||||
*/
|
||||
void setupDrawWithTexture(bool isAlpha8 = false);
|
||||
void setupDrawWithTextureAndColor(bool isAlpha8 = false);
|
||||
void setupDrawWithExternalTexture();
|
||||
void setupDrawNoTexture();
|
||||
void setupDrawAA();
|
||||
@ -811,6 +812,7 @@ private:
|
||||
void setupDrawTextureTransformUniforms(mat4& transform);
|
||||
void setupDrawTextGammaUniforms();
|
||||
void setupDrawMesh(GLvoid* vertices, GLvoid* texCoords = NULL, GLuint vbo = 0);
|
||||
void setupDrawMesh(GLvoid* vertices, GLvoid* texCoords, GLvoid* colors);
|
||||
void setupDrawMeshIndices(GLvoid* vertices, GLvoid* texCoords);
|
||||
void setupDrawVertices(GLvoid* vertices);
|
||||
void finishDrawTexture();
|
||||
|
@ -81,6 +81,8 @@ namespace uirenderer {
|
||||
|
||||
#define PROGRAM_IS_SIMPLE_GRADIENT 41
|
||||
|
||||
#define PROGRAM_HAS_COLORS 42
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
// Types
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
@ -120,6 +122,9 @@ struct ProgramDescription {
|
||||
bool hasExternalTexture;
|
||||
bool hasTextureTransform;
|
||||
|
||||
// Color attribute
|
||||
bool hasColors;
|
||||
|
||||
// Modulate, this should only be set when setColor() return true
|
||||
bool modulate;
|
||||
|
||||
@ -164,6 +169,8 @@ struct ProgramDescription {
|
||||
hasExternalTexture = false;
|
||||
hasTextureTransform = false;
|
||||
|
||||
hasColors = false;
|
||||
|
||||
isAA = false;
|
||||
|
||||
modulate = false;
|
||||
@ -259,6 +266,7 @@ struct ProgramDescription {
|
||||
if (hasTextureTransform) key |= programid(0x1) << PROGRAM_HAS_TEXTURE_TRANSFORM_SHIFT;
|
||||
if (hasGammaCorrection) key |= programid(0x1) << PROGRAM_HAS_GAMMA_CORRECTION;
|
||||
if (isSimpleGradient) key |= programid(0x1) << PROGRAM_IS_SIMPLE_GRADIENT;
|
||||
if (hasColors) key |= programid(0x1) << PROGRAM_HAS_COLORS;
|
||||
return key;
|
||||
}
|
||||
|
||||
|
@ -40,6 +40,8 @@ const char* gVS_Header_Attributes =
|
||||
"attribute vec4 position;\n";
|
||||
const char* gVS_Header_Attributes_TexCoords =
|
||||
"attribute vec2 texCoords;\n";
|
||||
const char* gVS_Header_Attributes_Colors =
|
||||
"attribute vec4 colors;\n";
|
||||
const char* gVS_Header_Attributes_AAVertexShapeParameters =
|
||||
"attribute float vtxAlpha;\n";
|
||||
const char* gVS_Header_Uniforms_TextureTransform =
|
||||
@ -65,6 +67,8 @@ const char* gVS_Header_Uniforms_HasBitmap =
|
||||
"uniform mediump vec2 textureDimension;\n";
|
||||
const char* gVS_Header_Varyings_HasTexture =
|
||||
"varying vec2 outTexCoords;\n";
|
||||
const char* gVS_Header_Varyings_HasColors =
|
||||
"varying vec4 outColors;\n";
|
||||
const char* gVS_Header_Varyings_IsAAVertexShape =
|
||||
"varying float alpha;\n";
|
||||
const char* gVS_Header_Varyings_HasBitmap =
|
||||
@ -94,6 +98,8 @@ const char* gVS_Main =
|
||||
"\nvoid main(void) {\n";
|
||||
const char* gVS_Main_OutTexCoords =
|
||||
" outTexCoords = texCoords;\n";
|
||||
const char* gVS_Main_OutColors =
|
||||
" outColors = colors;\n";
|
||||
const char* gVS_Main_OutTransformedTexCoords =
|
||||
" outTexCoords = (mainTextureTransform * vec4(texCoords, 0.0, 1.0)).xy;\n";
|
||||
const char* gVS_Main_OutGradient[6] = {
|
||||
@ -325,6 +331,8 @@ const char* gFS_Main_BitmapShader_Modulate[6] = {
|
||||
};
|
||||
const char* gFS_Main_FragColor =
|
||||
" gl_FragColor = fragColor;\n";
|
||||
const char* gFS_Main_FragColor_HasColors =
|
||||
" gl_FragColor *= outColors;\n";
|
||||
const char* gFS_Main_FragColor_Blend =
|
||||
" gl_FragColor = blendFramebuffer(fragColor, gl_LastFragColor);\n";
|
||||
const char* gFS_Main_FragColor_Blend_Swap =
|
||||
@ -459,6 +467,9 @@ String8 ProgramCache::generateVertexShader(const ProgramDescription& description
|
||||
if (description.isAA) {
|
||||
shader.append(gVS_Header_Attributes_AAVertexShapeParameters);
|
||||
}
|
||||
if (description.hasColors) {
|
||||
shader.append(gVS_Header_Attributes_Colors);
|
||||
}
|
||||
// Uniforms
|
||||
shader.append(gVS_Header_Uniforms);
|
||||
if (description.hasTextureTransform) {
|
||||
@ -480,6 +491,9 @@ String8 ProgramCache::generateVertexShader(const ProgramDescription& description
|
||||
if (description.isAA) {
|
||||
shader.append(gVS_Header_Varyings_IsAAVertexShape);
|
||||
}
|
||||
if (description.hasColors) {
|
||||
shader.append(gVS_Header_Varyings_HasColors);
|
||||
}
|
||||
if (description.hasGradient) {
|
||||
shader.append(gVS_Header_Varyings_HasGradient[gradientIndex(description)]);
|
||||
}
|
||||
@ -499,6 +513,9 @@ String8 ProgramCache::generateVertexShader(const ProgramDescription& description
|
||||
if (description.isAA) {
|
||||
shader.append(gVS_Main_AAVertexShape);
|
||||
}
|
||||
if (description.hasColors) {
|
||||
shader.append(gVS_Main_OutColors);
|
||||
}
|
||||
if (description.hasBitmap) {
|
||||
shader.append(description.isPoint ?
|
||||
gVS_Main_OutPointBitmapTexCoords :
|
||||
@ -549,6 +566,9 @@ String8 ProgramCache::generateFragmentShader(const ProgramDescription& descripti
|
||||
if (description.isAA) {
|
||||
shader.append(gVS_Header_Varyings_IsAAVertexShape);
|
||||
}
|
||||
if (description.hasColors) {
|
||||
shader.append(gVS_Header_Varyings_HasColors);
|
||||
}
|
||||
if (description.hasGradient) {
|
||||
shader.append(gVS_Header_Varyings_HasGradient[gradientIndex(description)]);
|
||||
}
|
||||
@ -583,7 +603,7 @@ String8 ProgramCache::generateFragmentShader(const ProgramDescription& descripti
|
||||
}
|
||||
|
||||
// Optimization for common cases
|
||||
if (!description.isAA && !blendFramebuffer &&
|
||||
if (!description.isAA && !blendFramebuffer && !description.hasColors &&
|
||||
description.colorOp == ProgramDescription::kColorNone && !description.isPoint) {
|
||||
bool fast = false;
|
||||
|
||||
@ -729,6 +749,9 @@ String8 ProgramCache::generateFragmentShader(const ProgramDescription& descripti
|
||||
shader.append(!description.swapSrcDst ?
|
||||
gFS_Main_FragColor_Blend : gFS_Main_FragColor_Blend_Swap);
|
||||
}
|
||||
if (description.hasColors) {
|
||||
shader.append(gFS_Main_FragColor_HasColors);
|
||||
}
|
||||
}
|
||||
// End the shader
|
||||
shader.append(gFS_Footer);
|
||||
|
@ -33,7 +33,7 @@ struct Vertex {
|
||||
}; // struct Vertex
|
||||
|
||||
/**
|
||||
* Simple structure to describe a vertex with a position and a texture.
|
||||
* Simple structure to describe a vertex with a position and texture UV.
|
||||
*/
|
||||
struct TextureVertex {
|
||||
float position[2];
|
||||
@ -52,6 +52,24 @@ struct TextureVertex {
|
||||
}
|
||||
}; // struct TextureVertex
|
||||
|
||||
/**
|
||||
* Simple structure to describe a vertex with a position, texture UV and ARGB color.
|
||||
*/
|
||||
struct ColorTextureVertex : TextureVertex {
|
||||
float color[4];
|
||||
|
||||
static inline void set(ColorTextureVertex* vertex, float x, float y,
|
||||
float u, float v, int color) {
|
||||
TextureVertex::set(vertex, x, y, u, v);
|
||||
|
||||
const float a = ((color >> 24) & 0xff) / 255.0f;
|
||||
vertex[0].color[0] = a * ((color >> 16) & 0xff) / 255.0f;
|
||||
vertex[0].color[1] = a * ((color >> 8) & 0xff) / 255.0f;
|
||||
vertex[0].color[2] = a * ((color ) & 0xff) / 255.0f;
|
||||
vertex[0].color[3] = a;
|
||||
}
|
||||
}; // struct ColorTextureVertex
|
||||
|
||||
/**
|
||||
* Simple structure to describe a vertex with a position and an alpha value.
|
||||
*/
|
||||
|
@ -54,7 +54,7 @@ public class BitmapMeshActivity extends Activity {
|
||||
0.0f, height * 2, width, height * 2, width * 2, height * 2, width * 3, height * 2,
|
||||
0.0f, height * 4, width, height * 4, width * 2, height * 4, width * 4, height * 4,
|
||||
};
|
||||
|
||||
|
||||
mColors = new int[] {
|
||||
0xffff0000, 0xff00ff00, 0xff0000ff, 0xffff0000,
|
||||
0xff0000ff, 0xffff0000, 0xff00ff00, 0xff00ff00,
|
||||
|
Reference in New Issue
Block a user