summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorsheepandshepherd <sheepandshepherd@hotmail.com>2019-10-21 18:08:03 +0200
committersheepandshepherd <sheepandshepherd@hotmail.com>2020-08-17 00:05:57 +0200
commit33f9de16e414ad091fb6d4a6326f5cc435016ef9 (patch)
tree2c5ef19206f913d1ac7ed670f41a07b8fc0e4748
parenta3fe496ad62ab735af3b55750aade43e87600289 (diff)
downloadredot-cpp-33f9de16e414ad091fb6d4a6326f5cc435016ef9.tar.gz
Use godot_object_cast_to instead of TagDB to cast engine types
-rw-r--r--binding_generator.py12
-rw-r--r--include/core/Godot.hpp31
2 files changed, 30 insertions, 13 deletions
diff --git a/binding_generator.py b/binding_generator.py
index 13505db..2f17592 100644
--- a/binding_generator.py
+++ b/binding_generator.py
@@ -146,10 +146,14 @@ def generate_class_header(used_classes, c):
source.append("\t};")
source.append("\tstatic ___method_bindings ___mb;")
+ source.append("\tstatic void *_detail_class_tag;")
source.append("")
source.append("public:")
source.append("\tstatic void ___init_method_bindings();")
+ # class id from core engine for casting
+ source.append("\tinline static size_t ___get_id() { return (size_t)_detail_class_tag; }")
+
source.append("")
@@ -355,11 +359,19 @@ def generate_class_implementation(icalls, used_classes, c):
source.append(class_name + "::___method_bindings " + class_name + "::___mb = {};")
source.append("")
+ source.append("void *" + class_name + "::_detail_class_tag = nullptr;")
+ source.append("")
+
source.append("void " + class_name + "::___init_method_bindings() {")
for method in c["methods"]:
source.append("\t___mb.mb_" + method["name"] + " = godot::api->godot_method_bind_get_method(\"" + c["name"] + "\", \"" + method["name"] + "\");")
+ source.append("\tgodot_string_name class_name;")
+ source.append("\tgodot::api->godot_string_name_new_data(&class_name, \"" + c["name"] + "\");")
+ source.append("\t_detail_class_tag = godot::core_1_2_api->godot_get_class_tag(&class_name);")
+ source.append("\tgodot::api->godot_string_name_destroy(&class_name);")
+
source.append("}")
source.append("")
diff --git a/include/core/Godot.hpp b/include/core/Godot.hpp
index ddf1e3e..9d17a2b 100644
--- a/include/core/Godot.hpp
+++ b/include/core/Godot.hpp
@@ -100,7 +100,7 @@ public:
return godot::detail::create_custom_class_instance<Name>(); \
} \
inline static size_t ___get_id() { return typeid(Name).hash_code(); } \
- inline static size_t ___get_base_id() { return typeid(Base).hash_code(); } \
+ inline static size_t ___get_base_id() { return Base::___get_id(); } \
inline static const char *___get_base_type_name() { return Base::___get_class_name(); } \
inline static godot::Object *___get_from_variant(godot::Variant a) { \
return (godot::Object *)godot::detail::get_custom_class_instance<Name>( \
@@ -513,23 +513,28 @@ T *Object::cast_to(const Object *obj) {
if (!obj)
return nullptr;
- size_t have_tag = (size_t)godot::nativescript_1_1_api->godot_nativescript_get_type_tag(obj->_owner);
-
- if (have_tag) {
- if (!godot::_TagDB::is_type_known((size_t)have_tag)) {
- have_tag = 0;
+ if (T::___CLASS_IS_SCRIPT) {
+ size_t have_tag = (size_t)godot::nativescript_1_1_api->godot_nativescript_get_type_tag(obj->_owner);
+ if (have_tag) {
+ if (!godot::_TagDB::is_type_known((size_t)have_tag)) {
+ have_tag = 0;
+ }
}
- }
- if (!have_tag) {
- have_tag = obj->_type_tag;
- }
+ if (!have_tag) {
+ have_tag = obj->_type_tag;
+ }
- if (godot::_TagDB::is_type_compatible(typeid(T).hash_code(), have_tag)) {
- return (T::___CLASS_IS_SCRIPT) ? detail::get_custom_class_instance<T>(obj) : (T *)obj;
+ if (godot::_TagDB::is_type_compatible(T::___get_id(), have_tag)) {
+ return detail::get_custom_class_instance<T>(obj);
+ }
} else {
- return nullptr;
+ if (godot::core_1_2_api->godot_object_cast_to(obj->_owner, (void *)T::___get_id())) {
+ return (T *)obj;
+ }
}
+
+ return nullptr;
}
#endif