| Flutter Impeller |

vertex_buffer_builder.h
Go to the documentation of this file.
1 // Copyright 2013 The Flutter Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #pragma once
6
7 #include <initializer_list>
8 #include <map>
9 #include <vector>
10
11 #include "flutter/fml/macros.h"
12 #include "impeller/base/strings.h"
13 #include "impeller/core/allocator.h"
14 #include "impeller/core/device_buffer.h"
15 #include "impeller/core/formats.h"
16 #include "impeller/core/host_buffer.h"
17 #include "impeller/core/vertex_buffer.h"
18 #include "impeller/geometry/vector.h"
19
20 namespace impeller {
21
22 template <class VertexType_, class IndexType_ = uint16_t>
23 class VertexBufferBuilder {
24 public:
25 using VertexType = VertexType_;
26 using IndexType = IndexType_;
27
28 VertexBufferBuilder() = default;
29
30 ~VertexBufferBuilder() = default;
31
32 constexpr impeller::IndexType GetIndexType() const {
33 if (indices_.size() == 0) {
34 return impeller::IndexType::kNone;
35 }
36 if constexpr (sizeof(IndexType) == 2) {
37 return impeller::IndexType::k16bit;
38 }
39 if (sizeof(IndexType) == 4) {
40 return impeller::IndexType::k32bit;
41 }
42 return impeller::IndexType::kUnknown;
43 }
44
45 void SetLabel(std::string label) { label_ = std::move(label); }
46
47 void Reserve(size_t count) { return vertices_.reserve(count); }
48
49 void ReserveIndices(size_t count) { return indices_.reserve(count); }
50
51 bool HasVertices() const { return !vertices_.empty(); }
52
53 size_t GetVertexCount() const { return vertices_.size(); }
54
55 size_t GetIndexCount() const {
56 return indices_.size() > 0 ? indices_.size() : vertices_.size();
57 }
58
59 VertexBufferBuilder& AppendVertex(VertexType_ vertex) {
60 vertices_.emplace_back(std::move(vertex));
61 return *this;
62 }
63
64 VertexBufferBuilder& AddVertices(
65 std::initializer_list<VertexType_> vertices) {
66 vertices_.reserve(vertices.size());
67 for (auto& vertex : vertices) {
68 vertices_.emplace_back(std::move(vertex));
69 }
70 return *this;
71 }
72
73 VertexBufferBuilder& AppendIndex(IndexType_ index) {
74 indices_.emplace_back(index);
75 return *this;
76 }
77
78 VertexBuffer CreateVertexBuffer(HostBuffer& host_buffer) const {
79 VertexBuffer buffer;
80 buffer.vertex_buffer = CreateVertexBufferView(host_buffer);
81 buffer.index_buffer = CreateIndexBufferView(host_buffer);
82 buffer.vertex_count = GetIndexCount();
83 buffer.index_type = GetIndexType();
84 return buffer;
85 };
86
87 VertexBuffer CreateVertexBuffer(Allocator& device_allocator) const {
88 VertexBuffer buffer;
89 // This can be merged into a single allocation.
90 buffer.vertex_buffer = CreateVertexBufferView(device_allocator);
91 buffer.index_buffer = CreateIndexBufferView(device_allocator);
92 buffer.vertex_count = GetIndexCount();
93 buffer.index_type = GetIndexType();
94 return buffer;
95 };
96
97 void IterateVertices(const std::function<void(VertexType&)>& iterator) {
98 for (auto& vertex : vertices_) {
99 iterator(vertex);
100 }
101 }
102
103 private:
104 std::vector<VertexType> vertices_;
105 std::vector<IndexType> indices_;
106 std::string label_;
107
108 BufferView CreateVertexBufferView(HostBuffer& buffer) const {
109 return buffer.Emplace(vertices_.data(),
110 vertices_.size() * sizeof(VertexType),
111 alignof(VertexType));
112 }
113
114 BufferView CreateVertexBufferView(Allocator& allocator) const {
115 auto buffer = allocator.CreateBufferWithCopy(
116 reinterpret_cast<const uint8_t*>(vertices_.data()),
117 vertices_.size() * sizeof(VertexType));
118 if (!buffer) {
119 return {};
120 }
121 if (!label_.empty()) {
122 buffer->SetLabel(SPrintF("%s Vertices", label_.c_str()));
123 }
124 return buffer->AsBufferView();
125 }
126
127 std::vector<IndexType> CreateIndexBuffer() const { return indices_; }
128
129 BufferView CreateIndexBufferView(HostBuffer& buffer) const {
130 const auto index_buffer = CreateIndexBuffer();
131 if (index_buffer.size() == 0) {
132 return {};
133 }
134 return buffer.Emplace(index_buffer.data(),
135 index_buffer.size() * sizeof(IndexType),
136 alignof(IndexType));
137 }
138
139 BufferView CreateIndexBufferView(Allocator& allocator) const {
140 const auto index_buffer = CreateIndexBuffer();
141 if (index_buffer.size() == 0) {
142 return {};
143 }
144 auto buffer = allocator.CreateBufferWithCopy(
145 reinterpret_cast<const uint8_t*>(index_buffer.data()),
146 index_buffer.size() * sizeof(IndexType));
147 if (!buffer) {
148 return {};
149 }
150 if (!label_.empty()) {
151 buffer->SetLabel(SPrintF("%s Indices", label_.c_str()));
152 }
153 return buffer->AsBufferView();
154 }
155 };
156
157 } // namespace impeller
impeller::VertexBuffer::index_type
IndexType index_type
Definition: vertex_buffer.h:18
host_buffer.h
impeller::IndexType::k16bit
@ k16bit
vertex_buffer.h
impeller::VertexBufferBuilder::GetVertexCount
size_t GetVertexCount() const
Definition: vertex_buffer_builder.h:53
device_buffer.h
impeller::VertexBufferBuilder::VertexType
VertexType_ VertexType
Definition: vertex_buffer_builder.h:25
impeller::HostBuffer
Definition: host_buffer.h:20
impeller::VertexBufferBuilder::~VertexBufferBuilder
~VertexBufferBuilder()=default
impeller::VertexBuffer
Definition: vertex_buffer.h:12
formats.h
impeller::HostBuffer::Emplace
BufferView Emplace(const BufferType &buffer)
Emplace non-uniform data (like contiguous vertices) onto the host buffer.
Definition: host_buffer.h:87
impeller::VertexBufferBuilder::AddVertices
VertexBufferBuilder & AddVertices(std::initializer_list< VertexType_ > vertices)
Definition: vertex_buffer_builder.h:64
impeller::IndexType::k32bit
@ k32bit
impeller::VertexBuffer::vertex_buffer
BufferView vertex_buffer
Definition: vertex_buffer.h:13
impeller::VertexBuffer::vertex_count
size_t vertex_count
Definition: vertex_buffer.h:17
impeller::VertexBufferBuilder::CreateVertexBuffer
VertexBuffer CreateVertexBuffer(Allocator &device_allocator) const
Definition: vertex_buffer_builder.h:87
impeller::VertexBufferBuilder::VertexBufferBuilder
VertexBufferBuilder()=default
impeller::VertexBufferBuilder::HasVertices
bool HasVertices() const
Definition: vertex_buffer_builder.h:51
impeller::SPrintF
std::string SPrintF(const char *format,...)
Definition: strings.cc:12
impeller::VertexBufferBuilder
Definition: vertex_buffer_builder.h:23
impeller::IndexType
IndexType
Definition: formats.h:320
impeller::VertexBufferBuilder::GetIndexCount
size_t GetIndexCount() const
Definition: vertex_buffer_builder.h:55
impeller::IndexType::kNone
@ kNone
Does not use the index buffer.
impeller::Allocator
An object that allocates device memory.
Definition: allocator.h:25
strings.h
impeller::VertexBufferBuilder::AppendIndex
VertexBufferBuilder & AppendIndex(IndexType_ index)
Definition: vertex_buffer_builder.h:73
impeller::VertexBufferBuilder::CreateVertexBuffer
VertexBuffer CreateVertexBuffer(HostBuffer &host_buffer) const
Definition: vertex_buffer_builder.h:78
impeller::VertexBufferBuilder::IterateVertices
void IterateVertices(const std::function< void(VertexType &)> &iterator)
Definition: vertex_buffer_builder.h:97
impeller::VertexBufferBuilder::ReserveIndices
void ReserveIndices(size_t count)
Definition: vertex_buffer_builder.h:49
impeller::VertexBuffer::index_buffer
BufferView index_buffer
Definition: vertex_buffer.h:14
allocator.h
impeller::VertexBufferBuilder::IndexType
IndexType_ IndexType
Definition: vertex_buffer_builder.h:26
impeller::BufferView
Definition: buffer_view.h:13
impeller::VertexBufferBuilder::GetIndexType
constexpr impeller::IndexType GetIndexType() const
Definition: vertex_buffer_builder.h:32
vector.h
impeller::VertexBufferBuilder::SetLabel
void SetLabel(std::string label)
Definition: vertex_buffer_builder.h:45
impeller::VertexBufferBuilder::AppendVertex
VertexBufferBuilder & AppendVertex(VertexType_ vertex)
Definition: vertex_buffer_builder.h:59
impeller::VertexBufferBuilder::Reserve
void Reserve(size_t count)
Definition: vertex_buffer_builder.h:47
impeller::HostBuffer::SetLabel
void SetLabel(std::string label)
Definition: host_buffer.cc:26
impeller
Definition: aiks_context.cc:10
impeller::IndexType::kUnknown
@ kUnknown