Skip to content
This repository was archived by the owner on Feb 25, 2025. It is now read-only.

Commit b2167a9

Browse files
[Impeller] write vertices geometry data to host buffer. (#49741)
Now that host buffer writes go directly to device buffers, there is no advantage to creating dedicated device buffers for the vertices contents. Fixes flutter/flutter#141202
1 parent 184cc83 commit b2167a9

File tree

1 file changed

+59
-96
lines changed

1 file changed

+59
-96
lines changed

impeller/entity/geometry/vertices_geometry.cc

Lines changed: 59 additions & 96 deletions
Original file line numberDiff line numberDiff line change
@@ -4,10 +4,10 @@
44

55
#include "impeller/entity/geometry/vertices_geometry.h"
66

7+
#include <cstdint>
78
#include <utility>
89

9-
#include <utility>
10-
#include "impeller/core/formats.h"
10+
#include "impeller/core/buffer_view.h"
1111

1212
namespace impeller {
1313

@@ -118,34 +118,22 @@ GeometryResult VerticesGeometry::GetPositionBuffer(
118118
size_t total_vtx_bytes = vertex_count * sizeof(float) * 2;
119119
size_t total_idx_bytes = index_count * sizeof(uint16_t);
120120

121-
DeviceBufferDescriptor buffer_desc;
122-
buffer_desc.size = total_vtx_bytes + total_idx_bytes;
123-
buffer_desc.storage_mode = StorageMode::kHostVisible;
124-
125-
auto buffer =
126-
renderer.GetContext()->GetResourceAllocator()->CreateBuffer(buffer_desc);
121+
auto vertex_buffer = renderer.GetTransientsBuffer().Emplace(
122+
reinterpret_cast<const uint8_t*>(vertices_.data()), total_vtx_bytes,
123+
alignof(float));
127124

128-
if (!buffer->CopyHostBuffer(
129-
reinterpret_cast<const uint8_t*>(vertices_.data()),
130-
Range{0, total_vtx_bytes}, 0)) {
131-
return {};
132-
}
133-
if (index_count > 0 &&
134-
!buffer->CopyHostBuffer(
135-
reinterpret_cast<uint8_t*>(const_cast<uint16_t*>(indices_.data())),
136-
Range{0, total_idx_bytes}, total_vtx_bytes)) {
137-
return {};
125+
BufferView index_buffer = {};
126+
if (index_count) {
127+
index_buffer = renderer.GetTransientsBuffer().Emplace(
128+
indices_.data(), total_idx_bytes, alignof(uint16_t));
138129
}
139130

140131
return GeometryResult{
141132
.type = GetPrimitiveType(),
142133
.vertex_buffer =
143134
{
144-
.vertex_buffer = {.buffer = buffer,
145-
.range = Range{0, total_vtx_bytes}},
146-
.index_buffer = {.buffer = buffer,
147-
.range =
148-
Range{total_vtx_bytes, total_idx_bytes}},
135+
.vertex_buffer = vertex_buffer,
136+
.index_buffer = index_buffer,
149137
.vertex_count = index_count > 0 ? index_count : vertex_count,
150138
.index_type =
151139
index_count > 0 ? IndexType::k16bit : IndexType::kNone,
@@ -163,47 +151,34 @@ GeometryResult VerticesGeometry::GetPositionColorBuffer(
163151

164152
auto index_count = indices_.size();
165153
auto vertex_count = vertices_.size();
166-
167-
std::vector<VS::PerVertexData> vertex_data(vertex_count);
168-
{
169-
for (auto i = 0u; i < vertex_count; i++) {
170-
vertex_data[i] = {
171-
.position = vertices_[i],
172-
.color = colors_[i],
173-
};
174-
}
175-
}
176-
177-
size_t total_vtx_bytes = vertex_data.size() * sizeof(VS::PerVertexData);
154+
size_t total_vtx_bytes = vertex_count * sizeof(VS::PerVertexData);
178155
size_t total_idx_bytes = index_count * sizeof(uint16_t);
179156

180-
DeviceBufferDescriptor buffer_desc;
181-
buffer_desc.size = total_vtx_bytes + total_idx_bytes;
182-
buffer_desc.storage_mode = StorageMode::kHostVisible;
183-
184-
auto buffer =
185-
renderer.GetContext()->GetResourceAllocator()->CreateBuffer(buffer_desc);
186-
187-
if (!buffer->CopyHostBuffer(reinterpret_cast<uint8_t*>(vertex_data.data()),
188-
Range{0, total_vtx_bytes}, 0)) {
189-
return {};
190-
}
191-
if (index_count > 0 &&
192-
!buffer->CopyHostBuffer(
193-
reinterpret_cast<uint8_t*>(const_cast<uint16_t*>(indices_.data())),
194-
Range{0, total_idx_bytes}, total_vtx_bytes)) {
195-
return {};
157+
auto vertex_buffer = renderer.GetTransientsBuffer().Emplace(
158+
total_vtx_bytes, alignof(VS::PerVertexData), [&](uint8_t* data) {
159+
VS::PerVertexData* vtx_contents =
160+
reinterpret_cast<VS::PerVertexData*>(data);
161+
for (auto i = 0u; i < vertices_.size(); i++) {
162+
VS::PerVertexData vertex_data = {
163+
.position = vertices_[i],
164+
.color = colors_[i],
165+
};
166+
std::memcpy(vtx_contents++, &vertex_data, sizeof(VS::PerVertexData));
167+
}
168+
});
169+
170+
BufferView index_buffer = {};
171+
if (index_count > 0) {
172+
index_buffer = renderer.GetTransientsBuffer().Emplace(
173+
indices_.data(), total_idx_bytes, alignof(uint16_t));
196174
}
197175

198176
return GeometryResult{
199177
.type = GetPrimitiveType(),
200178
.vertex_buffer =
201179
{
202-
.vertex_buffer = {.buffer = buffer,
203-
.range = Range{0, total_vtx_bytes}},
204-
.index_buffer = {.buffer = buffer,
205-
.range =
206-
Range{total_vtx_bytes, total_idx_bytes}},
180+
.vertex_buffer = vertex_buffer,
181+
.index_buffer = index_buffer,
207182
.vertex_count = index_count > 0 ? index_count : vertex_count,
208183
.index_type =
209184
index_count > 0 ? IndexType::k16bit : IndexType::kNone,
@@ -226,54 +201,42 @@ GeometryResult VerticesGeometry::GetPositionUVBuffer(
226201
auto uv_transform =
227202
texture_coverage.GetNormalizingTransform() * effect_transform;
228203
auto has_texture_coordinates = HasTextureCoordinates();
229-
std::vector<VS::PerVertexData> vertex_data(vertex_count);
230-
{
231-
for (auto i = 0u; i < vertex_count; i++) {
232-
auto vertex = vertices_[i];
233-
auto texture_coord =
234-
has_texture_coordinates ? texture_coordinates_[i] : vertices_[i];
235-
auto uv = uv_transform * texture_coord;
236-
// From experimentation we need to clamp these values to < 1.0 or else
237-
// there can be flickering.
238-
vertex_data[i] = {
239-
.position = vertex,
240-
.texture_coords =
241-
Point(std::clamp(uv.x, 0.0f, 1.0f - kEhCloseEnough),
242-
std::clamp(uv.y, 0.0f, 1.0f - kEhCloseEnough)),
243-
};
244-
}
245-
}
246204

247-
size_t total_vtx_bytes = vertex_data.size() * sizeof(VS::PerVertexData);
205+
size_t total_vtx_bytes = vertices_.size() * sizeof(VS::PerVertexData);
248206
size_t total_idx_bytes = index_count * sizeof(uint16_t);
249-
250-
DeviceBufferDescriptor buffer_desc;
251-
buffer_desc.size = total_vtx_bytes + total_idx_bytes;
252-
buffer_desc.storage_mode = StorageMode::kHostVisible;
253-
254-
auto buffer =
255-
renderer.GetContext()->GetResourceAllocator()->CreateBuffer(buffer_desc);
256-
257-
if (!buffer->CopyHostBuffer(reinterpret_cast<uint8_t*>(vertex_data.data()),
258-
Range{0, total_vtx_bytes}, 0)) {
259-
return {};
260-
}
261-
if (index_count > 0u &&
262-
!buffer->CopyHostBuffer(
263-
reinterpret_cast<uint8_t*>(const_cast<uint16_t*>(indices_.data())),
264-
Range{0, total_idx_bytes}, total_vtx_bytes)) {
265-
return {};
207+
auto vertex_buffer = renderer.GetTransientsBuffer().Emplace(
208+
total_vtx_bytes, alignof(VS::PerVertexData), [&](uint8_t* data) {
209+
VS::PerVertexData* vtx_contents =
210+
reinterpret_cast<VS::PerVertexData*>(data);
211+
for (auto i = 0u; i < vertices_.size(); i++) {
212+
auto vertex = vertices_[i];
213+
auto texture_coord =
214+
has_texture_coordinates ? texture_coordinates_[i] : vertices_[i];
215+
auto uv = uv_transform * texture_coord;
216+
// From experimentation we need to clamp these values to < 1.0 or else
217+
// there can be flickering.
218+
VS::PerVertexData vertex_data = {
219+
.position = vertex,
220+
.texture_coords =
221+
Point(std::clamp(uv.x, 0.0f, 1.0f - kEhCloseEnough),
222+
std::clamp(uv.y, 0.0f, 1.0f - kEhCloseEnough)),
223+
};
224+
std::memcpy(vtx_contents++, &vertex_data, sizeof(VS::PerVertexData));
225+
}
226+
});
227+
228+
BufferView index_buffer = {};
229+
if (index_count > 0) {
230+
index_buffer = renderer.GetTransientsBuffer().Emplace(
231+
indices_.data(), total_idx_bytes, alignof(uint16_t));
266232
}
267233

268234
return GeometryResult{
269235
.type = GetPrimitiveType(),
270236
.vertex_buffer =
271237
{
272-
.vertex_buffer = {.buffer = buffer,
273-
.range = Range{0, total_vtx_bytes}},
274-
.index_buffer = {.buffer = buffer,
275-
.range =
276-
Range{total_vtx_bytes, total_idx_bytes}},
238+
.vertex_buffer = vertex_buffer,
239+
.index_buffer = index_buffer,
277240
.vertex_count = index_count > 0 ? index_count : vertex_count,
278241
.index_type =
279242
index_count > 0 ? IndexType::k16bit : IndexType::kNone,

0 commit comments

Comments
 (0)