2#include <monopp/mono_property.h>
3#include <monopp/mono_property_invoker.h>
20struct managed_contact_point
55 safe_foreach(script_components_,
58 auto& obj =
script.scoped->object;
67 safe_foreach(script_components_,
70 auto& obj =
script.scoped->object;
77 safe_foreach(script_components_,
80 auto& obj =
script.scoped->object;
87 safe_foreach(script_components_,
90 auto& obj =
script.scoped->object;
97 safe_foreach(script_components_,
100 auto& obj =
script.scoped->object;
107 safe_foreach(script_components_,
110 auto& obj =
script.scoped->object;
117 safe_foreach(script_components_,
120 auto& obj =
script.scoped->object;
127 if(script_obj.is_enabled() || script_obj.is_marked_for_destroy())
132 script_obj.state->active =
true;
136 if(!script_obj.is_create_called())
142 auto& obj = script_obj.scoped->object;
144 obj.get_type().get_method(
"OnCollisionEnter", 1);
148 auto method = mono::make_method_invoker<void()>(obj,
"internal_n2m_on_enable");
151 catch(
const mono::mono_exception& e)
159 if(script_obj.is_disabled() || script_obj.is_marked_for_destroy())
164 script_obj.state->active = 0;
168 if(!script_obj.is_create_called())
173 auto& obj = script_obj.scoped->object;
177 auto method = mono::make_method_invoker<void()>(obj,
"internal_n2m_on_disable");
180 catch(
const mono::mono_exception& e)
188 if(script_obj.is_create_called())
193 script_obj.state->create_called =
true;
194 auto& obj = script_obj.scoped->object;
198 auto method = mono::make_method_invoker<void()>(obj,
"internal_n2m_on_create");
201 catch(
const mono::mono_exception& e)
208 if(script_obj.is_start_called())
212 script_obj.state->start_called =
true;
213 auto& obj = script_obj.scoped->object;
217 auto method = mono::make_method_invoker<void()>(obj,
"internal_n2m_on_start");
220 catch(
const mono::mono_exception& e)
228 auto& obj = script_obj.scoped->object;
231 auto method = mono::make_method_invoker<void()>(obj,
"internal_n2m_on_destroy");
234 catch(
const mono::mono_exception& e)
240void script_component::set_entity(
const mono::mono_object& obj, entt::handle e)
244 auto method = mono::make_method_invoker<void(entt::entity)>(obj,
"internal_n2m_set_entity");
245 method(obj,
e.entity());
247 catch(
const mono::mono_exception& e)
257 auto method = mono::make_method_invoker<void(entt::entity)>(obj,
"internal_n2m_on_sensor_enter");
258 method(obj, other.entity());
260 catch(
const mono::mono_exception& e)
270 auto method = mono::make_method_invoker<void(entt::entity)>(obj,
"internal_n2m_on_sensor_exit");
271 method(obj, other.entity());
273 catch(
const mono::mono_exception& e)
281 const std::vector<manifold_point>& manifolds,
284 std::vector<managed_contact_point> points;
285 points.reserve(manifolds.size());
286 for(
const auto& manifold : manifolds)
288 auto&
point = points.emplace_back();
291 point.
point = {manifold.b.x, manifold.b.y, manifold.b.z};
292 point.normal = {manifold.normal_on_b.x, manifold.normal_on_b.y, manifold.normal_on_b.z};
296 point.
point = {manifold.a.x, manifold.a.y, manifold.a.z};
297 point.normal = {manifold.normal_on_a.x, manifold.normal_on_a.y, manifold.normal_on_a.z};
299 point.distance = manifold.distance;
300 point.impulse = manifold.impulse;
305 auto method = mono::make_method_invoker<void(entt::entity,
const std::vector<managed_contact_point>&)>(
307 "internal_n2m_on_collision_enter");
308 method(obj,
b.entity(), points);
310 catch(
const mono::mono_exception& e)
318 const std::vector<manifold_point>& manifolds,
321 std::vector<managed_contact_point> points;
322 points.reserve(manifolds.size());
323 for(
const auto& manifold : manifolds)
325 auto&
point = points.emplace_back();
328 point.
point = {manifold.b.x, manifold.b.y, manifold.b.z};
329 point.normal = {manifold.normal_on_b.x, manifold.normal_on_b.y, manifold.normal_on_b.z};
333 point.
point = {manifold.a.x, manifold.a.y, manifold.a.z};
334 point.normal = {manifold.normal_on_a.x, manifold.normal_on_a.y, manifold.normal_on_a.z};
336 point.distance = manifold.distance;
337 point.impulse = manifold.impulse;
342 auto method = mono::make_method_invoker<void(entt::entity,
const std::vector<managed_contact_point>&)>(
344 "internal_n2m_on_collision_exit");
345 method(obj,
b.entity(), points);
347 catch(
const mono::mono_exception& e)
356 auto& ev = ctx.get_cached<
events>();
358 size_t erased = std::erase_if(script_components_,
361 bool marked = rhs.is_marked_for_destroy();
362 if(marked && ev.is_playing)
370 erased += std::erase_if(native_components_,
373 return rhs.is_marked_for_destroy();
379 while(!script_components_to_create_.empty())
381 auto comps = std::move(script_components_to_create_);
382 script_components_to_create_.clear();
386 if(!
script.is_marked_for_destroy())
396 while(!script_components_to_start_.empty())
398 auto comps = std::move(script_components_to_start_);
399 script_components_to_start_.clear();
403 if(!
script.is_marked_for_destroy())
420 auto& ev = ctx.get_cached<
events>();
426 if(
get_owner().all_of<active_component>())
428 enable(script_obj,
false);
440 auto obj =
type.new_instance();
441 return add_script_component(obj);
447 return add_script_component(script_obj);
452 script_components_.emplace_back(script_obj);
453 script_components_to_create_.emplace_back(script_obj);
454 script_components_to_start_.emplace_back(script_obj);
456 auto& obj = script_obj.scoped->object;
458 set_entity(obj, get_owner());
460 if(process_callbacks)
462 process_pending_actions(script_obj);
470 for(
auto& comp : comps)
481 for(
auto& comp : comps)
485 auto& obj = comp.scoped->object;
486 const auto&
type = obj.get_type();
499 auto obj =
type.new_instance();
500 auto& script_obj = native_components_.emplace_back(obj);
502 set_entity(obj, get_owner());
509 std::vector<mono::mono_object> result;
510 for(
const auto& component : script_components_)
512 const auto& comp_type = component.scoped->object.get_type();
514 if(comp_type.get_internal_ptr() ==
type.get_internal_ptr() || comp_type.is_derived_from(
type))
516 result.emplace_back(
static_cast<mono::mono_object&
>(component.scoped->object));
525 auto it = std::find_if(std::begin(script_components_),
526 std::end(script_components_),
527 [&](
const auto& component)
529 const auto& comp_type = component.scoped->object.get_type();
530 return comp_type.get_internal_ptr() ==
type.get_internal_ptr() ||
531 comp_type.is_derived_from(
type);
534 if(it != std::end(script_components_))
544 auto it = std::find_if(std::begin(native_components_),
545 std::end(native_components_),
546 [&](
const auto& component)
548 const auto& comp_type = component.scoped->object.get_type();
549 return comp_type.get_internal_ptr() ==
type.get_internal_ptr() ||
550 comp_type.is_derived_from(
type);
553 if(it != std::end(native_components_))
563 auto checker = [&](
const auto& rhs)
565 return rhs.scoped->object.get_internal_ptr() == obj.get_internal_ptr();
567 std::erase_if(script_components_to_create_, checker);
569 std::erase_if(script_components_to_start_, checker);
571 auto it = std::find_if(std::begin(script_components_), std::end(script_components_), checker);
573 if(it != std::end(script_components_))
575 auto& script_obj = *it;
579 script_obj.state->marked_for_destroy =
true;
588 auto checker = [&](
const auto& rhs)
590 return rhs.scoped->object.get_type().get_internal_ptr() ==
type.get_internal_ptr();
592 std::erase_if(script_components_to_create_, checker);
594 std::erase_if(script_components_to_start_, checker);
596 auto it = std::find_if(std::begin(script_components_), std::end(script_components_), checker);
598 if(it != std::end(script_components_))
600 auto& script_obj = *it;
601 auto& obj = script_obj.scoped->object;
604 script_obj.state->marked_for_destroy =
true;
613 auto it = std::find_if(std::begin(native_components_),
614 std::end(native_components_),
617 return rhs.scoped->object.get_internal_ptr() == obj.get_internal_ptr();
620 if(it != std::end(native_components_))
622 auto& script_obj = *it;
626 script_obj.state->marked_for_destroy =
true;
635 auto it = std::find_if(std::begin(native_components_),
636 std::end(native_components_),
639 return rhs.scoped->object.get_type().get_internal_ptr() ==
type.get_internal_ptr();
642 if(it != std::end(native_components_))
644 auto& script_obj = *it;
646 auto& obj = script_obj.scoped->object;
649 script_obj.state->marked_for_destroy =
true;
658 return script_components_;
663 return !script_components_.empty();
668 return std::any_of(std::begin(script_components_), std::end(script_components_), [&](
const auto& component)
670 return component.scoped->object.get_type().get_name() == type_name;
681 const auto&
object = obj.scoped->object;
682 const auto&
type =
object.get_type();
685 auto attrs =
type.get_attributes();
686 for(
auto& attr : attrs)
688 if(attr.get_type().get_fullname() ==
"Unravel.Core.ScriptSourceFileAttribute")
690 auto invoker = mono::make_property_invoker<std::string>(attr.get_type(),
"Path");
691 return invoker.get_value(attr);
694 auto prop =
type.get_property(
"SourceFilePath");
695 auto invoker = mono::make_property_invoker<std::string>(prop);
696 return invoker.get_value(
object);
698 catch(
const mono::mono_exception& e)
auto get_owner() const noexcept -> entt::const_handle
Gets the owner of the component.
void set_owner(entt::handle owner)
Sets the owner of the component.
Class that contains core data for audio listeners. There can only be one instance of it per scene.
auto get_script_source_location(const script_object &obj) const -> std::string
void on_collision_enter(entt::handle other, const std::vector< manifold_point > &manifolds, bool use_b)
auto add_native_component(const mono::mono_type &type) -> script_object
void add_missing_script_components(const script_components_t &comps)
auto remove_script_component(const mono::mono_object &obj) -> bool
void on_collision_exit(entt::handle other, const std::vector< manifold_point > &manifolds, bool use_b)
auto get_script_component(const mono::mono_type &type) -> script_object
auto get_native_component(const mono::mono_type &type) -> script_object
void process_pending_actions_create(script_object script_obj)
void add_script_components(const script_components_t &comps)
void on_sensor_enter(entt::handle other)
static void on_destroy_component(entt::registry &r, entt::entity e)
Called when the component is destroyed.
auto get_script_components() const -> const script_components_t &
void process_pending_actions()
void on_sensor_exit(entt::handle other)
auto add_script_component(const mono::mono_type &type) -> script_object
void process_pending_starts()
auto remove_native_component(const mono::mono_object &obj) -> bool
std::vector< script_object > script_components_t
auto has_script_components() const -> bool
static void on_create_component(entt::registry &r, entt::entity e)
Called when the component is created.
void process_pending_deletions()
void process_pending_creates()
static auto context() -> rtti::context &
auto is_create_called() const -> bool
static void log_exception(const mono::mono_exception &e, const hpp::source_location &loc=hpp::source_location::current())