mirror of
https://github.com/godotengine/godot.git
synced 2025-10-19 16:03:29 +00:00
Optimized ScriptEditor initialization when many scripts are loaded
This change avoids the editor to freeze for several seconds when a project with lots of scripts is loaded in the editor. It focuses on a few heavy operations previously executed on all previously loaded scripts: - Initialize script resource (script validation/parsing) only on focus - ScriptTextEditor: code editor and edit menu are added to the scene only on focus - Add to recent scripts only when opening new scripts (load/save scene metadata)
This commit is contained in:
parent
1ceb3d99a9
commit
ccff2f2551
9 changed files with 242 additions and 162 deletions
|
@ -140,10 +140,10 @@ RES ScriptTextEditor::get_edited_resource() const {
|
|||
}
|
||||
|
||||
void ScriptTextEditor::set_edited_resource(const RES &p_res) {
|
||||
ERR_FAIL_COND(!script.is_null());
|
||||
ERR_FAIL_COND(script.is_valid());
|
||||
ERR_FAIL_COND(p_res.is_null());
|
||||
|
||||
script = p_res;
|
||||
_set_theme_for_script();
|
||||
|
||||
code_editor->get_text_edit()->set_text(script->get_source_code());
|
||||
code_editor->get_text_edit()->clear_undo_history();
|
||||
|
@ -151,6 +151,17 @@ void ScriptTextEditor::set_edited_resource(const RES &p_res) {
|
|||
|
||||
emit_signal("name_changed");
|
||||
code_editor->update_line_and_column();
|
||||
}
|
||||
|
||||
void ScriptTextEditor::enable_editor() {
|
||||
if (editor_enabled) {
|
||||
return;
|
||||
}
|
||||
|
||||
editor_enabled = true;
|
||||
|
||||
_enable_code_editor();
|
||||
_set_theme_for_script();
|
||||
|
||||
_validate_script();
|
||||
}
|
||||
|
@ -301,14 +312,6 @@ void ScriptTextEditor::reload_text() {
|
|||
code_editor->update_line_and_column();
|
||||
}
|
||||
|
||||
void ScriptTextEditor::_notification(int p_what) {
|
||||
switch (p_what) {
|
||||
case NOTIFICATION_READY:
|
||||
_load_theme_settings();
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void ScriptTextEditor::add_callback(const String &p_function, PackedStringArray p_args) {
|
||||
String code = code_editor->get_text_edit()->get_text();
|
||||
int pos = script->get_language()->find_function(p_function, code);
|
||||
|
@ -352,6 +355,10 @@ void ScriptTextEditor::set_edit_state(const Variant &p_state) {
|
|||
_change_syntax_highlighter(idx);
|
||||
}
|
||||
}
|
||||
|
||||
if (editor_enabled) {
|
||||
ensure_focus();
|
||||
}
|
||||
}
|
||||
|
||||
void ScriptTextEditor::_convert_case(CodeTextEditor::CaseStyle p_case) {
|
||||
|
@ -1274,23 +1281,28 @@ void ScriptTextEditor::_edit_option_toggle_inline_comment() {
|
|||
}
|
||||
|
||||
void ScriptTextEditor::add_syntax_highlighter(Ref<EditorSyntaxHighlighter> p_highlighter) {
|
||||
ERR_FAIL_COND(p_highlighter.is_null());
|
||||
|
||||
highlighters[p_highlighter->_get_name()] = p_highlighter;
|
||||
highlighter_menu->add_radio_check_item(p_highlighter->_get_name());
|
||||
}
|
||||
|
||||
void ScriptTextEditor::set_syntax_highlighter(Ref<EditorSyntaxHighlighter> p_highlighter) {
|
||||
ERR_FAIL_COND(p_highlighter.is_null());
|
||||
|
||||
Map<String, Ref<EditorSyntaxHighlighter>>::Element *el = highlighters.front();
|
||||
while (el != nullptr) {
|
||||
int highlighter_index = highlighter_menu->get_item_idx_from_text(el->key());
|
||||
highlighter_menu->set_item_checked(highlighter_index, el->value() == p_highlighter);
|
||||
el = el->next();
|
||||
}
|
||||
|
||||
TextEdit *te = code_editor->get_text_edit();
|
||||
p_highlighter->_set_edited_resource(script);
|
||||
te->set_syntax_highlighter(p_highlighter);
|
||||
highlighter_menu->set_item_checked(highlighter_menu->get_item_idx_from_text(p_highlighter->_get_name()), true);
|
||||
}
|
||||
|
||||
void ScriptTextEditor::_change_syntax_highlighter(int p_idx) {
|
||||
Map<String, Ref<EditorSyntaxHighlighter>>::Element *el = highlighters.front();
|
||||
while (el != nullptr) {
|
||||
highlighter_menu->set_item_checked(highlighter_menu->get_item_idx_from_text(el->key()), false);
|
||||
el = el->next();
|
||||
}
|
||||
set_syntax_highlighter(highlighters[highlighter_menu->get_item_text(p_idx)]);
|
||||
}
|
||||
|
||||
|
@ -1606,64 +1618,40 @@ void ScriptTextEditor::_make_context_menu(bool p_selection, bool p_color, bool p
|
|||
context_menu->popup();
|
||||
}
|
||||
|
||||
ScriptTextEditor::ScriptTextEditor() {
|
||||
theme_loaded = false;
|
||||
script_is_valid = false;
|
||||
void ScriptTextEditor::_enable_code_editor() {
|
||||
ERR_FAIL_COND(code_editor->get_parent());
|
||||
|
||||
VSplitContainer *editor_box = memnew(VSplitContainer);
|
||||
add_child(editor_box);
|
||||
editor_box->set_anchors_and_margins_preset(Control::PRESET_WIDE);
|
||||
editor_box->set_v_size_flags(SIZE_EXPAND_FILL);
|
||||
|
||||
code_editor = memnew(CodeTextEditor);
|
||||
editor_box->add_child(code_editor);
|
||||
code_editor->add_theme_constant_override("separation", 2);
|
||||
code_editor->set_anchors_and_margins_preset(Control::PRESET_WIDE);
|
||||
code_editor->connect("show_warnings_panel", callable_mp(this, &ScriptTextEditor::_show_warnings_panel));
|
||||
code_editor->connect("validate_script", callable_mp(this, &ScriptTextEditor::_validate_script));
|
||||
code_editor->connect("load_theme_settings", callable_mp(this, &ScriptTextEditor::_load_theme_settings));
|
||||
code_editor->set_code_complete_func(_code_complete_scripts, this);
|
||||
code_editor->get_text_edit()->connect("breakpoint_toggled", callable_mp(this, &ScriptTextEditor::_breakpoint_toggled));
|
||||
code_editor->get_text_edit()->connect("symbol_lookup", callable_mp(this, &ScriptTextEditor::_lookup_symbol));
|
||||
code_editor->get_text_edit()->connect("symbol_validate", callable_mp(this, &ScriptTextEditor::_validate_symbol));
|
||||
code_editor->get_text_edit()->connect("info_clicked", callable_mp(this, &ScriptTextEditor::_lookup_connections));
|
||||
code_editor->set_v_size_flags(SIZE_EXPAND_FILL);
|
||||
code_editor->get_text_edit()->connect("gui_input", callable_mp(this, &ScriptTextEditor::_text_edit_gui_input));
|
||||
code_editor->show_toggle_scripts_button();
|
||||
|
||||
warnings_panel = memnew(RichTextLabel);
|
||||
editor_box->add_child(warnings_panel);
|
||||
warnings_panel->add_theme_font_override(
|
||||
"normal_font", EditorNode::get_singleton()->get_gui_base()->get_theme_font("main", "EditorFonts"));
|
||||
warnings_panel->set_custom_minimum_size(Size2(0, 100 * EDSCALE));
|
||||
warnings_panel->set_h_size_flags(SIZE_EXPAND_FILL);
|
||||
warnings_panel->set_meta_underline(true);
|
||||
warnings_panel->set_selection_enabled(true);
|
||||
warnings_panel->set_focus_mode(FOCUS_CLICK);
|
||||
warnings_panel->hide();
|
||||
|
||||
code_editor->connect("show_warnings_panel", callable_mp(this, &ScriptTextEditor::_show_warnings_panel));
|
||||
warnings_panel->connect("meta_clicked", callable_mp(this, &ScriptTextEditor::_warning_clicked));
|
||||
|
||||
update_settings();
|
||||
|
||||
code_editor->get_text_edit()->set_callhint_settings(
|
||||
EditorSettings::get_singleton()->get("text_editor/completion/put_callhint_tooltip_below_current_line"),
|
||||
EditorSettings::get_singleton()->get("text_editor/completion/callhint_tooltip_offset"));
|
||||
|
||||
code_editor->get_text_edit()->set_select_identifiers_on_hover(true);
|
||||
code_editor->get_text_edit()->set_context_menu_enabled(false);
|
||||
code_editor->get_text_edit()->connect("gui_input", callable_mp(this, &ScriptTextEditor::_text_edit_gui_input));
|
||||
|
||||
context_menu = memnew(PopupMenu);
|
||||
add_child(context_menu);
|
||||
context_menu->connect("id_pressed", callable_mp(this, &ScriptTextEditor::_edit_option));
|
||||
|
||||
color_panel = memnew(PopupPanel);
|
||||
add_child(color_panel);
|
||||
|
||||
color_picker = memnew(ColorPicker);
|
||||
color_picker->set_deferred_mode(true);
|
||||
color_panel->add_child(color_picker);
|
||||
color_picker->connect("color_changed", callable_mp(this, &ScriptTextEditor::_color_changed));
|
||||
|
||||
color_panel->add_child(color_picker);
|
||||
|
||||
// get default color picker mode from editor settings
|
||||
int default_color_mode = EDITOR_GET("interface/inspector/default_color_picker_mode");
|
||||
if (default_color_mode == 1) {
|
||||
|
@ -1672,12 +1660,27 @@ ScriptTextEditor::ScriptTextEditor() {
|
|||
color_picker->set_raw_mode(true);
|
||||
}
|
||||
|
||||
edit_hb = memnew(HBoxContainer);
|
||||
quick_open = memnew(ScriptEditorQuickOpen);
|
||||
quick_open->connect("goto_line", callable_mp(this, &ScriptTextEditor::_goto_line));
|
||||
add_child(quick_open);
|
||||
|
||||
edit_menu = memnew(MenuButton);
|
||||
edit_menu->set_text(TTR("Edit"));
|
||||
edit_menu->set_switch_on_hover(true);
|
||||
goto_line_dialog = memnew(GotoLineDialog);
|
||||
add_child(goto_line_dialog);
|
||||
|
||||
add_child(connection_info_dialog);
|
||||
|
||||
edit_hb->add_child(search_menu);
|
||||
search_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/find"), SEARCH_FIND);
|
||||
search_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/find_next"), SEARCH_FIND_NEXT);
|
||||
search_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/find_previous"), SEARCH_FIND_PREV);
|
||||
search_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/replace"), SEARCH_REPLACE);
|
||||
search_menu->get_popup()->add_separator();
|
||||
search_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/find_in_files"), SEARCH_IN_FILES);
|
||||
search_menu->get_popup()->add_separator();
|
||||
search_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/contextual_help"), HELP_CONTEXTUAL);
|
||||
search_menu->get_popup()->connect("id_pressed", callable_mp(this, &ScriptTextEditor::_edit_option));
|
||||
|
||||
edit_hb->add_child(edit_menu);
|
||||
edit_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/undo"), EDIT_UNDO);
|
||||
edit_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/redo"), EDIT_REDO);
|
||||
edit_menu->get_popup()->add_separator();
|
||||
|
@ -1707,8 +1710,6 @@ ScriptTextEditor::ScriptTextEditor() {
|
|||
edit_menu->get_popup()->connect("id_pressed", callable_mp(this, &ScriptTextEditor::_edit_option));
|
||||
edit_menu->get_popup()->add_separator();
|
||||
|
||||
PopupMenu *convert_case = memnew(PopupMenu);
|
||||
convert_case->set_name("convert_case");
|
||||
edit_menu->get_popup()->add_child(convert_case);
|
||||
edit_menu->get_popup()->add_submenu_item(TTR("Convert Case"), "convert_case");
|
||||
convert_case->add_shortcut(ED_SHORTCUT("script_text_editor/convert_to_uppercase", TTR("Uppercase"), KEY_MASK_SHIFT | KEY_F4), EDIT_TO_UPPERCASE);
|
||||
|
@ -1716,12 +1717,73 @@ ScriptTextEditor::ScriptTextEditor() {
|
|||
convert_case->add_shortcut(ED_SHORTCUT("script_text_editor/capitalize", TTR("Capitalize"), KEY_MASK_SHIFT | KEY_F6), EDIT_CAPITALIZE);
|
||||
convert_case->connect("id_pressed", callable_mp(this, &ScriptTextEditor::_edit_option));
|
||||
|
||||
highlighter_menu = memnew(PopupMenu);
|
||||
highlighter_menu->set_name("highlighter_menu");
|
||||
edit_menu->get_popup()->add_child(highlighter_menu);
|
||||
edit_menu->get_popup()->add_submenu_item(TTR("Syntax Highlighter"), "highlighter_menu");
|
||||
highlighter_menu->connect("id_pressed", callable_mp(this, &ScriptTextEditor::_change_syntax_highlighter));
|
||||
|
||||
_load_theme_settings();
|
||||
|
||||
search_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/replace_in_files"), REPLACE_IN_FILES);
|
||||
edit_hb->add_child(goto_menu);
|
||||
goto_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/goto_function"), SEARCH_LOCATE_FUNCTION);
|
||||
goto_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/goto_line"), SEARCH_GOTO_LINE);
|
||||
goto_menu->get_popup()->add_separator();
|
||||
|
||||
goto_menu->get_popup()->add_child(bookmarks_menu);
|
||||
goto_menu->get_popup()->add_submenu_item(TTR("Bookmarks"), "Bookmarks");
|
||||
_update_bookmark_list();
|
||||
bookmarks_menu->connect("about_to_popup", callable_mp(this, &ScriptTextEditor::_update_bookmark_list));
|
||||
bookmarks_menu->connect("index_pressed", callable_mp(this, &ScriptTextEditor::_bookmark_item_pressed));
|
||||
|
||||
goto_menu->get_popup()->add_child(breakpoints_menu);
|
||||
goto_menu->get_popup()->add_submenu_item(TTR("Breakpoints"), "Breakpoints");
|
||||
_update_breakpoint_list();
|
||||
breakpoints_menu->connect("about_to_popup", callable_mp(this, &ScriptTextEditor::_update_breakpoint_list));
|
||||
breakpoints_menu->connect("index_pressed", callable_mp(this, &ScriptTextEditor::_breakpoint_item_pressed));
|
||||
|
||||
goto_menu->get_popup()->connect("id_pressed", callable_mp(this, &ScriptTextEditor::_edit_option));
|
||||
}
|
||||
|
||||
ScriptTextEditor::ScriptTextEditor() {
|
||||
code_editor = memnew(CodeTextEditor);
|
||||
code_editor->add_theme_constant_override("separation", 2);
|
||||
code_editor->set_anchors_and_margins_preset(Control::PRESET_WIDE);
|
||||
code_editor->set_code_complete_func(_code_complete_scripts, this);
|
||||
code_editor->set_v_size_flags(SIZE_EXPAND_FILL);
|
||||
|
||||
warnings_panel = memnew(RichTextLabel);
|
||||
warnings_panel->set_custom_minimum_size(Size2(0, 100 * EDSCALE));
|
||||
warnings_panel->set_h_size_flags(SIZE_EXPAND_FILL);
|
||||
warnings_panel->set_meta_underline(true);
|
||||
warnings_panel->set_selection_enabled(true);
|
||||
warnings_panel->set_focus_mode(FOCUS_CLICK);
|
||||
warnings_panel->hide();
|
||||
|
||||
update_settings();
|
||||
|
||||
code_editor->get_text_edit()->set_callhint_settings(
|
||||
EditorSettings::get_singleton()->get("text_editor/completion/put_callhint_tooltip_below_current_line"),
|
||||
EditorSettings::get_singleton()->get("text_editor/completion/callhint_tooltip_offset"));
|
||||
|
||||
code_editor->get_text_edit()->set_select_identifiers_on_hover(true);
|
||||
code_editor->get_text_edit()->set_context_menu_enabled(false);
|
||||
|
||||
context_menu = memnew(PopupMenu);
|
||||
|
||||
color_panel = memnew(PopupPanel);
|
||||
|
||||
edit_hb = memnew(HBoxContainer);
|
||||
|
||||
edit_menu = memnew(MenuButton);
|
||||
edit_menu->set_text(TTR("Edit"));
|
||||
edit_menu->set_switch_on_hover(true);
|
||||
|
||||
convert_case = memnew(PopupMenu);
|
||||
convert_case->set_name("convert_case");
|
||||
|
||||
highlighter_menu = memnew(PopupMenu);
|
||||
highlighter_menu->set_name("highlighter_menu");
|
||||
|
||||
Ref<EditorPlainTextSyntaxHighlighter> plain_highlighter;
|
||||
plain_highlighter.instance();
|
||||
add_syntax_highlighter(plain_highlighter);
|
||||
|
@ -1732,64 +1794,42 @@ ScriptTextEditor::ScriptTextEditor() {
|
|||
set_syntax_highlighter(highlighter);
|
||||
|
||||
search_menu = memnew(MenuButton);
|
||||
edit_hb->add_child(search_menu);
|
||||
search_menu->set_text(TTR("Search"));
|
||||
search_menu->set_switch_on_hover(true);
|
||||
|
||||
search_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/find"), SEARCH_FIND);
|
||||
search_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/find_next"), SEARCH_FIND_NEXT);
|
||||
search_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/find_previous"), SEARCH_FIND_PREV);
|
||||
search_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/replace"), SEARCH_REPLACE);
|
||||
search_menu->get_popup()->add_separator();
|
||||
search_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/find_in_files"), SEARCH_IN_FILES);
|
||||
search_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/replace_in_files"), REPLACE_IN_FILES);
|
||||
search_menu->get_popup()->add_separator();
|
||||
search_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/contextual_help"), HELP_CONTEXTUAL);
|
||||
search_menu->get_popup()->connect("id_pressed", callable_mp(this, &ScriptTextEditor::_edit_option));
|
||||
|
||||
edit_hb->add_child(edit_menu);
|
||||
|
||||
MenuButton *goto_menu = memnew(MenuButton);
|
||||
edit_hb->add_child(goto_menu);
|
||||
goto_menu = memnew(MenuButton);
|
||||
goto_menu->set_text(TTR("Go To"));
|
||||
goto_menu->set_switch_on_hover(true);
|
||||
goto_menu->get_popup()->connect("id_pressed", callable_mp(this, &ScriptTextEditor::_edit_option));
|
||||
|
||||
goto_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/goto_function"), SEARCH_LOCATE_FUNCTION);
|
||||
goto_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/goto_line"), SEARCH_GOTO_LINE);
|
||||
goto_menu->get_popup()->add_separator();
|
||||
|
||||
bookmarks_menu = memnew(PopupMenu);
|
||||
bookmarks_menu->set_name("Bookmarks");
|
||||
goto_menu->get_popup()->add_child(bookmarks_menu);
|
||||
goto_menu->get_popup()->add_submenu_item(TTR("Bookmarks"), "Bookmarks");
|
||||
_update_bookmark_list();
|
||||
bookmarks_menu->connect("about_to_popup", callable_mp(this, &ScriptTextEditor::_update_bookmark_list));
|
||||
bookmarks_menu->connect("index_pressed", callable_mp(this, &ScriptTextEditor::_bookmark_item_pressed));
|
||||
|
||||
breakpoints_menu = memnew(PopupMenu);
|
||||
breakpoints_menu->set_name("Breakpoints");
|
||||
goto_menu->get_popup()->add_child(breakpoints_menu);
|
||||
goto_menu->get_popup()->add_submenu_item(TTR("Breakpoints"), "Breakpoints");
|
||||
_update_breakpoint_list();
|
||||
breakpoints_menu->connect("about_to_popup", callable_mp(this, &ScriptTextEditor::_update_breakpoint_list));
|
||||
breakpoints_menu->connect("index_pressed", callable_mp(this, &ScriptTextEditor::_breakpoint_item_pressed));
|
||||
|
||||
quick_open = memnew(ScriptEditorQuickOpen);
|
||||
add_child(quick_open);
|
||||
quick_open->connect("goto_line", callable_mp(this, &ScriptTextEditor::_goto_line));
|
||||
|
||||
goto_line_dialog = memnew(GotoLineDialog);
|
||||
add_child(goto_line_dialog);
|
||||
|
||||
connection_info_dialog = memnew(ConnectionInfoDialog);
|
||||
add_child(connection_info_dialog);
|
||||
|
||||
code_editor->get_text_edit()->set_drag_forwarding(this);
|
||||
}
|
||||
|
||||
ScriptTextEditor::~ScriptTextEditor() {
|
||||
highlighters.clear();
|
||||
|
||||
if (!editor_enabled) {
|
||||
memdelete(code_editor);
|
||||
memdelete(warnings_panel);
|
||||
memdelete(context_menu);
|
||||
memdelete(color_panel);
|
||||
memdelete(edit_hb);
|
||||
memdelete(edit_menu);
|
||||
memdelete(convert_case);
|
||||
memdelete(highlighter_menu);
|
||||
memdelete(search_menu);
|
||||
memdelete(goto_menu);
|
||||
memdelete(bookmarks_menu);
|
||||
memdelete(breakpoints_menu);
|
||||
memdelete(connection_info_dialog);
|
||||
}
|
||||
}
|
||||
|
||||
static ScriptEditorBase *create_editor(const RES &p_resource) {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue