diff options
Diffstat (limited to 'core')
45 files changed, 309 insertions, 309 deletions
diff --git a/core/SCsub b/core/SCsub index af83b49fea..383aaf0e12 100644 --- a/core/SCsub +++ b/core/SCsub @@ -18,9 +18,8 @@ gd_cpp = '#include "project_settings.h"\n' gd_cpp += gd_inc gd_cpp += "void ProjectSettings::register_global_defaults() {\n" + gd_call + "\n}\n" -f = open("global_defaults.gen.cpp", "w") -f.write(gd_cpp) -f.close() +with open("global_defaults.gen.cpp", "w") as f: + f.write(gd_cpp) # Generate AES256 script encryption key @@ -47,9 +46,8 @@ if ("SCRIPT_AES256_ENCRYPTION_KEY" in os.environ): txt = "0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0" print("Invalid AES256 encryption key, not 64 bits hex: " + e) -f = open("script_encryption_key.gen.cpp", "w") -f.write("#include \"project_settings.h\"\nuint8_t script_encryption_key[32]={" + txt + "};\n") -f.close() +with open("script_encryption_key.gen.cpp", "w") as f: + f.write("#include \"project_settings.h\"\nuint8_t script_encryption_key[32]={" + txt + "};\n") # Add required thirdparty code. Header paths are hardcoded, we don't need to append @@ -68,7 +66,6 @@ thirdparty_sources = [ "md5.cpp", "pcg.cpp", "triangulator.cpp", - "clipper.cpp", ] thirdparty_sources = [thirdparty_dir + file for file in thirdparty_sources] env.add_source_files(env.core_sources, thirdparty_sources) diff --git a/core/array.cpp b/core/array.cpp index 0ddac1662c..9e3250fd47 100644 --- a/core/array.cpp +++ b/core/array.cpp @@ -35,8 +35,8 @@ #include "variant.h" #include "vector.h" -struct ArrayPrivate { - +class ArrayPrivate { +public: SafeRefCount refcount; Vector<Variant> array; }; @@ -211,13 +211,13 @@ const Variant &Array::get(int p_idx) const { return operator[](p_idx); } -Array Array::duplicate() const { +Array Array::duplicate(bool p_deep) const { Array new_arr; int element_count = size(); new_arr.resize(element_count); for (int i = 0; i < element_count; i++) { - new_arr[i] = get(i); + new_arr[i] = p_deep ? get(i).duplicate(p_deep) : get(i); } return new_arr; diff --git a/core/array.h b/core/array.h index 684a8e265d..e549a886e6 100644 --- a/core/array.h +++ b/core/array.h @@ -88,7 +88,7 @@ public: Variant pop_back(); Variant pop_front(); - Array duplicate() const; + Array duplicate(bool p_deep = false) const; Array(const Array &p_from); Array(); diff --git a/core/bind/core_bind.cpp b/core/bind/core_bind.cpp index b57b24ee7d..20adf7ff02 100644 --- a/core/bind/core_bind.cpp +++ b/core/bind/core_bind.cpp @@ -205,6 +205,22 @@ String _OS::get_clipboard() const { return OS::get_singleton()->get_clipboard(); } +int _OS::get_video_driver_count() const { + return OS::get_singleton()->get_video_driver_count(); +} + +String _OS::get_video_driver_name(int p_driver) const { + return OS::get_singleton()->get_video_driver_name(p_driver); +} + +int _OS::get_audio_driver_count() const { + return OS::get_singleton()->get_audio_driver_count(); +} + +String _OS::get_audio_driver_name(int p_driver) const { + return OS::get_singleton()->get_audio_driver_name(p_driver); +} + void _OS::set_video_mode(const Size2 &p_size, bool p_fullscreen, bool p_resizeable, int p_screen) { OS::VideoMode vm; @@ -1015,6 +1031,11 @@ void _OS::_bind_methods() { //ClassDB::bind_method(D_METHOD("is_video_mode_resizable","screen"),&_OS::is_video_mode_resizable,DEFVAL(0)); //ClassDB::bind_method(D_METHOD("get_fullscreen_mode_list","screen"),&_OS::get_fullscreen_mode_list,DEFVAL(0)); + ClassDB::bind_method(D_METHOD("get_video_driver_count"), &_OS::get_video_driver_count); + ClassDB::bind_method(D_METHOD("get_video_driver_name"), &_OS::get_video_driver_name); + ClassDB::bind_method(D_METHOD("get_audio_driver_count"), &_OS::get_audio_driver_count); + ClassDB::bind_method(D_METHOD("get_audio_driver_name"), &_OS::get_audio_driver_name); + ClassDB::bind_method(D_METHOD("get_screen_count"), &_OS::get_screen_count); ClassDB::bind_method(D_METHOD("get_current_screen"), &_OS::get_current_screen); ClassDB::bind_method(D_METHOD("set_current_screen", "screen"), &_OS::set_current_screen); @@ -1514,6 +1535,17 @@ bool _File::is_open() const { return f != NULL; } +String _File::get_path() const { + + ERR_FAIL_COND_V(!f, ""); + return f->get_path(); +} + +String _File::get_path_absolute() const { + + ERR_FAIL_COND_V(!f, ""); + return f->get_path_absolute(); +} void _File::seek(int64_t p_position) { @@ -1803,6 +1835,8 @@ void _File::_bind_methods() { ClassDB::bind_method(D_METHOD("open", "path", "flags"), &_File::open); ClassDB::bind_method(D_METHOD("close"), &_File::close); + ClassDB::bind_method(D_METHOD("get_path"), &_File::get_path); + ClassDB::bind_method(D_METHOD("get_path_absolute"), &_File::get_path_absolute); ClassDB::bind_method(D_METHOD("is_open"), &_File::is_open); ClassDB::bind_method(D_METHOD("seek", "position"), &_File::seek); ClassDB::bind_method(D_METHOD("seek_end", "position"), &_File::seek_end, DEFVAL(0)); diff --git a/core/bind/core_bind.h b/core/bind/core_bind.h index 734b57937a..c40abd51f6 100644 --- a/core/bind/core_bind.h +++ b/core/bind/core_bind.h @@ -146,6 +146,12 @@ public: bool is_video_mode_resizable(int p_screen = 0) const; Array get_fullscreen_mode_list(int p_screen = 0) const; + virtual int get_video_driver_count() const; + virtual String get_video_driver_name(int p_driver) const; + + virtual int get_audio_driver_count() const; + virtual String get_audio_driver_name(int p_driver) const; + virtual int get_screen_count() const; virtual int get_current_screen() const; virtual void set_current_screen(int p_screen); @@ -409,6 +415,9 @@ public: void close(); ///< close a file bool is_open() const; ///< true when file is open + String get_path() const; /// returns the path for the current open file + String get_path_absolute() const; /// returns the absolute path for the current open file + void seek(int64_t p_position); ///< seek to a given position void seek_end(int64_t p_position = 0); ///< seek from the end of file int64_t get_position() const; ///< get position in the file diff --git a/core/class_db.cpp b/core/class_db.cpp index 3c9dae1acb..92aa131e2d 100644 --- a/core/class_db.cpp +++ b/core/class_db.cpp @@ -33,18 +33,9 @@ #include "os/mutex.h" #include "version.h" -#ifdef NO_THREADS - -#define OBJTYPE_RLOCK -#define OBJTYPE_WLOCK - -#else - #define OBJTYPE_RLOCK RWLockRead _rw_lockr_(lock); #define OBJTYPE_WLOCK RWLockWrite _rw_lockw_(lock); -#endif - #ifdef DEBUG_METHODS_ENABLED MethodDefinition D_METHOD(const char *p_name) { @@ -660,7 +651,6 @@ void ClassDB::bind_integer_constant(const StringName &p_class, const StringName } type->constant_map[p_name] = p_constant; -#ifdef DEBUG_METHODS_ENABLED String enum_name = p_enum; if (enum_name != String()) { @@ -679,6 +669,7 @@ void ClassDB::bind_integer_constant(const StringName &p_class, const StringName } } +#ifdef DEBUG_METHODS_ENABLED type->constant_order.push_back(p_name); #endif } @@ -734,7 +725,6 @@ int ClassDB::get_integer_constant(const StringName &p_class, const StringName &p return 0; } -#ifdef DEBUG_METHODS_ENABLED StringName ClassDB::get_integer_constant_enum(const StringName &p_class, const StringName &p_name, bool p_no_inheritance) { OBJTYPE_RLOCK; @@ -803,7 +793,6 @@ void ClassDB::get_enum_constants(const StringName &p_class, const StringName &p_ type = type->inherits_ptr; } } -#endif void ClassDB::add_signal(StringName p_class, const MethodInfo &p_signal) { @@ -895,15 +884,9 @@ void ClassDB::add_property_group(StringName p_class, const String &p_name, const void ClassDB::add_property(StringName p_class, const PropertyInfo &p_pinfo, const StringName &p_setter, const StringName &p_getter, int p_index) { -#ifndef NO_THREADS lock->read_lock(); -#endif - ClassInfo *type = classes.getptr(p_class); - -#ifndef NO_THREADS lock->read_unlock(); -#endif ERR_FAIL_COND(!type); @@ -1380,10 +1363,7 @@ RWLock *ClassDB::lock = NULL; void ClassDB::init() { -#ifndef NO_THREADS - lock = RWLock::create(); -#endif } void ClassDB::cleanup() { @@ -1406,10 +1386,7 @@ void ClassDB::cleanup() { resource_base_extensions.clear(); compat_classes.clear(); -#ifndef NO_THREADS - memdelete(lock); -#endif } // diff --git a/core/class_db.h b/core/class_db.h index d74317239b..2c77ffe65f 100644 --- a/core/class_db.h +++ b/core/class_db.h @@ -116,10 +116,10 @@ public: ClassInfo *inherits_ptr; HashMap<StringName, MethodBind *, StringNameHasher> method_map; HashMap<StringName, int, StringNameHasher> constant_map; + HashMap<StringName, List<StringName> > enum_map; HashMap<StringName, MethodInfo, StringNameHasher> signal_map; List<PropertyInfo> property_list; #ifdef DEBUG_METHODS_ENABLED - HashMap<StringName, List<StringName> > enum_map; List<StringName> constant_order; List<StringName> method_order; Set<StringName> methods_in_properties; @@ -344,11 +344,9 @@ public: static void get_integer_constant_list(const StringName &p_class, List<String> *p_constants, bool p_no_inheritance = false); static int get_integer_constant(const StringName &p_class, const StringName &p_name, bool *p_success = NULL); -#ifdef DEBUG_METHODS_ENABLED static StringName get_integer_constant_enum(const StringName &p_class, const StringName &p_name, bool p_no_inheritance = false); static void get_enum_list(const StringName &p_class, List<StringName> *p_enums, bool p_no_inheritance = false); static void get_enum_constants(const StringName &p_class, const StringName &p_enum, List<StringName> *p_constants, bool p_no_inheritance = false); -#endif static StringName get_category(const StringName &p_node); diff --git a/core/color.cpp b/core/color.cpp index 27d8e9b891..b2f5889166 100644 --- a/core/color.cpp +++ b/core/color.cpp @@ -402,6 +402,10 @@ String Color::to_html(bool p_alpha) const { Color Color::from_hsv(float p_h, float p_s, float p_v, float p_a) { + p_h = Math::fmod(p_h * 360.0f, 360.0f); + if (p_h < 0.0) + p_h += 360.0f; + const float h_ = p_h / 60.0f; const float c = p_v * p_s; const float x = c * (1.0f - Math::abs(Math::fmod(h_, 2.0f) - 1.0f)); diff --git a/core/command_queue_mt.cpp b/core/command_queue_mt.cpp index 6bb3135757..a39c920dfa 100644 --- a/core/command_queue_mt.cpp +++ b/core/command_queue_mt.cpp @@ -105,6 +105,7 @@ CommandQueueMT::CommandQueueMT(bool p_sync) { read_ptr = 0; write_ptr = 0; + dealloc_ptr = 0; mutex = Mutex::create(); for (int i = 0; i < SYNC_SEMAPHORES; i++) { diff --git a/core/command_queue_mt.h b/core/command_queue_mt.h index c1439bdc4c..3942b961d3 100644 --- a/core/command_queue_mt.h +++ b/core/command_queue_mt.h @@ -309,9 +309,9 @@ class CommandQueueMT { }; uint8_t command_mem[COMMAND_MEM_SIZE]; - uint32_t read_ptr = 0; - uint32_t write_ptr = 0; - uint32_t dealloc_ptr = 0; + uint32_t read_ptr; + uint32_t write_ptr; + uint32_t dealloc_ptr; SyncSemaphore sync_sems[SYNC_SEMAPHORES]; Mutex *mutex; Semaphore *sync; diff --git a/core/dictionary.cpp b/core/dictionary.cpp index e3f4aa5f28..ba0de95861 100644 --- a/core/dictionary.cpp +++ b/core/dictionary.cpp @@ -211,7 +211,7 @@ const Variant *Dictionary::next(const Variant *p_key) const { return NULL; } -Dictionary Dictionary::duplicate() const { +Dictionary Dictionary::duplicate(bool p_deep) const { Dictionary n; @@ -219,7 +219,7 @@ Dictionary Dictionary::duplicate() const { get_key_list(&keys); for (List<Variant>::Element *E = keys.front(); E; E = E->next()) { - n[E->get()] = operator[](E->get()); + n[E->get()] = p_deep ? operator[](E->get()).duplicate(p_deep) : operator[](E->get()); } return n; diff --git a/core/dictionary.h b/core/dictionary.h index f001f2d5e1..9eef265d5b 100644 --- a/core/dictionary.h +++ b/core/dictionary.h @@ -75,7 +75,7 @@ public: Array keys() const; Array values() const; - Dictionary duplicate() const; + Dictionary duplicate(bool p_deep = false) const; Dictionary(const Dictionary &p_from); Dictionary(); diff --git a/core/input_map.cpp b/core/input_map.cpp index a9ea1d9545..ea724d2595 100644 --- a/core/input_map.cpp +++ b/core/input_map.cpp @@ -35,6 +35,8 @@ InputMap *InputMap::singleton = NULL; +int InputMap::ALL_DEVICES = -1; + void InputMap::_bind_methods() { ClassDB::bind_method(D_METHOD("has_action", "action"), &InputMap::has_action); @@ -103,10 +105,10 @@ List<Ref<InputEvent> >::Element *InputMap::_find_event(List<Ref<InputEvent> > &p //if (e.type != Ref<InputEvent>::KEY && e.device != p_event.device) -- unsure about the KEY comparison, why is this here? // continue; - if (e->get_device() != p_event->get_device()) - continue; - if (e->action_match(p_event)) - return E; + int device = e->get_device(); + if (device == ALL_DEVICES || device == p_event->get_device()) + if (e->action_match(p_event)) + return E; } return NULL; @@ -282,6 +284,16 @@ void InputMap::load_default() { key->set_scancode(KEY_PAGEDOWN); action_add_event("ui_page_down", key); + add_action("ui_home"); + key.instance(); + key->set_scancode(KEY_HOME); + action_add_event("ui_home", key); + + add_action("ui_end"); + key.instance(); + key->set_scancode(KEY_END); + action_add_event("ui_end", key); + //set("display/window/handheld/orientation", "landscape"); } diff --git a/core/input_map.h b/core/input_map.h index 84d90f6f2a..9f3c13c2cf 100644 --- a/core/input_map.h +++ b/core/input_map.h @@ -39,6 +39,11 @@ class InputMap : public Object { GDCLASS(InputMap, Object); public: + /** + * A special value used to signify that a given Action can be triggered by any device + */ + static int ALL_DEVICES; + struct Action { int id; List<Ref<InputEvent> > inputs; diff --git a/core/io/file_access_pack.cpp b/core/io/file_access_pack.cpp index 1a16d0f61c..efb4c7a073 100644 --- a/core/io/file_access_pack.cpp +++ b/core/io/file_access_pack.cpp @@ -88,7 +88,11 @@ void PackedData::add_path(const String &pkg_path, const String &path, uint64_t o } } } - cd->files.insert(path.get_file()); + String filename = path.get_file(); + // Don't add as a file if the path points to a directoryy + if (!filename.empty()) { + cd->files.insert(filename); + } } } diff --git a/core/io/http_client.cpp b/core/io/http_client.cpp index a9eb9466b7..c787b7ec4c 100644 --- a/core/io/http_client.cpp +++ b/core/io/http_client.cpp @@ -298,7 +298,7 @@ Error HTTPClient::poll() { case StreamPeerTCP::STATUS_CONNECTED: { if (ssl) { Ref<StreamPeerSSL> ssl = StreamPeerSSL::create(); - Error err = ssl->connect_to_stream(tcp_connection, ssl_verify_host, ssl_verify_host ? conn_host : String()); + Error err = ssl->connect_to_stream(tcp_connection, ssl_verify_host, conn_host); if (err != OK) { close(); status = STATUS_SSL_HANDSHAKE_ERROR; @@ -618,7 +618,27 @@ String HTTPClient::query_string_from_dict(const Dictionary &p_dict) { String query = ""; Array keys = p_dict.keys(); for (int i = 0; i < keys.size(); ++i) { - query += "&" + String(keys[i]).http_escape() + "=" + String(p_dict[keys[i]]).http_escape(); + String encoded_key = String(keys[i]).percent_encode(); + Variant value = p_dict[keys[i]]; + switch (value.get_type()) { + case Variant::ARRAY: { + // Repeat the key with every values + Array values = value; + for (int j = 0; j < values.size(); ++j) { + query += "&" + encoded_key + "=" + String(values[j]).percent_encode(); + } + break; + } + case Variant::NIL: { + // Add the key with no value + query += "&" + encoded_key; + break; + } + default: { + // Add the key-value pair + query += "&" + encoded_key + "=" + String(value).percent_encode(); + } + } } query.erase(0, 1); return query; diff --git a/core/io/marshalls.cpp b/core/io/marshalls.cpp index 9e21287780..2ebe8d6df7 100644 --- a/core/io/marshalls.cpp +++ b/core/io/marshalls.cpp @@ -813,7 +813,7 @@ static void _encode_string(const String &p_string, uint8_t *&buf, int &r_len) { while (r_len % 4) { r_len++; //pad if (buf) { - buf++; + *(buf++) = 0; } } } diff --git a/core/io/resource_format_binary.cpp b/core/io/resource_format_binary.cpp index 5dfe067902..0c626c197b 100644 --- a/core/io/resource_format_binary.cpp +++ b/core/io/resource_format_binary.cpp @@ -1162,9 +1162,11 @@ Error ResourceFormatLoaderBinary::rename_dependencies(const String &p_path, cons ERR_FAIL_V(ERR_FILE_UNRECOGNIZED); } - fw->store_32(VERSION_MAJOR); //current version - fw->store_32(VERSION_MINOR); - fw->store_32(FORMAT_VERSION); + // Since we're not actually converting the file contents, leave the version + // numbers in the file untouched. + fw->store_32(ver_major); + fw->store_32(ver_minor); + fw->store_32(ver_format); save_ustring(fw, get_ustring(f)); //type diff --git a/core/io/stream_peer_ssl.cpp b/core/io/stream_peer_ssl.cpp index 07a01ff99f..012ba78c6d 100644 --- a/core/io/stream_peer_ssl.cpp +++ b/core/io/stream_peer_ssl.cpp @@ -29,6 +29,8 @@ /*************************************************************************/ #include "stream_peer_ssl.h" +#include "os/file_access.h" +#include "project_settings.h" StreamPeerSSL *(*StreamPeerSSL::_create)() = NULL; @@ -50,6 +52,35 @@ bool StreamPeerSSL::is_available() { return available; } +PoolByteArray StreamPeerSSL::get_project_cert_array() { + + PoolByteArray out; + String certs_path = GLOBAL_DEF("network/ssl/certificates", ""); + ProjectSettings::get_singleton()->set_custom_property_info("network/ssl/certificates", PropertyInfo(Variant::STRING, "network/ssl/certificates", PROPERTY_HINT_FILE, "*.crt")); + + if (certs_path != "") { + + FileAccess *f = FileAccess::open(certs_path, FileAccess::READ); + if (f) { + int flen = f->get_len(); + out.resize(flen + 1); + { + PoolByteArray::Write w = out.write(); + f->get_buffer(w.ptr(), flen); + w[flen] = 0; //end f string + } + + memdelete(f); + +#ifdef DEBUG_ENABLED + print_line("Loaded certs from '" + certs_path); +#endif + } + } + + return out; +} + void StreamPeerSSL::_bind_methods() { ClassDB::bind_method(D_METHOD("poll"), &StreamPeerSSL::poll); diff --git a/core/io/stream_peer_ssl.h b/core/io/stream_peer_ssl.h index f903438c28..77301a7c87 100644 --- a/core/io/stream_peer_ssl.h +++ b/core/io/stream_peer_ssl.h @@ -66,6 +66,7 @@ public: static StreamPeerSSL *create(); + static PoolByteArray get_project_cert_array(); static void load_certs_from_memory(const PoolByteArray &p_memory); static bool is_available(); diff --git a/core/make_binders.py b/core/make_binders.py index 1e581f8ce3..6a7602cd5d 100644 --- a/core/make_binders.py +++ b/core/make_binders.py @@ -265,10 +265,8 @@ def run(target, source, env): else: text += t - f = open(target[0].path, "w") - f.write(text) - f.close() + with open(target[0].path, "w") as f: + f.write(text) - f = open(target[1].path, "w") - f.write(text_ext) - f.close() + with open(target[1].path, "w") as f: + f.write(text_ext) diff --git a/core/math/math_2d.cpp b/core/math/math_2d.cpp index d2e4101999..3767d298a1 100644 --- a/core/math/math_2d.cpp +++ b/core/math/math_2d.cpp @@ -98,11 +98,6 @@ real_t Vector2::cross(const Vector2 &p_other) const { return x * p_other.y - y * p_other.x; } -Vector2 Vector2::cross(real_t p_other) const { - - return Vector2(p_other * y, -p_other * x); -} - Vector2 Vector2::floor() const { return Vector2(Math::floor(x), Math::floor(y)); diff --git a/core/math/math_2d.h b/core/math/math_2d.h index 8928349a44..e7188da85b 100644 --- a/core/math/math_2d.h +++ b/core/math/math_2d.h @@ -104,7 +104,6 @@ struct Vector2 { real_t dot(const Vector2 &p_other) const; real_t cross(const Vector2 &p_other) const; - Vector2 cross(real_t p_other) const; Vector2 project(const Vector2 &p_vec) const; Vector2 plane_project(real_t p_d, const Vector2 &p_vec) const; @@ -304,7 +303,7 @@ struct Rect2 { inline real_t distance_to(const Vector2 &p_point) const { - real_t dist; + real_t dist = 0.0; bool inside = true; if (p_point.x < position.x) { diff --git a/core/math/math_funcs.cpp b/core/math/math_funcs.cpp index f060a8e4ab..5c8512d8bd 100644 --- a/core/math/math_funcs.cpp +++ b/core/math/math_funcs.cpp @@ -177,18 +177,3 @@ float Math::random(float from, float to) { float ret = (float)r / (float)RANDOM_MAX; return (ret) * (to - from) + from; } - -int Math::wrapi(int value, int min, int max) { - --max; - int rng = max - min + 1; - value = ((value - min) % rng); - if (value < 0) - return max + 1 + value; - else - return min + value; -} - -float Math::wrapf(float value, float min, float max) { - float rng = max - min; - return min + (value - min) - (rng * floor((value - min) / rng)); -} diff --git a/core/math/math_funcs.h b/core/math/math_funcs.h index e15abc6b50..26e87f009b 100644 --- a/core/math/math_funcs.h +++ b/core/math/math_funcs.h @@ -209,8 +209,18 @@ public: static _ALWAYS_INLINE_ double round(double p_val) { return (p_val >= 0) ? Math::floor(p_val + 0.5) : -Math::floor(-p_val + 0.5); } static _ALWAYS_INLINE_ float round(float p_val) { return (p_val >= 0) ? Math::floor(p_val + 0.5) : -Math::floor(-p_val + 0.5); } - static int wrapi(int value, int min, int max); - static float wrapf(float value, float min, float max); + static _ALWAYS_INLINE_ int wrapi(int value, int min, int max) { + int rng = max - min; + return min + ((((value - min) % rng) + rng) % rng); + } + static _ALWAYS_INLINE_ double wrapf(double value, double min, double max) { + double rng = max - min; + return min + (value - min) - (rng * Math::floor((value - min) / rng)); + } + static _ALWAYS_INLINE_ float wrapf(float value, float min, float max) { + float rng = max - min; + return min + (value - min) - (rng * Math::floor((value - min) / rng)); + } // double only, as these functions are mainly used by the editor and not performance-critical, static double ease(double p_x, double p_c); diff --git a/core/os/dir_access.cpp b/core/os/dir_access.cpp index 1941b82602..330a9153ef 100644 --- a/core/os/dir_access.cpp +++ b/core/os/dir_access.cpp @@ -301,8 +301,8 @@ Error DirAccess::copy(String p_from, String p_to, int p_chmod_flags) { FileAccess *fsrc = FileAccess::open(p_from, FileAccess::READ, &err); if (err) { - - ERR_FAIL_COND_V(err, err); + ERR_PRINTS("Failed to open " + p_from); + return err; } FileAccess *fdst = FileAccess::open(p_to, FileAccess::WRITE, &err); @@ -310,7 +310,8 @@ Error DirAccess::copy(String p_from, String p_to, int p_chmod_flags) { fsrc->close(); memdelete(fsrc); - ERR_FAIL_COND_V(err, err); + ERR_PRINTS("Failed to open " + p_to); + return err; } fsrc->seek_end(0); diff --git a/core/os/file_access.h b/core/os/file_access.h index 5d10c1a9aa..c4635fdfbb 100644 --- a/core/os/file_access.h +++ b/core/os/file_access.h @@ -89,6 +89,9 @@ public: virtual void close() = 0; ///< close a file virtual bool is_open() const = 0; ///< true when file is open + virtual String get_path() const { return ""; } /// returns the path for the current open file + virtual String get_path_absolute() const { return ""; } /// returns the absolute path for the current open file + virtual void seek(size_t p_position) = 0; ///< seek to a given position virtual void seek_end(int64_t p_position = 0) = 0; ///< seek from the end of file virtual size_t get_position() const = 0; ///< get position in the file diff --git a/core/os/input.cpp b/core/os/input.cpp index 3089ab2ce3..1d7cd7c791 100644 --- a/core/os/input.cpp +++ b/core/os/input.cpp @@ -111,7 +111,7 @@ void Input::_bind_methods() { BIND_ENUM_CONSTANT(CURSOR_HSPLIT); BIND_ENUM_CONSTANT(CURSOR_HELP); - ADD_SIGNAL(MethodInfo("joy_connection_changed", PropertyInfo(Variant::INT, "index"), PropertyInfo(Variant::BOOL, "connected"))); + ADD_SIGNAL(MethodInfo("joy_connection_changed", PropertyInfo(Variant::INT, "device"), PropertyInfo(Variant::BOOL, "connected"))); } void Input::get_argument_options(const StringName &p_function, int p_idx, List<String> *r_options) const { diff --git a/core/os/keyboard.cpp b/core/os/keyboard.cpp index fa53cc85c8..9dfc91e308 100644 --- a/core/os/keyboard.cpp +++ b/core/os/keyboard.cpp @@ -461,99 +461,6 @@ const char *find_keycode_name(int p_keycode) { return ""; } -struct _KeyCodeReplace { - int from; - int to; -}; - -static const _KeyCodeReplace _keycode_replace_qwertz[] = { - { KEY_Y, KEY_Z }, - { KEY_Z, KEY_Y }, - { 0, 0 } -}; - -static const _KeyCodeReplace _keycode_replace_azerty[] = { - { KEY_W, KEY_Z }, - { KEY_Z, KEY_W }, - { KEY_A, KEY_Q }, - { KEY_Q, KEY_A }, - { KEY_SEMICOLON, KEY_M }, - { KEY_M, KEY_SEMICOLON }, - { 0, 0 } -}; - -static const _KeyCodeReplace _keycode_replace_qzerty[] = { - { KEY_W, KEY_Z }, - { KEY_Z, KEY_W }, - { KEY_SEMICOLON, KEY_M }, - { KEY_M, KEY_SEMICOLON }, - { 0, 0 } -}; - -static const _KeyCodeReplace _keycode_replace_dvorak[] = { - { KEY_UNDERSCORE, KEY_BRACELEFT }, - { KEY_EQUAL, KEY_BRACERIGHT }, - { KEY_Q, KEY_APOSTROPHE }, - { KEY_W, KEY_COMMA }, - { KEY_E, KEY_PERIOD }, - { KEY_R, KEY_P }, - { KEY_T, KEY_Y }, - { KEY_Y, KEY_F }, - { KEY_U, KEY_G }, - { KEY_I, KEY_C }, - { KEY_O, KEY_R }, - { KEY_P, KEY_L }, - { KEY_BRACELEFT, KEY_SLASH }, - { KEY_BRACERIGHT, KEY_EQUAL }, - { KEY_A, KEY_A }, - { KEY_S, KEY_O }, - { KEY_D, KEY_E }, - { KEY_F, KEY_U }, - { KEY_G, KEY_I }, - { KEY_H, KEY_D }, - { KEY_J, KEY_H }, - { KEY_K, KEY_T }, - { KEY_L, KEY_N }, - { KEY_SEMICOLON, KEY_S }, - { KEY_APOSTROPHE, KEY_UNDERSCORE }, - { KEY_Z, KEY_SEMICOLON }, - { KEY_X, KEY_Q }, - { KEY_C, KEY_J }, - { KEY_V, KEY_K }, - { KEY_B, KEY_X }, - { KEY_N, KEY_B }, - { KEY_M, KEY_M }, - { KEY_COMMA, KEY_W }, - { KEY_PERIOD, KEY_V }, - { KEY_SLASH, KEY_Z }, - { 0, 0 } -}; - -static const _KeyCodeReplace _keycode_replace_neo[] = { - { 0, 0 } -}; - -static const _KeyCodeReplace _keycode_replace_colemak[] = { - { KEY_E, KEY_F }, - { KEY_R, KEY_P }, - { KEY_T, KEY_G }, - { KEY_Y, KEY_J }, - { KEY_U, KEY_L }, - { KEY_I, KEY_U }, - { KEY_O, KEY_Y }, - { KEY_P, KEY_SEMICOLON }, - { KEY_S, KEY_R }, - { KEY_D, KEY_S }, - { KEY_F, KEY_T }, - { KEY_G, KEY_D }, - { KEY_J, KEY_N }, - { KEY_K, KEY_E }, - { KEY_L, KEY_I }, - { KEY_SEMICOLON, KEY_O }, - { KEY_N, KEY_K }, - { 0, 0 } -}; - int keycode_get_count() { const _KeyCodeText *kct = &_keycodes[0]; @@ -574,31 +481,3 @@ int keycode_get_value_by_index(int p_index) { const char *keycode_get_name_by_index(int p_index) { return _keycodes[p_index].text; } - -int latin_keyboard_keycode_convert(int p_keycode) { - - const _KeyCodeReplace *kcr = NULL; - switch (OS::get_singleton()->get_latin_keyboard_variant()) { - - case OS::LATIN_KEYBOARD_QWERTY: return p_keycode; break; - case OS::LATIN_KEYBOARD_QWERTZ: kcr = _keycode_replace_qwertz; break; - case OS::LATIN_KEYBOARD_AZERTY: kcr = _keycode_replace_azerty; break; - case OS::LATIN_KEYBOARD_QZERTY: kcr = _keycode_replace_qzerty; break; - case OS::LATIN_KEYBOARD_DVORAK: kcr = _keycode_replace_dvorak; break; - case OS::LATIN_KEYBOARD_NEO: kcr = _keycode_replace_neo; break; - case OS::LATIN_KEYBOARD_COLEMAK: kcr = _keycode_replace_colemak; break; - default: return p_keycode; - } - - if (!kcr) { - return p_keycode; - } - - while (kcr->from) { - if (kcr->from == p_keycode) - return kcr->to; - kcr++; - } - - return p_keycode; -} diff --git a/core/os/keyboard.h b/core/os/keyboard.h index 4c253fa4ce..a0e6f8b2ef 100644 --- a/core/os/keyboard.h +++ b/core/os/keyboard.h @@ -331,6 +331,5 @@ const char *find_keycode_name(int p_keycode); int keycode_get_count(); int keycode_get_value_by_index(int p_index); const char *keycode_get_name_by_index(int p_index); -int latin_keyboard_keycode_convert(int p_keycode); #endif diff --git a/core/os/os.cpp b/core/os/os.cpp index 422acf95dc..618a4bbac3 100644 --- a/core/os/os.cpp +++ b/core/os/os.cpp @@ -34,6 +34,7 @@ #include "input.h" #include "os/file_access.h" #include "project_settings.h" +#include "servers/audio_server.h" #include "version_generated.gen.h" #include <stdarg.h> @@ -627,6 +628,34 @@ void OS::center_window() { set_window_position(Vector2(x, y)); } +int OS::get_video_driver_count() const { + + return 2; +} + +const char *OS::get_video_driver_name(int p_driver) const { + + switch (p_driver) { + case VIDEO_DRIVER_GLES2: + return "GLES2"; + case VIDEO_DRIVER_GLES3: + default: + return "GLES3"; + } +} + +int OS::get_audio_driver_count() const { + + return AudioDriverManager::get_driver_count(); +} + +const char *OS::get_audio_driver_name(int p_driver) const { + + AudioDriver *driver = AudioDriverManager::get_driver(p_driver); + ERR_FAIL_COND_V(!driver, ""); + return AudioDriverManager::get_driver(p_driver)->get_name(); +} + OS::OS() { void *volatile stack_bottom; diff --git a/core/os/os.h b/core/os/os.h index 38e55fa3b7..5a2c998782 100644 --- a/core/os/os.h +++ b/core/os/os.h @@ -44,6 +44,12 @@ @author Juan Linietsky <reduzio@gmail.com> */ +enum VideoDriver { + VIDEO_DRIVER_GLES3, + VIDEO_DRIVER_GLES2, + VIDEO_DRIVER_MAX, +}; + class OS { static OS *singleton; @@ -115,12 +121,6 @@ protected: RenderThreadMode _render_thread_mode; // functions used by main to initialize/deintialize the OS - virtual int get_video_driver_count() const = 0; - virtual const char *get_video_driver_name(int p_driver) const = 0; - - virtual int get_audio_driver_count() const = 0; - virtual const char *get_audio_driver_name(int p_driver) const = 0; - void add_logger(Logger *p_logger); virtual void initialize_core() = 0; @@ -175,6 +175,12 @@ public: virtual VideoMode get_video_mode(int p_screen = 0) const = 0; virtual void get_fullscreen_mode_list(List<VideoMode> *p_list, int p_screen = 0) const = 0; + virtual int get_video_driver_count() const; + virtual const char *get_video_driver_name(int p_driver) const; + + virtual int get_audio_driver_count() const; + virtual const char *get_audio_driver_name(int p_driver) const; + virtual int get_screen_count() const { return 1; } virtual int get_current_screen() const { return 0; } virtual void set_current_screen(int p_screen) {} diff --git a/core/os/thread_dummy.cpp b/core/os/thread_dummy.cpp index fa0bb3dafd..b6371235c4 100644 --- a/core/os/thread_dummy.cpp +++ b/core/os/thread_dummy.cpp @@ -55,3 +55,11 @@ Semaphore *SemaphoreDummy::create() { void SemaphoreDummy::make_default() { Semaphore::create_func = &SemaphoreDummy::create; }; + +RWLock *RWLockDummy::create() { + return memnew(RWLockDummy); +}; + +void RWLockDummy::make_default() { + RWLock::create_func = &RWLockDummy::create; +}; diff --git a/core/os/thread_dummy.h b/core/os/thread_dummy.h index b67b52a726..74957b95fe 100644 --- a/core/os/thread_dummy.h +++ b/core/os/thread_dummy.h @@ -32,6 +32,7 @@ #define THREAD_DUMMY_H #include "mutex.h" +#include "rw_lock.h" #include "semaphore.h" #include "thread.h" @@ -69,4 +70,20 @@ public: static void make_default(); }; +class RWLockDummy : public RWLock { + + static RWLock *create(); + +public: + virtual void read_lock() {} + virtual void read_unlock() {} + virtual Error read_try_lock() { return OK; } + + virtual void write_lock() {} + virtual void write_unlock() {} + virtual Error write_try_lock() { return OK; } + + static void make_default(); +}; + #endif diff --git a/core/project_settings.cpp b/core/project_settings.cpp index 427fa77e62..20d91e7940 100644 --- a/core/project_settings.cpp +++ b/core/project_settings.cpp @@ -692,7 +692,10 @@ Error ProjectSettings::_save_settings_text(const String &p_file, const Map<Strin String vstr; VariantWriter::write_to_string(value, vstr); - file->store_string(F->get() + "=" + vstr + "\n"); + if (F->get().find(" ") != -1) + file->store_string(F->get().quote() + "=" + vstr + "\n"); + else + file->store_string(F->get() + "=" + vstr + "\n"); } } @@ -1027,6 +1030,20 @@ ProjectSettings::ProjectSettings() { GLOBAL_DEF("input/ui_page_down", va); input_presets.push_back("input/ui_page_down"); + va = Array(); + key.instance(); + key->set_scancode(KEY_HOME); + va.push_back(key); + GLOBAL_DEF("input/ui_home", va); + input_presets.push_back("input/ui_home"); + + va = Array(); + key.instance(); + key->set_scancode(KEY_END); + va.push_back(key); + GLOBAL_DEF("input/ui_end", va); + input_presets.push_back("input/ui_end"); + //GLOBAL_DEF("display/window/handheld/orientation", "landscape"); custom_prop_info["display/window/handheld/orientation"] = PropertyInfo(Variant::STRING, "display/window/handheld/orientation", PROPERTY_HINT_ENUM, "landscape,portrait,reverse_landscape,reverse_portrait,sensor_landscape,sensor_portrait,sensor"); diff --git a/core/reference.h b/core/reference.h index a0bdb62258..0d6b1ced6e 100644 --- a/core/reference.h +++ b/core/reference.h @@ -63,7 +63,7 @@ public: template <class T> class Ref { - T *reference = NULL; + T *reference; void ref(const Ref &p_from) { @@ -213,10 +213,9 @@ public: Ref(T *p_reference) { + reference = NULL; if (p_reference) ref_pointer(p_reference); - else - reference = NULL; } Ref(const Variant &p_variant) { diff --git a/core/resource.cpp b/core/resource.cpp index 2eeed50d9d..179333aa14 100644 --- a/core/resource.cpp +++ b/core/resource.cpp @@ -226,7 +226,7 @@ Ref<Resource> Resource::duplicate(bool p_subresources) const { if (!(E->get().usage & PROPERTY_USAGE_STORAGE)) continue; - Variant p = get(E->get().name); + Variant p = get(E->get().name).duplicate(true); if (p.get_type() == Variant::OBJECT && p_subresources) { RES sr = p; diff --git a/core/script_language.h b/core/script_language.h index d1da0a3b72..0c1f99cea6 100644 --- a/core/script_language.h +++ b/core/script_language.h @@ -203,6 +203,7 @@ public: virtual void make_template(const String &p_class_name, const String &p_base_class_name, Ref<Script> &p_script) {} virtual bool is_using_templates() { return false; } virtual bool validate(const String &p_script, int &r_line_error, int &r_col_error, String &r_test_error, const String &p_path = "", List<String> *r_functions = NULL) const = 0; + virtual String validate_path(const String &p_path) const { return ""; } virtual Script *create_script() const = 0; virtual bool has_named_classes() const = 0; virtual bool supports_builtin_mode() const = 0; @@ -220,7 +221,9 @@ public: RESULT_CLASS, RESULT_CLASS_CONSTANT, RESULT_CLASS_PROPERTY, - RESULT_CLASS_METHOD + RESULT_CLASS_METHOD, + RESULT_CLASS_ENUM, + RESULT_CLASS_TBD_GLOBALSCOPE }; Type type; Ref<Script> script; diff --git a/core/string_buffer.h b/core/string_buffer.h index b148e45544..7e9b151bea 100644 --- a/core/string_buffer.h +++ b/core/string_buffer.h @@ -39,7 +39,7 @@ class StringBuffer { CharType short_buffer[SHORT_BUFFER_SIZE]; String buffer; - int string_length = 0; + int string_length; _FORCE_INLINE_ CharType *current_buffer_ptr() { return static_cast<Vector<CharType> &>(buffer).empty() ? short_buffer : buffer.ptrw(); @@ -79,6 +79,10 @@ public: _FORCE_INLINE_ operator String() { return as_string(); } + + StringBuffer() { + string_length = 0; + } }; template <int SHORT_BUFFER_SIZE> diff --git a/core/string_builder.h b/core/string_builder.h index 9e2599ac32..596b3bf730 100644 --- a/core/string_builder.h +++ b/core/string_builder.h @@ -37,7 +37,7 @@ class StringBuilder { - uint32_t string_length = 0; + uint32_t string_length; Vector<String> strings; Vector<const char *> c_strings; @@ -75,6 +75,10 @@ public: _FORCE_INLINE_ operator String() const { return as_string(); } + + StringBuilder() { + string_length = 0; + } }; #endif // STRING_BUILDER_H diff --git a/core/ustring.cpp b/core/ustring.cpp index a7a7810837..d749146998 100644 --- a/core/ustring.cpp +++ b/core/ustring.cpp @@ -3165,11 +3165,11 @@ String String::word_wrap(int p_chars_per_line) const { return ret; } -String String::http_escape() const { +String String::percent_encode() const { const CharString temp = utf8(); String res; - for (int i = 0; i < length(); ++i) { - CharType ord = temp[i]; + for (int i = 0; i < temp.length(); ++i) { + char ord = temp[i]; if (ord == '.' || ord == '-' || ord == '_' || ord == '~' || (ord >= 'a' && ord <= 'z') || (ord >= 'A' && ord <= 'Z') || @@ -3178,9 +3178,9 @@ String String::http_escape() const { } else { char h_Val[3]; #if defined(__GNUC__) || defined(_MSC_VER) - snprintf(h_Val, 3, "%.2X", ord); + snprintf(h_Val, 3, "%hhX", ord); #else - sprintf(h_Val, "%.2X", ord); + sprintf(h_Val, "%hhX", ord); #endif res += "%"; res += h_Val; @@ -3189,7 +3189,7 @@ String String::http_escape() const { return res; } -String String::http_unescape() const { +String String::percent_decode() const { String res; for (int i = 0; i < length(); ++i) { if (ord_at(i) == '%' && i + 2 < length()) { @@ -3727,68 +3727,6 @@ String String::plus_file(const String &p_file) const { return *this + "/" + p_file; } -String String::percent_encode() const { - - CharString cs = utf8(); - String encoded; - for (int i = 0; i < cs.length(); i++) { - uint8_t c = cs[i]; - if ((c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z') || (c >= '0' && c <= '9') || c == '-' || c == '_' || c == '~' || c == '.') { - - char p[2] = { (char)c, 0 }; - encoded += p; - } else { - char p[4] = { '%', 0, 0, 0 }; - static const char hex[16] = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f' }; - - p[1] = hex[c >> 4]; - p[2] = hex[c & 0xF]; - encoded += p; - } - } - - return encoded; -} -String String::percent_decode() const { - - CharString pe; - - CharString cs = utf8(); - for (int i = 0; i < cs.length(); i++) { - - uint8_t c = cs[i]; - if (c == '%' && i < length() - 2) { - - uint8_t a = LOWERCASE(cs[i + 1]); - uint8_t b = LOWERCASE(cs[i + 2]); - - c = 0; - if (a >= '0' && a <= '9') - c = (a - '0') << 4; - else if (a >= 'a' && a <= 'f') - c = (a - 'a' + 10) << 4; - else - continue; - - uint8_t d = 0; - - if (b >= '0' && b <= '9') - d = (b - '0'); - else if (b >= 'a' && b <= 'f') - d = (b - 'a' + 10); - else - continue; - c += d; - i += 2; - } - pe.push_back(c); - } - - pe.push_back(0); - - return String::utf8(pe.ptr()); -} - String String::get_basename() const { int pos = find_last("."); diff --git a/core/ustring.h b/core/ustring.h index bb676ce623..8023c9b95d 100644 --- a/core/ustring.h +++ b/core/ustring.h @@ -226,17 +226,14 @@ public: String xml_escape(bool p_escape_quotes = false) const; String xml_unescape() const; - String http_escape() const; - String http_unescape() const; + String percent_encode() const; + String percent_decode() const; String c_escape() const; String c_escape_multiline() const; String c_unescape() const; String json_escape() const; String word_wrap(int p_chars_per_line) const; - String percent_encode() const; - String percent_decode() const; - bool is_valid_identifier() const; bool is_valid_integer() const; bool is_valid_float() const; diff --git a/core/variant.h b/core/variant.h index 0a4afada5b..2cdb5c9ab6 100644 --- a/core/variant.h +++ b/core/variant.h @@ -338,6 +338,7 @@ public: } void zero(); + Variant duplicate(bool deep = false) const; static void blend(const Variant &a, const Variant &b, float c, Variant &r_dst); static void interpolate(const Variant &a, const Variant &b, float c, Variant &r_dst); diff --git a/core/variant_call.cpp b/core/variant_call.cpp index d1d45f0e7c..c6e093010d 100644 --- a/core/variant_call.cpp +++ b/core/variant_call.cpp @@ -347,7 +347,7 @@ struct _VariantCall { VCALL_LOCALMEM1R(Vector2, bounce); VCALL_LOCALMEM1R(Vector2, reflect); VCALL_LOCALMEM0R(Vector2, angle); - //VCALL_LOCALMEM1R(Vector2,cross); + VCALL_LOCALMEM1R(Vector2, cross); VCALL_LOCALMEM0R(Vector2, abs); VCALL_LOCALMEM1R(Vector2, clamped); @@ -465,7 +465,7 @@ struct _VariantCall { VCALL_LOCALMEM0R(Dictionary, hash); VCALL_LOCALMEM0R(Dictionary, keys); VCALL_LOCALMEM0R(Dictionary, values); - VCALL_LOCALMEM0R(Dictionary, duplicate); + VCALL_LOCALMEM1R(Dictionary, duplicate); VCALL_LOCALMEM2(Array, set); VCALL_LOCALMEM1R(Array, get); @@ -494,7 +494,7 @@ struct _VariantCall { VCALL_LOCALMEM0(Array, shuffle); VCALL_LOCALMEM2R(Array, bsearch); VCALL_LOCALMEM4R(Array, bsearch_custom); - VCALL_LOCALMEM0R(Array, duplicate); + VCALL_LOCALMEM1R(Array, duplicate); VCALL_LOCALMEM0(Array, invert); static void _call_PoolByteArray_get_string_from_ascii(Variant &r_ret, Variant &p_self, const Variant **p_args) { @@ -1517,7 +1517,7 @@ void register_variant_methods() { ADDFUNC1R(VECTOR2, VECTOR2, Vector2, slide, VECTOR2, "n", varray()); ADDFUNC1R(VECTOR2, VECTOR2, Vector2, bounce, VECTOR2, "n", varray()); ADDFUNC1R(VECTOR2, VECTOR2, Vector2, reflect, VECTOR2, "n", varray()); - //ADDFUNC1R(VECTOR2,REAL,Vector2,cross,VECTOR2,"with",varray()); + ADDFUNC1R(VECTOR2, REAL, Vector2, cross, VECTOR2, "with", varray()); ADDFUNC0R(VECTOR2, VECTOR2, Vector2, abs, varray()); ADDFUNC1R(VECTOR2, VECTOR2, Vector2, clamped, REAL, "length", varray()); @@ -1613,7 +1613,7 @@ void register_variant_methods() { ADDFUNC0R(DICTIONARY, INT, Dictionary, hash, varray()); ADDFUNC0R(DICTIONARY, ARRAY, Dictionary, keys, varray()); ADDFUNC0R(DICTIONARY, ARRAY, Dictionary, values, varray()); - ADDFUNC0R(DICTIONARY, DICTIONARY, Dictionary, duplicate, varray()); + ADDFUNC1R(DICTIONARY, DICTIONARY, Dictionary, duplicate, BOOL, "deep", varray(false)); ADDFUNC0R(ARRAY, INT, Array, size, varray()); ADDFUNC0R(ARRAY, BOOL, Array, empty, varray()); @@ -1641,7 +1641,7 @@ void register_variant_methods() { ADDFUNC2R(ARRAY, INT, Array, bsearch, NIL, "value", BOOL, "before", varray(true)); ADDFUNC4R(ARRAY, INT, Array, bsearch_custom, NIL, "value", OBJECT, "obj", STRING, "func", BOOL, "before", varray(true)); ADDFUNC0NC(ARRAY, NIL, Array, invert, varray()); - ADDFUNC0RNC(ARRAY, ARRAY, Array, duplicate, varray()); + ADDFUNC1R(ARRAY, ARRAY, Array, duplicate, BOOL, "deep", varray(false)); ADDFUNC0R(POOL_BYTE_ARRAY, INT, PoolByteArray, size, varray()); ADDFUNC2(POOL_BYTE_ARRAY, NIL, PoolByteArray, set, INT, "idx", INT, "byte", varray()); diff --git a/core/variant_op.cpp b/core/variant_op.cpp index 97b469861c..8ad981ed0e 100644 --- a/core/variant_op.cpp +++ b/core/variant_op.cpp @@ -177,7 +177,7 @@ bool Variant::booleanize() const { CASE_TYPE(m_prefix, m_op_name, m_name) { \ if (p_b.type == INT) _RETURN(p_a._data.m_type m_op p_b._data._int); \ if (p_b.type == REAL) _RETURN(p_a._data.m_type m_op p_b._data._real); \ - if (p_b.type == NIL) _RETURN(!p_b.type m_op NIL); \ + if (p_b.type == NIL) _RETURN(!(p_b.type m_op NIL)); \ \ _RETURN_FAIL \ }; @@ -252,7 +252,7 @@ bool Variant::booleanize() const { CASE_TYPE(m_prefix, m_op_name, m_name) { \ if (p_b.type == STRING) _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op *reinterpret_cast<const String *>(p_b._data._mem)); \ if (p_b.type == NODE_PATH) _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op *reinterpret_cast<const NodePath *>(p_b._data._mem)); \ - if (p_b.type == NIL) _RETURN(!p_b.type m_op NIL); \ + if (p_b.type == NIL) _RETURN(!(p_b.type m_op NIL)); \ \ _RETURN_FAIL \ }; @@ -278,7 +278,7 @@ bool Variant::booleanize() const { if (p_b.type == m_name) \ _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op *reinterpret_cast<const m_type *>(p_b._data._mem)); \ if (p_b.type == NIL) \ - _RETURN(!p_b.type m_op NIL); \ + _RETURN(!(p_b.type m_op NIL)); \ \ _RETURN_FAIL \ }; @@ -323,7 +323,7 @@ bool Variant::booleanize() const { if (p_b.type == m_name) \ _RETURN(*p_a._data.m_sub m_op *p_b._data.m_sub); \ if (p_b.type == NIL) \ - _RETURN(!p_b.type m_op NIL); \ + _RETURN(!(p_b.type m_op NIL)); \ \ _RETURN_FAIL \ } @@ -3415,6 +3415,19 @@ Variant Variant::iter_get(const Variant &r_iter, bool &r_valid) const { return Variant(); } +Variant Variant::duplicate(bool deep) const { + switch (type) { + // case OBJECT: + // return operator Object *()->duplicate(); + case DICTIONARY: + return operator Dictionary().duplicate(deep); + case ARRAY: + return operator Array().duplicate(deep); + default: + return *this; + } +} + void Variant::blend(const Variant &a, const Variant &b, float c, Variant &r_dst) { if (a.type != b.type) { if (a.is_num() && b.is_num()) { |