21 #ifndef HX3D_GRAPHICS_FAST_BATCH 22 #define HX3D_GRAPHICS_FAST_BATCH 32 FastBatch(
unsigned int size): size(size), vboId(0), vboIndicesId(0), current(0), currentIdx(0), maxIdx(0), drawing(
false) {
33 vertices.resize(size * 36);
34 indices.resize(size * 6);
37 glGenBuffers(1, &vboId);
38 glGenBuffers(1, &vboIndicesId);
40 glBindBuffer(GL_ARRAY_BUFFER, vboId);
41 glBufferData(GL_ARRAY_BUFFER, size * 36 *
sizeof(
float), NULL, GL_STREAM_DRAW);
42 glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, vboIndicesId);
43 glBufferData(GL_ELEMENT_ARRAY_BUFFER, size * 6 *
sizeof(GLushort), NULL, GL_STREAM_DRAW);
47 this->shader = shader;
57 if (shader ==
nullptr) {
72 void draw(
Sprite& sprite) {
75 Log.
Error(
"FastBatch: not currently drawing !");
80 AttributeArrayBuffer& positions = sprite.
getGeometry()->getAttribute(
"Position");
81 unsigned int vertSize = positions.size() / 3;
82 unsigned int prevMaxIdx = maxIdx;
86 std::vector<float> newPositions;
87 newPositions.resize(vertSize * 3);
89 if (current + vertSize * 3 > size * 36) {
90 Log.
Error(
"FastBatch too small: force flush.");
94 if (maxIdx >= USHRT_MAX) {
95 Log.
Error(
"Too much indices ! (max: 65536): force flush.");
99 for (
unsigned int i = 0; i < vertSize*3; i += 3) {
101 positions.getValue(i),
102 positions.getValue(i+1),
103 positions.getValue(i+2),
107 glm::vec4 npos = model * pos;
109 newPositions[i] = npos.x;
110 newPositions[i+1] = npos.y;
111 newPositions[i+2] = npos.z;
114 for (
unsigned int i = 0; i < vertSize; ++i) {
115 for (
unsigned int j = i * 3; j < (i+1) * 3; ++j) {
116 vertices[current++] = newPositions[j];
118 for (
unsigned int j = i * 4; j < (i+1) * 4; ++j) {
119 vertices[current++] = sprite.
getGeometry()->getAttribute(
"Color").getValue(j);
121 for (
unsigned int j = i * 2; j < (i+1) * 2; ++j) {
122 vertices[current++] = sprite.
getGeometry()->getAttribute(
"Texture").getValue(j);
126 for (
unsigned int i = 0; i < ind.size(); ++i) {
127 unsigned int val = ind.getValue(i) + prevMaxIdx;
128 maxIdx = std::max(maxIdx, val);
129 indices[currentIdx++] = val;
135 glBindBuffer(GL_ARRAY_BUFFER, vboId);
136 glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, vboIndicesId);
138 glBufferSubData(GL_ARRAY_BUFFER, 0, current *
sizeof(
float), vertices.data());
139 glBufferSubData(GL_ELEMENT_ARRAY_BUFFER, 0, currentIdx *
sizeof(GLushort), indices.data());
141 glEnableVertexAttribArray(shader->getAttribute(
"a_position"));
142 glEnableVertexAttribArray(shader->getAttribute(
"a_color"));
143 glEnableVertexAttribArray(shader->getAttribute(
"a_texture"));
145 glVertexAttribPointer(shader->getAttribute(
"a_position"), 3, GL_FLOAT, GL_FALSE, 9*
sizeof(float), BUFFER_OFFSET(0));
146 glVertexAttribPointer(shader->getAttribute(
"a_color"), 4, GL_FLOAT, GL_FALSE, 9*
sizeof(float), BUFFER_OFFSET(3*
sizeof(
float)));
147 glVertexAttribPointer(shader->getAttribute(
"a_texture"), 2, GL_FLOAT, GL_FALSE, 9*
sizeof(float), BUFFER_OFFSET(7*
sizeof(
float)));
149 glDrawElements(GL_TRIANGLES, currentIdx, GL_UNSIGNED_SHORT, BUFFER_OFFSET(0));
151 glDisableVertexAttribArray(shader->getAttribute(
"a_position"));
152 glDisableVertexAttribArray(shader->getAttribute(
"a_color"));
153 glDisableVertexAttribArray(shader->getAttribute(
"a_texture"));
163 unsigned int vboIndicesId;
165 unsigned int current;
166 unsigned int currentIdx;
169 unsigned int drawCalls;
173 std::vector<float> vertices;
174 std::vector<GLushort> indices;
Real batching using real-time VBO generation.
void Error(const std::string fmt,...)
Write an error message.
static hx3d::LogImpl Log
Current log implementation.
Transform transform
Mesh transformation.
Ptr< geom::BaseGeometry > & getGeometry()
Get the mesh geometry.
std::shared_ptr< T > Ptr
Quick-typing shared ptr.