summaryrefslogtreecommitdiff
path: root/src/GFX/Util
diff options
context:
space:
mode:
Diffstat (limited to 'src/GFX/Util')
-rw-r--r--src/GFX/Util/MeshBuilder.hpp65
1 files changed, 65 insertions, 0 deletions
diff --git a/src/GFX/Util/MeshBuilder.hpp b/src/GFX/Util/MeshBuilder.hpp
new file mode 100644
index 0000000..e3caa8c
--- /dev/null
+++ b/src/GFX/Util/MeshBuilder.hpp
@@ -0,0 +1,65 @@
+#pragma once
+
+#include "../../Common/Sizes.hpp"
+#include "../../Math/Common.hpp"
+#include <vector>
+
+namespace MC::GFX::Util {
+
+template <typename... Attributes>
+class MeshBuilder {
+ using AttributeTuple = std::tuple<std::vector<Attributes>...>;
+
+ template <int N, typename AttributeContainer>
+ using EnableIfCorrectAttributeIndex =
+ std::enable_if_t<std::is_same_v<
+ typename std::tuple_element_t<N, AttributeTuple>::value_type,
+ typename AttributeContainer::value_type>, Bool>;
+
+ template <int N, typename A>
+ std::vector<A>& get() {
+ return std::get<N>(m_attributes);
+ }
+
+ template <USize... Sequence>
+ Mesh mesh(std::index_sequence<Sequence...>) {
+ return {
+ {m_positions, std::get<Sequence>(m_attributes)...},
+ m_indices,
+ };
+ }
+
+ std::vector<Vector<3, F32>> m_positions{};
+ std::vector<U32> m_indices{};
+ AttributeTuple m_attributes;
+public:
+ static constexpr UInt AttributesN = sizeof...(Attributes);
+
+ MeshBuilder() = default;
+
+ template<int N, typename AC, EnableIfCorrectAttributeIndex<N, AC> = true>
+ void attributes(const AC& from) {
+ auto& attribute_list = get<N, typename AC::value_type>();
+ attribute_list.insert(attribute_list.end(), from.begin(), from.end());
+ }
+
+ template<typename AC>
+ void positions(const AC& from) {
+ m_positions.insert(m_positions.end(), from.begin(), from.end());
+ }
+
+ template<typename AC>
+ void indices(const AC& from) {
+ m_indices.insert(m_indices.end(), from.begin(), from.end());
+ }
+
+ Mesh mesh() {
+ return mesh(std::make_index_sequence<AttributesN>{});
+ }
+
+ USize vertex_count() const {
+ return m_positions.size();
+ }
+};
+
+}