diff options
Diffstat (limited to 'core/variant')
-rw-r--r-- | core/variant/array.cpp | 6 | ||||
-rw-r--r-- | core/variant/binder_common.h | 9 | ||||
-rw-r--r-- | core/variant/callable.cpp | 3 | ||||
-rw-r--r-- | core/variant/dictionary.cpp | 11 | ||||
-rw-r--r-- | core/variant/dictionary.h | 1 | ||||
-rw-r--r-- | core/variant/type_info.h | 23 | ||||
-rw-r--r-- | core/variant/typed_array.h | 44 | ||||
-rw-r--r-- | core/variant/variant.cpp | 214 | ||||
-rw-r--r-- | core/variant/variant.h | 70 | ||||
-rw-r--r-- | core/variant/variant_call.cpp | 112 | ||||
-rw-r--r-- | core/variant/variant_callable.cpp | 81 | ||||
-rw-r--r-- | core/variant/variant_callable.h | 58 | ||||
-rw-r--r-- | core/variant/variant_internal.h | 152 | ||||
-rw-r--r-- | core/variant/variant_op.cpp | 9 | ||||
-rw-r--r-- | core/variant/variant_op.h | 32 | ||||
-rw-r--r-- | core/variant/variant_parser.cpp | 5 | ||||
-rw-r--r-- | core/variant/variant_setget.cpp | 93 |
17 files changed, 582 insertions, 341 deletions
diff --git a/core/variant/array.cpp b/core/variant/array.cpp index ab0315ae34..5d6fbb8bed 100644 --- a/core/variant/array.cpp +++ b/core/variant/array.cpp @@ -316,17 +316,17 @@ void Array::erase(const Variant &p_value) { } Variant Array::front() const { - ERR_FAIL_COND_V_MSG(_p->array.size() == 0, Variant(), "Can't take value from empty array."); + ERR_FAIL_COND_V_MSG(_p->array.is_empty(), Variant(), "Can't take value from empty array."); return operator[](0); } Variant Array::back() const { - ERR_FAIL_COND_V_MSG(_p->array.size() == 0, Variant(), "Can't take value from empty array."); + ERR_FAIL_COND_V_MSG(_p->array.is_empty(), Variant(), "Can't take value from empty array."); return operator[](_p->array.size() - 1); } Variant Array::pick_random() const { - ERR_FAIL_COND_V_MSG(_p->array.size() == 0, Variant(), "Can't take value from empty array."); + ERR_FAIL_COND_V_MSG(_p->array.is_empty(), Variant(), "Can't take value from empty array."); return operator[](Math::rand() % _p->array.size()); } diff --git a/core/variant/binder_common.h b/core/variant/binder_common.h index 34b54f1d00..a44b938395 100644 --- a/core/variant/binder_common.h +++ b/core/variant/binder_common.h @@ -51,7 +51,7 @@ template <class T> struct VariantCaster { static _FORCE_INLINE_ T cast(const Variant &p_variant) { using TStripped = std::remove_pointer_t<T>; - if constexpr (std::is_base_of<Object, TStripped>::value) { + if constexpr (std::is_base_of_v<Object, TStripped>) { return Object::cast_to<TStripped>(p_variant); } else { return p_variant; @@ -63,7 +63,7 @@ template <class T> struct VariantCaster<T &> { static _FORCE_INLINE_ T cast(const Variant &p_variant) { using TStripped = std::remove_pointer_t<T>; - if constexpr (std::is_base_of<Object, TStripped>::value) { + if constexpr (std::is_base_of_v<Object, TStripped>) { return Object::cast_to<TStripped>(p_variant); } else { return p_variant; @@ -75,7 +75,7 @@ template <class T> struct VariantCaster<const T &> { static _FORCE_INLINE_ T cast(const Variant &p_variant) { using TStripped = std::remove_pointer_t<T>; - if constexpr (std::is_base_of<Object, TStripped>::value) { + if constexpr (std::is_base_of_v<Object, TStripped>) { return Object::cast_to<TStripped>(p_variant); } else { return p_variant; @@ -176,6 +176,7 @@ VARIANT_ENUM_CAST(Variant::Operator); VARIANT_ENUM_CAST(Key); VARIANT_BITFIELD_CAST(KeyModifierMask); +VARIANT_ENUM_CAST(KeyLocation); static inline Key &operator|=(Key &a, BitField<KeyModifierMask> b) { a = static_cast<Key>(static_cast<int>(a) | static_cast<int>(b.operator int64_t())); @@ -225,7 +226,7 @@ template <typename T> struct VariantObjectClassChecker { static _FORCE_INLINE_ bool check(const Variant &p_variant) { using TStripped = std::remove_pointer_t<T>; - if constexpr (std::is_base_of<Object, TStripped>::value) { + if constexpr (std::is_base_of_v<Object, TStripped>) { Object *obj = p_variant; return Object::cast_to<TStripped>(p_variant) || !obj; } else { diff --git a/core/variant/callable.cpp b/core/variant/callable.cpp index 0b1174c873..55f687bdf9 100644 --- a/core/variant/callable.cpp +++ b/core/variant/callable.cpp @@ -31,13 +31,12 @@ #include "callable.h" #include "callable_bind.h" -#include "core/object/message_queue.h" #include "core/object/object.h" #include "core/object/ref_counted.h" #include "core/object/script_language.h" void Callable::call_deferredp(const Variant **p_arguments, int p_argcount) const { - MessageQueue::get_singleton()->push_callablep(*this, p_arguments, p_argcount); + MessageQueue::get_singleton()->push_callablep(*this, p_arguments, p_argcount, true); } void Callable::callp(const Variant **p_arguments, int p_argcount, Variant &r_return_value, CallError &r_call_error) const { diff --git a/core/variant/dictionary.cpp b/core/variant/dictionary.cpp index 141ce25fa6..9f65a73c6f 100644 --- a/core/variant/dictionary.cpp +++ b/core/variant/dictionary.cpp @@ -150,6 +150,15 @@ Variant Dictionary::get(const Variant &p_key, const Variant &p_default) const { return *result; } +Variant Dictionary::get_or_add(const Variant &p_key, const Variant &p_default) { + const Variant *result = getptr(p_key); + if (!result) { + operator[](p_key) = p_default; + return p_default; + } + return *result; +} + int Dictionary::size() const { return _p->variant_map.size(); } @@ -242,7 +251,7 @@ void Dictionary::clear() { void Dictionary::merge(const Dictionary &p_dictionary, bool p_overwrite) { for (const KeyValue<Variant, Variant> &E : p_dictionary._p->variant_map) { if (p_overwrite || !has(E.key)) { - this->operator[](E.key) = E.value; + operator[](E.key) = E.value; } } } diff --git a/core/variant/dictionary.h b/core/variant/dictionary.h index 8935d35ed9..f94a0da80a 100644 --- a/core/variant/dictionary.h +++ b/core/variant/dictionary.h @@ -58,6 +58,7 @@ public: Variant get_valid(const Variant &p_key) const; Variant get(const Variant &p_key, const Variant &p_default) const; + Variant get_or_add(const Variant &p_key, const Variant &p_default); int size() const; bool is_empty() const; diff --git a/core/variant/type_info.h b/core/variant/type_info.h index e89658d25b..49c4db8229 100644 --- a/core/variant/type_info.h +++ b/core/variant/type_info.h @@ -43,14 +43,10 @@ struct EnableIf<false, T> { }; template <typename, typename> -struct TypesAreSame { - static bool const value = false; -}; +inline constexpr bool types_are_same_v = false; -template <typename A> -struct TypesAreSame<A, A> { - static bool const value = true; -}; +template <typename T> +inline constexpr bool types_are_same_v<T, T> = true; template <typename B, typename D> struct TypeInherits { @@ -60,7 +56,7 @@ struct TypeInherits { static char (&test(...))[2]; static bool const value = sizeof(test(get_d())) == sizeof(char) && - !TypesAreSame<B volatile const, void volatile const>::value; + !types_are_same_v<B volatile const, void volatile const>; }; namespace GodotTypeInfo { @@ -287,14 +283,17 @@ class BitField { int64_t value = 0; public: - _FORCE_INLINE_ void set_flag(T p_flag) { value |= (int64_t)p_flag; } + _FORCE_INLINE_ BitField<T> &set_flag(T p_flag) { + value |= (int64_t)p_flag; + return *this; + } _FORCE_INLINE_ bool has_flag(T p_flag) const { return value & (int64_t)p_flag; } _FORCE_INLINE_ bool is_empty() const { return value == 0; } _FORCE_INLINE_ void clear_flag(T p_flag) { value &= ~(int64_t)p_flag; } _FORCE_INLINE_ void clear() { value = 0; } - _FORCE_INLINE_ BitField() = default; - _FORCE_INLINE_ BitField(int64_t p_value) { value = p_value; } - _FORCE_INLINE_ BitField(T p_value) { value = (int64_t)p_value; } + _FORCE_INLINE_ constexpr BitField() = default; + _FORCE_INLINE_ constexpr BitField(int64_t p_value) { value = p_value; } + _FORCE_INLINE_ constexpr BitField(T p_value) { value = (int64_t)p_value; } _FORCE_INLINE_ operator int64_t() const { return value; } _FORCE_INLINE_ operator Variant() const { return value; } }; diff --git a/core/variant/typed_array.h b/core/variant/typed_array.h index 037c5c7c2e..ed973b9daa 100644 --- a/core/variant/typed_array.h +++ b/core/variant/typed_array.h @@ -88,6 +88,8 @@ struct VariantInternalAccessor<const TypedArray<T> &> { } \ }; +// All Variant::OBJECT types are intentionally omitted from this list because they are handled by +// the unspecialized TypedArray definition. MAKE_TYPED_ARRAY(bool, Variant::BOOL) MAKE_TYPED_ARRAY(uint8_t, Variant::INT) MAKE_TYPED_ARRAY(int8_t, Variant::INT) @@ -107,11 +109,14 @@ MAKE_TYPED_ARRAY(Rect2i, Variant::RECT2I) MAKE_TYPED_ARRAY(Vector3, Variant::VECTOR3) MAKE_TYPED_ARRAY(Vector3i, Variant::VECTOR3I) MAKE_TYPED_ARRAY(Transform2D, Variant::TRANSFORM2D) +MAKE_TYPED_ARRAY(Vector4, Variant::VECTOR4) +MAKE_TYPED_ARRAY(Vector4i, Variant::VECTOR4I) MAKE_TYPED_ARRAY(Plane, Variant::PLANE) MAKE_TYPED_ARRAY(Quaternion, Variant::QUATERNION) MAKE_TYPED_ARRAY(AABB, Variant::AABB) MAKE_TYPED_ARRAY(Basis, Variant::BASIS) MAKE_TYPED_ARRAY(Transform3D, Variant::TRANSFORM3D) +MAKE_TYPED_ARRAY(Projection, Variant::PROJECTION) MAKE_TYPED_ARRAY(Color, Variant::COLOR) MAKE_TYPED_ARRAY(StringName, Variant::STRING_NAME) MAKE_TYPED_ARRAY(NodePath, Variant::NODE_PATH) @@ -120,15 +125,15 @@ MAKE_TYPED_ARRAY(Callable, Variant::CALLABLE) MAKE_TYPED_ARRAY(Signal, Variant::SIGNAL) MAKE_TYPED_ARRAY(Dictionary, Variant::DICTIONARY) MAKE_TYPED_ARRAY(Array, Variant::ARRAY) -MAKE_TYPED_ARRAY(Vector<uint8_t>, Variant::PACKED_BYTE_ARRAY) -MAKE_TYPED_ARRAY(Vector<int32_t>, Variant::PACKED_INT32_ARRAY) -MAKE_TYPED_ARRAY(Vector<int64_t>, Variant::PACKED_INT64_ARRAY) -MAKE_TYPED_ARRAY(Vector<float>, Variant::PACKED_FLOAT32_ARRAY) -MAKE_TYPED_ARRAY(Vector<double>, Variant::PACKED_FLOAT64_ARRAY) -MAKE_TYPED_ARRAY(Vector<String>, Variant::PACKED_STRING_ARRAY) -MAKE_TYPED_ARRAY(Vector<Vector2>, Variant::PACKED_VECTOR2_ARRAY) -MAKE_TYPED_ARRAY(Vector<Vector3>, Variant::PACKED_VECTOR3_ARRAY) -MAKE_TYPED_ARRAY(Vector<Color>, Variant::PACKED_COLOR_ARRAY) +MAKE_TYPED_ARRAY(PackedByteArray, Variant::PACKED_BYTE_ARRAY) +MAKE_TYPED_ARRAY(PackedInt32Array, Variant::PACKED_INT32_ARRAY) +MAKE_TYPED_ARRAY(PackedInt64Array, Variant::PACKED_INT64_ARRAY) +MAKE_TYPED_ARRAY(PackedFloat32Array, Variant::PACKED_FLOAT32_ARRAY) +MAKE_TYPED_ARRAY(PackedFloat64Array, Variant::PACKED_FLOAT64_ARRAY) +MAKE_TYPED_ARRAY(PackedStringArray, Variant::PACKED_STRING_ARRAY) +MAKE_TYPED_ARRAY(PackedVector2Array, Variant::PACKED_VECTOR2_ARRAY) +MAKE_TYPED_ARRAY(PackedVector3Array, Variant::PACKED_VECTOR3_ARRAY) +MAKE_TYPED_ARRAY(PackedColorArray, Variant::PACKED_COLOR_ARRAY) MAKE_TYPED_ARRAY(IPAddress, Variant::STRING) template <class T> @@ -205,11 +210,14 @@ MAKE_TYPED_ARRAY_INFO(Rect2i, Variant::RECT2I) MAKE_TYPED_ARRAY_INFO(Vector3, Variant::VECTOR3) MAKE_TYPED_ARRAY_INFO(Vector3i, Variant::VECTOR3I) MAKE_TYPED_ARRAY_INFO(Transform2D, Variant::TRANSFORM2D) +MAKE_TYPED_ARRAY_INFO(Vector4, Variant::VECTOR4) +MAKE_TYPED_ARRAY_INFO(Vector4i, Variant::VECTOR4I) MAKE_TYPED_ARRAY_INFO(Plane, Variant::PLANE) MAKE_TYPED_ARRAY_INFO(Quaternion, Variant::QUATERNION) MAKE_TYPED_ARRAY_INFO(AABB, Variant::AABB) MAKE_TYPED_ARRAY_INFO(Basis, Variant::BASIS) MAKE_TYPED_ARRAY_INFO(Transform3D, Variant::TRANSFORM3D) +MAKE_TYPED_ARRAY_INFO(Projection, Variant::PROJECTION) MAKE_TYPED_ARRAY_INFO(Color, Variant::COLOR) MAKE_TYPED_ARRAY_INFO(StringName, Variant::STRING_NAME) MAKE_TYPED_ARRAY_INFO(NodePath, Variant::NODE_PATH) @@ -218,15 +226,15 @@ MAKE_TYPED_ARRAY_INFO(Callable, Variant::CALLABLE) MAKE_TYPED_ARRAY_INFO(Signal, Variant::SIGNAL) MAKE_TYPED_ARRAY_INFO(Dictionary, Variant::DICTIONARY) MAKE_TYPED_ARRAY_INFO(Array, Variant::ARRAY) -MAKE_TYPED_ARRAY_INFO(Vector<uint8_t>, Variant::PACKED_BYTE_ARRAY) -MAKE_TYPED_ARRAY_INFO(Vector<int32_t>, Variant::PACKED_INT32_ARRAY) -MAKE_TYPED_ARRAY_INFO(Vector<int64_t>, Variant::PACKED_INT64_ARRAY) -MAKE_TYPED_ARRAY_INFO(Vector<float>, Variant::PACKED_FLOAT32_ARRAY) -MAKE_TYPED_ARRAY_INFO(Vector<double>, Variant::PACKED_FLOAT64_ARRAY) -MAKE_TYPED_ARRAY_INFO(Vector<String>, Variant::PACKED_STRING_ARRAY) -MAKE_TYPED_ARRAY_INFO(Vector<Vector2>, Variant::PACKED_VECTOR2_ARRAY) -MAKE_TYPED_ARRAY_INFO(Vector<Vector3>, Variant::PACKED_VECTOR3_ARRAY) -MAKE_TYPED_ARRAY_INFO(Vector<Color>, Variant::PACKED_COLOR_ARRAY) +MAKE_TYPED_ARRAY_INFO(PackedByteArray, Variant::PACKED_BYTE_ARRAY) +MAKE_TYPED_ARRAY_INFO(PackedInt32Array, Variant::PACKED_INT32_ARRAY) +MAKE_TYPED_ARRAY_INFO(PackedInt64Array, Variant::PACKED_INT64_ARRAY) +MAKE_TYPED_ARRAY_INFO(PackedFloat32Array, Variant::PACKED_FLOAT32_ARRAY) +MAKE_TYPED_ARRAY_INFO(PackedFloat64Array, Variant::PACKED_FLOAT64_ARRAY) +MAKE_TYPED_ARRAY_INFO(PackedStringArray, Variant::PACKED_STRING_ARRAY) +MAKE_TYPED_ARRAY_INFO(PackedVector2Array, Variant::PACKED_VECTOR2_ARRAY) +MAKE_TYPED_ARRAY_INFO(PackedVector3Array, Variant::PACKED_VECTOR3_ARRAY) +MAKE_TYPED_ARRAY_INFO(PackedColorArray, Variant::PACKED_COLOR_ARRAY) MAKE_TYPED_ARRAY_INFO(IPAddress, Variant::STRING) #undef MAKE_TYPED_ARRAY diff --git a/core/variant/variant.cpp b/core/variant/variant.cpp index 4c0212075b..67f2c10099 100644 --- a/core/variant/variant.cpp +++ b/core/variant/variant.cpp @@ -931,7 +931,7 @@ bool Variant::is_zero() const { return *reinterpret_cast<const ::RID *>(_data._mem) == ::RID(); } case OBJECT: { - return _get_obj().obj == nullptr; + return get_validated_object() == nullptr; } case CALLABLE: { return reinterpret_cast<const Callable *>(_data._mem)->is_null(); @@ -1246,53 +1246,53 @@ void Variant::zero() { case NIL: break; case BOOL: - this->_data._bool = false; + _data._bool = false; break; case INT: - this->_data._int = 0; + _data._int = 0; break; case FLOAT: - this->_data._float = 0; + _data._float = 0; break; case VECTOR2: - *reinterpret_cast<Vector2 *>(this->_data._mem) = Vector2(); + *reinterpret_cast<Vector2 *>(_data._mem) = Vector2(); break; case VECTOR2I: - *reinterpret_cast<Vector2i *>(this->_data._mem) = Vector2i(); + *reinterpret_cast<Vector2i *>(_data._mem) = Vector2i(); break; case RECT2: - *reinterpret_cast<Rect2 *>(this->_data._mem) = Rect2(); + *reinterpret_cast<Rect2 *>(_data._mem) = Rect2(); break; case RECT2I: - *reinterpret_cast<Rect2i *>(this->_data._mem) = Rect2i(); + *reinterpret_cast<Rect2i *>(_data._mem) = Rect2i(); break; case VECTOR3: - *reinterpret_cast<Vector3 *>(this->_data._mem) = Vector3(); + *reinterpret_cast<Vector3 *>(_data._mem) = Vector3(); break; case VECTOR3I: - *reinterpret_cast<Vector3i *>(this->_data._mem) = Vector3i(); + *reinterpret_cast<Vector3i *>(_data._mem) = Vector3i(); break; case VECTOR4: - *reinterpret_cast<Vector4 *>(this->_data._mem) = Vector4(); + *reinterpret_cast<Vector4 *>(_data._mem) = Vector4(); break; case VECTOR4I: - *reinterpret_cast<Vector4i *>(this->_data._mem) = Vector4i(); + *reinterpret_cast<Vector4i *>(_data._mem) = Vector4i(); break; case PLANE: - *reinterpret_cast<Plane *>(this->_data._mem) = Plane(); + *reinterpret_cast<Plane *>(_data._mem) = Plane(); break; case QUATERNION: - *reinterpret_cast<Quaternion *>(this->_data._mem) = Quaternion(); + *reinterpret_cast<Quaternion *>(_data._mem) = Quaternion(); break; case COLOR: - *reinterpret_cast<Color *>(this->_data._mem) = Color(); + *reinterpret_cast<Color *>(_data._mem) = Color(); break; default: Type prev_type = type; - this->clear(); + clear(); if (type != prev_type) { // clear() changes type to NIL, so it needs to be restored. Callable::CallError ce; @@ -1793,31 +1793,31 @@ String Variant::stringify(int recursion_count) const { } // Packed arrays cannot contain recursive structures, the recursion_count increment is not needed. case PACKED_VECTOR2_ARRAY: { - return stringify_vector(operator Vector<Vector2>(), recursion_count); + return stringify_vector(operator PackedVector2Array(), recursion_count); } case PACKED_VECTOR3_ARRAY: { - return stringify_vector(operator Vector<Vector3>(), recursion_count); + return stringify_vector(operator PackedVector3Array(), recursion_count); } case PACKED_COLOR_ARRAY: { - return stringify_vector(operator Vector<Color>(), recursion_count); + return stringify_vector(operator PackedColorArray(), recursion_count); } case PACKED_STRING_ARRAY: { - return stringify_vector(operator Vector<String>(), recursion_count); + return stringify_vector(operator PackedStringArray(), recursion_count); } case PACKED_BYTE_ARRAY: { - return stringify_vector(operator Vector<uint8_t>(), recursion_count); + return stringify_vector(operator PackedByteArray(), recursion_count); } case PACKED_INT32_ARRAY: { - return stringify_vector(operator Vector<int32_t>(), recursion_count); + return stringify_vector(operator PackedInt32Array(), recursion_count); } case PACKED_INT64_ARRAY: { - return stringify_vector(operator Vector<int64_t>(), recursion_count); + return stringify_vector(operator PackedInt64Array(), recursion_count); } case PACKED_FLOAT32_ARRAY: { - return stringify_vector(operator Vector<float>(), recursion_count); + return stringify_vector(operator PackedFloat32Array(), recursion_count); } case PACKED_FLOAT64_ARRAY: { - return stringify_vector(operator Vector<double>(), recursion_count); + return stringify_vector(operator PackedFloat64Array(), recursion_count); } case ARRAY: { ERR_FAIL_COND_V_MSG(recursion_count > MAX_RECURSION, "[...]", "Maximum array recursion reached!"); @@ -2207,31 +2207,31 @@ inline DA _convert_array_from_variant(const Variant &p_variant) { return _convert_array<DA, Array>(p_variant.operator Array()); } case Variant::PACKED_BYTE_ARRAY: { - return _convert_array<DA, Vector<uint8_t>>(p_variant.operator Vector<uint8_t>()); + return _convert_array<DA, PackedByteArray>(p_variant.operator PackedByteArray()); } case Variant::PACKED_INT32_ARRAY: { - return _convert_array<DA, Vector<int32_t>>(p_variant.operator Vector<int32_t>()); + return _convert_array<DA, PackedInt32Array>(p_variant.operator PackedInt32Array()); } case Variant::PACKED_INT64_ARRAY: { - return _convert_array<DA, Vector<int64_t>>(p_variant.operator Vector<int64_t>()); + return _convert_array<DA, PackedInt64Array>(p_variant.operator PackedInt64Array()); } case Variant::PACKED_FLOAT32_ARRAY: { - return _convert_array<DA, Vector<float>>(p_variant.operator Vector<float>()); + return _convert_array<DA, PackedFloat32Array>(p_variant.operator PackedFloat32Array()); } case Variant::PACKED_FLOAT64_ARRAY: { - return _convert_array<DA, Vector<double>>(p_variant.operator Vector<double>()); + return _convert_array<DA, PackedFloat64Array>(p_variant.operator PackedFloat64Array()); } case Variant::PACKED_STRING_ARRAY: { - return _convert_array<DA, Vector<String>>(p_variant.operator Vector<String>()); + return _convert_array<DA, PackedStringArray>(p_variant.operator PackedStringArray()); } case Variant::PACKED_VECTOR2_ARRAY: { - return _convert_array<DA, Vector<Vector2>>(p_variant.operator Vector<Vector2>()); + return _convert_array<DA, PackedVector2Array>(p_variant.operator PackedVector2Array()); } case Variant::PACKED_VECTOR3_ARRAY: { - return _convert_array<DA, Vector<Vector3>>(p_variant.operator Vector<Vector3>()); + return _convert_array<DA, PackedVector3Array>(p_variant.operator PackedVector3Array()); } case Variant::PACKED_COLOR_ARRAY: { - return _convert_array<DA, Vector<Color>>(p_variant.operator Vector<Color>()); + return _convert_array<DA, PackedColorArray>(p_variant.operator PackedColorArray()); } default: { return DA(); @@ -2247,75 +2247,75 @@ Variant::operator Array() const { } } -Variant::operator Vector<uint8_t>() const { +Variant::operator PackedByteArray() const { if (type == PACKED_BYTE_ARRAY) { return static_cast<PackedArrayRef<uint8_t> *>(_data.packed_array)->array; } else { - return _convert_array_from_variant<Vector<uint8_t>>(*this); + return _convert_array_from_variant<PackedByteArray>(*this); } } -Variant::operator Vector<int32_t>() const { +Variant::operator PackedInt32Array() const { if (type == PACKED_INT32_ARRAY) { return static_cast<PackedArrayRef<int32_t> *>(_data.packed_array)->array; } else { - return _convert_array_from_variant<Vector<int>>(*this); + return _convert_array_from_variant<PackedInt32Array>(*this); } } -Variant::operator Vector<int64_t>() const { +Variant::operator PackedInt64Array() const { if (type == PACKED_INT64_ARRAY) { return static_cast<PackedArrayRef<int64_t> *>(_data.packed_array)->array; } else { - return _convert_array_from_variant<Vector<int64_t>>(*this); + return _convert_array_from_variant<PackedInt64Array>(*this); } } -Variant::operator Vector<float>() const { +Variant::operator PackedFloat32Array() const { if (type == PACKED_FLOAT32_ARRAY) { return static_cast<PackedArrayRef<float> *>(_data.packed_array)->array; } else { - return _convert_array_from_variant<Vector<float>>(*this); + return _convert_array_from_variant<PackedFloat32Array>(*this); } } -Variant::operator Vector<double>() const { +Variant::operator PackedFloat64Array() const { if (type == PACKED_FLOAT64_ARRAY) { return static_cast<PackedArrayRef<double> *>(_data.packed_array)->array; } else { - return _convert_array_from_variant<Vector<double>>(*this); + return _convert_array_from_variant<PackedFloat64Array>(*this); } } -Variant::operator Vector<String>() const { +Variant::operator PackedStringArray() const { if (type == PACKED_STRING_ARRAY) { return static_cast<PackedArrayRef<String> *>(_data.packed_array)->array; } else { - return _convert_array_from_variant<Vector<String>>(*this); + return _convert_array_from_variant<PackedStringArray>(*this); } } -Variant::operator Vector<Vector3>() const { - if (type == PACKED_VECTOR3_ARRAY) { - return static_cast<PackedArrayRef<Vector3> *>(_data.packed_array)->array; +Variant::operator PackedVector2Array() const { + if (type == PACKED_VECTOR2_ARRAY) { + return static_cast<PackedArrayRef<Vector2> *>(_data.packed_array)->array; } else { - return _convert_array_from_variant<Vector<Vector3>>(*this); + return _convert_array_from_variant<PackedVector2Array>(*this); } } -Variant::operator Vector<Vector2>() const { - if (type == PACKED_VECTOR2_ARRAY) { - return static_cast<PackedArrayRef<Vector2> *>(_data.packed_array)->array; +Variant::operator PackedVector3Array() const { + if (type == PACKED_VECTOR3_ARRAY) { + return static_cast<PackedArrayRef<Vector3> *>(_data.packed_array)->array; } else { - return _convert_array_from_variant<Vector<Vector2>>(*this); + return _convert_array_from_variant<PackedVector3Array>(*this); } } -Variant::operator Vector<Color>() const { +Variant::operator PackedColorArray() const { if (type == PACKED_COLOR_ARRAY) { return static_cast<PackedArrayRef<Color> *>(_data.packed_array)->array; } else { - return _convert_array_from_variant<Vector<Color>>(*this); + return _convert_array_from_variant<PackedColorArray>(*this); } } @@ -2350,7 +2350,7 @@ Variant::operator Vector<Plane>() const { } Variant::operator Vector<Face3>() const { - Vector<Vector3> va = operator Vector<Vector3>(); + PackedVector3Array va = operator PackedVector3Array(); Vector<Face3> faces; int va_size = va.size(); if (va_size == 0) { @@ -2386,7 +2386,7 @@ Variant::operator Vector<Variant>() const { } Variant::operator Vector<StringName>() const { - Vector<String> from = operator Vector<String>(); + PackedStringArray from = operator PackedStringArray(); Vector<StringName> to; int len = from.size(); to.resize(len); @@ -2646,78 +2646,79 @@ Variant::Variant(const Array &p_array) { memnew_placement(_data._mem, Array(p_array)); } -Variant::Variant(const Vector<Plane> &p_array) { - type = ARRAY; - - Array *plane_array = memnew_placement(_data._mem, Array); - - plane_array->resize(p_array.size()); - - for (int i = 0; i < p_array.size(); i++) { - plane_array->operator[](i) = Variant(p_array[i]); - } -} - -Variant::Variant(const Vector<::RID> &p_array) { - type = ARRAY; - - Array *rid_array = memnew_placement(_data._mem, Array); - - rid_array->resize(p_array.size()); - - for (int i = 0; i < p_array.size(); i++) { - rid_array->set(i, Variant(p_array[i])); - } -} - -Variant::Variant(const Vector<uint8_t> &p_byte_array) { +Variant::Variant(const PackedByteArray &p_byte_array) { type = PACKED_BYTE_ARRAY; _data.packed_array = PackedArrayRef<uint8_t>::create(p_byte_array); } -Variant::Variant(const Vector<int32_t> &p_int32_array) { +Variant::Variant(const PackedInt32Array &p_int32_array) { type = PACKED_INT32_ARRAY; _data.packed_array = PackedArrayRef<int32_t>::create(p_int32_array); } -Variant::Variant(const Vector<int64_t> &p_int64_array) { +Variant::Variant(const PackedInt64Array &p_int64_array) { type = PACKED_INT64_ARRAY; _data.packed_array = PackedArrayRef<int64_t>::create(p_int64_array); } -Variant::Variant(const Vector<float> &p_float32_array) { +Variant::Variant(const PackedFloat32Array &p_float32_array) { type = PACKED_FLOAT32_ARRAY; _data.packed_array = PackedArrayRef<float>::create(p_float32_array); } -Variant::Variant(const Vector<double> &p_float64_array) { +Variant::Variant(const PackedFloat64Array &p_float64_array) { type = PACKED_FLOAT64_ARRAY; _data.packed_array = PackedArrayRef<double>::create(p_float64_array); } -Variant::Variant(const Vector<String> &p_string_array) { +Variant::Variant(const PackedStringArray &p_string_array) { type = PACKED_STRING_ARRAY; _data.packed_array = PackedArrayRef<String>::create(p_string_array); } -Variant::Variant(const Vector<Vector3> &p_vector3_array) { - type = PACKED_VECTOR3_ARRAY; - _data.packed_array = PackedArrayRef<Vector3>::create(p_vector3_array); -} - -Variant::Variant(const Vector<Vector2> &p_vector2_array) { +Variant::Variant(const PackedVector2Array &p_vector2_array) { type = PACKED_VECTOR2_ARRAY; _data.packed_array = PackedArrayRef<Vector2>::create(p_vector2_array); } -Variant::Variant(const Vector<Color> &p_color_array) { +Variant::Variant(const PackedVector3Array &p_vector3_array) { + type = PACKED_VECTOR3_ARRAY; + _data.packed_array = PackedArrayRef<Vector3>::create(p_vector3_array); +} + +Variant::Variant(const PackedColorArray &p_color_array) { type = PACKED_COLOR_ARRAY; _data.packed_array = PackedArrayRef<Color>::create(p_color_array); } +/* helpers */ +Variant::Variant(const Vector<::RID> &p_array) { + type = ARRAY; + + Array *rid_array = memnew_placement(_data._mem, Array); + + rid_array->resize(p_array.size()); + + for (int i = 0; i < p_array.size(); i++) { + rid_array->set(i, Variant(p_array[i])); + } +} + +Variant::Variant(const Vector<Plane> &p_array) { + type = ARRAY; + + Array *plane_array = memnew_placement(_data._mem, Array); + + plane_array->resize(p_array.size()); + + for (int i = 0; i < p_array.size(); i++) { + plane_array->operator[](i) = Variant(p_array[i]); + } +} + Variant::Variant(const Vector<Face3> &p_face_array) { - Vector<Vector3> vertices; + PackedVector3Array vertices; int face_count = p_face_array.size(); vertices.resize(face_count * 3); @@ -2737,7 +2738,6 @@ Variant::Variant(const Vector<Face3> &p_face_array) { *this = vertices; } -/* helpers */ Variant::Variant(const Vector<Variant> &p_array) { type = NIL; Array arr; @@ -2750,7 +2750,7 @@ Variant::Variant(const Vector<Variant> &p_array) { Variant::Variant(const Vector<StringName> &p_array) { type = NIL; - Vector<String> v; + PackedStringArray v; int len = p_array.size(); v.resize(len); for (int i = 0; i < len; i++) { @@ -3100,7 +3100,7 @@ uint32_t Variant::recursive_hash(int recursion_count) const { } break; case PACKED_BYTE_ARRAY: { - const Vector<uint8_t> &arr = PackedArrayRef<uint8_t>::get_array(_data.packed_array); + const PackedByteArray &arr = PackedArrayRef<uint8_t>::get_array(_data.packed_array); int len = arr.size(); if (likely(len)) { const uint8_t *r = arr.ptr(); @@ -3111,7 +3111,7 @@ uint32_t Variant::recursive_hash(int recursion_count) const { } break; case PACKED_INT32_ARRAY: { - const Vector<int32_t> &arr = PackedArrayRef<int32_t>::get_array(_data.packed_array); + const PackedInt32Array &arr = PackedArrayRef<int32_t>::get_array(_data.packed_array); int len = arr.size(); if (likely(len)) { const int32_t *r = arr.ptr(); @@ -3122,7 +3122,7 @@ uint32_t Variant::recursive_hash(int recursion_count) const { } break; case PACKED_INT64_ARRAY: { - const Vector<int64_t> &arr = PackedArrayRef<int64_t>::get_array(_data.packed_array); + const PackedInt64Array &arr = PackedArrayRef<int64_t>::get_array(_data.packed_array); int len = arr.size(); if (likely(len)) { const int64_t *r = arr.ptr(); @@ -3133,7 +3133,7 @@ uint32_t Variant::recursive_hash(int recursion_count) const { } break; case PACKED_FLOAT32_ARRAY: { - const Vector<float> &arr = PackedArrayRef<float>::get_array(_data.packed_array); + const PackedFloat32Array &arr = PackedArrayRef<float>::get_array(_data.packed_array); int len = arr.size(); if (likely(len)) { @@ -3149,7 +3149,7 @@ uint32_t Variant::recursive_hash(int recursion_count) const { } break; case PACKED_FLOAT64_ARRAY: { - const Vector<double> &arr = PackedArrayRef<double>::get_array(_data.packed_array); + const PackedFloat64Array &arr = PackedArrayRef<double>::get_array(_data.packed_array); int len = arr.size(); if (likely(len)) { @@ -3166,7 +3166,7 @@ uint32_t Variant::recursive_hash(int recursion_count) const { } break; case PACKED_STRING_ARRAY: { uint32_t hash = HASH_MURMUR3_SEED; - const Vector<String> &arr = PackedArrayRef<String>::get_array(_data.packed_array); + const PackedStringArray &arr = PackedArrayRef<String>::get_array(_data.packed_array); int len = arr.size(); if (likely(len)) { @@ -3182,7 +3182,7 @@ uint32_t Variant::recursive_hash(int recursion_count) const { } break; case PACKED_VECTOR2_ARRAY: { uint32_t hash = HASH_MURMUR3_SEED; - const Vector<Vector2> &arr = PackedArrayRef<Vector2>::get_array(_data.packed_array); + const PackedVector2Array &arr = PackedArrayRef<Vector2>::get_array(_data.packed_array); int len = arr.size(); if (likely(len)) { @@ -3199,7 +3199,7 @@ uint32_t Variant::recursive_hash(int recursion_count) const { } break; case PACKED_VECTOR3_ARRAY: { uint32_t hash = HASH_MURMUR3_SEED; - const Vector<Vector3> &arr = PackedArrayRef<Vector3>::get_array(_data.packed_array); + const PackedVector3Array &arr = PackedArrayRef<Vector3>::get_array(_data.packed_array); int len = arr.size(); if (likely(len)) { @@ -3217,7 +3217,7 @@ uint32_t Variant::recursive_hash(int recursion_count) const { } break; case PACKED_COLOR_ARRAY: { uint32_t hash = HASH_MURMUR3_SEED; - const Vector<Color> &arr = PackedArrayRef<Color>::get_array(_data.packed_array); + const PackedColorArray &arr = PackedArrayRef<Color>::get_array(_data.packed_array); int len = arr.size(); if (likely(len)) { diff --git a/core/variant/variant.h b/core/variant/variant.h index 17e701cf66..d685444c30 100644 --- a/core/variant/variant.h +++ b/core/variant/variant.h @@ -70,6 +70,7 @@ typedef Vector<int32_t> PackedInt32Array; typedef Vector<int64_t> PackedInt64Array; typedef Vector<float> PackedFloat32Array; typedef Vector<double> PackedFloat64Array; +typedef Vector<real_t> PackedRealArray; typedef Vector<String> PackedStringArray; typedef Vector<Vector2> PackedVector2Array; typedef Vector<Vector3> PackedVector3Array; @@ -175,7 +176,7 @@ private: struct PackedArrayRefBase { SafeRefCount refcount; _FORCE_INLINE_ PackedArrayRefBase *reference() { - if (this->refcount.ref()) { + if (refcount.ref()) { return this; } else { return nullptr; @@ -403,21 +404,21 @@ public: operator Dictionary() const; operator Array() const; - operator Vector<uint8_t>() const; - operator Vector<int32_t>() const; - operator Vector<int64_t>() const; - operator Vector<float>() const; - operator Vector<double>() const; - operator Vector<String>() const; - operator Vector<Vector3>() const; - operator Vector<Color>() const; + operator PackedByteArray() const; + operator PackedInt32Array() const; + operator PackedInt64Array() const; + operator PackedFloat32Array() const; + operator PackedFloat64Array() const; + operator PackedStringArray() const; + operator PackedVector3Array() const; + operator PackedVector2Array() const; + operator PackedColorArray() const; + + operator Vector<::RID>() const; operator Vector<Plane>() const; operator Vector<Face3>() const; - operator Vector<Variant>() const; operator Vector<StringName>() const; - operator Vector<::RID>() const; - operator Vector<Vector2>() const; // some core type enums to convert to operator Side() const; @@ -472,21 +473,21 @@ public: Variant(const Dictionary &p_dictionary); Variant(const Array &p_array); + Variant(const PackedByteArray &p_byte_array); + Variant(const PackedInt32Array &p_int32_array); + Variant(const PackedInt64Array &p_int64_array); + Variant(const PackedFloat32Array &p_float32_array); + Variant(const PackedFloat64Array &p_float64_array); + Variant(const PackedStringArray &p_string_array); + Variant(const PackedVector2Array &p_vector2_array); + Variant(const PackedVector3Array &p_vector3_array); + Variant(const PackedColorArray &p_color_array); + + Variant(const Vector<::RID> &p_array); // helper Variant(const Vector<Plane> &p_array); // helper - Variant(const Vector<uint8_t> &p_byte_array); - Variant(const Vector<int32_t> &p_int32_array); - Variant(const Vector<int64_t> &p_int64_array); - Variant(const Vector<float> &p_float32_array); - Variant(const Vector<double> &p_float64_array); - Variant(const Vector<String> &p_string_array); - Variant(const Vector<Vector3> &p_vector3_array); - Variant(const Vector<Color> &p_color_array); Variant(const Vector<Face3> &p_face_array); - Variant(const Vector<Variant> &p_array); Variant(const Vector<StringName> &p_array); - Variant(const Vector<::RID> &p_array); // helper - Variant(const Vector<Vector2> &p_array); // helper Variant(const IPAddress &p_address); @@ -501,6 +502,7 @@ public: VARIANT_ENUM_CLASS_CONSTRUCTOR(JoyAxis) VARIANT_ENUM_CLASS_CONSTRUCTOR(JoyButton) VARIANT_ENUM_CLASS_CONSTRUCTOR(Key) + VARIANT_ENUM_CLASS_CONSTRUCTOR(KeyLocation) VARIANT_ENUM_CLASS_CONSTRUCTOR(MIDIMessage) VARIANT_ENUM_CLASS_CONSTRUCTOR(MouseButton) @@ -571,6 +573,7 @@ public: static ValidatedBuiltInMethod get_validated_builtin_method(Variant::Type p_type, const StringName &p_method); static PTRBuiltInMethod get_ptr_builtin_method(Variant::Type p_type, const StringName &p_method); + static MethodInfo get_builtin_method_info(Variant::Type p_type, const StringName &p_method); static int get_builtin_method_argument_count(Variant::Type p_type, const StringName &p_method); static Variant::Type get_builtin_method_argument_type(Variant::Type p_type, const StringName &p_method, int p_argument); static String get_builtin_method_argument_name(Variant::Type p_type, const StringName &p_method, int p_argument); @@ -706,9 +709,20 @@ public: bool has_key(const Variant &p_key, bool &r_valid) const; /* Generic */ - - void set(const Variant &p_index, const Variant &p_value, bool *r_valid = nullptr); - Variant get(const Variant &p_index, bool *r_valid = nullptr) const; + enum VariantSetError { + SET_OK, + SET_KEYED_ERR, + SET_NAMED_ERR, + SET_INDEXED_ERR + }; + enum VariantGetError { + GET_OK, + GET_KEYED_ERR, + GET_NAMED_ERR, + GET_INDEXED_ERR + }; + void set(const Variant &p_index, const Variant &p_value, bool *r_valid = nullptr, VariantSetError *err_code = nullptr); + Variant get(const Variant &p_index, bool *r_valid = nullptr, VariantGetError *err_code = nullptr) const; bool in(const Variant &p_index, bool *r_valid = nullptr) const; bool iter_init(Variant &r_iter, bool &r_valid) const; @@ -768,8 +782,8 @@ public: static Variant get_constant_value(Variant::Type p_type, const StringName &p_value, bool *r_valid = nullptr); static void get_enums_for_type(Variant::Type p_type, List<StringName> *p_enums); - static void get_enumerations_for_enum(Variant::Type p_type, StringName p_enum_name, List<StringName> *p_enumerations); - static int get_enum_value(Variant::Type p_type, StringName p_enum_name, StringName p_enumeration, bool *r_valid = nullptr); + static void get_enumerations_for_enum(Variant::Type p_type, const StringName &p_enum_name, List<StringName> *p_enumerations); + static int get_enum_value(Variant::Type p_type, const StringName &p_enum_name, const StringName &p_enumeration, bool *r_valid = nullptr); typedef String (*ObjectDeConstruct)(const Variant &p_object, void *ud); typedef void (*ObjectConstruct)(const String &p_text, void *ud, Variant &r_value); diff --git a/core/variant/variant_call.cpp b/core/variant/variant_call.cpp index f041d2c95e..b551a7059e 100644 --- a/core/variant/variant_call.cpp +++ b/core/variant/variant_call.cpp @@ -666,7 +666,7 @@ struct _VariantCall { CharString cs; cs.resize(p_instance->size() + 1); memcpy(cs.ptrw(), r, p_instance->size()); - cs[p_instance->size()] = 0; + cs[(int)p_instance->size()] = 0; s = cs.get_data(); } @@ -885,7 +885,7 @@ struct _VariantCall { ERR_FAIL_COND_V_MSG(size % sizeof(int32_t), dest, "PackedByteArray size must be a multiple of 4 (size of 32-bit integer) to convert to PackedInt32Array."); const uint8_t *r = p_instance->ptr(); dest.resize(size / sizeof(int32_t)); - ERR_FAIL_COND_V(dest.size() == 0, dest); // Avoid UB in case resize failed. + ERR_FAIL_COND_V(dest.is_empty(), dest); // Avoid UB in case resize failed. memcpy(dest.ptrw(), r, dest.size() * sizeof(int32_t)); return dest; } @@ -899,7 +899,7 @@ struct _VariantCall { ERR_FAIL_COND_V_MSG(size % sizeof(int64_t), dest, "PackedByteArray size must be a multiple of 8 (size of 64-bit integer) to convert to PackedInt64Array."); const uint8_t *r = p_instance->ptr(); dest.resize(size / sizeof(int64_t)); - ERR_FAIL_COND_V(dest.size() == 0, dest); // Avoid UB in case resize failed. + ERR_FAIL_COND_V(dest.is_empty(), dest); // Avoid UB in case resize failed. memcpy(dest.ptrw(), r, dest.size() * sizeof(int64_t)); return dest; } @@ -913,7 +913,7 @@ struct _VariantCall { ERR_FAIL_COND_V_MSG(size % sizeof(float), dest, "PackedByteArray size must be a multiple of 4 (size of 32-bit float) to convert to PackedFloat32Array."); const uint8_t *r = p_instance->ptr(); dest.resize(size / sizeof(float)); - ERR_FAIL_COND_V(dest.size() == 0, dest); // Avoid UB in case resize failed. + ERR_FAIL_COND_V(dest.is_empty(), dest); // Avoid UB in case resize failed. memcpy(dest.ptrw(), r, dest.size() * sizeof(float)); return dest; } @@ -927,7 +927,7 @@ struct _VariantCall { ERR_FAIL_COND_V_MSG(size % sizeof(double), dest, "PackedByteArray size must be a multiple of 8 (size of 64-bit double) to convert to PackedFloat64Array."); const uint8_t *r = p_instance->ptr(); dest.resize(size / sizeof(double)); - ERR_FAIL_COND_V(dest.size() == 0, dest); // Avoid UB in case resize failed. + ERR_FAIL_COND_V(dest.is_empty(), dest); // Avoid UB in case resize failed. memcpy(dest.ptrw(), r, dest.size() * sizeof(double)); return dest; } @@ -1071,14 +1071,14 @@ struct _VariantCall { static ConstantData *constant_data; - static void add_constant(int p_type, StringName p_constant_name, int64_t p_constant_value) { + static void add_constant(int p_type, const StringName &p_constant_name, int64_t p_constant_value) { constant_data[p_type].value[p_constant_name] = p_constant_value; #ifdef DEBUG_ENABLED constant_data[p_type].value_ordered.push_back(p_constant_name); #endif } - static void add_variant_constant(int p_type, StringName p_constant_name, const Variant &p_constant_value) { + static void add_variant_constant(int p_type, const StringName &p_constant_name, const Variant &p_constant_value) { constant_data[p_type].variant_value[p_constant_name] = p_constant_value; #ifdef DEBUG_ENABLED constant_data[p_type].variant_value_ordered.push_back(p_constant_name); @@ -1091,7 +1091,7 @@ struct _VariantCall { static EnumData *enum_data; - static void add_enum_constant(int p_type, StringName p_enum_type_name, StringName p_enumeration_name, int p_enum_value) { + static void add_enum_constant(int p_type, const StringName &p_enum_type_name, const StringName &p_enumeration_name, int p_enum_value) { enum_data[p_type].value[p_enum_type_name][p_enumeration_name] = p_enum_value; } }; @@ -1114,6 +1114,46 @@ struct VariantBuiltInMethodInfo { Variant::Type return_type; int argument_count = 0; Variant::Type (*get_argument_type)(int p_arg) = nullptr; + + MethodInfo get_method_info(const StringName &p_name) const { + MethodInfo mi; + mi.name = p_name; + + if (has_return_type) { + mi.return_val.type = return_type; + if (mi.return_val.type == Variant::NIL) { + mi.return_val.usage |= PROPERTY_USAGE_NIL_IS_VARIANT; + } + } + + if (is_const) { + mi.flags |= METHOD_FLAG_CONST; + } + if (is_vararg) { + mi.flags |= METHOD_FLAG_VARARG; + } + if (is_static) { + mi.flags |= METHOD_FLAG_STATIC; + } + + for (int i = 0; i < argument_count; i++) { + PropertyInfo pi; +#ifdef DEBUG_METHODS_ENABLED + pi.name = argument_names[i]; +#else + pi.name = "arg" + itos(i + 1); +#endif + pi.type = (*get_argument_type)(i); + if (pi.type == Variant::NIL) { + pi.usage |= PROPERTY_USAGE_NIL_IS_VARIANT; + } + mi.arguments.push_back(pi); + } + + mi.default_arguments = default_arguments; + + return mi; + } }; typedef OAHashMap<StringName, VariantBuiltInMethodInfo> BuiltinMethodMap; @@ -1268,6 +1308,13 @@ Variant::PTRBuiltInMethod Variant::get_ptr_builtin_method(Variant::Type p_type, return method->ptrcall; } +MethodInfo Variant::get_builtin_method_info(Variant::Type p_type, const StringName &p_method) { + ERR_FAIL_INDEX_V(p_type, Variant::VARIANT_MAX, MethodInfo()); + const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].lookup_ptr(p_method); + ERR_FAIL_NULL_V(method, MethodInfo()); + return method->get_method_info(p_method); +} + int Variant::get_builtin_method_argument_count(Variant::Type p_type, const StringName &p_method) { ERR_FAIL_INDEX_V(p_type, Variant::VARIANT_MAX, 0); const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].lookup_ptr(p_method); @@ -1378,43 +1425,7 @@ void Variant::get_method_list(List<MethodInfo> *p_list) const { for (const StringName &E : builtin_method_names[type]) { const VariantBuiltInMethodInfo *method = builtin_method_info[type].lookup_ptr(E); ERR_CONTINUE(!method); - - MethodInfo mi; - mi.name = E; - - //return type - if (method->has_return_type) { - mi.return_val.type = method->return_type; - if (mi.return_val.type == Variant::NIL) { - mi.return_val.usage |= PROPERTY_USAGE_NIL_IS_VARIANT; - } - } - - if (method->is_const) { - mi.flags |= METHOD_FLAG_CONST; - } - if (method->is_vararg) { - mi.flags |= METHOD_FLAG_VARARG; - } - if (method->is_static) { - mi.flags |= METHOD_FLAG_STATIC; - } - for (int i = 0; i < method->argument_count; i++) { - PropertyInfo pi; -#ifdef DEBUG_METHODS_ENABLED - pi.name = method->argument_names[i]; -#else - pi.name = "arg" + itos(i + 1); -#endif - pi.type = method->get_argument_type(i); - if (pi.type == Variant::NIL) { - pi.usage |= PROPERTY_USAGE_NIL_IS_VARIANT; - } - mi.arguments.push_back(pi); - } - - mi.default_arguments = method->default_arguments; - p_list->push_back(mi); + p_list->push_back(method->get_method_info(E)); } } } @@ -1493,7 +1504,7 @@ void Variant::get_enums_for_type(Variant::Type p_type, List<StringName> *p_enums } } -void Variant::get_enumerations_for_enum(Variant::Type p_type, StringName p_enum_name, List<StringName> *p_enumerations) { +void Variant::get_enumerations_for_enum(Variant::Type p_type, const StringName &p_enum_name, List<StringName> *p_enumerations) { ERR_FAIL_INDEX(p_type, Variant::VARIANT_MAX); _VariantCall::EnumData &enum_data = _VariantCall::enum_data[p_type]; @@ -1505,7 +1516,7 @@ void Variant::get_enumerations_for_enum(Variant::Type p_type, StringName p_enum_ } } -int Variant::get_enum_value(Variant::Type p_type, StringName p_enum_name, StringName p_enumeration, bool *r_valid) { +int Variant::get_enum_value(Variant::Type p_type, const StringName &p_enum_name, const StringName &p_enumeration, bool *r_valid) { if (r_valid) { *r_valid = false; } @@ -1796,6 +1807,8 @@ static void _register_variant_builtin_methods() { bind_method(Vector2i, aspect, sarray(), varray()); bind_method(Vector2i, max_axis_index, sarray(), varray()); bind_method(Vector2i, min_axis_index, sarray(), varray()); + bind_method(Vector2i, distance_to, sarray("to"), varray()); + bind_method(Vector2i, distance_squared_to, sarray("to"), varray()); bind_method(Vector2i, length, sarray(), varray()); bind_method(Vector2i, length_squared, sarray(), varray()); bind_method(Vector2i, sign, sarray(), varray()); @@ -1886,6 +1899,8 @@ static void _register_variant_builtin_methods() { bind_method(Vector3i, min_axis_index, sarray(), varray()); bind_method(Vector3i, max_axis_index, sarray(), varray()); + bind_method(Vector3i, distance_to, sarray("to"), varray()); + bind_method(Vector3i, distance_squared_to, sarray("to"), varray()); bind_method(Vector3i, length, sarray(), varray()); bind_method(Vector3i, length_squared, sarray(), varray()); bind_method(Vector3i, sign, sarray(), varray()); @@ -1932,6 +1947,8 @@ static void _register_variant_builtin_methods() { bind_method(Vector4i, abs, sarray(), varray()); bind_method(Vector4i, clamp, sarray("min", "max"), varray()); bind_method(Vector4i, snapped, sarray("step"), varray()); + bind_method(Vector4i, distance_to, sarray("to"), varray()); + bind_method(Vector4i, distance_squared_to, sarray("to"), varray()); /* Plane */ @@ -2195,6 +2212,7 @@ static void _register_variant_builtin_methods() { bind_method(Dictionary, values, sarray(), varray()); bind_method(Dictionary, duplicate, sarray("deep"), varray(false)); bind_method(Dictionary, get, sarray("key", "default"), varray(Variant())); + bind_method(Dictionary, get_or_add, sarray("key", "default"), varray(Variant())); bind_method(Dictionary, make_read_only, sarray(), varray()); bind_method(Dictionary, is_read_only, sarray(), varray()); diff --git a/core/variant/variant_callable.cpp b/core/variant/variant_callable.cpp new file mode 100644 index 0000000000..dc31b6d1ac --- /dev/null +++ b/core/variant/variant_callable.cpp @@ -0,0 +1,81 @@ +/**************************************************************************/ +/* variant_callable.cpp */ +/**************************************************************************/ +/* This file is part of: */ +/* GODOT ENGINE */ +/* https://godotengine.org */ +/**************************************************************************/ +/* Copyright (c) 2014-present Godot Engine contributors (see AUTHORS.md). */ +/* Copyright (c) 2007-2014 Juan Linietsky, Ariel Manzur. */ +/* */ +/* Permission is hereby granted, free of charge, to any person obtaining */ +/* a copy of this software and associated documentation files (the */ +/* "Software"), to deal in the Software without restriction, including */ +/* without limitation the rights to use, copy, modify, merge, publish, */ +/* distribute, sublicense, and/or sell copies of the Software, and to */ +/* permit persons to whom the Software is furnished to do so, subject to */ +/* the following conditions: */ +/* */ +/* The above copyright notice and this permission notice shall be */ +/* included in all copies or substantial portions of the Software. */ +/* */ +/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */ +/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */ +/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. */ +/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */ +/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */ +/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */ +/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ +/**************************************************************************/ + +#include "variant_callable.h" + +#include "core/templates/hashfuncs.h" + +bool VariantCallable::compare_equal(const CallableCustom *p_a, const CallableCustom *p_b) { + return p_a->hash() == p_b->hash(); +} + +bool VariantCallable::compare_less(const CallableCustom *p_a, const CallableCustom *p_b) { + return p_a->hash() < p_b->hash(); +} + +uint32_t VariantCallable::hash() const { + return h; +} + +String VariantCallable::get_as_text() const { + return vformat("%s::%s (Callable)", Variant::get_type_name(variant.get_type()), method); +} + +CallableCustom::CompareEqualFunc VariantCallable::get_compare_equal_func() const { + return compare_equal; +} + +CallableCustom::CompareLessFunc VariantCallable::get_compare_less_func() const { + return compare_less; +} + +bool VariantCallable::is_valid() const { + return Variant::has_builtin_method(variant.get_type(), method); +} + +StringName VariantCallable::get_method() const { + return method; +} + +ObjectID VariantCallable::get_object() const { + return ObjectID(); +} + +void VariantCallable::call(const Variant **p_arguments, int p_argcount, Variant &r_return_value, Callable::CallError &r_call_error) const { + Variant v = variant; + v.callp(method, p_arguments, p_argcount, r_return_value, r_call_error); +} + +VariantCallable::VariantCallable(const Variant &p_variant, const StringName &p_method) { + variant = p_variant; + method = p_method; + h = variant.hash(); + h = hash_murmur3_one_64(Variant::get_builtin_method_hash(variant.get_type(), method), h); +} diff --git a/core/variant/variant_callable.h b/core/variant/variant_callable.h new file mode 100644 index 0000000000..3f2b058aaf --- /dev/null +++ b/core/variant/variant_callable.h @@ -0,0 +1,58 @@ +/**************************************************************************/ +/* variant_callable.h */ +/**************************************************************************/ +/* This file is part of: */ +/* GODOT ENGINE */ +/* https://godotengine.org */ +/**************************************************************************/ +/* Copyright (c) 2014-present Godot Engine contributors (see AUTHORS.md). */ +/* Copyright (c) 2007-2014 Juan Linietsky, Ariel Manzur. */ +/* */ +/* Permission is hereby granted, free of charge, to any person obtaining */ +/* a copy of this software and associated documentation files (the */ +/* "Software"), to deal in the Software without restriction, including */ +/* without limitation the rights to use, copy, modify, merge, publish, */ +/* distribute, sublicense, and/or sell copies of the Software, and to */ +/* permit persons to whom the Software is furnished to do so, subject to */ +/* the following conditions: */ +/* */ +/* The above copyright notice and this permission notice shall be */ +/* included in all copies or substantial portions of the Software. */ +/* */ +/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */ +/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */ +/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. */ +/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */ +/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */ +/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */ +/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ +/**************************************************************************/ + +#ifndef VARIANT_CALLABLE_H +#define VARIANT_CALLABLE_H + +#include "core/variant/callable.h" +#include "core/variant/variant.h" + +class VariantCallable : public CallableCustom { + Variant variant; + StringName method; + uint32_t h = 0; + + static bool compare_equal(const CallableCustom *p_a, const CallableCustom *p_b); + static bool compare_less(const CallableCustom *p_a, const CallableCustom *p_b); + +public: + uint32_t hash() const override; + String get_as_text() const override; + CompareEqualFunc get_compare_equal_func() const override; + CompareLessFunc get_compare_less_func() const override; + bool is_valid() const override; + StringName get_method() const override; + ObjectID get_object() const override; + void call(const Variant **p_arguments, int p_argcount, Variant &r_return_value, Callable::CallError &r_call_error) const override; + + VariantCallable(const Variant &p_variant, const StringName &p_method); +}; + +#endif // VARIANT_CALLABLE_H diff --git a/core/variant/variant_internal.h b/core/variant/variant_internal.h index 116210e8de..171074188f 100644 --- a/core/variant/variant_internal.h +++ b/core/variant/variant_internal.h @@ -1302,192 +1302,192 @@ struct VariantInitializer<Object *> { }; template <class T> -struct VariantZeroAssigner { +struct VariantDefaultInitializer { }; template <> -struct VariantZeroAssigner<bool> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_bool(v) = false; } +struct VariantDefaultInitializer<bool> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_bool(v) = false; } }; template <> -struct VariantZeroAssigner<int64_t> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_int(v) = 0; } +struct VariantDefaultInitializer<int64_t> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_int(v) = 0; } }; template <> -struct VariantZeroAssigner<double> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_float(v) = 0.0; } +struct VariantDefaultInitializer<double> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_float(v) = 0.0; } }; template <> -struct VariantZeroAssigner<float> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_float(v) = 0.0; } +struct VariantDefaultInitializer<float> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_float(v) = 0.0; } }; template <> -struct VariantZeroAssigner<String> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_string(v) = String(); } +struct VariantDefaultInitializer<String> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_string(v) = String(); } }; template <> -struct VariantZeroAssigner<Vector2> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_vector2(v) = Vector2(); } +struct VariantDefaultInitializer<Vector2> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_vector2(v) = Vector2(); } }; template <> -struct VariantZeroAssigner<Vector2i> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_vector2i(v) = Vector2i(); } +struct VariantDefaultInitializer<Vector2i> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_vector2i(v) = Vector2i(); } }; template <> -struct VariantZeroAssigner<Rect2> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_rect2(v) = Rect2(); } +struct VariantDefaultInitializer<Rect2> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_rect2(v) = Rect2(); } }; template <> -struct VariantZeroAssigner<Rect2i> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_rect2i(v) = Rect2i(); } +struct VariantDefaultInitializer<Rect2i> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_rect2i(v) = Rect2i(); } }; template <> -struct VariantZeroAssigner<Vector3> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_vector3(v) = Vector3(); } +struct VariantDefaultInitializer<Vector3> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_vector3(v) = Vector3(); } }; template <> -struct VariantZeroAssigner<Vector3i> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_vector3i(v) = Vector3i(); } +struct VariantDefaultInitializer<Vector3i> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_vector3i(v) = Vector3i(); } }; template <> -struct VariantZeroAssigner<Vector4> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_vector4(v) = Vector4(); } +struct VariantDefaultInitializer<Vector4> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_vector4(v) = Vector4(); } }; template <> -struct VariantZeroAssigner<Vector4i> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_vector4i(v) = Vector4i(); } +struct VariantDefaultInitializer<Vector4i> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_vector4i(v) = Vector4i(); } }; template <> -struct VariantZeroAssigner<Transform2D> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_transform2d(v) = Transform2D(); } +struct VariantDefaultInitializer<Transform2D> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_transform2d(v) = Transform2D(); } }; template <> -struct VariantZeroAssigner<Plane> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_plane(v) = Plane(); } +struct VariantDefaultInitializer<Plane> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_plane(v) = Plane(); } }; template <> -struct VariantZeroAssigner<Quaternion> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_quaternion(v) = Quaternion(); } +struct VariantDefaultInitializer<Quaternion> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_quaternion(v) = Quaternion(); } }; template <> -struct VariantZeroAssigner<AABB> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_aabb(v) = AABB(); } +struct VariantDefaultInitializer<AABB> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_aabb(v) = AABB(); } }; template <> -struct VariantZeroAssigner<Basis> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_basis(v) = Basis(); } +struct VariantDefaultInitializer<Basis> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_basis(v) = Basis(); } }; template <> -struct VariantZeroAssigner<Transform3D> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_transform(v) = Transform3D(); } +struct VariantDefaultInitializer<Transform3D> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_transform(v) = Transform3D(); } }; template <> -struct VariantZeroAssigner<Projection> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_projection(v) = Projection(); } +struct VariantDefaultInitializer<Projection> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_projection(v) = Projection(); } }; template <> -struct VariantZeroAssigner<Color> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_color(v) = Color(); } +struct VariantDefaultInitializer<Color> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_color(v) = Color(); } }; template <> -struct VariantZeroAssigner<StringName> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_string_name(v) = StringName(); } +struct VariantDefaultInitializer<StringName> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_string_name(v) = StringName(); } }; template <> -struct VariantZeroAssigner<NodePath> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_node_path(v) = NodePath(); } +struct VariantDefaultInitializer<NodePath> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_node_path(v) = NodePath(); } }; template <> -struct VariantZeroAssigner<::RID> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_rid(v) = RID(); } +struct VariantDefaultInitializer<::RID> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_rid(v) = RID(); } }; template <> -struct VariantZeroAssigner<Callable> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_callable(v) = Callable(); } +struct VariantDefaultInitializer<Callable> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_callable(v) = Callable(); } }; template <> -struct VariantZeroAssigner<Signal> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_signal(v) = Signal(); } +struct VariantDefaultInitializer<Signal> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_signal(v) = Signal(); } }; template <> -struct VariantZeroAssigner<Dictionary> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_dictionary(v) = Dictionary(); } +struct VariantDefaultInitializer<Dictionary> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_dictionary(v) = Dictionary(); } }; template <> -struct VariantZeroAssigner<Array> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_array(v) = Array(); } +struct VariantDefaultInitializer<Array> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_array(v) = Array(); } }; template <> -struct VariantZeroAssigner<PackedByteArray> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_byte_array(v) = PackedByteArray(); } +struct VariantDefaultInitializer<PackedByteArray> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_byte_array(v) = PackedByteArray(); } }; template <> -struct VariantZeroAssigner<PackedInt32Array> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_int32_array(v) = PackedInt32Array(); } +struct VariantDefaultInitializer<PackedInt32Array> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_int32_array(v) = PackedInt32Array(); } }; template <> -struct VariantZeroAssigner<PackedInt64Array> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_int64_array(v) = PackedInt64Array(); } +struct VariantDefaultInitializer<PackedInt64Array> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_int64_array(v) = PackedInt64Array(); } }; template <> -struct VariantZeroAssigner<PackedFloat32Array> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_float32_array(v) = PackedFloat32Array(); } +struct VariantDefaultInitializer<PackedFloat32Array> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_float32_array(v) = PackedFloat32Array(); } }; template <> -struct VariantZeroAssigner<PackedFloat64Array> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_float64_array(v) = PackedFloat64Array(); } +struct VariantDefaultInitializer<PackedFloat64Array> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_float64_array(v) = PackedFloat64Array(); } }; template <> -struct VariantZeroAssigner<PackedStringArray> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_string_array(v) = PackedStringArray(); } +struct VariantDefaultInitializer<PackedStringArray> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_string_array(v) = PackedStringArray(); } }; template <> -struct VariantZeroAssigner<PackedVector2Array> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_vector2_array(v) = PackedVector2Array(); } +struct VariantDefaultInitializer<PackedVector2Array> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_vector2_array(v) = PackedVector2Array(); } }; template <> -struct VariantZeroAssigner<PackedVector3Array> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_vector3_array(v) = PackedVector3Array(); } +struct VariantDefaultInitializer<PackedVector3Array> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_vector3_array(v) = PackedVector3Array(); } }; template <> -struct VariantZeroAssigner<PackedColorArray> { - static _FORCE_INLINE_ void zero(Variant *v) { *VariantInternal::get_color_array(v) = PackedColorArray(); } +struct VariantDefaultInitializer<PackedColorArray> { + static _FORCE_INLINE_ void init(Variant *v) { *VariantInternal::get_color_array(v) = PackedColorArray(); } }; template <class T> @@ -1504,7 +1504,7 @@ struct VariantTypeChanger { VariantInitializer<T>::init(v); } - VariantZeroAssigner<T>::zero(v); + VariantDefaultInitializer<T>::init(v); } }; diff --git a/core/variant/variant_op.cpp b/core/variant/variant_op.cpp index aed83ac010..4f9c38dc4c 100644 --- a/core/variant/variant_op.cpp +++ b/core/variant/variant_op.cpp @@ -412,6 +412,15 @@ void Variant::_register_variant_operators() { register_op<OperatorEvaluatorDivNZ<Vector4, Vector4i, double>>(Variant::OP_DIVIDE, Variant::VECTOR4I, Variant::FLOAT); register_op<OperatorEvaluatorDivNZ<Vector4i, Vector4i, int64_t>>(Variant::OP_DIVIDE, Variant::VECTOR4I, Variant::INT); + register_op<OperatorEvaluatorDiv<Transform2D, Transform2D, int64_t>>(Variant::OP_DIVIDE, Variant::TRANSFORM2D, Variant::INT); + register_op<OperatorEvaluatorDiv<Transform2D, Transform2D, double>>(Variant::OP_DIVIDE, Variant::TRANSFORM2D, Variant::FLOAT); + + register_op<OperatorEvaluatorDiv<Transform3D, Transform3D, int64_t>>(Variant::OP_DIVIDE, Variant::TRANSFORM3D, Variant::INT); + register_op<OperatorEvaluatorDiv<Transform3D, Transform3D, double>>(Variant::OP_DIVIDE, Variant::TRANSFORM3D, Variant::FLOAT); + + register_op<OperatorEvaluatorDiv<Basis, Basis, int64_t>>(Variant::OP_DIVIDE, Variant::BASIS, Variant::INT); + register_op<OperatorEvaluatorDiv<Basis, Basis, double>>(Variant::OP_DIVIDE, Variant::BASIS, Variant::FLOAT); + register_op<OperatorEvaluatorDiv<Quaternion, Quaternion, double>>(Variant::OP_DIVIDE, Variant::QUATERNION, Variant::FLOAT); register_op<OperatorEvaluatorDiv<Quaternion, Quaternion, int64_t>>(Variant::OP_DIVIDE, Variant::QUATERNION, Variant::INT); diff --git a/core/variant/variant_op.h b/core/variant/variant_op.h index 9e6367ab6d..17ad126891 100644 --- a/core/variant/variant_op.h +++ b/core/variant/variant_op.h @@ -549,14 +549,14 @@ public: class OperatorEvaluatorEqualObject { public: static void evaluate(const Variant &p_left, const Variant &p_right, Variant *r_ret, bool &r_valid) { - const Object *a = p_left.get_validated_object(); - const Object *b = p_right.get_validated_object(); + const ObjectID &a = VariantInternal::get_object_id(&p_left); + const ObjectID &b = VariantInternal::get_object_id(&p_right); *r_ret = a == b; r_valid = true; } static inline void validated_evaluate(const Variant *left, const Variant *right, Variant *r_ret) { - const Object *a = left->get_validated_object(); - const Object *b = right->get_validated_object(); + const ObjectID &a = VariantInternal::get_object_id(left); + const ObjectID &b = VariantInternal::get_object_id(right); *VariantGetInternalPtr<bool>::get_ptr(r_ret) = a == b; } static void ptr_evaluate(const void *left, const void *right, void *r_ret) { @@ -568,12 +568,12 @@ public: class OperatorEvaluatorEqualObjectNil { public: static void evaluate(const Variant &p_left, const Variant &p_right, Variant *r_ret, bool &r_valid) { - const Object *a = p_left.get_validated_object(); + const Object *a = p_left.operator Object *(); *r_ret = a == nullptr; r_valid = true; } static inline void validated_evaluate(const Variant *left, const Variant *right, Variant *r_ret) { - const Object *a = left->get_validated_object(); + const Object *a = left->operator Object *(); *VariantGetInternalPtr<bool>::get_ptr(r_ret) = a == nullptr; } static void ptr_evaluate(const void *left, const void *right, void *r_ret) { @@ -585,12 +585,12 @@ public: class OperatorEvaluatorEqualNilObject { public: static void evaluate(const Variant &p_left, const Variant &p_right, Variant *r_ret, bool &r_valid) { - const Object *b = p_right.get_validated_object(); + const Object *b = p_right.operator Object *(); *r_ret = nullptr == b; r_valid = true; } static inline void validated_evaluate(const Variant *left, const Variant *right, Variant *r_ret) { - const Object *b = right->get_validated_object(); + const Object *b = right->operator Object *(); *VariantGetInternalPtr<bool>::get_ptr(r_ret) = nullptr == b; } static void ptr_evaluate(const void *left, const void *right, void *r_ret) { @@ -620,14 +620,14 @@ public: class OperatorEvaluatorNotEqualObject { public: static void evaluate(const Variant &p_left, const Variant &p_right, Variant *r_ret, bool &r_valid) { - Object *a = p_left.get_validated_object(); - Object *b = p_right.get_validated_object(); + const ObjectID &a = VariantInternal::get_object_id(&p_left); + const ObjectID &b = VariantInternal::get_object_id(&p_right); *r_ret = a != b; r_valid = true; } static inline void validated_evaluate(const Variant *left, const Variant *right, Variant *r_ret) { - Object *a = left->get_validated_object(); - Object *b = right->get_validated_object(); + const ObjectID &a = VariantInternal::get_object_id(left); + const ObjectID &b = VariantInternal::get_object_id(right); *VariantGetInternalPtr<bool>::get_ptr(r_ret) = a != b; } static void ptr_evaluate(const void *left, const void *right, void *r_ret) { @@ -639,12 +639,12 @@ public: class OperatorEvaluatorNotEqualObjectNil { public: static void evaluate(const Variant &p_left, const Variant &p_right, Variant *r_ret, bool &r_valid) { - Object *a = p_left.get_validated_object(); + Object *a = p_left.operator Object *(); *r_ret = a != nullptr; r_valid = true; } static inline void validated_evaluate(const Variant *left, const Variant *right, Variant *r_ret) { - Object *a = left->get_validated_object(); + Object *a = left->operator Object *(); *VariantGetInternalPtr<bool>::get_ptr(r_ret) = a != nullptr; } static void ptr_evaluate(const void *left, const void *right, void *r_ret) { @@ -656,12 +656,12 @@ public: class OperatorEvaluatorNotEqualNilObject { public: static void evaluate(const Variant &p_left, const Variant &p_right, Variant *r_ret, bool &r_valid) { - Object *b = p_right.get_validated_object(); + Object *b = p_right.operator Object *(); *r_ret = nullptr != b; r_valid = true; } static inline void validated_evaluate(const Variant *left, const Variant *right, Variant *r_ret) { - Object *b = right->get_validated_object(); + Object *b = right->operator Object *(); *VariantGetInternalPtr<bool>::get_ptr(r_ret) = nullptr != b; } static void ptr_evaluate(const void *left, const void *right, void *r_ret) { diff --git a/core/variant/variant_parser.cpp b/core/variant/variant_parser.cpp index 86e7654090..e35751fd61 100644 --- a/core/variant/variant_parser.cpp +++ b/core/variant/variant_parser.cpp @@ -1026,7 +1026,10 @@ Error VariantParser::parse_value(Token &token, Variant &value, Stream *p_stream, Ref<Resource> res; Error err = p_res_parser->ext_func(p_res_parser->userdata, p_stream, res, line, r_err_str); if (err) { - return err; + // If the file is missing, the error can be ignored. + if (err != ERR_FILE_NOT_FOUND && err != ERR_CANT_OPEN) { + return err; + } } value = res; diff --git a/core/variant/variant_setget.cpp b/core/variant/variant_setget.cpp index 05f7abf32c..50c9c10987 100644 --- a/core/variant/variant_setget.cpp +++ b/core/variant/variant_setget.cpp @@ -30,6 +30,8 @@ #include "variant_setget.h" +#include "variant_callable.h" + struct VariantSetterGetterInfo { void (*setter)(Variant *base, const Variant *value, bool &valid); void (*getter)(const Variant *base, Variant *value); @@ -264,42 +266,45 @@ void Variant::set_named(const StringName &p_member, const Variant &p_value, bool } Variant Variant::get_named(const StringName &p_member, bool &r_valid) const { - Variant ret; uint32_t s = variant_setters_getters[type].size(); if (s) { for (uint32_t i = 0; i < s; i++) { if (variant_setters_getters_names[type][i] == p_member) { + Variant ret; variant_setters_getters[type][i].getter(this, &ret); r_valid = true; return ret; } } + } - r_valid = false; - - } else if (type == Variant::OBJECT) { - Object *obj = get_validated_object(); - if (!obj) { - r_valid = false; - return "Instance base is null."; - } else { - return obj->get(p_member, &r_valid); - } - } else if (type == Variant::DICTIONARY) { - const Variant *v = VariantGetInternalPtr<Dictionary>::get_ptr(this)->getptr(p_member); - if (v) { - r_valid = true; - - return *v; - } else { - r_valid = false; - } - - } else { - r_valid = false; + switch (type) { + case Variant::OBJECT: { + Object *obj = get_validated_object(); + if (!obj) { + r_valid = false; + return "Instance base is null."; + } else { + return obj->get(p_member, &r_valid); + } + } break; + case Variant::DICTIONARY: { + const Variant *v = VariantGetInternalPtr<Dictionary>::get_ptr(this)->getptr(p_member); + if (v) { + r_valid = true; + return *v; + } + } break; + default: { + if (Variant::has_builtin_method(type, p_member)) { + r_valid = true; + return Callable(memnew(VariantCallable(*this, p_member))); + } + } break; } - return ret; + r_valid = false; + return Variant(); } /**** INDEXED SETTERS AND GETTERS ****/ @@ -1166,30 +1171,48 @@ bool Variant::has_key(const Variant &p_key, bool &r_valid) const { } } -void Variant::set(const Variant &p_index, const Variant &p_value, bool *r_valid) { +void Variant::set(const Variant &p_index, const Variant &p_value, bool *r_valid, VariantSetError *err_code) { + if (err_code) { + *err_code = VariantSetError::SET_OK; + } if (type == DICTIONARY || type == OBJECT) { bool valid; set_keyed(p_index, p_value, valid); if (r_valid) { *r_valid = valid; + if (!valid && err_code) { + *err_code = VariantSetError::SET_KEYED_ERR; + } } } else { bool valid = false; if (p_index.get_type() == STRING_NAME) { set_named(*VariantGetInternalPtr<StringName>::get_ptr(&p_index), p_value, valid); + if (!valid && err_code) { + *err_code = VariantSetError::SET_NAMED_ERR; + } } else if (p_index.get_type() == INT) { bool obb; set_indexed(*VariantGetInternalPtr<int64_t>::get_ptr(&p_index), p_value, valid, obb); if (obb) { valid = false; + if (err_code) { + *err_code = VariantSetError::SET_INDEXED_ERR; + } } } else if (p_index.get_type() == STRING) { // less efficient version of named set_named(*VariantGetInternalPtr<String>::get_ptr(&p_index), p_value, valid); + if (!valid && err_code) { + *err_code = VariantSetError::SET_NAMED_ERR; + } } else if (p_index.get_type() == FLOAT) { // less efficient version of indexed bool obb; set_indexed(*VariantGetInternalPtr<double>::get_ptr(&p_index), p_value, valid, obb); if (obb) { valid = false; + if (err_code) { + *err_code = VariantSetError::SET_INDEXED_ERR; + } } } if (r_valid) { @@ -1198,31 +1221,49 @@ void Variant::set(const Variant &p_index, const Variant &p_value, bool *r_valid) } } -Variant Variant::get(const Variant &p_index, bool *r_valid) const { +Variant Variant::get(const Variant &p_index, bool *r_valid, VariantGetError *err_code) const { + if (err_code) { + *err_code = VariantGetError::GET_OK; + } Variant ret; if (type == DICTIONARY || type == OBJECT) { bool valid; ret = get_keyed(p_index, valid); if (r_valid) { *r_valid = valid; + if (!valid && err_code) { + *err_code = VariantGetError::GET_KEYED_ERR; + } } } else { bool valid = false; if (p_index.get_type() == STRING_NAME) { ret = get_named(*VariantGetInternalPtr<StringName>::get_ptr(&p_index), valid); + if (!valid && err_code) { + *err_code = VariantGetError::GET_NAMED_ERR; + } } else if (p_index.get_type() == INT) { bool obb; ret = get_indexed(*VariantGetInternalPtr<int64_t>::get_ptr(&p_index), valid, obb); if (obb) { valid = false; + if (err_code) { + *err_code = VariantGetError::GET_INDEXED_ERR; + } } } else if (p_index.get_type() == STRING) { // less efficient version of named ret = get_named(*VariantGetInternalPtr<String>::get_ptr(&p_index), valid); + if (!valid && err_code) { + *err_code = VariantGetError::GET_NAMED_ERR; + } } else if (p_index.get_type() == FLOAT) { // less efficient version of indexed bool obb; ret = get_indexed(*VariantGetInternalPtr<double>::get_ptr(&p_index), valid, obb); if (obb) { valid = false; + if (err_code) { + *err_code = VariantGetError::GET_INDEXED_ERR; + } } } if (r_valid) { |