summaryrefslogtreecommitdiff
path: root/editor
diff options
context:
space:
mode:
Diffstat (limited to 'editor')
-rw-r--r--editor/dependency_editor.h1
-rw-r--r--editor/editor_export.h5
-rw-r--r--editor/editor_file_dialog.cpp186
-rw-r--r--editor/editor_file_dialog.h20
-rw-r--r--editor/editor_file_system.cpp6
-rw-r--r--editor/editor_help.cpp154
-rw-r--r--editor/editor_help.h3
-rw-r--r--editor/editor_node.cpp10
-rw-r--r--editor/editor_themes.cpp1
-rw-r--r--editor/filesystem_dock.cpp22
-rw-r--r--editor/filesystem_dock.h10
-rw-r--r--editor/import/editor_import_collada.cpp2
-rw-r--r--editor/import/resource_importer_scene.cpp30
-rw-r--r--editor/import/resource_importer_scene.h2
-rw-r--r--editor/plugins/abstract_polygon_2d_editor.cpp32
-rw-r--r--editor/plugins/canvas_item_editor_plugin.cpp4
-rw-r--r--editor/plugins/collision_polygon_2d_editor_plugin.cpp8
-rw-r--r--editor/plugins/curve_editor_plugin.cpp6
-rw-r--r--editor/plugins/editor_preview_plugins.cpp39
-rw-r--r--editor/plugins/line_2d_editor_plugin.cpp8
-rw-r--r--editor/plugins/navigation_polygon_editor_plugin.cpp8
-rw-r--r--editor/plugins/polygon_2d_editor_plugin.cpp8
-rw-r--r--editor/plugins/script_editor_plugin.cpp12
-rw-r--r--editor/plugins/script_editor_plugin.h3
-rw-r--r--editor/plugins/script_text_editor.cpp2
-rw-r--r--editor/project_manager.cpp2
-rw-r--r--editor/property_editor.cpp79
-rw-r--r--editor/property_editor.h18
28 files changed, 468 insertions, 213 deletions
diff --git a/editor/dependency_editor.h b/editor/dependency_editor.h
index 9b0aca67d5..0cc153945d 100644
--- a/editor/dependency_editor.h
+++ b/editor/dependency_editor.h
@@ -35,6 +35,7 @@
#include "scene/gui/tab_container.h"
#include "scene/gui/tree.h"
+class EditorFileDialog;
class EditorFileSystemDirectory;
class EditorNode;
diff --git a/editor/editor_export.h b/editor/editor_export.h
index 346c3b58e1..215a770a12 100644
--- a/editor/editor_export.h
+++ b/editor/editor_export.h
@@ -122,8 +122,9 @@ struct SharedObject {
String path;
Vector<String> tags;
- SharedObject(const String &p_path, const Vector<String> &p_tags)
- : path(p_path), tags(p_tags) {
+ SharedObject(const String &p_path, const Vector<String> &p_tags) :
+ path(p_path),
+ tags(p_tags) {
}
SharedObject() {}
diff --git a/editor/editor_file_dialog.cpp b/editor/editor_file_dialog.cpp
index eb5af2eaeb..eaa57fa46b 100644
--- a/editor/editor_file_dialog.cpp
+++ b/editor/editor_file_dialog.cpp
@@ -28,12 +28,13 @@
/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
/*************************************************************************/
#include "editor_file_dialog.h"
-
+#include "dependency_editor.h"
#include "editor_resource_preview.h"
#include "editor_scale.h"
#include "editor_settings.h"
#include "os/file_access.h"
#include "os/keyboard.h"
+#include "os/os.h"
#include "print_string.h"
#include "scene/gui/center_container.h"
#include "scene/gui/label.h"
@@ -159,6 +160,10 @@ void EditorFileDialog::_unhandled_input(const Ref<InputEvent> &p_event) {
_make_dir();
handled = true;
}
+ if (ED_IS_SHORTCUT("file_dialog/delete", p_event)) {
+ _delete_items();
+ handled = true;
+ }
if (ED_IS_SHORTCUT("file_dialog/focus_path", p_event)) {
dir->grab_focus();
handled = true;
@@ -512,6 +517,106 @@ void EditorFileDialog::_item_dc_selected(int p_item) {
}
}
+void EditorFileDialog::_item_list_item_rmb_selected(int p_item, const Vector2 &p_pos) {
+
+ // Right click on specific file(s) or folder(s).
+ item_menu->clear();
+ item_menu->set_size(Size2(1, 1));
+
+ // Allow specific actions only on one item.
+ bool single_item_selected = item_list->get_selected_items().size() == 1;
+
+ // Disallow deleting the .import folder, Godot kills a cat if you do and it is possibly a senseless novice action.
+ bool allow_delete = true;
+ for (int i = 0; i < item_list->get_item_count(); i++) {
+ if (!item_list->is_selected(i)) {
+ continue;
+ }
+ Dictionary item_meta = item_list->get_item_metadata(i);
+ if (item_meta["path"] == "res://.import") {
+ allow_delete = false;
+ break;
+ }
+ }
+
+ if (single_item_selected) {
+ item_menu->add_icon_item(get_icon("CopyNodePath", "EditorIcons"), TTR("Copy Path"), ITEM_MENU_COPY_PATH);
+ }
+ if (allow_delete) {
+ item_menu->add_icon_item(get_icon("Remove", "EditorIcons"), TTR("Delete"), ITEM_MENU_DELETE, KEY_DELETE);
+ }
+ if (single_item_selected) {
+ item_menu->add_separator();
+ item_menu->add_icon_item(get_icon("Filesystem", "EditorIcons"), TTR("Show In File Manager"), ITEM_MENU_SHOW_IN_EXPLORER);
+ }
+
+ if (item_menu->get_item_count() > 0) {
+ item_menu->set_position(item_list->get_global_position() + p_pos);
+ item_menu->popup();
+ }
+}
+
+void EditorFileDialog::_item_list_rmb_clicked(const Vector2 &p_pos) {
+
+ // Right click on folder background. Deselect all files so that actions are applied on the current folder.
+ for (int i = 0; i < item_list->get_item_count(); i++) {
+ item_list->unselect(i);
+ }
+
+ item_menu->clear();
+ item_menu->set_size(Size2(1, 1));
+
+ if (can_create_dir) {
+ item_menu->add_icon_item(get_icon("folder", "FileDialog"), TTR("New Folder.."), ITEM_MENU_NEW_FOLDER, KEY_MASK_CMD | KEY_N);
+ }
+ item_menu->add_icon_item(get_icon("Reload", "EditorIcons"), TTR("Refresh"), ITEM_MENU_REFRESH, KEY_F5);
+ item_menu->add_separator();
+ item_menu->add_icon_item(get_icon("Filesystem", "EditorIcons"), TTR("Show In File Manager"), ITEM_MENU_SHOW_IN_EXPLORER);
+
+ item_menu->set_position(item_list->get_global_position() + p_pos);
+ item_menu->popup();
+}
+
+void EditorFileDialog::_item_menu_id_pressed(int p_option) {
+
+ switch (p_option) {
+
+ case ITEM_MENU_COPY_PATH: {
+ Dictionary item_meta = item_list->get_item_metadata(item_list->get_current());
+ OS::get_singleton()->set_clipboard(item_meta["path"]);
+ } break;
+
+ case ITEM_MENU_DELETE: {
+ _delete_items();
+ } break;
+
+ case ITEM_MENU_REFRESH: {
+ invalidate();
+ } break;
+
+ case ITEM_MENU_NEW_FOLDER: {
+ _make_dir();
+ } break;
+
+ case ITEM_MENU_SHOW_IN_EXPLORER: {
+ String path;
+ int idx = item_list->get_current();
+ if (idx == -1 || item_list->get_selected_items().size() == 0) {
+ // Folder background was clicked. Open this folder.
+ path = ProjectSettings::get_singleton()->globalize_path(dir_access->get_current_dir());
+ } else {
+ // Specific item was clicked. Open folders directly, or the folder containing a selected file.
+ Dictionary item_meta = item_list->get_item_metadata(idx);
+ path = ProjectSettings::get_singleton()->globalize_path(item_meta["path"]);
+ if (!item_meta["dir"]) {
+ path = path.get_base_dir();
+ }
+ }
+ OS::get_singleton()->shell_open(String("file://") + path);
+ } break;
+ }
+}
+
bool EditorFileDialog::_is_open_should_be_disabled() {
if (mode == MODE_OPEN_ANY || mode == MODE_SAVE_FILE)
@@ -617,7 +722,7 @@ void EditorFileDialog::update_file_list() {
Dictionary d;
d["name"] = dir_name;
- d["path"] = String();
+ d["path"] = cdir.plus_file(dir_name);
d["dir"] = true;
item_list->set_item_metadata(item_list->get_item_count() - 1, d);
@@ -657,8 +762,6 @@ void EditorFileDialog::update_file_list() {
}
}
- String base_dir = dir_access->get_current_dir();
-
while (!files.empty()) {
bool match = patterns.empty();
@@ -679,7 +782,7 @@ void EditorFileDialog::update_file_list() {
if (get_icon_func) {
- Ref<Texture> icon = get_icon_func(base_dir.plus_file(files.front()->get()));
+ Ref<Texture> icon = get_icon_func(cdir.plus_file(files.front()->get()));
//ti->set_icon(0,icon);
if (display_mode == DISPLAY_THUMBNAILS) {
@@ -698,12 +801,11 @@ void EditorFileDialog::update_file_list() {
Dictionary d;
d["name"] = files.front()->get();
d["dir"] = false;
- String fullpath = base_dir.plus_file(files.front()->get());
-
+ String fullpath = cdir.plus_file(files.front()->get());
if (display_mode == DISPLAY_THUMBNAILS) {
EditorResourcePreview::get_singleton()->queue_resource_preview(fullpath, this, "_thumbnail_result", fullpath);
}
- d["path"] = base_dir.plus_file(files.front()->get());
+ d["path"] = fullpath;
//ti->set_metadata(0,d);
item_list->set_item_metadata(item_list->get_item_count() - 1, d);
@@ -723,7 +825,7 @@ void EditorFileDialog::update_file_list() {
fav_down->set_disabled(true);
get_ok()->set_disabled(_is_open_should_be_disabled());
for (int i = 0; i < favorites->get_item_count(); i++) {
- if (favorites->get_item_metadata(i) == base_dir) {
+ if (favorites->get_item_metadata(i) == cdir) {
favorites->select(i);
favorite->set_pressed(true);
if (i > 0) {
@@ -854,27 +956,27 @@ void EditorFileDialog::set_mode(Mode p_mode) {
case MODE_OPEN_FILE:
get_ok()->set_text(TTR("Open"));
set_title(TTR("Open a File"));
- makedir->hide();
+ can_create_dir = false;
break;
case MODE_OPEN_FILES:
get_ok()->set_text(TTR("Open"));
set_title(TTR("Open File(s)"));
- makedir->hide();
+ can_create_dir = false;
break;
case MODE_OPEN_DIR:
get_ok()->set_text(TTR("Open"));
set_title(TTR("Open a Directory"));
- makedir->show();
+ can_create_dir = true;
break;
case MODE_OPEN_ANY:
get_ok()->set_text(TTR("Open"));
set_title(TTR("Open a File or Directory"));
- makedir->show();
+ can_create_dir = true;
break;
case MODE_SAVE_FILE:
get_ok()->set_text(TTR("Save"));
set_title(TTR("Save a File"));
- makedir->show();
+ can_create_dir = true;
break;
}
@@ -883,6 +985,12 @@ void EditorFileDialog::set_mode(Mode p_mode) {
} else {
item_list->set_select_mode(ItemList::SELECT_SINGLE);
}
+
+ if (can_create_dir) {
+ makedir->show();
+ } else {
+ makedir->hide();
+ }
}
EditorFileDialog::Mode EditorFileDialog::get_mode() const {
@@ -954,6 +1062,28 @@ void EditorFileDialog::_make_dir() {
makedirname->grab_focus();
}
+void EditorFileDialog::_delete_items() {
+
+ // Collect the selected folders and files to delete and check them in the deletion dependency dialog.
+ Vector<String> folders;
+ Vector<String> files;
+ for (int i = 0; i < item_list->get_item_count(); i++) {
+ if (!item_list->is_selected(i)) {
+ continue;
+ }
+ Dictionary item_meta = item_list->get_item_metadata(i);
+ if (item_meta["dir"]) {
+ folders.push_back(item_meta["path"]);
+ } else {
+ files.push_back(item_meta["path"]);
+ }
+ }
+ if (folders.size() + files.size() > 0) {
+ remove_dialog->set_size(Size2(1, 1));
+ remove_dialog->show(folders, files);
+ }
+}
+
void EditorFileDialog::_select_drive(int p_idx) {
String d = drives->get_item_text(p_idx);
@@ -1181,6 +1311,9 @@ void EditorFileDialog::_bind_methods() {
ClassDB::bind_method(D_METHOD("_item_selected"), &EditorFileDialog::_item_selected);
ClassDB::bind_method(D_METHOD("_items_clear_selection"), &EditorFileDialog::_items_clear_selection);
+ ClassDB::bind_method(D_METHOD("_item_list_item_rmb_selected"), &EditorFileDialog::_item_list_item_rmb_selected);
+ ClassDB::bind_method(D_METHOD("_item_list_rmb_clicked"), &EditorFileDialog::_item_list_rmb_clicked);
+ ClassDB::bind_method(D_METHOD("_item_menu_id_pressed"), &EditorFileDialog::_item_menu_id_pressed);
ClassDB::bind_method(D_METHOD("_item_db_selected"), &EditorFileDialog::_item_dc_selected);
ClassDB::bind_method(D_METHOD("_dir_entered"), &EditorFileDialog::_dir_entered);
ClassDB::bind_method(D_METHOD("_file_entered"), &EditorFileDialog::_file_entered);
@@ -1232,6 +1365,15 @@ void EditorFileDialog::_bind_methods() {
ADD_SIGNAL(MethodInfo("files_selected", PropertyInfo(Variant::POOL_STRING_ARRAY, "paths")));
ADD_SIGNAL(MethodInfo("dir_selected", PropertyInfo(Variant::STRING, "dir")));
+ ADD_PROPERTY(PropertyInfo(Variant::INT, "access", PROPERTY_HINT_ENUM, "Resources,User data,File system"), "set_access", "get_access");
+ ADD_PROPERTY(PropertyInfo(Variant::INT, "display_mode", PROPERTY_HINT_ENUM, "Thumbnails,List"), "set_display_mode", "get_display_mode");
+ ADD_PROPERTY(PropertyInfo(Variant::INT, "mode", PROPERTY_HINT_ENUM, "Open one,Open many,Open folder,Open any,Save"), "set_mode", "get_mode");
+ ADD_PROPERTY(PropertyInfo(Variant::STRING, "current_dir", PROPERTY_HINT_DIR), "set_current_dir", "get_current_dir");
+ ADD_PROPERTY(PropertyInfo(Variant::STRING, "current_file", PROPERTY_HINT_FILE, "*"), "set_current_file", "get_current_file");
+ ADD_PROPERTY(PropertyInfo(Variant::STRING, "current_path"), "set_current_path", "get_current_path");
+ ADD_PROPERTY(PropertyInfo(Variant::BOOL, "show_hidden_files"), "set_show_hidden_files", "is_showing_hidden_files");
+ ADD_PROPERTY(PropertyInfo(Variant::BOOL, "disable_overwrite_warning"), "set_disable_overwrite_warning", "is_overwrite_warning_disabled");
+
BIND_ENUM_CONSTANT(MODE_OPEN_FILE);
BIND_ENUM_CONSTANT(MODE_OPEN_FILES);
BIND_ENUM_CONSTANT(MODE_OPEN_DIR);
@@ -1317,6 +1459,7 @@ EditorFileDialog::EditorFileDialog() {
ED_SHORTCUT("file_dialog/toggle_favorite", TTR("Toggle Favorite"), KEY_MASK_ALT | KEY_F);
ED_SHORTCUT("file_dialog/toggle_mode", TTR("Toggle Mode"), KEY_MASK_ALT | KEY_V);
ED_SHORTCUT("file_dialog/create_folder", TTR("Create Folder"), KEY_MASK_CMD | KEY_N);
+ ED_SHORTCUT("file_dialog/delete", TTR("Delete"), KEY_DELETE);
ED_SHORTCUT("file_dialog/focus_path", TTR("Focus Path"), KEY_MASK_CMD | KEY_D);
ED_SHORTCUT("file_dialog/move_favorite_up", TTR("Move Favorite Up"), KEY_MASK_CMD | KEY_UP);
ED_SHORTCUT("file_dialog/move_favorite_down", TTR("Move Favorite Down"), KEY_MASK_CMD | KEY_DOWN);
@@ -1423,10 +1566,21 @@ EditorFileDialog::EditorFileDialog() {
list_vb->add_child(memnew(Label(TTR("Directories & Files:"))));
preview_hb->add_child(list_vb);
+ // Item (files and folders) list with context menu
+
item_list = memnew(ItemList);
item_list->set_v_size_flags(SIZE_EXPAND_FILL);
+ item_list->connect("item_rmb_selected", this, "_item_list_item_rmb_selected");
+ item_list->connect("rmb_clicked", this, "_item_list_rmb_clicked");
+ item_list->set_allow_rmb_select(true);
list_vb->add_child(item_list);
+ item_menu = memnew(PopupMenu);
+ item_menu->connect("id_pressed", this, "_item_menu_id_pressed");
+ add_child(item_menu);
+
+ // Other stuff
+
preview_vb = memnew(VBoxContainer);
preview_hb->add_child(preview_vb);
CenterContainer *prev_cc = memnew(CenterContainer);
@@ -1465,9 +1619,11 @@ EditorFileDialog::EditorFileDialog() {
confirm_save = memnew(ConfirmationDialog);
confirm_save->set_as_toplevel(true);
add_child(confirm_save);
-
confirm_save->connect("confirmed", this, "_save_confirm_pressed");
+ remove_dialog = memnew(DependencyRemoveDialog);
+ add_child(remove_dialog);
+
makedialog = memnew(ConfirmationDialog);
makedialog->set_title(TTR("Create Folder"));
VBoxContainer *makevb = memnew(VBoxContainer);
diff --git a/editor/editor_file_dialog.h b/editor/editor_file_dialog.h
index 0599d222f3..f4a9a174e7 100644
--- a/editor/editor_file_dialog.h
+++ b/editor/editor_file_dialog.h
@@ -39,6 +39,9 @@
#include "scene/gui/split_container.h"
#include "scene/gui/texture_rect.h"
#include "scene/gui/tool_button.h"
+
+class DependencyRemoveDialog;
+
/**
@author Juan Linietsky <reduzio@gmail.com>
*/
@@ -75,6 +78,14 @@ public:
static RegisterFunc unregister_func;
private:
+ enum ItemMenu {
+ ITEM_MENU_COPY_PATH,
+ ITEM_MENU_DELETE,
+ ITEM_MENU_REFRESH,
+ ITEM_MENU_NEW_FOLDER,
+ ITEM_MENU_SHOW_IN_EXPLORER
+ };
+
ConfirmationDialog *makedialog;
LineEdit *makedirname;
@@ -83,6 +94,7 @@ private:
//Button *action;
VBoxContainer *vbox;
Mode mode;
+ bool can_create_dir;
LineEdit *dir;
ToolButton *dir_prev;
@@ -91,6 +103,7 @@ private:
OptionButton *drives;
ItemList *item_list;
+ PopupMenu *item_menu;
TextureRect *preview;
VBoxContainer *preview_vb;
HSplitContainer *list_hb;
@@ -100,6 +113,7 @@ private:
OptionButton *filter;
DirAccess *dir_access;
ConfirmationDialog *confirm_save;
+ DependencyRemoveDialog *remove_dialog;
ToolButton *mode_thumbnails;
ToolButton *mode_list;
@@ -146,6 +160,10 @@ private:
void _items_clear_selection();
void _item_dc_selected(int p_item);
+ void _item_list_item_rmb_selected(int p_item, const Vector2 &p_pos);
+ void _item_list_rmb_clicked(const Vector2 &p_pos);
+ void _item_menu_id_pressed(int p_option);
+
void _select_drive(int p_idx);
void _dir_entered(String p_dir);
void _file_entered(const String &p_file);
@@ -156,6 +174,8 @@ private:
void _make_dir();
void _make_dir_confirm();
+ void _delete_items();
+
void _update_drives();
void _go_up();
diff --git a/editor/editor_file_system.cpp b/editor/editor_file_system.cpp
index 1cc518ff31..d462cce908 100644
--- a/editor/editor_file_system.cpp
+++ b/editor/editor_file_system.cpp
@@ -1244,8 +1244,10 @@ void EditorFileSystem::update_file(const String &p_file) {
if (!FileAccess::exists(p_file)) {
//was removed
_delete_internal_files(p_file);
- memdelete(fs->files[cpos]);
- fs->files.remove(cpos);
+ if (cpos != -1) { // Might've never been part of the editor file system (*.* files deleted in Open dialog).
+ memdelete(fs->files[cpos]);
+ fs->files.remove(cpos);
+ }
call_deferred("emit_signal", "filesystem_changed"); //update later
return;
}
diff --git a/editor/editor_help.cpp b/editor/editor_help.cpp
index 5fc27c2e3c..8f427582ae 100644
--- a/editor/editor_help.cpp
+++ b/editor/editor_help.cpp
@@ -78,50 +78,40 @@ void EditorHelpSearch::_sbox_input(const Ref<InputEvent> &p_ie) {
}
}
-void EditorHelpSearch::_update_search() {
+class EditorHelpSearch::IncrementalSearch : public Reference {
+ String term;
+ TreeItem *root;
- search_options->clear();
- search_options->set_hide_root(true);
+ EditorHelpSearch *search;
+ Tree *search_options;
- /*
- TreeItem *root = search_options->create_item();
- _parse_fs(EditorFileSystem::get_singleton()->get_filesystem());
-*/
+ DocData *doc;
+ Ref<Texture> def_icon;
- List<StringName> type_list;
- ClassDB::get_class_list(&type_list);
+ int phase;
+ Map<String, DocData::ClassDoc>::Element *iterator;
- DocData *doc = EditorHelp::get_doc_data();
- String term = search_box->get_text();
- if (term.length() < 2)
- return;
-
- TreeItem *root = search_options->create_item();
-
- Ref<Texture> def_icon = get_icon("Node", "EditorIcons");
- //classes first
- for (Map<String, DocData::ClassDoc>::Element *E = doc->class_list.front(); E; E = E->next()) {
+ void phase1(Map<String, DocData::ClassDoc>::Element *E) {
if (E->key().findn(term) != -1) {
TreeItem *item = search_options->create_item(root);
item->set_metadata(0, "class_name:" + E->key());
item->set_text(0, E->key() + " (Class)");
- if (has_icon(E->key(), "EditorIcons"))
- item->set_icon(0, get_icon(E->key(), "EditorIcons"));
+ if (search->has_icon(E->key(), "EditorIcons"))
+ item->set_icon(0, search->get_icon(E->key(), "EditorIcons"));
else
item->set_icon(0, def_icon);
}
}
- //class methods, etc second
- for (Map<String, DocData::ClassDoc>::Element *E = doc->class_list.front(); E; E = E->next()) {
+ void phase2(Map<String, DocData::ClassDoc>::Element *E) {
DocData::ClassDoc &c = E->get();
Ref<Texture> cicon;
- if (has_icon(E->key(), "EditorIcons"))
- cicon = get_icon(E->key(), "EditorIcons");
+ if (search->has_icon(E->key(), "EditorIcons"))
+ cicon = search->get_icon(E->key(), "EditorIcons");
else
cicon = def_icon;
@@ -180,72 +170,80 @@ void EditorHelpSearch::_update_search() {
}
}
- //same but descriptions
+ bool slice() {
- for (Map<String, DocData::ClassDoc>::Element *E = doc->class_list.front(); E; E = E->next()) {
+ if (phase > 2)
+ return true;
- DocData::ClassDoc &c = E->get();
+ if (iterator) {
- Ref<Texture> cicon;
- if (has_icon(E->key(), "EditorIcons"))
- cicon = get_icon(E->key(), "EditorIcons");
- else
- cicon = def_icon;
+ switch (phase) {
+
+ case 1: {
+ phase1(iterator);
+ } break;
+ case 2: {
+ phase2(iterator);
+ } break;
+ default: {
+ WARN_PRINT("illegal phase in IncrementalSearch");
+ return true;
+ }
+ }
- if (c.description.findn(term) != -1) {
+ iterator = iterator->next();
+ } else {
- TreeItem *item = search_options->create_item(root);
- item->set_metadata(0, "class_desc:" + E->key());
- item->set_text(0, E->key() + " (Class Description)");
- item->set_icon(0, cicon);
+ phase += 1;
+ iterator = doc->class_list.front();
}
- for (int i = 0; i < c.methods.size(); i++) {
+ return false;
+ }
- if (c.methods[i].description.findn(term) != -1) {
+public:
+ IncrementalSearch(EditorHelpSearch *p_search, Tree *p_search_options, const String &p_term)
+ : search(p_search), search_options(p_search_options) {
- TreeItem *item = search_options->create_item(root);
- item->set_metadata(0, "class_method_desc:" + E->key() + ":" + c.methods[i].name);
- item->set_text(0, E->key() + "." + c.methods[i].name + " (Method Description)");
- item->set_icon(0, cicon);
- }
- }
-
- for (int i = 0; i < c.signals.size(); i++) {
+ def_icon = search->get_icon("Node", "EditorIcons");
+ doc = EditorHelp::get_doc_data();
- if (c.signals[i].description.findn(term) != -1) {
+ term = p_term;
- TreeItem *item = search_options->create_item(root);
- item->set_metadata(0, "class_signal:" + E->key() + ":" + c.signals[i].name);
- item->set_text(0, E->key() + "." + c.signals[i].name + " (Signal Description)");
- item->set_icon(0, cicon);
- }
- }
+ root = search_options->create_item();
+ phase = 0;
+ iterator = 0;
+ }
- for (int i = 0; i < c.constants.size(); i++) {
+ bool empty() const {
- if (c.constants[i].description.findn(term) != -1) {
+ return root->get_children() == NULL;
+ }
- TreeItem *item = search_options->create_item(root);
- item->set_metadata(0, "class_constant:" + E->key() + ":" + c.constants[i].name);
- item->set_text(0, E->key() + "." + c.constants[i].name + " (Constant Description)");
- item->set_icon(0, cicon);
- }
- }
+ bool work(uint64_t slot = 1000000 / 10) {
- for (int i = 0; i < c.properties.size(); i++) {
+ const uint64_t until = OS::get_singleton()->get_ticks_usec() + slot;
- if (c.properties[i].description.findn(term) != -1) {
+ while (!slice()) {
- TreeItem *item = search_options->create_item(root);
- item->set_metadata(0, "class_property_desc:" + E->key() + ":" + c.properties[i].name);
- item->set_text(0, E->key() + "." + c.properties[i].name + " (Property Description)");
- item->set_icon(0, cicon);
- }
+ if (OS::get_singleton()->get_ticks_usec() > until)
+ return false;
}
+
+ return true;
}
+};
- get_ok()->set_disabled(root->get_children() == NULL);
+void EditorHelpSearch::_update_search() {
+ search_options->clear();
+ search_options->set_hide_root(true);
+
+ String term = search_box->get_text();
+ if (term.length() < 2)
+ return;
+
+ search = Ref<IncrementalSearch>(memnew(IncrementalSearch(this, search_options, term)));
+ set_process(true);
}
void EditorHelpSearch::_confirmed() {
@@ -281,6 +279,20 @@ void EditorHelpSearch::_notification(int p_what) {
//_update_icons
search_box->add_icon_override("right_icon", get_icon("Search", "EditorIcons"));
+ } else if (p_what == NOTIFICATION_PROCESS) {
+
+ if (search.is_valid()) {
+
+ if (search->work()) {
+
+ get_ok()->set_disabled(search->empty());
+ search = Ref<IncrementalSearch>();
+ set_process(false);
+ }
+ } else {
+
+ set_process(false);
+ }
}
}
diff --git a/editor/editor_help.h b/editor/editor_help.h
index 92c0e2f4d1..a224c7f8ee 100644
--- a/editor/editor_help.h
+++ b/editor/editor_help.h
@@ -53,6 +53,9 @@ class EditorHelpSearch : public ConfirmationDialog {
Tree *search_options;
String base_type;
+ class IncrementalSearch;
+ Ref<IncrementalSearch> search;
+
void _update_search();
void _sbox_input(const Ref<InputEvent> &p_ie);
diff --git a/editor/editor_node.cpp b/editor/editor_node.cpp
index 604f15a76f..76d77ac7a1 100644
--- a/editor/editor_node.cpp
+++ b/editor/editor_node.cpp
@@ -269,6 +269,7 @@ void EditorNode::_notification(int p_what) {
Engine::get_singleton()->set_editor_hint(true);
+ get_tree()->get_root()->set_usage(Viewport::USAGE_2D_NO_SAMPLING); //reduce memory usage
get_tree()->get_root()->set_disable_3d(true);
get_tree()->get_root()->set_as_audio_listener(false);
get_tree()->get_root()->set_as_audio_listener_2d(false);
@@ -1400,11 +1401,13 @@ void EditorNode::_property_editor_back() {
}
void EditorNode::_menu_collapseall() {
- property_editor->collapse_all_parent_nodes();
+
+ property_editor->collapse_all_folding();
}
void EditorNode::_menu_expandall() {
- property_editor->expand_all_parent_nodes();
+
+ property_editor->expand_all_folding();
}
void EditorNode::_save_default_environment() {
@@ -5032,6 +5035,7 @@ EditorNode::EditorNode() {
scene_root_parent->set_v_size_flags(Control::SIZE_EXPAND_FILL);
scene_root = memnew(Viewport);
+ scene_root->set_usage(Viewport::USAGE_2D);
scene_root->set_disable_3d(true);
VisualServer::get_singleton()->viewport_set_hide_scenario(scene_root->get_viewport_rid(), true);
@@ -5457,7 +5461,7 @@ EditorNode::EditorNode() {
property_editor->set_use_doc_hints(true);
property_editor->set_hide_script(false);
property_editor->set_enable_capitalize_paths(bool(EDITOR_DEF("interface/editor/capitalize_properties", true)));
- property_editor->set_use_folding(bool(EDITOR_DEF("interface/editor/expand_all_properties", false)) == false);
+ property_editor->set_use_folding(!bool(EDITOR_DEF("interface/editor/disable_inspector_folding", false)));
property_editor->hide_top_label();
property_editor->register_text_enter(search_box);
diff --git a/editor/editor_themes.cpp b/editor/editor_themes.cpp
index ae29b7420e..23c32a5793 100644
--- a/editor/editor_themes.cpp
+++ b/editor/editor_themes.cpp
@@ -793,6 +793,7 @@ Ref<Theme> create_editor_theme(const Ref<Theme> p_theme) {
// TextEdit
theme->set_stylebox("normal", "TextEdit", style_widget);
theme->set_stylebox("focus", "TextEdit", style_widget_hover);
+ theme->set_stylebox("read_only", "TextEdit", style_widget_disabled);
theme->set_constant("side_margin", "TabContainer", 0);
theme->set_icon("tab", "TextEdit", theme->get_icon("GuiTab", "EditorIcons"));
theme->set_color("font_color", "TextEdit", font_color);
diff --git a/editor/filesystem_dock.cpp b/editor/filesystem_dock.cpp
index 9fe3e2ad25..ca6571fdda 100644
--- a/editor/filesystem_dock.cpp
+++ b/editor/filesystem_dock.cpp
@@ -909,10 +909,11 @@ void FileSystemDock::_file_option(int p_option) {
OS::get_singleton()->shell_open(String("file://") + dir);
} break;
case FILE_OPEN: {
- int idx = files->get_current();
- if (idx < 0 || idx >= files->get_item_count())
- break;
- _select_file(idx);
+ for (int i = 0; i < files->get_item_count(); i++) {
+ if (files->is_selected(i)) {
+ _select_file(i);
+ }
+ }
} break;
case FILE_INSTANCE: {
@@ -1429,14 +1430,17 @@ void FileSystemDock::_files_list_rmb_select(int p_item, const Vector2 &p_pos) {
file_options->clear();
file_options->set_size(Size2(1, 1));
- if (all_files && filenames.size() > 0) {
- file_options->add_item(TTR("Open"), FILE_OPEN);
- if (all_files_scenes) {
+ if (all_files) {
+
+ if (all_files_scenes && filenames.size() >= 1) {
+ file_options->add_item(TTR("Open Scene(s)"), FILE_OPEN);
file_options->add_item(TTR("Instance"), FILE_INSTANCE);
+ file_options->add_separator();
}
- file_options->add_separator();
- if (filenames.size() == 1) {
+ if (!all_files_scenes && filenames.size() == 1) {
+ file_options->add_item(TTR("Open"), FILE_OPEN);
+ file_options->add_separator();
file_options->add_item(TTR("Edit Dependencies.."), FILE_DEPENDENCIES);
file_options->add_item(TTR("View Owners.."), FILE_OWNERS);
file_options->add_separator();
diff --git a/editor/filesystem_dock.h b/editor/filesystem_dock.h
index f1fd342052..b004b1974d 100644
--- a/editor/filesystem_dock.h
+++ b/editor/filesystem_dock.h
@@ -128,10 +128,12 @@ private:
String path;
bool is_file;
- FileOrFolder()
- : path(""), is_file(false) {}
- FileOrFolder(const String &p_path, bool p_is_file)
- : path(p_path), is_file(p_is_file) {}
+ FileOrFolder() :
+ path(""),
+ is_file(false) {}
+ FileOrFolder(const String &p_path, bool p_is_file) :
+ path(p_path),
+ is_file(p_is_file) {}
};
FileOrFolder to_rename;
Vector<FileOrFolder> to_move;
diff --git a/editor/import/editor_import_collada.cpp b/editor/import/editor_import_collada.cpp
index 3c73411dee..f51bc2d6be 100644
--- a/editor/import/editor_import_collada.cpp
+++ b/editor/import/editor_import_collada.cpp
@@ -1913,8 +1913,6 @@ void ColladaImport::create_animation(int p_clip, bool p_make_tracks_in_all_bones
/*************************************** SCENE ***********************************/
/*********************************************************************************/
-#define DEBUG_ANIMATION
-
uint32_t EditorSceneImporterCollada::get_import_flags() const {
return IMPORT_SCENE | IMPORT_ANIMATION;
diff --git a/editor/import/resource_importer_scene.cpp b/editor/import/resource_importer_scene.cpp
index 95445693b4..6484c37ffe 100644
--- a/editor/import/resource_importer_scene.cpp
+++ b/editor/import/resource_importer_scene.cpp
@@ -95,6 +95,9 @@ bool ResourceImporterScene::get_option_visibility(const String &p_option, const
if (p_option != "animation/import" && !bool(p_options["animation/import"]))
return false;
+ if (p_option == "animation/keep_custom_tracks" && int(p_options["animation/storage"]) == 0)
+ return false;
+
if (p_option.begins_with("animation/optimizer/") && p_option != "animation/optimizer/enabled" && !bool(p_options["animation/optimizer/enabled"]))
return false;
@@ -870,7 +873,7 @@ static String _make_extname(const String &p_str) {
return ext_name;
}
-void ResourceImporterScene::_make_external_resources(Node *p_node, const String &p_base_path, bool p_make_animations, bool p_make_materials, bool p_keep_materials, bool p_make_meshes, Map<Ref<Animation>, Ref<Animation> > &p_animations, Map<Ref<Material>, Ref<Material> > &p_materials, Map<Ref<ArrayMesh>, Ref<ArrayMesh> > &p_meshes) {
+void ResourceImporterScene::_make_external_resources(Node *p_node, const String &p_base_path, bool p_make_animations, bool p_keep_animations, bool p_make_materials, bool p_keep_materials, bool p_make_meshes, Map<Ref<Animation>, Ref<Animation> > &p_animations, Map<Ref<Material>, Ref<Material> > &p_materials, Map<Ref<ArrayMesh>, Ref<ArrayMesh> > &p_meshes) {
List<PropertyInfo> pi;
@@ -889,7 +892,26 @@ void ResourceImporterScene::_make_external_resources(Node *p_node, const String
if (!p_animations.has(anim)) {
+ //mark what comes from the file first, this helps eventually keep user data
+ for (int i = 0; i < anim->get_track_count(); i++) {
+ anim->track_set_imported(i, true);
+ }
+
String ext_name = p_base_path.plus_file(_make_extname(E->get()) + ".anim");
+
+ if (FileAccess::exists(ext_name) && p_keep_animations) {
+ //try to keep custom animation tracks
+ Ref<Animation> old_anim = ResourceLoader::load(ext_name, "Animation", true);
+ if (old_anim.is_valid()) {
+ //meergeee
+ for (int i = 0; i < old_anim->get_track_count(); i++) {
+ if (!old_anim->track_is_imported(i)) {
+ old_anim->copy_track(i, anim);
+ }
+ }
+ }
+ }
+
ResourceSaver::save(ext_name, anim, ResourceSaver::FLAG_CHANGE_PATH);
p_animations[anim] = anim;
}
@@ -997,7 +1019,7 @@ void ResourceImporterScene::_make_external_resources(Node *p_node, const String
for (int i = 0; i < p_node->get_child_count(); i++) {
- _make_external_resources(p_node->get_child(i), p_base_path, p_make_animations, p_make_materials, p_keep_materials, p_make_meshes, p_animations, p_materials, p_meshes);
+ _make_external_resources(p_node->get_child(i), p_base_path, p_make_animations, p_keep_animations, p_make_materials, p_keep_materials, p_make_meshes, p_animations, p_materials, p_meshes);
}
}
@@ -1036,6 +1058,7 @@ void ResourceImporterScene::get_import_options(List<ImportOption> *r_options, in
r_options->push_back(ImportOption(PropertyInfo(Variant::REAL, "animation/fps", PROPERTY_HINT_RANGE, "1,120,1"), 15));
r_options->push_back(ImportOption(PropertyInfo(Variant::STRING, "animation/filter_script", PROPERTY_HINT_MULTILINE_TEXT), ""));
r_options->push_back(ImportOption(PropertyInfo(Variant::INT, "animation/storage", PROPERTY_HINT_ENUM, "Built-In,Files"), animations_out ? true : false));
+ r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "animation/keep_custom_tracks"), animations_out ? true : false));
r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "animation/optimizer/enabled", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_DEFAULT | PROPERTY_USAGE_UPDATE_ALL_IF_MODIFIED), true));
r_options->push_back(ImportOption(PropertyInfo(Variant::REAL, "animation/optimizer/max_linear_error"), 0.05));
r_options->push_back(ImportOption(PropertyInfo(Variant::REAL, "animation/optimizer/max_angular_error"), 0.01));
@@ -1176,6 +1199,7 @@ Error ResourceImporterScene::import(const String &p_source_file, const String &p
}
bool external_animations = int(p_options["animation/storage"]) == 1;
+ bool keep_custom_tracks = p_options["animation/keep_custom_tracks"];
bool external_materials = p_options["materials/storage"];
bool external_meshes = p_options["meshes/storage"];
bool external_scenes = int(p_options["nodes/storage"]) == 1;
@@ -1202,7 +1226,7 @@ Error ResourceImporterScene::import(const String &p_source_file, const String &p
bool keep_materials = bool(p_options["materials/keep_on_reimport"]);
- _make_external_resources(scene, base_path, external_animations, external_materials, keep_materials, external_meshes, anim_map, mat_map, mesh_map);
+ _make_external_resources(scene, base_path, external_animations, keep_custom_tracks, external_materials, keep_materials, external_meshes, anim_map, mat_map, mesh_map);
}
progress.step(TTR("Running Custom Script.."), 2);
diff --git a/editor/import/resource_importer_scene.h b/editor/import/resource_importer_scene.h
index 92777fafb6..cbdafe8e21 100644
--- a/editor/import/resource_importer_scene.h
+++ b/editor/import/resource_importer_scene.h
@@ -128,7 +128,7 @@ public:
virtual bool get_option_visibility(const String &p_option, const Map<StringName, Variant> &p_options) const;
virtual int get_import_order() const { return 100; } //after everything
- void _make_external_resources(Node *p_node, const String &p_base_path, bool p_make_animations, bool p_make_materials, bool p_keep_materials, bool p_make_meshes, Map<Ref<Animation>, Ref<Animation> > &p_animations, Map<Ref<Material>, Ref<Material> > &p_materials, Map<Ref<ArrayMesh>, Ref<ArrayMesh> > &p_meshes);
+ void _make_external_resources(Node *p_node, const String &p_base_path, bool p_make_animations, bool p_keep_animations, bool p_make_materials, bool p_keep_materials, bool p_make_meshes, Map<Ref<Animation>, Ref<Animation> > &p_animations, Map<Ref<Material>, Ref<Material> > &p_materials, Map<Ref<ArrayMesh>, Ref<ArrayMesh> > &p_meshes);
Node *_fix_node(Node *p_node, Node *p_root, Map<Ref<ArrayMesh>, Ref<Shape> > &collision_map, LightBakeMode p_light_bake_mode);
diff --git a/editor/plugins/abstract_polygon_2d_editor.cpp b/editor/plugins/abstract_polygon_2d_editor.cpp
index cabdfa761d..ff72a5a25e 100644
--- a/editor/plugins/abstract_polygon_2d_editor.cpp
+++ b/editor/plugins/abstract_polygon_2d_editor.cpp
@@ -32,18 +32,21 @@
#include "canvas_item_editor_plugin.h"
#include "core/os/keyboard.h"
-AbstractPolygon2DEditor::Vertex::Vertex()
- : polygon(-1), vertex(-1) {
+AbstractPolygon2DEditor::Vertex::Vertex() :
+ polygon(-1),
+ vertex(-1) {
// invalid vertex
}
-AbstractPolygon2DEditor::Vertex::Vertex(int p_vertex)
- : polygon(-1), vertex(p_vertex) {
+AbstractPolygon2DEditor::Vertex::Vertex(int p_vertex) :
+ polygon(-1),
+ vertex(p_vertex) {
// vertex p_vertex of current wip polygon
}
-AbstractPolygon2DEditor::Vertex::Vertex(int p_polygon, int p_vertex)
- : polygon(p_polygon), vertex(p_vertex) {
+AbstractPolygon2DEditor::Vertex::Vertex(int p_polygon, int p_vertex) :
+ polygon(p_polygon),
+ vertex(p_vertex) {
// vertex p_vertex of polygon p_polygon
}
@@ -66,12 +69,14 @@ AbstractPolygon2DEditor::PosVertex::PosVertex() {
// invalid vertex
}
-AbstractPolygon2DEditor::PosVertex::PosVertex(const Vertex &p_vertex, const Vector2 &p_pos)
- : Vertex(p_vertex.polygon, p_vertex.vertex), pos(p_pos) {
+AbstractPolygon2DEditor::PosVertex::PosVertex(const Vertex &p_vertex, const Vector2 &p_pos) :
+ Vertex(p_vertex.polygon, p_vertex.vertex),
+ pos(p_pos) {
}
-AbstractPolygon2DEditor::PosVertex::PosVertex(int p_polygon, int p_vertex, const Vector2 &p_pos)
- : Vertex(p_polygon, p_vertex), pos(p_pos) {
+AbstractPolygon2DEditor::PosVertex::PosVertex(int p_polygon, int p_vertex, const Vector2 &p_pos) :
+ Vertex(p_polygon, p_vertex),
+ pos(p_pos) {
}
bool AbstractPolygon2DEditor::_is_empty() const {
@@ -167,7 +172,7 @@ void AbstractPolygon2DEditor::_menu_option(int p_option) {
} break;
case MODE_EDIT: {
- wip_active = false;
+ _wip_close();
mode = MODE_EDIT;
button_create->set_pressed(false);
button_edit->set_pressed(true);
@@ -175,7 +180,7 @@ void AbstractPolygon2DEditor::_menu_option(int p_option) {
} break;
case MODE_DELETE: {
- wip_active = false;
+ _wip_close();
mode = MODE_DELETE;
button_create->set_pressed(false);
button_edit->set_pressed(false);
@@ -224,6 +229,9 @@ void AbstractPolygon2DEditor::_wip_changed() {
}
void AbstractPolygon2DEditor::_wip_close() {
+ if (!wip_active)
+ return;
+
if (_is_line()) {
_set_polygon(0, wip);
diff --git a/editor/plugins/canvas_item_editor_plugin.cpp b/editor/plugins/canvas_item_editor_plugin.cpp
index ddcdb5a321..8eee9c7e7c 100644
--- a/editor/plugins/canvas_item_editor_plugin.cpp
+++ b/editor/plugins/canvas_item_editor_plugin.cpp
@@ -69,8 +69,8 @@ class SnapDialog : public ConfirmationDialog {
SpinBox *rotation_step;
public:
- SnapDialog()
- : ConfirmationDialog() {
+ SnapDialog() :
+ ConfirmationDialog() {
const int SPIN_BOX_GRID_RANGE = 256;
const int SPIN_BOX_ROTATION_RANGE = 360;
Label *label;
diff --git a/editor/plugins/collision_polygon_2d_editor_plugin.cpp b/editor/plugins/collision_polygon_2d_editor_plugin.cpp
index 00e6d617a1..6ac80caf94 100644
--- a/editor/plugins/collision_polygon_2d_editor_plugin.cpp
+++ b/editor/plugins/collision_polygon_2d_editor_plugin.cpp
@@ -39,10 +39,10 @@ void CollisionPolygon2DEditor::_set_node(Node *p_polygon) {
node = Object::cast_to<CollisionPolygon2D>(p_polygon);
}
-CollisionPolygon2DEditor::CollisionPolygon2DEditor(EditorNode *p_editor)
- : AbstractPolygon2DEditor(p_editor) {
+CollisionPolygon2DEditor::CollisionPolygon2DEditor(EditorNode *p_editor) :
+ AbstractPolygon2DEditor(p_editor) {
}
-CollisionPolygon2DEditorPlugin::CollisionPolygon2DEditorPlugin(EditorNode *p_node)
- : AbstractPolygon2DEditorPlugin(p_node, memnew(CollisionPolygon2DEditor(p_node)), "CollisionPolygon2D") {
+CollisionPolygon2DEditorPlugin::CollisionPolygon2DEditorPlugin(EditorNode *p_node) :
+ AbstractPolygon2DEditorPlugin(p_node, memnew(CollisionPolygon2DEditor(p_node)), "CollisionPolygon2D") {
}
diff --git a/editor/plugins/curve_editor_plugin.cpp b/editor/plugins/curve_editor_plugin.cpp
index 2754aeed06..f77016c1d6 100644
--- a/editor/plugins/curve_editor_plugin.cpp
+++ b/editor/plugins/curve_editor_plugin.cpp
@@ -586,8 +586,10 @@ struct CanvasItemPlotCurve {
Color color1;
Color color2;
- CanvasItemPlotCurve(CanvasItem &p_ci, Color p_color1, Color p_color2)
- : ci(p_ci), color1(p_color1), color2(p_color2) {}
+ CanvasItemPlotCurve(CanvasItem &p_ci, Color p_color1, Color p_color2) :
+ ci(p_ci),
+ color1(p_color1),
+ color2(p_color2) {}
void operator()(Vector2 pos0, Vector2 pos1, bool in_definition) {
ci.draw_line(pos0, pos1, in_definition ? color1 : color2);
diff --git a/editor/plugins/editor_preview_plugins.cpp b/editor/plugins/editor_preview_plugins.cpp
index ed04c90cc5..558f44769d 100644
--- a/editor/plugins/editor_preview_plugins.cpp
+++ b/editor/plugins/editor_preview_plugins.cpp
@@ -235,29 +235,34 @@ Ref<Texture> EditorMaterialPreviewPlugin::generate(const RES &p_from) {
Ref<Material> material = p_from;
ERR_FAIL_COND_V(material.is_null(), Ref<Texture>());
- VS::get_singleton()->mesh_surface_set_material(sphere, 0, material->get_rid());
+ if (material->get_shader_mode() == Shader::MODE_SPATIAL) {
- VS::get_singleton()->viewport_set_update_mode(viewport, VS::VIEWPORT_UPDATE_ONCE); //once used for capture
+ VS::get_singleton()->mesh_surface_set_material(sphere, 0, material->get_rid());
- preview_done = false;
- VS::get_singleton()->request_frame_drawn_callback(this, "_preview_done", Variant());
+ VS::get_singleton()->viewport_set_update_mode(viewport, VS::VIEWPORT_UPDATE_ONCE); //once used for capture
- while (!preview_done) {
- OS::get_singleton()->delay_usec(10);
- }
+ preview_done = false;
+ VS::get_singleton()->request_frame_drawn_callback(this, "_preview_done", Variant());
- Ref<Image> img = VS::get_singleton()->VS::get_singleton()->texture_get_data(viewport_texture);
- VS::get_singleton()->mesh_surface_set_material(sphere, 0, RID());
+ while (!preview_done) {
+ OS::get_singleton()->delay_usec(10);
+ }
- ERR_FAIL_COND_V(!img.is_valid(), Ref<ImageTexture>());
+ Ref<Image> img = VS::get_singleton()->VS::get_singleton()->texture_get_data(viewport_texture);
+ VS::get_singleton()->mesh_surface_set_material(sphere, 0, RID());
- int thumbnail_size = EditorSettings::get_singleton()->get("filesystem/file_dialog/thumbnail_size");
- thumbnail_size *= EDSCALE;
- img->convert(Image::FORMAT_RGBA8);
- img->resize(thumbnail_size, thumbnail_size);
- Ref<ImageTexture> ptex = Ref<ImageTexture>(memnew(ImageTexture));
- ptex->create_from_image(img, 0);
- return ptex;
+ ERR_FAIL_COND_V(!img.is_valid(), Ref<ImageTexture>());
+
+ int thumbnail_size = EditorSettings::get_singleton()->get("filesystem/file_dialog/thumbnail_size");
+ thumbnail_size *= EDSCALE;
+ img->convert(Image::FORMAT_RGBA8);
+ img->resize(thumbnail_size, thumbnail_size);
+ Ref<ImageTexture> ptex = Ref<ImageTexture>(memnew(ImageTexture));
+ ptex->create_from_image(img, 0);
+ return ptex;
+ }
+
+ return Ref<Texture>();
}
EditorMaterialPreviewPlugin::EditorMaterialPreviewPlugin() {
diff --git a/editor/plugins/line_2d_editor_plugin.cpp b/editor/plugins/line_2d_editor_plugin.cpp
index 51fa488b43..04d8519b2f 100644
--- a/editor/plugins/line_2d_editor_plugin.cpp
+++ b/editor/plugins/line_2d_editor_plugin.cpp
@@ -61,10 +61,10 @@ void Line2DEditor::_action_set_polygon(int p_idx, const Variant &p_previous, con
undo_redo->add_undo_method(node, "set_points", p_previous);
}
-Line2DEditor::Line2DEditor(EditorNode *p_editor)
- : AbstractPolygon2DEditor(p_editor) {
+Line2DEditor::Line2DEditor(EditorNode *p_editor) :
+ AbstractPolygon2DEditor(p_editor) {
}
-Line2DEditorPlugin::Line2DEditorPlugin(EditorNode *p_node)
- : AbstractPolygon2DEditorPlugin(p_node, memnew(Line2DEditor(p_node)), "Line2D") {
+Line2DEditorPlugin::Line2DEditorPlugin(EditorNode *p_node) :
+ AbstractPolygon2DEditorPlugin(p_node, memnew(Line2DEditor(p_node)), "Line2D") {
}
diff --git a/editor/plugins/navigation_polygon_editor_plugin.cpp b/editor/plugins/navigation_polygon_editor_plugin.cpp
index 6560a8dac7..36c608310b 100644
--- a/editor/plugins/navigation_polygon_editor_plugin.cpp
+++ b/editor/plugins/navigation_polygon_editor_plugin.cpp
@@ -120,10 +120,10 @@ void NavigationPolygonEditor::_create_resource() {
_menu_option(MODE_CREATE);
}
-NavigationPolygonEditor::NavigationPolygonEditor(EditorNode *p_editor)
- : AbstractPolygon2DEditor(p_editor) {
+NavigationPolygonEditor::NavigationPolygonEditor(EditorNode *p_editor) :
+ AbstractPolygon2DEditor(p_editor) {
}
-NavigationPolygonEditorPlugin::NavigationPolygonEditorPlugin(EditorNode *p_node)
- : AbstractPolygon2DEditorPlugin(p_node, memnew(NavigationPolygonEditor(p_node)), "NavigationPolygonInstance") {
+NavigationPolygonEditorPlugin::NavigationPolygonEditorPlugin(EditorNode *p_node) :
+ AbstractPolygon2DEditorPlugin(p_node, memnew(NavigationPolygonEditor(p_node)), "NavigationPolygonInstance") {
}
diff --git a/editor/plugins/polygon_2d_editor_plugin.cpp b/editor/plugins/polygon_2d_editor_plugin.cpp
index ebb5f57e99..25e734187d 100644
--- a/editor/plugins/polygon_2d_editor_plugin.cpp
+++ b/editor/plugins/polygon_2d_editor_plugin.cpp
@@ -459,8 +459,8 @@ Vector2 Polygon2DEditor::snap_point(Vector2 p_target) const {
return p_target;
}
-Polygon2DEditor::Polygon2DEditor(EditorNode *p_editor)
- : AbstractPolygon2DEditor(p_editor) {
+Polygon2DEditor::Polygon2DEditor(EditorNode *p_editor) :
+ AbstractPolygon2DEditor(p_editor) {
snap_step = Vector2(10, 10);
use_snap = false;
@@ -609,6 +609,6 @@ Polygon2DEditor::Polygon2DEditor(EditorNode *p_editor)
uv_edit_draw->set_clip_contents(true);
}
-Polygon2DEditorPlugin::Polygon2DEditorPlugin(EditorNode *p_node)
- : AbstractPolygon2DEditorPlugin(p_node, memnew(Polygon2DEditor(p_node)), "Polygon2D") {
+Polygon2DEditorPlugin::Polygon2DEditorPlugin(EditorNode *p_node) :
+ AbstractPolygon2DEditorPlugin(p_node, memnew(Polygon2DEditor(p_node)), "Polygon2D") {
}
diff --git a/editor/plugins/script_editor_plugin.cpp b/editor/plugins/script_editor_plugin.cpp
index 3c2d52c128..c02b3458e5 100644
--- a/editor/plugins/script_editor_plugin.cpp
+++ b/editor/plugins/script_editor_plugin.cpp
@@ -586,6 +586,12 @@ void ScriptEditor::_close_docs_tab() {
}
}
+void ScriptEditor::_copy_script_path() {
+ ScriptEditorBase *se = Object::cast_to<ScriptEditorBase>(tab_container->get_child(tab_container->get_current_tab()));
+ Ref<Script> script = se->get_edited_script();
+ OS::get_singleton()->set_clipboard(script->get_path());
+}
+
void ScriptEditor::_close_other_tabs() {
int child_count = tab_container->get_child_count();
@@ -1026,6 +1032,9 @@ void ScriptEditor::_menu_option(int p_option) {
_close_current_tab();
}
} break;
+ case FILE_COPY_PATH: {
+ _copy_script_path();
+ } break;
case CLOSE_DOCS: {
_close_docs_tab();
} break;
@@ -2175,6 +2184,7 @@ void ScriptEditor::_make_script_list_context_menu() {
context_menu->add_shortcut(ED_GET_SHORTCUT("script_editor/close_all"), CLOSE_ALL);
context_menu->add_shortcut(ED_GET_SHORTCUT("script_editor/close_other_tabs"), CLOSE_OTHER_TABS);
context_menu->add_separator();
+ context_menu->add_shortcut(ED_GET_SHORTCUT("script_editor/copy_path"), FILE_COPY_PATH);
context_menu->add_shortcut(ED_GET_SHORTCUT("script_editor/reload_script_soft"), FILE_TOOL_RELOAD_SOFT);
Ref<Script> scr = se->get_edited_script();
@@ -2507,6 +2517,7 @@ void ScriptEditor::_bind_methods() {
ClassDB::bind_method("_help_search", &ScriptEditor::_help_search);
ClassDB::bind_method("_help_index", &ScriptEditor::_help_index);
ClassDB::bind_method("_save_history", &ScriptEditor::_save_history);
+ ClassDB::bind_method("_copy_script_path", &ScriptEditor::_copy_script_path);
ClassDB::bind_method("_breaked", &ScriptEditor::_breaked);
ClassDB::bind_method("_show_debugger", &ScriptEditor::_show_debugger);
@@ -2626,6 +2637,7 @@ ScriptEditor::ScriptEditor(EditorNode *p_editor) {
file_menu->get_popup()->add_shortcut(ED_SHORTCUT("script_editor/save_all", TTR("Save All"), KEY_MASK_CMD | KEY_MASK_SHIFT | KEY_MASK_ALT | KEY_S), FILE_SAVE_ALL);
file_menu->get_popup()->add_separator();
file_menu->get_popup()->add_shortcut(ED_SHORTCUT("script_editor/reload_script_soft", TTR("Soft Reload Script"), KEY_MASK_CMD | KEY_MASK_SHIFT | KEY_R), FILE_TOOL_RELOAD_SOFT);
+ file_menu->get_popup()->add_shortcut(ED_SHORTCUT("script_editor/copy_path", TTR("Copy Script Path")), FILE_COPY_PATH);
file_menu->get_popup()->add_separator();
file_menu->get_popup()->add_shortcut(ED_SHORTCUT("script_editor/history_previous", TTR("History Prev"), KEY_MASK_ALT | KEY_LEFT), WINDOW_PREV);
diff --git a/editor/plugins/script_editor_plugin.h b/editor/plugins/script_editor_plugin.h
index 77ca4bc9d9..ffd42d18ca 100644
--- a/editor/plugins/script_editor_plugin.h
+++ b/editor/plugins/script_editor_plugin.h
@@ -137,6 +137,7 @@ class ScriptEditor : public PanelContainer {
CLOSE_ALL,
CLOSE_OTHER_TABS,
TOGGLE_SCRIPTS_PANEL,
+ FILE_COPY_PATH,
FILE_TOOL_RELOAD,
FILE_TOOL_RELOAD_SOFT,
DEBUG_NEXT,
@@ -255,6 +256,8 @@ class ScriptEditor : public PanelContainer {
void _close_other_tabs();
void _close_all_tabs();
+ void _copy_script_path();
+
void _ask_close_current_unsaved_tab(ScriptEditorBase *current);
bool grab_focus_block;
diff --git a/editor/plugins/script_text_editor.cpp b/editor/plugins/script_text_editor.cpp
index 3a443e1bf7..3c5bc7ac33 100644
--- a/editor/plugins/script_text_editor.cpp
+++ b/editor/plugins/script_text_editor.cpp
@@ -1509,6 +1509,8 @@ void ScriptTextEditor::_make_context_menu(bool p_selection, bool p_color, bool p
if (p_selection) {
context_menu->add_separator();
+ context_menu->add_shortcut(ED_GET_SHORTCUT("script_text_editor/convert_to_uppercase"), EDIT_TO_UPPERCASE);
+ context_menu->add_shortcut(ED_GET_SHORTCUT("script_text_editor/convert_to_lowercase"), EDIT_TO_LOWERCASE);
context_menu->add_shortcut(ED_GET_SHORTCUT("script_text_editor/indent_left"), EDIT_INDENT_LEFT);
context_menu->add_shortcut(ED_GET_SHORTCUT("script_text_editor/indent_right"), EDIT_INDENT_RIGHT);
context_menu->add_shortcut(ED_GET_SHORTCUT("script_text_editor/toggle_comment"), EDIT_TOGGLE_COMMENT);
diff --git a/editor/project_manager.cpp b/editor/project_manager.cpp
index b4d89526b0..00488a2a88 100644
--- a/editor/project_manager.cpp
+++ b/editor/project_manager.cpp
@@ -508,7 +508,7 @@ public:
} else if (current->has_setting("application/config/name")) {
project_name->set_text(current->get("application/config/name"));
}
-
+
project_name->call_deferred("grab_focus");
create_dir->hide();
diff --git a/editor/property_editor.cpp b/editor/property_editor.cpp
index 6f9454be2c..eed1efaf9c 100644
--- a/editor/property_editor.cpp
+++ b/editor/property_editor.cpp
@@ -2101,6 +2101,23 @@ bool PropertyEditor::_is_property_different(const Variant &p_current, const Vari
return bool(Variant::evaluate(Variant::OP_NOT_EQUAL, p_current, p_orig));
}
+bool PropertyEditor::_is_instanced_node_with_original_property_different(const String &p_name, TreeItem *item) {
+ bool mbi = _might_be_in_instance();
+ if (mbi) {
+ Variant vorig;
+ Dictionary d = item->get_metadata(0);
+ int usage = d.has("usage") ? int(int(d["usage"]) & (PROPERTY_USAGE_STORE_IF_NONONE | PROPERTY_USAGE_STORE_IF_NONZERO)) : 0;
+ if (_get_instanced_node_original_property(p_name, vorig) || usage) {
+ Variant v = obj->get(p_name);
+
+ if (_is_property_different(v, vorig, usage)) {
+ return true;
+ }
+ }
+ }
+ return false;
+}
+
TreeItem *PropertyEditor::find_item(TreeItem *p_item, const String &p_name) {
if (!p_item)
@@ -2360,6 +2377,10 @@ void PropertyEditor::_check_reload_status(const String &p_name, TreeItem *item)
}
}
+ if (_is_instanced_node_with_original_property_different(p_name, item)) {
+ has_reload = true;
+ }
+
if (obj->call("property_can_revert", p_name).operator bool()) {
has_reload = true;
@@ -2665,18 +2686,14 @@ TreeItem *PropertyEditor::get_parent_node(String p_path, HashMap<String, TreeIte
item->set_editable(1, false);
item->set_selectable(1, subsection_selectable);
- if (use_folding || folding_behaviour != FB_UNDEFINED) { // Even if you disabled folding (expand all by default), you still can collapse all manually.
+ if (use_folding) { //
if (!obj->editor_is_section_unfolded(p_path)) {
updating_folding = true;
- if (folding_behaviour == FB_COLLAPSEALL)
- item->set_collapsed(true);
- else if (folding_behaviour == FB_EXPANDALL || is_expandall_enabled)
- item->set_collapsed(false);
- else
- item->set_collapsed(true);
+ item->set_collapsed(true);
updating_folding = false;
}
item->set_metadata(0, p_path);
+ foldable_property_cache.push_back(p_path);
}
if (item->get_parent() == root) {
@@ -2725,6 +2742,7 @@ void PropertyEditor::refresh() {
void PropertyEditor::update_tree() {
tree->clear();
+ foldable_property_cache.clear();
if (!obj)
return;
@@ -3512,20 +3530,9 @@ void PropertyEditor::update_tree() {
bool has_reload = false;
- bool mbi = _might_be_in_instance();
- if (mbi) {
-
- Variant vorig;
- Dictionary d = item->get_metadata(0);
- int usage = d.has("usage") ? int(int(d["usage"]) & (PROPERTY_USAGE_STORE_IF_NONONE | PROPERTY_USAGE_STORE_IF_NONZERO)) : 0;
- if (_get_instanced_node_original_property(p.name, vorig) || usage) {
- Variant v = obj->get(p.name);
-
- if (_is_property_different(v, vorig, usage)) {
- item->add_button(1, get_icon("ReloadSmall", "EditorIcons"), 3);
- has_reload = true;
- }
- }
+ if (_is_instanced_node_with_original_property_different(p.name, item)) {
+ item->add_button(1, get_icon("ReloadSmall", "EditorIcons"), 3);
+ has_reload = true;
}
if (obj->call("property_can_revert", p.name).operator bool()) {
@@ -3545,7 +3552,7 @@ void PropertyEditor::update_tree() {
}
}
- if (mbi && !has_reload && item->get_cell_mode(1) == TreeItem::CELL_MODE_RANGE && item->get_text(1) == String()) {
+ if (_might_be_in_instance() && !has_reload && item->get_cell_mode(1) == TreeItem::CELL_MODE_RANGE && item->get_text(1) == String()) {
item->add_button(1, get_icon("ReloadEmpty", "EditorIcons"), 3, true);
}
}
@@ -3733,8 +3740,8 @@ void PropertyEditor::_item_edited() {
_edit_set(name, item->get_text(1), refresh_all);
}
} break;
- // math types
+ // math types
case Variant::VECTOR3: {
} break;
@@ -4212,29 +4219,29 @@ void PropertyEditor::set_subsection_selectable(bool p_selectable) {
update_tree();
}
-bool PropertyEditor::is_expand_all_properties_enabled() const {
-
- return (use_folding == false);
-}
-
void PropertyEditor::set_use_folding(bool p_enable) {
use_folding = p_enable;
tree->set_hide_folding(false);
}
-void PropertyEditor::collapse_all_parent_nodes() {
-
- folding_behaviour = FB_COLLAPSEALL;
+void PropertyEditor::collapse_all_folding() {
+ if (!obj)
+ return;
+ for (List<String>::Element *E = foldable_property_cache.front(); E; E = E->next()) {
+ obj->editor_set_section_unfold(E->get(), false);
+ }
update_tree();
- folding_behaviour = FB_UNDEFINED;
}
-void PropertyEditor::expand_all_parent_nodes() {
+void PropertyEditor::expand_all_folding() {
- folding_behaviour = FB_EXPANDALL;
+ if (!obj)
+ return;
+ for (List<String>::Element *E = foldable_property_cache.front(); E; E = E->next()) {
+ obj->editor_set_section_unfold(E->get(), true);
+ }
update_tree();
- folding_behaviour = FB_UNDEFINED;
}
PropertyEditor::PropertyEditor() {
@@ -4309,8 +4316,6 @@ PropertyEditor::PropertyEditor() {
subsection_selectable = false;
property_selectable = false;
show_type_icons = false; // maybe one day will return.
- folding_behaviour = FB_UNDEFINED;
- is_expandall_enabled = bool(EDITOR_DEF("interface/editor/expand_all_properties", true));
}
PropertyEditor::~PropertyEditor() {
diff --git a/editor/property_editor.h b/editor/property_editor.h
index a337a05e46..f684f5768d 100644
--- a/editor/property_editor.h
+++ b/editor/property_editor.h
@@ -203,18 +203,9 @@ class PropertyEditor : public Control {
bool hide_script;
bool use_folding;
bool property_selectable;
- bool is_expandall_enabled;
-
bool updating_folding;
- enum FOLDING_BEHAVIOUR {
- FB_UNDEFINED,
- FB_COLLAPSEALL,
- FB_EXPANDALL,
- FB_EXPANDALL_FORCE
- };
- FOLDING_BEHAVIOUR folding_behaviour;
-
+ List<String> foldable_property_cache;
HashMap<String, String> pending;
String selected_property;
@@ -253,6 +244,7 @@ class PropertyEditor : public Control {
bool _might_be_in_instance();
bool _get_instanced_node_original_property(const StringName &p_prop, Variant &value);
bool _is_property_different(const Variant &p_current, const Variant &p_orig, int p_usage = 0);
+ bool _is_instanced_node_with_original_property_different(const String &p_name, TreeItem *item);
void _refresh_item(TreeItem *p_item);
void _set_range_def(Object *p_item, String prop, float p_frame);
@@ -314,10 +306,8 @@ public:
void set_use_folding(bool p_enable);
- bool is_expand_all_properties_enabled() const;
-
- void collapse_all_parent_nodes();
- void expand_all_parent_nodes();
+ void collapse_all_folding();
+ void expand_all_folding();
PropertyEditor();
~PropertyEditor();
};