summaryrefslogtreecommitdiffstats
path: root/libs
diff options
context:
space:
mode:
authorChris Craik <ccraik@google.com>2015-02-25 17:16:16 -0800
committerChris Craik <ccraik@google.com>2015-02-26 10:56:07 -0800
commitef2507439c08f4e9c4c9bba1c6243ca9df2ee827 (patch)
tree0312e1808ee6915a96e1770cb190ea4674e2376a /libs
parent03ae272459869b854e5db252fc81a64a516e111f (diff)
downloadframeworks_base-ef2507439c08f4e9c4c9bba1c6243ca9df2ee827.zip
frameworks_base-ef2507439c08f4e9c4c9bba1c6243ca9df2ee827.tar.gz
frameworks_base-ef2507439c08f4e9c4c9bba1c6243ca9df2ee827.tar.bz2
Glop mesh reorg, support for drawBitmapMesh
Change-Id: Iaf5550bdd93da93e59a5b838234ab5612e067387
Diffstat (limited to 'libs')
-rw-r--r--libs/hwui/DisplayListOp.h7
-rw-r--r--libs/hwui/Glop.h43
-rw-r--r--libs/hwui/GlopBuilder.cpp127
-rw-r--r--libs/hwui/GlopBuilder.h3
-rw-r--r--libs/hwui/OpenGLRenderer.cpp37
-rw-r--r--libs/hwui/renderstate/MeshState.h1
-rw-r--r--libs/hwui/renderstate/RenderState.cpp90
-rw-r--r--libs/hwui/utils/Macros.h6
8 files changed, 179 insertions, 135 deletions
diff --git a/libs/hwui/DisplayListOp.h b/libs/hwui/DisplayListOp.h
index dba5121..1963475 100644
--- a/libs/hwui/DisplayListOp.h
+++ b/libs/hwui/DisplayListOp.h
@@ -1399,8 +1399,11 @@ class DrawRenderNodeOp : public DrawBoundedOp {
friend class DisplayListData; // grant DisplayListData access to info of child
public:
DrawRenderNodeOp(RenderNode* renderNode, int flags, const mat4& transformFromParent)
- : DrawBoundedOp(0, 0, renderNode->getWidth(), renderNode->getHeight(), nullptr),
- mRenderNode(renderNode), mFlags(flags), mTransformFromParent(transformFromParent) {}
+ : DrawBoundedOp(0, 0, renderNode->getWidth(), renderNode->getHeight(), nullptr)
+ , mRenderNode(renderNode)
+ , mFlags(flags)
+ , mTransformFromParent(transformFromParent)
+ , mSkipInOrderDraw(false) {}
virtual void defer(DeferStateStruct& deferStruct, int saveCount, int level,
bool useQuickReject) override {
diff --git a/libs/hwui/Glop.h b/libs/hwui/Glop.h
index e500546..c9a5679 100644
--- a/libs/hwui/Glop.h
+++ b/libs/hwui/Glop.h
@@ -41,12 +41,13 @@ class Texture;
* Position is always enabled by MeshState, these other attributes
* are enabled/disabled dynamically based on mesh content.
*/
-enum VertexAttribFlags {
- kNone_Attrib = 0,
- kTextureCoord_Attrib = 1 << 0,
- kColor_Attrib = 1 << 1,
- kAlpha_Attrib = 1 << 2,
+enum class VertexAttribFlags {
+ kNone = 0,
+ kTextureCoord = 1 << 0,
+ kColor = 1 << 1,
+ kAlpha = 1 << 2,
};
+MAKE_FLAGS_ENUM(VertexAttribFlags)
/**
* Structure containing all data required to issue an OpenGL draw
@@ -63,22 +64,28 @@ enum VertexAttribFlags {
*/
// TODO: PREVENT_COPY_AND_ASSIGN(...) or similar
struct Glop {
- /*
- * Stores mesh - vertex and index data.
- *
- * buffer objects and void*s are mutually exclusive
- * indices are optional, currently only GL_UNSIGNED_SHORT supported
- */
struct Mesh {
- VertexAttribFlags vertexFlags;
GLuint primitiveMode; // GL_TRIANGLES and GL_TRIANGLE_STRIP supported
- GLuint vertexBufferObject;
- GLuint indexBufferObject;
- const void* vertices;
- const void* indices;
- GLvoid* texCoordOffset;
+
+ // buffer object and void* are mutually exclusive.
+ // Only GL_UNSIGNED_SHORT supported.
+ struct Indices {
+ GLuint bufferObject;
+ const void* indices;
+ } indices;
+
+ // buffer object and void*s are mutually exclusive.
+ // TODO: enforce mutual exclusion with restricted setters and/or unions
+ struct Vertices {
+ GLuint bufferObject;
+ VertexAttribFlags flags;
+ const void* position;
+ const void* texCoord;
+ const void* color;
+ GLsizei stride;
+ } vertices;
+
int elementCount;
- GLsizei stride;
TextureVertex mappedVertices[4];
} mesh;
diff --git a/libs/hwui/GlopBuilder.cpp b/libs/hwui/GlopBuilder.cpp
index 1342c52..f50dfc8 100644
--- a/libs/hwui/GlopBuilder.cpp
+++ b/libs/hwui/GlopBuilder.cpp
@@ -61,15 +61,14 @@ GlopBuilder::GlopBuilder(RenderState& renderState, Caches& caches, Glop* outGlop
GlopBuilder& GlopBuilder::setMeshUnitQuad() {
TRIGGER_STAGE(kMeshStage);
- mOutGlop->mesh.vertexFlags = kNone_Attrib;
mOutGlop->mesh.primitiveMode = GL_TRIANGLE_STRIP;
- mOutGlop->mesh.vertexBufferObject = mRenderState.meshState().getUnitQuadVBO();
- mOutGlop->mesh.vertices = nullptr;
- mOutGlop->mesh.indexBufferObject = 0;
- mOutGlop->mesh.indices = nullptr;
+ mOutGlop->mesh.indices = { 0, nullptr };
+ mOutGlop->mesh.vertices = {
+ mRenderState.meshState().getUnitQuadVBO(),
+ VertexAttribFlags::kNone,
+ nullptr, nullptr, nullptr,
+ kTextureVertexStride };
mOutGlop->mesh.elementCount = 4;
- mOutGlop->mesh.stride = kTextureVertexStride;
- mOutGlop->mesh.texCoordOffset = nullptr;
return *this;
}
@@ -81,70 +80,76 @@ GlopBuilder& GlopBuilder::setMeshTexturedUnitQuad(const UvMapper* uvMapper) {
TRIGGER_STAGE(kMeshStage);
- mOutGlop->mesh.vertexFlags = kTextureCoord_Attrib;
mOutGlop->mesh.primitiveMode = GL_TRIANGLE_STRIP;
- mOutGlop->mesh.vertexBufferObject = mRenderState.meshState().getUnitQuadVBO();
- mOutGlop->mesh.vertices = nullptr;
- mOutGlop->mesh.texCoordOffset = (GLvoid*) kMeshTextureOffset;
- mOutGlop->mesh.indexBufferObject = 0;
- mOutGlop->mesh.indices = nullptr;
+ mOutGlop->mesh.indices = { 0, nullptr };
+ mOutGlop->mesh.vertices = {
+ mRenderState.meshState().getUnitQuadVBO(),
+ VertexAttribFlags::kTextureCoord,
+ nullptr, (const void*) kMeshTextureOffset, nullptr,
+ kTextureVertexStride };
mOutGlop->mesh.elementCount = 4;
- mOutGlop->mesh.stride = kTextureVertexStride;
- mDescription.hasTexture = true;
return *this;
}
GlopBuilder& GlopBuilder::setMeshTexturedUvQuad(const UvMapper* uvMapper, Rect uvs) {
TRIGGER_STAGE(kMeshStage);
- mOutGlop->mesh.vertexFlags = kTextureCoord_Attrib;
- mOutGlop->mesh.primitiveMode = GL_TRIANGLE_STRIP;
-
if (CC_UNLIKELY(uvMapper)) {
uvMapper->map(uvs);
}
setUnitQuadTextureCoords(uvs, &mOutGlop->mesh.mappedVertices[0]);
- mOutGlop->mesh.vertexBufferObject = 0;
- mOutGlop->mesh.vertices = &mOutGlop->mesh.mappedVertices[0].x;
- mOutGlop->mesh.texCoordOffset = &mOutGlop->mesh.mappedVertices[0].u;
- mOutGlop->mesh.indexBufferObject = 0;
- mOutGlop->mesh.indices = nullptr;
+ const TextureVertex* textureVertex = mOutGlop->mesh.mappedVertices;
+ mOutGlop->mesh.primitiveMode = GL_TRIANGLE_STRIP;
+ mOutGlop->mesh.indices = { 0, nullptr };
+ mOutGlop->mesh.vertices = {
+ 0,
+ VertexAttribFlags::kTextureCoord,
+ &textureVertex[0].x, &textureVertex[0].u, nullptr,
+ kTextureVertexStride };
mOutGlop->mesh.elementCount = 4;
- mOutGlop->mesh.stride = kTextureVertexStride;
- mDescription.hasTexture = true;
return *this;
}
-GlopBuilder& GlopBuilder::setMeshIndexedQuads(void* vertexData, int quadCount) {
+GlopBuilder& GlopBuilder::setMeshIndexedQuads(Vertex* vertexData, int quadCount) {
TRIGGER_STAGE(kMeshStage);
- mOutGlop->mesh.vertexFlags = kNone_Attrib;
mOutGlop->mesh.primitiveMode = GL_TRIANGLES;
- mOutGlop->mesh.vertexBufferObject = 0;
- mOutGlop->mesh.vertices = vertexData;
- mOutGlop->mesh.indexBufferObject = mRenderState.meshState().getQuadListIBO();
- mOutGlop->mesh.indices = nullptr;
- mOutGlop->mesh.texCoordOffset = nullptr;
+ mOutGlop->mesh.indices = { mRenderState.meshState().getQuadListIBO(), nullptr };
+ mOutGlop->mesh.vertices = {
+ 0,
+ VertexAttribFlags::kNone,
+ vertexData, nullptr, nullptr,
+ kVertexStride };
mOutGlop->mesh.elementCount = 6 * quadCount;
- mOutGlop->mesh.stride = kVertexStride;
-
return *this;
}
GlopBuilder& GlopBuilder::setMeshTexturedIndexedQuads(TextureVertex* vertexData, int elementCount) {
TRIGGER_STAGE(kMeshStage);
- mOutGlop->mesh.vertexFlags = kTextureCoord_Attrib;
mOutGlop->mesh.primitiveMode = GL_TRIANGLES;
- mOutGlop->mesh.vertexBufferObject = 0;
- mOutGlop->mesh.vertices = &vertexData[0].x;
- mOutGlop->mesh.indexBufferObject = mRenderState.meshState().getQuadListIBO();
- mOutGlop->mesh.indices = nullptr;
- mOutGlop->mesh.texCoordOffset = &vertexData[0].u;
+ mOutGlop->mesh.indices = { mRenderState.meshState().getQuadListIBO(), nullptr };
+ mOutGlop->mesh.vertices = {
+ 0,
+ VertexAttribFlags::kTextureCoord,
+ &vertexData[0].x, &vertexData[0].u, nullptr,
+ kTextureVertexStride };
+ mOutGlop->mesh.elementCount = elementCount;
+ return *this;
+}
+
+GlopBuilder& GlopBuilder::setMeshColoredTexturedMesh(ColorTextureVertex* vertexData, int elementCount) {
+ TRIGGER_STAGE(kMeshStage);
+
+ mOutGlop->mesh.primitiveMode = GL_TRIANGLES;
+ mOutGlop->mesh.indices = { 0, nullptr };
+ mOutGlop->mesh.vertices = {
+ 0,
+ static_cast<VertexAttribFlags>(VertexAttribFlags::kTextureCoord | VertexAttribFlags::kColor),
+ &vertexData[0].x, &vertexData[0].u, &vertexData[0].r,
+ kColorTextureVertexStride };
mOutGlop->mesh.elementCount = elementCount;
- mOutGlop->mesh.stride = kTextureVertexStride;
- mDescription.hasTexture = true;
return *this;
}
@@ -155,18 +160,17 @@ GlopBuilder& GlopBuilder::setMeshVertexBuffer(const VertexBuffer& vertexBuffer,
bool alphaVertex = flags & VertexBuffer::kAlpha;
bool indices = flags & VertexBuffer::kIndices;
- mOutGlop->mesh.vertexFlags = alphaVertex ? kAlpha_Attrib : kNone_Attrib;
+
mOutGlop->mesh.primitiveMode = GL_TRIANGLE_STRIP;
- mOutGlop->mesh.vertexBufferObject = 0;
- mOutGlop->mesh.vertices = vertexBuffer.getBuffer();
- mOutGlop->mesh.indexBufferObject = 0;
- mOutGlop->mesh.indices = vertexBuffer.getIndices();
- mOutGlop->mesh.texCoordOffset = nullptr;
+ mOutGlop->mesh.indices = { 0, vertexBuffer.getIndices() };
+ mOutGlop->mesh.vertices = {
+ 0,
+ alphaVertex ? VertexAttribFlags::kAlpha : VertexAttribFlags::kNone,
+ vertexBuffer.getBuffer(), nullptr, nullptr,
+ alphaVertex ? kAlphaVertexStride : kVertexStride };
mOutGlop->mesh.elementCount = indices
- ? vertexBuffer.getIndexCount() : vertexBuffer.getVertexCount();
- mOutGlop->mesh.stride = alphaVertex ? kAlphaVertexStride : kVertexStride;
+ ? vertexBuffer.getIndexCount() : vertexBuffer.getVertexCount();
- mDescription.hasVertexAlpha = alphaVertex;
mDescription.useShadowAlphaInterp = shadowInterp;
return *this;
}
@@ -197,7 +201,7 @@ void GlopBuilder::setFill(int color, float alphaScale, SkXfermode::Mode mode,
mOutGlop->blend = { GL_ZERO, GL_ZERO };
if (mOutGlop->fill.color.a < 1.0f
- || (mOutGlop->mesh.vertexFlags & kAlpha_Attrib)
+ || (mOutGlop->mesh.vertices.flags & VertexAttribFlags::kAlpha)
|| (mOutGlop->fill.texture.texture && mOutGlop->fill.texture.texture->blend)
|| mOutGlop->roundRectClipState
|| PaintUtils::isBlendedShader(shader)
@@ -288,7 +292,7 @@ GlopBuilder& GlopBuilder::setFillTexturePaint(Texture& texture, bool isAlphaMask
const bool SWAP_SRC_DST = false;
if (alphaScale < 1.0f
- || (mOutGlop->mesh.vertexFlags & kAlpha_Attrib)
+ || (mOutGlop->mesh.vertices.flags & VertexAttribFlags::kAlpha)
|| texture.blend
|| mOutGlop->roundRectClipState) {
Blend::getFactors(SkXfermode::kSrcOver_Mode, SWAP_SRC_DST,
@@ -489,20 +493,25 @@ GlopBuilder& GlopBuilder::setRoundRectClipState(const RoundRectClipState* roundR
void verify(const ProgramDescription& description, const Glop& glop) {
bool hasTexture = glop.fill.texture.texture != nullptr;
LOG_ALWAYS_FATAL_IF(description.hasTexture != hasTexture);
- LOG_ALWAYS_FATAL_IF((glop.mesh.vertexFlags & kTextureCoord_Attrib) != hasTexture);
+ LOG_ALWAYS_FATAL_IF((glop.mesh.vertices.flags & VertexAttribFlags::kTextureCoord) != hasTexture);
+
+ if ((glop.mesh.vertices.flags & VertexAttribFlags::kAlpha) && glop.mesh.vertices.bufferObject) {
+ LOG_ALWAYS_FATAL("VBO and alpha attributes are not currently compatible");
+ }
}
void GlopBuilder::build() {
REQUIRE_STAGES(kAllStages);
+ mDescription.hasTexture = static_cast<int>(mOutGlop->mesh.vertices.flags & VertexAttribFlags::kTextureCoord);
+ mDescription.hasColors = static_cast<int>(mOutGlop->mesh.vertices.flags & VertexAttribFlags::kColor);
+ mDescription.hasVertexAlpha = static_cast<int>(mOutGlop->mesh.vertices.flags & VertexAttribFlags::kAlpha);
+
// serialize shader info into ShaderData
GLuint textureUnit = mOutGlop->fill.texture.texture ? 1 : 0;
SkiaShader::store(mCaches, mShader, mOutGlop->transform.modelView,
&textureUnit, &mDescription, &(mOutGlop->fill.skiaShaderData));
- mOutGlop->fill.program = mCaches.programCache.get(mDescription);
- mOutGlop->transform.canvas.mapRect(mOutGlop->bounds);
-
// duplicates ProgramCache's definition of color uniform presence
const bool singleColor = !mDescription.hasTexture
&& !mDescription.hasExternalTexture
@@ -511,6 +520,10 @@ void GlopBuilder::build() {
mOutGlop->fill.colorEnabled = mDescription.modulate || singleColor;
verify(mDescription, *mOutGlop);
+
+ // Final step: populate program and map bounds into render target space
+ mOutGlop->fill.program = mCaches.programCache.get(mDescription);
+ mOutGlop->transform.canvas.mapRect(mOutGlop->bounds);
}
} /* namespace uirenderer */
diff --git a/libs/hwui/GlopBuilder.h b/libs/hwui/GlopBuilder.h
index 5a8354d..c24b122 100644
--- a/libs/hwui/GlopBuilder.h
+++ b/libs/hwui/GlopBuilder.h
@@ -42,7 +42,8 @@ public:
GlopBuilder& setMeshTexturedUnitQuad(const UvMapper* uvMapper);
GlopBuilder& setMeshTexturedUvQuad(const UvMapper* uvMapper, const Rect uvs);
GlopBuilder& setMeshVertexBuffer(const VertexBuffer& vertexBuffer, bool shadowInterp);
- GlopBuilder& setMeshIndexedQuads(void* vertexData, int quadCount);
+ GlopBuilder& setMeshIndexedQuads(Vertex* vertexData, int quadCount);
+ GlopBuilder& setMeshColoredTexturedMesh(ColorTextureVertex* vertexData, int elementCount);
GlopBuilder& setMeshTexturedIndexedQuads(TextureVertex* vertexData, int elementCount); // TODO: take quadCount
GlopBuilder& setFillPaint(const SkPaint& paint, float alphaScale);
diff --git a/libs/hwui/OpenGLRenderer.cpp b/libs/hwui/OpenGLRenderer.cpp
index 2bca9fa..3913ee5 100644
--- a/libs/hwui/OpenGLRenderer.cpp
+++ b/libs/hwui/OpenGLRenderer.cpp
@@ -1234,7 +1234,7 @@ void OpenGLRenderer::clearLayerRegions() {
aBuilder.setMeshIndexedQuads(&mesh[0], quadCount)
.setFillClear()
.setTransform(currentSnapshot()->getOrthoMatrix(), Matrix4::identity(), false)
- .setModelViewOffsetRect(0, 0, currentSnapshot()->getClipRect())
+ .setModelViewOffsetRect(0, 0, Rect(currentSnapshot()->getClipRect()))
.setRoundRectClipState(currentSnapshot()->roundRectClipState)
.build();
renderGlop(glop);
@@ -2077,17 +2077,14 @@ void OpenGLRenderer::drawBitmapMesh(const SkBitmap* bitmap, int meshWidth, int m
return;
}
- // TODO: use quickReject on bounds from vertices
- mRenderState.scissor().setEnabled(true);
-
float left = FLT_MAX;
float top = FLT_MAX;
float right = FLT_MIN;
float bottom = FLT_MIN;
- const uint32_t count = meshWidth * meshHeight * 6;
+ const uint32_t elementCount = meshWidth * meshHeight * 6;
- std::unique_ptr<ColorTextureVertex[]> mesh(new ColorTextureVertex[count]);
+ std::unique_ptr<ColorTextureVertex[]> mesh(new ColorTextureVertex[elementCount]);
ColorTextureVertex* vertex = &mesh[0];
std::unique_ptr<int[]> tempColors;
@@ -2098,7 +2095,6 @@ void OpenGLRenderer::drawBitmapMesh(const SkBitmap* bitmap, int meshWidth, int m
colors = tempColors.get();
}
- mCaches.textureState().activateTexture(0);
Texture* texture = mRenderState.assetAtlas().getEntryTexture(bitmap);
const UvMapper& mapper(getMapper(texture));
@@ -2149,6 +2145,25 @@ void OpenGLRenderer::drawBitmapMesh(const SkBitmap* bitmap, int meshWidth, int m
}
const AutoTexture autoCleanup(texture);
+ if (USE_GLOPS) {
+ /*
+ * TODO: handle alpha_8 textures correctly by applying paint color, but *not*
+ * shader in that case to mimic the behavior in SkiaCanvas::drawBitmapMesh.
+ */
+ bool isAlpha8Texture = false;
+ Glop glop;
+ GlopBuilder aBuilder(mRenderState, mCaches, &glop);
+ aBuilder.setMeshColoredTexturedMesh(mesh.get(), elementCount)
+ .setFillTexturePaint(*texture, isAlpha8Texture, paint, currentSnapshot()->alpha)
+ .setTransform(currentSnapshot()->getOrthoMatrix(), *currentTransform(), false)
+ .setModelViewOffsetRect(0, 0, Rect(left, top, right, bottom))
+ .setRoundRectClipState(currentSnapshot()->roundRectClipState)
+ .build();
+ renderGlop(glop);
+ return;
+ }
+
+ mCaches.textureState().activateTexture(0);
texture->setWrap(GL_CLAMP_TO_EDGE, true);
texture->setFilter(PaintUtils::getFilter(paint), true);
@@ -2156,12 +2171,10 @@ void OpenGLRenderer::drawBitmapMesh(const SkBitmap* bitmap, int meshWidth, int m
SkXfermode::Mode mode;
getAlphaAndMode(paint, &alpha, &mode);
- float a = alpha / 255.0f;
- if (hasLayer()) {
- dirtyLayer(left, top, right, bottom, *currentTransform());
- }
+ dirtyLayer(left, top, right, bottom, *currentTransform());
+ float a = alpha / 255.0f;
setupDraw();
setupDrawWithTextureAndColor();
setupDrawColor(a, a, a, a);
@@ -2175,7 +2188,7 @@ void OpenGLRenderer::drawBitmapMesh(const SkBitmap* bitmap, int meshWidth, int m
setupDrawColorFilterUniforms(getColorFilter(paint));
setupDrawMesh(&mesh[0].x, &mesh[0].u, &mesh[0].r);
- glDrawArrays(GL_TRIANGLES, 0, count);
+ glDrawArrays(GL_TRIANGLES, 0, elementCount);
int slot = mCaches.program().getAttrib("colors");
if (slot >= 0) {
diff --git a/libs/hwui/renderstate/MeshState.h b/libs/hwui/renderstate/MeshState.h
index 3c92ad8..e80f4d0 100644
--- a/libs/hwui/renderstate/MeshState.h
+++ b/libs/hwui/renderstate/MeshState.h
@@ -42,6 +42,7 @@ const TextureVertex kUnitQuadVertices[] = {
const GLsizei kVertexStride = sizeof(Vertex);
const GLsizei kAlphaVertexStride = sizeof(AlphaVertex);
const GLsizei kTextureVertexStride = sizeof(TextureVertex);
+const GLsizei kColorTextureVertexStride = sizeof(ColorTextureVertex);
const GLsizei kMeshTextureOffset = 2 * sizeof(float);
const GLsizei kVertexAlphaOffset = 2 * sizeof(float);
diff --git a/libs/hwui/renderstate/RenderState.cpp b/libs/hwui/renderstate/RenderState.cpp
index 192bf81..7992077 100644
--- a/libs/hwui/renderstate/RenderState.cpp
+++ b/libs/hwui/renderstate/RenderState.cpp
@@ -199,16 +199,10 @@ void RenderState::postDecStrong(VirtualLightRefBase* object) {
// Render
///////////////////////////////////////////////////////////////////////////////
-/*
- * Not yet supported:
- *
- * Textures + coordinates
- * SkiaShader
- * RoundRect clipping
- */
-
void RenderState::render(const Glop& glop) {
const Glop::Mesh& mesh = glop.mesh;
+ const Glop::Mesh::Vertices& vertices = mesh.vertices;
+ const Glop::Mesh::Indices& indices = mesh.indices;
const Glop::Fill& fill = glop.fill;
// ---------------------------------------------
@@ -226,15 +220,15 @@ void RenderState::render(const Glop& glop) {
glop.transform.fudgingOffset);
// Color filter uniforms
- if (glop.fill.filterMode == ProgramDescription::kColorBlend) {
- const FloatColor& color = glop.fill.filter.color;
+ if (fill.filterMode == ProgramDescription::kColorBlend) {
+ const FloatColor& color = fill.filter.color;
glUniform4f(mCaches->program().getUniform("colorBlend"),
color.r, color.g, color.b, color.a);
- } else if (glop.fill.filterMode == ProgramDescription::kColorMatrix) {
+ } else if (fill.filterMode == ProgramDescription::kColorMatrix) {
glUniformMatrix4fv(mCaches->program().getUniform("colorMatrix"), 1, GL_FALSE,
- glop.fill.filter.matrix.matrix);
+ fill.filter.matrix.matrix);
glUniform4fv(mCaches->program().getUniform("colorMatrixVector"), 1,
- glop.fill.filter.matrix.vector);
+ fill.filter.matrix.vector);
}
// Round rect clipping uniforms
@@ -253,48 +247,51 @@ void RenderState::render(const Glop& glop) {
glUniform1f(fill.program->getUniform("roundRectRadius"),
roundedOutRadius);
}
+
// --------------------------------
// ---------- Mesh setup ----------
// --------------------------------
// vertices
- const bool force = meshState().bindMeshBufferInternal(mesh.vertexBufferObject)
- || (mesh.vertices != nullptr);
- meshState().bindPositionVertexPointer(force, mesh.vertices, mesh.stride);
+ const bool force = meshState().bindMeshBufferInternal(vertices.bufferObject)
+ || (vertices.position != nullptr);
+ meshState().bindPositionVertexPointer(force, vertices.position, vertices.stride);
// indices
- meshState().bindIndicesBufferInternal(mesh.indexBufferObject);
+ meshState().bindIndicesBufferInternal(indices.bufferObject);
- if (mesh.vertexFlags & kTextureCoord_Attrib) {
- // glop.fill.texture always takes slot 0, shader samplers increment from there
+ if (vertices.flags & VertexAttribFlags::kTextureCoord) {
+ // fill.texture always takes slot 0, shader samplers increment from there
mCaches->textureState().activateTexture(0);
- if (glop.fill.texture.clamp != GL_INVALID_ENUM) {
- glop.fill.texture.texture->setWrap(glop.fill.texture.clamp, true);
+ if (fill.texture.clamp != GL_INVALID_ENUM) {
+ fill.texture.texture->setWrap(fill.texture.clamp, true);
}
- if (glop.fill.texture.filter != GL_INVALID_ENUM) {
- glop.fill.texture.texture->setFilter(glop.fill.texture.filter, true);
+ if (fill.texture.filter != GL_INVALID_ENUM) {
+ fill.texture.texture->setFilter(fill.texture.filter, true);
}
mCaches->textureState().bindTexture(fill.texture.texture->id);
meshState().enableTexCoordsVertexArray();
- meshState().bindTexCoordsVertexPointer(force, mesh.texCoordOffset, mesh.stride);
+ meshState().bindTexCoordsVertexPointer(force, vertices.texCoord, vertices.stride);
} else {
meshState().disableTexCoordsVertexArray();
}
- if (mesh.vertexFlags & kColor_Attrib) {
- LOG_ALWAYS_FATAL("color vertex attribute not yet supported");
- // TODO: enable color attribute, disable when done
+ int colorLocation = -1;
+ if (vertices.flags & VertexAttribFlags::kColor) {
+ colorLocation = fill.program->getAttrib("colors");
+ glEnableVertexAttribArray(colorLocation);
+ glVertexAttribPointer(colorLocation, 4, GL_FLOAT, GL_FALSE, vertices.stride, vertices.color);
}
- int alphaSlot = -1;
- if (mesh.vertexFlags & kAlpha_Attrib) {
- const void* alphaCoords = ((const GLbyte*) glop.mesh.vertices) + kVertexAlphaOffset;
- alphaSlot = fill.program->getAttrib("vtxAlpha");
- glEnableVertexAttribArray(alphaSlot);
- glVertexAttribPointer(alphaSlot, 1, GL_FLOAT, GL_FALSE, kAlphaVertexStride, alphaCoords);
+ int alphaLocation = -1;
+ if (vertices.flags & VertexAttribFlags::kAlpha) {
+ // NOTE: alpha vertex position is computed assuming no VBO
+ const void* alphaCoords = ((const GLbyte*) vertices.position) + kVertexAlphaOffset;
+ alphaLocation = fill.program->getAttrib("vtxAlpha");
+ glEnableVertexAttribArray(alphaLocation);
+ glVertexAttribPointer(alphaLocation, 1, GL_FLOAT, GL_FALSE, vertices.stride, alphaCoords);
}
-
// Shader uniforms
- SkiaShader::apply(*mCaches, glop.fill.skiaShaderData);
+ SkiaShader::apply(*mCaches, fill.skiaShaderData);
// ------------------------------------
// ---------- GL state setup ----------
@@ -304,27 +301,27 @@ void RenderState::render(const Glop& glop) {
// ------------------------------------
// ---------- Actual drawing ----------
// ------------------------------------
- if (mesh.indexBufferObject == meshState().getQuadListIBO()) {
+ if (indices.bufferObject == meshState().getQuadListIBO()) {
// Since the indexed quad list is of limited length, we loop over
// the glDrawXXX method while updating the vertex pointer
GLsizei elementsCount = mesh.elementCount;
- const GLbyte* vertices = static_cast<const GLbyte*>(mesh.vertices);
+ const GLbyte* vertexData = static_cast<const GLbyte*>(vertices.position);
while (elementsCount > 0) {
GLsizei drawCount = MathUtils::min(elementsCount, (GLsizei) kMaxNumberOfQuads * 6);
// rebind pointers without forcing, since initial bind handled above
- meshState().bindPositionVertexPointer(false, vertices, mesh.stride);
- if (mesh.vertexFlags & kTextureCoord_Attrib) {
+ meshState().bindPositionVertexPointer(false, vertexData, vertices.stride);
+ if (vertices.flags & VertexAttribFlags::kTextureCoord) {
meshState().bindTexCoordsVertexPointer(false,
- vertices + kMeshTextureOffset, mesh.stride);
+ vertexData + kMeshTextureOffset, vertices.stride);
}
glDrawElements(mesh.primitiveMode, drawCount, GL_UNSIGNED_SHORT, nullptr);
elementsCount -= drawCount;
- vertices += (drawCount / 6) * 4 * mesh.stride;
+ vertexData += (drawCount / 6) * 4 * vertices.stride;
}
- } else if (mesh.indexBufferObject || mesh.indices) {
- glDrawElements(mesh.primitiveMode, mesh.elementCount, GL_UNSIGNED_SHORT, mesh.indices);
+ } else if (indices.bufferObject || indices.indices) {
+ glDrawElements(mesh.primitiveMode, mesh.elementCount, GL_UNSIGNED_SHORT, indices.indices);
} else {
glDrawArrays(mesh.primitiveMode, 0, mesh.elementCount);
}
@@ -332,8 +329,11 @@ void RenderState::render(const Glop& glop) {
// -----------------------------------
// ---------- Mesh teardown ----------
// -----------------------------------
- if (glop.mesh.vertexFlags & kAlpha_Attrib) {
- glDisableVertexAttribArray(alphaSlot);
+ if (vertices.flags & VertexAttribFlags::kAlpha) {
+ glDisableVertexAttribArray(alphaLocation);
+ }
+ if (vertices.flags & VertexAttribFlags::kColor) {
+ glDisableVertexAttribArray(colorLocation);
}
}
diff --git a/libs/hwui/utils/Macros.h b/libs/hwui/utils/Macros.h
index 49d364e7..2ed605e 100644
--- a/libs/hwui/utils/Macros.h
+++ b/libs/hwui/utils/Macros.h
@@ -41,6 +41,12 @@
} \
inline int operator&(int lhs, enumType rhs) { \
return lhs & static_cast<int>(rhs); \
+ } \
+ inline int operator&(enumType lhs, int rhs) { \
+ return static_cast<int>(lhs) & rhs; \
+ } \
+ inline int operator&(enumType lhs, enumType rhs) { \
+ return static_cast<int>(lhs) & static_cast<int>(rhs); \
}
#endif /* MACROS_H */