diff options
Diffstat (limited to 'editor/project_manager.cpp')
-rw-r--r-- | editor/project_manager.cpp | 578 |
1 files changed, 251 insertions, 327 deletions
diff --git a/editor/project_manager.cpp b/editor/project_manager.cpp index 35311b32eb..6393aa30ed 100644 --- a/editor/project_manager.cpp +++ b/editor/project_manager.cpp @@ -330,6 +330,7 @@ private: return; } } + String sp = p.simplify_path(); project_path->set_text(sp); _path_text_changed(sp); @@ -411,7 +412,7 @@ private: _test_path(); if (p_text == "") { - set_message(TTR("It would be a good idea to name your project."), MESSAGE_WARNING); + set_message(TTR("It would be a good idea to name your project."), MESSAGE_ERROR); } } @@ -1012,7 +1013,7 @@ public: void update_dock_menu(); void load_projects(); void set_search_term(String p_search_term); - void set_order_option(ProjectListFilter::FilterOption p_option); + void set_order_option(int p_option); void sort_projects(); int get_project_count() const; void select_project(int p_index); @@ -1045,7 +1046,7 @@ private: static void load_project_data(const String &p_property_key, Item &p_item, bool p_favorite); String _search_term; - ProjectListFilter::FilterOption _order_option; + FilterOption _order_option; Set<String> _selected_project_keys; String _last_clicked; // Project key VBoxContainer *_scroll_children; @@ -1055,7 +1056,7 @@ private: }; struct ProjectListComparator { - ProjectListFilter::FilterOption order_option; + FilterOption order_option; // operator< _FORCE_INLINE_ bool operator()(const ProjectList::Item &a, const ProjectList::Item &b) const { @@ -1066,9 +1067,9 @@ struct ProjectListComparator { return false; } switch (order_option) { - case ProjectListFilter::FILTER_PATH: + case PATH: return a.project_key < b.project_key; - case ProjectListFilter::FILTER_EDIT_DATE: + case EDIT_DATE: return a.last_edited > b.last_edited; default: return a.project_name < b.project_name; @@ -1077,8 +1078,7 @@ struct ProjectListComparator { }; ProjectList::ProjectList() { - _order_option = ProjectListFilter::FILTER_EDIT_DATE; - + _order_option = FilterOption::NAME; _scroll_children = memnew(VBoxContainer); _scroll_children->set_h_size_flags(Control::SIZE_EXPAND_FILL); add_child(_scroll_children); @@ -1238,8 +1238,6 @@ void ProjectList::load_projects() { create_project_item_control(i); } - sort_projects(); - set_v_scroll(0); update_icons_async(); @@ -1391,12 +1389,13 @@ void ProjectList::set_search_term(String p_search_term) { _search_term = p_search_term; } -void ProjectList::set_order_option(ProjectListFilter::FilterOption p_option) { - if (_order_option != p_option) { - _order_option = p_option; - EditorSettings::get_singleton()->set("project_manager/sorting_order", (int)_order_option); - EditorSettings::get_singleton()->save(); - } +void ProjectList::set_order_option(int p_option) { + FilterOption selected = (FilterOption)p_option; + EditorSettings::get_singleton()->set("project_manager/sorting_order", p_option); + EditorSettings::get_singleton()->save(); + _order_option = selected; + + sort_projects(); } void ProjectList::sort_projects() { @@ -1798,6 +1797,9 @@ void ProjectList::_bind_methods() { void ProjectManager::_notification(int p_what) { switch (p_what) { case NOTIFICATION_ENTER_TREE: { + search_box->set_right_icon(get_theme_icon("Search", "EditorIcons")); + search_box->set_clear_button_enabled(true); + Engine::get_singleton()->set_editor_hint(false); } break; case NOTIFICATION_RESIZED: { @@ -1806,6 +1808,10 @@ void ProjectManager::_notification(int p_what) { } } break; case NOTIFICATION_READY: { + int default_sorting = (int)EditorSettings::get_singleton()->get("project_manager/sorting_order"); + filter_option->select(default_sorting); + _project_list->set_order_option(default_sorting); + if (_project_list->get_project_count() == 0 && StreamPeerSSL::is_available()) { open_templates->popup_centered(); } @@ -1813,7 +1819,7 @@ void ProjectManager::_notification(int p_what) { if (_project_list->get_project_count() >= 1) { // Focus on the search box immediately to allow the user // to search without having to reach for their mouse - project_filter->search_box->grab_focus(); + search_box->grab_focus(); } } break; case NOTIFICATION_VISIBILITY_CHANGED: { @@ -1833,7 +1839,7 @@ void ProjectManager::_dim_window() { // No transition is applied, as the effect needs to be visible immediately float c = 0.5f; Color dim_color = Color(c, c, c); - gui_base->set_modulate(dim_color); + set_modulate(dim_color); } void ProjectManager::_update_project_buttons() { @@ -1853,7 +1859,7 @@ void ProjectManager::_update_project_buttons() { rename_btn->set_disabled(empty_selection || is_missing_project_selected); run_btn->set_disabled(empty_selection || is_missing_project_selected); - erase_missing_btn->set_visible(_project_list->is_any_project_missing()); + erase_missing_btn->set_disabled(!_project_list->is_any_project_missing()); } void ProjectManager::_unhandled_input(const Ref<InputEvent> &p_ev) { @@ -1930,7 +1936,7 @@ void ProjectManager::_unhandled_input(const Ref<InputEvent> &p_ev) { } break; case KEY_F: { if (k->get_command()) { - this->project_filter->search_box->grab_focus(); + this->search_box->grab_focus(); } else { keycode_handled = false; } @@ -1947,8 +1953,7 @@ void ProjectManager::_unhandled_input(const Ref<InputEvent> &p_ev) { } void ProjectManager::_load_recent_projects() { - _project_list->set_order_option(project_order_filter->get_filter_option()); - _project_list->set_search_term(project_filter->get_search_term()); + _project_list->set_search_term(search_box->get_text().strip_edges()); _project_list->load_projects(); _update_project_buttons(); @@ -1970,7 +1975,7 @@ void ProjectManager::_on_projects_updated() { } void ProjectManager::_on_project_created(const String &dir) { - project_filter->clear(); + search_box->clear(); int i = _project_list->refresh_project(dir); _project_list->select_project(i); _project_list->ensure_project_visible(i); @@ -2088,7 +2093,8 @@ void ProjectManager::_run_project_confirm() { const String &selected = selected_list[i].project_key; String path = EditorSettings::get_singleton()->get("projects/" + selected); - if (!DirAccess::exists(path + "/.import")) { + // `.right(6)` on `IMPORTED_FILES_PATH` strips away the leading "res://". + if (!DirAccess::exists(path.plus_file(ProjectSettings::IMPORTED_FILES_PATH.right(6)))) { run_error_diag->set_text(TTR("Can't run project: Assets need to be imported.\nPlease edit the project to trigger the initial import.")); run_error_diag->popup_centered(); return; @@ -2113,7 +2119,6 @@ void ProjectManager::_run_project_confirm() { } } -// When you press the "Run" button void ProjectManager::_run_project() { const Set<String> &selected_list = _project_list->get_selected_project_keys(); @@ -2226,8 +2231,6 @@ void ProjectManager::_erase_missing_projects() { void ProjectManager::_language_selected(int p_id) { String lang = language_btn->get_item_metadata(p_id); EditorSettings::get_singleton()->set("interface/editor/editor_language", lang); - language_btn->set_text(lang); - language_btn->set_icon(get_theme_icon("Environment", "EditorIcons")); language_restart_ask->set_text(TTR("Language changed.\nThe interface will update after restarting the editor or project manager.")); language_restart_ask->popup_centered(); @@ -2304,13 +2307,14 @@ void ProjectManager::_scan_multiple_folders(PackedStringArray p_files) { } } -void ProjectManager::_on_order_option_changed() { - _project_list->set_order_option(project_order_filter->get_filter_option()); - _project_list->sort_projects(); +void ProjectManager::_on_order_option_changed(int p_idx) { + if (is_inside_tree()) { + _project_list->set_order_option(p_idx); + } } -void ProjectManager::_on_filter_option_changed() { - _project_list->set_search_term(project_filter->get_search_term()); +void ProjectManager::_on_search_term_changed(const String &p_term) { + _project_list->set_search_term(p_term); _project_list->sort_projects(); // Select the first visible project in the list. @@ -2341,7 +2345,6 @@ ProjectManager::ProjectManager() { { int display_scale = EditorSettings::get_singleton()->get("interface/editor/display_scale"); - float custom_display_scale = EditorSettings::get_singleton()->get("interface/editor/custom_display_scale"); switch (display_scale) { case 0: { @@ -2372,9 +2375,8 @@ ProjectManager::ProjectManager() { case 6: editor_set_scale(2.0); break; - default: { - editor_set_scale(custom_display_scale); + editor_set_scale(EditorSettings::get_singleton()->get("interface/editor/custom_display_scale")); } break; } @@ -2385,28 +2387,27 @@ ProjectManager::ProjectManager() { DisplayServer::get_singleton()->window_set_size(DisplayServer::get_singleton()->window_get_size() * MAX(1, EDSCALE)); } + String cp; + cp += 0xA9; + // TRANSLATORS: This refers to the application where users manage their Godot projects. + DisplayServer::get_singleton()->window_set_title(VERSION_NAME + String(" - ") + TTR("Project Manager") + " - " + cp + " 2007-2020 Juan Linietsky, Ariel Manzur & Godot Contributors"); + FileDialog::set_default_show_hidden_files(EditorSettings::get_singleton()->get("filesystem/file_dialog/show_hidden_files")); set_anchors_and_margins_preset(Control::PRESET_WIDE); set_theme(create_custom_theme()); - gui_base = memnew(Control); - add_child(gui_base); - gui_base->set_anchors_and_margins_preset(Control::PRESET_WIDE); + set_anchors_and_margins_preset(Control::PRESET_WIDE); Panel *panel = memnew(Panel); - gui_base->add_child(panel); + add_child(panel); panel->set_anchors_and_margins_preset(Control::PRESET_WIDE); - panel->add_theme_style_override("panel", gui_base->get_theme_stylebox("Background", "EditorStyles")); + panel->add_theme_style_override("panel", get_theme_stylebox("Background", "EditorStyles")); VBoxContainer *vb = memnew(VBoxContainer); panel->add_child(vb); vb->set_anchors_and_margins_preset(Control::PRESET_WIDE, Control::PRESET_MODE_MINSIZE, 8 * EDSCALE); - String cp; - cp += 0xA9; - DisplayServer::get_singleton()->window_set_title(VERSION_NAME + String(" - ") + TTR("Project Manager") + " - " + cp + " 2007-2020 Juan Linietsky, Ariel Manzur & Godot Contributors"); - Control *center_box = memnew(Control); center_box->set_v_size_flags(Control::SIZE_EXPAND_FILL); vb->add_child(center_box); @@ -2416,218 +2417,231 @@ ProjectManager::ProjectManager() { tabs->set_anchors_and_margins_preset(Control::PRESET_WIDE); tabs->set_tab_align(TabContainer::ALIGN_LEFT); - HBoxContainer *tree_hb = memnew(HBoxContainer); - projects_hb = tree_hb; - + HBoxContainer *projects_hb = memnew(HBoxContainer); projects_hb->set_name(TTR("Projects")); + tabs->add_child(projects_hb); - tabs->add_child(tree_hb); - - VBoxContainer *search_tree_vb = memnew(VBoxContainer); - tree_hb->add_child(search_tree_vb); - search_tree_vb->set_h_size_flags(Control::SIZE_EXPAND_FILL); - - HBoxContainer *sort_filters = memnew(HBoxContainer); - Label *sort_label = memnew(Label); - sort_label->set_text(TTR("Sort:")); - sort_filters->add_child(sort_label); - Vector<String> sort_filter_titles; - sort_filter_titles.push_back(TTR("Name")); - sort_filter_titles.push_back(TTR("Path")); - sort_filter_titles.push_back(TTR("Last Edited")); - project_order_filter = memnew(ProjectListFilter); - project_order_filter->add_filter_option(); - project_order_filter->_setup_filters(sort_filter_titles); - project_order_filter->set_filter_size(150); - sort_filters->add_child(project_order_filter); - project_order_filter->connect("filter_changed", callable_mp(this, &ProjectManager::_on_order_option_changed)); - project_order_filter->set_custom_minimum_size(Size2(180, 10) * EDSCALE); - - int projects_sorting_order = (int)EditorSettings::get_singleton()->get("project_manager/sorting_order"); - project_order_filter->set_filter_option((ProjectListFilter::FilterOption)projects_sorting_order); - - sort_filters->add_spacer(true); - - project_filter = memnew(ProjectListFilter); - project_filter->add_search_box(); - project_filter->connect("filter_changed", callable_mp(this, &ProjectManager::_on_filter_option_changed)); - project_filter->set_custom_minimum_size(Size2(280, 10) * EDSCALE); - sort_filters->add_child(project_filter); - - search_tree_vb->add_child(sort_filters); - - PanelContainer *pc = memnew(PanelContainer); - pc->add_theme_style_override("panel", gui_base->get_theme_stylebox("bg", "Tree")); - search_tree_vb->add_child(pc); - pc->set_v_size_flags(Control::SIZE_EXPAND_FILL); - - _project_list = memnew(ProjectList); - _project_list->connect(ProjectList::SIGNAL_SELECTION_CHANGED, callable_mp(this, &ProjectManager::_update_project_buttons)); - _project_list->connect(ProjectList::SIGNAL_PROJECT_ASK_OPEN, callable_mp(this, &ProjectManager::_open_selected_projects_ask)); - pc->add_child(_project_list); - _project_list->set_enable_h_scroll(false); - - VBoxContainer *tree_vb = memnew(VBoxContainer); - tree_hb->add_child(tree_vb); - - Button *open = memnew(Button); - open->set_text(TTR("Edit")); - tree_vb->add_child(open); - open->connect("pressed", callable_mp(this, &ProjectManager::_open_selected_projects_ask)); - open_btn = open; - - Button *run = memnew(Button); - run->set_text(TTR("Run")); - tree_vb->add_child(run); - run->connect("pressed", callable_mp(this, &ProjectManager::_run_project)); - run_btn = run; - - tree_vb->add_child(memnew(HSeparator)); - - Button *scan = memnew(Button); - scan->set_text(TTR("Scan")); - tree_vb->add_child(scan); - scan->connect("pressed", callable_mp(this, &ProjectManager::_scan_projects)); - - tree_vb->add_child(memnew(HSeparator)); - - scan_dir = memnew(FileDialog); - scan_dir->set_access(FileDialog::ACCESS_FILESYSTEM); - scan_dir->set_file_mode(FileDialog::FILE_MODE_OPEN_DIR); - scan_dir->set_title(TTR("Select a Folder to Scan")); // must be after mode or it's overridden - scan_dir->set_current_dir(EditorSettings::get_singleton()->get("filesystem/directories/default_project_path")); - gui_base->add_child(scan_dir); - scan_dir->connect("dir_selected", callable_mp(this, &ProjectManager::_scan_begin)); - - Button *create = memnew(Button); - create->set_text(TTR("New Project")); - tree_vb->add_child(create); - create->connect("pressed", callable_mp(this, &ProjectManager::_new_project)); - - Button *import = memnew(Button); - import->set_text(TTR("Import")); - tree_vb->add_child(import); - import->connect("pressed", callable_mp(this, &ProjectManager::_import_project)); - - Button *rename = memnew(Button); - rename->set_text(TTR("Rename")); - tree_vb->add_child(rename); - rename->connect("pressed", callable_mp(this, &ProjectManager::_rename_project)); - rename_btn = rename; - - Button *erase = memnew(Button); - erase->set_text(TTR("Remove")); - tree_vb->add_child(erase); - erase->connect("pressed", callable_mp(this, &ProjectManager::_erase_project)); - erase_btn = erase; - - Button *erase_missing = memnew(Button); - erase_missing->set_text(TTR("Remove Missing")); - tree_vb->add_child(erase_missing); - erase_missing->connect("pressed", callable_mp(this, &ProjectManager::_erase_missing_projects)); - erase_missing_btn = erase_missing; - - tree_vb->add_spacer(); + { + // Projects + search bar + VBoxContainer *search_tree_vb = memnew(VBoxContainer); + projects_hb->add_child(search_tree_vb); + search_tree_vb->set_h_size_flags(Control::SIZE_EXPAND_FILL); - if (StreamPeerSSL::is_available()) { - asset_library = memnew(EditorAssetLibrary(true)); - asset_library->set_name(TTR("Templates")); - tabs->add_child(asset_library); - asset_library->connect("install_asset", callable_mp(this, &ProjectManager::_install_project)); - } else { - WARN_PRINT("Asset Library not available, as it requires SSL to work."); - } + HBoxContainer *hb = memnew(HBoxContainer); + hb->set_h_size_flags(Control::SIZE_EXPAND_FILL); + search_tree_vb->add_child(hb); - HBoxContainer *settings_hb = memnew(HBoxContainer); - settings_hb->set_alignment(BoxContainer::ALIGN_END); - settings_hb->set_h_grow_direction(Control::GROW_DIRECTION_BEGIN); + search_box = memnew(LineEdit); + search_box->set_placeholder(TTR("Search")); + search_box->set_tooltip(TTR("The search box filters projects by name and last path component.\nTo filter projects by name and full path, the query must contain at least one `/` character.")); + search_box->connect("text_changed", callable_mp(this, &ProjectManager::_on_search_term_changed)); + search_box->set_h_size_flags(Control::SIZE_EXPAND_FILL); + hb->add_child(search_box); - Label *version_label = memnew(Label); - String hash = String(VERSION_HASH); - if (hash.length() != 0) { - hash = "." + hash.left(9); - } - version_label->set_text("v" VERSION_FULL_BUILD "" + hash); - // Fade out the version label to be less prominent, but still readable - version_label->set_self_modulate(Color(1, 1, 1, 0.6)); - version_label->set_align(Label::ALIGN_CENTER); - settings_hb->add_child(version_label); + hb->add_spacer(); - language_btn = memnew(OptionButton); - language_btn->set_flat(true); - language_btn->set_focus_mode(Control::FOCUS_NONE); + Label *sort_label = memnew(Label); + sort_label->set_text(TTR("Sort:")); + hb->add_child(sort_label); - Vector<String> editor_languages; - List<PropertyInfo> editor_settings_properties; - EditorSettings::get_singleton()->get_property_list(&editor_settings_properties); - for (List<PropertyInfo>::Element *E = editor_settings_properties.front(); E; E = E->next()) { - PropertyInfo &pi = E->get(); - if (pi.name == "interface/editor/editor_language") { - editor_languages = pi.hint_string.split(","); - } - } - String current_lang = EditorSettings::get_singleton()->get("interface/editor/editor_language"); - for (int i = 0; i < editor_languages.size(); i++) { - String lang = editor_languages[i]; - String lang_name = TranslationServer::get_singleton()->get_locale_name(lang); - language_btn->add_item(lang_name + " [" + lang + "]", i); - language_btn->set_item_metadata(i, lang); - if (current_lang == lang) { - language_btn->select(i); - language_btn->set_text(lang); - } - } - language_btn->set_icon(get_theme_icon("Environment", "EditorIcons")); + filter_option = memnew(OptionButton); + filter_option->set_clip_text(true); + filter_option->set_custom_minimum_size(Size2(150 * EDSCALE, 10 * EDSCALE)); + filter_option->connect("item_selected", callable_mp(this, &ProjectManager::_on_order_option_changed)); + hb->add_child(filter_option); - settings_hb->add_child(language_btn); - language_btn->connect("item_selected", callable_mp(this, &ProjectManager::_language_selected)); + Vector<String> sort_filter_titles; + sort_filter_titles.push_back(TTR("Name")); + sort_filter_titles.push_back(TTR("Path")); + sort_filter_titles.push_back(TTR("Last Edited")); - center_box->add_child(settings_hb); - settings_hb->set_anchors_and_margins_preset(Control::PRESET_TOP_RIGHT); + for (int i = 0; i < sort_filter_titles.size(); i++) { + filter_option->add_item(sort_filter_titles[i]); + } - ////////////////////////////////////////////////////////////// + PanelContainer *pc = memnew(PanelContainer); + pc->add_theme_style_override("panel", get_theme_stylebox("bg", "Tree")); + pc->set_v_size_flags(Control::SIZE_EXPAND_FILL); + search_tree_vb->add_child(pc); - language_restart_ask = memnew(ConfirmationDialog); - language_restart_ask->get_ok()->set_text(TTR("Restart Now")); - language_restart_ask->get_ok()->connect("pressed", callable_mp(this, &ProjectManager::_restart_confirm)); - language_restart_ask->get_cancel()->set_text(TTR("Continue")); - gui_base->add_child(language_restart_ask); + _project_list = memnew(ProjectList); + _project_list->connect(ProjectList::SIGNAL_SELECTION_CHANGED, callable_mp(this, &ProjectManager::_update_project_buttons)); + _project_list->connect(ProjectList::SIGNAL_PROJECT_ASK_OPEN, callable_mp(this, &ProjectManager::_open_selected_projects_ask)); + _project_list->set_enable_h_scroll(false); + pc->add_child(_project_list); + } - erase_missing_ask = memnew(ConfirmationDialog); - erase_missing_ask->get_ok()->set_text(TTR("Remove All")); - erase_missing_ask->get_ok()->connect("pressed", callable_mp(this, &ProjectManager::_erase_missing_projects_confirm)); - gui_base->add_child(erase_missing_ask); + { + // Project tab side bar + VBoxContainer *tree_vb = memnew(VBoxContainer); + tree_vb->set_custom_minimum_size(Size2(120, 120)); + projects_hb->add_child(tree_vb); + + Button *create = memnew(Button); + create->set_text(TTR("New Project")); + create->connect("pressed", callable_mp(this, &ProjectManager::_new_project)); + tree_vb->add_child(create); + + Button *import = memnew(Button); + import->set_text(TTR("Import")); + import->connect("pressed", callable_mp(this, &ProjectManager::_import_project)); + tree_vb->add_child(import); + + Button *scan = memnew(Button); + scan->set_text(TTR("Scan")); + scan->connect("pressed", callable_mp(this, &ProjectManager::_scan_projects)); + tree_vb->add_child(scan); + + tree_vb->add_child(memnew(HSeparator)); + + open_btn = memnew(Button); + open_btn->set_text(TTR("Edit")); + open_btn->connect("pressed", callable_mp(this, &ProjectManager::_open_selected_projects_ask)); + tree_vb->add_child(open_btn); + + run_btn = memnew(Button); + run_btn->set_text(TTR("Run")); + run_btn->connect("pressed", callable_mp(this, &ProjectManager::_run_project)); + tree_vb->add_child(run_btn); + + rename_btn = memnew(Button); + rename_btn->set_text(TTR("Rename")); + rename_btn->connect("pressed", callable_mp(this, &ProjectManager::_rename_project)); + tree_vb->add_child(rename_btn); + + erase_btn = memnew(Button); + erase_btn->set_text(TTR("Remove")); + erase_btn->connect("pressed", callable_mp(this, &ProjectManager::_erase_project)); + tree_vb->add_child(erase_btn); + + erase_missing_btn = memnew(Button); + erase_missing_btn->set_text(TTR("Remove Missing")); + erase_missing_btn->connect("pressed", callable_mp(this, &ProjectManager::_erase_missing_projects)); + tree_vb->add_child(erase_missing_btn); + } - erase_ask = memnew(ConfirmationDialog); - erase_ask->get_ok()->set_text(TTR("Remove")); - erase_ask->get_ok()->connect("pressed", callable_mp(this, &ProjectManager::_erase_project_confirm)); - gui_base->add_child(erase_ask); + { + // Version info and language options + HBoxContainer *settings_hb = memnew(HBoxContainer); + settings_hb->set_alignment(BoxContainer::ALIGN_END); + settings_hb->set_h_grow_direction(Control::GROW_DIRECTION_BEGIN); + + Label *version_label = memnew(Label); + String hash = String(VERSION_HASH); + if (hash.length() != 0) { + hash = "." + hash.left(9); + } + version_label->set_text("v" VERSION_FULL_BUILD "" + hash); + version_label->set_self_modulate(Color(1, 1, 1, 0.6)); + version_label->set_align(Label::ALIGN_CENTER); + settings_hb->add_child(version_label); + + language_btn = memnew(OptionButton); + language_btn->set_flat(true); + language_btn->set_icon(get_theme_icon("Environment", "EditorIcons")); + language_btn->set_focus_mode(Control::FOCUS_NONE); + language_btn->connect("item_selected", callable_mp(this, &ProjectManager::_language_selected)); + + Vector<String> editor_languages; + List<PropertyInfo> editor_settings_properties; + EditorSettings::get_singleton()->get_property_list(&editor_settings_properties); + for (List<PropertyInfo>::Element *E = editor_settings_properties.front(); E; E = E->next()) { + PropertyInfo &pi = E->get(); + if (pi.name == "interface/editor/editor_language") { + editor_languages = pi.hint_string.split(","); + break; + } + } - multi_open_ask = memnew(ConfirmationDialog); - multi_open_ask->get_ok()->set_text(TTR("Edit")); - multi_open_ask->get_ok()->connect("pressed", callable_mp(this, &ProjectManager::_open_selected_projects)); - gui_base->add_child(multi_open_ask); + String current_lang = EditorSettings::get_singleton()->get("interface/editor/editor_language"); + language_btn->set_text(current_lang); - multi_run_ask = memnew(ConfirmationDialog); - multi_run_ask->get_ok()->set_text(TTR("Run")); - multi_run_ask->get_ok()->connect("pressed", callable_mp(this, &ProjectManager::_run_project_confirm)); - gui_base->add_child(multi_run_ask); + for (int i = 0; i < editor_languages.size(); i++) { + String lang = editor_languages[i]; + String lang_name = TranslationServer::get_singleton()->get_locale_name(lang); + language_btn->add_item(lang_name + " [" + lang + "]", i); + language_btn->set_item_metadata(i, lang); + if (current_lang == lang) { + language_btn->select(i); + } + } - multi_scan_ask = memnew(ConfirmationDialog); - multi_scan_ask->get_ok()->set_text(TTR("Scan")); - gui_base->add_child(multi_scan_ask); + settings_hb->add_child(language_btn); + center_box->add_child(settings_hb); + settings_hb->set_anchors_and_margins_preset(Control::PRESET_TOP_RIGHT); + } - ask_update_settings = memnew(ConfirmationDialog); - ask_update_settings->get_ok()->connect("pressed", callable_mp(this, &ProjectManager::_confirm_update_settings)); - gui_base->add_child(ask_update_settings); + if (StreamPeerSSL::is_available()) { + asset_library = memnew(EditorAssetLibrary(true)); + asset_library->set_name(TTR("Templates")); + tabs->add_child(asset_library); + asset_library->connect("install_asset", callable_mp(this, &ProjectManager::_install_project)); + } else { + WARN_PRINT("Asset Library not available, as it requires SSL to work."); + } - OS::get_singleton()->set_low_processor_usage_mode(true); + { + // Dialogs + language_restart_ask = memnew(ConfirmationDialog); + language_restart_ask->get_ok()->set_text(TTR("Restart Now")); + language_restart_ask->get_ok()->connect("pressed", callable_mp(this, &ProjectManager::_restart_confirm)); + language_restart_ask->get_cancel()->set_text(TTR("Continue")); + add_child(language_restart_ask); + + scan_dir = memnew(FileDialog); + scan_dir->set_access(FileDialog::ACCESS_FILESYSTEM); + scan_dir->set_file_mode(FileDialog::FILE_MODE_OPEN_DIR); + scan_dir->set_title(TTR("Select a Folder to Scan")); // must be after mode or it's overridden + scan_dir->set_current_dir(EditorSettings::get_singleton()->get("filesystem/directories/default_project_path")); + add_child(scan_dir); + scan_dir->connect("dir_selected", callable_mp(this, &ProjectManager::_scan_begin)); + + erase_missing_ask = memnew(ConfirmationDialog); + erase_missing_ask->get_ok()->set_text(TTR("Remove All")); + erase_missing_ask->get_ok()->connect("pressed", callable_mp(this, &ProjectManager::_erase_missing_projects_confirm)); + add_child(erase_missing_ask); + + erase_ask = memnew(ConfirmationDialog); + erase_ask->get_ok()->set_text(TTR("Remove")); + erase_ask->get_ok()->connect("pressed", callable_mp(this, &ProjectManager::_erase_project_confirm)); + add_child(erase_ask); + + multi_open_ask = memnew(ConfirmationDialog); + multi_open_ask->get_ok()->set_text(TTR("Edit")); + multi_open_ask->get_ok()->connect("pressed", callable_mp(this, &ProjectManager::_open_selected_projects)); + add_child(multi_open_ask); + + multi_run_ask = memnew(ConfirmationDialog); + multi_run_ask->get_ok()->set_text(TTR("Run")); + multi_run_ask->get_ok()->connect("pressed", callable_mp(this, &ProjectManager::_run_project_confirm)); + add_child(multi_run_ask); + + multi_scan_ask = memnew(ConfirmationDialog); + multi_scan_ask->get_ok()->set_text(TTR("Scan")); + add_child(multi_scan_ask); + + ask_update_settings = memnew(ConfirmationDialog); + ask_update_settings->get_ok()->connect("pressed", callable_mp(this, &ProjectManager::_confirm_update_settings)); + add_child(ask_update_settings); + + npdialog = memnew(ProjectDialog); + npdialog->connect("projects_updated", callable_mp(this, &ProjectManager::_on_projects_updated)); + npdialog->connect("project_created", callable_mp(this, &ProjectManager::_on_project_created)); + add_child(npdialog); + + run_error_diag = memnew(AcceptDialog); + run_error_diag->set_title(TTR("Can't run project")); + add_child(run_error_diag); - npdialog = memnew(ProjectDialog); - gui_base->add_child(npdialog); + dialog_error = memnew(AcceptDialog); + add_child(dialog_error); - npdialog->connect("projects_updated", callable_mp(this, &ProjectManager::_on_projects_updated)); - npdialog->connect("project_created", callable_mp(this, &ProjectManager::_on_project_created)); + open_templates = memnew(ConfirmationDialog); + open_templates->set_text(TTR("You currently don't have any projects.\nWould you like to explore official example projects in the Asset Library?")); + open_templates->get_ok()->set_text(TTR("Open Asset Library")); + open_templates->connect("confirmed", callable_mp(this, &ProjectManager::_open_asset_library)); + add_child(open_templates); + } _load_recent_projects(); @@ -2637,18 +2651,7 @@ ProjectManager::ProjectManager() { SceneTree::get_singleton()->get_root()->connect("files_dropped", callable_mp(this, &ProjectManager::_files_dropped)); - run_error_diag = memnew(AcceptDialog); - gui_base->add_child(run_error_diag); - run_error_diag->set_title(TTR("Can't run project")); - - dialog_error = memnew(AcceptDialog); - gui_base->add_child(dialog_error); - - open_templates = memnew(ConfirmationDialog); - open_templates->set_text(TTR("You currently don't have any projects.\nWould you like to explore official example projects in the Asset Library?")); - open_templates->get_ok()->set_text(TTR("Open Asset Library")); - open_templates->connect("confirmed", callable_mp(this, &ProjectManager::_open_asset_library)); - add_child(open_templates); + OS::get_singleton()->set_low_processor_usage_mode(true); } ProjectManager::~ProjectManager() { @@ -2656,82 +2659,3 @@ ProjectManager::~ProjectManager() { EditorSettings::destroy(); } } - -void ProjectListFilter::_setup_filters(Vector<String> options) { - filter_option->clear(); - for (int i = 0; i < options.size(); i++) { - filter_option->add_item(options[i]); - } -} - -void ProjectListFilter::_search_text_changed(const String &p_newtext) { - emit_signal("filter_changed"); -} - -String ProjectListFilter::get_search_term() { - return search_box->get_text().strip_edges(); -} - -ProjectListFilter::FilterOption ProjectListFilter::get_filter_option() { - return _current_filter; -} - -void ProjectListFilter::set_filter_option(FilterOption option) { - filter_option->select((int)option); - _filter_option_selected(0); -} - -void ProjectListFilter::_filter_option_selected(int p_idx) { - FilterOption selected = (FilterOption)(filter_option->get_selected()); - if (_current_filter != selected) { - _current_filter = selected; - if (is_inside_tree()) { - emit_signal("filter_changed"); - } - } -} - -void ProjectListFilter::_notification(int p_what) { - if (p_what == NOTIFICATION_ENTER_TREE && has_search_box) { - search_box->set_right_icon(get_theme_icon("Search", "EditorIcons")); - search_box->set_clear_button_enabled(true); - } -} - -void ProjectListFilter::_bind_methods() { - ADD_SIGNAL(MethodInfo("filter_changed")); -} - -void ProjectListFilter::add_filter_option() { - filter_option = memnew(OptionButton); - filter_option->set_clip_text(true); - filter_option->connect("item_selected", callable_mp(this, &ProjectListFilter::_filter_option_selected)); - add_child(filter_option); -} - -void ProjectListFilter::add_search_box() { - search_box = memnew(LineEdit); - search_box->set_placeholder(TTR("Search")); - search_box->set_tooltip( - TTR("The search box filters projects by name and last path component.\nTo filter projects by name and full path, the query must contain at least one `/` character.")); - search_box->connect("text_changed", callable_mp(this, &ProjectListFilter::_search_text_changed)); - search_box->set_h_size_flags(Control::SIZE_EXPAND_FILL); - add_child(search_box); - - has_search_box = true; -} - -void ProjectListFilter::set_filter_size(int h_size) { - filter_option->set_custom_minimum_size(Size2(h_size * EDSCALE, 10 * EDSCALE)); -} - -ProjectListFilter::ProjectListFilter() { - _current_filter = FILTER_NAME; - has_search_box = false; -} - -void ProjectListFilter::clear() { - if (has_search_box) { - search_box->clear(); - } -} |