diff options
47 files changed, 528 insertions, 337 deletions
diff --git a/core/io/marshalls.cpp b/core/io/marshalls.cpp index 8eb40b61d7..c5d59f786d 100644 --- a/core/io/marshalls.cpp +++ b/core/io/marshalls.cpp @@ -33,8 +33,28 @@ #include "reference.h" #include <stdio.h> +void EncodedObjectAsID::_bind_methods() { + ClassDB::bind_method(D_METHOD("set_object_id", "id"), &EncodedObjectAsID::set_object_id); + ClassDB::bind_method(D_METHOD("get_object_id"), &EncodedObjectAsID::get_object_id); +} + +void EncodedObjectAsID::set_object_id(ObjectID p_id) { + id = p_id; +} + +ObjectID EncodedObjectAsID::get_object_id() const { + + return id; +} + +EncodedObjectAsID::EncodedObjectAsID() { + + id = 0; +} + #define ENCODE_MASK 0xFF #define ENCODE_FLAG_64 1 << 16 +#define ENCODE_FLAG_OBJECT_AS_ID 1 << 16 static Error _decode_string(const uint8_t *&buf, int &len, int *r_len, String &r_string) { ERR_FAIL_COND_V(len < 4, ERR_INVALID_DATA); @@ -381,56 +401,74 @@ Error decode_variant(Variant &r_variant, const uint8_t *p_buffer, int p_len, int } break; case Variant::OBJECT: { - ERR_FAIL_COND_V(!p_allow_objects, ERR_UNAUTHORIZED); - - String str; - Error err = _decode_string(buf, len, r_len, str); - if (err) - return err; + if (type & ENCODE_FLAG_OBJECT_AS_ID) { + //this _is_ allowed + ObjectID val = decode_uint64(buf); + if (r_len) + (*r_len) += 8; - if (str == String()) { - r_variant = (Object *)NULL; - } else { + if (val == 0) { + r_variant = (Object *)NULL; + } else { + Ref<EncodedObjectAsID> obj_as_id; + obj_as_id.instance(); + obj_as_id->set_object_id(val); - Object *obj = ClassDB::instance(str); + r_variant = obj_as_id; + } - ERR_FAIL_COND_V(!obj, ERR_UNAVAILABLE); - ERR_FAIL_COND_V(len < 4, ERR_INVALID_DATA); + } else { + ERR_FAIL_COND_V(!p_allow_objects, ERR_UNAUTHORIZED); - int32_t count = decode_uint32(buf); - buf += 4; - len -= 4; - if (r_len) { - (*r_len) += 4; - } + String str; + Error err = _decode_string(buf, len, r_len, str); + if (err) + return err; - for (int i = 0; i < count; i++) { + if (str == String()) { + r_variant = (Object *)NULL; + } else { - str = String(); - err = _decode_string(buf, len, r_len, str); - if (err) - return err; + Object *obj = ClassDB::instance(str); - Variant value; - int used; - err = decode_variant(value, buf, len, &used, p_allow_objects); - if (err) - return err; + ERR_FAIL_COND_V(!obj, ERR_UNAVAILABLE); + ERR_FAIL_COND_V(len < 4, ERR_INVALID_DATA); - buf += used; - len -= used; + int32_t count = decode_uint32(buf); + buf += 4; + len -= 4; if (r_len) { - (*r_len) += used; + (*r_len) += 4; } - obj->set(str, value); - } + for (int i = 0; i < count; i++) { - if (obj->cast_to<Reference>()) { - REF ref = REF(obj->cast_to<Reference>()); - r_variant = ref; - } else { - r_variant = obj; + str = String(); + err = _decode_string(buf, len, r_len, str); + if (err) + return err; + + Variant value; + int used; + err = decode_variant(value, buf, len, &used, p_allow_objects); + if (err) + return err; + + buf += used; + len -= used; + if (r_len) { + (*r_len) += used; + } + + obj->set(str, value); + } + + if (obj->cast_to<Reference>()) { + REF ref = REF(obj->cast_to<Reference>()); + r_variant = ref; + } else { + r_variant = obj; + } } } @@ -776,7 +814,7 @@ static void _encode_string(const String &p_string, uint8_t *&buf, int &r_len) { r_len++; //pad } -Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len) { +Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len, bool p_object_as_id) { uint8_t *buf = r_buffer; @@ -800,6 +838,11 @@ Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len) { flags |= ENCODE_FLAG_64; //always encode real as double } } break; + case Variant::OBJECT: { + if (p_object_as_id) { + flags |= ENCODE_FLAG_OBJECT_AS_ID; + } + } break; } if (buf) { @@ -1071,49 +1114,66 @@ Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len) { } break; case Variant::OBJECT: { - Object *obj = p_variant; - if (!obj) { + if (p_object_as_id) { + if (buf) { - encode_uint32(0, buf); - buf += 4; - r_len += 4; + + Object *obj = p_variant; + ObjectID id = 0; + if (obj && ObjectDB::instance_validate(obj)) { + id = obj->get_instance_id(); + } + + encode_uint64(id, buf); } + + r_len += 8; + } else { - _encode_string(obj->get_class(), buf, r_len); + Object *obj = p_variant; + if (!obj) { + if (buf) { + encode_uint32(0, buf); + buf += 4; + r_len += 4; + } + } else { + _encode_string(obj->get_class(), buf, r_len); - List<PropertyInfo> props; - obj->get_property_list(&props); + List<PropertyInfo> props; + obj->get_property_list(&props); - int pc = 0; - for (List<PropertyInfo>::Element *E = props.front(); E; E = E->next()) { + int pc = 0; + for (List<PropertyInfo>::Element *E = props.front(); E; E = E->next()) { - if (!(E->get().usage & PROPERTY_USAGE_STORAGE)) - continue; - pc++; - } + if (!(E->get().usage & PROPERTY_USAGE_STORAGE)) + continue; + pc++; + } - if (buf) { - encode_uint32(pc, buf); - buf += 4; - } + if (buf) { + encode_uint32(pc, buf); + buf += 4; + } - r_len += 4; + r_len += 4; - for (List<PropertyInfo>::Element *E = props.front(); E; E = E->next()) { + for (List<PropertyInfo>::Element *E = props.front(); E; E = E->next()) { - if (!(E->get().usage & PROPERTY_USAGE_STORAGE)) - continue; + if (!(E->get().usage & PROPERTY_USAGE_STORAGE)) + continue; - _encode_string(E->get().name, buf, r_len); + _encode_string(E->get().name, buf, r_len); - int len; - Error err = encode_variant(obj->get(E->get().name), buf, len); - if (err) - return err; - ERR_FAIL_COND_V(len % 4, ERR_BUG); - r_len += len; - if (buf) - buf += len; + int len; + Error err = encode_variant(obj->get(E->get().name), buf, len, p_object_as_id); + if (err) + return err; + ERR_FAIL_COND_V(len % 4, ERR_BUG); + r_len += len; + if (buf) + buf += len; + } } } @@ -1147,12 +1207,12 @@ Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len) { r_len++; //pad */ int len; - encode_variant(E->get(), buf, len); + encode_variant(E->get(), buf, len, p_object_as_id); ERR_FAIL_COND_V(len % 4, ERR_BUG); r_len += len; if (buf) buf += len; - encode_variant(d[E->get()], buf, len); + encode_variant(d[E->get()], buf, len, p_object_as_id); ERR_FAIL_COND_V(len % 4, ERR_BUG); r_len += len; if (buf) @@ -1174,7 +1234,7 @@ Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len) { for (int i = 0; i < v.size(); i++) { int len; - encode_variant(v.get(i), buf, len); + encode_variant(v.get(i), buf, len, p_object_as_id); ERR_FAIL_COND_V(len % 4, ERR_BUG); r_len += len; if (buf) diff --git a/core/io/marshalls.h b/core/io/marshalls.h index a6cc72b691..234ae3b183 100644 --- a/core/io/marshalls.h +++ b/core/io/marshalls.h @@ -32,8 +32,8 @@ #include "typedefs.h" +#include "reference.h" #include "variant.h" - /** * Miscellaneous helpers for marshalling data types, and encoding * in an endian independent way @@ -183,7 +183,22 @@ static inline double decode_double(const uint8_t *p_arr) { return md.d; } -Error decode_variant(Variant &r_variant, const uint8_t *p_buffer, int p_len, int *r_len = NULL, bool p_allow_objects=true); -Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len); +class EncodedObjectAsID : public Reference { + GDCLASS(EncodedObjectAsID, Reference); + + ObjectID id; + +protected: + static void _bind_methods(); + +public: + void set_object_id(ObjectID p_id); + ObjectID get_object_id() const; + + EncodedObjectAsID(); +}; + +Error decode_variant(Variant &r_variant, const uint8_t *p_buffer, int p_len, int *r_len = NULL, bool p_allow_objects = true); +Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len, bool p_object_as_id = false); #endif diff --git a/core/io/packet_peer.cpp b/core/io/packet_peer.cpp index 66f8eea171..ca00b8b480 100644 --- a/core/io/packet_peer.cpp +++ b/core/io/packet_peer.cpp @@ -92,7 +92,7 @@ Error PacketPeer::get_var(Variant &r_variant) const { Error PacketPeer::put_var(const Variant &p_packet) { int len; - Error err = encode_variant(p_packet, NULL, len); // compute len first + Error err = encode_variant(p_packet, NULL, len, !allow_object_decoding); // compute len first if (err) return err; @@ -101,7 +101,7 @@ Error PacketPeer::put_var(const Variant &p_packet) { uint8_t *buf = (uint8_t *)alloca(len); ERR_FAIL_COND_V(!buf, ERR_OUT_OF_MEMORY); - err = encode_variant(p_packet, buf, len); + err = encode_variant(p_packet, buf, len, !allow_object_decoding); ERR_FAIL_COND_V(err, err); return put_packet(buf, len); @@ -155,6 +155,8 @@ void PacketPeerStream::_bind_methods() { ClassDB::bind_method(D_METHOD("set_stream_peer", "peer"), &PacketPeerStream::_set_stream_peer); ClassDB::bind_method(D_METHOD("set_input_buffer_max_size", "max_size_bytes"), &PacketPeerStream::set_input_buffer_max_size); ClassDB::bind_method(D_METHOD("set_output_buffer_max_size", "max_size_bytes"), &PacketPeerStream::set_output_buffer_max_size); + ClassDB::bind_method(D_METHOD("get_input_buffer_max_size"), &PacketPeerStream::get_input_buffer_max_size); + ClassDB::bind_method(D_METHOD("get_output_buffer_max_size"), &PacketPeerStream::get_output_buffer_max_size); } Error PacketPeerStream::_poll_buffer() const { @@ -268,11 +270,21 @@ void PacketPeerStream::set_input_buffer_max_size(int p_max_size) { input_buffer.resize(next_power_of_2(p_max_size + 4)); } +int PacketPeerStream::get_input_buffer_max_size() const { + + return input_buffer.size() - 4; +} + void PacketPeerStream::set_output_buffer_max_size(int p_max_size) { output_buffer.resize(next_power_of_2(p_max_size + 4)); } +int PacketPeerStream::get_output_buffer_max_size() const { + + return output_buffer.size() - 4; +} + PacketPeerStream::PacketPeerStream() { int rbsize = GLOBAL_GET("network/limits/packet_peer_stream/max_buffer_po2"); diff --git a/core/io/packet_peer.h b/core/io/packet_peer.h index 3bd6876aa7..597119f7f4 100644 --- a/core/io/packet_peer.h +++ b/core/io/packet_peer.h @@ -98,7 +98,9 @@ public: void set_stream_peer(const Ref<StreamPeer> &p_peer); void set_input_buffer_max_size(int p_max_size); + int get_input_buffer_max_size() const; void set_output_buffer_max_size(int p_max_size); + int get_output_buffer_max_size() const; PacketPeerStream(); }; diff --git a/core/math/rect3.h b/core/math/rect3.h index 7c971f5ac7..4890a19d99 100644 --- a/core/math/rect3.h +++ b/core/math/rect3.h @@ -47,12 +47,12 @@ public: real_t get_area() const; /// get area _FORCE_INLINE_ bool has_no_area() const { - return (size.x <= CMP_EPSILON || size.y <= CMP_EPSILON || size.z <= CMP_EPSILON); + return (size.x <= 0 || size.y <= 0 || size.z <= 0); } _FORCE_INLINE_ bool has_no_surface() const { - return (size.x <= CMP_EPSILON && size.y <= CMP_EPSILON && size.z <= CMP_EPSILON); + return (size.x <= 0 && size.y <= 0 && size.z <= 0); } const Vector3 &get_position() const { return position; } diff --git a/core/object.cpp b/core/object.cpp index 3cfd74a448..06c2603b74 100644 --- a/core/object.cpp +++ b/core/object.cpp @@ -1560,7 +1560,7 @@ void Object::initialize_class() { initialized = true; } -StringName Object::localize(const StringName &p_message) const { +StringName Object::tr(const StringName &p_message) const { if (!_can_translate || !TranslationServer::get_singleton()) return p_message; @@ -1707,11 +1707,11 @@ void Object::_bind_methods() { ClassDB::bind_method(D_METHOD("set_block_signals", "enable"), &Object::set_block_signals); ClassDB::bind_method(D_METHOD("is_blocking_signals"), &Object::is_blocking_signals); - ClassDB::bind_method(D_METHOD("set_message_localization", "enable"), &Object::set_message_localization); - ClassDB::bind_method(D_METHOD("can_translate_messages"), &Object::can_translate_messages); ClassDB::bind_method(D_METHOD("property_list_changed_notify"), &Object::property_list_changed_notify); - ClassDB::bind_method(D_METHOD("localize", "message"), &Object::localize); + ClassDB::bind_method(D_METHOD("set_message_translation", "enable"), &Object::set_message_translation); + ClassDB::bind_method(D_METHOD("can_translate_messages"), &Object::can_translate_messages); + ClassDB::bind_method(D_METHOD("tr", "message"), &Object::tr); ClassDB::bind_method(D_METHOD("is_queued_for_deletion"), &Object::is_queued_for_deletion); diff --git a/core/object.h b/core/object.h index ebcd4afeb9..8a858b5b00 100644 --- a/core/object.h +++ b/core/object.h @@ -83,6 +83,7 @@ enum PropertyHint { PROPERTY_HINT_PROPERTY_OF_BASE_TYPE, ///< a property of a base type PROPERTY_HINT_PROPERTY_OF_INSTANCE, ///< a property of an instance PROPERTY_HINT_PROPERTY_OF_SCRIPT, ///< a property of a script & base + PROPERTY_HINT_OBJECT_TOO_BIG, ///< object is too big to send PROPERTY_HINT_MAX, }; @@ -678,12 +679,12 @@ public: virtual void get_argument_options(const StringName &p_function, int p_idx, List<String> *r_options) const; - StringName localize(const StringName &p_message) const; //translate message (internationalization) + StringName tr(const StringName &p_message) const; // translate message (internationalization) bool _is_queued_for_deletion; // set to true by SceneTree::queue_delete() bool is_queued_for_deletion() const; - _FORCE_INLINE_ void set_message_localization(bool p_enable) { _can_translate = p_enable; } + _FORCE_INLINE_ void set_message_translation(bool p_enable) { _can_translate = p_enable; } _FORCE_INLINE_ bool can_translate_messages() const { return _can_translate; } #ifdef TOOLS_ENABLED diff --git a/core/register_core_types.cpp b/core/register_core_types.cpp index 43f781af55..fca9afbf5e 100644 --- a/core/register_core_types.cpp +++ b/core/register_core_types.cpp @@ -39,6 +39,7 @@ #include "input_map.h" #include "io/config_file.h" #include "io/http_client.h" +#include "io/marshalls.h" #include "io/packet_peer.h" #include "io/packet_peer_udp.h" #include "io/pck_packer.h" @@ -56,7 +57,6 @@ #include "project_settings.h" #include "translation.h" #include "undo_redo.h" - static ResourceFormatSaverBinary *resource_saver_binary = NULL; static ResourceFormatLoaderBinary *resource_loader_binary = NULL; static ResourceFormatImporter *resource_format_importer = NULL; @@ -157,6 +157,7 @@ void register_core_types() { ClassDB::register_class<PackedDataContainer>(); ClassDB::register_virtual_class<PackedDataContainerRef>(); ClassDB::register_class<AStar>(); + ClassDB::register_class<EncodedObjectAsID>(); ip = IP::create(); diff --git a/core/script_debugger_remote.cpp b/core/script_debugger_remote.cpp index 44e86bca6a..25f0044cc6 100644 --- a/core/script_debugger_remote.cpp +++ b/core/script_debugger_remote.cpp @@ -30,10 +30,10 @@ #include "script_debugger_remote.h" #include "io/ip.h" +#include "io/marshalls.h" #include "os/input.h" #include "os/os.h" #include "project_settings.h" - void ScriptDebuggerRemote::_send_video_memory() { List<ResourceUsage> usage; @@ -120,6 +120,18 @@ static ObjectID safe_get_instance_id(const Variant &p_v) { } } +void ScriptDebuggerRemote::_put_variable(const String &p_name, const Variant &p_variable) { + + packet_peer_stream->put_var(p_name); + int len = 0; + Error err = encode_variant(p_variable, NULL, len); + if (len > packet_peer_stream->get_output_buffer_max_size()) { //limit to max size + packet_peer_stream->put_var(Variant()); + } else { + packet_peer_stream->put_var(p_variable); + } +} + void ScriptDebuggerRemote::debug(ScriptLanguage *p_script, bool p_can_continue) { //this function is called when there is a debugger break (bug on script) @@ -210,14 +222,7 @@ void ScriptDebuggerRemote::debug(ScriptLanguage *p_script, bool p_can_continue) while (E) { - if (F->get().get_type() == Variant::OBJECT) { - packet_peer_stream->put_var("*" + E->get()); - String pretty_print = F->get().operator String(); - packet_peer_stream->put_var(pretty_print.ascii().get_data()); - } else { - packet_peer_stream->put_var(E->get()); - packet_peer_stream->put_var(F->get()); - } + _put_variable(E->get(), F->get()); E = E->next(); F = F->next(); @@ -231,15 +236,7 @@ void ScriptDebuggerRemote::debug(ScriptLanguage *p_script, bool p_can_continue) List<Variant>::Element *F = local_vals.front(); while (E) { - - if (F->get().get_type() == Variant::OBJECT) { - packet_peer_stream->put_var("*" + E->get()); - String pretty_print = F->get().operator String(); - packet_peer_stream->put_var(pretty_print.ascii().get_data()); - } else { - packet_peer_stream->put_var(E->get()); - packet_peer_stream->put_var(F->get()); - } + _put_variable(E->get(), F->get()); E = E->next(); F = F->next(); @@ -566,30 +563,19 @@ void ScriptDebuggerRemote::_send_object_id(ObjectID p_id) { } Variant var = obj->get(E->get().name); + packet_peer_stream->put_var(E->get().type); + //only send information that can be sent.. - if (E->get().type == Variant::OBJECT || var.get_type() == Variant::OBJECT) { - - ObjectID id2; - Object *obj = var; - if (obj) { - id2 = obj->get_instance_id(); - } else { - id2 = 0; - } + int len = 0; //test how big is this to encode + encode_variant(var, NULL, len); - packet_peer_stream->put_var(Variant::INT); //hint string - packet_peer_stream->put_var(PROPERTY_HINT_OBJECT_ID); //hint - packet_peer_stream->put_var(E->get().hint_string); //hint string - packet_peer_stream->put_var(id2); //value + if (len > packet_peer_stream->get_output_buffer_max_size()) { //limit to max size + packet_peer_stream->put_var(PROPERTY_HINT_OBJECT_TOO_BIG); + packet_peer_stream->put_var(""); + packet_peer_stream->put_var(Variant()); } else { - packet_peer_stream->put_var(E->get().type); packet_peer_stream->put_var(E->get().hint); packet_peer_stream->put_var(E->get().hint_string); - //only send information that can be sent.. - - if (var.get_type() >= Variant::DICTIONARY) { - var = Array(); //send none for now, may be to big - } packet_peer_stream->put_var(var); } } diff --git a/core/script_debugger_remote.h b/core/script_debugger_remote.h index 924e3774a2..cf75c0eb4a 100644 --- a/core/script_debugger_remote.h +++ b/core/script_debugger_remote.h @@ -126,6 +126,8 @@ class ScriptDebuggerRemote : public ScriptDebugger { Vector<FrameData> profile_frame_data; + void _put_variable(const String &p_name, const Variant &p_variable); + public: struct ResourceUsage { diff --git a/doc/base/classes.xml b/doc/base/classes.xml index 418739aa3d..f21fa2c7c0 100644 --- a/doc/base/classes.xml +++ b/doc/base/classes.xml @@ -28259,15 +28259,6 @@ <description> </description> </method> - <method name="localize" qualifiers="const"> - <return type="String"> - </return> - <argument index="0" name="message" type="String"> - </argument> - <description> - Localize (translate) a message. Only works if message localization is enabled (which it is by default). See [method set_message_localization]. - </description> - </method> <method name="notification"> <argument index="0" name="what" type="int"> </argument> @@ -28297,11 +28288,11 @@ If set to true, signal emission is blocked. </description> </method> - <method name="set_message_localization"> + <method name="set_message_translation"> <argument index="0" name="enable" type="bool"> </argument> <description> - Define whether this object can localize strings (with calls to [code]localize[/code]). Default is true. + Define whether this object can translate strings (with calls to [method tr]). Default is true. </description> </method> <method name="set_meta"> @@ -28320,6 +28311,15 @@ Set a script into the object, scripts extend the object functionality. </description> </method> + <method name="tr" qualifiers="const"> + <return type="String"> + </return> + <argument index="0" name="message" type="String"> + </argument> + <description> + Translate a message. Only works if message translation is enabled (which it is by default). See [method set_message_translation]. + </description> + </method> </methods> <signals> <signal name="script_changed"> diff --git a/editor/connections_dialog.h b/editor/connections_dialog.h index bff85941cb..849bb880d4 100644 --- a/editor/connections_dialog.h +++ b/editor/connections_dialog.h @@ -103,8 +103,6 @@ class ConnectionsDock : public VBoxContainer { ConfirmationDialog *remove_confirm; ConnectDialog *connect_dialog; - void update_tree(); - void _close(); void _connect(); void _something_selected(); @@ -121,6 +119,7 @@ public: void set_node(Node *p_node); String get_selected_type(); + void update_tree(); ConnectionsDock(EditorNode *p_editor = NULL); ~ConnectionsDock(); diff --git a/editor/editor_audio_buses.cpp b/editor/editor_audio_buses.cpp index 993429a5a4..282055be4a 100644 --- a/editor/editor_audio_buses.cpp +++ b/editor/editor_audio_buses.cpp @@ -705,8 +705,8 @@ EditorAudioBus::EditorAudioBus(EditorAudioBuses *p_buses) { effects->set_drag_forwarding(this); effects->connect("item_rmb_selected", this, "_effect_rmb"); effects->set_allow_rmb_select(true); - effects->set_single_select_cell_editing_only_when_already_selected(true); effects->set_focus_mode(FOCUS_CLICK); + effects->set_allow_reselect(true); send = memnew(OptionButton); send->set_clip_text(true); diff --git a/editor/editor_autoload_settings.cpp b/editor/editor_autoload_settings.cpp index dde94cb334..0d7874818c 100644 --- a/editor/editor_autoload_settings.cpp +++ b/editor/editor_autoload_settings.cpp @@ -580,7 +580,7 @@ EditorAutoloadSettings::EditorAutoloadSettings() { tree = memnew(Tree); tree->set_hide_root(true); tree->set_select_mode(Tree::SELECT_MULTI); - tree->set_single_select_cell_editing_only_when_already_selected(true); + tree->set_allow_reselect(true); tree->set_drag_forwarding(this); diff --git a/editor/editor_node.cpp b/editor/editor_node.cpp index 8bb5633fd7..a5f0478854 100644 --- a/editor/editor_node.cpp +++ b/editor/editor_node.cpp @@ -3940,6 +3940,7 @@ void EditorNode::_dock_select_input(const Ref<InputEvent> &p_input) { splits[i]->hide(); } + _edit_current(); _save_docks(); } } @@ -3967,6 +3968,7 @@ void EditorNode::_dock_move_left() { dock_slot[dock_popup_selected]->move_child(current, prev->get_index()); dock_slot[dock_popup_selected]->set_current_tab(dock_slot[dock_popup_selected]->get_current_tab() - 1); dock_select->update(); + _edit_current(); _save_docks(); } @@ -3979,6 +3981,7 @@ void EditorNode::_dock_move_right() { dock_slot[dock_popup_selected]->move_child(next, current->get_index()); dock_slot[dock_popup_selected]->set_current_tab(dock_slot[dock_popup_selected]->get_current_tab() + 1); dock_select->update(); + _edit_current(); _save_docks(); } diff --git a/editor/node_dock.cpp b/editor/node_dock.cpp index 0f3f4b96f5..b1a538ed2e 100644 --- a/editor/node_dock.cpp +++ b/editor/node_dock.cpp @@ -63,6 +63,11 @@ void NodeDock::_notification(int p_what) { NodeDock *NodeDock::singleton = NULL; +void NodeDock::update_lists() { + + connections->update_tree(); +} + void NodeDock::set_node(Node *p_node) { connections->set_node(p_node); diff --git a/editor/node_dock.h b/editor/node_dock.h index 0af65719c9..29e5dc5169 100644 --- a/editor/node_dock.h +++ b/editor/node_dock.h @@ -59,6 +59,8 @@ public: void show_groups(); void show_connections(); + void update_lists(); + NodeDock(); }; diff --git a/editor/plugins/path_editor_plugin.cpp b/editor/plugins/path_editor_plugin.cpp index c32ed1064f..96a98f3c48 100644 --- a/editor/plugins/path_editor_plugin.cpp +++ b/editor/plugins/path_editor_plugin.cpp @@ -222,8 +222,10 @@ void PathSpatialGizmo::redraw() { //v3p.push_back(r[i]+Vector3(0,0.2,0)); } - add_lines(v3p, PathEditorPlugin::singleton->path_material); - add_collision_segments(v3p); + if (v3p.size() > 1) { + add_lines(v3p, PathEditorPlugin::singleton->path_material); + add_collision_segments(v3p); + } if (PathEditorPlugin::singleton->get_edited_path() == path) { v3p.clear(); @@ -247,9 +249,15 @@ void PathSpatialGizmo::redraw() { } } - add_lines(v3p, PathEditorPlugin::singleton->path_thin_material); - add_handles(handles); - add_handles(sec_handles, false, true); + if (v3p.size() > 1) { + add_lines(v3p, PathEditorPlugin::singleton->path_thin_material); + } + if (handles.size()) { + add_handles(handles); + } + if (sec_handles.size()) { + add_handles(sec_handles, false, true); + } } } diff --git a/editor/plugins/script_editor_plugin.cpp b/editor/plugins/script_editor_plugin.cpp index 1873a3f58b..fc89a4b9b4 100644 --- a/editor/plugins/script_editor_plugin.cpp +++ b/editor/plugins/script_editor_plugin.cpp @@ -34,18 +34,19 @@ #include "editor/script_editor_debugger.h" #include "io/resource_loader.h" #include "io/resource_saver.h" +#include "node_dock.h" #include "os/file_access.h" #include "os/input.h" #include "os/keyboard.h" #include "os/os.h" #include "project_settings.h" #include "scene/main/viewport.h" - /*** SCRIPT EDITOR ****/ void ScriptEditorBase::_bind_methods() { ADD_SIGNAL(MethodInfo("name_changed")); + ADD_SIGNAL(MethodInfo("script_changed")); ADD_SIGNAL(MethodInfo("request_help_search", PropertyInfo(Variant::STRING, "topic"))); ADD_SIGNAL(MethodInfo("request_help_index")); ADD_SIGNAL(MethodInfo("request_open_script_at_line", PropertyInfo(Variant::OBJECT, "script"), PropertyInfo(Variant::INT, "line"))); @@ -1714,6 +1715,7 @@ bool ScriptEditor::edit(const Ref<Script> &p_script, int p_line, int p_col, bool _update_script_names(); _save_layout(); se->connect("name_changed", this, "_update_script_names"); + se->connect("script_changed", this, "_script_changed"); se->connect("request_help_search", this, "_help_search"); se->connect("request_open_script_at_line", this, "_goto_script_line"); se->connect("go_to_help", this, "_help_class_goto"); @@ -2200,6 +2202,11 @@ void ScriptEditor::register_create_script_editor_function(CreateScriptEditorFunc script_editor_funcs[script_editor_func_count++] = p_func; } +void ScriptEditor::_script_changed() { + + NodeDock::singleton->update_lists(); +} + void ScriptEditor::_bind_methods() { ClassDB::bind_method("_file_dialog_action", &ScriptEditor::_file_dialog_action); @@ -2241,6 +2248,7 @@ void ScriptEditor::_bind_methods() { ClassDB::bind_method("_history_back", &ScriptEditor::_history_back); ClassDB::bind_method("_live_auto_reload_running_scripts", &ScriptEditor::_live_auto_reload_running_scripts); ClassDB::bind_method("_unhandled_input", &ScriptEditor::_unhandled_input); + ClassDB::bind_method("_script_changed", &ScriptEditor::_script_changed); ClassDB::bind_method(D_METHOD("get_current_script"), &ScriptEditor::_get_current_script); ClassDB::bind_method(D_METHOD("get_open_scripts"), &ScriptEditor::_get_open_scripts); diff --git a/editor/plugins/script_editor_plugin.h b/editor/plugins/script_editor_plugin.h index 4614a41605..f87a20a1f0 100644 --- a/editor/plugins/script_editor_plugin.h +++ b/editor/plugins/script_editor_plugin.h @@ -318,6 +318,7 @@ class ScriptEditor : public PanelContainer { void _update_script_colors(); void _update_modified_scripts_for_external_editor(Ref<Script> p_for_script = Ref<Script>()); + void _script_changed(); int file_dialog_option; void _file_dialog_action(String p_file); diff --git a/editor/plugins/script_text_editor.cpp b/editor/plugins/script_text_editor.cpp index 422c656351..1aa9f04484 100644 --- a/editor/plugins/script_text_editor.cpp +++ b/editor/plugins/script_text_editor.cpp @@ -524,6 +524,7 @@ void ScriptTextEditor::_validate_script() { } emit_signal("name_changed"); + emit_signal("script_changed"); } static Node *_find_node_for_script(Node *p_base, Node *p_current, const Ref<Script> &p_script) { diff --git a/editor/plugins/sprite_frames_editor_plugin.cpp b/editor/plugins/sprite_frames_editor_plugin.cpp index 0f008552d0..0608ecec58 100644 --- a/editor/plugins/sprite_frames_editor_plugin.cpp +++ b/editor/plugins/sprite_frames_editor_plugin.cpp @@ -747,7 +747,7 @@ SpriteFramesEditor::SpriteFramesEditor() { animations->set_hide_root(true); animations->connect("cell_selected", this, "_animation_select"); animations->connect("item_edited", this, "_animation_name_edited"); - animations->set_single_select_cell_editing_only_when_already_selected(true); + animations->set_allow_reselect(true); anim_speed = memnew(SpinBox); vbc_animlist->add_margin_child(TTR("Speed (FPS):"), anim_speed); diff --git a/editor/property_editor.cpp b/editor/property_editor.cpp index 2f47d3e130..0ec83d8a36 100644 --- a/editor/property_editor.cpp +++ b/editor/property_editor.cpp @@ -38,6 +38,7 @@ #include "editor_node.h" #include "editor_settings.h" #include "io/image_loader.h" +#include "io/marshalls.h" #include "io/resource_loader.h" #include "multi_node_edit.h" #include "os/input.h" @@ -2320,7 +2321,15 @@ void PropertyEditor::set_item_text(TreeItem *p_item, int p_type, const String &p } break; case Variant::OBJECT: { - if (obj->get(p_name).get_type() == Variant::NIL || obj->get(p_name).operator RefPtr().is_null()) { + Ref<EncodedObjectAsID> encoded = obj->get(p_name); //for debugger and remote tools + + if (encoded.is_valid()) { + + p_item->set_text(1, "Object: " + itos(encoded->get_object_id())); + p_item->set_icon(1, Ref<Texture>()); + p_item->set_custom_as_button(1, true); + + } else if (obj->get(p_name).get_type() == Variant::NIL || obj->get(p_name).operator RefPtr().is_null()) { p_item->set_text(1, "<null>"); p_item->set_icon(1, Ref<Texture>()); p_item->set_custom_as_button(1, false); @@ -3610,7 +3619,16 @@ void PropertyEditor::update_tree() { RES res = obj->get(p.name).operator RefPtr(); - if (obj->get(p.name).get_type() == Variant::NIL || res.is_null()) { + Ref<EncodedObjectAsID> encoded = obj->get(p.name); //for debugger and remote tools + + if (encoded.is_valid()) { + + item->set_text(1, "Object: " + itos(encoded->get_object_id())); + item->set_icon(1, Ref<Texture>()); + item->set_custom_as_button(1, true); + item->set_editable(1, true); + + } else if (obj->get(p.name).get_type() == Variant::NIL || res.is_null()) { item->set_text(1, "<null>"); item->set_icon(1, Ref<Texture>()); item->set_custom_as_button(1, false); @@ -3939,6 +3957,13 @@ void PropertyEditor::_item_edited() { if (!item->is_custom_set_as_button(1)) break; + Ref<EncodedObjectAsID> encoded = obj->get(name); //for debugger and remote tools + + if (encoded.is_valid()) { + + emit_signal("object_id_selected", encoded->get_object_id()); + } + RES res = obj->get(name); if (res.is_valid()) { emit_signal("resource_selected", res.get_ref_ptr(), name); diff --git a/editor/scene_tree_dock.cpp b/editor/scene_tree_dock.cpp index ce3b85332f..e984098bd4 100644 --- a/editor/scene_tree_dock.cpp +++ b/editor/scene_tree_dock.cpp @@ -2030,6 +2030,7 @@ SceneTreeDock::SceneTreeDock(EditorNode *p_editor, Node *p_scene_root, EditorSel tb->set_tooltip(TTR("Attach a new or existing script for the selected node.")); tb->set_shortcut(ED_GET_SHORTCUT("scene_tree/attach_script")); filter_hbc->add_child(tb); + tb->hide(); button_create_script = tb; tb = memnew(ToolButton); @@ -2038,6 +2039,7 @@ SceneTreeDock::SceneTreeDock(EditorNode *p_editor, Node *p_scene_root, EditorSel tb->set_shortcut(ED_GET_SHORTCUT("scene_tree/clear_script")); filter_hbc->add_child(tb); button_clear_script = tb; + tb->hide(); scene_tree = memnew(SceneTreeEditor(false, true, true)); vbc->add_child(scene_tree); diff --git a/editor/script_editor_debugger.cpp b/editor/script_editor_debugger.cpp index 01cfdc1b57..bcf24b98f6 100644 --- a/editor/script_editor_debugger.cpp +++ b/editor/script_editor_debugger.cpp @@ -372,7 +372,13 @@ void ScriptEditorDebugger::_parse_message(const String &p_msg, const Array &p_da if (has_icon(p_data[i + 2], "EditorIcons")) it->set_icon(0, get_icon(p_data[i + 2], "EditorIcons")); it->set_metadata(0, id); + if (id == inspected_object_id) { + TreeItem *cti = it->get_parent(); //ensure selected is always uncollapsed + while (cti) { + cti->set_collapsed(false); + cti = cti->get_parent(); + } it->select(0); } @@ -385,6 +391,7 @@ void ScriptEditorDebugger::_parse_message(const String &p_msg, const Array &p_da it->set_collapsed(true); } } + lv[level] = it; } updating_scene_tree = false; @@ -439,11 +446,8 @@ void ScriptEditorDebugger::_parse_message(const String &p_msg, const Array &p_da inspected_object->last_edited_id = id; - if (tabs->get_current_tab() == 2) { - inspect_properties->edit(inspected_object); - } else { - editor->push_item(inspected_object); - } + tabs->set_current_tab(inspect_info->get_index()); + inspect_properties->edit(inspected_object); } else if (p_msg == "message:video_mem") { diff --git a/editor/spatial_editor_gizmos.cpp b/editor/spatial_editor_gizmos.cpp index 24be2095ce..0e6e7420e2 100644 --- a/editor/spatial_editor_gizmos.cpp +++ b/editor/spatial_editor_gizmos.cpp @@ -1150,7 +1150,7 @@ CameraSpatialGizmo::CameraSpatialGizmo(Camera *p_camera) { void MeshInstanceSpatialGizmo::redraw() { - Ref<ArrayMesh> m = mesh->get_mesh(); + Ref<Mesh> m = mesh->get_mesh(); if (!m.is_valid()) return; //none diff --git a/modules/visual_script/visual_script_editor.cpp b/modules/visual_script/visual_script_editor.cpp index 0f6b47c56d..9a1033e954 100644 --- a/modules/visual_script/visual_script_editor.cpp +++ b/modules/visual_script/visual_script_editor.cpp @@ -886,6 +886,8 @@ void VisualScriptEditor::_member_edited() { undo_redo->add_undo_method(this, "_update_members"); undo_redo->add_do_method(this, "_update_graph"); undo_redo->add_undo_method(this, "_update_graph"); + undo_redo->add_do_method(this, "emit_signal", "script_changed"); + undo_redo->add_undo_method(this, "emit_signal", "script_changed"); undo_redo->commit_action(); // _update_graph(); @@ -901,6 +903,8 @@ void VisualScriptEditor::_member_edited() { undo_redo->add_undo_method(script.ptr(), "rename_variable", new_name, name); undo_redo->add_do_method(this, "_update_members"); undo_redo->add_undo_method(this, "_update_members"); + undo_redo->add_do_method(this, "emit_signal", "script_changed"); + undo_redo->add_undo_method(this, "emit_signal", "script_changed"); undo_redo->commit_action(); return; //or crash because it will become invalid @@ -914,6 +918,8 @@ void VisualScriptEditor::_member_edited() { undo_redo->add_undo_method(script.ptr(), "rename_custom_signal", new_name, name); undo_redo->add_do_method(this, "_update_members"); undo_redo->add_undo_method(this, "_update_members"); + undo_redo->add_do_method(this, "emit_signal", "script_changed"); + undo_redo->add_undo_method(this, "emit_signal", "script_changed"); undo_redo->commit_action(); return; //or crash because it will become invalid @@ -1051,7 +1057,8 @@ void VisualScriptEditor::_member_button(Object *p_item, int p_column, int p_butt undo_redo->add_undo_method(this, "_update_members"); undo_redo->add_do_method(this, "_update_graph"); undo_redo->add_undo_method(this, "_update_graph"); - + undo_redo->add_do_method(this, "emit_signal", "script_changed"); + undo_redo->add_undo_method(this, "emit_signal", "script_changed"); undo_redo->commit_action(); _update_graph(); @@ -1070,6 +1077,8 @@ void VisualScriptEditor::_member_button(Object *p_item, int p_column, int p_butt undo_redo->add_undo_method(script.ptr(), "remove_variable", name); undo_redo->add_do_method(this, "_update_members"); undo_redo->add_undo_method(this, "_update_members"); + undo_redo->add_do_method(this, "emit_signal", "script_changed"); + undo_redo->add_undo_method(this, "emit_signal", "script_changed"); undo_redo->commit_action(); return; //or crash because it will become invalid } @@ -1084,6 +1093,8 @@ void VisualScriptEditor::_member_button(Object *p_item, int p_column, int p_butt undo_redo->add_undo_method(script.ptr(), "remove_custom_signal", name); undo_redo->add_do_method(this, "_update_members"); undo_redo->add_undo_method(this, "_update_members"); + undo_redo->add_do_method(this, "emit_signal", "script_changed"); + undo_redo->add_undo_method(this, "emit_signal", "script_changed"); undo_redo->commit_action(); return; //or crash because it will become invalid } @@ -3223,7 +3234,7 @@ VisualScriptEditor::VisualScriptEditor() { members->connect("button_pressed", this, "_member_button"); members->connect("item_edited", this, "_member_edited"); members->connect("cell_selected", this, "_member_selected", varray(), CONNECT_DEFERRED); - members->set_single_select_cell_editing_only_when_already_selected(true); + members->set_allow_reselect(true); members->set_hide_folding(true); members->set_drag_forwarding(this); diff --git a/platform/windows/detect.py b/platform/windows/detect.py index 4d93b3f244..882e1a808e 100644 --- a/platform/windows/detect.py +++ b/platform/windows/detect.py @@ -14,69 +14,56 @@ def get_name(): def can_build(): if (os.name == "nt"): - # building natively on windows! - if (os.getenv("VCINSTALLDIR")): + # Building natively on Windows + if (os.getenv("VCINSTALLDIR")): # MSVC return True - else: - print("\nMSVC not detected, attempting MinGW.") - mingw32 = "" - mingw64 = "" - if (os.getenv("MINGW32_PREFIX")): - mingw32 = os.getenv("MINGW32_PREFIX") - if (os.getenv("MINGW64_PREFIX")): - mingw64 = os.getenv("MINGW64_PREFIX") - - test = "gcc --version > NUL 2>&1" - if os.system(test) != 0 and os.system(mingw32 + test) != 0 and os.system(mingw64 + test) != 0: - print("- could not detect gcc.") - print("Please, make sure a path to a MinGW /bin directory is accessible into the environment PATH.\n") - return False - else: - print("- gcc detected.") + print("MSVC not detected (no VCINSTALLDIR environment variable), attempting MinGW.") + mingw32 = "" + mingw64 = "" + if (os.getenv("MINGW32_PREFIX")): + mingw32 = os.getenv("MINGW32_PREFIX") + if (os.getenv("MINGW64_PREFIX")): + mingw64 = os.getenv("MINGW64_PREFIX") + + test = "gcc --version > NUL 2>&1" + if (os.system(test) == 0 or os.system(mingw32 + test) == 0 or os.system(mingw64 + test) == 0): return True if (os.name == "posix"): - - mingw = "i586-mingw32msvc-" - mingw64 = "x86_64-w64-mingw32-" + # Cross-compiling with MinGW-w64 (old MinGW32 is not supported) mingw32 = "i686-w64-mingw32-" + mingw64 = "x86_64-w64-mingw32-" if (os.getenv("MINGW32_PREFIX")): mingw32 = os.getenv("MINGW32_PREFIX") - mingw = mingw32 if (os.getenv("MINGW64_PREFIX")): mingw64 = os.getenv("MINGW64_PREFIX") test = "gcc --version > /dev/null 2>&1" - if (os.system(mingw + test) == 0 or os.system(mingw64 + test) == 0 or os.system(mingw32 + test) == 0): + if (os.system(mingw64 + test) == 0 or os.system(mingw32 + test) == 0): return True + print("Could not detect MinGW. Ensure its binaries are in your PATH or that MINGW32_PREFIX or MINGW64_PREFIX are properly defined.") return False def get_opts(): - mingw = "" mingw32 = "" mingw64 = "" if (os.name == "posix"): - mingw = "i586-mingw32msvc-" mingw32 = "i686-w64-mingw32-" mingw64 = "x86_64-w64-mingw32-" - if os.system(mingw32 + "gcc --version > /dev/null 2>&1") != 0: - mingw32 = mingw - if (os.getenv("MINGW32_PREFIX")): mingw32 = os.getenv("MINGW32_PREFIX") - mingw = mingw32 if (os.getenv("MINGW64_PREFIX")): mingw64 = os.getenv("MINGW64_PREFIX") return [ - ('mingw_prefix', 'MinGW Prefix', mingw32), - ('mingw_prefix_64', 'MinGW Prefix 64 bits', mingw64), + ('mingw_prefix_32', 'MinGW prefix (Win32)', mingw32), + ('mingw_prefix_64', 'MinGW prefix (Win64)', mingw64), ] @@ -88,12 +75,10 @@ def get_flags(): def build_res_file(target, source, env): - cmdbase = "" if (env["bits"] == "32"): - cmdbase = env['mingw_prefix'] + cmdbase = env['mingw_prefix_32'] else: cmdbase = env['mingw_prefix_64'] - CPPPATH = env['CPPPATH'] cmdbase = cmdbase + 'windres --include-dir . ' import subprocess for x in range(len(source)): @@ -111,8 +96,10 @@ def configure(env): env.Append(CPPPATH=['#platform/windows']) - # Targeted Windows version: Vista (and later) - winver = "0x0600" # Windows Vista is the minimum target for windows builds + # Targeted Windows version: 7 (and later), minimum supported version + # XP support dropped after EOL due to missing API for IPv6 and other issues + # Vista support dropped after EOL due to GH-10243 + winver = "0x0601" if (os.name == "nt" and os.getenv("VCINSTALLDIR")): # MSVC @@ -247,7 +234,7 @@ def configure(env): env.Append(LINKFLAGS=['-static']) env.Append(LINKFLAGS=['-static-libgcc']) env.Append(LINKFLAGS=['-static-libstdc++']) - mingw_prefix = env["mingw_prefix"] + mingw_prefix = env["mingw_prefix_32"] else: env.Append(LINKFLAGS=['-static']) mingw_prefix = env["mingw_prefix_64"] diff --git a/platform/windows/os_windows.cpp b/platform/windows/os_windows.cpp index 54021b8172..72f6068eb6 100644 --- a/platform/windows/os_windows.cpp +++ b/platform/windows/os_windows.cpp @@ -63,12 +63,11 @@ __attribute__((visibility("default"))) DWORD NvOptimusEnablement = 0x00000001; #endif } -#ifndef WM_MOUSEHWHEEL -#define WM_MOUSEHWHEEL 0x020e +// Workaround mingw-w64 < 4.0 bug +#ifndef WM_TOUCH +#define WM_TOUCH 576 #endif -//#define STDOUT_FILE - extern HINSTANCE godot_hinstance; void RedirectIOToConsole() { diff --git a/scene/gui/button.cpp b/scene/gui/button.cpp index e2c9f5ecb4..5036e4f7f6 100644 --- a/scene/gui/button.cpp +++ b/scene/gui/button.cpp @@ -59,7 +59,7 @@ void Button::_notification(int p_what) { if (p_what == NOTIFICATION_TRANSLATION_CHANGED) { - xl_text = localize(text); + xl_text = tr(text); minimum_size_changed(); update(); } @@ -172,7 +172,7 @@ void Button::set_text(const String &p_text) { if (text == p_text) return; text = p_text; - xl_text = localize(p_text); + xl_text = tr(p_text); update(); _change_notify("text"); minimum_size_changed(); diff --git a/scene/gui/dialogs.cpp b/scene/gui/dialogs.cpp index d5872d92ec..ef8b0adfa9 100644 --- a/scene/gui/dialogs.cpp +++ b/scene/gui/dialogs.cpp @@ -271,7 +271,7 @@ int WindowDialog::_drag_hit_test(const Point2 &pos) const { void WindowDialog::set_title(const String &p_title) { - title = localize(p_title); + title = tr(p_title); update(); } String WindowDialog::get_title() const { diff --git a/scene/gui/file_dialog.cpp b/scene/gui/file_dialog.cpp index 197683b825..b3530c2971 100644 --- a/scene/gui/file_dialog.cpp +++ b/scene/gui/file_dialog.cpp @@ -464,7 +464,7 @@ void FileDialog::update_filters() { String flt = filters[i].get_slice(";", 0).strip_edges(); String desc = filters[i].get_slice(";", 1).strip_edges(); if (desc.length()) - filter->add_item(String(localize(desc)) + " ( " + flt + " )"); + filter->add_item(String(tr(desc)) + " ( " + flt + " )"); else filter->add_item("( " + flt + " )"); } diff --git a/scene/gui/label.cpp b/scene/gui/label.cpp index 758aafd115..b2afca8766 100644 --- a/scene/gui/label.cpp +++ b/scene/gui/label.cpp @@ -63,7 +63,7 @@ void Label::_notification(int p_what) { if (p_what == NOTIFICATION_TRANSLATION_CHANGED) { - String new_text = localize(text); + String new_text = tr(text); if (new_text == xl_text) return; //nothing new xl_text = new_text; @@ -526,7 +526,7 @@ void Label::set_text(const String &p_string) { if (text == p_string) return; text = p_string; - xl_text = localize(p_string); + xl_text = tr(p_string); word_cache_dirty = true; if (percent_visible < 1) visible_chars = get_total_character_count() * percent_visible; diff --git a/scene/gui/line_edit.cpp b/scene/gui/line_edit.cpp index 2dc60b3dcb..e91f8add31 100644 --- a/scene/gui/line_edit.cpp +++ b/scene/gui/line_edit.cpp @@ -991,7 +991,7 @@ String LineEdit::get_text() const { void LineEdit::set_placeholder(String p_text) { - placeholder = localize(p_text); + placeholder = tr(p_text); update(); } diff --git a/scene/gui/popup_menu.cpp b/scene/gui/popup_menu.cpp index a3c06a7b17..1ba936c4e9 100644 --- a/scene/gui/popup_menu.cpp +++ b/scene/gui/popup_menu.cpp @@ -96,7 +96,7 @@ Size2 PopupMenu::get_minimum_size() const { size.width += check_w + hseparation; } - String text = items[i].shortcut.is_valid() ? String(localize(items[i].shortcut->get_name())) : items[i].xl_text; + String text = items[i].shortcut.is_valid() ? String(tr(items[i].shortcut->get_name())) : items[i].xl_text; size.width += font->get_string_size(text).width; if (i > 0) size.height += vseparation; @@ -395,7 +395,7 @@ void PopupMenu::_notification(int p_what) { case NOTIFICATION_TRANSLATION_CHANGED: { for (int i = 0; i < items.size(); i++) { - items[i].xl_text = localize(items[i].text); + items[i].xl_text = tr(items[i].text); } minimum_size_changed(); @@ -475,7 +475,7 @@ void PopupMenu::_notification(int p_what) { } item_ofs.y += font->get_ascent(); - String text = items[i].shortcut.is_valid() ? String(localize(items[i].shortcut->get_name())) : items[i].xl_text; + String text = items[i].shortcut.is_valid() ? String(tr(items[i].shortcut->get_name())) : items[i].xl_text; if (!items[i].separator) { font->draw(ci, item_ofs + Point2(0, Math::floor((h - font_h) / 2.0)), text, items[i].disabled ? font_color_disabled : (i == mouse_over ? font_color_hover : font_color)); @@ -513,7 +513,7 @@ void PopupMenu::add_icon_item(const Ref<Texture> &p_icon, const String &p_label, Item item; item.icon = p_icon; item.text = p_label; - item.xl_text = localize(p_label); + item.xl_text = tr(p_label); item.accel = p_accel; item.ID = p_ID; items.push_back(item); @@ -523,7 +523,7 @@ void PopupMenu::add_item(const String &p_label, int p_ID, uint32_t p_accel) { Item item; item.text = p_label; - item.xl_text = localize(p_label); + item.xl_text = tr(p_label); item.accel = p_accel; item.ID = p_ID; items.push_back(item); @@ -534,7 +534,7 @@ void PopupMenu::add_submenu_item(const String &p_label, const String &p_submenu, Item item; item.text = p_label; - item.xl_text = localize(p_label); + item.xl_text = tr(p_label); item.ID = p_ID; item.submenu = p_submenu; items.push_back(item); @@ -546,7 +546,7 @@ void PopupMenu::add_icon_check_item(const Ref<Texture> &p_icon, const String &p_ Item item; item.icon = p_icon; item.text = p_label; - item.xl_text = localize(p_label); + item.xl_text = tr(p_label); item.accel = p_accel; item.ID = p_ID; item.checkable = true; @@ -557,7 +557,7 @@ void PopupMenu::add_check_item(const String &p_label, int p_ID, uint32_t p_accel Item item; item.text = p_label; - item.xl_text = localize(p_label); + item.xl_text = tr(p_label); item.accel = p_accel; item.ID = p_ID; item.checkable = true; @@ -628,7 +628,7 @@ void PopupMenu::set_item_text(int p_idx, const String &p_text) { ERR_FAIL_INDEX(p_idx, items.size()); items[p_idx].text = p_text; - items[p_idx].xl_text = localize(p_text); + items[p_idx].xl_text = tr(p_text); update(); } diff --git a/scene/gui/tab_container.cpp b/scene/gui/tab_container.cpp index 520de951d5..d32b899de7 100644 --- a/scene/gui/tab_container.cpp +++ b/scene/gui/tab_container.cpp @@ -231,7 +231,7 @@ void TabContainer::_notification(int p_what) { // Draw the tab contents. Control *control = tabs[i + first_tab_cache]->cast_to<Control>(); - String text = control->has_meta("_tab_name") ? String(localize(String(control->get_meta("_tab_name")))) : String(control->get_name()); + String text = control->has_meta("_tab_name") ? String(tr(String(control->get_meta("_tab_name")))) : String(control->get_name()); int x_content = tab_rect.position.x + tab_style->get_margin(MARGIN_LEFT); int top_margin = tab_style->get_margin(MARGIN_TOP); @@ -299,7 +299,7 @@ int TabContainer::_get_tab_width(int p_index) const { // Get the width of the text displayed on the tab. Ref<Font> font = get_font("font"); - String text = control->has_meta("_tab_name") ? String(localize(String(control->get_meta("_tab_name")))) : String(control->get_name()); + String text = control->has_meta("_tab_name") ? String(tr(String(control->get_meta("_tab_name")))) : String(control->get_name()); int width = font->get_string_size(text).width; // Add space for a tab icon. diff --git a/scene/gui/text_edit.cpp b/scene/gui/text_edit.cpp index 2b47539c42..324c0cd0d1 100644 --- a/scene/gui/text_edit.cpp +++ b/scene/gui/text_edit.cpp @@ -2248,6 +2248,13 @@ void TextEdit::_gui_input(const Ref<InputEvent> &p_gui_input) { #endif bool prev_char = false; int cc = cursor.column; + + if (cc == 0 && cursor.line > 0) { + cursor_set_line(cursor.line - 1); + cursor_set_column(text[cursor.line].length()); + break; + } + while (cc > 0) { bool ischar = _is_text_char(text[cursor.line][cc - 1]); @@ -2305,6 +2312,13 @@ void TextEdit::_gui_input(const Ref<InputEvent> &p_gui_input) { #endif bool prev_char = false; int cc = cursor.column; + + if (cc == text[cursor.line].length() && cursor.line < text.size() - 1) { + cursor_set_line(cursor.line + 1); + cursor_set_column(0); + break; + } + while (cc < text[cursor.line].length()) { bool ischar = _is_text_char(text[cursor.line][cc]); diff --git a/scene/gui/tree.cpp b/scene/gui/tree.cpp index fa499ff277..3e8d8aed8a 100644 --- a/scene/gui/tree.cpp +++ b/scene/gui/tree.cpp @@ -1455,7 +1455,7 @@ void Tree::select_single_item(TreeItem *p_selected, TreeItem *p_current, int p_c if (select_mode == SELECT_ROW) { - if (p_selected == p_current && !c.selected) { + if (p_selected == p_current && (!c.selected || allow_reselect)) { c.selected = true; selected_item = p_selected; selected_col = 0; @@ -1478,7 +1478,7 @@ void Tree::select_single_item(TreeItem *p_selected, TreeItem *p_current, int p_c if (!r_in_range && &selected_cell == &c) { - if (!selected_cell.selected || force_select_on_already_selected) { + if (!selected_cell.selected || allow_reselect) { selected_cell.selected = true; @@ -1743,7 +1743,7 @@ int Tree::propagate_mouse_event(const Point2i &p_pos, int x_ofs, int y_ofs, bool /* editing */ - bool bring_up_editor = force_select_on_already_selected ? (c.selected && already_selected) : c.selected; + bool bring_up_editor = allow_reselect ? (c.selected && already_selected) : c.selected; String editor_text = c.text; switch (c.mode) { @@ -3557,16 +3557,6 @@ int Tree::get_drop_mode_flags() const { return drop_mode_flags; } -void Tree::set_single_select_cell_editing_only_when_already_selected(bool p_enable) { - - force_select_on_already_selected = p_enable; -} - -bool Tree::get_single_select_cell_editing_only_when_already_selected() const { - - return force_select_on_already_selected; -} - void Tree::set_edit_checkbox_cell_only_when_checkbox_is_pressed(bool p_enable) { force_edit_checkbox_only_on_checkbox = p_enable; @@ -3587,6 +3577,15 @@ bool Tree::get_allow_rmb_select() const { return allow_rmb_select; } +void Tree::set_allow_reselect(bool p_allow) { + allow_reselect = p_allow; +} + +bool Tree::get_allow_reselect() const { + + return allow_reselect; +} + void Tree::_bind_methods() { ClassDB::bind_method(D_METHOD("_range_click_timeout"), &Tree::_range_click_timeout); @@ -3640,8 +3639,8 @@ void Tree::_bind_methods() { ClassDB::bind_method(D_METHOD("set_allow_rmb_select", "allow"), &Tree::set_allow_rmb_select); ClassDB::bind_method(D_METHOD("get_allow_rmb_select"), &Tree::get_allow_rmb_select); - ClassDB::bind_method(D_METHOD("set_single_select_cell_editing_only_when_already_selected", "enable"), &Tree::set_single_select_cell_editing_only_when_already_selected); - ClassDB::bind_method(D_METHOD("get_single_select_cell_editing_only_when_already_selected"), &Tree::get_single_select_cell_editing_only_when_already_selected); + ClassDB::bind_method(D_METHOD("set_allow_reselect", "allow"), &Tree::set_allow_reselect); + ClassDB::bind_method(D_METHOD("get_allow_reselect"), &Tree::get_allow_reselect); ADD_SIGNAL(MethodInfo("item_selected")); ADD_SIGNAL(MethodInfo("cell_selected")); @@ -3751,7 +3750,6 @@ Tree::Tree() { drop_mode_over = NULL; drop_mode_section = 0; single_select_defer = NULL; - force_select_on_already_selected = false; allow_rmb_select = false; force_edit_checkbox_only_on_checkbox = false; @@ -3760,6 +3758,8 @@ Tree::Tree() { cache.hover_item = NULL; cache.hover_cell = -1; + + allow_reselect = false; } Tree::~Tree() { diff --git a/scene/gui/tree.h b/scene/gui/tree.h index 81880122a9..1e46956cd9 100644 --- a/scene/gui/tree.h +++ b/scene/gui/tree.h @@ -490,7 +490,8 @@ private: bool allow_rmb_select; bool scrolling; - bool force_select_on_already_selected; + bool allow_reselect; + bool force_edit_checkbox_only_on_checkbox; bool hide_folding; @@ -566,15 +567,15 @@ public: void set_drop_mode_flags(int p_flags); int get_drop_mode_flags() const; - void set_single_select_cell_editing_only_when_already_selected(bool p_enable); - bool get_single_select_cell_editing_only_when_already_selected() const; - void set_edit_checkbox_cell_only_when_checkbox_is_pressed(bool p_enable); bool get_edit_checkbox_cell_only_when_checkbox_is_pressed() const; void set_allow_rmb_select(bool p_allow); bool get_allow_rmb_select() const; + void set_allow_reselect(bool p_allow); + bool get_allow_reselect() const; + void set_value_evaluator(ValueEvaluator *p_evaluator); Tree(); diff --git a/scene/main/scene_tree.cpp b/scene/main/scene_tree.cpp index 66eafa1070..2e67a1feaf 100644 --- a/scene/main/scene_tree.cpp +++ b/scene/main/scene_tree.cpp @@ -392,86 +392,11 @@ void SceneTree::input_event(const Ref<InputEvent> &p_event) { Ref<InputEvent> ev = p_event; ev->set_id(++last_id); //this should work better -#if 0 - switch(ev.type) { - - case InputEvent::MOUSE_BUTTON: { - - Matrix32 ai = root->get_final_transform().affine_inverse(); - Vector2 g = ai.xform(Vector2(ev.mouse_button.global_x,ev.mouse_button.global_y)); - Vector2 l = ai.xform(Vector2(ev->get_pos().x,ev->get_pos().y)); - ev->get_pos().x=l.x; - ev->get_pos().y=l.y; - ev.mouse_button.global_x=g.x; - ev.mouse_button.global_y=g.y; - - } break; - case InputEvent::MOUSE_MOTION: { - - Matrix32 ai = root->get_final_transform().affine_inverse(); - Vector2 g = ai.xform(Vector2(ev.mouse_motion.global_x,ev.mouse_motion.global_y)); - Vector2 l = ai.xform(Vector2(ev.mouse_motion.x,ev.mouse_motion.y)); - Vector2 r = ai.xform(Vector2(ev->get_relative().x,ev->get_relative().y)); - ev.mouse_motion.x=l.x; - ev.mouse_motion.y=l.y; - ev.mouse_motion.global_x=g.x; - ev.mouse_motion.global_y=g.y; - ev->get_relative().x=r.x; - ev->get_relative().y=r.y; - - } break; - case InputEvent::SCREEN_TOUCH: { - - Matrix32 ai = root->get_final_transform().affine_inverse(); - Vector2 t = ai.xform(Vector2(ev.screen_touch.x,ev.screen_touch.y)); - ev.screen_touch.x=t.x; - ev.screen_touch.y=t.y; - - } break; - case InputEvent::SCREEN_DRAG: { - - Matrix32 ai = root->get_final_transform().affine_inverse(); - Vector2 t = ai.xform(Vector2(ev.screen_drag.x,ev.screen_drag.y)); - Vector2 r = ai.xform(Vector2(ev.screen_drag.relative_x,ev.screen_drag.relative_y)); - Vector2 s = ai.xform(Vector2(ev.screen_drag.speed_x,ev.screen_drag.speed_y)); - ev.screen_drag.x=t.x; - ev.screen_drag.y=t.y; - ev.screen_drag.relative_x=r.x; - ev.screen_drag.relative_y=r.y; - ev.screen_drag.speed_x=s.x; - ev.screen_drag.speed_y=s.y; - } break; - } - -#endif MainLoop::input_event(ev); -#if 0 - _call_input_pause("input","_input",ev); - - call_group(GROUP_CALL_REVERSE|GROUP_CALL_REALTIME|GROUP_CALL_MULIILEVEL,"_gui_input","_gui_input",p_event); //special one for GUI, as controls use their own process check - - //call_group(GROUP_CALL_REVERSE|GROUP_CALL_REALTIME|GROUP_CALL_MULIILEVEL,"input","_input",ev); - - /* - if (ev.type==InputEvent::KEY && ev->is_pressed() && !ev->is_echo() && ev->get_scancode()==KEY_F12) { - - print_line("RAM: "+itos(Memory::get_static_mem_usage())); - print_line("DRAM: "+itos(Memory::get_dynamic_mem_usage())); - } - if (ev.type==InputEvent::KEY && ev->is_pressed() && !ev->is_echo() && ev->get_scancode()==KEY_F11) { - - Memory::dump_static_mem_to_file("memdump.txt"); - } - */ - - //transform for the rest -#else call_group_flags(GROUP_CALL_REALTIME, "_viewports", "_vp_input", ev); //special one for GUI, as controls use their own process check -#endif - if (ScriptDebugger::get_singleton() && ScriptDebugger::get_singleton()->is_remote()) { //quit from game window using F8 Ref<InputEventKey> k = ev; @@ -482,7 +407,7 @@ void SceneTree::input_event(const Ref<InputEvent> &p_event) { _flush_ugc(); root_lock--; - MessageQueue::get_singleton()->flush(); //small little hack + //MessageQueue::get_singleton()->flush(); //flushing here causes UI and other places slowness root_lock++; @@ -503,7 +428,7 @@ void SceneTree::input_event(const Ref<InputEvent> &p_event) { input_handled = true; _flush_ugc(); root_lock--; - MessageQueue::get_singleton()->flush(); //small little hack + //MessageQueue::get_singleton()->flush(); //flushing here causes UI and other places slowness } else { input_handled = true; root_lock--; diff --git a/scene/resources/sky_box.cpp b/scene/resources/sky_box.cpp index 5750960845..cc3cfe4dc0 100644 --- a/scene/resources/sky_box.cpp +++ b/scene/resources/sky_box.cpp @@ -128,7 +128,7 @@ void ProceduralSky::_radiance_changed() { VS::get_singleton()->sky_set_texture(sky, texture, size[get_radiance_size()]); } -void ProceduralSky::_update_sky() { +Ref<Image> ProceduralSky::_generate_sky() { update_queued = false; @@ -215,9 +215,7 @@ void ProceduralSky::_update_sky() { image.instance(); image->create(w, h, false, Image::FORMAT_RGBE9995, imgdata); - VS::get_singleton()->texture_allocate(texture, w, h, Image::FORMAT_RGBE9995, VS::TEXTURE_FLAG_FILTER | VS::TEXTURE_FLAG_REPEAT); - VS::get_singleton()->texture_set_data(texture, image); - _radiance_changed(); + return image; } void ProceduralSky::set_sky_top_color(const Color &p_sky_top) { @@ -385,6 +383,33 @@ RID ProceduralSky::get_rid() const { return sky; } +void ProceduralSky::_update_sky() { + + bool use_thread = true; + if (first_time) { + use_thread = false; + first_time = false; + } +#ifdef NO_THREADS + use_thread = false; +#endif + if (use_thread) { + + if (!sky_thread) { + sky_thread = Thread::create(_thread_function, this); + regen_queued = false; + } else { + regen_queued = true; + } + + } else { + Ref<Image> image = _generate_sky(); + VS::get_singleton()->texture_allocate(texture, image->get_width(), image->get_height(), Image::FORMAT_RGBE9995, VS::TEXTURE_FLAG_FILTER | VS::TEXTURE_FLAG_REPEAT); + VS::get_singleton()->texture_set_data(texture, image); + _radiance_changed(); + } +} + void ProceduralSky::_queue_update() { if (update_queued) @@ -394,6 +419,26 @@ void ProceduralSky::_queue_update() { call_deferred("_update_sky"); } +void ProceduralSky::_thread_done(const Ref<Image> &image) { + + VS::get_singleton()->texture_allocate(texture, image->get_width(), image->get_height(), Image::FORMAT_RGBE9995, VS::TEXTURE_FLAG_FILTER | VS::TEXTURE_FLAG_REPEAT); + VS::get_singleton()->texture_set_data(texture, image); + _radiance_changed(); + Thread::wait_to_finish(sky_thread); + memdelete(sky_thread); + sky_thread = NULL; + if (regen_queued) { + sky_thread = Thread::create(_thread_function, this); + regen_queued = false; + } +} + +void ProceduralSky::_thread_function(void *p_ud) { + + ProceduralSky *psky = (ProceduralSky *)p_ud; + psky->call_deferred("_thread_done", psky->_generate_sky()); +} + void ProceduralSky::_bind_methods() { ClassDB::bind_method(D_METHOD("_update_sky"), &ProceduralSky::_update_sky); @@ -446,6 +491,8 @@ void ProceduralSky::_bind_methods() { ClassDB::bind_method(D_METHOD("set_texture_size", "size"), &ProceduralSky::set_texture_size); ClassDB::bind_method(D_METHOD("get_texture_size"), &ProceduralSky::get_texture_size); + ClassDB::bind_method(D_METHOD("_thread_done", "image"), &ProceduralSky::_thread_done); + ADD_GROUP("Sky", "sky_"); ADD_PROPERTY(PropertyInfo(Variant::COLOR, "sky_top_color"), "set_sky_top_color", "get_sky_top_color"); ADD_PROPERTY(PropertyInfo(Variant::COLOR, "sky_horizon_color"), "set_sky_horizon_color", "get_sky_horizon_color"); @@ -503,12 +550,20 @@ ProceduralSky::ProceduralSky() { sun_energy = 16; texture_size = TEXTURE_SIZE_1024; + sky_thread = NULL; + regen_queued = false; + first_time = true; _queue_update(); } ProceduralSky::~ProceduralSky() { + if (sky_thread) { + Thread::wait_to_finish(sky_thread); + memdelete(sky_thread); + sky_thread = NULL; + } VS::get_singleton()->free(sky); VS::get_singleton()->free(texture); } diff --git a/scene/resources/sky_box.h b/scene/resources/sky_box.h index 8298d1b3c0..9bd60cddaf 100644 --- a/scene/resources/sky_box.h +++ b/scene/resources/sky_box.h @@ -30,8 +30,8 @@ #ifndef Sky_H #define Sky_H +#include "os/thread.h" #include "scene/resources/texture.h" - class Sky : public Resource { GDCLASS(Sky, Resource); @@ -97,6 +97,7 @@ public: }; private: + Thread *sky_thread; Color sky_top_color; Color sky_horizon_color; float sky_curve; @@ -121,12 +122,20 @@ private: RID texture; bool update_queued; + bool regen_queued; + + bool first_time; + + void _thread_done(const Ref<Image> &p_image); + static void _thread_function(void *p_ud); protected: static void _bind_methods(); virtual void _radiance_changed(); + Ref<Image> _generate_sky(); void _update_sky(); + void _queue_update(); public: diff --git a/scene/resources/style_box.cpp b/scene/resources/style_box.cpp index 48efa242e9..67bc5b30ff 100644 --- a/scene/resources/style_box.cpp +++ b/scene/resources/style_box.cpp @@ -717,7 +717,7 @@ void StyleBoxFlat::_bind_methods() { ClassDB::bind_method(D_METHOD("get_bg_color"), &StyleBoxFlat::get_bg_color); ClassDB::bind_method(D_METHOD("set_border_color", "color"), &StyleBoxFlat::set_border_color_all); - ClassDB::bind_method(D_METHOD("get_border_color", "color"), &StyleBoxFlat::get_border_color_all); + ClassDB::bind_method(D_METHOD("get_border_color"), &StyleBoxFlat::get_border_color_all); ClassDB::bind_method(D_METHOD("set_border_width_all", "width"), &StyleBoxFlat::set_border_width_all); ClassDB::bind_method(D_METHOD("get_border_width_min"), &StyleBoxFlat::get_border_width_min); diff --git a/servers/audio_server.cpp b/servers/audio_server.cpp index 3547f86eb3..f9fdd9432d 100644 --- a/servers/audio_server.cpp +++ b/servers/audio_server.cpp @@ -159,6 +159,8 @@ void AudioServer::_driver_process(int p_frames, int32_t *p_buffer) { void AudioServer::_mix_step() { + bool solo_mode = false; + for (int i = 0; i < buses.size(); i++) { Bus *bus = buses[i]; bus->index_cache = i; //might be moved around by editor, so.. @@ -166,6 +168,33 @@ void AudioServer::_mix_step() { bus->channels[k].used = false; } + + if (bus->solo) { + //solo chain + solo_mode = true; + bus->soloed = true; + do { + + if (bus != buses[0]) { + //everything has a send save for master bus + if (!bus_map.has(bus->send)) { + bus = buses[0]; //send to master + } else { + bus = bus_map[bus->send]; + if (bus->index_cache >= bus->index_cache) { //invalid, send to master + bus = buses[0]; + } + } + + bus->soloed = true; + } else { + bus = NULL; + } + + } while (bus); + } else { + bus->soloed = false; + } } //make callbacks for mixing the audio @@ -192,24 +221,26 @@ void AudioServer::_mix_step() { } //process effects - for (int j = 0; j < bus->effects.size(); j++) { + if (!bus->bypass) { + for (int j = 0; j < bus->effects.size(); j++) { - if (!bus->effects[j].enabled) - continue; + if (!bus->effects[j].enabled) + continue; - for (int k = 0; k < bus->channels.size(); k++) { + for (int k = 0; k < bus->channels.size(); k++) { - if (!bus->channels[k].active) - continue; - bus->channels[k].effect_instances[j]->process(bus->channels[k].buffer.ptr(), temp_buffer[k].ptr(), buffer_size); - } + if (!bus->channels[k].active) + continue; + bus->channels[k].effect_instances[j]->process(bus->channels[k].buffer.ptr(), temp_buffer[k].ptr(), buffer_size); + } - //swap buffers, so internal buffer always has the right data - for (int k = 0; k < bus->channels.size(); k++) { + //swap buffers, so internal buffer always has the right data + for (int k = 0; k < bus->channels.size(); k++) { - if (!buses[i]->channels[k].active) - continue; - SWAP(bus->channels[k].buffer, temp_buffer[k]); + if (!buses[i]->channels[k].active) + continue; + SWAP(bus->channels[k].buffer, temp_buffer[k]); + } } } @@ -237,7 +268,24 @@ void AudioServer::_mix_step() { AudioFrame *buf = bus->channels[k].buffer.ptr(); AudioFrame peak = AudioFrame(0, 0); + + float volume = Math::db2linear(bus->volume_db); + + if (solo_mode) { + if (!bus->soloed) { + volume = 0.0; + } + } else { + if (bus->mute) { + volume = 0.0; + } + } + + //apply volume and compute peak for (uint32_t j = 0; j < buffer_size; j++) { + + buf[j] *= volume; + float l = ABS(buf[j].l); if (l > peak.l) { peak.l = l; diff --git a/servers/audio_server.h b/servers/audio_server.h index caa07891f7..c92ff6d3a0 100644 --- a/servers/audio_server.h +++ b/servers/audio_server.h @@ -125,6 +125,8 @@ private: bool mute; bool bypass; + bool soloed; + //Each channel is a stereo pair. struct Channel { bool used; diff --git a/servers/visual/visual_server_scene.cpp b/servers/visual/visual_server_scene.cpp index 5faf0e67ca..8e21ecc189 100644 --- a/servers/visual/visual_server_scene.cpp +++ b/servers/visual/visual_server_scene.cpp @@ -1048,8 +1048,9 @@ void VisualServerScene::_update_instance(Instance *p_instance) { VSG::storage->particles_set_emission_transform(p_instance->base, p_instance->transform); } - if (p_instance->aabb.has_no_surface()) + if (p_instance->aabb.has_no_area()) { return; + } #if 0 if (p_instance->base_type == VS::INSTANCE_PARTICLES) { @@ -3278,8 +3279,9 @@ void VisualServerScene::render_probes() { void VisualServerScene::_update_dirty_instance(Instance *p_instance) { - if (p_instance->update_aabb) + if (p_instance->update_aabb) { _update_instance_aabb(p_instance); + } if (p_instance->update_materials) { diff --git a/servers/visual_server.cpp b/servers/visual_server.cpp index 65dd4d7661..dacf04f8d6 100644 --- a/servers/visual_server.cpp +++ b/servers/visual_server.cpp @@ -339,7 +339,7 @@ Error VisualServer::_surface_set_data(Array p_arrays, uint32_t p_format, uint32_ if (i == 0) { - aabb = Rect2(src[i], Vector2()); + aabb = Rect2(src[i], Vector2(0.00001, 0.00001)); //must have a bit of size } else { aabb.expand_to(src[i]); @@ -355,7 +355,7 @@ Error VisualServer::_surface_set_data(Array p_arrays, uint32_t p_format, uint32_ if (i == 0) { - aabb = Rect2(src[i], Vector2()); + aabb = Rect2(src[i], Vector2(0.00001, 0.00001)); //must have a bit of size } else { aabb.expand_to(src[i]); @@ -385,7 +385,7 @@ Error VisualServer::_surface_set_data(Array p_arrays, uint32_t p_format, uint32_ if (i == 0) { - aabb = Rect3(src[i], Vector3()); + aabb = Rect3(src[i], Vector3(0.00001, 0.00001, 0.00001)); } else { aabb.expand_to(src[i]); @@ -401,7 +401,7 @@ Error VisualServer::_surface_set_data(Array p_arrays, uint32_t p_format, uint32_ if (i == 0) { - aabb = Rect3(src[i], Vector3()); + aabb = Rect3(src[i], Vector3(0.00001, 0.00001, 0.00001)); } else { aabb.expand_to(src[i]); @@ -735,6 +735,7 @@ Error VisualServer::_surface_set_data(Array p_arrays, uint32_t p_format, uint32_ //first bptr[idx] = Rect3(); bptr[idx].position = v; + bptr[idx].size = Vector3(0.00001, 0.00001, 0.00001); //must have at least a bit of size any_valid = true; } else { bptr[idx].expand_to(v); |