Quellcode durchsuchen

meta: further refine typed allow_cast

skypjack vor 4 Monaten
Ursprung
Commit
7eeb828980
2 geänderte Dateien mit 12 neuen und 2 gelöschten Zeilen
  1. 1 1
      TODO
  2. 11 1
      src/entt/meta/meta.hpp

+ 1 - 1
TODO

@@ -34,6 +34,6 @@ TODO:
 * finish the imgui viewer/editor!
 * introduce compile-time flag to skip dll-only checks in basic_any
 * archetype-like a-là EnTT support (see my own notes)
-* meta_any typed try_cast/allow_cast should not rely on non-typed ones for perf reasons
+* meta_any refine allow_cast implementations
 * meta: conversion_helper machinery has lot of room for improvements
 * meta_factory: add a replace flag to traits to get around the |-only mechanism

+ 11 - 1
src/entt/meta/meta.hpp

@@ -520,7 +520,17 @@ public:
         if constexpr(std::is_reference_v<Type> && !std::is_const_v<std::remove_reference_t<Type>>) {
             return allow_cast<const std::remove_reference_t<Type> &>() && (storage.data() != nullptr);
         } else {
-            return storage.has_value<std::remove_const_t<std::remove_reference_t<Type>>>() || allow_cast(meta_type{*ctx, internal::resolve<std::remove_const_t<std::remove_reference_t<Type>>>(internal::meta_context::from(*ctx))});
+            if(storage.has_value<std::remove_const_t<std::remove_reference_t<Type>>>()) {
+                return true;
+            } else if(auto other = std::as_const(*this).allow_cast<std::remove_const_t<std::remove_reference_t<Type>>>(); other) {
+                if(other.storage.owner()) {
+                    std::swap(*this, other);
+                }
+
+                return true;
+            }
+
+            return false;
         }
     }