Flecs v3.2
A fast entity component system (ECS) for C & C++
Loading...
Searching...
No Matches
builder_i.hpp
Go to the documentation of this file.
1
6#pragma once
7
8#include "../term/builder_i.hpp"
9
10namespace flecs
11{
12
17template<typename Base, typename ... Components>
19 filter_builder_i(ecs_filter_desc_t *desc, int32_t term_index = 0)
20 : m_term_index(term_index)
21 , m_expr_count(0)
22 , m_desc(desc) { }
23
24 Base& instanced() {
25 m_desc->instanced = true;
26 return *this;
27 }
28
29 Base& filter_flags(ecs_flags32_t flags) {
30 m_desc->flags |= flags;
31 return *this;
32 }
33
34 Base& expr(const char *expr) {
35 ecs_check(m_expr_count == 0, ECS_INVALID_OPERATION,
36 "filter_builder::expr() called more than once");
37 m_desc->expr = expr;
38 m_expr_count ++;
39
40 error:
41 return *this;
42 }
43
44 /* With/without shorthand notation. */
45
46 template <typename ... Args>
47 Base& with(Args&&... args) {
48 return this->term(FLECS_FWD(args)...);
49 }
50
51 template <typename T, typename ... Args>
52 Base& with(Args&&... args) {
53 return this->term<T>(FLECS_FWD(args)...);
54 }
55
56 template <typename First, typename Second>
57 Base& with() {
58 return this->term<First, Second>();
59 }
60
61 template <typename ... Args>
62 Base& without(Args&&... args) {
63 return this->term(FLECS_FWD(args)...).not_();
64 }
65
66 template <typename T, typename ... Args>
67 Base& without(Args&&... args) {
68 return this->term<T>(FLECS_FWD(args)...).not_();
69 }
70
71 template <typename First, typename Second>
72 Base& without() {
73 return this->term<First, Second>().not_();
74 }
75
76 /* Write/read shorthand notation */
77
78 Base& write() {
80 return *this;
81 }
82
83 template <typename ... Args>
84 Base& write(Args&&... args) {
85 return this->term(FLECS_FWD(args)...).write();
86 }
87
88 template <typename T, typename ... Args>
89 Base& write(Args&&... args) {
90 return this->term<T>(FLECS_FWD(args)...).write();
91 }
92
93 template <typename First, typename Second>
94 Base& write() {
95 return this->term<First, Second>().write();
96 }
97
98 Base& read() {
100 return *this;
101 }
102
103 template <typename ... Args>
104 Base& read(Args&&... args) {
105 return this->term(FLECS_FWD(args)...).read();
106 }
107
108 template <typename T, typename ... Args>
109 Base& read(Args&&... args) {
110 return this->term<T>(FLECS_FWD(args)...).read();
111 }
112
113 template <typename First, typename Second>
114 Base& read() {
115 return this->term<First, Second>().read();
116 }
117
118 /* Term notation for more complex query features */
119
120 Base& term() {
121 if (this->m_term) {
122 ecs_check(ecs_term_is_initialized(this->m_term),
123 ECS_INVALID_OPERATION,
124 "filter_builder::term() called without initializing term");
125 }
126
127 if (m_term_index >= FLECS_TERM_DESC_MAX) {
128 if (m_term_index == FLECS_TERM_DESC_MAX) {
129 m_desc->terms_buffer = ecs_os_calloc_n(
130 ecs_term_t, m_term_index + 1);
131 ecs_os_memcpy_n(m_desc->terms_buffer, m_desc->terms,
132 ecs_term_t, m_term_index);
133 ecs_os_memset_n(m_desc->terms, 0,
135 } else {
136 m_desc->terms_buffer = ecs_os_realloc_n(m_desc->terms_buffer,
137 ecs_term_t, m_term_index + 1);
138 }
139
140 m_desc->terms_buffer_count = m_term_index + 1;
141
142 this->set_term(&m_desc->terms_buffer[m_term_index]);
143 } else {
144 this->set_term(&m_desc->terms[m_term_index]);
145 }
146
147 m_term_index ++;
148
149 error:
150 return *this;
151 }
152
153 Base& term_at(int32_t term_index) {
154 ecs_assert(term_index > 0, ECS_INVALID_PARAMETER, NULL);
155 int32_t prev_index = m_term_index;
156 m_term_index = term_index - 1;
157 this->term();
158 m_term_index = prev_index;
159 ecs_assert(ecs_term_is_initialized(this->m_term),
160 ECS_INVALID_PARAMETER, NULL);
161 return *this;
162 }
163
164 Base& arg(int32_t term_index) {
165 return this->term_at(term_index);
166 }
167
168 template<typename T>
169 Base& term() {
170 this->term();
171 *this->m_term = flecs::term(_::cpp_type<T>::id(this->world_v())).move();
172 this->m_term->inout = static_cast<ecs_inout_kind_t>(
173 _::type_to_inout<T>());
174 return *this;
175 }
176
177 Base& term(id_t id) {
178 this->term();
179 *this->m_term = flecs::term(id).move();
180 return *this;
181 }
182
183 Base& term(const char *name) {
184 this->term();
185 *this->m_term = flecs::term().first(name).move();
186 return *this;
187 }
188
189 Base& term(const char *first, const char *second) {
190 this->term();
191 *this->m_term = flecs::term().first(first).second(second).move();
192 return *this;
193 }
194
195 Base& term(entity_t r, entity_t o) {
196 this->term();
197 *this->m_term = flecs::term(r, o).move();
198 return *this;
199 }
200
201 Base& term(entity_t r, const char *o) {
202 this->term();
203 *this->m_term = flecs::term(r).second(o).move();
204 return *this;
205 }
206
207 template<typename First>
208 Base& term(id_t o) {
209 return this->term(_::cpp_type<First>::id(this->world_v()), o);
210 }
211
212 template<typename First>
213 Base& term(const char *second) {
214 return this->term(_::cpp_type<First>::id(this->world_v())).second(second);
215 }
216
217 template<typename First, typename Second>
218 Base& term() {
219 return this->term<First>(_::cpp_type<Second>::id(this->world_v()));
220 }
221
222 template <typename E, if_t< is_enum<E>::value > = 0>
223 Base& term(E value) {
224 flecs::entity_t r = _::cpp_type<E>::id(this->world_v());
225 auto o = enum_type<E>(this->world_v()).entity(value);
226 return this->term(r, o);
227 }
228
229 Base& term(flecs::term& term) {
230 this->term();
231 *this->m_term = term.move();
232 return *this;
233 }
234
235 Base& term(flecs::term&& term) {
236 this->term();
237 *this->m_term = term.move();
238 return *this;
239 }
240
241protected:
242 virtual flecs::world_t* world_v() = 0;
243 int32_t m_term_index;
244 int32_t m_expr_count;
245
246private:
247 operator Base&() {
248 return *static_cast<Base*>(this);
249 }
250
251 ecs_filter_desc_t *m_desc;
252};
253
254}
#define ecs_assert(condition, error_code,...)
Assert.
Definition log.h:352
#define ecs_check(condition, error_code,...)
Check.
Definition log.h:388
bool ecs_term_is_initialized(const ecs_term_t *term)
Test whether a term is set.
#define FLECS_TERM_DESC_MAX
Maximum number of terms in ecs_filter_desc_t.
Definition flecs.h:235
ecs_inout_kind_t
Specify read/write access for term.
Definition flecs.h:532
Used with ecs_filter_init.
Definition flecs.h:840
ecs_term_t * terms_buffer
For filters with lots of terms an outside array can be provided.
Definition flecs.h:848
bool instanced
When true, terms returned by an iterator may either contain 1 or N elements, where terms with N eleme...
Definition flecs.h:861
ecs_term_t terms[(16)]
Terms of the filter.
Definition flecs.h:845
int32_t terms_buffer_count
Number of terms in array provided in terms_buffer.
Definition flecs.h:851
ecs_flags32_t flags
Flags for advanced usage.
Definition flecs.h:864
const char * expr
Filter expression.
Definition flecs.h:867
Type that describes a term (single element in a query)
Definition flecs.h:596
ecs_inout_kind_t inout
Access to contents matched by term.
Definition flecs.h:606
Filter builder interface.
Definition builder_i.hpp:18
Term builder interface.
Base & read()
Short for inout_stage(flecs::In).
Base & write()
Short for inout_stage(flecs::Out).
Class that describes a term.
Definition impl.hpp:16