Entity Generator 1.1.0
Composable, deterministic entity generation for C++23
Loading...
Searching...
No Matches
flecs_adapter.hpp
Go to the documentation of this file.
1#ifndef DASMIG_EXT_FLECS_ADAPTER_HPP
2#define DASMIG_EXT_FLECS_ADAPTER_HPP
3
4#include "../entitygen.hpp"
5#include <flecs.h>
6#include <functional>
7#include <string>
8#include <vector>
9
10namespace dasmig::ext
11{
12
13/// @file flecs_adapter.hpp
14/// @brief Adapter bridging entity-generator with Flecs.
15
16/// @brief Adapter that bridges entity-generator with Flecs.
17///
18/// Users register mappings from generator component keys to Flecs component
19/// types, then spawn() converts generated entities into Flecs entities with
20/// typed components.
21///
22/// @par Example
23/// @code
24/// flecs::world world;
25/// dasmig::ext::flecs_adapter adapter(world);
26/// adapter.map<Position>(L"pos", [](const dasmig::entity& e) {
27/// return Position{ e.get<float>(L"x"), e.get<float>(L"y") };
28/// });
29/// auto flecs_entity = adapter.spawn(gen.generate());
30/// @endcode
31/// @see entt_adapter
33{
34 public:
35 /// @brief Construct an adapter bound to a Flecs world.
36 /// @param world The Flecs world to create entities in.
37 explicit flecs_adapter(flecs::world& world)
38 : _world{world} {}
39
40 /// @brief Register a transform mapping from a generator key to a Flecs component.
41 ///
42 /// The mapper receives the full generated entity so it can read any
43 /// combination of keys. The component is only set when the specified
44 /// key is present in the generated entity.
45 /// @tparam Component The Flecs component type.
46 /// @param key Generator component key to watch for.
47 /// @param mapper Transform function producing the Flecs component.
48 /// @return `*this` for chaining.
49 template <typename Component>
50 flecs_adapter& map(const std::wstring& key,
51 std::function<Component(const entity&)> mapper)
52 {
53 _mappings.push_back({key,
54 [mapper = std::move(mapper)](flecs::entity target,
55 const entity& src) {
56 target.set<Component>(mapper(src));
57 }});
58 return *this;
59 }
60
61 /// @brief Register a direct mapping (value type matches Flecs component type).
62 /// @tparam Component The Flecs component type.
63 /// @param key Generator component key whose value type is @p Component.
64 /// @return `*this` for chaining.
65 template <typename Component>
66 flecs_adapter& map(const std::wstring& key)
67 {
68 _mappings.push_back({key,
69 [key](flecs::entity target, const entity& src) {
70 target.set<Component>(src.get<Component>(key));
71 }});
72 return *this;
73 }
74
75 /// @brief Create a Flecs entity from a generated entity.
76 ///
77 /// Sets all mapped components whose keys are present.
78 /// @param src The generated entity.
79 /// @return The new Flecs entity.
80 [[nodiscard]] flecs::entity spawn(const entity& src)
81 {
82 auto target = _world.entity();
83 apply(target, src);
84 return target;
85 }
86
87 /// @brief Set mapped components onto an existing Flecs entity.
88 /// @param target The pre-existing Flecs entity.
89 /// @param src The generated entity.
90 void spawn_into(flecs::entity target, const entity& src)
91 {
92 apply(target, src);
93 }
94
95 /// @brief Create Flecs entities for a batch of generated entities.
96 /// @param sources A vector of generated entities.
97 /// @return A vector of new Flecs entities.
98 [[nodiscard]] std::vector<flecs::entity> spawn_batch(
99 const std::vector<entity>& sources)
100 {
101 std::vector<flecs::entity> result;
102 result.reserve(sources.size());
103 for (const auto& src : sources)
104 {
105 result.push_back(spawn(src));
106 }
107 return result;
108 }
109
110 /// @brief Remove all registered mappings.
111 /// @return `*this` for chaining.
113 {
114 _mappings.clear();
115 return *this;
116 }
117
118 private:
119 using set_fn = std::function<void(flecs::entity, const entity&)>;
120
121 struct mapping
122 {
123 std::wstring key;
124 set_fn apply_component;
125 };
126
127 void apply(flecs::entity target, const entity& src)
128 {
129 for (const auto& m : _mappings)
130 {
131 if (src.has(m.key))
132 {
133 m.apply_component(target, src);
134 }
135 }
136 }
137
138 flecs::world& _world;
139 std::vector<mapping> _mappings;
140};
141
142} // namespace dasmig::ext
143
144#endif // DASMIG_EXT_FLECS_ADAPTER_HPP
A generated entity holding component values in registration order.
bool has(const std::wstring &component_key) const
Check if a component value exists by key.
Adapter that bridges entity-generator with Flecs.
std::vector< flecs::entity > spawn_batch(const std::vector< entity > &sources)
Create Flecs entities for a batch of generated entities.
void spawn_into(flecs::entity target, const entity &src)
Set mapped components onto an existing Flecs entity.
flecs::entity spawn(const entity &src)
Create a Flecs entity from a generated entity.
flecs_adapter(flecs::world &world)
Construct an adapter bound to a Flecs world.
flecs_adapter & clear_mappings()
Remove all registered mappings.
flecs_adapter & map(const std::wstring &key, std::function< Component(const entity &)> mapper)
Register a transform mapping from a generator key to a Flecs component.
flecs_adapter & map(const std::wstring &key)
Register a direct mapping (value type matches Flecs component type).