196a5c4c7bab6718524de7253da8309143ab48befChris Craik/* 296a5c4c7bab6718524de7253da8309143ab48befChris Craik * Copyright (C) 2015 The Android Open Source Project 396a5c4c7bab6718524de7253da8309143ab48befChris Craik * 496a5c4c7bab6718524de7253da8309143ab48befChris Craik * Licensed under the Apache License, Version 2.0 (the "License"); 596a5c4c7bab6718524de7253da8309143ab48befChris Craik * you may not use this file except in compliance with the License. 696a5c4c7bab6718524de7253da8309143ab48befChris Craik * You may obtain a copy of the License at 796a5c4c7bab6718524de7253da8309143ab48befChris Craik * 896a5c4c7bab6718524de7253da8309143ab48befChris Craik * http://www.apache.org/licenses/LICENSE-2.0 996a5c4c7bab6718524de7253da8309143ab48befChris Craik * 1096a5c4c7bab6718524de7253da8309143ab48befChris Craik * Unless required by applicable law or agreed to in writing, software 1196a5c4c7bab6718524de7253da8309143ab48befChris Craik * distributed under the License is distributed on an "AS IS" BASIS, 1296a5c4c7bab6718524de7253da8309143ab48befChris Craik * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1396a5c4c7bab6718524de7253da8309143ab48befChris Craik * See the License for the specific language governing permissions and 1496a5c4c7bab6718524de7253da8309143ab48befChris Craik * limitations under the License. 1596a5c4c7bab6718524de7253da8309143ab48befChris Craik */ 1696a5c4c7bab6718524de7253da8309143ab48befChris Craik#include "renderstate/MeshState.h" 1796a5c4c7bab6718524de7253da8309143ab48befChris Craik 1896a5c4c7bab6718524de7253da8309143ab48befChris Craik#include "Program.h" 1996a5c4c7bab6718524de7253da8309143ab48befChris Craik 2096a5c4c7bab6718524de7253da8309143ab48befChris Craik#include "ShadowTessellator.h" 2196a5c4c7bab6718524de7253da8309143ab48befChris Craik 2296a5c4c7bab6718524de7253da8309143ab48befChris Craiknamespace android { 2396a5c4c7bab6718524de7253da8309143ab48befChris Craiknamespace uirenderer { 2496a5c4c7bab6718524de7253da8309143ab48befChris Craik 2596a5c4c7bab6718524de7253da8309143ab48befChris CraikMeshState::MeshState() 26117bdbcfa3e8306dad21e7e01fa71b00cdfa7265Chris Craik : mCurrentIndicesBuffer(0) 27117bdbcfa3e8306dad21e7e01fa71b00cdfa7265Chris Craik , mCurrentPixelBuffer(0) 28117bdbcfa3e8306dad21e7e01fa71b00cdfa7265Chris Craik , mCurrentPositionPointer(this) 2996a5c4c7bab6718524de7253da8309143ab48befChris Craik , mCurrentPositionStride(0) 3096a5c4c7bab6718524de7253da8309143ab48befChris Craik , mCurrentTexCoordsPointer(this) 3196a5c4c7bab6718524de7253da8309143ab48befChris Craik , mCurrentTexCoordsStride(0) 32117bdbcfa3e8306dad21e7e01fa71b00cdfa7265Chris Craik , mTexCoordsArrayEnabled(false) 33117bdbcfa3e8306dad21e7e01fa71b00cdfa7265Chris Craik , mQuadListIndices(0) { 34031888744e24b5c7243ac99ec98b78aff5db1c78Chris Craik glGenBuffers(1, &mUnitQuadBuffer); 35031888744e24b5c7243ac99ec98b78aff5db1c78Chris Craik glBindBuffer(GL_ARRAY_BUFFER, mUnitQuadBuffer); 36031888744e24b5c7243ac99ec98b78aff5db1c78Chris Craik glBufferData(GL_ARRAY_BUFFER, sizeof(kUnitQuadVertices), kUnitQuadVertices, GL_STATIC_DRAW); 37031888744e24b5c7243ac99ec98b78aff5db1c78Chris Craik mCurrentBuffer = mUnitQuadBuffer; 386c15ffa196fc9b7724c189d833c3435d8db12266Chris Craik 39182952f5eeefc2a21d76d4664ada0e2d78c1105cChris Craik uint16_t regionIndices[kMaxNumberOfQuads * 6]; 402ab95d780b023152556d9f8659de734ec7b55047Chris Craik for (uint32_t i = 0; i < kMaxNumberOfQuads; i++) { 412ab95d780b023152556d9f8659de734ec7b55047Chris Craik uint16_t quad = i * 4; 422ab95d780b023152556d9f8659de734ec7b55047Chris Craik int index = i * 6; 432ab95d780b023152556d9f8659de734ec7b55047Chris Craik regionIndices[index ] = quad; // top-left 442ab95d780b023152556d9f8659de734ec7b55047Chris Craik regionIndices[index + 1] = quad + 1; // top-right 452ab95d780b023152556d9f8659de734ec7b55047Chris Craik regionIndices[index + 2] = quad + 2; // bottom-left 462ab95d780b023152556d9f8659de734ec7b55047Chris Craik regionIndices[index + 3] = quad + 2; // bottom-left 472ab95d780b023152556d9f8659de734ec7b55047Chris Craik regionIndices[index + 4] = quad + 1; // top-right 482ab95d780b023152556d9f8659de734ec7b55047Chris Craik regionIndices[index + 5] = quad + 3; // bottom-right 492ab95d780b023152556d9f8659de734ec7b55047Chris Craik } 502ab95d780b023152556d9f8659de734ec7b55047Chris Craik glGenBuffers(1, &mQuadListIndices); 512ab95d780b023152556d9f8659de734ec7b55047Chris Craik glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, mQuadListIndices); 52182952f5eeefc2a21d76d4664ada0e2d78c1105cChris Craik glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(regionIndices), regionIndices, GL_STATIC_DRAW); 532ab95d780b023152556d9f8659de734ec7b55047Chris Craik mCurrentIndicesBuffer = mQuadListIndices; 542ab95d780b023152556d9f8659de734ec7b55047Chris Craik 556c15ffa196fc9b7724c189d833c3435d8db12266Chris Craik // position attribute always enabled 566c15ffa196fc9b7724c189d833c3435d8db12266Chris Craik glEnableVertexAttribArray(Program::kBindingPosition); 5796a5c4c7bab6718524de7253da8309143ab48befChris Craik} 5896a5c4c7bab6718524de7253da8309143ab48befChris Craik 5996a5c4c7bab6718524de7253da8309143ab48befChris CraikMeshState::~MeshState() { 60031888744e24b5c7243ac99ec98b78aff5db1c78Chris Craik glDeleteBuffers(1, &mUnitQuadBuffer); 6196a5c4c7bab6718524de7253da8309143ab48befChris Craik mCurrentBuffer = 0; 6296a5c4c7bab6718524de7253da8309143ab48befChris Craik 6396a5c4c7bab6718524de7253da8309143ab48befChris Craik glDeleteBuffers(1, &mQuadListIndices); 6496a5c4c7bab6718524de7253da8309143ab48befChris Craik mQuadListIndices = 0; 65117bdbcfa3e8306dad21e7e01fa71b00cdfa7265Chris Craik} 6696a5c4c7bab6718524de7253da8309143ab48befChris Craik 67117bdbcfa3e8306dad21e7e01fa71b00cdfa7265Chris Craikvoid MeshState::dump() { 6808fa43fdeb646f56edcd8b33d06ee7d79b203426Chris Craik ALOGD("MeshState VBOs: unitQuad %d, current %d", mUnitQuadBuffer, mCurrentBuffer); 69f27133df2d179c99d6bc1ae644af09e9153a0071Chris Craik ALOGD("MeshState IBOs: quadList %d, current %d", mQuadListIndices, mCurrentIndicesBuffer); 7008fa43fdeb646f56edcd8b33d06ee7d79b203426Chris Craik ALOGD("MeshState vertices: vertex data %p, stride %d", 7108fa43fdeb646f56edcd8b33d06ee7d79b203426Chris Craik mCurrentPositionPointer, mCurrentPositionStride); 7208fa43fdeb646f56edcd8b33d06ee7d79b203426Chris Craik ALOGD("MeshState texCoord: data %p, stride %d", 7308fa43fdeb646f56edcd8b33d06ee7d79b203426Chris Craik mCurrentTexCoordsPointer, mCurrentTexCoordsStride); 7496a5c4c7bab6718524de7253da8309143ab48befChris Craik} 7596a5c4c7bab6718524de7253da8309143ab48befChris Craik 7696a5c4c7bab6718524de7253da8309143ab48befChris Craik/////////////////////////////////////////////////////////////////////////////// 7796a5c4c7bab6718524de7253da8309143ab48befChris Craik// Buffer Objects 7896a5c4c7bab6718524de7253da8309143ab48befChris Craik/////////////////////////////////////////////////////////////////////////////// 7996a5c4c7bab6718524de7253da8309143ab48befChris Craik 801b7db4000eabb570697f4c5097588acbfa4df62bChris Craikvoid MeshState::bindMeshBuffer(GLuint buffer) { 81117bdbcfa3e8306dad21e7e01fa71b00cdfa7265Chris Craik if (mCurrentBuffer != buffer) { 82117bdbcfa3e8306dad21e7e01fa71b00cdfa7265Chris Craik glBindBuffer(GL_ARRAY_BUFFER, buffer); 83117bdbcfa3e8306dad21e7e01fa71b00cdfa7265Chris Craik mCurrentBuffer = buffer; 841b7db4000eabb570697f4c5097588acbfa4df62bChris Craik 851b7db4000eabb570697f4c5097588acbfa4df62bChris Craik // buffer has changed, so invalidate cached vertex pos/texcoord pointers 861b7db4000eabb570697f4c5097588acbfa4df62bChris Craik resetVertexPointers(); 8796a5c4c7bab6718524de7253da8309143ab48befChris Craik } 881b7db4000eabb570697f4c5097588acbfa4df62bChris Craik} 891b7db4000eabb570697f4c5097588acbfa4df62bChris Craik 901b7db4000eabb570697f4c5097588acbfa4df62bChris Craikvoid MeshState::unbindMeshBuffer() { 911b7db4000eabb570697f4c5097588acbfa4df62bChris Craik return bindMeshBuffer(0); 9296a5c4c7bab6718524de7253da8309143ab48befChris Craik} 9396a5c4c7bab6718524de7253da8309143ab48befChris Craik 948d2cf943d9c7292e54726399faefdec4a01c084bChris Craikvoid MeshState::genOrUpdateMeshBuffer(GLuint* buffer, GLsizeiptr size, 958d2cf943d9c7292e54726399faefdec4a01c084bChris Craik const void* data, GLenum usage) { 968d2cf943d9c7292e54726399faefdec4a01c084bChris Craik if (!*buffer) { 978d2cf943d9c7292e54726399faefdec4a01c084bChris Craik glGenBuffers(1, buffer); 988d2cf943d9c7292e54726399faefdec4a01c084bChris Craik } 998d2cf943d9c7292e54726399faefdec4a01c084bChris Craik bindMeshBuffer(*buffer); 1008d2cf943d9c7292e54726399faefdec4a01c084bChris Craik glBufferData(GL_ARRAY_BUFFER, size, data, usage); 1018d2cf943d9c7292e54726399faefdec4a01c084bChris Craik} 1028d2cf943d9c7292e54726399faefdec4a01c084bChris Craik 1038d2cf943d9c7292e54726399faefdec4a01c084bChris Craikvoid MeshState::deleteMeshBuffer(GLuint buffer) { 1048d2cf943d9c7292e54726399faefdec4a01c084bChris Craik if (buffer == mCurrentBuffer) { 1058d2cf943d9c7292e54726399faefdec4a01c084bChris Craik // GL defines that deleting the currently bound VBO rebinds to 0 (no VBO). 1068d2cf943d9c7292e54726399faefdec4a01c084bChris Craik // Reflect this in our cached value. 1078d2cf943d9c7292e54726399faefdec4a01c084bChris Craik mCurrentBuffer = 0; 1088d2cf943d9c7292e54726399faefdec4a01c084bChris Craik } 1098d2cf943d9c7292e54726399faefdec4a01c084bChris Craik glDeleteBuffers(1, &buffer); 1108d2cf943d9c7292e54726399faefdec4a01c084bChris Craik} 1118d2cf943d9c7292e54726399faefdec4a01c084bChris Craik 11296a5c4c7bab6718524de7253da8309143ab48befChris Craik/////////////////////////////////////////////////////////////////////////////// 11396a5c4c7bab6718524de7253da8309143ab48befChris Craik// Vertices 11496a5c4c7bab6718524de7253da8309143ab48befChris Craik/////////////////////////////////////////////////////////////////////////////// 11596a5c4c7bab6718524de7253da8309143ab48befChris Craik 1161b7db4000eabb570697f4c5097588acbfa4df62bChris Craikvoid MeshState::bindPositionVertexPointer(const GLvoid* vertices, GLsizei stride) { 1171b7db4000eabb570697f4c5097588acbfa4df62bChris Craik // update pos coords if !current vbo, since vertices may point into mutable memory (e.g. stack) 1181b7db4000eabb570697f4c5097588acbfa4df62bChris Craik if (mCurrentBuffer == 0 1191b7db4000eabb570697f4c5097588acbfa4df62bChris Craik || vertices != mCurrentPositionPointer 1201b7db4000eabb570697f4c5097588acbfa4df62bChris Craik || stride != mCurrentPositionStride) { 1216c15ffa196fc9b7724c189d833c3435d8db12266Chris Craik glVertexAttribPointer(Program::kBindingPosition, 2, GL_FLOAT, GL_FALSE, stride, vertices); 12296a5c4c7bab6718524de7253da8309143ab48befChris Craik mCurrentPositionPointer = vertices; 12396a5c4c7bab6718524de7253da8309143ab48befChris Craik mCurrentPositionStride = stride; 12496a5c4c7bab6718524de7253da8309143ab48befChris Craik } 12596a5c4c7bab6718524de7253da8309143ab48befChris Craik} 12696a5c4c7bab6718524de7253da8309143ab48befChris Craik 1271b7db4000eabb570697f4c5097588acbfa4df62bChris Craikvoid MeshState::bindTexCoordsVertexPointer(const GLvoid* vertices, GLsizei stride) { 1281b7db4000eabb570697f4c5097588acbfa4df62bChris Craik // update tex coords if !current vbo, since vertices may point into mutable memory (e.g. stack) 1291b7db4000eabb570697f4c5097588acbfa4df62bChris Craik if (mCurrentBuffer == 0 1301b7db4000eabb570697f4c5097588acbfa4df62bChris Craik || vertices != mCurrentTexCoordsPointer 1311b7db4000eabb570697f4c5097588acbfa4df62bChris Craik || stride != mCurrentTexCoordsStride) { 1326c15ffa196fc9b7724c189d833c3435d8db12266Chris Craik glVertexAttribPointer(Program::kBindingTexCoords, 2, GL_FLOAT, GL_FALSE, stride, vertices); 13396a5c4c7bab6718524de7253da8309143ab48befChris Craik mCurrentTexCoordsPointer = vertices; 13496a5c4c7bab6718524de7253da8309143ab48befChris Craik mCurrentTexCoordsStride = stride; 13596a5c4c7bab6718524de7253da8309143ab48befChris Craik } 13696a5c4c7bab6718524de7253da8309143ab48befChris Craik} 13796a5c4c7bab6718524de7253da8309143ab48befChris Craik 13896a5c4c7bab6718524de7253da8309143ab48befChris Craikvoid MeshState::resetVertexPointers() { 13996a5c4c7bab6718524de7253da8309143ab48befChris Craik mCurrentPositionPointer = this; 14096a5c4c7bab6718524de7253da8309143ab48befChris Craik mCurrentTexCoordsPointer = this; 14196a5c4c7bab6718524de7253da8309143ab48befChris Craik} 14296a5c4c7bab6718524de7253da8309143ab48befChris Craik 14396a5c4c7bab6718524de7253da8309143ab48befChris Craikvoid MeshState::enableTexCoordsVertexArray() { 14496a5c4c7bab6718524de7253da8309143ab48befChris Craik if (!mTexCoordsArrayEnabled) { 14596a5c4c7bab6718524de7253da8309143ab48befChris Craik glEnableVertexAttribArray(Program::kBindingTexCoords); 14696a5c4c7bab6718524de7253da8309143ab48befChris Craik mCurrentTexCoordsPointer = this; 14796a5c4c7bab6718524de7253da8309143ab48befChris Craik mTexCoordsArrayEnabled = true; 14896a5c4c7bab6718524de7253da8309143ab48befChris Craik } 14996a5c4c7bab6718524de7253da8309143ab48befChris Craik} 15096a5c4c7bab6718524de7253da8309143ab48befChris Craik 15196a5c4c7bab6718524de7253da8309143ab48befChris Craikvoid MeshState::disableTexCoordsVertexArray() { 15296a5c4c7bab6718524de7253da8309143ab48befChris Craik if (mTexCoordsArrayEnabled) { 15396a5c4c7bab6718524de7253da8309143ab48befChris Craik glDisableVertexAttribArray(Program::kBindingTexCoords); 15496a5c4c7bab6718524de7253da8309143ab48befChris Craik mTexCoordsArrayEnabled = false; 15596a5c4c7bab6718524de7253da8309143ab48befChris Craik } 15696a5c4c7bab6718524de7253da8309143ab48befChris Craik} 15796a5c4c7bab6718524de7253da8309143ab48befChris Craik 15896a5c4c7bab6718524de7253da8309143ab48befChris Craik/////////////////////////////////////////////////////////////////////////////// 15996a5c4c7bab6718524de7253da8309143ab48befChris Craik// Indices 16096a5c4c7bab6718524de7253da8309143ab48befChris Craik/////////////////////////////////////////////////////////////////////////////// 16196a5c4c7bab6718524de7253da8309143ab48befChris Craik 1621b7db4000eabb570697f4c5097588acbfa4df62bChris Craikvoid MeshState::bindIndicesBuffer(const GLuint buffer) { 16396a5c4c7bab6718524de7253da8309143ab48befChris Craik if (mCurrentIndicesBuffer != buffer) { 16496a5c4c7bab6718524de7253da8309143ab48befChris Craik glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, buffer); 16596a5c4c7bab6718524de7253da8309143ab48befChris Craik mCurrentIndicesBuffer = buffer; 16696a5c4c7bab6718524de7253da8309143ab48befChris Craik } 16796a5c4c7bab6718524de7253da8309143ab48befChris Craik} 16896a5c4c7bab6718524de7253da8309143ab48befChris Craik 1691b7db4000eabb570697f4c5097588acbfa4df62bChris Craikvoid MeshState::unbindIndicesBuffer() { 17096a5c4c7bab6718524de7253da8309143ab48befChris Craik if (mCurrentIndicesBuffer) { 17196a5c4c7bab6718524de7253da8309143ab48befChris Craik glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0); 17296a5c4c7bab6718524de7253da8309143ab48befChris Craik mCurrentIndicesBuffer = 0; 17396a5c4c7bab6718524de7253da8309143ab48befChris Craik } 17496a5c4c7bab6718524de7253da8309143ab48befChris Craik} 17596a5c4c7bab6718524de7253da8309143ab48befChris Craik 17696a5c4c7bab6718524de7253da8309143ab48befChris Craik} /* namespace uirenderer */ 17796a5c4c7bab6718524de7253da8309143ab48befChris Craik} /* namespace android */ 17896a5c4c7bab6718524de7253da8309143ab48befChris Craik 179