diff --git a/src/entt/meta/meta.hpp b/src/entt/meta/meta.hpp index 8421a84ef..a0dfa298b 100644 --- a/src/entt/meta/meta.hpp +++ b/src/entt/meta/meta.hpp @@ -172,38 +172,54 @@ class meta_any { } break; case operation::REF: + static_cast(to)->emplace(any_cast(const_cast(from))); + break; case operation::CREF: - *static_cast(to) = (op == operation::REF ? meta_any{std::ref(any_cast(const_cast(from)))} : meta_any{std::cref(any_cast &>(from))}); + static_cast(to)->emplace &>(any_cast &>(from)); break; case operation::DEREF: + if constexpr(is_meta_pointer_like_v>>) { + using element_type = std::remove_const_t>::element_type>; + + if constexpr(std::is_function_v) { + *static_cast(to) = any_cast>(from); + } else if constexpr(!std::is_same_v>::element_type>, void>) { + using in_place_type = decltype(adl_meta_pointer_like>::dereference(any_cast &>(from))); + static_cast(to)->emplace(adl_meta_pointer_like>::dereference(any_cast &>(from))); + } + } + break; case operation::CDEREF: if constexpr(is_meta_pointer_like_v>>) { using element_type = std::remove_const_t>::element_type>; if constexpr(std::is_function_v) { *static_cast(to) = any_cast>(from); - } else if constexpr(!std::is_same_v) { - using adl_meta_pointer_like_type = adl_meta_pointer_like>; - - if constexpr(std::is_lvalue_reference_v &>()))>) { - auto &&obj = adl_meta_pointer_like_type::dereference(any_cast &>(from)); - *static_cast(to) = (op == operation::DEREF ? meta_any{std::ref(obj)} : meta_any{std::cref(obj)}); - } else { - *static_cast(to) = adl_meta_pointer_like_type::dereference(any_cast &>(from)); - } + } else if constexpr(!std::is_same_v>::element_type>, void>) { + using deref_type = decltype(adl_meta_pointer_like>::dereference(any_cast &>(from))); + using in_place_type = std::conditional_t, const std::remove_reference_t &, deref_type>; + static_cast(to)->emplace(adl_meta_pointer_like>::dereference(any_cast &>(from))); } } break; case operation::SEQ: + if constexpr(is_complete_v>>) { + *static_cast(to) = { std::in_place_type>, const_cast(from).as_ref() }; + } + break; case operation::CSEQ: if constexpr(is_complete_v>>) { - *static_cast(to) = { std::in_place_type>, (op == operation::SEQ ? const_cast(from).as_ref() : from.as_ref()) }; + *static_cast(to) = { std::in_place_type>, from.as_ref() }; } break; case operation::ASSOC: + if constexpr(is_complete_v>>) { + *static_cast(to) = { std::in_place_type>, const_cast(from).as_ref() }; + } + break; case operation::CASSOC: if constexpr(is_complete_v>>) { - *static_cast(to) = { std::in_place_type>, (op == operation::ASSOC ? const_cast(from).as_ref() : from.as_ref()) }; + *static_cast(to) = { std::in_place_type>, from.as_ref() }; } break; } @@ -1958,10 +1974,12 @@ class meta_associative_container::meta_iterator { ++any_cast(const_cast(from)); break; case operation::DEREF: + const auto &it = any_cast(from); if constexpr(KeyOnly) { - static_cast *>(to)->first = std::cref(*any_cast(from)); + static_cast *>(to)->first.emplace(*it); } else { - *static_cast *>(to) = std::make_pair(std::cref(any_cast(from)->first), std::ref(any_cast(from)->second)); + static_cast *>(to)->first.emplacefirst))>(it->first); + static_cast *>(to)->second.emplacesecond))>(it->second); } break; } diff --git a/src/entt/meta/utility.hpp b/src/entt/meta/utility.hpp index 5497b108c..066e7db40 100644 --- a/src/entt/meta/utility.hpp +++ b/src/entt/meta/utility.hpp @@ -209,9 +209,10 @@ template if constexpr(std::is_same_v) { return meta_any{std::in_place_type, std::forward(value)}; } else if constexpr(std::is_same_v) { - return meta_any{std::reference_wrapper{std::forward(value)}}; + return meta_any{std::in_place_type, std::forward(value)}; } else if constexpr(std::is_same_v) { - return meta_any{std::cref(std::forward(value))}; + const auto &cvalue = std::as_const(value); + return meta_any{std::in_place_type, cvalue}; } else { static_assert(std::is_same_v, "Policy not supported"); return meta_any{std::forward(value)}; @@ -263,9 +264,11 @@ template(params)...); return meta_any{std::in_place_type}; } else if constexpr(std::is_same_v) { - return meta_any{std::reference_wrapper{std::invoke(Candidate, std::forward(params)...)}}; + auto &value = std::invoke(Candidate, std::forward(params)...); + return meta_any{std::in_place_type, value}; } else if constexpr(std::is_same_v) { - return meta_any{std::cref(std::invoke(Candidate, std::forward(params)...))}; + const auto &cvalue = std::invoke(Candidate, std::forward(params)...); + return meta_any{std::in_place_type, cvalue}; } else { static_assert(std::is_same_v, "Policy not supported"); return meta_any{std::invoke(Candidate, std::forward(params)...)};