summaryrefslogtreecommitdiff
path: root/scene
diff options
context:
space:
mode:
Diffstat (limited to 'scene')
-rw-r--r--scene/2d/animated_sprite.cpp1
-rw-r--r--scene/2d/line_2d.cpp1
-rw-r--r--scene/2d/mesh_instance_2d.cpp2
-rw-r--r--scene/2d/multimesh_instance_2d.cpp111
-rw-r--r--scene/2d/multimesh_instance_2d.h65
-rw-r--r--scene/2d/position_2d.cpp34
-rw-r--r--scene/2d/position_2d.h7
-rw-r--r--scene/2d/tile_map.cpp9
-rw-r--r--scene/gui/graph_node.cpp4
-rw-r--r--scene/gui/item_list.cpp20
-rw-r--r--scene/gui/line_edit.cpp5
-rw-r--r--scene/gui/option_button.cpp1
-rw-r--r--scene/gui/popup_menu.cpp56
-rw-r--r--scene/gui/popup_menu.h7
-rw-r--r--scene/gui/text_edit.cpp2
-rw-r--r--scene/gui/tree.cpp50
-rw-r--r--scene/gui/tree.h4
-rw-r--r--scene/register_scene_types.cpp16
-rw-r--r--scene/resources/default_theme/default_theme.cpp12
-rw-r--r--scene/resources/height_map_shape.cpp1
-rw-r--r--scene/resources/mesh.cpp2
-rw-r--r--scene/resources/mesh.h5
-rw-r--r--scene/resources/particles_material.cpp1
-rw-r--r--scene/resources/primitive_meshes.cpp6
-rw-r--r--scene/resources/primitive_meshes.h1
-rw-r--r--scene/resources/resource_format_text.cpp6
-rw-r--r--scene/resources/tile_set.cpp32
-rw-r--r--scene/resources/tile_set.h1
28 files changed, 415 insertions, 47 deletions
diff --git a/scene/2d/animated_sprite.cpp b/scene/2d/animated_sprite.cpp
index 25ad6bd5c9..075b0e6252 100644
--- a/scene/2d/animated_sprite.cpp
+++ b/scene/2d/animated_sprite.cpp
@@ -646,6 +646,7 @@ void AnimatedSprite::_reset_timeout() {
void AnimatedSprite::set_animation(const StringName &p_animation) {
ERR_EXPLAIN(vformat("There is no animation with name '%s'.", p_animation));
+ ERR_FAIL_COND(frames == NULL)
ERR_FAIL_COND(frames->get_animation_names().find(p_animation) == -1);
if (animation == p_animation)
diff --git a/scene/2d/line_2d.cpp b/scene/2d/line_2d.cpp
index ba06b3ebff..e116d404d6 100644
--- a/scene/2d/line_2d.cpp
+++ b/scene/2d/line_2d.cpp
@@ -105,6 +105,7 @@ void Line2D::set_point_position(int i, Vector2 pos) {
}
Vector2 Line2D::get_point_position(int i) const {
+ ERR_FAIL_INDEX_V(i, _points.size(), Vector2())
return _points.get(i);
}
diff --git a/scene/2d/mesh_instance_2d.cpp b/scene/2d/mesh_instance_2d.cpp
index b382ca7b33..bcd4bca940 100644
--- a/scene/2d/mesh_instance_2d.cpp
+++ b/scene/2d/mesh_instance_2d.cpp
@@ -50,6 +50,8 @@ void MeshInstance2D::_bind_methods() {
ClassDB::bind_method(D_METHOD("set_normal_map", "normal_map"), &MeshInstance2D::set_normal_map);
ClassDB::bind_method(D_METHOD("get_normal_map"), &MeshInstance2D::get_normal_map);
+ ADD_SIGNAL(MethodInfo("texture_changed"));
+
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "mesh", PROPERTY_HINT_RESOURCE_TYPE, "Mesh"), "set_mesh", "get_mesh");
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "texture", PROPERTY_HINT_RESOURCE_TYPE, "Texture"), "set_texture", "get_texture");
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "normal_map", PROPERTY_HINT_RESOURCE_TYPE, "Texture"), "set_normal_map", "get_normal_map");
diff --git a/scene/2d/multimesh_instance_2d.cpp b/scene/2d/multimesh_instance_2d.cpp
new file mode 100644
index 0000000000..ca75302163
--- /dev/null
+++ b/scene/2d/multimesh_instance_2d.cpp
@@ -0,0 +1,111 @@
+/*************************************************************************/
+/* multimesh_instance_2d.cpp */
+/*************************************************************************/
+/* This file is part of: */
+/* GODOT ENGINE */
+/* https://godotengine.org */
+/*************************************************************************/
+/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */
+/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */
+/* */
+/* Permission is hereby granted, free of charge, to any person obtaining */
+/* a copy of this software and associated documentation files (the */
+/* "Software"), to deal in the Software without restriction, including */
+/* without limitation the rights to use, copy, modify, merge, publish, */
+/* distribute, sublicense, and/or sell copies of the Software, and to */
+/* permit persons to whom the Software is furnished to do so, subject to */
+/* the following conditions: */
+/* */
+/* The above copyright notice and this permission notice shall be */
+/* included in all copies or substantial portions of the Software. */
+/* */
+/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */
+/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */
+/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/
+/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */
+/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */
+/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */
+/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
+/*************************************************************************/
+
+#include "multimesh_instance_2d.h"
+
+void MultiMeshInstance2D::_notification(int p_what) {
+
+ if (p_what == NOTIFICATION_DRAW) {
+ if (multimesh.is_valid()) {
+ draw_multimesh(multimesh, texture, normal_map);
+ }
+ }
+}
+
+void MultiMeshInstance2D::_bind_methods() {
+
+ ClassDB::bind_method(D_METHOD("set_multimesh", "multimesh"), &MultiMeshInstance2D::set_multimesh);
+ ClassDB::bind_method(D_METHOD("get_multimesh"), &MultiMeshInstance2D::get_multimesh);
+
+ ClassDB::bind_method(D_METHOD("set_texture", "texture"), &MultiMeshInstance2D::set_texture);
+ ClassDB::bind_method(D_METHOD("get_texture"), &MultiMeshInstance2D::get_texture);
+
+ ClassDB::bind_method(D_METHOD("set_normal_map", "normal_map"), &MultiMeshInstance2D::set_normal_map);
+ ClassDB::bind_method(D_METHOD("get_normal_map"), &MultiMeshInstance2D::get_normal_map);
+
+ ADD_SIGNAL(MethodInfo("texture_changed"));
+
+ ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "multimesh", PROPERTY_HINT_RESOURCE_TYPE, "MultiMesh"), "set_multimesh", "get_multimesh");
+ ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "texture", PROPERTY_HINT_RESOURCE_TYPE, "Texture"), "set_texture", "get_texture");
+ ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "normal_map", PROPERTY_HINT_RESOURCE_TYPE, "Texture"), "set_normal_map", "get_normal_map");
+}
+
+void MultiMeshInstance2D::set_multimesh(const Ref<MultiMesh> &p_multimesh) {
+
+ multimesh = p_multimesh;
+ update();
+}
+
+Ref<MultiMesh> MultiMeshInstance2D::get_multimesh() const {
+
+ return multimesh;
+}
+
+void MultiMeshInstance2D::set_texture(const Ref<Texture> &p_texture) {
+
+ if (p_texture == texture)
+ return;
+ texture = p_texture;
+ update();
+ emit_signal("texture_changed");
+ _change_notify("texture");
+}
+
+Ref<Texture> MultiMeshInstance2D::get_texture() const {
+
+ return texture;
+}
+
+void MultiMeshInstance2D::set_normal_map(const Ref<Texture> &p_texture) {
+
+ normal_map = p_texture;
+ update();
+}
+
+Ref<Texture> MultiMeshInstance2D::get_normal_map() const {
+
+ return normal_map;
+}
+
+Rect2 MultiMeshInstance2D::_edit_get_rect() const {
+
+ if (multimesh.is_valid()) {
+ AABB aabb = multimesh->get_aabb();
+ return Rect2(aabb.position.x, aabb.position.y, aabb.size.x, aabb.size.y);
+ }
+
+ return Node2D::_edit_get_rect();
+}
+
+MultiMeshInstance2D::MultiMeshInstance2D() {
+}
+
+MultiMeshInstance2D::~MultiMeshInstance2D() {
+}
diff --git a/scene/2d/multimesh_instance_2d.h b/scene/2d/multimesh_instance_2d.h
new file mode 100644
index 0000000000..3795497183
--- /dev/null
+++ b/scene/2d/multimesh_instance_2d.h
@@ -0,0 +1,65 @@
+/*************************************************************************/
+/* multimesh_instance_2d.h */
+/*************************************************************************/
+/* This file is part of: */
+/* GODOT ENGINE */
+/* https://godotengine.org */
+/*************************************************************************/
+/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */
+/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */
+/* */
+/* Permission is hereby granted, free of charge, to any person obtaining */
+/* a copy of this software and associated documentation files (the */
+/* "Software"), to deal in the Software without restriction, including */
+/* without limitation the rights to use, copy, modify, merge, publish, */
+/* distribute, sublicense, and/or sell copies of the Software, and to */
+/* permit persons to whom the Software is furnished to do so, subject to */
+/* the following conditions: */
+/* */
+/* The above copyright notice and this permission notice shall be */
+/* included in all copies or substantial portions of the Software. */
+/* */
+/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */
+/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */
+/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/
+/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */
+/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */
+/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */
+/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
+/*************************************************************************/
+
+#ifndef MULTIMESH_INSTANCE_2D_H
+#define MULTIMESH_INSTANCE_2D_H
+
+#include "scene/2d/node_2d.h"
+#include "scene/resources/multimesh.h"
+
+class MultiMeshInstance2D : public Node2D {
+ GDCLASS(MultiMeshInstance2D, Node2D);
+
+ Ref<MultiMesh> multimesh;
+
+ Ref<Texture> texture;
+ Ref<Texture> normal_map;
+
+protected:
+ void _notification(int p_what);
+ static void _bind_methods();
+
+public:
+ void set_multimesh(const Ref<MultiMesh> &p_multimesh);
+ Ref<MultiMesh> get_multimesh() const;
+
+ void set_texture(const Ref<Texture> &p_texture);
+ Ref<Texture> get_texture() const;
+
+ void set_normal_map(const Ref<Texture> &p_texture);
+ Ref<Texture> get_normal_map() const;
+
+ virtual Rect2 _edit_get_rect() const;
+
+ MultiMeshInstance2D();
+ ~MultiMeshInstance2D();
+};
+
+#endif // MULTIMESH_INSTANCE_2D_H
diff --git a/scene/2d/position_2d.cpp b/scene/2d/position_2d.cpp
index bed6f8a816..8bccf117fd 100644
--- a/scene/2d/position_2d.cpp
+++ b/scene/2d/position_2d.cpp
@@ -35,13 +35,15 @@
void Position2D::_draw_cross() {
- draw_line(Point2(-10, 0), Point2(+10, 0), Color(1, 0.5, 0.5));
- draw_line(Point2(0, -10), Point2(0, +10), Color(0.5, 1, 0.5));
+ float extents = get_gizmo_extents();
+ draw_line(Point2(-extents, 0), Point2(+extents, 0), Color(1, 0.5, 0.5));
+ draw_line(Point2(0, -extents), Point2(0, +extents), Color(0.5, 1, 0.5));
}
Rect2 Position2D::_edit_get_rect() const {
- return Rect2(Point2(-10, -10), Size2(20, 20));
+ float extents = get_gizmo_extents();
+ return Rect2(Point2(-extents, -extents), Size2(extents * 2, extents * 2));
}
bool Position2D::_edit_use_rect() const {
@@ -66,5 +68,31 @@ void Position2D::_notification(int p_what) {
}
}
+void Position2D::set_gizmo_extents(float p_extents) {
+ if (p_extents == DEFAULT_GIZMO_EXTENTS) {
+ set_meta("_gizmo_extents_", Variant());
+ } else {
+ set_meta("_gizmo_extents_", p_extents);
+ }
+
+ update();
+}
+
+float Position2D::get_gizmo_extents() const {
+ if (has_meta("_gizmo_extents_")) {
+ return get_meta("_gizmo_extents_");
+ } else {
+ return DEFAULT_GIZMO_EXTENTS;
+ }
+}
+
+void Position2D::_bind_methods() {
+
+ ClassDB::bind_method(D_METHOD("_set_gizmo_extents", "extents"), &Position2D::set_gizmo_extents);
+ ClassDB::bind_method(D_METHOD("_get_gizmo_extents"), &Position2D::get_gizmo_extents);
+
+ ADD_PROPERTY(PropertyInfo(Variant::REAL, "gizmo_extents", PROPERTY_HINT_RANGE, "0,1000,0.1,or_greater", PROPERTY_USAGE_EDITOR | PROPERTY_USAGE_INTERNAL), "_set_gizmo_extents", "_get_gizmo_extents");
+}
+
Position2D::Position2D() {
}
diff --git a/scene/2d/position_2d.h b/scene/2d/position_2d.h
index c95315fea3..dc9cc2df15 100644
--- a/scene/2d/position_2d.h
+++ b/scene/2d/position_2d.h
@@ -37,14 +37,21 @@ class Position2D : public Node2D {
GDCLASS(Position2D, Node2D)
+ const float DEFAULT_GIZMO_EXTENTS = 10.0;
+
void _draw_cross();
protected:
void _notification(int p_what);
+ static void _bind_methods();
public:
virtual Rect2 _edit_get_rect() const;
virtual bool _edit_use_rect() const;
+
+ void set_gizmo_extents(float p_extents);
+ float get_gizmo_extents() const;
+
Position2D();
};
diff --git a/scene/2d/tile_map.cpp b/scene/2d/tile_map.cpp
index 86be8762d4..2b43861eea 100644
--- a/scene/2d/tile_map.cpp
+++ b/scene/2d/tile_map.cpp
@@ -868,8 +868,17 @@ void TileMap::update_cell_bitmask(int p_x, int p_y) {
_make_quadrant_dirty(Q);
} else if (tile_set->tile_get_tile_mode(id) == TileSet::SINGLE_TILE) {
+
E->get().autotile_coord_x = 0;
E->get().autotile_coord_y = 0;
+ } else if (tile_set->tile_get_tile_mode(id) == TileSet::ATLAS_TILE) {
+
+ if (tile_set->autotile_get_bitmask(id, Vector2(p_x, p_y)) == TileSet::BIND_CENTER) {
+ Vector2 coord = tile_set->atlastile_get_subtile_by_priority(id, this, Vector2(p_x, p_y));
+
+ E->get().autotile_coord_x = (int)coord.x;
+ E->get().autotile_coord_y = (int)coord.y;
+ }
}
}
}
diff --git a/scene/gui/graph_node.cpp b/scene/gui/graph_node.cpp
index e8692d56d2..6463ee5ad5 100644
--- a/scene/gui/graph_node.cpp
+++ b/scene/gui/graph_node.cpp
@@ -159,9 +159,7 @@ void GraphNode::_resort() {
fit_child_in_rect(c, r);
cache_y.push_back(vofs + size.y * 0.5);
- if (vofs > 0)
- vofs += sep;
- vofs += size.y;
+ vofs += size.y + sep;
}
update();
diff --git a/scene/gui/item_list.cpp b/scene/gui/item_list.cpp
index 406c8e4f48..91b76839d7 100644
--- a/scene/gui/item_list.cpp
+++ b/scene/gui/item_list.cpp
@@ -749,9 +749,21 @@ void ItemList::_gui_input(const Ref<InputEvent> &p_event) {
search_string = "";
}
- search_string += String::chr(k->get_unicode());
- for (int i = 0; i < items.size(); i++) {
- if (items[i].text.begins_with(search_string)) {
+ if (String::chr(k->get_unicode()) != search_string)
+ search_string += String::chr(k->get_unicode());
+
+ for (int i = current + 1; i <= items.size(); i++) {
+ if (i == items.size()) {
+ if (current == 0)
+ break;
+ else
+ i = 0;
+ }
+
+ if (i == current)
+ break;
+
+ if (items[i].text.findn(search_string) == 0) {
set_current(i);
ensure_current_is_visible();
if (select_mode == SELECT_SINGLE) {
@@ -1248,7 +1260,7 @@ int ItemList::get_item_at_position(const Point2 &p_pos, bool p_exact) const {
Rect2 rc = items[i].rect_cache;
if (i % current_columns == current_columns - 1) {
- rc.size.width = get_size().width; //not right but works
+ rc.size.width = get_size().width - rc.position.x; //make sure you can still select the last item when clicking past the column
}
if (rc.has_point(pos)) {
diff --git a/scene/gui/line_edit.cpp b/scene/gui/line_edit.cpp
index 1f778bc516..58bdde1ffd 100644
--- a/scene/gui/line_edit.cpp
+++ b/scene/gui/line_edit.cpp
@@ -44,7 +44,7 @@
static bool _is_text_char(CharType c) {
- return (c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z') || (c >= '0' && c <= '9') || c == '_';
+ return !is_symbol(c);
}
void LineEdit::_gui_input(Ref<InputEvent> p_event) {
@@ -923,7 +923,8 @@ void LineEdit::cut_text() {
void LineEdit::paste_text() {
- String paste_buffer = OS::get_singleton()->get_clipboard();
+ // Strip escape characters like \n and \t as they can't be displayed on LineEdit.
+ String paste_buffer = OS::get_singleton()->get_clipboard().strip_escapes();
if (paste_buffer != "") {
diff --git a/scene/gui/option_button.cpp b/scene/gui/option_button.cpp
index 694065497a..7027fceb84 100644
--- a/scene/gui/option_button.cpp
+++ b/scene/gui/option_button.cpp
@@ -354,6 +354,7 @@ OptionButton::OptionButton() {
add_child(popup);
popup->set_pass_on_modal_close_click(false);
popup->set_notify_transform(true);
+ popup->set_allow_search(true);
popup->connect("id_pressed", this, "_selected");
popup->connect("id_focused", this, "_focused");
popup->connect("popup_hide", this, "set_pressed", varray(false));
diff --git a/scene/gui/popup_menu.cpp b/scene/gui/popup_menu.cpp
index 984307530d..2cac345dae 100644
--- a/scene/gui/popup_menu.cpp
+++ b/scene/gui/popup_menu.cpp
@@ -31,6 +31,7 @@
#include "popup_menu.h"
#include "core/os/input.h"
#include "core/os/keyboard.h"
+#include "core/os/os.h"
#include "core/print_string.h"
#include "core/translation.h"
@@ -380,6 +381,43 @@ void PopupMenu::_gui_input(const Ref<InputEvent> &p_event) {
_scroll(-pan_gesture->get_delta().y, pan_gesture->get_position());
}
}
+
+ Ref<InputEventKey> k = p_event;
+
+ if (allow_search && k.is_valid() && k->get_unicode()) {
+
+ uint64_t now = OS::get_singleton()->get_ticks_msec();
+ uint64_t diff = now - search_time_msec;
+ uint64_t max_interval = uint64_t(GLOBAL_DEF("gui/timers/incremental_search_max_interval_msec", 2000));
+ search_time_msec = now;
+
+ if (diff > max_interval) {
+ search_string = "";
+ }
+
+ if (String::chr(k->get_unicode()) != search_string)
+ search_string += String::chr(k->get_unicode());
+
+ for (int i = mouse_over + 1; i <= items.size(); i++) {
+ if (i == items.size()) {
+ if (mouse_over <= 0)
+ break;
+ else
+ i = 0;
+ }
+
+ if (i == mouse_over)
+ break;
+
+ if (items[i].text.findn(search_string) == 0) {
+ mouse_over = i;
+ emit_signal("id_focused", i);
+ update();
+ accept_event();
+ break;
+ }
+ }
+ }
}
bool PopupMenu::has_point(const Point2 &p_point) const {
@@ -1289,6 +1327,16 @@ float PopupMenu::get_submenu_popup_delay() const {
return submenu_timer->get_wait_time();
}
+void PopupMenu::set_allow_search(bool p_allow) {
+
+ allow_search = p_allow;
+}
+
+bool PopupMenu::get_allow_search() const {
+
+ return allow_search;
+}
+
void PopupMenu::set_hide_on_window_lose_focus(bool p_enabled) {
hide_on_window_lose_focus = p_enabled;
@@ -1407,6 +1455,9 @@ void PopupMenu::_bind_methods() {
ClassDB::bind_method(D_METHOD("set_hide_on_window_lose_focus", "enable"), &PopupMenu::set_hide_on_window_lose_focus);
ClassDB::bind_method(D_METHOD("is_hide_on_window_lose_focus"), &PopupMenu::is_hide_on_window_lose_focus);
+ ClassDB::bind_method(D_METHOD("set_allow_search", "allow"), &PopupMenu::set_allow_search);
+ ClassDB::bind_method(D_METHOD("get_allow_search"), &PopupMenu::get_allow_search);
+
ClassDB::bind_method(D_METHOD("_submenu_timeout"), &PopupMenu::_submenu_timeout);
ADD_PROPERTY(PropertyInfo(Variant::ARRAY, "items", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NOEDITOR | PROPERTY_USAGE_INTERNAL), "_set_items", "_get_items");
@@ -1414,6 +1465,7 @@ void PopupMenu::_bind_methods() {
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "hide_on_checkable_item_selection"), "set_hide_on_checkable_item_selection", "is_hide_on_checkable_item_selection");
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "hide_on_state_item_selection"), "set_hide_on_state_item_selection", "is_hide_on_state_item_selection");
ADD_PROPERTY(PropertyInfo(Variant::REAL, "submenu_popup_delay"), "set_submenu_popup_delay", "get_submenu_popup_delay");
+ ADD_PROPERTY(PropertyInfo(Variant::BOOL, "allow_search"), "set_allow_search", "get_allow_search");
ADD_SIGNAL(MethodInfo("id_pressed", PropertyInfo(Variant::INT, "id")));
ADD_SIGNAL(MethodInfo("id_focused", PropertyInfo(Variant::INT, "id")));
@@ -1435,6 +1487,10 @@ PopupMenu::PopupMenu() {
initial_button_mask = 0;
during_grabbed_click = false;
+ allow_search = false;
+ search_time_msec = 0;
+ search_string = "";
+
set_focus_mode(FOCUS_ALL);
set_as_toplevel(true);
set_hide_on_item_selection(true);
diff --git a/scene/gui/popup_menu.h b/scene/gui/popup_menu.h
index 687006d58d..babdd21281 100644
--- a/scene/gui/popup_menu.h
+++ b/scene/gui/popup_menu.h
@@ -112,6 +112,10 @@ class PopupMenu : public Popup {
void _ref_shortcut(Ref<ShortCut> p_sc);
void _unref_shortcut(Ref<ShortCut> p_sc);
+ bool allow_search;
+ uint64_t search_time_msec;
+ String search_string;
+
protected:
virtual bool has_point(const Point2 &p_point) const;
@@ -206,6 +210,9 @@ public:
void set_submenu_popup_delay(float p_time);
float get_submenu_popup_delay() const;
+ void set_allow_search(bool p_allow);
+ bool get_allow_search() const;
+
virtual void popup(const Rect2 &p_bounds = Rect2());
void set_hide_on_window_lose_focus(bool p_enabled);
diff --git a/scene/gui/text_edit.cpp b/scene/gui/text_edit.cpp
index 3117d8c59f..6203b15992 100644
--- a/scene/gui/text_edit.cpp
+++ b/scene/gui/text_edit.cpp
@@ -50,7 +50,7 @@ inline bool _is_symbol(CharType c) {
static bool _is_text_char(CharType c) {
- return (c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z') || (c >= '0' && c <= '9') || c == '_';
+ return !is_symbol(c);
}
static bool _is_whitespace(CharType c) {
diff --git a/scene/gui/tree.cpp b/scene/gui/tree.cpp
index e5313061da..2007ae2669 100644
--- a/scene/gui/tree.cpp
+++ b/scene/gui/tree.cpp
@@ -389,7 +389,7 @@ TreeItem *TreeItem::get_children() {
return children;
}
-TreeItem *TreeItem::get_prev_visible() {
+TreeItem *TreeItem::get_prev_visible(bool p_wrap) {
TreeItem *current = this;
@@ -398,8 +398,20 @@ TreeItem *TreeItem::get_prev_visible() {
if (!prev) {
current = current->parent;
- if (!current || (current == tree->root && tree->hide_root))
+ if (current == tree->root && tree->hide_root) {
return NULL;
+ } else if (!current) {
+ if (p_wrap) {
+ current = this;
+ TreeItem *temp = this->get_next_visible();
+ while (temp) {
+ current = temp;
+ temp = temp->get_next_visible();
+ }
+ } else {
+ return NULL;
+ }
+ }
} else {
current = prev;
@@ -415,7 +427,7 @@ TreeItem *TreeItem::get_prev_visible() {
return current;
}
-TreeItem *TreeItem::get_next_visible() {
+TreeItem *TreeItem::get_next_visible(bool p_wrap) {
TreeItem *current = this;
@@ -433,10 +445,14 @@ TreeItem *TreeItem::get_next_visible() {
current = current->parent;
}
- if (current == NULL)
- return NULL;
- else
+ if (!current) {
+ if (p_wrap)
+ return tree->root;
+ else
+ return NULL;
+ } else {
current = current->next;
+ }
}
return current;
@@ -740,8 +756,8 @@ void TreeItem::_bind_methods() {
ClassDB::bind_method(D_METHOD("get_parent"), &TreeItem::get_parent);
ClassDB::bind_method(D_METHOD("get_children"), &TreeItem::get_children);
- ClassDB::bind_method(D_METHOD("get_next_visible"), &TreeItem::get_next_visible);
- ClassDB::bind_method(D_METHOD("get_prev_visible"), &TreeItem::get_prev_visible);
+ ClassDB::bind_method(D_METHOD("get_next_visible", "wrap"), &TreeItem::get_next_visible, DEFVAL(false));
+ ClassDB::bind_method(D_METHOD("get_prev_visible", "wrap"), &TreeItem::get_prev_visible, DEFVAL(false));
ClassDB::bind_method(D_METHOD("remove_child", "child"), &TreeItem::_remove_child);
@@ -3491,6 +3507,7 @@ void Tree::scroll_to_item(TreeItem *p_item) {
TreeItem *Tree::_search_item_text(TreeItem *p_at, const String &p_find, int *r_col, bool p_selectable, bool p_backwards) {
+ TreeItem *from = p_at;
while (p_at) {
for (int i = 0; i < columns.size(); i++) {
@@ -3502,9 +3519,12 @@ TreeItem *Tree::_search_item_text(TreeItem *p_at, const String &p_find, int *r_c
}
if (p_backwards)
- p_at = p_at->get_prev_visible();
+ p_at = p_at->get_prev_visible(true);
else
- p_at = p_at->get_next_visible();
+ p_at = p_at->get_next_visible(true);
+
+ if ((p_at) == from)
+ break;
}
return NULL;
@@ -3512,10 +3532,14 @@ TreeItem *Tree::_search_item_text(TreeItem *p_at, const String &p_find, int *r_c
TreeItem *Tree::search_item_text(const String &p_find, int *r_col, bool p_selectable) {
- if (!root)
+ TreeItem *from = get_selected();
+
+ if (!from)
+ from = root;
+ if (!from)
return NULL;
- return _search_item_text(root, p_find, r_col, p_selectable);
+ return _search_item_text(from->get_next_visible(true), p_find, r_col, p_selectable);
}
void Tree::_do_incr_search(const String &p_add) {
@@ -3524,7 +3548,7 @@ void Tree::_do_incr_search(const String &p_add) {
uint64_t diff = time - last_keypress;
if (diff > uint64_t(GLOBAL_DEF("gui/timers/incremental_search_max_interval_msec", 2000)))
incr_search = p_add;
- else
+ else if (incr_search != p_add)
incr_search += p_add;
last_keypress = time;
diff --git a/scene/gui/tree.h b/scene/gui/tree.h
index 26d64baafb..45d451eb72 100644
--- a/scene/gui/tree.h
+++ b/scene/gui/tree.h
@@ -238,8 +238,8 @@ public:
TreeItem *get_parent();
TreeItem *get_children();
- TreeItem *get_prev_visible();
- TreeItem *get_next_visible();
+ TreeItem *get_prev_visible(bool p_wrap = false);
+ TreeItem *get_next_visible(bool p_wrap = false);
void remove_child(TreeItem *p_item);
diff --git a/scene/register_scene_types.cpp b/scene/register_scene_types.cpp
index 5440c88fa8..5e4cf9c2ee 100644
--- a/scene/register_scene_types.cpp
+++ b/scene/register_scene_types.cpp
@@ -48,6 +48,7 @@
#include "scene/2d/light_occluder_2d.h"
#include "scene/2d/line_2d.h"
#include "scene/2d/mesh_instance_2d.h"
+#include "scene/2d/multimesh_instance_2d.h"
#include "scene/2d/navigation_2d.h"
#include "scene/2d/parallax_background.h"
#include "scene/2d/parallax_layer.h"
@@ -144,7 +145,6 @@
#include "scene/resources/material.h"
#include "scene/resources/mesh.h"
#include "scene/resources/mesh_data_tool.h"
-#include "scene/resources/mesh_library.h"
#include "scene/resources/packed_scene.h"
#include "scene/resources/particles_material.h"
#include "scene/resources/physics_material.h"
@@ -209,6 +209,7 @@
#include "scene/3d/visibility_notifier.h"
#include "scene/animation/skeleton_ik.h"
#include "scene/resources/environment.h"
+#include "scene/resources/mesh_library.h"
#endif
static Ref<ResourceFormatSaverText> resource_saver_text;
@@ -468,7 +469,7 @@ void register_scene_types() {
OS::get_singleton()->yield(); //may take time to init
#endif
- ClassDB::register_class<MeshLibrary>();
+
AcceptDialog::set_swap_ok_cancel(GLOBAL_DEF("gui/common/swap_ok_cancel", bool(OS::get_singleton()->get_swap_ok_cancel())));
ClassDB::register_class<Shader>();
@@ -543,6 +544,7 @@ void register_scene_types() {
ClassDB::register_class<Position2D>();
ClassDB::register_class<Line2D>();
ClassDB::register_class<MeshInstance2D>();
+ ClassDB::register_class<MultiMeshInstance2D>();
ClassDB::register_virtual_class<CollisionObject2D>();
ClassDB::register_virtual_class<PhysicsBody2D>();
ClassDB::register_class<StaticBody2D>();
@@ -587,9 +589,13 @@ void register_scene_types() {
SceneTree::add_idle_callback(ParticlesMaterial::flush_changes);
ParticlesMaterial::init_shaders();
-#ifndef _3D_DISABLED
ClassDB::register_virtual_class<Mesh>();
ClassDB::register_class<ArrayMesh>();
+ ClassDB::register_class<MultiMesh>();
+ ClassDB::register_class<SurfaceTool>();
+ ClassDB::register_class<MeshDataTool>();
+
+#ifndef _3D_DISABLED
ClassDB::register_virtual_class<PrimitiveMesh>();
ClassDB::register_class<CapsuleMesh>();
ClassDB::register_class<CubeMesh>();
@@ -603,7 +609,6 @@ void register_scene_types() {
SceneTree::add_idle_callback(SpatialMaterial::flush_changes);
SpatialMaterial::init_shaders();
- ClassDB::register_class<MultiMesh>();
ClassDB::register_class<MeshLibrary>();
OS::get_singleton()->yield(); //may take time to init
@@ -619,9 +624,6 @@ void register_scene_types() {
ClassDB::register_class<ConvexPolygonShape>();
ClassDB::register_class<ConcavePolygonShape>();
- ClassDB::register_class<SurfaceTool>();
- ClassDB::register_class<MeshDataTool>();
-
OS::get_singleton()->yield(); //may take time to init
ClassDB::register_class<SpatialVelocityTracker>();
diff --git a/scene/resources/default_theme/default_theme.cpp b/scene/resources/default_theme/default_theme.cpp
index bdb6c78782..e8359e3dfe 100644
--- a/scene/resources/default_theme/default_theme.cpp
+++ b/scene/resources/default_theme/default_theme.cpp
@@ -582,14 +582,14 @@ void fill_default_theme(Ref<Theme> &theme, const Ref<Font> &default_font, const
// GraphNode
- Ref<StyleBoxTexture> graphsb = make_stylebox(graph_node_png, 6, 24, 6, 5, 16, 24, 16, 5);
- Ref<StyleBoxTexture> graphsbcomment = make_stylebox(graph_node_comment_png, 6, 24, 6, 5, 16, 24, 16, 5);
- Ref<StyleBoxTexture> graphsbcommentselected = make_stylebox(graph_node_comment_focus_png, 6, 24, 6, 5, 16, 24, 16, 5);
- Ref<StyleBoxTexture> graphsbselected = make_stylebox(graph_node_selected_png, 6, 24, 6, 5, 16, 24, 16, 5);
+ Ref<StyleBoxTexture> graphsb = make_stylebox(graph_node_png, 6, 24, 6, 5, 16, 24, 16, 6);
+ Ref<StyleBoxTexture> graphsbcomment = make_stylebox(graph_node_comment_png, 6, 24, 6, 5, 16, 24, 16, 6);
+ Ref<StyleBoxTexture> graphsbcommentselected = make_stylebox(graph_node_comment_focus_png, 6, 24, 6, 5, 16, 24, 16, 6);
+ Ref<StyleBoxTexture> graphsbselected = make_stylebox(graph_node_selected_png, 6, 24, 6, 5, 16, 24, 16, 6);
Ref<StyleBoxTexture> graphsbdefault = make_stylebox(graph_node_default_png, 4, 4, 4, 4, 6, 4, 4, 4);
Ref<StyleBoxTexture> graphsbdeffocus = make_stylebox(graph_node_default_focus_png, 4, 4, 4, 4, 6, 4, 4, 4);
- Ref<StyleBoxTexture> graph_bpoint = make_stylebox(graph_node_breakpoint_png, 6, 24, 6, 5, 16, 24, 16, 5);
- Ref<StyleBoxTexture> graph_position = make_stylebox(graph_node_position_png, 6, 24, 6, 5, 16, 24, 16, 5);
+ Ref<StyleBoxTexture> graph_bpoint = make_stylebox(graph_node_breakpoint_png, 6, 24, 6, 5, 16, 24, 16, 6);
+ Ref<StyleBoxTexture> graph_position = make_stylebox(graph_node_position_png, 6, 24, 6, 5, 16, 24, 16, 6);
//graphsb->set_expand_margin_size(MARGIN_LEFT,10);
//graphsb->set_expand_margin_size(MARGIN_RIGHT,10);
diff --git a/scene/resources/height_map_shape.cpp b/scene/resources/height_map_shape.cpp
index 8cd271dab0..f763700d52 100644
--- a/scene/resources/height_map_shape.cpp
+++ b/scene/resources/height_map_shape.cpp
@@ -85,6 +85,7 @@ void HeightMapShape::_update_shape() {
d["min_height"] = min_height;
d["max_height"] = max_height;
PhysicsServer::get_singleton()->shape_set_data(get_shape(), d);
+ Shape::_update_shape();
}
void HeightMapShape::set_map_width(int p_new) {
diff --git a/scene/resources/mesh.cpp b/scene/resources/mesh.cpp
index 67639858ce..6443b44bb6 100644
--- a/scene/resources/mesh.cpp
+++ b/scene/resources/mesh.cpp
@@ -489,6 +489,7 @@ void Mesh::_bind_methods() {
ClassDB::bind_method(D_METHOD("get_surface_count"), &Mesh::get_surface_count);
ClassDB::bind_method(D_METHOD("surface_get_arrays", "surf_idx"), &Mesh::surface_get_arrays);
ClassDB::bind_method(D_METHOD("surface_get_blend_shape_arrays", "surf_idx"), &Mesh::surface_get_blend_shape_arrays);
+ ClassDB::bind_method(D_METHOD("surface_set_material", "surf_idx", "material"), &Mesh::surface_set_material);
ClassDB::bind_method(D_METHOD("surface_get_material", "surf_idx"), &Mesh::surface_get_material);
BIND_ENUM_CONSTANT(PRIMITIVE_POINTS);
@@ -1305,7 +1306,6 @@ void ArrayMesh::_bind_methods() {
ClassDB::bind_method(D_METHOD("surface_get_array_index_len", "surf_idx"), &ArrayMesh::surface_get_array_index_len);
ClassDB::bind_method(D_METHOD("surface_get_format", "surf_idx"), &ArrayMesh::surface_get_format);
ClassDB::bind_method(D_METHOD("surface_get_primitive_type", "surf_idx"), &ArrayMesh::surface_get_primitive_type);
- ClassDB::bind_method(D_METHOD("surface_set_material", "surf_idx", "material"), &ArrayMesh::surface_set_material);
ClassDB::bind_method(D_METHOD("surface_find_by_name", "name"), &ArrayMesh::surface_find_by_name);
ClassDB::bind_method(D_METHOD("surface_set_name", "surf_idx", "name"), &ArrayMesh::surface_set_name);
ClassDB::bind_method(D_METHOD("surface_get_name", "surf_idx"), &ArrayMesh::surface_get_name);
diff --git a/scene/resources/mesh.h b/scene/resources/mesh.h
index 1457d283bd..b38791b9a6 100644
--- a/scene/resources/mesh.h
+++ b/scene/resources/mesh.h
@@ -128,6 +128,7 @@ public:
virtual Array surface_get_blend_shape_arrays(int p_surface) const = 0;
virtual uint32_t surface_get_format(int p_idx) const = 0;
virtual PrimitiveType surface_get_primitive_type(int p_idx) const = 0;
+ virtual void surface_set_material(int p_idx, const Ref<Material> &p_material) = 0;
virtual Ref<Material> surface_get_material(int p_idx) const = 0;
virtual int get_blend_shape_count() const = 0;
virtual StringName get_blend_shape_name(int p_index) const = 0;
@@ -215,8 +216,8 @@ public:
PrimitiveType surface_get_primitive_type(int p_idx) const;
bool surface_is_alpha_sorting_enabled(int p_idx) const;
- void surface_set_material(int p_idx, const Ref<Material> &p_material);
- Ref<Material> surface_get_material(int p_idx) const;
+ virtual void surface_set_material(int p_idx, const Ref<Material> &p_material);
+ virtual Ref<Material> surface_get_material(int p_idx) const;
int surface_find_by_name(const String &p_name) const;
void surface_set_name(int p_idx, const String &p_name);
diff --git a/scene/resources/particles_material.cpp b/scene/resources/particles_material.cpp
index ef67e6ea80..758475b75e 100644
--- a/scene/resources/particles_material.cpp
+++ b/scene/resources/particles_material.cpp
@@ -1186,6 +1186,7 @@ void ParticlesMaterial::_bind_methods() {
BIND_ENUM_CONSTANT(FLAG_ALIGN_Y_TO_VELOCITY);
BIND_ENUM_CONSTANT(FLAG_ROTATE_Y);
+ BIND_ENUM_CONSTANT(FLAG_DISABLE_Z);
BIND_ENUM_CONSTANT(FLAG_MAX);
BIND_ENUM_CONSTANT(EMISSION_SHAPE_POINT);
diff --git a/scene/resources/primitive_meshes.cpp b/scene/resources/primitive_meshes.cpp
index db58fe7823..04d13c8869 100644
--- a/scene/resources/primitive_meshes.cpp
+++ b/scene/resources/primitive_meshes.cpp
@@ -157,6 +157,12 @@ Mesh::PrimitiveType PrimitiveMesh::surface_get_primitive_type(int p_idx) const {
return primitive_type;
}
+void PrimitiveMesh::surface_set_material(int p_idx, const Ref<Material> &p_material) {
+ ERR_FAIL_INDEX(p_idx, 1);
+
+ set_material(p_material);
+}
+
Ref<Material> PrimitiveMesh::surface_get_material(int p_idx) const {
ERR_FAIL_INDEX_V(p_idx, 1, NULL);
diff --git a/scene/resources/primitive_meshes.h b/scene/resources/primitive_meshes.h
index 88a26801b7..0045a48736 100644
--- a/scene/resources/primitive_meshes.h
+++ b/scene/resources/primitive_meshes.h
@@ -72,6 +72,7 @@ public:
virtual Array surface_get_blend_shape_arrays(int p_surface) const;
virtual uint32_t surface_get_format(int p_idx) const;
virtual Mesh::PrimitiveType surface_get_primitive_type(int p_idx) const;
+ virtual void surface_set_material(int p_idx, const Ref<Material> &p_material);
virtual Ref<Material> surface_get_material(int p_idx) const;
virtual int get_blend_shape_count() const;
virtual StringName get_blend_shape_name(int p_index) const;
diff --git a/scene/resources/resource_format_text.cpp b/scene/resources/resource_format_text.cpp
index 6e7bb27e74..0921c0dae9 100644
--- a/scene/resources/resource_format_text.cpp
+++ b/scene/resources/resource_format_text.cpp
@@ -1712,15 +1712,15 @@ Error ResourceFormatSaverTextInstance::save(const String &p_path, const RES &p_r
Vector<StringName> groups = state->get_node_groups(i);
String header = "[node";
- header += " name=\"" + String(name) + "\"";
+ header += " name=\"" + String(name).c_escape() + "\"";
if (type != StringName()) {
header += " type=\"" + String(type) + "\"";
}
if (path != NodePath()) {
- header += " parent=\"" + String(path.simplified()) + "\"";
+ header += " parent=\"" + String(path.simplified()).c_escape() + "\"";
}
if (owner != NodePath() && owner != NodePath(".")) {
- header += " owner=\"" + String(owner.simplified()) + "\"";
+ header += " owner=\"" + String(owner.simplified()).c_escape() + "\"";
}
if (index >= 0) {
header += " index=\"" + itos(index) + "\"";
diff --git a/scene/resources/tile_set.cpp b/scene/resources/tile_set.cpp
index 5b5968c10f..d09fac47f0 100644
--- a/scene/resources/tile_set.cpp
+++ b/scene/resources/tile_set.cpp
@@ -319,6 +319,7 @@ void TileSet::_get_property_list(List<PropertyInfo> *p_list) const {
p_list->push_back(PropertyInfo(Variant::INT, pre + "autotile/spacing", PROPERTY_HINT_RANGE, "0,256,1", PROPERTY_USAGE_NOEDITOR | PROPERTY_USAGE_INTERNAL));
p_list->push_back(PropertyInfo(Variant::ARRAY, pre + "autotile/occluder_map", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NOEDITOR | PROPERTY_USAGE_INTERNAL));
p_list->push_back(PropertyInfo(Variant::ARRAY, pre + "autotile/navpoly_map", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NOEDITOR | PROPERTY_USAGE_INTERNAL));
+ p_list->push_back(PropertyInfo(Variant::ARRAY, pre + "autotile/priority_map", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NOEDITOR | PROPERTY_USAGE_INTERNAL));
p_list->push_back(PropertyInfo(Variant::ARRAY, pre + "autotile/z_index_map", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NOEDITOR | PROPERTY_USAGE_INTERNAL));
}
p_list->push_back(PropertyInfo(Variant::VECTOR2, pre + "occluder_offset"));
@@ -646,6 +647,36 @@ Vector2 TileSet::autotile_get_subtile_for_bitmask(int p_id, uint16_t p_bitmask,
}
}
+Vector2 TileSet::atlastile_get_subtile_by_priority(int p_id, const Node *p_tilemap_node, const Vector2 &p_tile_location) {
+
+ ERR_FAIL_COND_V(!tile_map.has(p_id), Vector2());
+ //First try to forward selection to script
+ if (get_script_instance() != NULL) {
+ if (get_script_instance()->has_method("_forward_atlas_subtile_selection")) {
+ Variant ret = get_script_instance()->call("_forward_atlas_subtile_selection", p_id, p_tilemap_node, p_tile_location);
+ if (ret.get_type() == Variant::VECTOR2) {
+ return ret;
+ }
+ }
+ }
+
+ Vector2 coord = tile_get_region(p_id).size / autotile_get_size(p_id);
+
+ List<Vector2> coords;
+ for (int x = 0; x < coord.x; x++) {
+ for (int y = 0; y < coord.y; y++) {
+ for (int i = 0; i < autotile_get_subtile_priority(p_id, Vector2(x, y)); i++) {
+ coords.push_back(Vector2(x, y));
+ }
+ }
+ }
+ if (coords.size() == 0) {
+ return autotile_get_icon_coordinate(p_id);
+ } else {
+ return coords[Math::random(0, (int)coords.size())];
+ }
+}
+
void TileSet::tile_set_name(int p_id, const String &p_name) {
ERR_FAIL_COND(!tile_map.has(p_id));
@@ -1141,6 +1172,7 @@ void TileSet::_bind_methods() {
BIND_VMETHOD(MethodInfo(Variant::BOOL, "_is_tile_bound", PropertyInfo(Variant::INT, "drawn_id"), PropertyInfo(Variant::INT, "neighbor_id")));
BIND_VMETHOD(MethodInfo(Variant::VECTOR2, "_forward_subtile_selection", PropertyInfo(Variant::INT, "autotile_id"), PropertyInfo(Variant::INT, "bitmask"), PropertyInfo(Variant::OBJECT, "tilemap", PROPERTY_HINT_NONE, "TileMap"), PropertyInfo(Variant::VECTOR2, "tile_location")));
+ BIND_VMETHOD(MethodInfo(Variant::VECTOR2, "_forward_atlas_subtile_selection", PropertyInfo(Variant::INT, "atlastile_id"), PropertyInfo(Variant::OBJECT, "tilemap", PROPERTY_HINT_NONE, "TileMap"), PropertyInfo(Variant::VECTOR2, "tile_location")));
BIND_ENUM_CONSTANT(BITMASK_2X2);
BIND_ENUM_CONSTANT(BITMASK_3X3_MINIMAL);
diff --git a/scene/resources/tile_set.h b/scene/resources/tile_set.h
index fb84cee218..5fc22b9fc6 100644
--- a/scene/resources/tile_set.h
+++ b/scene/resources/tile_set.h
@@ -195,6 +195,7 @@ public:
uint32_t autotile_get_bitmask(int p_id, Vector2 p_coord);
const Map<Vector2, uint32_t> &autotile_get_bitmask_map(int p_id);
Vector2 autotile_get_subtile_for_bitmask(int p_id, uint16_t p_bitmask, const Node *p_tilemap_node = NULL, const Vector2 &p_tile_location = Vector2());
+ Vector2 atlastile_get_subtile_by_priority(int p_id, const Node *p_tilemap_node = NULL, const Vector2 &p_tile_location = Vector2());
void tile_set_shape(int p_id, int p_shape_id, const Ref<Shape2D> &p_shape);
Ref<Shape2D> tile_get_shape(int p_id, int p_shape_id) const;