1 #ifndef ENTT_ENTITY_OBSERVER_HPP
2 #define ENTT_ENTITY_OBSERVER_HPP
10 #include "../config/config.h"
11 #include "../core/type_traits.hpp"
12 #include "registry.hpp"
13 #include "storage.hpp"
14 #include "utility.hpp"
53 template<
typename... AllOf,
typename... NoneOf>
63 template<
typename AnyOf>
64 static constexpr
auto update() ENTT_NOEXCEPT {
77 template<
typename... Reject,
typename... Require,
typename... Rule,
typename... Other>
88 template<
typename... AllOf,
typename... NoneOf>
98 template<
typename AnyOf>
99 static constexpr
auto update() ENTT_NOEXCEPT {
109 template<
typename... AllOf,
typename... NoneOf>
170 template<
typename Entity>
172 using payload_type = std::uint32_t;
175 struct matcher_handler;
177 template<
typename... Reject,
typename... Require,
typename AnyOf>
179 template<std::
size_t Index>
181 if(reg.template has<Require...>(
entt) && !reg.template any<Reject...>(
entt)) {
186 obs.view.
get(
entt) |= (1 << Index);
190 template<std::
size_t Index>
192 if(
auto *value = obs.view.
try_get(
entt); value && !(*value &= (~(1 << Index)))) {
197 template<std::
size_t Index>
199 (reg.template on_destroy<Require>().template connect<&discard_if<Index>>(obs), ...);
200 (reg.template on_construct<Reject>().template connect<&discard_if<Index>>(obs), ...);
201 reg.template on_update<AnyOf>().template connect<&maybe_valid_if<Index>>(obs);
202 reg.template on_destroy<AnyOf>().template connect<&discard_if<Index>>(obs);
206 (reg.template on_destroy<Require>().disconnect(obs), ...);
207 (reg.template on_construct<Reject>().disconnect(obs), ...);
208 reg.template on_update<AnyOf>().disconnect(obs);
209 reg.template on_destroy<AnyOf>().disconnect(obs);
213 template<
typename... Reject,
typename... Require,
typename... NoneOf,
typename... AllOf>
215 template<std::size_t Index,
typename... Ignore>
218 if constexpr(
sizeof...(Ignore) == 0) {
219 return reg.template has<AllOf..., Require...>(
entt) && !reg.template any<NoneOf..., Reject...>(
entt);
221 return reg.template has<AllOf..., Require...>(
entt) && ((std::is_same_v<Ignore..., NoneOf> || !reg.template any<NoneOf>(
entt)) && ...) && !reg.template any<Reject...>(
entt);
229 obs.view.
get(
entt) |= (1 << Index);
233 template<std::
size_t Index>
235 if(
auto *value = obs.view.
try_get(
entt); value && !(*value &= (~(1 << Index)))) {
240 template<std::
size_t Index>
242 (reg.template on_destroy<Require>().template connect<&discard_if<Index>>(obs), ...);
243 (reg.template on_construct<Reject>().template connect<&discard_if<Index>>(obs), ...);
244 (reg.template on_construct<AllOf>().template connect<&maybe_valid_if<Index>>(obs), ...);
245 (reg.template on_destroy<NoneOf>().template connect<&maybe_valid_if<Index, NoneOf>>(obs), ...);
246 (reg.template on_destroy<AllOf>().template connect<&discard_if<Index>>(obs), ...);
247 (reg.template on_construct<NoneOf>().template connect<&discard_if<Index>>(obs), ...);
251 (reg.template on_destroy<Require>().disconnect(obs), ...);
252 (reg.template on_construct<Reject>().disconnect(obs), ...);
253 (reg.template on_construct<AllOf>().disconnect(obs), ...);
254 (reg.template on_destroy<NoneOf>().disconnect(obs), ...);
255 (reg.template on_destroy<AllOf>().disconnect(obs), ...);
256 (reg.template on_construct<NoneOf>().disconnect(obs), ...);
260 template<
typename... Matcher>
262 (matcher_handler<Matcher>::disconnect(obs, reg), ...);
265 template<
typename... Matcher, std::size_t... Index>
267 static_assert(
sizeof...(Matcher) < std::numeric_limits<payload_type>::digits,
"Too many matchers");
268 (matcher_handler<Matcher>::template connect<Index>(*
this, reg), ...);
282 : target{}, release{}, view{}
295 template<
typename... Matcher>
301 connect<Matcher...>(reg, std::index_sequence_for<Matcher...>{});
324 template<
typename... Matcher>
327 connect<Matcher...>(reg, std::index_sequence_for<Matcher...>{});
335 release(*
this, *target);
352 [[nodiscard]]
bool empty() const ENTT_NOEXCEPT {
381 return view.sparse_set<entity_type>::begin();
395 return view.sparse_set<entity_type>::end();
416 template<
typename Func>
418 for(
const auto entity: *
this) {
432 template<
typename Func>
434 std::as_const(*this).each(std::move(func));