diff options
Diffstat (limited to 'editor')
26 files changed, 242 insertions, 188 deletions
diff --git a/editor/SCsub b/editor/SCsub index 82a4ecb6c0..7d48e47c9f 100644 --- a/editor/SCsub +++ b/editor/SCsub @@ -79,9 +79,6 @@ if env['tools']: env.CommandNoCache('#editor/builtin_fonts.gen.h', flist, run_in_subprocess(editor_builders.make_fonts_header)) env.add_source_files(env.editor_sources, "*.cpp") - env_thirdparty = env.Clone() - env_thirdparty.disable_warnings() - env_thirdparty.add_source_files(env.editor_sources, ["#thirdparty/misc/clipper.cpp"]) SConscript('collada/SCsub') SConscript('doc/SCsub') diff --git a/editor/animation_track_editor.cpp b/editor/animation_track_editor.cpp index b2af11fab0..0eec01f2cb 100644 --- a/editor/animation_track_editor.cpp +++ b/editor/animation_track_editor.cpp @@ -63,8 +63,6 @@ public: ClassDB::bind_method("_dont_undo_redo", &AnimationTrackKeyEdit::_dont_undo_redo); } - //PopupDialog *ke_dialog; - void _fix_node_path(Variant &value) { NodePath np = value; @@ -3456,7 +3454,7 @@ void AnimationTrackEditor::_update_tracks() { Ref<Texture> icon = get_icon("Node", "EditorIcons"); String name = base_path; String tooltip; - if (root) { + if (root && root->has_node(base_path)) { Node *n = root->get_node(base_path); if (n) { if (has_icon(n->get_class(), "EditorIcons")) { @@ -3656,7 +3654,8 @@ void AnimationTrackEditor::_update_step(double p_new_step) { step->set_block_signals(true); undo_redo->commit_action(); step->set_block_signals(false); - emit_signal("animation_step_changed", step_value); + emit_signal("animation_step_changed", p_new_step); + animation->_change_notify("step"); } void AnimationTrackEditor::_update_length(double p_new_len) { @@ -4931,7 +4930,6 @@ void AnimationTrackEditor::_bind_methods() { ClassDB::bind_method("_update_scroll", &AnimationTrackEditor::_update_scroll); ClassDB::bind_method("_update_tracks", &AnimationTrackEditor::_update_tracks); ClassDB::bind_method("_update_step", &AnimationTrackEditor::_update_step); - ClassDB::bind_method("_update_length", &AnimationTrackEditor::_update_length); ClassDB::bind_method("_dropped_track", &AnimationTrackEditor::_dropped_track); ClassDB::bind_method("_add_track", &AnimationTrackEditor::_add_track); ClassDB::bind_method("_new_track_node_selected", &AnimationTrackEditor::_new_track_node_selected); @@ -4992,7 +4990,6 @@ AnimationTrackEditor::AnimationTrackEditor() { timeline->connect("name_limit_changed", this, "_name_limit_changed"); timeline->connect("track_added", this, "_add_track"); timeline->connect("value_changed", this, "_timeline_value_changed"); - timeline->connect("length_changed", this, "_update_length"); scroll = memnew(ScrollContainer); timeline_vbox->add_child(scroll); diff --git a/editor/editor_export.cpp b/editor/editor_export.cpp index 6751e58bb2..37f148bdbb 100644 --- a/editor/editor_export.cpp +++ b/editor/editor_export.cpp @@ -615,6 +615,7 @@ void EditorExportPlugin::_bind_methods() { BIND_VMETHOD(MethodInfo("_export_file", PropertyInfo(Variant::STRING, "path"), PropertyInfo(Variant::STRING, "type"), PropertyInfo(Variant::POOL_STRING_ARRAY, "features"))); BIND_VMETHOD(MethodInfo("_export_begin", PropertyInfo(Variant::POOL_STRING_ARRAY, "features"), PropertyInfo(Variant::BOOL, "is_debug"), PropertyInfo(Variant::STRING, "path"), PropertyInfo(Variant::INT, "flags"))); + BIND_VMETHOD(MethodInfo("_export_end")); } EditorExportPlugin::EditorExportPlugin() { @@ -692,6 +693,10 @@ Error EditorExportPlatform::export_project_files(const Ref<EditorExportPreset> & } } + //add native icons to non-resource include list + _edit_filter_list(paths, String("*.icns"), false); + _edit_filter_list(paths, String("*.ico"), false); + _edit_filter_list(paths, p_preset->get_include_filter(), false); _edit_filter_list(paths, p_preset->get_exclude_filter(), true); diff --git a/editor/editor_file_system.cpp b/editor/editor_file_system.cpp index 90af593166..4ddb28b440 100644 --- a/editor/editor_file_system.cpp +++ b/editor/editor_file_system.cpp @@ -844,7 +844,7 @@ void EditorFileSystem::_scan_fs_changes(EditorFileSystemDirectory *p_dir, const bool updated_dir = false; String cd = p_dir->get_path(); - if (current_mtime != p_dir->modified_time || using_fat_32) { + if (current_mtime != p_dir->modified_time || using_fat32_or_exfat) { updated_dir = true; p_dir->modified_time = current_mtime; @@ -2140,8 +2140,8 @@ EditorFileSystem::EditorFileSystem() { if (da->change_dir("res://.import") != OK) { da->make_dir("res://.import"); } - //this should probably also work on Unix and use the string it returns for FAT32 - using_fat_32 = da->get_filesystem_type() == "FAT32"; + // This should probably also work on Unix and use the string it returns for FAT32 or exFAT + using_fat32_or_exfat = (da->get_filesystem_type() == "FAT32" || da->get_filesystem_type() == "exFAT"); memdelete(da); scan_total = 0; diff --git a/editor/editor_file_system.h b/editor/editor_file_system.h index 8943706202..72d9489f21 100644 --- a/editor/editor_file_system.h +++ b/editor/editor_file_system.h @@ -237,7 +237,7 @@ class EditorFileSystem : public Node { static Error _resource_import(const String &p_path); - bool using_fat_32; //workaround for projects in FAT32 filesystem (pendrives, most of the time) + bool using_fat32_or_exfat; // Workaround for projects in FAT32 or exFAT filesystem (pendrives, most of the time) void _find_group_files(EditorFileSystemDirectory *efd, Map<String, Vector<String> > &group_files, Set<String> &groups_to_reimport); diff --git a/editor/editor_node.cpp b/editor/editor_node.cpp index 907d43b26f..82e7a37f19 100644 --- a/editor/editor_node.cpp +++ b/editor/editor_node.cpp @@ -6403,7 +6403,7 @@ EditorNode::EditorNode() { ED_SHORTCUT("editor/editor_2d", TTR("Open 2D Editor"), KEY_F1); ED_SHORTCUT("editor/editor_3d", TTR("Open 3D Editor"), KEY_F2); ED_SHORTCUT("editor/editor_script", TTR("Open Script Editor"), KEY_F3); //hack needed for script editor F3 search to work :) Assign like this or don't use F3 - ED_SHORTCUT("editor/editor_help", TTR("Search Help"), KEY_F4); + ED_SHORTCUT("editor/editor_help", TTR("Search Help"), KEY_MASK_SHIFT | KEY_F1); #endif ED_SHORTCUT("editor/editor_assetlib", TTR("Open Asset Library")); ED_SHORTCUT("editor/editor_next", TTR("Open the next Editor")); diff --git a/editor/editor_resource_preview.cpp b/editor/editor_resource_preview.cpp index 173333dac9..2baad8c904 100644 --- a/editor/editor_resource_preview.cpp +++ b/editor/editor_resource_preview.cpp @@ -71,7 +71,21 @@ Ref<Texture> EditorResourcePreviewGenerator::generate_from_path(const String &p_ return generate(res, p_size); } -bool EditorResourcePreviewGenerator::should_generate_small_preview() const { +bool EditorResourcePreviewGenerator::generate_small_preview_automatically() const { + + if (get_script_instance() && get_script_instance()->has_method("generate_small_preview_automatically")) { + return get_script_instance()->call("generate_small_preview_automatically"); + } + + return false; +} + +bool EditorResourcePreviewGenerator::can_generate_small_preview() const { + + if (get_script_instance() && get_script_instance()->has_method("can_generate_small_preview")) { + return get_script_instance()->call("can_generate_small_preview"); + } + return false; } @@ -80,6 +94,8 @@ void EditorResourcePreviewGenerator::_bind_methods() { ClassDB::add_virtual_method(get_class_static(), MethodInfo(Variant::BOOL, "handles", PropertyInfo(Variant::STRING, "type"))); ClassDB::add_virtual_method(get_class_static(), MethodInfo(CLASS_INFO(Texture), "generate", PropertyInfo(Variant::OBJECT, "from", PROPERTY_HINT_RESOURCE_TYPE, "Resource"), PropertyInfo(Variant::VECTOR2, "size"))); ClassDB::add_virtual_method(get_class_static(), MethodInfo(CLASS_INFO(Texture), "generate_from_path", PropertyInfo(Variant::STRING, "path", PROPERTY_HINT_FILE), PropertyInfo(Variant::VECTOR2, "size"))); + ClassDB::add_virtual_method(get_class_static(), MethodInfo(Variant::BOOL, "generate_small_preview_automatically")); + ClassDB::add_virtual_method(get_class_static(), MethodInfo(Variant::BOOL, "can_generate_small_preview")); } EditorResourcePreviewGenerator::EditorResourcePreviewGenerator() { @@ -154,16 +170,27 @@ void EditorResourcePreview::_generate_preview(Ref<ImageTexture> &r_texture, Ref< } r_texture = generated; - if (r_texture.is_valid() && preview_generators[i]->should_generate_small_preview()) { - int small_thumbnail_size = EditorNode::get_singleton()->get_theme_base()->get_icon("Object", "EditorIcons")->get_width(); // Kind of a workaround to retrieve the default icon size - small_thumbnail_size *= EDSCALE; + int small_thumbnail_size = EditorNode::get_singleton()->get_theme_base()->get_icon("Object", "EditorIcons")->get_width(); // Kind of a workaround to retrieve the default icon size + small_thumbnail_size *= EDSCALE; + if (preview_generators[i]->can_generate_small_preview()) { + Ref<Texture> generated_small; + if (p_item.resource.is_valid()) { + generated_small = preview_generators[i]->generate(p_item.resource, Vector2(small_thumbnail_size, small_thumbnail_size)); + } else { + generated_small = preview_generators[i]->generate_from_path(p_item.path, Vector2(small_thumbnail_size, small_thumbnail_size)); + } + r_small_texture = generated_small; + } + + if (!r_small_texture.is_valid() && r_texture.is_valid() && preview_generators[i]->generate_small_preview_automatically()) { Ref<Image> small_image = r_texture->get_data(); small_image = small_image->duplicate(); small_image->resize(small_thumbnail_size, small_thumbnail_size, Image::INTERPOLATE_CUBIC); r_small_texture.instance(); r_small_texture->create_from_image(small_image); } + break; } diff --git a/editor/editor_resource_preview.h b/editor/editor_resource_preview.h index 9b9223a818..e0fd54c924 100644 --- a/editor/editor_resource_preview.h +++ b/editor/editor_resource_preview.h @@ -48,7 +48,8 @@ public: virtual Ref<Texture> generate(const RES &p_from, const Size2 p_size) const; virtual Ref<Texture> generate_from_path(const String &p_path, const Size2 p_size) const; - virtual bool should_generate_small_preview() const; + virtual bool generate_small_preview_automatically() const; + virtual bool can_generate_small_preview() const; EditorResourcePreviewGenerator(); }; diff --git a/editor/editor_settings.cpp b/editor/editor_settings.cpp index cb40926ce3..79dcbca7a2 100644 --- a/editor/editor_settings.cpp +++ b/editor/editor_settings.cpp @@ -268,6 +268,11 @@ void EditorSettings::_load_defaults(Ref<ConfigFile> p_extra_config) { String host_lang = OS::get_singleton()->get_locale(); host_lang = TranslationServer::standardize_locale(host_lang); + // Some locales are not properly supported currently in Godot due to lack of font shaping + // (e.g. Arabic or Hindi), so even though we have work in progress translations for them, + // we skip them as they don't render properly. (GH-28577) + const Vector<String> locales_to_skip = String("ar,bn,fa,he,hi,ml,si,ta,te,ur").split(","); + String best; EditorTranslationList *etl = _editor_translations; @@ -275,6 +280,15 @@ void EditorSettings::_load_defaults(Ref<ConfigFile> p_extra_config) { while (etl->data) { const String &locale = etl->lang; + + // Skip locales which we can't render properly (see above comment). + // Test against language code without regional variants (e.g. ur_PK). + String lang_code = locale.get_slice("_", 0); + if (locales_to_skip.find(lang_code) != -1) { + etl++; + continue; + } + lang_hint += ","; lang_hint += locale; diff --git a/editor/filesystem_dock.cpp b/editor/filesystem_dock.cpp index b7e9d36d88..52ed94e428 100644 --- a/editor/filesystem_dock.cpp +++ b/editor/filesystem_dock.cpp @@ -756,7 +756,7 @@ void FileSystemDock::_update_file_list(bool p_keep_selection) { Ref<Texture> type_icon; Ref<Texture> big_icon; - String tooltip = fname; + String tooltip = fpath; // Select the icons if (!finfo->import_broken) { diff --git a/editor/plugins/animation_player_editor_plugin.cpp b/editor/plugins/animation_player_editor_plugin.cpp index 0a9436952b..eabb781288 100644 --- a/editor/plugins/animation_player_editor_plugin.cpp +++ b/editor/plugins/animation_player_editor_plugin.cpp @@ -54,13 +54,9 @@ void AnimationPlayerEditor::_node_removed(Node *p_node) { track_editor->set_root(NULL); track_editor->show_select_node_warning(true); _update_player(); - //editor->animation_editor_make_visible(false); } } -void AnimationPlayerEditor::_gui_input(Ref<InputEvent> p_event) { -} - void AnimationPlayerEditor::_notification(int p_what) { switch (p_what) { case NOTIFICATION_PROCESS: { @@ -293,25 +289,40 @@ void AnimationPlayerEditor::_pause_pressed() { //player->set_pause( pause->is_pressed() ); } -void AnimationPlayerEditor::_animation_selected(int p_which) { - if (updating) - return; +String AnimationPlayerEditor::_get_current_animation() const { + // when selecting an animation, the idea is that the only interesting behavior // ui-wise is that it should play/blend the next one if currently playing - String current; if (animation->get_selected() >= 0 && animation->get_selected() < animation->get_item_count()) { - current = animation->get_item_text(animation->get_selected()); + return animation->get_item_text(animation->get_selected()); } - if (current != "") { + return ""; +} - player->set_assigned_animation(current); +void AnimationPlayerEditor::_animation_selected(int p_which) { + + if (updating) + return; + + _current_animation_updated(); +} +void AnimationPlayerEditor::_current_animation_updated() { + + String current = _get_current_animation(); + + if (current != "") { Ref<Animation> anim = player->get_animation(current); + + player->set_assigned_animation(current); { + if (!anim->is_connected("changed", this, "_current_animation_updated")) + anim->connect("changed", this, "_current_animation_updated"); + track_editor->set_animation(anim); Node *root = player->get_node(player->get_root()); if (root) { @@ -679,10 +690,14 @@ Dictionary AnimationPlayerEditor::get_state() const { } void AnimationPlayerEditor::set_state(const Dictionary &p_state) { - if (p_state.has("visible") && p_state["visible"]) { + if (!p_state.has("visible") || !p_state["visible"]) { + return; + } + if (!EditorNode::get_singleton()->get_edited_scene()) { + return; + } - if (!EditorNode::get_singleton()->get_edited_scene()) - return; + if (p_state.has("player")) { Node *n = EditorNode::get_singleton()->get_edited_scene()->get_node(p_state["player"]); if (Object::cast_to<AnimationPlayer>(n) && EditorNode::get_singleton()->get_editor_selection()->is_selected(n)) { @@ -691,7 +706,6 @@ void AnimationPlayerEditor::set_state(const Dictionary &p_state) { show(); set_process(true); ensure_visibility(); - //EditorNode::get_singleton()->animation_panel_make_visible(true); if (p_state.has("animation")) { String anim = p_state["animation"]; @@ -699,10 +713,10 @@ void AnimationPlayerEditor::set_state(const Dictionary &p_state) { _animation_edit(); } } + } - if (p_state.has("track_editor_state")) { - track_editor->set_state(p_state["track_editor_state"]); - } + if (p_state.has("track_editor_state")) { + track_editor->set_state(p_state["track_editor_state"]); } } @@ -721,17 +735,17 @@ void AnimationPlayerEditor::_animation_edit() { String current = animation->get_item_text(animation->get_selected()); Ref<Animation> anim = player->get_animation(current); track_editor->set_animation(anim); + Node *root = player->get_node(player->get_root()); if (root) { track_editor->set_root(root); } - } else { - track_editor->set_animation(Ref<Animation>()); track_editor->set_root(NULL); } } + void AnimationPlayerEditor::_dialog_action(String p_file) { switch (current_option) { @@ -881,8 +895,6 @@ void AnimationPlayerEditor::_update_player() { _animation_selected(0); } - //pause->set_pressed(player->is_paused()); - if (animation->get_item_count()) { String current = animation->get_item_text(animation->get_selected()); Ref<Animation> anim = player->get_animation(current); @@ -910,8 +922,6 @@ void AnimationPlayerEditor::edit(AnimationPlayer *p_player) { track_editor->show_select_node_warning(false); } else { track_editor->show_select_node_warning(true); - - //hide(); } } @@ -1068,17 +1078,19 @@ void AnimationPlayerEditor::_list_changed() { _update_player(); } -void AnimationPlayerEditor::_animation_key_editor_anim_len_changed(float p_len) { - - frame->set_max(p_len); -} - void AnimationPlayerEditor::_animation_key_editor_anim_step_changed(float p_len) { if (p_len) frame->set_step(p_len); else frame->set_step(0.00001); + + String current = _get_current_animation(); + + if (current != "") { + Ref<Animation> anim = player->get_animation(current); + anim->_change_notify("step"); + } } void AnimationPlayerEditor::_animation_key_editor_seek(float p_pos, bool p_drag) { @@ -1110,7 +1122,6 @@ void AnimationPlayerEditor::_hide_anim_editors() { track_editor->set_animation(Ref<Animation>()); track_editor->set_root(NULL); track_editor->show_select_node_warning(true); - //editor->animation_editor_make_visible(false); } void AnimationPlayerEditor::_animation_about_to_show_menu() { @@ -1431,6 +1442,7 @@ void AnimationPlayerEditor::_prepare_onion_layers_2() { new_state["show_rulers"] = false; new_state["show_guides"] = false; new_state["show_helpers"] = false; + new_state["show_zoom_control"] = false; // TODO: Save/restore only affected entries CanvasItemEditor::get_singleton()->set_state(new_state); } @@ -1483,7 +1495,7 @@ void AnimationPlayerEditor::_prepare_onion_layers_2() { if (valid) { player->seek(pos, true); get_tree()->flush_transform_notifications(); // Needed for transforms of Spatials - values_backup.update_skeletons(); // Needed for Skeletons + values_backup.update_skeletons(); // Needed for Skeletons (2D & 3D) VS::get_singleton()->viewport_set_active(onion.captures[cidx], true); VS::get_singleton()->viewport_set_parent_viewport(root_vp, onion.captures[cidx]); @@ -1547,7 +1559,6 @@ void AnimationPlayerEditor::_pin_pressed() { void AnimationPlayerEditor::_bind_methods() { - ClassDB::bind_method(D_METHOD("_gui_input"), &AnimationPlayerEditor::_gui_input); ClassDB::bind_method(D_METHOD("_node_removed"), &AnimationPlayerEditor::_node_removed); ClassDB::bind_method(D_METHOD("_play_pressed"), &AnimationPlayerEditor::_play_pressed); ClassDB::bind_method(D_METHOD("_play_from_pressed"), &AnimationPlayerEditor::_play_from_pressed); @@ -1557,6 +1568,7 @@ void AnimationPlayerEditor::_bind_methods() { ClassDB::bind_method(D_METHOD("_autoplay_pressed"), &AnimationPlayerEditor::_autoplay_pressed); ClassDB::bind_method(D_METHOD("_pause_pressed"), &AnimationPlayerEditor::_pause_pressed); ClassDB::bind_method(D_METHOD("_animation_selected"), &AnimationPlayerEditor::_animation_selected); + ClassDB::bind_method(D_METHOD("_current_animation_updated"), &AnimationPlayerEditor::_current_animation_updated); ClassDB::bind_method(D_METHOD("_animation_name_edited"), &AnimationPlayerEditor::_animation_name_edited); ClassDB::bind_method(D_METHOD("_animation_new"), &AnimationPlayerEditor::_animation_new); ClassDB::bind_method(D_METHOD("_animation_rename"), &AnimationPlayerEditor::_animation_rename); @@ -1576,7 +1588,6 @@ void AnimationPlayerEditor::_bind_methods() { //ClassDB::bind_method(D_METHOD("_editor_load_all"),&AnimationPlayerEditor::_editor_load_all); ClassDB::bind_method(D_METHOD("_list_changed"), &AnimationPlayerEditor::_list_changed); ClassDB::bind_method(D_METHOD("_animation_key_editor_seek"), &AnimationPlayerEditor::_animation_key_editor_seek); - ClassDB::bind_method(D_METHOD("_animation_key_editor_anim_len_changed"), &AnimationPlayerEditor::_animation_key_editor_anim_len_changed); ClassDB::bind_method(D_METHOD("_animation_key_editor_anim_step_changed"), &AnimationPlayerEditor::_animation_key_editor_anim_step_changed); ClassDB::bind_method(D_METHOD("_hide_anim_editors"), &AnimationPlayerEditor::_hide_anim_editors); ClassDB::bind_method(D_METHOD("_animation_duplicate"), &AnimationPlayerEditor::_animation_duplicate); @@ -1610,12 +1621,6 @@ AnimationPlayerEditor::AnimationPlayerEditor(EditorNode *p_editor, AnimationPlay player = NULL; - Label *l; - - /*l= memnew( Label ); - l->set_text("Animation Player:"); - add_child(l);*/ - HBoxContainer *hb = memnew(HBoxContainer); add_child(hb); @@ -1640,10 +1645,6 @@ AnimationPlayerEditor::AnimationPlayerEditor(EditorNode *p_editor, AnimationPlay play_from->set_tooltip(TTR("Play selected animation from current pos. (D)")); hb->add_child(play_from); - //pause = memnew( Button ); - //pause->set_toggle_mode(true); - //hb->add_child(pause); - frame = memnew(SpinBox); hb->add_child(frame); frame->set_custom_minimum_size(Size2(60, 0)); @@ -1669,7 +1670,6 @@ AnimationPlayerEditor::AnimationPlayerEditor(EditorNode *p_editor, AnimationPlay tool_anim = memnew(MenuButton); tool_anim->set_flat(false); - //tool_anim->set_flat(false); tool_anim->set_tooltip(TTR("Animation Tools")); tool_anim->set_text(TTR("Animation")); tool_anim->get_popup()->add_shortcut(ED_SHORTCUT("animation_player_editor/new_animation", TTR("New")), TOOL_NEW_ANIM); @@ -1700,9 +1700,6 @@ AnimationPlayerEditor::AnimationPlayerEditor(EditorNode *p_editor, AnimationPlay hb->add_child(autoplay); autoplay->set_tooltip(TTR("Autoplay on Load")); - //tool_anim->get_popup()->add_separator(); - //tool_anim->get_popup()->add_item("Edit Anim Resource",TOOL_PASTE_ANIM); - hb->add_child(memnew(VSeparator)); track_editor = memnew(AnimationTrackEditor); @@ -1752,10 +1749,8 @@ AnimationPlayerEditor::AnimationPlayerEditor(EditorNode *p_editor, AnimationPlay VBoxContainer *vb = memnew(VBoxContainer); name_dialog->add_child(vb); - l = memnew(Label); - l->set_text(TTR("Animation Name:")); - vb->add_child(l); - name_title = l; + name_title = memnew(Label(TTR("Animation Name:"))); + vb->add_child(name_title); name = memnew(LineEdit); vb->add_child(name); @@ -1774,7 +1769,6 @@ AnimationPlayerEditor::AnimationPlayerEditor(EditorNode *p_editor, AnimationPlay blend_editor.dialog->set_hide_on_ok(true); VBoxContainer *blend_vb = memnew(VBoxContainer); blend_editor.dialog->add_child(blend_vb); - //blend_editor.dialog->set_child_rect(blend_vb); blend_editor.tree = memnew(Tree); blend_editor.tree->set_columns(2); blend_vb->add_margin_child(TTR("Blend Times:"), blend_editor.tree, true); @@ -1792,8 +1786,6 @@ AnimationPlayerEditor::AnimationPlayerEditor(EditorNode *p_editor, AnimationPlay play_bw->connect("pressed", this, "_play_bw_pressed"); play_bw_from->connect("pressed", this, "_play_bw_from_pressed"); stop->connect("pressed", this, "_stop_pressed"); - //pause->connect("pressed", this,"_pause_pressed"); - //frame->connect("text_entered", this,"_seek_frame_changed"); animation->connect("item_selected", this, "_animation_selected", Vector<Variant>(), true); @@ -1809,7 +1801,6 @@ AnimationPlayerEditor::AnimationPlayerEditor(EditorNode *p_editor, AnimationPlay add_child(track_editor); track_editor->set_v_size_flags(SIZE_EXPAND_FILL); track_editor->connect("timeline_changed", this, "_animation_key_editor_seek"); - track_editor->connect("animation_len_changed", this, "_animation_key_editor_anim_len_changed"); track_editor->connect("animation_step_changed", this, "_animation_key_editor_anim_step_changed"); _update_player(); @@ -1883,6 +1874,8 @@ void AnimationPlayerEditorPlugin::edit(Object *p_object) { if (!p_object) return; anim_editor->edit(Object::cast_to<AnimationPlayer>(p_object)); + // In case switching to a scene with an AnimationPlayer selected but with the animation editor closed. + button->set_pressed(true); } bool AnimationPlayerEditorPlugin::handles(Object *p_object) const { @@ -1897,11 +1890,6 @@ void AnimationPlayerEditorPlugin::make_visible(bool p_visible) { editor->make_bottom_panel_item_visible(anim_editor); anim_editor->set_process(true); anim_editor->ensure_visibility(); - //editor->animation_panel_make_visible(true); - } else { - - //anim_editor->hide(); - //anim_editor->set_idle_process(false); } } @@ -1910,16 +1898,7 @@ AnimationPlayerEditorPlugin::AnimationPlayerEditorPlugin(EditorNode *p_node) { editor = p_node; anim_editor = memnew(AnimationPlayerEditor(editor, this)); anim_editor->set_undo_redo(editor->get_undo_redo()); - - editor->add_bottom_panel_item(TTR("Animation"), anim_editor); - /* - editor->get_viewport()->add_child(anim_editor); - anim_editor->set_anchors_and_margins_preset(Control::PRESET_WIDE); - anim_editor->set_anchor( MARGIN_TOP, Control::ANCHOR_END); - anim_editor->set_margin( MARGIN_TOP, 75 ); - anim_editor->set_anchor( MARGIN_RIGHT, Control::ANCHOR_END); - anim_editor->set_margin( MARGIN_RIGHT, 0 );*/ - anim_editor->hide(); + button = editor->add_bottom_panel_item(TTR("Animation"), anim_editor); } AnimationPlayerEditorPlugin::~AnimationPlayerEditorPlugin() { diff --git a/editor/plugins/animation_player_editor_plugin.h b/editor/plugins/animation_player_editor_plugin.h index c6ab6c5e30..9b72ebac7e 100644 --- a/editor/plugins/animation_player_editor_plugin.h +++ b/editor/plugins/animation_player_editor_plugin.h @@ -97,8 +97,6 @@ class AnimationPlayerEditor : public VBoxContainer { Button *play_from; Button *play_bw; Button *play_bw_from; - - //Button *pause; Button *autoplay; MenuButton *tool_anim; @@ -173,7 +171,9 @@ class AnimationPlayerEditor : public VBoxContainer { void _autoplay_pressed(); void _stop_pressed(); void _pause_pressed(); + String _get_current_animation() const; void _animation_selected(int p_which); + void _current_animation_updated(); void _animation_new(); void _animation_rename(); void _animation_name_edited(); @@ -229,7 +229,6 @@ class AnimationPlayerEditor : public VBoxContainer { protected: void _notification(int p_what); - void _gui_input(Ref<InputEvent> p_event); void _node_removed(Node *p_node); static void _bind_methods(); @@ -258,6 +257,7 @@ class AnimationPlayerEditorPlugin : public EditorPlugin { AnimationPlayerEditor *anim_editor; EditorNode *editor; + Button *button; protected: void _notification(int p_what); diff --git a/editor/plugins/canvas_item_editor_plugin.cpp b/editor/plugins/canvas_item_editor_plugin.cpp index 126cd20c53..92cc12d931 100644 --- a/editor/plugins/canvas_item_editor_plugin.cpp +++ b/editor/plugins/canvas_item_editor_plugin.cpp @@ -4009,6 +4009,7 @@ void CanvasItemEditor::_popup_callback(int p_op) { show_rulers = !show_rulers; int idx = view_menu->get_popup()->get_item_index(SHOW_RULERS); view_menu->get_popup()->set_item_checked(idx, show_rulers); + _update_scrollbars(); viewport->update(); } break; case SHOW_GUIDES: { @@ -4321,6 +4322,7 @@ void CanvasItemEditor::_popup_callback(int p_op) { Map<Node *, Object *> &selection = editor_selection->get_selection(); + undo_redo->create_action(TTR("Create Custom Bone(s) from Node(s)")); for (Map<Node *, Object *>::Element *E = selection.front(); E; E = E->next()) { Node2D *n2d = Object::cast_to<Node2D>(E->key()); @@ -4330,19 +4332,24 @@ void CanvasItemEditor::_popup_callback(int p_op) { continue; if (!n2d->get_parent_item()) continue; + if (n2d->has_meta("_edit_bone_") && (bool)n2d->get_meta("_edit_bone_") == true) + continue; - n2d->set_meta("_edit_bone_", true); - if (!skeleton_show_bones) - skeleton_menu->get_popup()->activate_item(skeleton_menu->get_popup()->get_item_index(SKELETON_SHOW_BONES)); + undo_redo->add_do_method(n2d, "set_meta", "_edit_bone_", true); + undo_redo->add_undo_method(n2d, "remove_meta", "_edit_bone_"); } - _queue_update_bone_list(); - viewport->update(); + undo_redo->add_do_method(this, "_queue_update_bone_list"); + undo_redo->add_undo_method(this, "_queue_update_bone_list"); + undo_redo->add_do_method(viewport, "update"); + undo_redo->add_undo_method(viewport, "update"); + undo_redo->commit_action(); } break; case SKELETON_CLEAR_BONES: { Map<Node *, Object *> &selection = editor_selection->get_selection(); + undo_redo->create_action(TTR("Clear Bones")); for (Map<Node *, Object *>::Element *E = selection.front(); E; E = E->next()) { Node2D *n2d = Object::cast_to<Node2D>(E->key()); @@ -4350,40 +4357,47 @@ void CanvasItemEditor::_popup_callback(int p_op) { continue; if (!n2d->is_visible_in_tree()) continue; + if (!n2d->has_meta("_edit_bone_")) + continue; - n2d->set_meta("_edit_bone_", Variant()); - if (!skeleton_show_bones) - skeleton_menu->get_popup()->activate_item(skeleton_menu->get_popup()->get_item_index(SKELETON_SHOW_BONES)); + undo_redo->add_do_method(n2d, "remove_meta", "_edit_bone_"); + undo_redo->add_undo_method(n2d, "set_meta", "_edit_bone_", n2d->get_meta("_edit_bone_")); } - _queue_update_bone_list(); - viewport->update(); + undo_redo->add_do_method(this, "_queue_update_bone_list"); + undo_redo->add_undo_method(this, "_queue_update_bone_list"); + undo_redo->add_do_method(viewport, "update"); + undo_redo->add_undo_method(viewport, "update"); + undo_redo->commit_action(); } break; case SKELETON_SET_IK_CHAIN: { List<Node *> selection = editor_selection->get_selected_node_list(); + undo_redo->create_action(TTR("Make IK Chain")); for (List<Node *>::Element *E = selection.front(); E; E = E->next()) { CanvasItem *canvas_item = Object::cast_to<CanvasItem>(E->get()); if (!canvas_item || !canvas_item->is_visible_in_tree()) continue; - if (canvas_item->get_viewport() != EditorNode::get_singleton()->get_scene_root()) continue; + if (canvas_item->has_meta("_edit_ik_") && (bool)canvas_item->get_meta("_edit_ik_") == true) + continue; - canvas_item->set_meta("_edit_ik_", true); - if (!skeleton_show_bones) - skeleton_menu->get_popup()->activate_item(skeleton_menu->get_popup()->get_item_index(SKELETON_SHOW_BONES)); + undo_redo->add_do_method(canvas_item, "set_meta", "_edit_ik_", true); + undo_redo->add_undo_method(canvas_item, "remove_meta", "_edit_ik_"); } - - viewport->update(); + undo_redo->add_do_method(viewport, "update"); + undo_redo->add_undo_method(viewport, "update"); + undo_redo->commit_action(); } break; case SKELETON_CLEAR_IK_CHAIN: { Map<Node *, Object *> &selection = editor_selection->get_selection(); + undo_redo->create_action(TTR("Clear IK Chain")); for (Map<Node *, Object *>::Element *E = selection.front(); E; E = E->next()) { CanvasItem *n2d = Object::cast_to<CanvasItem>(E->key()); @@ -4391,12 +4405,15 @@ void CanvasItemEditor::_popup_callback(int p_op) { continue; if (!n2d->is_visible_in_tree()) continue; + if (!n2d->has_meta("_edit_ik_")) + continue; - n2d->set_meta("_edit_ik_", Variant()); - if (!skeleton_show_bones) - skeleton_menu->get_popup()->activate_item(skeleton_menu->get_popup()->get_item_index(SKELETON_SHOW_BONES)); + undo_redo->add_do_method(n2d, "remove_meta", "_edit_ik_"); + undo_redo->add_undo_method(n2d, "set_meta", "_edit_ik_", n2d->get_meta("_edit_ik_")); } - viewport->update(); + undo_redo->add_do_method(viewport, "update"); + undo_redo->add_undo_method(viewport, "update"); + undo_redo->commit_action(); } break; } @@ -4478,6 +4495,7 @@ void CanvasItemEditor::_bind_methods() { ClassDB::bind_method("_draw_viewport", &CanvasItemEditor::_draw_viewport); ClassDB::bind_method("_gui_input_viewport", &CanvasItemEditor::_gui_input_viewport); ClassDB::bind_method("_snap_changed", &CanvasItemEditor::_snap_changed); + ClassDB::bind_method("_queue_update_bone_list", &CanvasItemEditor::_update_bone_list); ClassDB::bind_method("_update_bone_list", &CanvasItemEditor::_update_bone_list); ClassDB::bind_method("_tree_changed", &CanvasItemEditor::_tree_changed); ClassDB::bind_method("_selection_changed", &CanvasItemEditor::_selection_changed); @@ -4514,6 +4532,7 @@ Dictionary CanvasItemEditor::get_state() const { state["show_rulers"] = show_rulers; state["show_guides"] = show_guides; state["show_helpers"] = show_helpers; + state["show_zoom_control"] = zoom_hb->is_visible(); state["show_edit_locks"] = show_edit_locks; state["snap_rotation"] = snap_rotation; state["snap_relative"] = snap_relative; @@ -4524,6 +4543,7 @@ Dictionary CanvasItemEditor::get_state() const { void CanvasItemEditor::set_state(const Dictionary &p_state) { + bool update_scrollbars = false; Dictionary state = p_state; if (state.has("zoom")) { zoom = p_state["zoom"]; @@ -4532,7 +4552,7 @@ void CanvasItemEditor::set_state(const Dictionary &p_state) { if (state.has("ofs")) { view_offset = p_state["ofs"]; previous_update_view_offset = view_offset; - _update_scrollbars(); + update_scrollbars = true; } if (state.has("grid_offset")) { @@ -4620,6 +4640,7 @@ void CanvasItemEditor::set_state(const Dictionary &p_state) { show_rulers = state["show_rulers"]; int idx = view_menu->get_popup()->get_item_index(SHOW_RULERS); view_menu->get_popup()->set_item_checked(idx, show_rulers); + update_scrollbars = true; } if (state.has("show_guides")) { @@ -4640,6 +4661,11 @@ void CanvasItemEditor::set_state(const Dictionary &p_state) { view_menu->get_popup()->set_item_checked(idx, show_edit_locks); } + if (state.has("show_zoom_control")) { + // This one is not user-controllable, but instrumentable + zoom_hb->set_visible(state["show_zoom_control"]); + } + if (state.has("snap_rotation")) { snap_rotation = state["snap_rotation"]; int idx = snap_config_menu->get_popup()->get_item_index(SNAP_USE_ROTATION); @@ -4664,6 +4690,9 @@ void CanvasItemEditor::set_state(const Dictionary &p_state) { skeleton_menu->get_popup()->set_item_checked(idx, skeleton_show_bones); } + if (update_scrollbars) { + _update_scrollbars(); + } viewport->update(); } diff --git a/editor/plugins/editor_preview_plugins.cpp b/editor/plugins/editor_preview_plugins.cpp index 58d7968723..28e57ac48a 100644 --- a/editor/plugins/editor_preview_plugins.cpp +++ b/editor/plugins/editor_preview_plugins.cpp @@ -78,7 +78,7 @@ bool EditorTexturePreviewPlugin::handles(const String &p_type) const { return ClassDB::is_parent_class(p_type, "Texture"); } -bool EditorTexturePreviewPlugin::should_generate_small_preview() const { +bool EditorTexturePreviewPlugin::generate_small_preview_automatically() const { return true; } @@ -186,7 +186,7 @@ Ref<Texture> EditorImagePreviewPlugin::generate(const RES &p_from, const Size2 p EditorImagePreviewPlugin::EditorImagePreviewPlugin() { } -bool EditorImagePreviewPlugin::should_generate_small_preview() const { +bool EditorImagePreviewPlugin::generate_small_preview_automatically() const { return true; } //////////////////////////////////////////////////////////////////////////// @@ -250,7 +250,7 @@ Ref<Texture> EditorBitmapPreviewPlugin::generate(const RES &p_from, const Size2 return ptex; } -bool EditorBitmapPreviewPlugin::should_generate_small_preview() const { +bool EditorBitmapPreviewPlugin::generate_small_preview_automatically() const { return true; } @@ -317,7 +317,7 @@ bool EditorMaterialPreviewPlugin::handles(const String &p_type) const { return ClassDB::is_parent_class(p_type, "Material"); //any material } -bool EditorMaterialPreviewPlugin::should_generate_small_preview() const { +bool EditorMaterialPreviewPlugin::generate_small_preview_automatically() const { return true; } diff --git a/editor/plugins/editor_preview_plugins.h b/editor/plugins/editor_preview_plugins.h index ed2c003a0a..16b1f3082b 100644 --- a/editor/plugins/editor_preview_plugins.h +++ b/editor/plugins/editor_preview_plugins.h @@ -39,7 +39,7 @@ class EditorTexturePreviewPlugin : public EditorResourcePreviewGenerator { GDCLASS(EditorTexturePreviewPlugin, EditorResourcePreviewGenerator) public: virtual bool handles(const String &p_type) const; - virtual bool should_generate_small_preview() const; + virtual bool generate_small_preview_automatically() const; virtual Ref<Texture> generate(const RES &p_from, const Size2 p_size) const; EditorTexturePreviewPlugin(); @@ -49,7 +49,7 @@ class EditorImagePreviewPlugin : public EditorResourcePreviewGenerator { GDCLASS(EditorImagePreviewPlugin, EditorResourcePreviewGenerator) public: virtual bool handles(const String &p_type) const; - virtual bool should_generate_small_preview() const; + virtual bool generate_small_preview_automatically() const; virtual Ref<Texture> generate(const RES &p_from, const Size2 p_size) const; EditorImagePreviewPlugin(); @@ -59,7 +59,7 @@ class EditorBitmapPreviewPlugin : public EditorResourcePreviewGenerator { GDCLASS(EditorBitmapPreviewPlugin, EditorResourcePreviewGenerator) public: virtual bool handles(const String &p_type) const; - virtual bool should_generate_small_preview() const; + virtual bool generate_small_preview_automatically() const; virtual Ref<Texture> generate(const RES &p_from, const Size2 p_size) const; EditorBitmapPreviewPlugin(); @@ -98,7 +98,7 @@ protected: public: virtual bool handles(const String &p_type) const; - virtual bool should_generate_small_preview() const; + virtual bool generate_small_preview_automatically() const; virtual Ref<Texture> generate(const RES &p_from, const Size2 p_size) const; EditorMaterialPreviewPlugin(); diff --git a/editor/plugins/script_editor_plugin.cpp b/editor/plugins/script_editor_plugin.cpp index 828abef9a9..38985a2b2c 100644 --- a/editor/plugins/script_editor_plugin.cpp +++ b/editor/plugins/script_editor_plugin.cpp @@ -1558,7 +1558,15 @@ struct _ScriptEditorItemData { bool operator<(const _ScriptEditorItemData &id) const { - return category == id.category ? sort_key < id.sort_key : category < id.category; + if (category == id.category) { + if (sort_key == id.sort_key) { + return index < id.index; + } else { + return sort_key < id.sort_key; + } + } else { + return category < id.category; + } } }; diff --git a/editor/plugins/script_text_editor.cpp b/editor/plugins/script_text_editor.cpp index ff0959c8a1..f66ae0465f 100644 --- a/editor/plugins/script_text_editor.cpp +++ b/editor/plugins/script_text_editor.cpp @@ -1772,7 +1772,7 @@ void ScriptTextEditor::register_editor() { #ifdef OSX_ENABLED ED_SHORTCUT("script_text_editor/contextual_help", TTR("Contextual Help"), KEY_MASK_ALT | KEY_MASK_SHIFT | KEY_SPACE); #else - ED_SHORTCUT("script_text_editor/contextual_help", TTR("Contextual Help"), KEY_MASK_SHIFT | KEY_F1); + ED_SHORTCUT("script_text_editor/contextual_help", TTR("Contextual Help"), KEY_MASK_ALT | KEY_F1); #endif ScriptEditor::register_create_script_editor_function(create_editor); diff --git a/editor/plugins/spatial_editor_plugin.cpp b/editor/plugins/spatial_editor_plugin.cpp index 95a70f2ae5..60f1248ace 100644 --- a/editor/plugins/spatial_editor_plugin.cpp +++ b/editor/plugins/spatial_editor_plugin.cpp @@ -3510,10 +3510,14 @@ SpatialEditorViewport::SpatialEditorViewport(SpatialEditor *p_spatial_editor, Ed camera->make_current(); surface->set_focus_mode(FOCUS_ALL); + VBoxContainer *vbox = memnew(VBoxContainer); + surface->add_child(vbox); + vbox->set_position(Point2(10, 10) * EDSCALE); + view_menu = memnew(MenuButton); view_menu->set_flat(false); - surface->add_child(view_menu); - view_menu->set_position(Point2(10, 10) * EDSCALE); + vbox->add_child(view_menu); + view_menu->set_h_size_flags(0); view_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("spatial_editor/top_view"), VIEW_TOP); view_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("spatial_editor/bottom_view"), VIEW_BOTTOM); @@ -3566,9 +3570,9 @@ SpatialEditorViewport::SpatialEditorViewport(SpatialEditor *p_spatial_editor, Ed ED_SHORTCUT("spatial_editor/freelook_speed_modifier", TTR("Freelook Speed Modifier"), KEY_SHIFT); preview_camera = memnew(CheckBox); - preview_camera->set_position(Point2(10, 38) * EDSCALE); // Below the 'view_menu' MenuButton. preview_camera->set_text(TTR("Preview")); - surface->add_child(preview_camera); + vbox->add_child(preview_camera); + preview_camera->set_h_size_flags(0); preview_camera->hide(); preview_camera->connect("toggled", this, "_toggle_camera_preview"); previewing = NULL; diff --git a/editor/plugins/theme_editor_plugin.cpp b/editor/plugins/theme_editor_plugin.cpp index 672d5d3496..5b67d259ba 100644 --- a/editor/plugins/theme_editor_plugin.cpp +++ b/editor/plugins/theme_editor_plugin.cpp @@ -879,11 +879,9 @@ ThemeEditor::ThemeEditor() { void ThemeEditorPlugin::edit(Object *p_node) { if (Object::cast_to<Theme>(p_node)) { - theme_editor->show(); theme_editor->edit(Object::cast_to<Theme>(p_node)); } else { theme_editor->edit(Ref<Theme>()); - theme_editor->hide(); } } @@ -898,11 +896,11 @@ void ThemeEditorPlugin::make_visible(bool p_visible) { theme_editor->set_process(true); button->show(); editor->make_bottom_panel_item_visible(theme_editor); - } else { theme_editor->set_process(false); if (theme_editor->is_visible_in_tree()) editor->hide_bottom_panel(); + button->hide(); } } diff --git a/editor/plugins/visual_shader_editor_plugin.cpp b/editor/plugins/visual_shader_editor_plugin.cpp index 31f5d337a7..2c68633a3c 100644 --- a/editor/plugins/visual_shader_editor_plugin.cpp +++ b/editor/plugins/visual_shader_editor_plugin.cpp @@ -701,7 +701,7 @@ void VisualShaderEditor::_update_graph() { expression_box->set_context_menu_enabled(false); expression_box->set_show_line_numbers(true); - expression_box->connect("text_changed", this, "_set_expression", varray(nodes[n_i]), CONNECT_DEFERRED); + expression_box->connect("focus_exited", this, "_expression_focus_out", varray(expression_box, nodes[n_i])); } if (!uniform.is_valid()) { @@ -915,7 +915,7 @@ void VisualShaderEditor::_remove_output_port(int p_node, int p_port) { undo_redo->commit_action(); } -void VisualShaderEditor::_set_expression(int p_node) { +void VisualShaderEditor::_expression_focus_out(Object *text_edit, int p_node) { VisualShader::Type type = VisualShader::Type(edit_type->get_selected()); Ref<VisualShaderNodeExpression> node = visual_shader->get_node(type, p_node); @@ -923,24 +923,19 @@ void VisualShaderEditor::_set_expression(int p_node) { return; } - TextEdit *expression_box = Object::cast_to<TextEdit>(node->get_control(0)); + TextEdit *expression_box = Object::cast_to<TextEdit>(text_edit); + + if (node->get_expression() == expression_box->get_text()) + return; undo_redo->create_action(TTR("Set expression")); undo_redo->add_do_method(node.ptr(), "set_expression", expression_box->get_text()); undo_redo->add_undo_method(node.ptr(), "set_expression", node->get_expression()); - undo_redo->add_do_method(this, "_start_rebuild_timer", 1.0); + undo_redo->add_do_method(this, "_rebuild"); undo_redo->add_undo_method(this, "_rebuild"); undo_redo->commit_action(); } -void VisualShaderEditor::_start_rebuild_timer(int p_delay) { - build_timer->start(p_delay); -} - -void VisualShaderEditor::_rebuild_timeout() { - _rebuild(); -} - void VisualShaderEditor::_rebuild() { EditorNode::get_singleton()->get_log()->clear(); visual_shader->rebuild(); @@ -1797,9 +1792,7 @@ void VisualShaderEditor::_bind_methods() { ClassDB::bind_method("_rebuild", &VisualShaderEditor::_rebuild); ClassDB::bind_method("_update_graph", &VisualShaderEditor::_update_graph); ClassDB::bind_method("_update_options_menu", &VisualShaderEditor::_update_options_menu); - ClassDB::bind_method("_start_rebuild_timer", &VisualShaderEditor::_start_rebuild_timer); - ClassDB::bind_method("_set_expression", &VisualShaderEditor::_set_expression); - ClassDB::bind_method("_rebuild_timeout", &VisualShaderEditor::_rebuild_timeout); + ClassDB::bind_method("_expression_focus_out", &VisualShaderEditor::_expression_focus_out); ClassDB::bind_method("_add_node", &VisualShaderEditor::_add_node); ClassDB::bind_method("_node_dragged", &VisualShaderEditor::_node_dragged); ClassDB::bind_method("_connection_request", &VisualShaderEditor::_connection_request); @@ -2287,13 +2280,6 @@ VisualShaderEditor::VisualShaderEditor() { add_child(property_editor); property_editor->connect("variant_changed", this, "_port_edited"); - - // BUILD TIMER FOR EXPRESSION NODES - - build_timer = memnew(Timer); - add_child(build_timer); - build_timer->connect("timeout", this, "_rebuild_timeout"); - build_timer->set_one_shot(true); } void VisualShaderEditorPlugin::edit(Object *p_object) { diff --git a/editor/plugins/visual_shader_editor_plugin.h b/editor/plugins/visual_shader_editor_plugin.h index b1cf2e7244..e851030ab4 100644 --- a/editor/plugins/visual_shader_editor_plugin.h +++ b/editor/plugins/visual_shader_editor_plugin.h @@ -84,8 +84,6 @@ class VisualShaderEditor : public VBoxContainer { LineEdit *node_filter; RichTextLabel *node_desc; - Timer *build_timer; - void _tools_menu_option(int p_idx); void _show_members_dialog(bool at_mouse_pos); @@ -184,10 +182,7 @@ class VisualShaderEditor : public VBoxContainer { void _change_output_port_type(int p_type, int p_node, int p_port); void _change_output_port_name(const String &p_text, Object *line_edit, int p_node, int p_port); - void _start_rebuild_timer(int p_delay); - - void _set_expression(int p_node); - void _rebuild_timeout(); + void _expression_focus_out(Object *text_edit, int p_node); void _set_node_size(int p_type, int p_node, const Size2 &p_size); void _node_resized(const Vector2 &p_new_size, int p_type, int p_node); diff --git a/editor/project_export.cpp b/editor/project_export.cpp index e1950c666c..cc110f309c 100644 --- a/editor/project_export.cpp +++ b/editor/project_export.cpp @@ -571,9 +571,8 @@ void ProjectExportDialog::_duplicate_preset() { Ref<EditorExportPreset> preset = current->get_platform()->create_preset(); ERR_FAIL_COND(!preset.is_valid()); - String name = current->get_name() + "" + itos(1); + String name = current->get_name() + " (copy)"; bool make_runnable = true; - int attempt = 2; while (true) { bool valid = true; @@ -592,8 +591,7 @@ void ProjectExportDialog::_duplicate_preset() { if (valid) break; - attempt++; - name = current->get_name() + " " + itos(attempt); + name += " (copy)"; } preset->set_name(name); diff --git a/editor/project_manager.cpp b/editor/project_manager.cpp index 6de4330493..b0baf954d2 100644 --- a/editor/project_manager.cpp +++ b/editor/project_manager.cpp @@ -1627,40 +1627,28 @@ void ProjectManager::_show_project(const String &p_path) { OS::get_singleton()->shell_open(String("file://") + p_path); } -void ProjectManager::_scan_dir(DirAccess *da, float pos, float total, List<String> *r_projects) { - - List<String> subdirs; +void ProjectManager::_scan_dir(const String &path, List<String> *r_projects) { + DirAccess *da = DirAccess::create(DirAccess::ACCESS_FILESYSTEM); + da->change_dir(path); da->list_dir_begin(); String n = da->get_next(); while (n != String()) { if (da->current_is_dir() && !n.begins_with(".")) { - subdirs.push_front(n); + _scan_dir(da->get_current_dir().plus_file(n), r_projects); } else if (n == "project.godot") { r_projects->push_back(da->get_current_dir()); } n = da->get_next(); } da->list_dir_end(); - int m = 0; - for (List<String>::Element *E = subdirs.front(); E; E = E->next()) { - - da->change_dir(E->get()); - - float slice = total / subdirs.size(); - _scan_dir(da, pos + slice * m, slice, r_projects); - da->change_dir(".."); - m++; - } + memdelete(da); } void ProjectManager::_scan_begin(const String &p_base) { print_line("Scanning projects at: " + p_base); List<String> projects; - DirAccess *da = DirAccess::create(DirAccess::ACCESS_FILESYSTEM); - da->change_dir(p_base); - _scan_dir(da, 0, 1, &projects); - memdelete(da); + _scan_dir(p_base, &projects); print_line("Found " + itos(projects.size()) + " projects."); for (List<String>::Element *E = projects.front(); E; E = E->next()) { @@ -2166,6 +2154,19 @@ ProjectManager::ProjectManager() { Button *cancel = memnew(Button); cancel->set_text(TTR("Exit")); cancel->set_custom_minimum_size(Size2(100, 1) * EDSCALE); + +#ifndef OSX_ENABLED + // Pressing Command + Q quits the Project Manager + // This is handled by the platform implementation on macOS, + // so only define the shortcut on other platforms + InputEventKey *quit_key = memnew(InputEventKey); + quit_key->set_command(true); + quit_key->set_scancode(KEY_Q); + ShortCut *quit_shortcut = memnew(ShortCut); + quit_shortcut->set_shortcut(quit_key); + cancel->set_shortcut(quit_shortcut); +#endif + cc->add_child(cancel); cancel->connect("pressed", this, "_exit_dialog"); vb->add_child(cc); diff --git a/editor/project_manager.h b/editor/project_manager.h index 382e9fc8fb..fa878e75a6 100644 --- a/editor/project_manager.h +++ b/editor/project_manager.h @@ -106,7 +106,7 @@ class ProjectManager : public Control { void _on_project_created(const String &dir); void _on_projects_updated(); void _update_scroll_position(const String &dir); - void _scan_dir(DirAccess *da, float pos, float total, List<String> *r_projects); + void _scan_dir(const String &path, List<String> *r_projects); void _install_project(const String &p_zip_path, const String &p_title); diff --git a/editor/scene_tree_editor.cpp b/editor/scene_tree_editor.cpp index 76feaedb1a..5ca3448693 100644 --- a/editor/scene_tree_editor.cpp +++ b/editor/scene_tree_editor.cpp @@ -379,6 +379,12 @@ bool SceneTreeEditor::_add_nodes(Node *p_node, TreeItem *p_parent) { } if (!keep) { + if (editor_selection) { + Node *n = get_node(item->get_metadata(0)); + if (n) { + editor_selection->remove_node(n); + } + } memdelete(item); return false; } else { @@ -471,6 +477,17 @@ void SceneTreeEditor::_node_removed(Node *p_node) { emit_signal("node_selected"); } } + +void SceneTreeEditor::_node_renamed(Node *p_node) { + + emit_signal("node_renamed"); + + if (!tree_dirty) { + MessageQueue::get_singleton()->push_call(this, "_update_tree"); + tree_dirty = true; + } +} + void SceneTreeEditor::_update_tree() { if (!is_inside_tree()) { @@ -594,6 +611,7 @@ void SceneTreeEditor::_notification(int p_what) { get_tree()->connect("tree_changed", this, "_tree_changed"); get_tree()->connect("node_removed", this, "_node_removed"); + get_tree()->connect("node_renamed", this, "_node_renamed"); get_tree()->connect("node_configuration_warning_changed", this, "_warning_changed"); tree->connect("item_collapsed", this, "_cell_collapsed"); @@ -604,6 +622,7 @@ void SceneTreeEditor::_notification(int p_what) { get_tree()->disconnect("tree_changed", this, "_tree_changed"); get_tree()->disconnect("node_removed", this, "_node_removed"); + get_tree()->disconnect("node_renamed", this, "_node_renamed"); tree->disconnect("item_collapsed", this, "_cell_collapsed"); get_tree()->disconnect("node_configuration_warning_changed", this, "_warning_changed"); } break; @@ -685,12 +704,6 @@ void SceneTreeEditor::_rename_node(ObjectID p_node, const String &p_name) { n->set_name(p_name); item->set_metadata(0, n->get_path()); item->set_text(0, p_name); - emit_signal("node_renamed"); - - if (!tree_dirty) { - MessageQueue::get_singleton()->push_call(this, "_update_tree"); - tree_dirty = true; - } } void SceneTreeEditor::_renamed() { @@ -1025,6 +1038,7 @@ void SceneTreeEditor::_bind_methods() { ClassDB::bind_method("_tree_changed", &SceneTreeEditor::_tree_changed); ClassDB::bind_method("_update_tree", &SceneTreeEditor::_update_tree); ClassDB::bind_method("_node_removed", &SceneTreeEditor::_node_removed); + ClassDB::bind_method("_node_renamed", &SceneTreeEditor::_node_renamed); ClassDB::bind_method("_selected_changed", &SceneTreeEditor::_selected_changed); ClassDB::bind_method("_deselect_items", &SceneTreeEditor::_deselect_items); ClassDB::bind_method("_renamed", &SceneTreeEditor::_renamed); diff --git a/editor/scene_tree_editor.h b/editor/scene_tree_editor.h index 9158c4aa48..1c14da0d3a 100644 --- a/editor/scene_tree_editor.h +++ b/editor/scene_tree_editor.h @@ -78,6 +78,7 @@ class SceneTreeEditor : public Control { void _update_tree(); void _tree_changed(); void _node_removed(Node *p_node); + void _node_renamed(Node *p_node); TreeItem *_find(TreeItem *p_node, const NodePath &p_path); void _notification(int p_what); |