summaryrefslogtreecommitdiff
path: root/editor
diff options
context:
space:
mode:
Diffstat (limited to 'editor')
-rw-r--r--editor/action_map_editor.cpp26
-rw-r--r--editor/animation_track_editor.cpp4
-rw-r--r--editor/audio_stream_preview.cpp2
-rw-r--r--editor/code_editor.cpp87
-rw-r--r--editor/code_editor.h9
-rw-r--r--editor/create_dialog.cpp12
-rw-r--r--editor/debugger/editor_debugger_node.cpp2
-rw-r--r--editor/debugger/editor_debugger_server.cpp2
-rw-r--r--editor/debugger/editor_network_profiler.cpp10
-rw-r--r--editor/debugger/editor_profiler.cpp10
-rw-r--r--editor/debugger/editor_visual_profiler.cpp10
-rw-r--r--editor/debugger/script_editor_debugger.cpp8
-rw-r--r--editor/dependency_editor.cpp2
-rw-r--r--editor/doc_tools.cpp6
-rw-r--r--editor/editor_atlas_packer.cpp2
-rw-r--r--editor/editor_audio_buses.cpp6
-rw-r--r--editor/editor_autoload_settings.cpp12
-rw-r--r--editor/editor_data.cpp8
-rw-r--r--editor/editor_export.cpp8
-rw-r--r--editor/editor_feature_profile.cpp53
-rw-r--r--editor/editor_file_dialog.cpp2
-rw-r--r--editor/editor_file_system.cpp6
-rw-r--r--editor/editor_folding.cpp8
-rw-r--r--editor/editor_fonts.cpp44
-rw-r--r--editor/editor_help.cpp2
-rw-r--r--editor/editor_help_search.cpp2
-rw-r--r--editor/editor_inspector.cpp6
-rw-r--r--editor/editor_inspector.h6
-rw-r--r--editor/editor_layouts_dialog.cpp2
-rw-r--r--editor/editor_log.cpp27
-rw-r--r--editor/editor_node.cpp129
-rw-r--r--editor/editor_node.h7
-rw-r--r--editor/editor_plugin_settings.cpp10
-rw-r--r--editor/editor_properties.cpp451
-rw-r--r--editor/editor_properties.h34
-rw-r--r--editor/editor_properties_array_dict.cpp8
-rw-r--r--editor/editor_resource_picker.cpp8
-rw-r--r--editor/editor_resource_preview.cpp10
-rw-r--r--editor/editor_run_native.cpp2
-rw-r--r--editor/editor_settings.cpp14
-rw-r--r--editor/editor_spin_slider.cpp25
-rw-r--r--editor/editor_spin_slider.h4
-rw-r--r--editor/editor_themes.cpp4
-rw-r--r--editor/export_template_manager.cpp8
-rw-r--r--editor/fileserver/editor_file_server.cpp2
-rw-r--r--editor/filesystem_dock.cpp34
-rw-r--r--editor/filesystem_dock.h1
-rw-r--r--editor/find_in_files.cpp2
-rw-r--r--editor/icons/CenterView.svg1
-rw-r--r--editor/icons/RectangleAddRemove.svg1
-rw-r--r--editor/icons/TileChecked.svg1
-rw-r--r--editor/icons/TileUnchecked.svg1
-rw-r--r--editor/import/editor_import_collada.cpp6
-rw-r--r--editor/import/resource_importer_bitmask.cpp4
-rw-r--r--editor/import/resource_importer_csv_translation.cpp2
-rw-r--r--editor/import/resource_importer_layered_texture.cpp4
-rw-r--r--editor/import/resource_importer_obj.cpp8
-rw-r--r--editor/import/resource_importer_scene.cpp4
-rw-r--r--editor/import/resource_importer_shader_file.cpp2
-rw-r--r--editor/import/resource_importer_texture.cpp6
-rw-r--r--editor/import/resource_importer_texture_atlas.cpp16
-rw-r--r--editor/import/resource_importer_wav.cpp4
-rw-r--r--editor/import/scene_import_settings.cpp16
-rw-r--r--editor/import/scene_importer_mesh.cpp15
-rw-r--r--editor/import_dock.cpp10
-rw-r--r--editor/localization_editor.cpp2
-rw-r--r--editor/node_3d_editor_gizmos.cpp8
-rw-r--r--editor/plugins/animation_blend_space_1d_editor.cpp6
-rw-r--r--editor/plugins/animation_blend_space_2d_editor.cpp6
-rw-r--r--editor/plugins/animation_blend_tree_editor_plugin.cpp4
-rw-r--r--editor/plugins/animation_player_editor_plugin.cpp8
-rw-r--r--editor/plugins/animation_state_machine_editor.cpp8
-rw-r--r--editor/plugins/animation_tree_editor_plugin.cpp2
-rw-r--r--editor/plugins/asset_library_editor_plugin.cpp16
-rw-r--r--editor/plugins/canvas_item_editor_plugin.cpp56
-rw-r--r--editor/plugins/collision_polygon_3d_editor_plugin.cpp94
-rw-r--r--editor/plugins/collision_polygon_3d_editor_plugin.h5
-rw-r--r--editor/plugins/cpu_particles_2d_editor_plugin.cpp2
-rw-r--r--editor/plugins/curve_editor_plugin.cpp6
-rw-r--r--editor/plugins/editor_preview_plugins.cpp12
-rw-r--r--editor/plugins/font_editor_plugin.cpp4
-rw-r--r--editor/plugins/gpu_particles_2d_editor_plugin.cpp14
-rw-r--r--editor/plugins/gpu_particles_3d_editor_plugin.cpp4
-rw-r--r--editor/plugins/gpu_particles_collision_sdf_editor_plugin.cpp2
-rw-r--r--editor/plugins/gradient_editor_plugin.cpp2
-rw-r--r--editor/plugins/material_editor_plugin.cpp34
-rw-r--r--editor/plugins/mesh_editor_plugin.cpp4
-rw-r--r--editor/plugins/mesh_library_editor_plugin.cpp2
-rw-r--r--editor/plugins/node_3d_editor_plugin.cpp90
-rw-r--r--editor/plugins/node_3d_editor_plugin.h3
-rw-r--r--editor/plugins/occluder_instance_3d_editor_plugin.cpp2
-rw-r--r--editor/plugins/ot_features_plugin.cpp2
-rw-r--r--editor/plugins/path_3d_editor_plugin.cpp2
-rw-r--r--editor/plugins/polygon_2d_editor_plugin.cpp4
-rw-r--r--editor/plugins/resource_preloader_editor_plugin.cpp4
-rw-r--r--editor/plugins/script_editor_plugin.cpp26
-rw-r--r--editor/plugins/script_editor_plugin.h3
-rw-r--r--editor/plugins/script_text_editor.cpp129
-rw-r--r--editor/plugins/script_text_editor.h3
-rw-r--r--editor/plugins/shader_editor_plugin.cpp16
-rw-r--r--editor/plugins/shader_file_editor_plugin.cpp2
-rw-r--r--editor/plugins/skeleton_3d_editor_plugin.cpp2
-rw-r--r--editor/plugins/sprite_2d_editor_plugin.cpp6
-rw-r--r--editor/plugins/sprite_frames_editor_plugin.cpp2
-rw-r--r--editor/plugins/style_box_editor_plugin.cpp2
-rw-r--r--editor/plugins/text_editor.cpp8
-rw-r--r--editor/plugins/texture_3d_editor_plugin.cpp6
-rw-r--r--editor/plugins/texture_editor_plugin.cpp2
-rw-r--r--editor/plugins/texture_layered_editor_plugin.cpp10
-rw-r--r--editor/plugins/theme_editor_plugin.cpp37
-rw-r--r--editor/plugins/theme_editor_plugin.h4
-rw-r--r--editor/plugins/theme_editor_preview.cpp4
-rw-r--r--editor/plugins/tiles/tile_atlas_view.cpp199
-rw-r--r--editor/plugins/tiles/tile_atlas_view.h19
-rw-r--r--editor/plugins/tiles/tile_data_editors.cpp2468
-rw-r--r--editor/plugins/tiles/tile_data_editors.h359
-rw-r--r--editor/plugins/tiles/tile_map_editor.cpp55
-rw-r--r--editor/plugins/tiles/tile_set_atlas_source_editor.cpp1211
-rw-r--r--editor/plugins/tiles/tile_set_atlas_source_editor.h30
-rw-r--r--editor/plugins/tiles/tile_set_editor.cpp96
-rw-r--r--editor/plugins/tiles/tile_set_editor.h12
-rw-r--r--editor/plugins/visual_shader_editor_plugin.cpp27
-rw-r--r--editor/project_export.cpp12
-rw-r--r--editor/project_manager.cpp4
-rw-r--r--editor/property_editor.cpp18
-rw-r--r--editor/scene_tree_dock.cpp267
-rw-r--r--editor/scene_tree_dock.h11
-rw-r--r--editor/scene_tree_editor.cpp2
-rw-r--r--editor/script_create_dialog.cpp8
-rw-r--r--editor/settings_config_dialog.cpp2
-rw-r--r--editor/translations/ca.po28
-rw-r--r--editor/translations/cs.po10
-rw-r--r--editor/translations/de.po21
-rw-r--r--editor/translations/es.po19
-rw-r--r--editor/translations/es_AR.po10
-rw-r--r--editor/translations/eu.po86
-rw-r--r--editor/translations/fi.po10
-rw-r--r--editor/translations/fr.po14
-rw-r--r--editor/translations/ko.po12
-rw-r--r--editor/translations/pl.po12
-rw-r--r--editor/translations/pt_BR.po17
-rw-r--r--editor/translations/ru.po19
-rw-r--r--editor/translations/uk.po10
-rw-r--r--editor/translations/zh_CN.po9
144 files changed, 5025 insertions, 1960 deletions
diff --git a/editor/action_map_editor.cpp b/editor/action_map_editor.cpp
index b0b79ca069..fe1401bdf9 100644
--- a/editor/action_map_editor.cpp
+++ b/editor/action_map_editor.cpp
@@ -310,7 +310,7 @@ void InputEventConfigurationDialog::_update_input_list() {
MouseButton mouse_buttons[9] = { MOUSE_BUTTON_LEFT, MOUSE_BUTTON_RIGHT, MOUSE_BUTTON_MIDDLE, MOUSE_BUTTON_WHEEL_UP, MOUSE_BUTTON_WHEEL_DOWN, MOUSE_BUTTON_WHEEL_LEFT, MOUSE_BUTTON_WHEEL_RIGHT, MOUSE_BUTTON_XBUTTON1, MOUSE_BUTTON_XBUTTON2 };
for (int i = 0; i < 9; i++) {
Ref<InputEventMouseButton> mb;
- mb.instance();
+ mb.instantiate();
mb->set_button_index(mouse_buttons[i]);
String desc = get_event_text(mb);
@@ -333,8 +333,8 @@ void InputEventConfigurationDialog::_update_input_list() {
for (int i = 0; i < JOY_BUTTON_MAX; i++) {
Ref<InputEventJoypadButton> joyb;
- joyb.instance();
- joyb->set_button_index(i);
+ joyb.instantiate();
+ joyb->set_button_index((JoyButton)i);
String desc = get_event_text(joyb);
if (!search_term.is_empty() && desc.findn(search_term) == -1) {
@@ -358,8 +358,8 @@ void InputEventConfigurationDialog::_update_input_list() {
int axis = i / 2;
int direction = (i & 1) ? 1 : -1;
Ref<InputEventJoypadMotion> joym;
- joym.instance();
- joym->set_axis(axis);
+ joym.instantiate();
+ joym->set_axis((JoyAxis)axis);
joym->set_axis_value(direction);
String desc = get_event_text(joym);
@@ -458,7 +458,7 @@ void InputEventConfigurationDialog::_input_list_item_selected() {
case InputEventConfigurationDialog::INPUT_KEY: {
int kc = selected->get_meta("__keycode");
Ref<InputEventKey> k;
- k.instance();
+ k.instantiate();
if (physical_key_checkbox->is_pressed()) {
k->set_physical_keycode(kc);
@@ -481,8 +481,8 @@ void InputEventConfigurationDialog::_input_list_item_selected() {
case InputEventConfigurationDialog::INPUT_MOUSE_BUTTON: {
int idx = selected->get_meta("__index");
Ref<InputEventMouseButton> mb;
- mb.instance();
- mb->set_button_index(idx);
+ mb.instantiate();
+ mb->set_button_index((MouseButton)idx);
// Maintain modifier state from checkboxes
mb->set_alt_pressed(mod_checkboxes[MOD_ALT]->is_pressed());
mb->set_shift_pressed(mod_checkboxes[MOD_SHIFT]->is_pressed());
@@ -495,7 +495,7 @@ void InputEventConfigurationDialog::_input_list_item_selected() {
} break;
case InputEventConfigurationDialog::INPUT_JOY_BUTTON: {
int idx = selected->get_meta("__index");
- Ref<InputEventJoypadButton> jb = InputEventJoypadButton::create_reference(idx);
+ Ref<InputEventJoypadButton> jb = InputEventJoypadButton::create_reference((JoyButton)idx);
_set_event(jb);
} break;
case InputEventConfigurationDialog::INPUT_JOY_MOTION: {
@@ -503,8 +503,8 @@ void InputEventConfigurationDialog::_input_list_item_selected() {
int value = selected->get_meta("__value");
Ref<InputEventJoypadMotion> jm;
- jm.instance();
- jm->set_axis(axis);
+ jm.instantiate();
+ jm->set_axis((JoyAxis)axis);
jm->set_axis_value(value);
_set_event(jm);
} break;
@@ -1125,9 +1125,9 @@ ActionMapEditor::ActionMapEditor() {
action_tree->set_column_title(0, TTR("Action"));
action_tree->set_column_title(1, TTR("Deadzone"));
action_tree->set_column_expand(1, false);
- action_tree->set_column_min_width(1, 80 * EDSCALE);
+ action_tree->set_column_custom_minimum_width(1, 80 * EDSCALE);
action_tree->set_column_expand(2, false);
- action_tree->set_column_min_width(2, 50 * EDSCALE);
+ action_tree->set_column_custom_minimum_width(2, 50 * EDSCALE);
action_tree->connect("item_edited", callable_mp(this, &ActionMapEditor::_action_edited));
action_tree->connect("item_activated", callable_mp(this, &ActionMapEditor::_tree_item_activated));
action_tree->connect("button_pressed", callable_mp(this, &ActionMapEditor::_tree_button_pressed));
diff --git a/editor/animation_track_editor.cpp b/editor/animation_track_editor.cpp
index 4196bc8940..f61fb6bab3 100644
--- a/editor/animation_track_editor.cpp
+++ b/editor/animation_track_editor.cpp
@@ -3760,7 +3760,7 @@ Ref<Animation> AnimationTrackEditor::_create_and_get_reset_animation() {
return player->get_animation("RESET");
} else {
Ref<Animation> reset_anim;
- reset_anim.instance();
+ reset_anim.instantiate();
reset_anim->set_length(ANIM_MIN_LENGTH);
undo_redo->add_do_method(player, "add_animation", "RESET", reset_anim);
undo_redo->add_do_method(AnimationPlayerEditor::singleton, "_animation_player_changed", player);
@@ -5983,7 +5983,7 @@ AnimationTrackEditor::AnimationTrackEditor() {
//default plugins
Ref<AnimationTrackEditDefaultPlugin> def_plugin;
- def_plugin.instance();
+ def_plugin.instantiate();
add_track_edit_plugin(def_plugin);
//dialogs
diff --git a/editor/audio_stream_preview.cpp b/editor/audio_stream_preview.cpp
index 539657afd7..ad6e3ac1dc 100644
--- a/editor/audio_stream_preview.cpp
+++ b/editor/audio_stream_preview.cpp
@@ -192,7 +192,7 @@ Ref<AudioStreamPreview> AudioStreamPreviewGenerator::generate_preview(const Ref<
}
}
- preview->preview.instance();
+ preview->preview.instantiate();
preview->preview->preview = maxmin;
preview->preview->length = len_s;
diff --git a/editor/code_editor.cpp b/editor/code_editor.cpp
index 807a45eb32..3e4f382383 100644
--- a/editor/code_editor.cpp
+++ b/editor/code_editor.cpp
@@ -105,6 +105,11 @@ void FindReplaceBar::_notification(int p_what) {
hide_button->set_custom_minimum_size(hide_button->get_normal_texture()->get_size());
} else if (p_what == NOTIFICATION_THEME_CHANGED) {
matches_label->add_theme_color_override("font_color", results_count > 0 ? get_theme_color("font_color", "Label") : get_theme_color("error_color", "Editor"));
+ } else if (p_what == NOTIFICATION_PREDELETE) {
+ if (base_text_editor) {
+ base_text_editor->remove_find_replace_bar();
+ base_text_editor = nullptr;
+ }
}
}
@@ -117,7 +122,7 @@ void FindReplaceBar::_unhandled_input(const Ref<InputEvent> &p_event) {
}
Control *focus_owner = get_focus_owner();
- if (text_editor->has_focus() || (focus_owner && vbc_lineedit->is_a_parent_of(focus_owner))) {
+ if (text_editor->has_focus() || (focus_owner && vbc_lineedit->is_ancestor_of(focus_owner))) {
bool accepted = true;
switch (k->get_keycode()) {
@@ -595,6 +600,10 @@ void FindReplaceBar::set_text_edit(CodeTextEditor *p_text_editor) {
text_editor = nullptr;
}
+ if (!p_text_editor) {
+ return;
+ }
+
results_count = -1;
base_text_editor = p_text_editor;
text_editor = base_text_editor->get_text_editor();
@@ -930,7 +939,7 @@ void CodeTextEditor::update_editor_settings() {
text_editor->set_highlight_current_line(EditorSettings::get_singleton()->get("text_editor/highlighting/highlight_current_line"));
text_editor->set_indent_using_spaces(EditorSettings::get_singleton()->get("text_editor/indent/type"));
text_editor->set_indent_size(EditorSettings::get_singleton()->get("text_editor/indent/size"));
- text_editor->set_auto_indent(EditorSettings::get_singleton()->get("text_editor/indent/auto_indent"));
+ text_editor->set_auto_indent_enabled(EditorSettings::get_singleton()->get("text_editor/indent/auto_indent"));
text_editor->set_draw_tabs(EditorSettings::get_singleton()->get("text_editor/indent/draw_tabs"));
text_editor->set_draw_spaces(EditorSettings::get_singleton()->get("text_editor/indent/draw_spaces"));
text_editor->set_smooth_scroll_enabled(EditorSettings::get_singleton()->get("text_editor/navigation/smooth_scrolling"));
@@ -1255,7 +1264,7 @@ void CodeTextEditor::_delete_line(int p_line) {
text_editor->cursor_set_line(1);
text_editor->cursor_set_column(0);
}
- text_editor->backspace_at_cursor();
+ text_editor->backspace();
text_editor->unfold_line(p_line);
text_editor->cursor_set_line(p_line);
}
@@ -1612,15 +1621,19 @@ void CodeTextEditor::validate_script() {
idle->start();
}
-void CodeTextEditor::_warning_label_gui_input(const Ref<InputEvent> &p_event) {
- Ref<InputEventMouseButton> mb = p_event;
- if (mb.is_valid() && mb->is_pressed() && mb->get_button_index() == MOUSE_BUTTON_LEFT) {
- _warning_button_pressed();
- }
+void CodeTextEditor::_error_button_pressed() {
+ _set_show_errors_panel(!is_errors_panel_opened);
+ _set_show_warnings_panel(false);
}
void CodeTextEditor::_warning_button_pressed() {
_set_show_warnings_panel(!is_warnings_panel_opened);
+ _set_show_errors_panel(false);
+}
+
+void CodeTextEditor::_set_show_errors_panel(bool p_show) {
+ is_errors_panel_opened = p_show;
+ emit_signal("show_errors_panel", p_show);
}
void CodeTextEditor::_set_show_warnings_panel(bool p_show) {
@@ -1653,6 +1666,7 @@ void CodeTextEditor::_notification(int p_what) {
_update_font();
} break;
case NOTIFICATION_ENTER_TREE: {
+ error_button->set_icon(get_theme_icon("StatusError", "EditorIcons"));
warning_button->set_icon(get_theme_icon("NodeWarning", "EditorIcons"));
add_theme_constant_override("separation", 4 * EDSCALE);
} break;
@@ -1662,16 +1676,28 @@ void CodeTextEditor::_notification(int p_what) {
}
set_process_input(is_visible_in_tree());
} break;
+ case NOTIFICATION_PREDELETE: {
+ if (find_replace_bar) {
+ find_replace_bar->set_text_edit(nullptr);
+ }
+ } break;
default:
break;
}
}
-void CodeTextEditor::set_warning_nb(int p_warning_nb) {
- warning_count_label->set_text(itos(p_warning_nb));
- warning_count_label->set_visible(p_warning_nb > 0);
- warning_button->set_visible(p_warning_nb > 0);
- if (!p_warning_nb) {
+void CodeTextEditor::set_error_count(int p_error_count) {
+ error_button->set_text(itos(p_error_count));
+ error_button->set_visible(p_error_count > 0);
+ if (!p_error_count) {
+ _set_show_errors_panel(false);
+ }
+}
+
+void CodeTextEditor::set_warning_count(int p_warning_count) {
+ warning_button->set_text(itos(p_warning_count));
+ warning_button->set_visible(p_warning_count > 0);
+ if (!p_warning_count) {
_set_show_warnings_panel(false);
}
}
@@ -1738,6 +1764,7 @@ void CodeTextEditor::_bind_methods() {
ADD_SIGNAL(MethodInfo("validate_script"));
ADD_SIGNAL(MethodInfo("load_theme_settings"));
+ ADD_SIGNAL(MethodInfo("show_errors_panel"));
ADD_SIGNAL(MethodInfo("show_warnings_panel"));
}
@@ -1796,7 +1823,7 @@ CodeTextEditor::CodeTextEditor() {
text_editor->set_draw_line_numbers(true);
text_editor->set_brace_matching(true);
- text_editor->set_auto_indent(true);
+ text_editor->set_auto_indent_enabled(true);
status_bar = memnew(HBoxContainer);
add_child(status_bar);
@@ -1835,6 +1862,22 @@ CodeTextEditor::CodeTextEditor() {
error->set_mouse_filter(MOUSE_FILTER_STOP);
error->connect("gui_input", callable_mp(this, &CodeTextEditor::_error_pressed));
+ // Errors
+ error_button = memnew(Button);
+ error_button->set_flat(true);
+ status_bar->add_child(error_button);
+ error_button->set_v_size_flags(SIZE_EXPAND | SIZE_SHRINK_CENTER);
+ error_button->set_default_cursor_shape(CURSOR_POINTING_HAND);
+ error_button->connect("pressed", callable_mp(this, &CodeTextEditor::_error_button_pressed));
+ error_button->set_tooltip(TTR("Errors"));
+
+ error_button->add_theme_color_override("font_color", EditorNode::get_singleton()->get_gui_base()->get_theme_color("error_color", "Editor"));
+ error_button->add_theme_font_override("font", EditorNode::get_singleton()->get_gui_base()->get_theme_font("status_source", "EditorFonts"));
+ error_button->add_theme_font_size_override("font_size", EditorNode::get_singleton()->get_gui_base()->get_theme_font_size("status_source_size", "EditorFonts"));
+
+ is_errors_panel_opened = false;
+ set_error_count(0);
+
// Warnings
warning_button = memnew(Button);
warning_button->set_flat(true);
@@ -1844,20 +1887,12 @@ CodeTextEditor::CodeTextEditor() {
warning_button->connect("pressed", callable_mp(this, &CodeTextEditor::_warning_button_pressed));
warning_button->set_tooltip(TTR("Warnings"));
- warning_count_label = memnew(Label);
- status_bar->add_child(warning_count_label);
- warning_count_label->set_v_size_flags(SIZE_EXPAND | SIZE_SHRINK_CENTER);
- warning_count_label->set_align(Label::ALIGN_RIGHT);
- warning_count_label->set_default_cursor_shape(CURSOR_POINTING_HAND);
- warning_count_label->set_mouse_filter(MOUSE_FILTER_STOP);
- warning_count_label->set_tooltip(TTR("Warnings"));
- warning_count_label->add_theme_color_override("font_color", EditorNode::get_singleton()->get_gui_base()->get_theme_color("warning_color", "Editor"));
- warning_count_label->add_theme_font_override("font", EditorNode::get_singleton()->get_gui_base()->get_theme_font("status_source", "EditorFonts"));
- warning_count_label->add_theme_font_size_override("font_size", EditorNode::get_singleton()->get_gui_base()->get_theme_font_size("status_source_size", "EditorFonts"));
- warning_count_label->connect("gui_input", callable_mp(this, &CodeTextEditor::_warning_label_gui_input));
+ warning_button->add_theme_color_override("font_color", EditorNode::get_singleton()->get_gui_base()->get_theme_color("warning_color", "Editor"));
+ warning_button->add_theme_font_override("font", EditorNode::get_singleton()->get_gui_base()->get_theme_font("status_source", "EditorFonts"));
+ warning_button->add_theme_font_size_override("font_size", EditorNode::get_singleton()->get_gui_base()->get_theme_font_size("status_source_size", "EditorFonts"));
is_warnings_panel_opened = false;
- set_warning_nb(0);
+ set_warning_count(0);
// Line and column
line_and_col_txt = memnew(Label);
diff --git a/editor/code_editor.h b/editor/code_editor.h
index f368305e85..28b09e0a5d 100644
--- a/editor/code_editor.h
+++ b/editor/code_editor.h
@@ -145,8 +145,8 @@ class CodeTextEditor : public VBoxContainer {
HBoxContainer *status_bar;
Button *toggle_scripts_button;
+ Button *error_button;
Button *warning_button;
- Label *warning_count_label;
Label *line_and_col_txt;
@@ -184,8 +184,9 @@ class CodeTextEditor : public VBoxContainer {
CodeTextEditorCodeCompleteFunc code_complete_func;
void *code_complete_ud;
- void _warning_label_gui_input(const Ref<InputEvent> &p_event);
+ void _error_button_pressed();
void _warning_button_pressed();
+ void _set_show_errors_panel(bool p_show);
void _set_show_warnings_panel(bool p_show);
void _error_pressed(const Ref<InputEvent> &p_event);
@@ -205,6 +206,7 @@ protected:
static void _bind_methods();
bool is_warnings_panel_opened;
+ bool is_errors_panel_opened;
public:
void trim_trailing_whitespace();
@@ -238,7 +240,8 @@ public:
Variant get_edit_state();
void set_edit_state(const Variant &p_state);
- void set_warning_nb(int p_warning_nb);
+ void set_error_count(int p_error_count);
+ void set_warning_count(int p_warning_count);
void update_editor_settings();
void set_error(const String &p_error);
diff --git a/editor/create_dialog.cpp b/editor/create_dialog.cpp
index 968b24893c..027cee3f1c 100644
--- a/editor/create_dialog.cpp
+++ b/editor/create_dialog.cpp
@@ -130,7 +130,7 @@ bool CreateDialog::_should_hide_type(const String &p_type) const {
}
if (ClassDB::class_exists(p_type)) {
- if (!ClassDB::can_instance(p_type)) {
+ if (!ClassDB::can_instantiate(p_type)) {
return true; // Can't create abstract class.
}
@@ -234,8 +234,8 @@ void CreateDialog::_configure_search_option_item(TreeItem *r_item, const String
r_item->set_text(0, p_type);
}
- bool can_instance = (p_cpp_type && ClassDB::can_instance(p_type)) || !p_cpp_type;
- if (!can_instance) {
+ bool can_instantiate = (p_cpp_type && ClassDB::can_instantiate(p_type)) || !p_cpp_type;
+ if (!can_instantiate) {
r_item->set_custom_color(0, search_options->get_theme_color("disabled_font_color", "Editor"));
r_item->set_icon(0, EditorNode::get_singleton()->get_class_icon(p_type, "NodeDisabled"));
r_item->set_selectable(0, false);
@@ -247,7 +247,7 @@ void CreateDialog::_configure_search_option_item(TreeItem *r_item, const String
r_item->set_collapsed(false);
} else {
// Don't collapse the root node or an abstract node on the first tree level.
- bool should_collapse = p_type != base_type && (r_item->get_parent()->get_text(0) != base_type || can_instance);
+ bool should_collapse = p_type != base_type && (r_item->get_parent()->get_text(0) != base_type || can_instantiate);
if (should_collapse && bool(EditorSettings::get_singleton()->get("docks/scene_tree/start_create_dialog_fully_expanded"))) {
should_collapse = false; // Collapse all nodes anyway.
@@ -432,7 +432,7 @@ Variant CreateDialog::instance_selected() {
obj = EditorNode::get_editor_data().instance_custom_type(selected->get_text(0), custom);
}
} else {
- obj = ClassDB::instance(selected->get_text(0));
+ obj = ClassDB::instantiate(selected->get_text(0));
}
// Check if any Object-type property should be instantiated.
@@ -442,7 +442,7 @@ Variant CreateDialog::instance_selected() {
for (List<PropertyInfo>::Element *E = pinfo.front(); E; E = E->next()) {
PropertyInfo pi = E->get();
if (pi.type == Variant::OBJECT && pi.usage & PROPERTY_USAGE_EDITOR_INSTANTIATE_OBJECT) {
- Object *prop = ClassDB::instance(pi.class_name);
+ Object *prop = ClassDB::instantiate(pi.class_name);
((Object *)obj)->set(pi.name, prop);
}
}
diff --git a/editor/debugger/editor_debugger_node.cpp b/editor/debugger/editor_debugger_node.cpp
index ded0ee3aa7..5f90680115 100644
--- a/editor/debugger/editor_debugger_node.cpp
+++ b/editor/debugger/editor_debugger_node.cpp
@@ -65,7 +65,7 @@ EditorDebuggerNode::EditorDebuggerNode() {
add_child(tabs);
Ref<StyleBoxEmpty> empty;
- empty.instance();
+ empty.instantiate();
tabs->add_theme_style_override("panel", empty);
auto_switch_remote_scene_tree = EDITOR_DEF("debugger/auto_switch_to_remote_scene_tree", false);
diff --git a/editor/debugger/editor_debugger_server.cpp b/editor/debugger/editor_debugger_server.cpp
index 662f247062..e8524e0702 100644
--- a/editor/debugger/editor_debugger_server.cpp
+++ b/editor/debugger/editor_debugger_server.cpp
@@ -60,7 +60,7 @@ EditorDebuggerServer *EditorDebuggerServerTCP::create(const String &p_protocol)
}
EditorDebuggerServerTCP::EditorDebuggerServerTCP() {
- server.instance();
+ server.instantiate();
}
Error EditorDebuggerServerTCP::start() {
diff --git a/editor/debugger/editor_network_profiler.cpp b/editor/debugger/editor_network_profiler.cpp
index 2d57dff69d..af83baeff8 100644
--- a/editor/debugger/editor_network_profiler.cpp
+++ b/editor/debugger/editor_network_profiler.cpp
@@ -178,19 +178,19 @@ EditorNetworkProfiler::EditorNetworkProfiler() {
counters_display->set_column_titles_visible(true);
counters_display->set_column_title(0, TTR("Node"));
counters_display->set_column_expand(0, true);
- counters_display->set_column_min_width(0, 60 * EDSCALE);
+ counters_display->set_column_custom_minimum_width(0, 60 * EDSCALE);
counters_display->set_column_title(1, TTR("Incoming RPC"));
counters_display->set_column_expand(1, false);
- counters_display->set_column_min_width(1, 120 * EDSCALE);
+ counters_display->set_column_custom_minimum_width(1, 120 * EDSCALE);
counters_display->set_column_title(2, TTR("Incoming RSET"));
counters_display->set_column_expand(2, false);
- counters_display->set_column_min_width(2, 120 * EDSCALE);
+ counters_display->set_column_custom_minimum_width(2, 120 * EDSCALE);
counters_display->set_column_title(3, TTR("Outgoing RPC"));
counters_display->set_column_expand(3, false);
- counters_display->set_column_min_width(3, 120 * EDSCALE);
+ counters_display->set_column_custom_minimum_width(3, 120 * EDSCALE);
counters_display->set_column_title(4, TTR("Outgoing RSET"));
counters_display->set_column_expand(4, false);
- counters_display->set_column_min_width(4, 120 * EDSCALE);
+ counters_display->set_column_custom_minimum_width(4, 120 * EDSCALE);
add_child(counters_display);
frame_delay = memnew(Timer);
diff --git a/editor/debugger/editor_profiler.cpp b/editor/debugger/editor_profiler.cpp
index d60e2783ec..449aaa42ff 100644
--- a/editor/debugger/editor_profiler.cpp
+++ b/editor/debugger/editor_profiler.cpp
@@ -305,12 +305,12 @@ void EditorProfiler::_update_plot() {
}
Ref<Image> img;
- img.instance();
+ img.instantiate();
img->create(w, h, false, Image::FORMAT_RGBA8, graph_image);
if (reset_texture) {
if (graph_texture.is_null()) {
- graph_texture.instance();
+ graph_texture.instantiate();
}
graph_texture->create_from_image(img);
}
@@ -631,13 +631,13 @@ EditorProfiler::EditorProfiler() {
variables->set_column_titles_visible(true);
variables->set_column_title(0, TTR("Name"));
variables->set_column_expand(0, true);
- variables->set_column_min_width(0, 60 * EDSCALE);
+ variables->set_column_custom_minimum_width(0, 60 * EDSCALE);
variables->set_column_title(1, TTR("Time"));
variables->set_column_expand(1, false);
- variables->set_column_min_width(1, 100 * EDSCALE);
+ variables->set_column_custom_minimum_width(1, 100 * EDSCALE);
variables->set_column_title(2, TTR("Calls"));
variables->set_column_expand(2, false);
- variables->set_column_min_width(2, 60 * EDSCALE);
+ variables->set_column_custom_minimum_width(2, 60 * EDSCALE);
variables->connect("item_edited", callable_mp(this, &EditorProfiler::_item_edited));
graph = memnew(TextureRect);
diff --git a/editor/debugger/editor_visual_profiler.cpp b/editor/debugger/editor_visual_profiler.cpp
index 5bb10b3794..d3948dee97 100644
--- a/editor/debugger/editor_visual_profiler.cpp
+++ b/editor/debugger/editor_visual_profiler.cpp
@@ -299,12 +299,12 @@ void EditorVisualProfiler::_update_plot() {
}
Ref<Image> img;
- img.instance();
+ img.instantiate();
img->create(w, h, false, Image::FORMAT_RGBA8, graph_image);
if (reset_texture) {
if (graph_texture.is_null()) {
- graph_texture.instance();
+ graph_texture.instantiate();
}
graph_texture->create_from_image(img);
}
@@ -773,13 +773,13 @@ EditorVisualProfiler::EditorVisualProfiler() {
variables->set_column_titles_visible(true);
variables->set_column_title(0, TTR("Name"));
variables->set_column_expand(0, true);
- variables->set_column_min_width(0, 60);
+ variables->set_column_custom_minimum_width(0, 60);
variables->set_column_title(1, TTR("CPU"));
variables->set_column_expand(1, false);
- variables->set_column_min_width(1, 60 * EDSCALE);
+ variables->set_column_custom_minimum_width(1, 60 * EDSCALE);
variables->set_column_title(2, TTR("GPU"));
variables->set_column_expand(2, false);
- variables->set_column_min_width(2, 60 * EDSCALE);
+ variables->set_column_custom_minimum_width(2, 60 * EDSCALE);
variables->connect("cell_selected", callable_mp(this, &EditorVisualProfiler::_item_selected));
graph = memnew(TextureRect);
diff --git a/editor/debugger/script_editor_debugger.cpp b/editor/debugger/script_editor_debugger.cpp
index 7493cc2a8d..0d3fd8c7f6 100644
--- a/editor/debugger/script_editor_debugger.cpp
+++ b/editor/debugger/script_editor_debugger.cpp
@@ -1643,7 +1643,7 @@ ScriptEditorDebugger::ScriptEditorDebugger(EditorNode *p_editor) {
error_tree->set_columns(2);
error_tree->set_column_expand(0, false);
- error_tree->set_column_min_width(0, 140);
+ error_tree->set_column_custom_minimum_width(0, 140);
error_tree->set_column_expand(1, true);
@@ -1731,13 +1731,13 @@ ScriptEditorDebugger::ScriptEditorDebugger(EditorNode *p_editor) {
vmem_tree->set_column_expand(0, true);
vmem_tree->set_column_expand(1, false);
vmem_tree->set_column_title(1, TTR("Type"));
- vmem_tree->set_column_min_width(1, 100 * EDSCALE);
+ vmem_tree->set_column_custom_minimum_width(1, 100 * EDSCALE);
vmem_tree->set_column_expand(2, false);
vmem_tree->set_column_title(2, TTR("Format"));
- vmem_tree->set_column_min_width(2, 150 * EDSCALE);
+ vmem_tree->set_column_custom_minimum_width(2, 150 * EDSCALE);
vmem_tree->set_column_expand(3, false);
vmem_tree->set_column_title(3, TTR("Usage"));
- vmem_tree->set_column_min_width(3, 80 * EDSCALE);
+ vmem_tree->set_column_custom_minimum_width(3, 80 * EDSCALE);
vmem_tree->set_hide_root(true);
tabs->add_child(vmem_vb);
diff --git a/editor/dependency_editor.cpp b/editor/dependency_editor.cpp
index 7534b419fe..74a8ad9077 100644
--- a/editor/dependency_editor.cpp
+++ b/editor/dependency_editor.cpp
@@ -769,7 +769,7 @@ OrphanResourcesDialog::OrphanResourcesDialog() {
files = memnew(Tree);
files->set_columns(2);
files->set_column_titles_visible(true);
- files->set_column_min_width(1, 100);
+ files->set_column_custom_minimum_width(1, 100);
files->set_column_expand(0, true);
files->set_column_expand(1, false);
files->set_column_title(0, TTR("Resource"));
diff --git a/editor/doc_tools.cpp b/editor/doc_tools.cpp
index d3df4d91a6..befafec6cb 100644
--- a/editor/doc_tools.cpp
+++ b/editor/doc_tools.cpp
@@ -206,14 +206,14 @@ static Variant get_documentation_default_value(const StringName &p_class_name, c
Variant default_value = Variant();
r_default_value_valid = false;
- if (ClassDB::can_instance(p_class_name)) {
+ if (ClassDB::can_instantiate(p_class_name)) {
default_value = ClassDB::class_get_default_property_value(p_class_name, p_property_name, &r_default_value_valid);
} else {
- // Cannot get default value of classes that can't be instanced
+ // Cannot get default value of classes that can't be instantiated
List<StringName> inheriting_classes;
ClassDB::get_direct_inheriters_from_class(p_class_name, &inheriting_classes);
for (List<StringName>::Element *E2 = inheriting_classes.front(); E2; E2 = E2->next()) {
- if (ClassDB::can_instance(E2->get())) {
+ if (ClassDB::can_instantiate(E2->get())) {
default_value = ClassDB::class_get_default_property_value(E2->get(), p_property_name, &r_default_value_valid);
if (r_default_value_valid) {
break;
diff --git a/editor/editor_atlas_packer.cpp b/editor/editor_atlas_packer.cpp
index 1b4a505edb..85541c093a 100644
--- a/editor/editor_atlas_packer.cpp
+++ b/editor/editor_atlas_packer.cpp
@@ -105,7 +105,7 @@ void EditorAtlasPacker::chart_pack(Vector<Chart> &charts, int &r_width, int &r_h
}
Ref<BitMap> src_bitmap;
- src_bitmap.instance();
+ src_bitmap.instantiate();
src_bitmap->create(aabb.size / divide_by);
int w = src_bitmap->get_size().width;
diff --git a/editor/editor_audio_buses.cpp b/editor/editor_audio_buses.cpp
index e08334c00e..3e3428ad93 100644
--- a/editor/editor_audio_buses.cpp
+++ b/editor/editor_audio_buses.cpp
@@ -525,7 +525,7 @@ void EditorAudioBus::_effect_add(int p_which) {
StringName name = effect_options->get_item_metadata(p_which);
- Object *fx = ClassDB::instance(name);
+ Object *fx = ClassDB::instantiate(name);
ERR_FAIL_COND(!fx);
AudioEffect *afx = Object::cast_to<AudioEffect>(fx);
ERR_FAIL_COND(!afx);
@@ -921,7 +921,7 @@ EditorAudioBus::EditorAudioBus(EditorAudioBuses *p_buses, bool p_is_master) {
ClassDB::get_inheriters_from_class("AudioEffect", &effects);
effects.sort_custom<StringName::AlphCompare>();
for (List<StringName>::Element *E = effects.front(); E; E = E->next()) {
- if (!ClassDB::can_instance(E->get())) {
+ if (!ClassDB::can_instantiate(E->get())) {
continue;
}
@@ -1238,7 +1238,7 @@ void EditorAudioBuses::_file_dialog_callback(const String &p_string) {
} else if (file_dialog->get_file_mode() == EditorFileDialog::FILE_MODE_SAVE_FILE) {
if (new_layout) {
Ref<AudioBusLayout> empty_state;
- empty_state.instance();
+ empty_state.instantiate();
AudioServer::get_singleton()->set_bus_layout(empty_state);
}
diff --git a/editor/editor_autoload_settings.cpp b/editor/editor_autoload_settings.cpp
index 304c2fe532..306a88047a 100644
--- a/editor/editor_autoload_settings.cpp
+++ b/editor/editor_autoload_settings.cpp
@@ -349,14 +349,14 @@ Node *EditorAutoloadSettings::_create_autoload(const String &p_path) {
Node *n = nullptr;
if (res->is_class("PackedScene")) {
Ref<PackedScene> ps = res;
- n = ps->instance();
+ n = ps->instantiate();
} else if (res->is_class("Script")) {
Ref<Script> s = res;
StringName ibt = s->get_instance_base_type();
bool valid_type = ClassDB::is_parent_class(ibt, "Node");
ERR_FAIL_COND_V_MSG(!valid_type, nullptr, "Script does not inherit a Node: " + p_path + ".");
- Object *obj = ClassDB::instance(ibt);
+ Object *obj = ClassDB::instantiate(ibt);
ERR_FAIL_COND_V_MSG(obj == nullptr, nullptr, "Cannot instance script for autoload, expected 'Node' inheritance, got: " + String(ibt) + ".");
@@ -882,19 +882,19 @@ EditorAutoloadSettings::EditorAutoloadSettings() {
tree->set_column_title(0, TTR("Name"));
tree->set_column_expand(0, true);
- tree->set_column_min_width(0, 100 * EDSCALE);
+ tree->set_column_custom_minimum_width(0, 100 * EDSCALE);
tree->set_column_title(1, TTR("Path"));
tree->set_column_expand(1, true);
- tree->set_column_min_width(1, 100 * EDSCALE);
+ tree->set_column_custom_minimum_width(1, 100 * EDSCALE);
tree->set_column_title(2, TTR("Global Variable"));
tree->set_column_expand(2, false);
// Reserve enough space for translations of "Global Variable" which may be longer.
- tree->set_column_min_width(2, 150 * EDSCALE);
+ tree->set_column_custom_minimum_width(2, 150 * EDSCALE);
tree->set_column_expand(3, false);
- tree->set_column_min_width(3, 120 * EDSCALE);
+ tree->set_column_custom_minimum_width(3, 120 * EDSCALE);
tree->connect("cell_selected", callable_mp(this, &EditorAutoloadSettings::_autoload_selected));
tree->connect("item_edited", callable_mp(this, &EditorAutoloadSettings::_autoload_edited));
diff --git a/editor/editor_data.cpp b/editor/editor_data.cpp
index 56c6a416af..3823d7e14f 100644
--- a/editor/editor_data.cpp
+++ b/editor/editor_data.cpp
@@ -476,7 +476,7 @@ Variant EditorData::instance_custom_type(const String &p_type, const String &p_i
if (get_custom_types()[p_inherits][i].name == p_type) {
Ref<Script> script = get_custom_types()[p_inherits][i].script;
- Variant ob = ClassDB::instance(p_inherits);
+ Variant ob = ClassDB::instantiate(p_inherits);
ERR_FAIL_COND_V(!ob, Variant());
Node *n = Object::cast_to<Node>(ob);
if (n) {
@@ -603,7 +603,7 @@ bool EditorData::check_and_update_scene(int p_idx) {
if (must_reload) {
Ref<PackedScene> pscene;
- pscene.instance();
+ pscene.instantiate();
EditorProgress ep("update_scene", TTR("Updating Scene"), 2);
ep.step(TTR("Storing local changes..."), 0);
@@ -611,7 +611,7 @@ bool EditorData::check_and_update_scene(int p_idx) {
Error err = pscene->pack(edited_scene[p_idx].root);
ERR_FAIL_COND_V(err != OK, false);
ep.step(TTR("Updating scene..."), 1);
- Node *new_scene = pscene->instance(PackedScene::GEN_EDIT_STATE_MAIN);
+ Node *new_scene = pscene->instantiate(PackedScene::GEN_EDIT_STATE_MAIN);
ERR_FAIL_COND_V(!new_scene, false);
//transfer selection
@@ -908,7 +908,7 @@ StringName EditorData::script_class_get_base(const String &p_class) const {
Variant EditorData::script_class_instance(const String &p_class) {
if (ScriptServer::is_global_class(p_class)) {
- Variant obj = ClassDB::instance(ScriptServer::get_global_class_native_base(p_class));
+ Variant obj = ClassDB::instantiate(ScriptServer::get_global_class_native_base(p_class));
if (obj) {
Ref<Script> script = script_class_load_script(p_class);
if (script.is_valid()) {
diff --git a/editor/editor_export.cpp b/editor/editor_export.cpp
index 7c5a06107d..fc483b46b7 100644
--- a/editor/editor_export.cpp
+++ b/editor/editor_export.cpp
@@ -430,7 +430,7 @@ bool EditorExportPlatform::exists_export_template(String template_file_name, Str
Ref<EditorExportPreset> EditorExportPlatform::create_preset() {
Ref<EditorExportPreset> preset;
- preset.instance();
+ preset.instantiate();
preset->platform = Ref<EditorExportPlatform>(this);
List<ExportOption> options;
@@ -873,7 +873,7 @@ Error EditorExportPlatform::export_project_files(const Ref<EditorExportPreset> &
if (FileAccess::exists(path + ".import")) {
//file is imported, replace by what it imports
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
err = config->load(path + ".import");
if (err != OK) {
ERR_PRINT("Could not parse: '" + path + "', not exported.");
@@ -1391,7 +1391,7 @@ EditorExport *EditorExport::singleton = nullptr;
void EditorExport::_save() {
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
for (int i = 0; i < export_presets.size(); i++) {
Ref<EditorExportPreset> preset = export_presets[i];
String section = "preset." + itos(i);
@@ -1546,7 +1546,7 @@ void EditorExport::_notification(int p_what) {
void EditorExport::load_config() {
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Error err = config->load("res://export_presets.cfg");
if (err != OK) {
return;
diff --git a/editor/editor_feature_profile.cpp b/editor/editor_feature_profile.cpp
index 51c6b473ad..58d2b6e86e 100644
--- a/editor/editor_feature_profile.cpp
+++ b/editor/editor_feature_profile.cpp
@@ -161,21 +161,21 @@ String EditorFeatureProfile::get_feature_description(Feature p_feature) {
}
Error EditorFeatureProfile::save_to_file(const String &p_path) {
- Dictionary json;
- json["type"] = "feature_profile";
+ Dictionary data;
+ data["type"] = "feature_profile";
Array dis_classes;
for (Set<StringName>::Element *E = disabled_classes.front(); E; E = E->next()) {
dis_classes.push_back(String(E->get()));
}
dis_classes.sort();
- json["disabled_classes"] = dis_classes;
+ data["disabled_classes"] = dis_classes;
Array dis_editors;
for (Set<StringName>::Element *E = disabled_editors.front(); E; E = E->next()) {
dis_editors.push_back(String(E->get()));
}
dis_editors.sort();
- json["disabled_editors"] = dis_editors;
+ data["disabled_editors"] = dis_editors;
Array dis_props;
@@ -185,7 +185,7 @@ Error EditorFeatureProfile::save_to_file(const String &p_path) {
}
}
- json["disabled_properties"] = dis_props;
+ data["disabled_properties"] = dis_props;
Array dis_features;
for (int i = 0; i < FEATURE_MAX; i++) {
@@ -194,12 +194,13 @@ Error EditorFeatureProfile::save_to_file(const String &p_path) {
}
}
- json["disabled_features"] = dis_features;
+ data["disabled_features"] = dis_features;
FileAccessRef f = FileAccess::open(p_path, FileAccess::WRITE);
ERR_FAIL_COND_V_MSG(!f, ERR_CANT_CREATE, "Cannot create file '" + p_path + "'.");
- String text = JSON::print(json, "\t");
+ JSON json;
+ String text = json.stringify(data, "\t");
f->store_string(text);
f->close();
return OK;
@@ -212,26 +213,24 @@ Error EditorFeatureProfile::load_from_file(const String &p_path) {
return err;
}
- String err_str;
- int err_line;
- Variant v;
- err = JSON::parse(text, v, err_str, err_line);
+ JSON json;
+ err = json.parse(text);
if (err != OK) {
- ERR_PRINT("Error parsing '" + p_path + "' on line " + itos(err_line) + ": " + err_str);
+ ERR_PRINT("Error parsing '" + p_path + "' on line " + itos(json.get_error_line()) + ": " + json.get_error_message());
return ERR_PARSE_ERROR;
}
- Dictionary json = v;
+ Dictionary data = json.get_data();
- if (!json.has("type") || String(json["type"]) != "feature_profile") {
+ if (!data.has("type") || String(data["type"]) != "feature_profile") {
ERR_PRINT("Error parsing '" + p_path + "', it's not a feature profile.");
return ERR_PARSE_ERROR;
}
disabled_classes.clear();
- if (json.has("disabled_classes")) {
- Array disabled_classes_arr = json["disabled_classes"];
+ if (data.has("disabled_classes")) {
+ Array disabled_classes_arr = data["disabled_classes"];
for (int i = 0; i < disabled_classes_arr.size(); i++) {
disabled_classes.insert(disabled_classes_arr[i]);
}
@@ -239,8 +238,8 @@ Error EditorFeatureProfile::load_from_file(const String &p_path) {
disabled_editors.clear();
- if (json.has("disabled_editors")) {
- Array disabled_editors_arr = json["disabled_editors"];
+ if (data.has("disabled_editors")) {
+ Array disabled_editors_arr = data["disabled_editors"];
for (int i = 0; i < disabled_editors_arr.size(); i++) {
disabled_editors.insert(disabled_editors_arr[i]);
}
@@ -248,16 +247,16 @@ Error EditorFeatureProfile::load_from_file(const String &p_path) {
disabled_properties.clear();
- if (json.has("disabled_properties")) {
- Array disabled_properties_arr = json["disabled_properties"];
+ if (data.has("disabled_properties")) {
+ Array disabled_properties_arr = data["disabled_properties"];
for (int i = 0; i < disabled_properties_arr.size(); i++) {
String s = disabled_properties_arr[i];
set_disable_class_property(s.get_slice(":", 0), s.get_slice(":", 1), true);
}
}
- if (json.has("disabled_features")) {
- Array disabled_features_arr = json["disabled_features"];
+ if (data.has("disabled_features")) {
+ Array disabled_features_arr = data["disabled_features"];
for (int i = 0; i < FEATURE_MAX; i++) {
bool found = false;
String f = feature_identifiers[i];
@@ -312,7 +311,7 @@ void EditorFeatureProfileManager::_notification(int p_what) {
if (p_what == NOTIFICATION_READY) {
current_profile = EDITOR_GET("_default_feature_profile");
if (current_profile != String()) {
- current.instance();
+ current.instantiate();
Error err = current->load_from_file(EditorSettings::get_singleton()->get_feature_profiles_dir().plus_file(current_profile + ".profile"));
if (err != OK) {
ERR_PRINT("Error loading default feature profile: " + current_profile);
@@ -474,7 +473,7 @@ void EditorFeatureProfileManager::_create_new_profile() {
}
Ref<EditorFeatureProfile> new_profile;
- new_profile.instance();
+ new_profile.instantiate();
new_profile->save_to_file(file);
_update_profile_list(name);
@@ -731,7 +730,7 @@ void EditorFeatureProfileManager::_update_selected_profile() {
ERR_FAIL_COND(current.is_null()); //nothing selected, current should never be null
} else {
//reload edited, if different from current
- edited.instance();
+ edited.instantiate();
Error err = edited->load_from_file(EditorSettings::get_singleton()->get_feature_profiles_dir().plus_file(profile + ".profile"));
ERR_FAIL_COND_MSG(err != OK, "Error when loading EditorSettings from file '" + EditorSettings::get_singleton()->get_feature_profiles_dir().plus_file(profile + ".profile") + "'.");
}
@@ -780,7 +779,7 @@ void EditorFeatureProfileManager::_import_profiles(const Vector<String> &p_paths
//test it first
for (int i = 0; i < p_paths.size(); i++) {
Ref<EditorFeatureProfile> profile;
- profile.instance();
+ profile.instantiate();
Error err = profile->load_from_file(p_paths[i]);
String basefile = p_paths[i].get_file();
if (err != OK) {
@@ -799,7 +798,7 @@ void EditorFeatureProfileManager::_import_profiles(const Vector<String> &p_paths
//do it second
for (int i = 0; i < p_paths.size(); i++) {
Ref<EditorFeatureProfile> profile;
- profile.instance();
+ profile.instantiate();
Error err = profile->load_from_file(p_paths[i]);
ERR_CONTINUE(err != OK);
String basefile = p_paths[i].get_file();
diff --git a/editor/editor_file_dialog.cpp b/editor/editor_file_dialog.cpp
index f3cee7576d..fe4c6f490d 100644
--- a/editor/editor_file_dialog.cpp
+++ b/editor/editor_file_dialog.cpp
@@ -1544,7 +1544,7 @@ EditorFileDialog::EditorFileDialog() {
pathhb->add_child(memnew(VSeparator));
Ref<ButtonGroup> view_mode_group;
- view_mode_group.instance();
+ view_mode_group.instantiate();
mode_thumbnails = memnew(Button);
mode_thumbnails->set_flat(true);
diff --git a/editor/editor_file_system.cpp b/editor/editor_file_system.cpp
index 3f715c1f93..a2507f3cf2 100644
--- a/editor/editor_file_system.cpp
+++ b/editor/editor_file_system.cpp
@@ -1524,7 +1524,7 @@ Error EditorFileSystem::_reimport_group(const String &p_group_file, const Vector
Map<String, String> base_paths;
for (int i = 0; i < p_files.size(); i++) {
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Error err = config->load(p_files[i] + ".import");
ERR_CONTINUE(err != OK);
ERR_CONTINUE(!config->has_section_key("remap", "importer"));
@@ -1706,7 +1706,7 @@ void EditorFileSystem::_reimport_file(const String &p_file, const Map<StringName
//use existing
if (p_custom_options == nullptr) {
Ref<ConfigFile> cf;
- cf.instance();
+ cf.instantiate();
Error err = cf->load(p_file + ".import");
if (err == OK) {
if (cf->has_section("params")) {
@@ -2068,7 +2068,7 @@ void EditorFileSystem::_move_group_files(EditorFileSystemDirectory *efd, const S
files[i]->import_group_file = p_new_location;
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
String path = efd->get_file_path(i) + ".import";
Error err = config->load(path);
if (err != OK) {
diff --git a/editor/editor_folding.cpp b/editor/editor_folding.cpp
index 4030aecbf5..5d6c415d39 100644
--- a/editor/editor_folding.cpp
+++ b/editor/editor_folding.cpp
@@ -50,7 +50,7 @@ Vector<String> EditorFolding::_get_unfolds(const Object *p_object) {
void EditorFolding::save_resource_folding(const RES &p_resource, const String &p_path) {
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Vector<String> unfolds = _get_unfolds(p_resource.ptr());
config->set_value("folding", "sections_unfolded", unfolds);
@@ -70,7 +70,7 @@ void EditorFolding::_set_unfolds(Object *p_object, const Vector<String> &p_unfol
void EditorFolding::load_resource_folding(RES p_resource, const String &p_path) {
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
String file = p_path.get_file() + "-folding-" + p_path.md5_text() + ".cfg";
file = EditorSettings::get_singleton()->get_project_settings_dir().plus_file(file);
@@ -137,7 +137,7 @@ void EditorFolding::save_scene_folding(const Node *p_scene, const String &p_path
}
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Array unfolds, res_unfolds;
Set<RES> resources;
@@ -155,7 +155,7 @@ void EditorFolding::save_scene_folding(const Node *p_scene, const String &p_path
void EditorFolding::load_scene_folding(Node *p_scene, const String &p_path) {
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
String path = EditorSettings::get_singleton()->get_project_settings_dir();
String file = p_path.get_file() + "-folding-" + p_path.md5_text() + ".cfg";
diff --git a/editor/editor_fonts.cpp b/editor/editor_fonts.cpp
index 2f5451fba3..d548196a2d 100644
--- a/editor/editor_fonts.cpp
+++ b/editor/editor_fonts.cpp
@@ -55,7 +55,7 @@
// the custom spacings might only work with Noto Sans
#define MAKE_DEFAULT_FONT(m_name) \
Ref<Font> m_name; \
- m_name.instance(); \
+ m_name.instantiate(); \
if (CustomFont.is_valid()) { \
m_name->add_data(CustomFont); \
m_name->add_data(DefaultFont); \
@@ -68,7 +68,7 @@
#define MAKE_BOLD_FONT(m_name) \
Ref<Font> m_name; \
- m_name.instance(); \
+ m_name.instantiate(); \
if (CustomFontBold.is_valid()) { \
m_name->add_data(CustomFontBold); \
m_name->add_data(DefaultFontBold); \
@@ -81,7 +81,7 @@
#define MAKE_SOURCE_FONT(m_name) \
Ref<Font> m_name; \
- m_name.instance(); \
+ m_name.instantiate(); \
if (CustomFontSource.is_valid()) { \
m_name->add_data(CustomFontSource); \
m_name->add_data(dfmono); \
@@ -129,7 +129,7 @@ void editor_register_fonts(Ref<Theme> p_theme) {
String custom_font_path = EditorSettings::get_singleton()->get("interface/editor/main_font");
Ref<FontData> CustomFont;
if (custom_font_path.length() > 0 && dir->file_exists(custom_font_path)) {
- CustomFont.instance();
+ CustomFont.instantiate();
CustomFont->load_resource(custom_font_path, default_font_size);
CustomFont->set_antialiased(font_antialiased);
CustomFont->set_hinting(font_hinting);
@@ -143,7 +143,7 @@ void editor_register_fonts(Ref<Theme> p_theme) {
String custom_font_path_bold = EditorSettings::get_singleton()->get("interface/editor/main_font_bold");
Ref<FontData> CustomFontBold;
if (custom_font_path_bold.length() > 0 && dir->file_exists(custom_font_path_bold)) {
- CustomFontBold.instance();
+ CustomFontBold.instantiate();
CustomFontBold->load_resource(custom_font_path_bold, default_font_size);
CustomFontBold->set_antialiased(font_antialiased);
CustomFontBold->set_hinting(font_hinting);
@@ -157,7 +157,7 @@ void editor_register_fonts(Ref<Theme> p_theme) {
String custom_font_path_source = EditorSettings::get_singleton()->get("interface/editor/code_font");
Ref<FontData> CustomFontSource;
if (custom_font_path_source.length() > 0 && dir->file_exists(custom_font_path_source)) {
- CustomFontSource.instance();
+ CustomFontSource.instantiate();
CustomFontSource->load_resource(custom_font_path_source, default_font_size);
CustomFontSource->set_antialiased(font_antialiased);
CustomFontSource->set_hinting(font_hinting);
@@ -178,105 +178,105 @@ void editor_register_fonts(Ref<Theme> p_theme) {
/* Droid Sans */
Ref<FontData> DefaultFont;
- DefaultFont.instance();
+ DefaultFont.instantiate();
DefaultFont->load_memory(_font_NotoSansUI_Regular, _font_NotoSansUI_Regular_size, "ttf", default_font_size);
DefaultFont->set_antialiased(font_antialiased);
DefaultFont->set_hinting(font_hinting);
DefaultFont->set_force_autohinter(true); //just looks better..i think?
Ref<FontData> DefaultFontBold;
- DefaultFontBold.instance();
+ DefaultFontBold.instantiate();
DefaultFontBold->load_memory(_font_NotoSansUI_Bold, _font_NotoSansUI_Bold_size, "ttf", default_font_size);
DefaultFontBold->set_antialiased(font_antialiased);
DefaultFontBold->set_hinting(font_hinting);
DefaultFontBold->set_force_autohinter(true); // just looks better..i think?
Ref<FontData> FontFallback;
- FontFallback.instance();
+ FontFallback.instantiate();
FontFallback->load_memory(_font_DroidSansFallback, _font_DroidSansFallback_size, "ttf", default_font_size);
FontFallback->set_antialiased(font_antialiased);
FontFallback->set_hinting(font_hinting);
FontFallback->set_force_autohinter(true); //just looks better..i think?
Ref<FontData> FontJapanese;
- FontJapanese.instance();
+ FontJapanese.instantiate();
FontJapanese->load_memory(_font_DroidSansJapanese, _font_DroidSansJapanese_size, "ttf", default_font_size);
FontJapanese->set_antialiased(font_antialiased);
FontJapanese->set_hinting(font_hinting);
FontJapanese->set_force_autohinter(true); //just looks better..i think?
Ref<FontData> FontArabic;
- FontArabic.instance();
+ FontArabic.instantiate();
FontArabic->load_memory(_font_NotoNaskhArabicUI_Regular, _font_NotoNaskhArabicUI_Regular_size, "ttf", default_font_size);
FontArabic->set_antialiased(font_antialiased);
FontArabic->set_hinting(font_hinting);
FontArabic->set_force_autohinter(true); //just looks better..i think?
Ref<FontData> FontBengali;
- FontBengali.instance();
+ FontBengali.instantiate();
FontBengali->load_memory(_font_NotoSansBengali_Regular, _font_NotoSansBengali_Regular_size, "ttf", default_font_size);
FontBengali->set_antialiased(font_antialiased);
FontBengali->set_hinting(font_hinting);
FontBengali->set_force_autohinter(true); //just looks better..i think?
Ref<FontData> FontGeorgian;
- FontGeorgian.instance();
+ FontGeorgian.instantiate();
FontGeorgian->load_memory(_font_NotoSansGeorgian_Regular, _font_NotoSansGeorgian_Regular_size, "ttf", default_font_size);
FontGeorgian->set_antialiased(font_antialiased);
FontGeorgian->set_hinting(font_hinting);
FontGeorgian->set_force_autohinter(true); //just looks better..i think?
Ref<FontData> FontHebrew;
- FontHebrew.instance();
+ FontHebrew.instantiate();
FontHebrew->load_memory(_font_NotoSansHebrew_Regular, _font_NotoSansHebrew_Regular_size, "ttf", default_font_size);
FontHebrew->set_antialiased(font_antialiased);
FontHebrew->set_hinting(font_hinting);
FontHebrew->set_force_autohinter(true); //just looks better..i think?
Ref<FontData> FontMalayalam;
- FontMalayalam.instance();
+ FontMalayalam.instantiate();
FontMalayalam->load_memory(_font_NotoSansMalayalamUI_Regular, _font_NotoSansMalayalamUI_Regular_size, "ttf", default_font_size);
FontMalayalam->set_antialiased(font_antialiased);
FontMalayalam->set_hinting(font_hinting);
FontMalayalam->set_force_autohinter(true); //just looks better..i think?
Ref<FontData> FontOriya;
- FontOriya.instance();
+ FontOriya.instantiate();
FontOriya->load_memory(_font_NotoSansOriyaUI_Regular, _font_NotoSansOriyaUI_Regular_size, "ttf", default_font_size);
FontOriya->set_antialiased(font_antialiased);
FontOriya->set_hinting(font_hinting);
FontOriya->set_force_autohinter(true); //just looks better..i think?
Ref<FontData> FontSinhala;
- FontSinhala.instance();
+ FontSinhala.instantiate();
FontSinhala->load_memory(_font_NotoSansSinhalaUI_Regular, _font_NotoSansSinhalaUI_Regular_size, "ttf", default_font_size);
FontSinhala->set_antialiased(font_antialiased);
FontSinhala->set_hinting(font_hinting);
FontSinhala->set_force_autohinter(true); //just looks better..i think?
Ref<FontData> FontTamil;
- FontTamil.instance();
+ FontTamil.instantiate();
FontTamil->load_memory(_font_NotoSansTamilUI_Regular, _font_NotoSansTamilUI_Regular_size, "ttf", default_font_size);
FontTamil->set_antialiased(font_antialiased);
FontTamil->set_hinting(font_hinting);
FontTamil->set_force_autohinter(true); //just looks better..i think?
Ref<FontData> FontTelugu;
- FontTelugu.instance();
+ FontTelugu.instantiate();
FontTelugu->load_memory(_font_NotoSansTeluguUI_Regular, _font_NotoSansTeluguUI_Regular_size, "ttf", default_font_size);
FontTelugu->set_antialiased(font_antialiased);
FontTelugu->set_hinting(font_hinting);
FontTelugu->set_force_autohinter(true); //just looks better..i think?
Ref<FontData> FontThai;
- FontThai.instance();
+ FontThai.instantiate();
FontThai->load_memory(_font_NotoSansThaiUI_Regular, _font_NotoSansThaiUI_Regular_size, "ttf", default_font_size);
FontThai->set_antialiased(font_antialiased);
FontThai->set_hinting(font_hinting);
FontThai->set_force_autohinter(true); //just looks better..i think?
Ref<FontData> FontHindi;
- FontHindi.instance();
+ FontHindi.instantiate();
FontHindi->load_memory(_font_NotoSansDevanagariUI_Regular, _font_NotoSansDevanagariUI_Regular_size, "ttf", default_font_size);
FontHindi->set_antialiased(font_antialiased);
FontHindi->set_hinting(font_hinting);
@@ -285,7 +285,7 @@ void editor_register_fonts(Ref<Theme> p_theme) {
/* Hack */
Ref<FontData> dfmono;
- dfmono.instance();
+ dfmono.instantiate();
dfmono->load_memory(_font_Hack_Regular, _font_Hack_Regular_size, "ttf", default_font_size);
dfmono->set_antialiased(font_antialiased);
dfmono->set_hinting(font_hinting);
diff --git a/editor/editor_help.cpp b/editor/editor_help.cpp
index 7365e8fd7d..16db465a4a 100644
--- a/editor/editor_help.cpp
+++ b/editor/editor_help.cpp
@@ -1909,7 +1909,7 @@ void FindBar::_unhandled_input(const Ref<InputEvent> &p_event) {
Ref<InputEventKey> k = p_event;
if (k.is_valid()) {
- if (k->is_pressed() && (rich_text_label->has_focus() || is_a_parent_of(get_focus_owner()))) {
+ if (k->is_pressed() && (rich_text_label->has_focus() || is_ancestor_of(get_focus_owner()))) {
bool accepted = true;
switch (k->get_keycode()) {
diff --git a/editor/editor_help_search.cpp b/editor/editor_help_search.cpp
index b93ffa9321..57ddc64e95 100644
--- a/editor/editor_help_search.cpp
+++ b/editor/editor_help_search.cpp
@@ -239,7 +239,7 @@ EditorHelpSearch::EditorHelpSearch() {
results_tree->set_column_title(0, TTR("Name"));
results_tree->set_column_title(1, TTR("Member Type"));
results_tree->set_column_expand(1, false);
- results_tree->set_column_min_width(1, 150 * EDSCALE);
+ results_tree->set_column_custom_minimum_width(1, 150 * EDSCALE);
results_tree->set_custom_minimum_size(Size2(0, 100) * EDSCALE);
results_tree->set_hide_root(true);
results_tree->set_select_mode(Tree::SELECT_ROW);
diff --git a/editor/editor_inspector.cpp b/editor/editor_inspector.cpp
index 69709315ff..cfce37ea1b 100644
--- a/editor/editor_inspector.cpp
+++ b/editor/editor_inspector.cpp
@@ -417,7 +417,7 @@ bool EditorPropertyRevert::may_node_be_in_instance(Node *p_node) {
return might_be; // or might not be
}
-bool EditorPropertyRevert::get_instanced_node_original_property(Node *p_node, const StringName &p_prop, Variant &value) {
+bool EditorPropertyRevert::get_instantiated_node_original_property(Node *p_node, const StringName &p_prop, Variant &value) {
Node *node = p_node;
Node *orig = node;
@@ -524,7 +524,7 @@ bool EditorPropertyRevert::can_property_revert(Object *p_object, const StringNam
if (node && EditorPropertyRevert::may_node_be_in_instance(node)) {
//check for difference including instantiation
Variant vorig;
- if (EditorPropertyRevert::get_instanced_node_original_property(node, p_property, vorig)) {
+ if (EditorPropertyRevert::get_instantiated_node_original_property(node, p_property, vorig)) {
Variant v = p_object->get(p_property);
if (EditorPropertyRevert::is_node_property_different(node, v, vorig)) {
@@ -764,7 +764,7 @@ void EditorProperty::_gui_input(const Ref<InputEvent> &p_event) {
Variant vorig;
Node *node = Object::cast_to<Node>(object);
- if (node && EditorPropertyRevert::may_node_be_in_instance(node) && EditorPropertyRevert::get_instanced_node_original_property(node, property, vorig)) {
+ if (node && EditorPropertyRevert::may_node_be_in_instance(node) && EditorPropertyRevert::get_instantiated_node_original_property(node, property, vorig)) {
emit_changed(property, vorig.duplicate(true));
update_property();
return;
diff --git a/editor/editor_inspector.h b/editor/editor_inspector.h
index e4bcab3e3f..f493290b09 100644
--- a/editor/editor_inspector.h
+++ b/editor/editor_inspector.h
@@ -40,7 +40,7 @@ class UndoRedo;
class EditorPropertyRevert {
public:
static bool may_node_be_in_instance(Node *p_node);
- static bool get_instanced_node_original_property(Node *p_node, const StringName &p_prop, Variant &value);
+ static bool get_instantiated_node_original_property(Node *p_node, const StringName &p_prop, Variant &value);
static bool is_node_property_different(Node *p_node, const Variant &p_current, const Variant &p_orig);
static bool can_property_revert(Object *p_object, const StringName &p_property);
@@ -83,7 +83,7 @@ private:
bool draw_top_bg;
bool _is_property_different(const Variant &p_current, const Variant &p_orig);
- bool _get_instanced_node_original_property(const StringName &p_prop, Variant &value);
+ bool _get_instantiated_node_original_property(const StringName &p_prop, Variant &value);
void _focusable_focused(int p_index);
bool selectable;
@@ -271,7 +271,7 @@ class EditorInspector : public ScrollContainer {
VBoxContainer *main_vbox;
- //map use to cache the instanced editors
+ //map use to cache the instantiated editors
Map<StringName, List<EditorProperty *>> editor_property_map;
List<EditorInspectorSection *> sections;
Set<StringName> pending;
diff --git a/editor/editor_layouts_dialog.cpp b/editor/editor_layouts_dialog.cpp
index 0bf1863459..437841ccc1 100644
--- a/editor/editor_layouts_dialog.cpp
+++ b/editor/editor_layouts_dialog.cpp
@@ -83,7 +83,7 @@ void EditorLayoutsDialog::_post_popup() {
layout_names->clear();
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Error err = config->load(EditorSettings::get_singleton()->get_editor_layouts_config());
if (err != OK) {
return;
diff --git a/editor/editor_log.cpp b/editor/editor_log.cpp
index 35d8021394..b3e90236a6 100644
--- a/editor/editor_log.cpp
+++ b/editor/editor_log.cpp
@@ -103,7 +103,7 @@ void EditorLog::_start_state_save_timer() {
void EditorLog::_save_state() {
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
// Load and amend existing config if it exists.
config->load(EditorSettings::get_singleton()->get_project_settings_dir().plus_file("editor_layout.cfg"));
@@ -122,22 +122,21 @@ void EditorLog::_load_state() {
is_loading_state = true;
Ref<ConfigFile> config;
- config.instance();
- Error err = config->load(EditorSettings::get_singleton()->get_project_settings_dir().plus_file("editor_layout.cfg"));
-
- if (err == OK) {
- const String section = "editor_log";
- for (Map<MessageType, LogFilter *>::Element *E = type_filter_map.front(); E; E = E->next()) {
- E->get()->set_active(config->get_value(section, "log_filter_" + itos(E->key()), false));
- }
+ config.instantiate();
+ config->load(EditorSettings::get_singleton()->get_project_settings_dir().plus_file("editor_layout.cfg"));
- collapse = config->get_value(section, "collapse", false);
- collapse_button->set_pressed(collapse);
- bool show_search = config->get_value(section, "show_search", true);
- search_box->set_visible(show_search);
- show_search_button->set_pressed(show_search);
+ // Run the below code even if config->load returns an error, since we want the defaults to be set even if the file does not exist yet.
+ const String section = "editor_log";
+ for (Map<MessageType, LogFilter *>::Element *E = type_filter_map.front(); E; E = E->next()) {
+ E->get()->set_active(config->get_value(section, "log_filter_" + itos(E->key()), true));
}
+ collapse = config->get_value(section, "collapse", false);
+ collapse_button->set_pressed(collapse);
+ bool show_search = config->get_value(section, "show_search", true);
+ search_box->set_visible(show_search);
+ show_search_button->set_pressed(show_search);
+
is_loading_state = false;
}
diff --git a/editor/editor_node.cpp b/editor/editor_node.cpp
index 657ec9d70b..31f84d2508 100644
--- a/editor/editor_node.cpp
+++ b/editor/editor_node.cpp
@@ -32,6 +32,7 @@
#include "core/config/project_settings.h"
#include "core/core_bind.h"
+#include "core/extension/native_extension_manager.h"
#include "core/input/input.h"
#include "core/io/config_file.h"
#include "core/io/file_access.h"
@@ -708,6 +709,7 @@ void EditorNode::_notification(int p_what) {
p->set_item_icon(p->get_item_index(HELP_DOCS), gui_base->get_theme_icon("Instance", "EditorIcons"));
p->set_item_icon(p->get_item_index(HELP_QA), gui_base->get_theme_icon("Instance", "EditorIcons"));
p->set_item_icon(p->get_item_index(HELP_REPORT_A_BUG), gui_base->get_theme_icon("Instance", "EditorIcons"));
+ p->set_item_icon(p->get_item_index(HELP_SUGGEST_A_FEATURE), gui_base->get_theme_icon("Instance", "EditorIcons"));
p->set_item_icon(p->get_item_index(HELP_SEND_DOCS_FEEDBACK), gui_base->get_theme_icon("Instance", "EditorIcons"));
p->set_item_icon(p->get_item_index(HELP_COMMUNITY), gui_base->get_theme_icon("Instance", "EditorIcons"));
p->set_item_icon(p->get_item_index(HELP_ABOUT), gui_base->get_theme_icon("Godot", "EditorIcons"));
@@ -1243,7 +1245,7 @@ void EditorNode::_get_scene_metadata(const String &p_file) {
String path = EditorSettings::get_singleton()->get_project_settings_dir().plus_file(p_file.get_file() + "-editstate-" + p_file.md5_text() + ".cfg");
Ref<ConfigFile> cf;
- cf.instance();
+ cf.instantiate();
Error err = cf->load(path);
if (err != OK || !cf->has_section("editor_states")) {
@@ -1277,7 +1279,7 @@ void EditorNode::_set_scene_metadata(const String &p_file, int p_idx) {
String path = EditorSettings::get_singleton()->get_project_settings_dir().plus_file(p_file.get_file() + "-editstate-" + p_file.md5_text() + ".cfg");
Ref<ConfigFile> cf;
- cf.instance();
+ cf.instantiate();
Dictionary md;
@@ -1422,7 +1424,7 @@ void EditorNode::_save_scene_with_preview(String p_file, int p_idx) {
// We cannot fallback on the 2D editor, because it may not have been used yet,
// which would result in an invalid texture.
if (c3d == 0 && c2d == 0) {
- img.instance();
+ img.instantiate();
img->create(1, 1, false, Image::FORMAT_RGB8);
} else if (c3d < c2d) {
Ref<ViewportTexture> viewport_texture = scene_root->get_texture();
@@ -1607,16 +1609,16 @@ void EditorNode::_save_scene(String p_file, int idx) {
if (ResourceCache::has(p_file)) {
// something may be referencing this resource and we are good with that.
// we must update it, but also let the previous scene state go, as
- // old version still work for referencing changes in instanced or inherited scenes
+ // old version still work for referencing changes in instantiated or inherited scenes
sdata = Ref<PackedScene>(Object::cast_to<PackedScene>(ResourceCache::get(p_file)));
if (sdata.is_valid()) {
sdata->recreate_state();
} else {
- sdata.instance();
+ sdata.instantiate();
}
} else {
- sdata.instance();
+ sdata.instantiate();
}
Error err = sdata->pack(scene);
@@ -1625,15 +1627,6 @@ void EditorNode::_save_scene(String p_file, int idx) {
return;
}
- // force creation of node path cache
- // (hacky but needed for the tree to update properly)
- Node *dummy_scene = sdata->instance(PackedScene::GEN_EDIT_STATE_INSTANCE);
- if (!dummy_scene) {
- show_accept(TTR("Couldn't save scene. Likely dependencies (instances or inheritance) couldn't be satisfied."), TTR("OK"));
- return;
- }
- memdelete(dummy_scene);
-
int flg = 0;
if (EditorSettings::get_singleton()->get("filesystem/on_save/compress_binary_resources")) {
flg |= ResourceSaver::FLAG_COMPRESS;
@@ -1849,11 +1842,11 @@ void EditorNode::_dialog_action(String p_file) {
}
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Error err = config->load(EditorSettings::get_singleton()->get_editor_layouts_config());
if (err == ERR_FILE_CANT_OPEN || err == ERR_FILE_NOT_FOUND) {
- config.instance(); // new config
+ config.instantiate(); // new config
} else if (err != OK) {
show_warning(TTR("An error occurred while trying to save the editor layout.\nMake sure the editor's user data path is writable."));
return;
@@ -1877,7 +1870,7 @@ void EditorNode::_dialog_action(String p_file) {
}
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Error err = config->load(EditorSettings::get_singleton()->get_editor_layouts_config());
if (err != OK || !config->has_section(p_file)) {
@@ -2082,7 +2075,7 @@ void EditorNode::_edit_current() {
editable_warning = TTR("This resource belongs to a scene that was imported, so it's not editable.\nPlease read the documentation relevant to importing scenes to better understand this workflow.");
} else {
if ((!get_edited_scene() || get_edited_scene()->get_filename() != base_path) && ResourceLoader::get_resource_type(base_path) == "PackedScene") {
- editable_warning = TTR("This resource belongs to a scene that was instanced or inherited.\nChanges to it won't be kept when saving the current scene.");
+ editable_warning = TTR("This resource belongs to a scene that was instantiated or inherited.\nChanges to it won't be kept when saving the current scene.");
}
}
} else if (current_res->get_path().is_resource_file()) {
@@ -2804,6 +2797,9 @@ void EditorNode::_menu_option_confirm(int p_option, bool p_confirmed) {
case HELP_REPORT_A_BUG: {
OS::get_singleton()->shell_open("https://github.com/godotengine/godot/issues");
} break;
+ case HELP_SUGGEST_A_FEATURE: {
+ OS::get_singleton()->shell_open("https://github.com/godotengine/godot-proposals#readme");
+ } break;
case HELP_SEND_DOCS_FEEDBACK: {
OS::get_singleton()->shell_open("https://github.com/godotengine/godot-docs/issues");
} break;
@@ -3144,7 +3140,7 @@ void EditorNode::set_addon_plugin_enabled(const String &p_addon, bool p_enabled,
}
Ref<ConfigFile> cf;
- cf.instance();
+ cf.instantiate();
if (!DirAccess::exists(p_addon.get_base_dir())) {
_remove_plugin_from_enabled(p_addon);
WARN_PRINT("Addon '" + p_addon + "' failed to load. No directory found. Removing from enabled plugins.");
@@ -3525,7 +3521,7 @@ Error EditorNode::load_scene(const String &p_scene, bool p_ignore_broken_deps, b
sdata->set_path(lpath, true); //take over path
}
- Node *new_scene = sdata->instance(PackedScene::GEN_EDIT_STATE_MAIN);
+ Node *new_scene = sdata->instantiate(PackedScene::GEN_EDIT_STATE_MAIN);
if (!new_scene) {
sdata.unref();
@@ -3589,11 +3585,11 @@ void EditorNode::open_request(const String &p_path) {
}
void EditorNode::request_instance_scene(const String &p_path) {
- scene_tree_dock->instance(p_path);
+ scene_tree_dock->instantiate(p_path);
}
-void EditorNode::request_instance_scenes(const Vector<String> &p_files) {
- scene_tree_dock->instance_scenes(p_files);
+void EditorNode::request_instantiate_scenes(const Vector<String> &p_files) {
+ scene_tree_dock->instantiate_scenes(p_files);
}
ImportDock *EditorNode::get_import_dock() {
@@ -3617,8 +3613,8 @@ void EditorNode::_inherit_request(String p_file) {
_dialog_action(p_file);
}
-void EditorNode::_instance_request(const Vector<String> &p_files) {
- request_instance_scenes(p_files);
+void EditorNode::_instantiate_request(const Vector<String> &p_files) {
+ request_instantiate_scenes(p_files);
}
void EditorNode::_close_messages() {
@@ -3780,9 +3776,12 @@ void EditorNode::register_editor_types() {
ClassDB::register_class<EditorScenePostImport>();
//ClassDB::register_type<EditorImportExport>();
ClassDB::register_class<EditorDebuggerPlugin>();
+
+ NativeExtensionManager::get_singleton()->initialize_extensions(NativeExtension::INITIALIZATION_LEVEL_EDITOR);
}
void EditorNode::unregister_editor_types() {
+ NativeExtensionManager::get_singleton()->deinitialize_extensions(NativeExtension::INITIALIZATION_LEVEL_EDITOR);
_init_callbacks.clear();
if (EditorPaths::get_singleton()) {
EditorPaths::free();
@@ -4352,7 +4351,7 @@ void EditorNode::_save_docks() {
return; //scanning, do not touch docks
}
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
// Load and amend existing config if it exists.
config->load(EditorSettings::get_singleton()->get_project_settings_dir().plus_file("editor_layout.cfg"));
@@ -4417,7 +4416,7 @@ void EditorNode::_dock_split_dragged(int ofs) {
void EditorNode::_load_docks() {
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Error err = config->load(EditorSettings::get_singleton()->get_project_settings_dir().plus_file("editor_layout.cfg"));
if (err != OK) {
//no config
@@ -4650,7 +4649,7 @@ bool EditorNode::has_scenes_in_session() {
return false;
}
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Error err = config->load(EditorSettings::get_singleton()->get_project_settings_dir().plus_file("editor_layout.cfg"));
if (err != OK) {
return false;
@@ -4743,7 +4742,7 @@ void EditorNode::_update_layouts_menu() {
editor_layouts->add_shortcut(ED_SHORTCUT("layout/default", TTR("Default")), SETTINGS_LAYOUT_DEFAULT);
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Error err = config->load(EditorSettings::get_singleton()->get_editor_layouts_config());
if (err != OK) {
return; //no config
@@ -4786,7 +4785,7 @@ void EditorNode::_layout_menu_option(int p_id) {
} break;
default: {
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Error err = config->load(EditorSettings::get_singleton()->get_editor_layouts_config());
if (err != OK) {
return; //no config
@@ -5337,7 +5336,7 @@ void EditorNode::reload_scene(const String &p_path) {
if (scene_idx == -1) {
if (get_edited_scene()) {
- //scene is not open, so at it might be instanced. We'll refresh the whole scene later.
+ //scene is not open, so at it might be instantiated. We'll refresh the whole scene later.
editor_data.get_undo_redo().clear_history();
}
return;
@@ -5734,87 +5733,87 @@ EditorNode::EditorNode() {
{ //register importers at the beginning, so dialogs are created with the right extensions
Ref<ResourceImporterTexture> import_texture;
- import_texture.instance();
+ import_texture.instantiate();
ResourceFormatImporter::get_singleton()->add_importer(import_texture);
Ref<ResourceImporterLayeredTexture> import_cubemap;
- import_cubemap.instance();
+ import_cubemap.instantiate();
import_cubemap->set_mode(ResourceImporterLayeredTexture::MODE_CUBEMAP);
ResourceFormatImporter::get_singleton()->add_importer(import_cubemap);
Ref<ResourceImporterLayeredTexture> import_array;
- import_array.instance();
+ import_array.instantiate();
import_array->set_mode(ResourceImporterLayeredTexture::MODE_2D_ARRAY);
ResourceFormatImporter::get_singleton()->add_importer(import_array);
Ref<ResourceImporterLayeredTexture> import_cubemap_array;
- import_cubemap_array.instance();
+ import_cubemap_array.instantiate();
import_cubemap_array->set_mode(ResourceImporterLayeredTexture::MODE_CUBEMAP_ARRAY);
ResourceFormatImporter::get_singleton()->add_importer(import_cubemap_array);
Ref<ResourceImporterLayeredTexture> import_3d;
- import_3d.instance();
+ import_3d.instantiate();
import_3d->set_mode(ResourceImporterLayeredTexture::MODE_3D);
ResourceFormatImporter::get_singleton()->add_importer(import_3d);
Ref<ResourceImporterImage> import_image;
- import_image.instance();
+ import_image.instantiate();
ResourceFormatImporter::get_singleton()->add_importer(import_image);
Ref<ResourceImporterTextureAtlas> import_texture_atlas;
- import_texture_atlas.instance();
+ import_texture_atlas.instantiate();
ResourceFormatImporter::get_singleton()->add_importer(import_texture_atlas);
Ref<ResourceImporterCSVTranslation> import_csv_translation;
- import_csv_translation.instance();
+ import_csv_translation.instantiate();
ResourceFormatImporter::get_singleton()->add_importer(import_csv_translation);
Ref<ResourceImporterWAV> import_wav;
- import_wav.instance();
+ import_wav.instantiate();
ResourceFormatImporter::get_singleton()->add_importer(import_wav);
Ref<ResourceImporterOBJ> import_obj;
- import_obj.instance();
+ import_obj.instantiate();
ResourceFormatImporter::get_singleton()->add_importer(import_obj);
Ref<ResourceImporterShaderFile> import_shader_file;
- import_shader_file.instance();
+ import_shader_file.instantiate();
ResourceFormatImporter::get_singleton()->add_importer(import_shader_file);
Ref<ResourceImporterScene> import_scene;
- import_scene.instance();
+ import_scene.instantiate();
ResourceFormatImporter::get_singleton()->add_importer(import_scene);
{
Ref<EditorSceneImporterCollada> import_collada;
- import_collada.instance();
+ import_collada.instantiate();
import_scene->add_importer(import_collada);
Ref<EditorOBJImporter> import_obj2;
- import_obj2.instance();
+ import_obj2.instantiate();
import_scene->add_importer(import_obj2);
Ref<EditorSceneImporterESCN> import_escn;
- import_escn.instance();
+ import_escn.instantiate();
import_scene->add_importer(import_escn);
}
Ref<ResourceImporterBitMap> import_bitmap;
- import_bitmap.instance();
+ import_bitmap.instantiate();
ResourceFormatImporter::get_singleton()->add_importer(import_bitmap);
}
{
Ref<EditorInspectorDefaultPlugin> eidp;
- eidp.instance();
+ eidp.instantiate();
EditorInspector::add_inspector_plugin(eidp);
Ref<EditorInspectorRootMotionPlugin> rmp;
- rmp.instance();
+ rmp.instantiate();
EditorInspector::add_inspector_plugin(rmp);
Ref<EditorInspectorShaderModePlugin> smp;
- smp.instance();
+ smp.instantiate();
EditorInspector::add_inspector_plugin(smp);
}
@@ -6117,7 +6116,8 @@ EditorNode::EditorNode() {
scene_root_parent->set_v_size_flags(Control::SIZE_EXPAND_FILL);
scene_root = memnew(SubViewport);
- //scene_root->set_usage(Viewport::USAGE_2D); canvas BG mode prevents usage of this as 2D
+ scene_root->set_embed_subwindows_hint(true);
+ scene_root->set_disable_3d(true);
RenderingServer::get_singleton()->viewport_set_hide_scenario(scene_root->get_viewport_rid(), true);
scene_root->set_disable_input(true);
@@ -6366,6 +6366,7 @@ EditorNode::EditorNode() {
p->add_icon_shortcut(gui_base->get_theme_icon("Instance", "EditorIcons"), ED_SHORTCUT("editor/online_docs", TTR("Online Documentation")), HELP_DOCS);
p->add_icon_shortcut(gui_base->get_theme_icon("Instance", "EditorIcons"), ED_SHORTCUT("editor/q&a", TTR("Questions & Answers")), HELP_QA);
p->add_icon_shortcut(gui_base->get_theme_icon("Instance", "EditorIcons"), ED_SHORTCUT("editor/report_a_bug", TTR("Report a Bug")), HELP_REPORT_A_BUG);
+ p->add_icon_shortcut(gui_base->get_theme_icon("Instance", "EditorIcons"), ED_SHORTCUT("editor/suggest_a_feature", TTR("Suggest a Feature")), HELP_SUGGEST_A_FEATURE);
p->add_icon_shortcut(gui_base->get_theme_icon("Instance", "EditorIcons"), ED_SHORTCUT("editor/send_docs_feedback", TTR("Send Docs Feedback")), HELP_SEND_DOCS_FEEDBACK);
p->add_icon_shortcut(gui_base->get_theme_icon("Instance", "EditorIcons"), ED_SHORTCUT("editor/community", TTR("Community")), HELP_COMMUNITY);
p->add_separator();
@@ -6517,7 +6518,7 @@ EditorNode::EditorNode() {
filesystem_dock = memnew(FileSystemDock(this));
filesystem_dock->connect("inherit", callable_mp(this, &EditorNode::_inherit_request));
- filesystem_dock->connect("instance", callable_mp(this, &EditorNode::_instance_request));
+ filesystem_dock->connect("instance", callable_mp(this, &EditorNode::_instantiate_request));
filesystem_dock->connect("display_mode_changed", callable_mp(this, &EditorNode::_save_docks));
// Scene: Top left
@@ -6557,7 +6558,7 @@ EditorNode::EditorNode() {
const String docks_section = "docks";
overridden_default_layout = -1;
- default_layout.instance();
+ default_layout.instantiate();
// Dock numbers are based on DockSlot enum value + 1
default_layout->set_value(docks_section, "dock_3", "Scene,Import");
default_layout->set_value(docks_section, "dock_4", "FileSystem");
@@ -6838,31 +6839,31 @@ EditorNode::EditorNode() {
{
Ref<StandardMaterial3DConversionPlugin> spatial_mat_convert;
- spatial_mat_convert.instance();
+ spatial_mat_convert.instantiate();
resource_conversion_plugins.push_back(spatial_mat_convert);
Ref<CanvasItemMaterialConversionPlugin> canvas_item_mat_convert;
- canvas_item_mat_convert.instance();
+ canvas_item_mat_convert.instantiate();
resource_conversion_plugins.push_back(canvas_item_mat_convert);
Ref<ParticlesMaterialConversionPlugin> particles_mat_convert;
- particles_mat_convert.instance();
+ particles_mat_convert.instantiate();
resource_conversion_plugins.push_back(particles_mat_convert);
Ref<ProceduralSkyMaterialConversionPlugin> procedural_sky_mat_convert;
- procedural_sky_mat_convert.instance();
+ procedural_sky_mat_convert.instantiate();
resource_conversion_plugins.push_back(procedural_sky_mat_convert);
Ref<PanoramaSkyMaterialConversionPlugin> panorama_sky_mat_convert;
- panorama_sky_mat_convert.instance();
+ panorama_sky_mat_convert.instantiate();
resource_conversion_plugins.push_back(panorama_sky_mat_convert);
Ref<PhysicalSkyMaterialConversionPlugin> physical_sky_mat_convert;
- physical_sky_mat_convert.instance();
+ physical_sky_mat_convert.instantiate();
resource_conversion_plugins.push_back(physical_sky_mat_convert);
Ref<VisualShaderConversionPlugin> vshader_convert;
- vshader_convert.instance();
+ vshader_convert.instantiate();
resource_conversion_plugins.push_back(vshader_convert);
}
update_spinner_step_msec = OS::get_singleton()->get_ticks_msec();
@@ -6875,12 +6876,12 @@ EditorNode::EditorNode() {
editor_plugins_force_input_forwarding = memnew(EditorPluginList);
Ref<EditorExportTextSceneToBinaryPlugin> export_text_to_binary_plugin;
- export_text_to_binary_plugin.instance();
+ export_text_to_binary_plugin.instantiate();
EditorExport::get_singleton()->add_export_plugin(export_text_to_binary_plugin);
Ref<PackedSceneEditorTranslationParserPlugin> packed_scene_translation_parser_plugin;
- packed_scene_translation_parser_plugin.instance();
+ packed_scene_translation_parser_plugin.instantiate();
EditorTranslationParser::get_singleton()->add_parser(packed_scene_translation_parser_plugin, EditorTranslationParser::STANDARD);
_edit_current();
@@ -6901,7 +6902,7 @@ EditorNode::EditorNode() {
saved_version = 1;
unsaved_cache = true;
- _last_instanced_scene = nullptr;
+ _last_instantiated_scene = nullptr;
quick_open = memnew(EditorQuickOpen);
gui_base->add_child(quick_open);
diff --git a/editor/editor_node.h b/editor/editor_node.h
index 037ed263c5..dcb6ad6e94 100644
--- a/editor/editor_node.h
+++ b/editor/editor_node.h
@@ -194,6 +194,7 @@ private:
HELP_DOCS,
HELP_QA,
HELP_REPORT_A_BUG,
+ HELP_SUGGEST_A_FEATURE,
HELP_SEND_DOCS_FEEDBACK,
HELP_COMMUNITY,
HELP_ABOUT,
@@ -332,7 +333,7 @@ private:
EditorNativeShaderSourceVisualizer *native_shader_source_visualizer;
String defer_load_scene;
- Node *_last_instanced_scene;
+ Node *_last_instantiated_scene;
EditorLog *log;
CenterContainer *tabs_center;
@@ -491,7 +492,7 @@ private:
void _discard_changes(const String &p_str = String());
void _inherit_request(String p_file);
- void _instance_request(const Vector<String> &p_files);
+ void _instantiate_request(const Vector<String> &p_files);
void _display_top_editors(bool p_display);
void _set_top_editors(Vector<EditorPlugin *> p_editor_plugins_over);
@@ -770,7 +771,7 @@ public:
static VSplitContainer *get_top_split() { return singleton->top_split; }
void request_instance_scene(const String &p_path);
- void request_instance_scenes(const Vector<String> &p_files);
+ void request_instantiate_scenes(const Vector<String> &p_files);
FileSystemDock *get_filesystem_dock();
ImportDock *get_import_dock();
SceneTreeDock *get_scene_tree_dock();
diff --git a/editor/editor_plugin_settings.cpp b/editor/editor_plugin_settings.cpp
index 1db24bb908..62fbad7bcf 100644
--- a/editor/editor_plugin_settings.cpp
+++ b/editor/editor_plugin_settings.cpp
@@ -57,7 +57,7 @@ void EditorPluginSettings::update_plugins() {
for (int i = 0; i < plugins.size(); i++) {
Ref<ConfigFile> cf;
- cf.instance();
+ cf.instantiate();
const String path = plugins[i];
Error err2 = cf->load(path);
@@ -216,10 +216,10 @@ EditorPluginSettings::EditorPluginSettings() {
plugin_list->set_column_expand(2, false);
plugin_list->set_column_expand(3, false);
plugin_list->set_column_expand(4, false);
- plugin_list->set_column_min_width(1, 100 * EDSCALE);
- plugin_list->set_column_min_width(2, 250 * EDSCALE);
- plugin_list->set_column_min_width(3, 80 * EDSCALE);
- plugin_list->set_column_min_width(4, 40 * EDSCALE);
+ plugin_list->set_column_custom_minimum_width(1, 100 * EDSCALE);
+ plugin_list->set_column_custom_minimum_width(2, 250 * EDSCALE);
+ plugin_list->set_column_custom_minimum_width(3, 80 * EDSCALE);
+ plugin_list->set_column_custom_minimum_width(4, 40 * EDSCALE);
plugin_list->set_hide_root(true);
plugin_list->connect("item_edited", callable_mp(this, &EditorPluginSettings::_plugin_activity_changed));
diff --git a/editor/editor_properties.cpp b/editor/editor_properties.cpp
index 3feeaec070..8f716a2499 100644
--- a/editor/editor_properties.cpp
+++ b/editor/editor_properties.cpp
@@ -491,6 +491,7 @@ void EditorPropertyEnum::update_property() {
}
void EditorPropertyEnum::setup(const Vector<String> &p_options) {
+ options->clear();
int64_t current_val = 0;
for (int i = 0; i < p_options.size(); i++) {
Vector<String> text_split = p_options[i].split(":");
@@ -892,11 +893,17 @@ void EditorPropertyFloat::_value_changed(double val) {
return;
}
+ if (angle_in_radians) {
+ val = Math::deg2rad(val);
+ }
emit_changed(get_edited_property(), val);
}
void EditorPropertyFloat::update_property() {
double val = get_edited_object()->get(get_edited_property());
+ if (angle_in_radians) {
+ val = Math::rad2deg(val);
+ }
setting = true;
spin->set_value(val);
setting = false;
@@ -905,7 +912,8 @@ void EditorPropertyFloat::update_property() {
void EditorPropertyFloat::_bind_methods() {
}
-void EditorPropertyFloat::setup(double p_min, double p_max, double p_step, bool p_no_slider, bool p_exp_range, bool p_greater, bool p_lesser) {
+void EditorPropertyFloat::setup(double p_min, double p_max, double p_step, bool p_no_slider, bool p_exp_range, bool p_greater, bool p_lesser, const String &p_suffix, bool p_angle_in_radians) {
+ angle_in_radians = p_angle_in_radians;
spin->set_min(p_min);
spin->set_max(p_max);
spin->set_step(p_step);
@@ -913,6 +921,7 @@ void EditorPropertyFloat::setup(double p_min, double p_max, double p_step, bool
spin->set_exp_ratio(p_exp_range);
spin->set_allow_greater(p_greater);
spin->set_allow_lesser(p_lesser);
+ spin->set_suffix(p_suffix);
}
EditorPropertyFloat::EditorPropertyFloat() {
@@ -921,7 +930,6 @@ EditorPropertyFloat::EditorPropertyFloat() {
add_child(spin);
add_focusable(spin);
spin->connect("value_changed", callable_mp(this, &EditorPropertyFloat::_value_changed));
- setting = false;
}
///////////////////// EASING /////////////////////////
@@ -1171,7 +1179,7 @@ void EditorPropertyVector2::_notification(int p_what) {
void EditorPropertyVector2::_bind_methods() {
}
-void EditorPropertyVector2::setup(double p_min, double p_max, double p_step, bool p_no_slider) {
+void EditorPropertyVector2::setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix) {
for (int i = 0; i < 2; i++) {
spin[i]->set_min(p_min);
spin[i]->set_max(p_max);
@@ -1179,6 +1187,7 @@ void EditorPropertyVector2::setup(double p_min, double p_max, double p_step, boo
spin[i]->set_hide_slider(p_no_slider);
spin[i]->set_allow_greater(true);
spin[i]->set_allow_lesser(true);
+ spin[i]->set_suffix(p_suffix);
}
}
@@ -1257,7 +1266,7 @@ void EditorPropertyRect2::_notification(int p_what) {
void EditorPropertyRect2::_bind_methods() {
}
-void EditorPropertyRect2::setup(double p_min, double p_max, double p_step, bool p_no_slider) {
+void EditorPropertyRect2::setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix) {
for (int i = 0; i < 4; i++) {
spin[i]->set_min(p_min);
spin[i]->set_max(p_max);
@@ -1265,6 +1274,7 @@ void EditorPropertyRect2::setup(double p_min, double p_max, double p_step, bool
spin[i]->set_hide_slider(p_no_slider);
spin[i]->set_allow_greater(true);
spin[i]->set_allow_lesser(true);
+ spin[i]->set_suffix(p_suffix);
}
}
@@ -1325,6 +1335,11 @@ void EditorPropertyVector3::_value_changed(double val, const String &p_name) {
v3.x = spin[0]->get_value();
v3.y = spin[1]->get_value();
v3.z = spin[2]->get_value();
+ if (angle_in_radians) {
+ v3.x = Math::deg2rad(v3.x);
+ v3.y = Math::deg2rad(v3.y);
+ v3.z = Math::deg2rad(v3.z);
+ }
emit_changed(get_edited_property(), v3, p_name);
}
@@ -1333,6 +1348,11 @@ void EditorPropertyVector3::update_property() {
}
void EditorPropertyVector3::update_using_vector(Vector3 p_vector) {
+ if (angle_in_radians) {
+ p_vector.x = Math::rad2deg(p_vector.x);
+ p_vector.y = Math::rad2deg(p_vector.y);
+ p_vector.z = Math::rad2deg(p_vector.z);
+ }
setting = true;
spin[0]->set_value(p_vector.x);
spin[1]->set_value(p_vector.y);
@@ -1345,6 +1365,12 @@ Vector3 EditorPropertyVector3::get_vector() {
v3.x = spin[0]->get_value();
v3.y = spin[1]->get_value();
v3.z = spin[2]->get_value();
+ if (angle_in_radians) {
+ v3.x = Math::deg2rad(v3.x);
+ v3.y = Math::deg2rad(v3.y);
+ v3.z = Math::deg2rad(v3.z);
+ }
+
return v3;
}
@@ -1362,7 +1388,8 @@ void EditorPropertyVector3::_notification(int p_what) {
void EditorPropertyVector3::_bind_methods() {
}
-void EditorPropertyVector3::setup(double p_min, double p_max, double p_step, bool p_no_slider) {
+void EditorPropertyVector3::setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix, bool p_angle_in_radians) {
+ angle_in_radians = p_angle_in_radians;
for (int i = 0; i < 3; i++) {
spin[i]->set_min(p_min);
spin[i]->set_max(p_max);
@@ -1370,6 +1397,7 @@ void EditorPropertyVector3::setup(double p_min, double p_max, double p_step, boo
spin[i]->set_hide_slider(p_no_slider);
spin[i]->set_allow_greater(true);
spin[i]->set_allow_lesser(true);
+ spin[i]->set_suffix(p_suffix);
}
}
@@ -1406,7 +1434,6 @@ EditorPropertyVector3::EditorPropertyVector3(bool p_force_wide) {
if (!horizontal) {
set_label_reference(spin[0]); //show text and buttons around this
}
- setting = false;
}
///////////////////// VECTOR2i /////////////////////////
@@ -1444,7 +1471,7 @@ void EditorPropertyVector2i::_notification(int p_what) {
void EditorPropertyVector2i::_bind_methods() {
}
-void EditorPropertyVector2i::setup(int p_min, int p_max, bool p_no_slider) {
+void EditorPropertyVector2i::setup(int p_min, int p_max, bool p_no_slider, const String &p_suffix) {
for (int i = 0; i < 2; i++) {
spin[i]->set_min(p_min);
spin[i]->set_max(p_max);
@@ -1452,6 +1479,7 @@ void EditorPropertyVector2i::setup(int p_min, int p_max, bool p_no_slider) {
spin[i]->set_hide_slider(p_no_slider);
spin[i]->set_allow_greater(true);
spin[i]->set_allow_lesser(true);
+ spin[i]->set_suffix(p_suffix);
}
}
@@ -1530,7 +1558,7 @@ void EditorPropertyRect2i::_notification(int p_what) {
void EditorPropertyRect2i::_bind_methods() {
}
-void EditorPropertyRect2i::setup(int p_min, int p_max, bool p_no_slider) {
+void EditorPropertyRect2i::setup(int p_min, int p_max, bool p_no_slider, const String &p_suffix) {
for (int i = 0; i < 4; i++) {
spin[i]->set_min(p_min);
spin[i]->set_max(p_max);
@@ -1538,6 +1566,7 @@ void EditorPropertyRect2i::setup(int p_min, int p_max, bool p_no_slider) {
spin[i]->set_hide_slider(p_no_slider);
spin[i]->set_allow_greater(true);
spin[i]->set_allow_lesser(true);
+ spin[i]->set_suffix(p_suffix);
}
}
@@ -1624,7 +1653,7 @@ void EditorPropertyVector3i::_notification(int p_what) {
void EditorPropertyVector3i::_bind_methods() {
}
-void EditorPropertyVector3i::setup(int p_min, int p_max, bool p_no_slider) {
+void EditorPropertyVector3i::setup(int p_min, int p_max, bool p_no_slider, const String &p_suffix) {
for (int i = 0; i < 3; i++) {
spin[i]->set_min(p_min);
spin[i]->set_max(p_max);
@@ -1632,6 +1661,7 @@ void EditorPropertyVector3i::setup(int p_min, int p_max, bool p_no_slider) {
spin[i]->set_hide_slider(p_no_slider);
spin[i]->set_allow_greater(true);
spin[i]->set_allow_lesser(true);
+ spin[i]->set_suffix(p_suffix);
}
}
@@ -1709,7 +1739,7 @@ void EditorPropertyPlane::_notification(int p_what) {
void EditorPropertyPlane::_bind_methods() {
}
-void EditorPropertyPlane::setup(double p_min, double p_max, double p_step, bool p_no_slider) {
+void EditorPropertyPlane::setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix) {
for (int i = 0; i < 4; i++) {
spin[i]->set_min(p_min);
spin[i]->set_max(p_max);
@@ -1717,6 +1747,7 @@ void EditorPropertyPlane::setup(double p_min, double p_max, double p_step, bool
spin[i]->set_hide_slider(p_no_slider);
spin[i]->set_allow_greater(true);
spin[i]->set_allow_lesser(true);
+ spin[i]->set_suffix(p_suffix);
}
}
@@ -1795,7 +1826,7 @@ void EditorPropertyQuaternion::_notification(int p_what) {
void EditorPropertyQuaternion::_bind_methods() {
}
-void EditorPropertyQuaternion::setup(double p_min, double p_max, double p_step, bool p_no_slider) {
+void EditorPropertyQuaternion::setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix) {
for (int i = 0; i < 4; i++) {
spin[i]->set_min(p_min);
spin[i]->set_max(p_max);
@@ -1803,6 +1834,7 @@ void EditorPropertyQuaternion::setup(double p_min, double p_max, double p_step,
spin[i]->set_hide_slider(p_no_slider);
spin[i]->set_allow_greater(true);
spin[i]->set_allow_lesser(true);
+ spin[i]->set_suffix(p_suffix);
}
}
@@ -1884,7 +1916,7 @@ void EditorPropertyAABB::_notification(int p_what) {
void EditorPropertyAABB::_bind_methods() {
}
-void EditorPropertyAABB::setup(double p_min, double p_max, double p_step, bool p_no_slider) {
+void EditorPropertyAABB::setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix) {
for (int i = 0; i < 6; i++) {
spin[i]->set_min(p_min);
spin[i]->set_max(p_max);
@@ -1892,6 +1924,7 @@ void EditorPropertyAABB::setup(double p_min, double p_max, double p_step, bool p
spin[i]->set_hide_slider(p_no_slider);
spin[i]->set_allow_greater(true);
spin[i]->set_allow_lesser(true);
+ spin[i]->set_suffix(p_suffix);
}
}
@@ -1960,7 +1993,7 @@ void EditorPropertyTransform2D::_notification(int p_what) {
void EditorPropertyTransform2D::_bind_methods() {
}
-void EditorPropertyTransform2D::setup(double p_min, double p_max, double p_step, bool p_no_slider) {
+void EditorPropertyTransform2D::setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix) {
for (int i = 0; i < 6; i++) {
spin[i]->set_min(p_min);
spin[i]->set_max(p_max);
@@ -1968,6 +2001,7 @@ void EditorPropertyTransform2D::setup(double p_min, double p_max, double p_step,
spin[i]->set_hide_slider(p_no_slider);
spin[i]->set_allow_greater(true);
spin[i]->set_allow_lesser(true);
+ spin[i]->set_suffix(p_suffix);
}
}
@@ -2041,7 +2075,7 @@ void EditorPropertyBasis::_notification(int p_what) {
void EditorPropertyBasis::_bind_methods() {
}
-void EditorPropertyBasis::setup(double p_min, double p_max, double p_step, bool p_no_slider) {
+void EditorPropertyBasis::setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix) {
for (int i = 0; i < 9; i++) {
spin[i]->set_min(p_min);
spin[i]->set_max(p_max);
@@ -2049,6 +2083,7 @@ void EditorPropertyBasis::setup(double p_min, double p_max, double p_step, bool
spin[i]->set_hide_slider(p_no_slider);
spin[i]->set_allow_greater(true);
spin[i]->set_allow_lesser(true);
+ spin[i]->set_suffix(p_suffix);
}
}
@@ -2130,7 +2165,7 @@ void EditorPropertyTransform3D::_notification(int p_what) {
void EditorPropertyTransform3D::_bind_methods() {
}
-void EditorPropertyTransform3D::setup(double p_min, double p_max, double p_step, bool p_no_slider) {
+void EditorPropertyTransform3D::setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix) {
for (int i = 0; i < 12; i++) {
spin[i]->set_min(p_min);
spin[i]->set_max(p_max);
@@ -2138,6 +2173,7 @@ void EditorPropertyTransform3D::setup(double p_min, double p_max, double p_step,
spin[i]->set_hide_slider(p_no_slider);
spin[i]->set_allow_greater(true);
spin[i]->set_allow_lesser(true);
+ spin[i]->set_suffix(p_suffix);
}
}
@@ -2535,7 +2571,7 @@ void EditorPropertyResource::_viewport_selected(const NodePath &p_path) {
}
Ref<ViewportTexture> vt;
- vt.instance();
+ vt.instantiate();
vt->set_viewport_path_in_scene(get_tree()->get_edited_scene_root()->get_path_to(to_node));
vt->setup_local_to_scene();
@@ -2699,30 +2735,96 @@ void EditorInspectorDefaultPlugin::parse_begin(Object *p_object) {
}
bool EditorInspectorDefaultPlugin::parse_property(Object *p_object, Variant::Type p_type, const String &p_path, PropertyHint p_hint, const String &p_hint_text, int p_usage, bool p_wide) {
+ Control *editor = EditorInspectorDefaultPlugin::get_editor_for_property(p_object, p_type, p_path, p_hint, p_hint_text, p_usage, p_wide);
+ if (editor) {
+ add_property_editor(p_path, editor);
+ }
+ return false;
+}
+
+void EditorInspectorDefaultPlugin::parse_end() {
+ //do none
+}
+
+struct EditorPropertyRangeHint {
+ bool angle_in_degrees = false;
+ bool greater = true;
+ bool lesser = true;
+ double min = -99999;
+ double max = 99999;
+ double step = 0;
+ String suffix;
+ bool exp_range = false;
+ bool hide_slider = true;
+ bool radians = false;
+};
+
+static EditorPropertyRangeHint _parse_range_hint(PropertyHint p_hint, const String &p_hint_text, double p_default_step) {
+ EditorPropertyRangeHint hint;
+ hint.step = p_default_step;
+ bool degrees = false;
+ if (p_hint == PROPERTY_HINT_RANGE && p_hint_text.get_slice_count(",") >= 2) {
+ hint.greater = false; //if using ranged, assume false by default
+ hint.lesser = false;
+
+ hint.min = p_hint_text.get_slice(",", 0).to_float();
+ hint.max = p_hint_text.get_slice(",", 1).to_float();
+ if (p_hint_text.get_slice_count(",") >= 3) {
+ hint.step = p_hint_text.get_slice(",", 2).to_float();
+ }
+ hint.hide_slider = false;
+ for (int i = 2; i < p_hint_text.get_slice_count(","); i++) {
+ String slice = p_hint_text.get_slice(",", i).strip_edges();
+ if (slice == "radians") {
+ hint.radians = true;
+ } else if (slice == "degrees") {
+ degrees = true;
+ } else if (slice == "or_greater") {
+ hint.greater = true;
+ } else if (slice == "or_lesser") {
+ hint.lesser = true;
+ } else if (slice == "noslider") {
+ hint.hide_slider = true;
+ } else if (slice == "exp") {
+ hint.exp_range = true;
+ } else if (slice.begins_with("suffix:")) {
+ hint.suffix = " " + slice.replace_first("suffix:", "").strip_edges();
+ }
+ }
+ }
+
+ if ((hint.radians || degrees) && hint.suffix == String()) {
+ hint.suffix = U"\u00B0";
+ }
+
+ return hint;
+}
+
+EditorProperty *EditorInspectorDefaultPlugin::get_editor_for_property(Object *p_object, Variant::Type p_type, const String &p_path, PropertyHint p_hint, const String &p_hint_text, int p_usage, bool p_wide) {
double default_float_step = EDITOR_GET("interface/inspector/default_float_step");
switch (p_type) {
// atomic types
case Variant::NIL: {
EditorPropertyNil *editor = memnew(EditorPropertyNil);
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::BOOL: {
EditorPropertyCheck *editor = memnew(EditorPropertyCheck);
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::INT: {
if (p_hint == PROPERTY_HINT_ENUM) {
EditorPropertyEnum *editor = memnew(EditorPropertyEnum);
Vector<String> options = p_hint_text.split(",");
editor->setup(options);
- add_property_editor(p_path, editor);
+ return editor;
} else if (p_hint == PROPERTY_HINT_FLAGS) {
EditorPropertyFlags *editor = memnew(EditorPropertyFlags);
Vector<String> options = p_hint_text.split(",");
editor->setup(options);
- add_property_editor(p_path, editor);
+ return editor;
} else if (p_hint == PROPERTY_HINT_LAYERS_2D_PHYSICS ||
p_hint == PROPERTY_HINT_LAYERS_2D_RENDER ||
@@ -2755,41 +2857,20 @@ bool EditorInspectorDefaultPlugin::parse_property(Object *p_object, Variant::Typ
}
EditorPropertyLayers *editor = memnew(EditorPropertyLayers);
editor->setup(lt);
- add_property_editor(p_path, editor);
+ return editor;
} else if (p_hint == PROPERTY_HINT_OBJECT_ID) {
EditorPropertyObjectID *editor = memnew(EditorPropertyObjectID);
editor->setup(p_hint_text);
- add_property_editor(p_path, editor);
+ return editor;
} else {
EditorPropertyInteger *editor = memnew(EditorPropertyInteger);
- int min = 0, max = 65535, step = 1;
- bool greater = true, lesser = true;
- if (p_hint == PROPERTY_HINT_RANGE && p_hint_text.get_slice_count(",") >= 2) {
- greater = false; //if using ranged, assume false by default
- lesser = false;
- min = p_hint_text.get_slice(",", 0).to_int();
- max = p_hint_text.get_slice(",", 1).to_int();
+ EditorPropertyRangeHint hint = _parse_range_hint(p_hint, p_hint_text, 1);
- if (p_hint_text.get_slice_count(",") >= 3) {
- step = p_hint_text.get_slice(",", 2).to_int();
- }
+ editor->setup(hint.min, hint.max, hint.step, hint.greater, hint.lesser);
- for (int i = 2; i < p_hint_text.get_slice_count(","); i++) {
- String slice = p_hint_text.get_slice(",", i).strip_edges();
- if (slice == "or_greater") {
- greater = true;
- }
- if (slice == "or_lesser") {
- lesser = true;
- }
- }
- }
-
- editor->setup(min, max, step, greater, lesser);
-
- add_property_editor(p_path, editor);
+ return editor;
}
} break;
case Variant::FLOAT: {
@@ -2809,39 +2890,15 @@ bool EditorInspectorDefaultPlugin::parse_property(Object *p_object, Variant::Typ
}
editor->setup(full, flip);
- add_property_editor(p_path, editor);
+ return editor;
} else {
EditorPropertyFloat *editor = memnew(EditorPropertyFloat);
- double min = -65535, max = 65535, step = default_float_step;
- bool hide_slider = true;
- bool exp_range = false;
- bool greater = true, lesser = true;
-
- if ((p_hint == PROPERTY_HINT_RANGE || p_hint == PROPERTY_HINT_EXP_RANGE) && p_hint_text.get_slice_count(",") >= 2) {
- greater = false; //if using ranged, assume false by default
- lesser = false;
- min = p_hint_text.get_slice(",", 0).to_float();
- max = p_hint_text.get_slice(",", 1).to_float();
- if (p_hint_text.get_slice_count(",") >= 3) {
- step = p_hint_text.get_slice(",", 2).to_float();
- }
- hide_slider = false;
- exp_range = p_hint == PROPERTY_HINT_EXP_RANGE;
- for (int i = 2; i < p_hint_text.get_slice_count(","); i++) {
- String slice = p_hint_text.get_slice(",", i).strip_edges();
- if (slice == "or_greater") {
- greater = true;
- }
- if (slice == "or_lesser") {
- lesser = true;
- }
- }
- }
- editor->setup(min, max, step, hide_slider, exp_range, greater, lesser);
+ EditorPropertyRangeHint hint = _parse_range_hint(p_hint, p_hint_text, default_float_step);
+ editor->setup(hint.min, hint.max, hint.step, hint.hide_slider, hint.exp_range, hint.greater, hint.lesser, hint.suffix, hint.radians);
- add_property_editor(p_path, editor);
+ return editor;
}
} break;
case Variant::STRING: {
@@ -2849,14 +2906,14 @@ bool EditorInspectorDefaultPlugin::parse_property(Object *p_object, Variant::Typ
EditorPropertyTextEnum *editor = memnew(EditorPropertyTextEnum);
Vector<String> options = p_hint_text.split(",");
editor->setup(options);
- add_property_editor(p_path, editor);
+ return editor;
} else if (p_hint == PROPERTY_HINT_MULTILINE_TEXT) {
EditorPropertyMultilineText *editor = memnew(EditorPropertyMultilineText);
- add_property_editor(p_path, editor);
+ return editor;
} else if (p_hint == PROPERTY_HINT_TYPE_STRING) {
EditorPropertyClassName *editor = memnew(EditorPropertyClassName);
editor->setup("Object", p_hint_text);
- add_property_editor(p_path, editor);
+ return editor;
} else if (p_hint == PROPERTY_HINT_DIR || p_hint == PROPERTY_HINT_FILE || p_hint == PROPERTY_HINT_SAVE_FILE || p_hint == PROPERTY_HINT_GLOBAL_DIR || p_hint == PROPERTY_HINT_GLOBAL_FILE) {
Vector<String> extensions = p_hint_text.split(",");
bool global = p_hint == PROPERTY_HINT_GLOBAL_DIR || p_hint == PROPERTY_HINT_GLOBAL_FILE;
@@ -2867,7 +2924,7 @@ bool EditorInspectorDefaultPlugin::parse_property(Object *p_object, Variant::Typ
if (save) {
editor->set_save_mode();
}
- add_property_editor(p_path, editor);
+ return editor;
} else if (p_hint == PROPERTY_HINT_METHOD_OF_VARIANT_TYPE ||
p_hint == PROPERTY_HINT_METHOD_OF_BASE_TYPE ||
p_hint == PROPERTY_HINT_METHOD_OF_INSTANCE ||
@@ -2905,14 +2962,14 @@ bool EditorInspectorDefaultPlugin::parse_property(Object *p_object, Variant::Typ
}
}
editor->setup(type, p_hint_text);
- add_property_editor(p_path, editor);
+ return editor;
} else {
EditorPropertyText *editor = memnew(EditorPropertyText);
if (p_hint == PROPERTY_HINT_PLACEHOLDER_TEXT) {
editor->set_placeholder(p_hint_text);
}
- add_property_editor(p_path, editor);
+ return editor;
}
} break;
@@ -2920,204 +2977,82 @@ bool EditorInspectorDefaultPlugin::parse_property(Object *p_object, Variant::Typ
case Variant::VECTOR2: {
EditorPropertyVector2 *editor = memnew(EditorPropertyVector2(p_wide));
- double min = -65535, max = 65535, step = default_float_step;
- bool hide_slider = true;
-
- if (p_hint == PROPERTY_HINT_RANGE && p_hint_text.get_slice_count(",") >= 2) {
- min = p_hint_text.get_slice(",", 0).to_float();
- max = p_hint_text.get_slice(",", 1).to_float();
- if (p_hint_text.get_slice_count(",") >= 3) {
- step = p_hint_text.get_slice(",", 2).to_float();
- }
- hide_slider = false;
- }
- editor->setup(min, max, step, hide_slider);
- add_property_editor(p_path, editor);
+ EditorPropertyRangeHint hint = _parse_range_hint(p_hint, p_hint_text, default_float_step);
+ editor->setup(hint.min, hint.max, hint.step, hint.hide_slider, hint.suffix);
+ return editor;
} break;
case Variant::VECTOR2I: {
EditorPropertyVector2i *editor = memnew(EditorPropertyVector2i(p_wide));
- int min = -65535, max = 65535;
- bool hide_slider = true;
-
- if (p_hint == PROPERTY_HINT_RANGE && p_hint_text.get_slice_count(",") >= 2) {
- min = p_hint_text.get_slice(",", 0).to_float();
- max = p_hint_text.get_slice(",", 1).to_float();
- hide_slider = false;
- }
-
- editor->setup(min, max, hide_slider);
- add_property_editor(p_path, editor);
+ EditorPropertyRangeHint hint = _parse_range_hint(p_hint, p_hint_text, 1);
+ editor->setup(hint.min, hint.max, hint.hide_slider, hint.suffix);
+ return editor;
} break;
case Variant::RECT2: {
EditorPropertyRect2 *editor = memnew(EditorPropertyRect2(p_wide));
- double min = -65535, max = 65535, step = default_float_step;
- bool hide_slider = true;
-
- if (p_hint == PROPERTY_HINT_RANGE && p_hint_text.get_slice_count(",") >= 2) {
- min = p_hint_text.get_slice(",", 0).to_float();
- max = p_hint_text.get_slice(",", 1).to_float();
- if (p_hint_text.get_slice_count(",") >= 3) {
- step = p_hint_text.get_slice(",", 2).to_float();
- }
- hide_slider = false;
- }
-
- editor->setup(min, max, step, hide_slider);
- add_property_editor(p_path, editor);
+ EditorPropertyRangeHint hint = _parse_range_hint(p_hint, p_hint_text, default_float_step);
+ editor->setup(hint.min, hint.max, hint.step, hint.hide_slider, hint.suffix);
+ return editor;
} break;
case Variant::RECT2I: {
EditorPropertyRect2i *editor = memnew(EditorPropertyRect2i(p_wide));
- int min = -65535, max = 65535;
- bool hide_slider = true;
-
- if (p_hint == PROPERTY_HINT_RANGE && p_hint_text.get_slice_count(",") >= 2) {
- min = p_hint_text.get_slice(",", 0).to_float();
- max = p_hint_text.get_slice(",", 1).to_float();
- hide_slider = false;
- }
+ EditorPropertyRangeHint hint = _parse_range_hint(p_hint, p_hint_text, 1);
+ editor->setup(hint.min, hint.max, hint.hide_slider, hint.suffix);
- editor->setup(min, max, hide_slider);
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::VECTOR3: {
EditorPropertyVector3 *editor = memnew(EditorPropertyVector3(p_wide));
- double min = -65535, max = 65535, step = default_float_step;
- bool hide_slider = true;
-
- if (p_hint == PROPERTY_HINT_RANGE && p_hint_text.get_slice_count(",") >= 2) {
- min = p_hint_text.get_slice(",", 0).to_float();
- max = p_hint_text.get_slice(",", 1).to_float();
- if (p_hint_text.get_slice_count(",") >= 3) {
- step = p_hint_text.get_slice(",", 2).to_float();
- }
- hide_slider = false;
- }
-
- editor->setup(min, max, step, hide_slider);
- add_property_editor(p_path, editor);
+ EditorPropertyRangeHint hint = _parse_range_hint(p_hint, p_hint_text, default_float_step);
+ editor->setup(hint.min, hint.max, hint.step, hint.hide_slider, hint.suffix, hint.radians);
+ return editor;
} break;
case Variant::VECTOR3I: {
EditorPropertyVector3i *editor = memnew(EditorPropertyVector3i(p_wide));
- int min = -65535, max = 65535;
- bool hide_slider = true;
-
- if (p_hint == PROPERTY_HINT_RANGE && p_hint_text.get_slice_count(",") >= 2) {
- min = p_hint_text.get_slice(",", 0).to_float();
- max = p_hint_text.get_slice(",", 1).to_float();
-
- hide_slider = false;
- }
-
- editor->setup(min, max, hide_slider);
- add_property_editor(p_path, editor);
+ EditorPropertyRangeHint hint = _parse_range_hint(p_hint, p_hint_text, 1);
+ editor->setup(hint.min, hint.max, hint.hide_slider, hint.suffix);
+ return editor;
} break;
case Variant::TRANSFORM2D: {
EditorPropertyTransform2D *editor = memnew(EditorPropertyTransform2D);
- double min = -65535, max = 65535, step = default_float_step;
- bool hide_slider = true;
-
- if (p_hint == PROPERTY_HINT_RANGE && p_hint_text.get_slice_count(",") >= 2) {
- min = p_hint_text.get_slice(",", 0).to_float();
- max = p_hint_text.get_slice(",", 1).to_float();
- if (p_hint_text.get_slice_count(",") >= 3) {
- step = p_hint_text.get_slice(",", 2).to_float();
- }
- hide_slider = false;
- }
-
- editor->setup(min, max, step, hide_slider);
- add_property_editor(p_path, editor);
+ EditorPropertyRangeHint hint = _parse_range_hint(p_hint, p_hint_text, default_float_step);
+ editor->setup(hint.min, hint.max, hint.step, hint.hide_slider, hint.suffix);
+ return editor;
} break;
case Variant::PLANE: {
EditorPropertyPlane *editor = memnew(EditorPropertyPlane(p_wide));
- double min = -65535, max = 65535, step = default_float_step;
- bool hide_slider = true;
-
- if (p_hint == PROPERTY_HINT_RANGE && p_hint_text.get_slice_count(",") >= 2) {
- min = p_hint_text.get_slice(",", 0).to_float();
- max = p_hint_text.get_slice(",", 1).to_float();
- if (p_hint_text.get_slice_count(",") >= 3) {
- step = p_hint_text.get_slice(",", 2).to_float();
- }
- hide_slider = false;
- }
-
- editor->setup(min, max, step, hide_slider);
- add_property_editor(p_path, editor);
+ EditorPropertyRangeHint hint = _parse_range_hint(p_hint, p_hint_text, default_float_step);
+ editor->setup(hint.min, hint.max, hint.step, hint.hide_slider, hint.suffix);
+ return editor;
} break;
case Variant::QUATERNION: {
EditorPropertyQuaternion *editor = memnew(EditorPropertyQuaternion);
- double min = -65535, max = 65535, step = default_float_step;
- bool hide_slider = true;
-
- if (p_hint == PROPERTY_HINT_RANGE && p_hint_text.get_slice_count(",") >= 2) {
- min = p_hint_text.get_slice(",", 0).to_float();
- max = p_hint_text.get_slice(",", 1).to_float();
- if (p_hint_text.get_slice_count(",") >= 3) {
- step = p_hint_text.get_slice(",", 2).to_float();
- }
- hide_slider = false;
- }
-
- editor->setup(min, max, step, hide_slider);
- add_property_editor(p_path, editor);
+ EditorPropertyRangeHint hint = _parse_range_hint(p_hint, p_hint_text, default_float_step);
+ editor->setup(hint.min, hint.max, hint.step, hint.hide_slider, hint.suffix);
+ return editor;
} break;
case Variant::AABB: {
EditorPropertyAABB *editor = memnew(EditorPropertyAABB);
- double min = -65535, max = 65535, step = default_float_step;
- bool hide_slider = true;
-
- if (p_hint == PROPERTY_HINT_RANGE && p_hint_text.get_slice_count(",") >= 2) {
- min = p_hint_text.get_slice(",", 0).to_float();
- max = p_hint_text.get_slice(",", 1).to_float();
- if (p_hint_text.get_slice_count(",") >= 3) {
- step = p_hint_text.get_slice(",", 2).to_float();
- }
- hide_slider = false;
- }
-
- editor->setup(min, max, step, hide_slider);
- add_property_editor(p_path, editor);
+ EditorPropertyRangeHint hint = _parse_range_hint(p_hint, p_hint_text, default_float_step);
+ editor->setup(hint.min, hint.max, hint.step, hint.hide_slider, hint.suffix);
+ return editor;
} break;
case Variant::BASIS: {
EditorPropertyBasis *editor = memnew(EditorPropertyBasis);
- double min = -65535, max = 65535, step = default_float_step;
- bool hide_slider = true;
-
- if (p_hint == PROPERTY_HINT_RANGE && p_hint_text.get_slice_count(",") >= 2) {
- min = p_hint_text.get_slice(",", 0).to_float();
- max = p_hint_text.get_slice(",", 1).to_float();
- if (p_hint_text.get_slice_count(",") >= 3) {
- step = p_hint_text.get_slice(",", 2).to_float();
- }
- hide_slider = false;
- }
-
- editor->setup(min, max, step, hide_slider);
- add_property_editor(p_path, editor);
+ EditorPropertyRangeHint hint = _parse_range_hint(p_hint, p_hint_text, default_float_step);
+ editor->setup(hint.min, hint.max, hint.step, hint.hide_slider, hint.suffix);
+ return editor;
} break;
case Variant::TRANSFORM3D: {
EditorPropertyTransform3D *editor = memnew(EditorPropertyTransform3D);
- double min = -65535, max = 65535, step = default_float_step;
- bool hide_slider = true;
-
- if (p_hint == PROPERTY_HINT_RANGE && p_hint_text.get_slice_count(",") >= 2) {
- min = p_hint_text.get_slice(",", 0).to_float();
- max = p_hint_text.get_slice(",", 1).to_float();
- if (p_hint_text.get_slice_count(",") >= 3) {
- step = p_hint_text.get_slice(",", 2).to_float();
- }
- hide_slider = false;
- }
-
- editor->setup(min, max, step, hide_slider);
- add_property_editor(p_path, editor);
+ EditorPropertyRangeHint hint = _parse_range_hint(p_hint, p_hint_text, default_float_step);
+ editor->setup(hint.min, hint.max, hint.step, hint.hide_slider, hint.suffix);
+ return editor;
} break;
@@ -3125,21 +3060,21 @@ bool EditorInspectorDefaultPlugin::parse_property(Object *p_object, Variant::Typ
case Variant::COLOR: {
EditorPropertyColor *editor = memnew(EditorPropertyColor);
editor->setup(p_hint != PROPERTY_HINT_COLOR_NO_ALPHA);
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::STRING_NAME: {
if (p_hint == PROPERTY_HINT_ENUM) {
EditorPropertyTextEnum *editor = memnew(EditorPropertyTextEnum);
Vector<String> options = p_hint_text.split(",");
editor->setup(options, true);
- add_property_editor(p_path, editor);
+ return editor;
} else {
EditorPropertyText *editor = memnew(EditorPropertyText);
if (p_hint == PROPERTY_HINT_PLACEHOLDER_TEXT) {
editor->set_placeholder(p_hint_text);
}
editor->set_string_name(true);
- add_property_editor(p_path, editor);
+ return editor;
}
} break;
case Variant::NODE_PATH: {
@@ -3152,12 +3087,12 @@ bool EditorInspectorDefaultPlugin::parse_property(Object *p_object, Variant::Typ
Vector<StringName> sn = Variant(types); //convert via variant
editor->setup(NodePath(), sn, (p_usage & PROPERTY_USAGE_NODE_PATH_FROM_SCENE_ROOT));
}
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::RID: {
EditorPropertyRID *editor = memnew(EditorPropertyRID);
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::OBJECT: {
EditorPropertyResource *editor = memnew(EditorPropertyResource);
@@ -3176,70 +3111,66 @@ bool EditorInspectorDefaultPlugin::parse_property(Object *p_object, Variant::Typ
}
}
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::DICTIONARY: {
EditorPropertyDictionary *editor = memnew(EditorPropertyDictionary);
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::ARRAY: {
EditorPropertyArray *editor = memnew(EditorPropertyArray);
editor->setup(Variant::ARRAY, p_hint_text);
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::PACKED_BYTE_ARRAY: {
EditorPropertyArray *editor = memnew(EditorPropertyArray);
editor->setup(Variant::PACKED_BYTE_ARRAY);
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::PACKED_INT32_ARRAY: {
EditorPropertyArray *editor = memnew(EditorPropertyArray);
editor->setup(Variant::PACKED_INT32_ARRAY);
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::PACKED_INT64_ARRAY: {
EditorPropertyArray *editor = memnew(EditorPropertyArray);
editor->setup(Variant::PACKED_INT64_ARRAY);
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::PACKED_FLOAT32_ARRAY: {
EditorPropertyArray *editor = memnew(EditorPropertyArray);
editor->setup(Variant::PACKED_FLOAT32_ARRAY);
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::PACKED_FLOAT64_ARRAY: {
EditorPropertyArray *editor = memnew(EditorPropertyArray);
editor->setup(Variant::PACKED_FLOAT64_ARRAY);
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::PACKED_STRING_ARRAY: {
EditorPropertyArray *editor = memnew(EditorPropertyArray);
editor->setup(Variant::PACKED_STRING_ARRAY);
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::PACKED_VECTOR2_ARRAY: {
EditorPropertyArray *editor = memnew(EditorPropertyArray);
editor->setup(Variant::PACKED_VECTOR2_ARRAY);
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::PACKED_VECTOR3_ARRAY: {
EditorPropertyArray *editor = memnew(EditorPropertyArray);
editor->setup(Variant::PACKED_VECTOR3_ARRAY);
- add_property_editor(p_path, editor);
+ return editor;
} break;
case Variant::PACKED_COLOR_ARRAY: {
EditorPropertyArray *editor = memnew(EditorPropertyArray);
editor->setup(Variant::PACKED_COLOR_ARRAY);
- add_property_editor(p_path, editor);
+
} break;
default: {
}
}
- return false; //can be overridden, although it will most likely be last anyway
-}
-
-void EditorInspectorDefaultPlugin::parse_end() {
- //do none
+ return nullptr;
}
diff --git a/editor/editor_properties.h b/editor/editor_properties.h
index dcde7dda3d..6b5bda295b 100644
--- a/editor/editor_properties.h
+++ b/editor/editor_properties.h
@@ -298,7 +298,8 @@ public:
class EditorPropertyFloat : public EditorProperty {
GDCLASS(EditorPropertyFloat, EditorProperty);
EditorSpinSlider *spin;
- bool setting;
+ bool setting = false;
+ bool angle_in_radians = false;
void _value_changed(double p_val);
protected:
@@ -306,7 +307,7 @@ protected:
public:
virtual void update_property() override;
- void setup(double p_min, double p_max, double p_step, bool p_no_slider, bool p_exp_range, bool p_greater, bool p_lesser);
+ void setup(double p_min, double p_max, double p_step, bool p_no_slider, bool p_exp_range, bool p_greater, bool p_lesser, const String &p_suffix = String(), bool p_angle_in_radians = false);
EditorPropertyFloat();
};
@@ -363,7 +364,7 @@ protected:
public:
virtual void update_property() override;
- void setup(double p_min, double p_max, double p_step, bool p_no_slider);
+ void setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix = String());
EditorPropertyVector2(bool p_force_wide = false);
};
@@ -379,14 +380,15 @@ protected:
public:
virtual void update_property() override;
- void setup(double p_min, double p_max, double p_step, bool p_no_slider);
+ void setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix = String());
EditorPropertyRect2(bool p_force_wide = false);
};
class EditorPropertyVector3 : public EditorProperty {
GDCLASS(EditorPropertyVector3, EditorProperty);
EditorSpinSlider *spin[3];
- bool setting;
+ bool setting = false;
+ bool angle_in_radians = false;
void _value_changed(double p_val, const String &p_name);
protected:
@@ -397,7 +399,7 @@ public:
virtual void update_property() override;
virtual void update_using_vector(Vector3 p_vector);
virtual Vector3 get_vector();
- void setup(double p_min, double p_max, double p_step, bool p_no_slider);
+ void setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix = String(), bool p_angle_in_radians = false);
EditorPropertyVector3(bool p_force_wide = false);
};
@@ -413,7 +415,7 @@ protected:
public:
virtual void update_property() override;
- void setup(int p_min, int p_max, bool p_no_slider);
+ void setup(int p_min, int p_max, bool p_no_slider, const String &p_suffix = String());
EditorPropertyVector2i(bool p_force_wide = false);
};
@@ -429,7 +431,7 @@ protected:
public:
virtual void update_property() override;
- void setup(int p_min, int p_max, bool p_no_slider);
+ void setup(int p_min, int p_max, bool p_no_slider, const String &p_suffix = String());
EditorPropertyRect2i(bool p_force_wide = false);
};
@@ -445,7 +447,7 @@ protected:
public:
virtual void update_property() override;
- void setup(int p_min, int p_max, bool p_no_slider);
+ void setup(int p_min, int p_max, bool p_no_slider, const String &p_suffix = String());
EditorPropertyVector3i(bool p_force_wide = false);
};
@@ -461,7 +463,7 @@ protected:
public:
virtual void update_property() override;
- void setup(double p_min, double p_max, double p_step, bool p_no_slider);
+ void setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix = String());
EditorPropertyPlane(bool p_force_wide = false);
};
@@ -477,7 +479,7 @@ protected:
public:
virtual void update_property() override;
- void setup(double p_min, double p_max, double p_step, bool p_no_slider);
+ void setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix = String());
EditorPropertyQuaternion();
};
@@ -493,7 +495,7 @@ protected:
public:
virtual void update_property() override;
- void setup(double p_min, double p_max, double p_step, bool p_no_slider);
+ void setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix = String());
EditorPropertyAABB();
};
@@ -509,7 +511,7 @@ protected:
public:
virtual void update_property() override;
- void setup(double p_min, double p_max, double p_step, bool p_no_slider);
+ void setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix = String());
EditorPropertyTransform2D();
};
@@ -525,7 +527,7 @@ protected:
public:
virtual void update_property() override;
- void setup(double p_min, double p_max, double p_step, bool p_no_slider);
+ void setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix = String());
EditorPropertyBasis();
};
@@ -542,7 +544,7 @@ protected:
public:
virtual void update_property() override;
virtual void update_using_transform(Transform3D p_transform);
- void setup(double p_min, double p_max, double p_step, bool p_no_slider);
+ void setup(double p_min, double p_max, double p_step, bool p_no_slider, const String &p_suffix = String());
EditorPropertyTransform3D();
};
@@ -649,6 +651,8 @@ public:
virtual void parse_begin(Object *p_object) override;
virtual bool parse_property(Object *p_object, Variant::Type p_type, const String &p_path, PropertyHint p_hint, const String &p_hint_text, int p_usage, bool p_wide = false) override;
virtual void parse_end() override;
+
+ static EditorProperty *get_editor_for_property(Object *p_object, Variant::Type p_type, const String &p_path, PropertyHint p_hint, const String &p_hint_text, int p_usage, bool p_wide = false);
};
#endif // EDITOR_PROPERTIES_H
diff --git a/editor/editor_properties_array_dict.cpp b/editor/editor_properties_array_dict.cpp
index 66fabcd940..9987aaf3fe 100644
--- a/editor/editor_properties_array_dict.cpp
+++ b/editor/editor_properties_array_dict.cpp
@@ -550,6 +550,8 @@ void EditorPropertyArray::_length_changed(double p_page) {
void EditorPropertyArray::setup(Variant::Type p_array_type, const String &p_hint_string) {
array_type = p_array_type;
+ // The format of p_hint_string is:
+ // subType/subTypeHint:nextSubtype ... etc
if (array_type == Variant::ARRAY && !p_hint_string.is_empty()) {
int hint_subtype_separator = p_hint_string.find(":");
if (hint_subtype_separator >= 0) {
@@ -572,7 +574,7 @@ void EditorPropertyArray::_bind_methods() {
}
EditorPropertyArray::EditorPropertyArray() {
- object.instance();
+ object.instantiate();
page_len = int(EDITOR_GET("interface/inspector/max_array_dictionary_items_per_page"));
edit = memnew(Button);
edit->set_h_size_flags(SIZE_EXPAND_FILL);
@@ -971,7 +973,7 @@ void EditorPropertyDictionary::update_property() {
PanelContainer *pc = memnew(PanelContainer);
vbox->add_child(pc);
Ref<StyleBoxFlat> flat;
- flat.instance();
+ flat.instantiate();
for (int j = 0; j < 4; j++) {
flat->set_default_margin(Side(j), 2 * EDSCALE);
}
@@ -1066,7 +1068,7 @@ void EditorPropertyDictionary::_bind_methods() {
}
EditorPropertyDictionary::EditorPropertyDictionary() {
- object.instance();
+ object.instantiate();
page_len = int(EDITOR_GET("interface/inspector/max_array_dictionary_items_per_page"));
edit = memnew(Button);
edit->set_h_size_flags(SIZE_EXPAND_FILL);
diff --git a/editor/editor_resource_picker.cpp b/editor/editor_resource_picker.cpp
index b591007a93..350fc5eccb 100644
--- a/editor/editor_resource_picker.cpp
+++ b/editor/editor_resource_picker.cpp
@@ -271,7 +271,7 @@ void EditorResourcePicker::_edit_menu_cbk(int p_which) {
}
String orig_type = edited_resource->get_class();
- Object *inst = ClassDB::instance(orig_type);
+ Object *inst = ClassDB::instantiate(orig_type);
Ref<Resource> unique_resource = Ref<Resource>(Object::cast_to<Resource>(inst));
ERR_FAIL_COND(unique_resource.is_null());
@@ -334,7 +334,7 @@ void EditorResourcePicker::_edit_menu_cbk(int p_which) {
Variant obj;
if (ScriptServer::is_global_class(intype)) {
- obj = ClassDB::instance(ScriptServer::get_global_class_native_base(intype));
+ obj = ClassDB::instantiate(ScriptServer::get_global_class_native_base(intype));
if (obj) {
Ref<Script> script = ResourceLoader::load(ScriptServer::get_global_class_path(intype));
if (script.is_valid()) {
@@ -342,7 +342,7 @@ void EditorResourcePicker::_edit_menu_cbk(int p_which) {
}
}
} else {
- obj = ClassDB::instance(intype);
+ obj = ClassDB::instantiate(intype);
}
if (!obj) {
@@ -395,7 +395,7 @@ void EditorResourcePicker::set_create_options(Object *p_menu_node) {
}
}
- if (!is_custom_resource && !(ScriptServer::is_global_class(t) || ClassDB::can_instance(t))) {
+ if (!is_custom_resource && !(ScriptServer::is_global_class(t) || ClassDB::can_instantiate(t))) {
continue;
}
diff --git a/editor/editor_resource_preview.cpp b/editor/editor_resource_preview.cpp
index 0f1b70936a..f904ae80a7 100644
--- a/editor/editor_resource_preview.cpp
+++ b/editor/editor_resource_preview.cpp
@@ -177,7 +177,7 @@ void EditorResourcePreview::_generate_preview(Ref<ImageTexture> &r_texture, Ref<
Ref<Image> small_image = r_texture->get_image();
small_image = small_image->duplicate();
small_image->resize(small_thumbnail_size, small_thumbnail_size, Image::INTERPOLATE_CUBIC);
- r_small_texture.instance();
+ r_small_texture.instantiate();
r_small_texture->create_from_image(small_image);
}
@@ -293,21 +293,21 @@ void EditorResourcePreview::_thread() {
if (cache_valid) {
Ref<Image> img;
- img.instance();
+ img.instantiate();
Ref<Image> small_img;
- small_img.instance();
+ small_img.instantiate();
if (img->load(cache_base + ".png") != OK) {
cache_valid = false;
} else {
- texture.instance();
+ texture.instantiate();
texture->create_from_image(img);
if (has_small_texture) {
if (small_img->load(cache_base + "_small.png") != OK) {
cache_valid = false;
} else {
- small_texture.instance();
+ small_texture.instantiate();
small_texture->create_from_image(small_img);
}
}
diff --git a/editor/editor_run_native.cpp b/editor/editor_run_native.cpp
index 1ffa20d1ea..a604022391 100644
--- a/editor/editor_run_native.cpp
+++ b/editor/editor_run_native.cpp
@@ -49,7 +49,7 @@ void EditorRunNative::_notification(int p_what) {
if (!im->is_empty()) {
im->resize(16 * EDSCALE, 16 * EDSCALE);
Ref<ImageTexture> small_icon;
- small_icon.instance();
+ small_icon.instantiate();
small_icon->create_from_image(im);
MenuButton *mb = memnew(MenuButton);
mb->get_popup()->connect("id_pressed", callable_mp(this, &EditorRunNative::_run_native), varray(i));
diff --git a/editor/editor_settings.cpp b/editor/editor_settings.cpp
index 3f66326b41..3f02b76ff6 100644
--- a/editor/editor_settings.cpp
+++ b/editor/editor_settings.cpp
@@ -79,7 +79,7 @@ bool EditorSettings::_set_only(const StringName &p_name, const Variant &p_value)
Ref<InputEvent> shortcut = arr[i + 1];
Ref<Shortcut> sc;
- sc.instance();
+ sc.instantiate();
sc->set_shortcut(shortcut);
add_shortcut(name, sc);
}
@@ -1476,7 +1476,7 @@ Ref<Shortcut> EditorSettings::get_shortcut(const String &p_name) const {
Ref<Shortcut> sc;
const Map<String, List<Ref<InputEvent>>>::Element *builtin_override = builtin_action_overrides.find(p_name);
if (builtin_override) {
- sc.instance();
+ sc.instantiate();
sc->set_shortcut(builtin_override->get().front()->get());
sc->set_name(InputMap::get_singleton()->get_builtin_display_name(p_name));
}
@@ -1485,7 +1485,7 @@ Ref<Shortcut> EditorSettings::get_shortcut(const String &p_name) const {
if (sc.is_null()) {
const OrderedHashMap<String, List<Ref<InputEvent>>>::ConstElement builtin_default = InputMap::get_singleton()->get_builtins().find(p_name);
if (builtin_default) {
- sc.instance();
+ sc.instantiate();
sc->set_shortcut(builtin_default.get().front()->get());
sc->set_name(InputMap::get_singleton()->get_builtin_display_name(p_name));
}
@@ -1528,7 +1528,7 @@ Ref<Shortcut> ED_SHORTCUT(const String &p_path, const String &p_name, uint32_t p
Ref<InputEventKey> ie;
if (p_keycode) {
- ie.instance();
+ ie.instantiate();
ie->set_unicode(p_keycode & KEY_CODE_MASK);
ie->set_keycode(p_keycode & KEY_CODE_MASK);
@@ -1540,7 +1540,7 @@ Ref<Shortcut> ED_SHORTCUT(const String &p_path, const String &p_name, uint32_t p
if (!EditorSettings::get_singleton()) {
Ref<Shortcut> sc;
- sc.instance();
+ sc.instantiate();
sc->set_name(p_name);
sc->set_shortcut(ie);
sc->set_meta("original", ie);
@@ -1554,7 +1554,7 @@ Ref<Shortcut> ED_SHORTCUT(const String &p_path, const String &p_name, uint32_t p
return sc;
}
- sc.instance();
+ sc.instantiate();
sc->set_name(p_name);
sc->set_shortcut(ie);
sc->set_meta("original", ie); //to compare against changes
@@ -1585,7 +1585,7 @@ void EditorSettings::set_builtin_action_override(const String &p_name, const Arr
// Check equality of each event.
for (List<Ref<InputEvent>>::Element *E = builtin_events.front(); E; E = E->next()) {
- if (!E->get()->shortcut_match(p_events[event_idx])) {
+ if (!E->get()->is_match(p_events[event_idx])) {
same_as_builtin = false;
break;
}
diff --git a/editor/editor_spin_slider.cpp b/editor/editor_spin_slider.cpp
index 4f0d75ecce..c1540f2cdd 100644
--- a/editor/editor_spin_slider.cpp
+++ b/editor/editor_spin_slider.cpp
@@ -255,7 +255,15 @@ void EditorSpinSlider::_notification(int p_what) {
draw_string(font, Vector2(Math::round(sb->get_offset().x), vofs), label, HALIGN_LEFT, -1, font_size, lc * Color(1, 1, 1, 0.5));
- draw_string(font, Vector2(Math::round(sb->get_offset().x + string_width + sep), vofs), numstr, HALIGN_LEFT, number_width, font_size, fc);
+ Vector2 text_ofs = Vector2(Math::round(sb->get_offset().x + string_width + sep), vofs);
+ draw_string(font, text_ofs, numstr, HALIGN_LEFT, number_width, font_size, fc);
+
+ if (suffix != String()) {
+ int sw = font->get_string_size(numstr).width;
+ text_ofs.x += sw;
+ fc.a *= 0.4;
+ draw_string(font, text_ofs, suffix, HALIGN_LEFT, MAX(0, number_width - sw), font_size, fc);
+ }
if (get_step() == 1) {
Ref<Texture2D> updown2 = get_theme_icon("updown", "SpinBox");
@@ -365,6 +373,15 @@ String EditorSpinSlider::get_label() const {
return label;
}
+void EditorSpinSlider::set_suffix(const String &p_suffix) {
+ suffix = p_suffix;
+ update();
+}
+
+String EditorSpinSlider::get_suffix() const {
+ return suffix;
+}
+
void EditorSpinSlider::_evaluate_input_text() {
// Replace comma with dot to support it as decimal separator (GH-6028).
// This prevents using functions like `pow()`, but using functions
@@ -373,7 +390,7 @@ void EditorSpinSlider::_evaluate_input_text() {
const String text = TS->parse_number(value_input->get_text().replace(",", "."));
Ref<Expression> expr;
- expr.instance();
+ expr.instantiate();
Error err = expr->parse(text);
if (err != OK) {
return;
@@ -468,6 +485,9 @@ void EditorSpinSlider::_bind_methods() {
ClassDB::bind_method(D_METHOD("set_label", "label"), &EditorSpinSlider::set_label);
ClassDB::bind_method(D_METHOD("get_label"), &EditorSpinSlider::get_label);
+ ClassDB::bind_method(D_METHOD("set_suffix", "suffix"), &EditorSpinSlider::set_suffix);
+ ClassDB::bind_method(D_METHOD("get_suffix"), &EditorSpinSlider::get_suffix);
+
ClassDB::bind_method(D_METHOD("set_read_only", "read_only"), &EditorSpinSlider::set_read_only);
ClassDB::bind_method(D_METHOD("is_read_only"), &EditorSpinSlider::is_read_only);
@@ -477,6 +497,7 @@ void EditorSpinSlider::_bind_methods() {
ClassDB::bind_method(D_METHOD("_gui_input"), &EditorSpinSlider::_gui_input);
ADD_PROPERTY(PropertyInfo(Variant::STRING, "label"), "set_label", "get_label");
+ ADD_PROPERTY(PropertyInfo(Variant::STRING, "suffix"), "set_suffix", "get_suffix");
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "read_only"), "set_read_only", "is_read_only");
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "flat"), "set_flat", "is_flat");
}
diff --git a/editor/editor_spin_slider.h b/editor/editor_spin_slider.h
index 50d04c9583..c30ff30390 100644
--- a/editor/editor_spin_slider.h
+++ b/editor/editor_spin_slider.h
@@ -39,6 +39,7 @@ class EditorSpinSlider : public Range {
GDCLASS(EditorSpinSlider, Range);
String label;
+ String suffix;
int updown_offset;
bool hover_updown;
bool mouse_hover;
@@ -93,6 +94,9 @@ public:
void set_label(const String &p_label);
String get_label() const;
+ void set_suffix(const String &p_suffix);
+ String get_suffix() const;
+
void set_hide_slider(bool p_hide);
bool is_hiding_slider() const;
diff --git a/editor/editor_themes.cpp b/editor/editor_themes.cpp
index fa543b7455..131a77e52f 100644
--- a/editor/editor_themes.cpp
+++ b/editor/editor_themes.cpp
@@ -766,12 +766,12 @@ Ref<Theme> create_editor_theme(const Ref<Theme> p_theme) {
theme->set_stylebox("sub_inspector_bg" + itos(i), "Editor", sub_inspector_bg);
Ref<StyleBoxFlat> bg_color;
- bg_color.instance();
+ bg_color.instantiate();
bg_color->set_bg_color(si_base_color * Color(0.7, 0.7, 0.7, 0.8));
bg_color->set_border_width_all(0);
Ref<StyleBoxFlat> bg_color_selected;
- bg_color_selected.instance();
+ bg_color_selected.instantiate();
bg_color_selected->set_border_width_all(0);
bg_color_selected->set_bg_color(si_base_color * Color(0.8, 0.8, 0.8, 0.8));
diff --git a/editor/export_template_manager.cpp b/editor/export_template_manager.cpp
index 76c6fcc3d3..dd4ce74406 100644
--- a/editor/export_template_manager.cpp
+++ b/editor/export_template_manager.cpp
@@ -242,10 +242,8 @@ void ExportTemplateManager::_refresh_mirrors_completed(int p_status, int p_code,
response_json.parse_utf8((const char *)r, p_data.size());
}
- Variant response;
- String errs;
- int errline;
- Error err = JSON::parse(response_json, response, errs, errline);
+ JSON json;
+ Error err = json.parse(response_json);
if (err != OK) {
EditorNode::get_singleton()->show_warning(TTR("Error parsing JSON with the list of mirrors. Please report this issue!"));
is_refreshing_mirrors = false;
@@ -260,7 +258,7 @@ void ExportTemplateManager::_refresh_mirrors_completed(int p_status, int p_code,
mirrors_available = false;
- Dictionary data = response;
+ Dictionary data = json.get_data();
if (data.has("mirrors")) {
Array mirrors = data["mirrors"];
diff --git a/editor/fileserver/editor_file_server.cpp b/editor/fileserver/editor_file_server.cpp
index 654915e3e5..8f019a95fd 100644
--- a/editor/fileserver/editor_file_server.cpp
+++ b/editor/fileserver/editor_file_server.cpp
@@ -312,7 +312,7 @@ void EditorFileServer::stop() {
}
EditorFileServer::EditorFileServer() {
- server.instance();
+ server.instantiate();
quit = false;
active = false;
cmd = CMD_NONE;
diff --git a/editor/filesystem_dock.cpp b/editor/filesystem_dock.cpp
index fe1fa9f9d6..527ffc86df 100644
--- a/editor/filesystem_dock.cpp
+++ b/editor/filesystem_dock.cpp
@@ -945,7 +945,7 @@ void FileSystemDock::_select_file(const String &p_path, bool p_select_in_favorit
} else if (fpath != "Favorites") {
if (FileAccess::exists(fpath + ".import")) {
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Error err = config->load(fpath + ".import");
if (err == OK) {
if (config->has_section_key("remap", "importer")) {
@@ -1985,20 +1985,6 @@ void FileSystemDock::_resource_created() {
editor->save_resource_as(RES(r), fpath);
}
-void FileSystemDock::_focus_current_search_box() {
- LineEdit *current_search_box = nullptr;
- if (display_mode == DISPLAY_MODE_TREE_ONLY) {
- current_search_box = tree_search_box;
- } else if (display_mode == DISPLAY_MODE_SPLIT) {
- current_search_box = file_list_search_box;
- }
-
- if (current_search_box) {
- current_search_box->grab_focus();
- current_search_box->select_all();
- }
-}
-
void FileSystemDock::_search_changed(const String &p_text, const Control *p_from) {
if (searched_string.length() == 0) {
// Register the uncollapsed paths before they change.
@@ -2040,7 +2026,17 @@ void FileSystemDock::fix_dependencies(const String &p_for_file) {
}
void FileSystemDock::focus_on_filter() {
- file_list_search_box->grab_focus();
+ LineEdit *current_search_box = nullptr;
+ if (display_mode == DISPLAY_MODE_TREE_ONLY) {
+ current_search_box = tree_search_box;
+ } else if (display_mode == DISPLAY_MODE_SPLIT) {
+ current_search_box = file_list_search_box;
+ }
+
+ if (current_search_box) {
+ current_search_box->grab_focus();
+ current_search_box->select_all();
+ }
}
void FileSystemDock::set_file_list_display_mode(FileListDisplayMode p_mode) {
@@ -2590,7 +2586,7 @@ void FileSystemDock::_tree_gui_input(Ref<InputEvent> p_event) {
} else if (ED_IS_SHORTCUT("filesystem_dock/rename", p_event)) {
_tree_rmb_option(FILE_RENAME);
} else if (ED_IS_SHORTCUT("editor/open_search", p_event)) {
- _focus_current_search_box();
+ focus_on_filter();
} else {
return;
}
@@ -2611,7 +2607,7 @@ void FileSystemDock::_file_list_gui_input(Ref<InputEvent> p_event) {
} else if (ED_IS_SHORTCUT("filesystem_dock/rename", p_event)) {
_file_list_rmb_option(FILE_RENAME);
} else if (ED_IS_SHORTCUT("editor/open_search", p_event)) {
- _focus_current_search_box();
+ focus_on_filter();
} else {
return;
}
@@ -2675,7 +2671,7 @@ void FileSystemDock::_update_import_dock() {
for (int i = 0; i < efiles.size(); i++) {
String fpath = efiles[i];
Ref<ConfigFile> cf;
- cf.instance();
+ cf.instantiate();
Error err = cf->load(fpath + ".import");
if (err != OK) {
imports.clear();
diff --git a/editor/filesystem_dock.h b/editor/filesystem_dock.h
index 12c567fb69..21a7abe622 100644
--- a/editor/filesystem_dock.h
+++ b/editor/filesystem_dock.h
@@ -253,7 +253,6 @@ private:
void _toggle_split_mode(bool p_active);
- void _focus_current_search_box();
void _search_changed(const String &p_text, const Control *p_from);
MenuButton *_create_file_menu_button();
diff --git a/editor/find_in_files.cpp b/editor/find_in_files.cpp
index c29b5d5906..cb8de09a9a 100644
--- a/editor/find_in_files.cpp
+++ b/editor/find_in_files.cpp
@@ -638,7 +638,7 @@ void FindInFilesPanel::set_with_replace(bool with_replace) {
// Results show checkboxes on their left so they can be opted out
_results_display->set_columns(2);
_results_display->set_column_expand(0, false);
- _results_display->set_column_min_width(0, 48 * EDSCALE);
+ _results_display->set_column_custom_minimum_width(0, 48 * EDSCALE);
} else {
// Results are single-cell items
diff --git a/editor/icons/CenterView.svg b/editor/icons/CenterView.svg
new file mode 100644
index 0000000000..c2a918fe81
--- /dev/null
+++ b/editor/icons/CenterView.svg
@@ -0,0 +1 @@
+<svg height="16" viewBox="0 0 16 16" width="16" xmlns="http://www.w3.org/2000/svg"><circle cx="4" cy="12" fill="none" r="2"/><g fill="#e0e0e0"><path d="m7.3333333 6c-.7386666 0-1.3333333.5946667-1.3333333 1.3333333v1.3333334c0 .7386663.5946667 1.3333333 1.3333333 1.3333333h1.3333334c.7386666 0 1.3333333-.594667 1.3333333-1.3333333v-1.3333334c0-.7386666-.5946667-1.3333333-1.3333333-1.3333333z" stroke-width=".666667"/><g stroke-width=".830398"><path d="m2.9918978 5.5000002c-.7478701.0001968-1.1170118.9026572-.5810669 1.4205652l.2441488.2424178h-2.15497967v1.6548989h2.15497967l-.2441488.242418c-.8159014.77992.3929613 1.9802119 1.178451 1.1700959l1.6667154-1.6548989c.3253369-.3231472.3253369-.8469488 0-1.170096l-1.6667154-1.6548989c-.1568986-.1601378-.3723426-.2504824-.5973507-.2504937z"/><path d="m13.008102 10.5c.74787-.000197 1.117012-.9026571.581067-1.4205651l-.244149-.242418h2.15498v-1.6548988h-2.15498l.244149-.2424179c.815901-.7799207-.392961-1.9802122-1.178451-1.1700961l-1.666715 1.6548987c-.325337.3231474-.325337.846949 0 1.1700961l1.666715 1.6548991c.156899.160138.372343.250482.597351.250494z"/><path d="m5.5000001 13.008102c.000197.74787.902657 1.117012 1.420565.581067l.242418-.244149v2.15498h1.654899v-2.15498l.242418.244149c.77992.815901 1.9802119-.392961 1.1700959-1.178451l-1.6548989-1.666715c-.323147-.325337-.846949-.325337-1.170096 0l-1.654899 1.666715c-.160138.156899-.250482.372343-.250494.597351z"/><path d="m10.5 2.9918983c-.000197-.7478701-.9026571-1.1170121-1.4205651-.581067l-.242418.244149v-2.1549801h-1.6548989v2.1549801l-.242418-.2441491c-.77992-.815901-1.9802121.3929611-1.170096 1.1784512l1.654899 1.6667148c.3231469.325337.8469489.325337 1.1700959 0l1.6548991-1.6667148c.160138-.156899.250482-.3723431.250494-.597351z"/></g></g></svg>
diff --git a/editor/icons/RectangleAddRemove.svg b/editor/icons/RectangleAddRemove.svg
deleted file mode 100644
index 87e2155a0d..0000000000
--- a/editor/icons/RectangleAddRemove.svg
+++ /dev/null
@@ -1 +0,0 @@
-<svg height="16" viewBox="0 0 16 16" width="16" xmlns="http://www.w3.org/2000/svg"><path d="m2 2c-.5522619.0000552-.9999448.4477381-1 1v10c.0000552.552262.4477381.999945 1 1h6v-2h-5v-8h10v1h2v-2c-.000055-.5522619-.447738-.9999448-1-1zm9.25 4v2.25h-2.25v1.5h2.25v2.25h1.5v-2.25h2.25v-1.5h-2.25v-2.25zm-2.25 7.5v1.5h6v-1.5z" fill="#e0e0e0"/></svg>
diff --git a/editor/icons/TileChecked.svg b/editor/icons/TileChecked.svg
new file mode 100644
index 0000000000..33b99a0e4c
--- /dev/null
+++ b/editor/icons/TileChecked.svg
@@ -0,0 +1 @@
+<svg height="16" viewBox="0 0 16 15.999999" width="16" xmlns="http://www.w3.org/2000/svg"><path d="m3.3333333 1c-1.2887 0-2.3333333 1.0446683-2.3333333 2.3333333v9.3333337c0 1.2887 1.0446683 2.333333 2.3333333 2.333333h9.3333337c1.2887 0 2.333333-1.044668 2.333333-2.333333v-9.3333337c0-1.2887-1.044668-2.3333333-2.333333-2.3333333z" fill="#808080" stroke-width="1.16667"/><path d="m11.500773 3.7343508-5.6117507 5.6117502-1.7045017-1.6814543-1.4992276 1.4992276 3.2037293 3.1806817 7.1109777-7.1109775z" fill="#fff" stroke-width="1.06023"/></svg>
diff --git a/editor/icons/TileUnchecked.svg b/editor/icons/TileUnchecked.svg
new file mode 100644
index 0000000000..cd8db4ee19
--- /dev/null
+++ b/editor/icons/TileUnchecked.svg
@@ -0,0 +1 @@
+<svg height="16" viewBox="0 0 16 15.999999" width="16" xmlns="http://www.w3.org/2000/svg"><path d="m3.3333333 1c-1.2887 0-2.3333333 1.0446683-2.3333333 2.3333333v9.3333337c0 1.2887 1.0446683 2.333333 2.3333333 2.333333h9.3333337c1.2887 0 2.333333-1.044668 2.333333-2.333333v-9.3333337c0-1.2887-1.044668-2.3333333-2.333333-2.3333333z" fill="#808080" stroke-width="1.16667"/></svg>
diff --git a/editor/import/editor_import_collada.cpp b/editor/import/editor_import_collada.cpp
index dc1bd38a99..ddf89f077b 100644
--- a/editor/import/editor_import_collada.cpp
+++ b/editor/import/editor_import_collada.cpp
@@ -850,7 +850,7 @@ Error ColladaImport::_create_mesh_surfaces(bool p_optimize, Ref<EditorSceneImpor
}
Ref<SurfaceTool> surftool;
- surftool.instance();
+ surftool.instantiate();
surftool->begin(Mesh::PRIMITIVE_TRIANGLES);
for (int k = 0; k < vertex_array.size(); k++) {
@@ -1544,7 +1544,7 @@ void ColladaImport::create_animation(int p_clip, bool p_make_tracks_in_all_bones
}
Vector3 s = xform.basis.get_scale();
- bool singular_matrix = Math::is_equal_approx(s.x, 0.0f) || Math::is_equal_approx(s.y, 0.0f) || Math::is_equal_approx(s.z, 0.0f);
+ bool singular_matrix = Math::is_zero_approx(s.x) || Math::is_zero_approx(s.y) || Math::is_zero_approx(s.z);
Quaternion q = singular_matrix ? Quaternion() : xform.basis.get_rotation_quaternion();
Vector3 l = xform.origin;
@@ -1595,7 +1595,7 @@ void ColladaImport::create_animation(int p_clip, bool p_make_tracks_in_all_bones
xform = sk->get_bone_rest(nm.bone).affine_inverse() * xform;
Vector3 s = xform.basis.get_scale();
- bool singular_matrix = Math::is_equal_approx(s.x, 0.0f) || Math::is_equal_approx(s.y, 0.0f) || Math::is_equal_approx(s.z, 0.0f);
+ bool singular_matrix = Math::is_zero_approx(s.x) || Math::is_zero_approx(s.y) || Math::is_zero_approx(s.z);
Quaternion q = singular_matrix ? Quaternion() : xform.basis.get_rotation_quaternion();
Vector3 l = xform.origin;
diff --git a/editor/import/resource_importer_bitmask.cpp b/editor/import/resource_importer_bitmask.cpp
index ffef759c07..7fd9230284 100644
--- a/editor/import/resource_importer_bitmask.cpp
+++ b/editor/import/resource_importer_bitmask.cpp
@@ -78,7 +78,7 @@ Error ResourceImporterBitMap::import(const String &p_source_file, const String &
int create_from = p_options["create_from"];
float threshold = p_options["threshold"];
Ref<Image> image;
- image.instance();
+ image.instantiate();
Error err = ImageLoader::load_image(p_source_file, image);
if (err != OK) {
return err;
@@ -88,7 +88,7 @@ Error ResourceImporterBitMap::import(const String &p_source_file, const String &
int h = image->get_height();
Ref<BitMap> bitmap;
- bitmap.instance();
+ bitmap.instantiate();
bitmap->create(Size2(w, h));
for (int i = 0; i < h; i++) {
diff --git a/editor/import/resource_importer_csv_translation.cpp b/editor/import/resource_importer_csv_translation.cpp
index c9e446a1a2..07647d8b6a 100644
--- a/editor/import/resource_importer_csv_translation.cpp
+++ b/editor/import/resource_importer_csv_translation.cpp
@@ -104,7 +104,7 @@ Error ResourceImporterCSVTranslation::import(const String &p_source_file, const
locales.push_back(locale);
Ref<Translation> translation;
- translation.instance();
+ translation.instantiate();
translation->set_locale(locale);
translations.push_back(translation);
}
diff --git a/editor/import/resource_importer_layered_texture.cpp b/editor/import/resource_importer_layered_texture.cpp
index 6d2215c379..2ac8b8bd7d 100644
--- a/editor/import/resource_importer_layered_texture.cpp
+++ b/editor/import/resource_importer_layered_texture.cpp
@@ -186,7 +186,7 @@ void ResourceImporterLayeredTexture::_save_tex(Vector<Ref<Image>> p_images, cons
for (int i = 0; i < mm_d; i++) {
Ref<Image> mm;
- mm.instance();
+ mm.instantiate();
mm->create(mm_w, mm_h, false, p_images[0]->get_format());
Vector3 pos;
pos.z = float(i) * float(d) / float(mm_d) + 0.5;
@@ -328,7 +328,7 @@ Error ResourceImporterLayeredTexture::import(const String &p_source_file, const
}
Ref<Image> image;
- image.instance();
+ image.instantiate();
Error err = ImageLoader::load_image(p_source_file, image, nullptr, false, 1.0);
if (err != OK) {
return err;
diff --git a/editor/import/resource_importer_obj.cpp b/editor/import/resource_importer_obj.cpp
index 3aa17ee581..01603c0a6a 100644
--- a/editor/import/resource_importer_obj.cpp
+++ b/editor/import/resource_importer_obj.cpp
@@ -57,7 +57,7 @@ static Error _parse_material_library(const String &p_path, Map<String, Ref<Stand
//vertex
current_name = l.replace("newmtl", "").strip_edges();
- current.instance();
+ current.instantiate();
current->set_name(current_name);
material_map[current_name] = current;
} else if (l.begins_with("Ka ")) {
@@ -207,7 +207,7 @@ static Error _parse_obj(const String &p_path, List<Ref<Mesh>> &r_meshes, bool p_
ERR_FAIL_COND_V_MSG(!f, ERR_CANT_OPEN, vformat("Couldn't open OBJ file '%s', it may not exist or not be readable.", p_path));
Ref<ArrayMesh> mesh;
- mesh.instance();
+ mesh.instantiate();
bool generate_tangents = p_generate_tangents;
Vector3 scale_mesh = p_scale_mesh;
@@ -378,7 +378,7 @@ static Error _parse_obj(const String &p_path, List<Ref<Mesh>> &r_meshes, bool p_
if (!p_single_mesh) {
mesh->set_name(name);
r_meshes.push_back(mesh);
- mesh.instance();
+ mesh.instantiate();
current_group = "";
current_material = "";
}
@@ -440,7 +440,7 @@ Node *EditorOBJImporter::import_scene(const String &p_path, uint32_t p_flags, in
for (List<Ref<Mesh>>::Element *E = meshes.front(); E; E = E->next()) {
Ref<EditorSceneImporterMesh> mesh;
- mesh.instance();
+ mesh.instantiate();
Ref<Mesh> m = E->get();
for (int i = 0; i < m->get_surface_count(); i++) {
mesh->add_surface(m->surface_get_primitive_type(i), m->surface_get_arrays(i), Array(), Dictionary(), m->surface_get_material(i));
diff --git a/editor/import/resource_importer_scene.cpp b/editor/import/resource_importer_scene.cpp
index 08aa2fecbb..c14b948dae 100644
--- a/editor/import/resource_importer_scene.cpp
+++ b/editor/import/resource_importer_scene.cpp
@@ -1422,7 +1422,7 @@ Error ResourceImporterScene::import(const String &p_source_file, const String &p
}
if (root_type != "Node3D") {
- Node *base_node = Object::cast_to<Node>(ClassDB::instance(root_type));
+ Node *base_node = Object::cast_to<Node>(ClassDB::instantiate(root_type));
if (base_node) {
scene->replace_by(base_node);
@@ -1557,7 +1557,7 @@ Node *EditorSceneImporterESCN::import_scene(const String &p_path, uint32_t p_fla
Ref<PackedScene> ps = ResourceFormatLoaderText::singleton->load(p_path, p_path, &error);
ERR_FAIL_COND_V_MSG(!ps.is_valid(), nullptr, "Cannot load scene as text resource from path '" + p_path + "'.");
- Node *scene = ps->instance();
+ Node *scene = ps->instantiate();
ERR_FAIL_COND_V(!scene, nullptr);
return scene;
diff --git a/editor/import/resource_importer_shader_file.cpp b/editor/import/resource_importer_shader_file.cpp
index 70119bfd1c..4d92490675 100644
--- a/editor/import/resource_importer_shader_file.cpp
+++ b/editor/import/resource_importer_shader_file.cpp
@@ -99,7 +99,7 @@ Error ResourceImporterShaderFile::import(const String &p_source_file, const Stri
String file_txt = file->get_as_utf8_string();
Ref<RDShaderFile> shader_file;
- shader_file.instance();
+ shader_file.instantiate();
String base_path = p_source_file.get_base_dir();
err = shader_file->parse_versions_from_text(file_txt, "", _include_function, &base_path);
diff --git a/editor/import/resource_importer_texture.cpp b/editor/import/resource_importer_texture.cpp
index 72df65a787..daf7b15794 100644
--- a/editor/import/resource_importer_texture.cpp
+++ b/editor/import/resource_importer_texture.cpp
@@ -88,7 +88,7 @@ void ResourceImporterTexture::update_imports() {
for (Map<StringName, MakeInfo>::Element *E = make_flags.front(); E; E = E->next()) {
Ref<ConfigFile> cf;
- cf.instance();
+ cf.instantiate();
String src_path = String(E->key()) + ".import";
Error err = cf->load(src_path);
@@ -411,13 +411,13 @@ Error ResourceImporterTexture::import(const String &p_source_file, const String
Image::RoughnessChannel roughness_channel = Image::ROUGHNESS_CHANNEL_R;
if (mipmaps && roughness > 1 && FileAccess::exists(normal_map)) {
- normal_image.instance();
+ normal_image.instantiate();
if (ImageLoader::load_image(normal_map, normal_image) == OK) {
roughness_channel = Image::RoughnessChannel(roughness - 2);
}
}
Ref<Image> image;
- image.instance();
+ image.instantiate();
Error err = ImageLoader::load_image(p_source_file, image, nullptr, hdr_as_srgb, scale);
if (err != OK) {
return err;
diff --git a/editor/import/resource_importer_texture_atlas.cpp b/editor/import/resource_importer_texture_atlas.cpp
index d5d1a14be3..dec1466da1 100644
--- a/editor/import/resource_importer_texture_atlas.cpp
+++ b/editor/import/resource_importer_texture_atlas.cpp
@@ -87,7 +87,7 @@ Error ResourceImporterTextureAtlas::import(const String &p_source_file, const St
//it's a simple hack
Ref<Image> broken = memnew(Image((const char **)atlas_import_failed_xpm));
Ref<ImageTexture> broken_texture;
- broken_texture.instance();
+ broken_texture.instantiate();
broken_texture->create_from_image(broken);
String target_file = p_save_path + ".tex";
@@ -201,7 +201,7 @@ Error ResourceImporterTextureAtlas::import_group_file(const String &p_group_file
const Map<StringName, Variant> &options = E->get();
Ref<Image> image;
- image.instance();
+ image.instantiate();
Error err = ImageLoader::load_image(source, image);
ERR_CONTINUE(err != OK);
@@ -240,7 +240,7 @@ Error ResourceImporterTextureAtlas::import_group_file(const String &p_group_file
pack_data.is_mesh = true;
Ref<BitMap> bit_map;
- bit_map.instance();
+ bit_map.instantiate();
bit_map->create_from_image_alpha(image);
Vector<Vector<Vector2>> polygons = bit_map->clip_opaque_to_polygons(Rect2(0, 0, image->get_width(), image->get_height()));
@@ -272,7 +272,7 @@ Error ResourceImporterTextureAtlas::import_group_file(const String &p_group_file
//blit the atlas
Ref<Image> new_atlas;
- new_atlas.instance();
+ new_atlas.instantiate();
new_atlas->create(atlas_width, atlas_height, false, Image::FORMAT_RGBA8);
for (int i = 0; i < pack_data_files.size(); i++) {
@@ -303,7 +303,7 @@ Error ResourceImporterTextureAtlas::import_group_file(const String &p_group_file
cache.reference_ptr(resptr);
} else {
Ref<ImageTexture> res_cache;
- res_cache.instance();
+ res_cache.instantiate();
res_cache->create_from_image(new_atlas);
res_cache->set_path(p_group_file);
cache = res_cache;
@@ -321,7 +321,7 @@ Error ResourceImporterTextureAtlas::import_group_file(const String &p_group_file
//region
Ref<AtlasTexture> atlas_texture;
- atlas_texture.instance();
+ atlas_texture.instantiate();
atlas_texture->set_atlas(cache);
atlas_texture->set_region(Rect2(offset, pack_data.region.size));
atlas_texture->set_margin(Rect2(pack_data.region.position, Size2(pack_data.image->get_width(), pack_data.image->get_height()) - pack_data.region.size));
@@ -329,7 +329,7 @@ Error ResourceImporterTextureAtlas::import_group_file(const String &p_group_file
texture = atlas_texture;
} else {
Ref<ArrayMesh> mesh;
- mesh.instance();
+ mesh.instantiate();
for (int i = 0; i < pack_data.chart_pieces.size(); i++) {
const EditorAtlasPacker::Chart &chart = charts[pack_data.chart_pieces[i]];
@@ -375,7 +375,7 @@ Error ResourceImporterTextureAtlas::import_group_file(const String &p_group_file
}
Ref<MeshTexture> mesh_texture;
- mesh_texture.instance();
+ mesh_texture.instantiate();
mesh_texture->set_base_texture(cache);
mesh_texture->set_image_size(pack_data.image->get_size());
mesh_texture->set_mesh(mesh);
diff --git a/editor/import/resource_importer_wav.cpp b/editor/import/resource_importer_wav.cpp
index e615212569..2db1db9e51 100644
--- a/editor/import/resource_importer_wav.cpp
+++ b/editor/import/resource_importer_wav.cpp
@@ -78,7 +78,7 @@ void ResourceImporterWAV::get_import_options(List<ImportOption> *r_options, int
r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "force/8_bit"), false));
r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "force/mono"), false));
r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "force/max_rate", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_DEFAULT | PROPERTY_USAGE_UPDATE_ALL_IF_MODIFIED), false));
- r_options->push_back(ImportOption(PropertyInfo(Variant::FLOAT, "force/max_rate_hz", PROPERTY_HINT_EXP_RANGE, "11025,192000,1"), 44100));
+ r_options->push_back(ImportOption(PropertyInfo(Variant::FLOAT, "force/max_rate_hz", PROPERTY_HINT_RANGE, "11025,192000,1,exp"), 44100));
r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "edit/trim"), false));
r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "edit/normalize"), false));
r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "edit/loop"), false));
@@ -508,7 +508,7 @@ Error ResourceImporterWAV::import(const String &p_source_file, const String &p_s
}
Ref<AudioStreamSample> sample;
- sample.instance();
+ sample.instantiate();
sample->set_data(dst_data);
sample->set_format(dst_format);
sample->set_mix_rate(rate);
diff --git a/editor/import/scene_import_settings.cpp b/editor/import/scene_import_settings.cpp
index 600f3fe2f0..f9f47ec4f4 100644
--- a/editor/import/scene_import_settings.cpp
+++ b/editor/import/scene_import_settings.cpp
@@ -435,7 +435,7 @@ void SceneImportSettings::open_settings(const String &p_path) {
base_subresource_settings.clear();
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Error err = config->load(p_path + ".import");
if (err == OK) {
List<String> keys;
@@ -1105,12 +1105,12 @@ SceneImportSettings::SceneImportSettings() {
{
Ref<StandardMaterial3D> selection_mat;
- selection_mat.instance();
+ selection_mat.instantiate();
selection_mat->set_shading_mode(StandardMaterial3D::SHADING_MODE_UNSHADED);
selection_mat->set_albedo(Color(1, 0.8, 1.0));
Ref<SurfaceTool> st;
- st.instance();
+ st.instantiate();
st->begin(Mesh::PRIMITIVE_LINES);
AABB base_aabb;
@@ -1126,7 +1126,7 @@ SceneImportSettings::SceneImportSettings() {
st->add_vertex(b.lerp(a, 0.2));
}
- selection_mesh.instance();
+ selection_mesh.instantiate();
st->commit(selection_mesh);
selection_mesh->surface_set_material(0, selection_mat);
@@ -1141,7 +1141,7 @@ SceneImportSettings::SceneImportSettings() {
base_viewport->add_child(mesh_preview);
mesh_preview->hide();
- material_preview.instance();
+ material_preview.instantiate();
}
inspector = memnew(EditorInspector);
@@ -1163,13 +1163,13 @@ SceneImportSettings::SceneImportSettings() {
external_path_tree->set_columns(3);
external_path_tree->set_column_titles_visible(true);
external_path_tree->set_column_expand(0, true);
- external_path_tree->set_column_min_width(0, 100 * EDSCALE);
+ external_path_tree->set_column_custom_minimum_width(0, 100 * EDSCALE);
external_path_tree->set_column_title(0, TTR("Resource"));
external_path_tree->set_column_expand(1, true);
- external_path_tree->set_column_min_width(1, 100 * EDSCALE);
+ external_path_tree->set_column_custom_minimum_width(1, 100 * EDSCALE);
external_path_tree->set_column_title(1, TTR("Path"));
external_path_tree->set_column_expand(2, false);
- external_path_tree->set_column_min_width(2, 200 * EDSCALE);
+ external_path_tree->set_column_custom_minimum_width(2, 200 * EDSCALE);
external_path_tree->set_column_title(2, TTR("Status"));
save_path = memnew(EditorFileDialog);
save_path->set_file_mode(EditorFileDialog::FILE_MODE_OPEN_DIR);
diff --git a/editor/import/scene_importer_mesh.cpp b/editor/import/scene_importer_mesh.cpp
index bf17ea7bca..ce78166d1e 100644
--- a/editor/import/scene_importer_mesh.cpp
+++ b/editor/import/scene_importer_mesh.cpp
@@ -215,6 +215,7 @@ void EditorSceneImporterMesh::generate_lods() {
int index_target = indices.size() * threshold;
float max_mesh_error_percentage = 1e0f;
float mesh_error = 0.0f;
+ float scale = SurfaceTool::simplify_scale_func((const float *)vertices_ptr, vertex_count, sizeof(Vector3));
while (index_target > min_indices) {
Vector<int> new_indices;
new_indices.resize(indices.size());
@@ -223,8 +224,8 @@ void EditorSceneImporterMesh::generate_lods() {
break;
}
Surface::LOD lod;
- lod.distance = mesh_error;
- if (Math::is_equal_approx(mesh_error, 0.0f)) {
+ lod.distance = mesh_error * scale;
+ if (Math::is_zero_approx(mesh_error)) {
break;
}
if (new_len <= 0) {
@@ -251,7 +252,7 @@ Ref<ArrayMesh> EditorSceneImporterMesh::get_mesh(const Ref<Mesh> &p_base) {
mesh = p_base;
}
if (mesh.is_null()) {
- mesh.instance();
+ mesh.instantiate();
}
mesh->set_name(get_name());
if (has_meta("import_id")) {
@@ -320,7 +321,7 @@ void EditorSceneImporterMesh::create_shadow_mesh() {
}
}
- shadow_mesh.instance();
+ shadow_mesh.instantiate();
for (int i = 0; i < surfaces.size(); i++) {
LocalVector<int> vertex_remap;
@@ -528,7 +529,7 @@ Vector<Ref<Shape3D>> EditorSceneImporterMesh::convex_decompose() const {
}
Ref<ConvexPolygonShape3D> shape;
- shape.instance();
+ shape.instantiate();
shape->set_points(convex_points);
ret.push_back(shape);
}
@@ -587,7 +588,7 @@ Ref<NavigationMesh> EditorSceneImporterMesh::create_navigation_mesh() {
}
Ref<NavigationMesh> nm;
- nm.instance();
+ nm.instantiate();
nm->set_vertices(vertices);
Vector<int> v3;
@@ -733,7 +734,7 @@ Error EditorSceneImporterMesh::lightmap_unwrap_cached(const Transform3D &p_base_
for (int i = 0; i < lightmap_surfaces.size(); i++) {
Ref<SurfaceTool> st;
- st.instance();
+ st.instantiate();
st->begin(Mesh::PRIMITIVE_TRIANGLES);
st->set_material(lightmap_surfaces[i].material);
st->set_meta("name", lightmap_surfaces[i].name);
diff --git a/editor/import_dock.cpp b/editor/import_dock.cpp
index 17c51f0f85..6fa9864830 100644
--- a/editor/import_dock.cpp
+++ b/editor/import_dock.cpp
@@ -91,7 +91,7 @@ public:
void ImportDock::set_edit_path(const String &p_path) {
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Error err = config->load(p_path + ".import");
if (err != OK) {
clear();
@@ -182,7 +182,7 @@ void ImportDock::set_edit_multiple_paths(const Vector<String> &p_paths) {
for (int i = 0; i < p_paths.size(); i++) {
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Error err = config->load(p_paths[i] + ".import");
ERR_CONTINUE(err != OK);
@@ -328,7 +328,7 @@ void ImportDock::_importer_selected(int i_idx) {
Ref<ConfigFile> config;
if (params->paths.size()) {
- config.instance();
+ config.instantiate();
Error err = config->load(params->paths[0] + ".import");
if (err != OK) {
config.unref();
@@ -440,7 +440,7 @@ void ImportDock::_reimport_attempt() {
}
for (int i = 0; i < params->paths.size(); i++) {
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Error err = config->load(params->paths[i] + ".import");
ERR_CONTINUE(err != OK);
@@ -477,7 +477,7 @@ void ImportDock::_advanced_options() {
void ImportDock::_reimport() {
for (int i = 0; i < params->paths.size(); i++) {
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
Error err = config->load(params->paths[i] + ".import");
ERR_CONTINUE(err != OK);
diff --git a/editor/localization_editor.cpp b/editor/localization_editor.cpp
index 161f1dde0d..91a15f1131 100644
--- a/editor/localization_editor.cpp
+++ b/editor/localization_editor.cpp
@@ -729,7 +729,7 @@ LocalizationEditor::LocalizationEditor() {
translation_remap_options->set_column_titles_visible(true);
translation_remap_options->set_column_expand(0, true);
translation_remap_options->set_column_expand(1, false);
- translation_remap_options->set_column_min_width(1, 200);
+ translation_remap_options->set_column_custom_minimum_width(1, 200);
translation_remap_options->connect("item_edited", callable_mp(this, &LocalizationEditor::_translation_res_option_changed));
translation_remap_options->connect("button_pressed", callable_mp(this, &LocalizationEditor::_translation_res_option_delete));
tmc->add_child(translation_remap_options);
diff --git a/editor/node_3d_editor_gizmos.cpp b/editor/node_3d_editor_gizmos.cpp
index 19663e46e1..2a399f4b03 100644
--- a/editor/node_3d_editor_gizmos.cpp
+++ b/editor/node_3d_editor_gizmos.cpp
@@ -600,8 +600,6 @@ bool EditorNode3DGizmo::intersect_ray(Camera3D *p_camera, const Point2 &p_point,
r_normal = -p_camera->project_ray_normal(p_point);
return true;
}
-
- return false;
}
if (collision_segments.size()) {
@@ -652,8 +650,6 @@ bool EditorNode3DGizmo::intersect_ray(Camera3D *p_camera, const Point2 &p_point,
r_normal = -p_camera->project_ray_normal(p_point);
return true;
}
-
- return false;
}
if (collision_mesh.is_valid()) {
@@ -759,7 +755,7 @@ EditorNode3DGizmo::EditorNode3DGizmo() {
hidden = false;
base = nullptr;
selected = false;
- instanced = false;
+ instantiated = false;
spatial_node = nullptr;
gizmo_plugin = nullptr;
selectable_icon_size = -1.0f;
@@ -3427,7 +3423,7 @@ void LightmapGIGizmoPlugin::redraw(EditorNode3DGizmo *p_gizmo) {
array[RS::ARRAY_COLOR] = colors;
Ref<ArrayMesh> mesh;
- mesh.instance();
+ mesh.instantiate();
mesh->add_surface_from_arrays(Mesh::PRIMITIVE_TRIANGLES, array, Array(), Dictionary(), 0); //no compression
mesh->surface_set_material(0, material_probes);
diff --git a/editor/plugins/animation_blend_space_1d_editor.cpp b/editor/plugins/animation_blend_space_1d_editor.cpp
index f7c0ebcfaf..b6dd9474d3 100644
--- a/editor/plugins/animation_blend_space_1d_editor.cpp
+++ b/editor/plugins/animation_blend_space_1d_editor.cpp
@@ -386,7 +386,7 @@ void AnimationNodeBlendSpace1DEditor::_add_menu_type(int p_index) {
} else {
String type = menu->get_item_metadata(p_index);
- Object *obj = ClassDB::instance(type);
+ Object *obj = ClassDB::instantiate(type);
ERR_FAIL_COND(!obj);
AnimationNode *an = Object::cast_to<AnimationNode>(obj);
ERR_FAIL_COND(!an);
@@ -413,7 +413,7 @@ void AnimationNodeBlendSpace1DEditor::_add_menu_type(int p_index) {
void AnimationNodeBlendSpace1DEditor::_add_animation_type(int p_index) {
Ref<AnimationNodeAnimation> anim;
- anim.instance();
+ anim.instantiate();
anim->set_animation(animations_to_add[p_index]);
@@ -594,7 +594,7 @@ AnimationNodeBlendSpace1DEditor::AnimationNodeBlendSpace1DEditor() {
add_child(top_hb);
Ref<ButtonGroup> bg;
- bg.instance();
+ bg.instantiate();
tool_blend = memnew(Button);
tool_blend->set_flat(true);
diff --git a/editor/plugins/animation_blend_space_2d_editor.cpp b/editor/plugins/animation_blend_space_2d_editor.cpp
index e719df53d5..359df95bce 100644
--- a/editor/plugins/animation_blend_space_2d_editor.cpp
+++ b/editor/plugins/animation_blend_space_2d_editor.cpp
@@ -308,7 +308,7 @@ void AnimationNodeBlendSpace2DEditor::_add_menu_type(int p_index) {
} else {
String type = menu->get_item_metadata(p_index);
- Object *obj = ClassDB::instance(type);
+ Object *obj = ClassDB::instantiate(type);
ERR_FAIL_COND(!obj);
AnimationNode *an = Object::cast_to<AnimationNode>(obj);
ERR_FAIL_COND(!an);
@@ -335,7 +335,7 @@ void AnimationNodeBlendSpace2DEditor::_add_menu_type(int p_index) {
void AnimationNodeBlendSpace2DEditor::_add_animation_type(int p_index) {
Ref<AnimationNodeAnimation> anim;
- anim.instance();
+ anim.instantiate();
anim->set_animation(animations_to_add[p_index]);
@@ -818,7 +818,7 @@ AnimationNodeBlendSpace2DEditor::AnimationNodeBlendSpace2DEditor() {
add_child(top_hb);
Ref<ButtonGroup> bg;
- bg.instance();
+ bg.instantiate();
tool_blend = memnew(Button);
tool_blend->set_flat(true);
diff --git a/editor/plugins/animation_blend_tree_editor_plugin.cpp b/editor/plugins/animation_blend_tree_editor_plugin.cpp
index 867c701733..dcde89f177 100644
--- a/editor/plugins/animation_blend_tree_editor_plugin.cpp
+++ b/editor/plugins/animation_blend_tree_editor_plugin.cpp
@@ -288,14 +288,14 @@ void AnimationNodeBlendTreeEditor::_add_node(int p_idx) {
ERR_FAIL_COND(!anode.is_valid());
base_name = anode->get_class();
} else if (add_options[p_idx].type != String()) {
- AnimationNode *an = Object::cast_to<AnimationNode>(ClassDB::instance(add_options[p_idx].type));
+ AnimationNode *an = Object::cast_to<AnimationNode>(ClassDB::instantiate(add_options[p_idx].type));
ERR_FAIL_COND(!an);
anode = Ref<AnimationNode>(an);
base_name = add_options[p_idx].name;
} else {
ERR_FAIL_COND(add_options[p_idx].script.is_null());
String base_type = add_options[p_idx].script->get_instance_base_type();
- AnimationNode *an = Object::cast_to<AnimationNode>(ClassDB::instance(base_type));
+ AnimationNode *an = Object::cast_to<AnimationNode>(ClassDB::instantiate(base_type));
ERR_FAIL_COND(!an);
anode = Ref<AnimationNode>(an);
anode->set_script(add_options[p_idx].script);
diff --git a/editor/plugins/animation_player_editor_plugin.cpp b/editor/plugins/animation_player_editor_plugin.cpp
index 4a3f3212fa..48d7cfdee2 100644
--- a/editor/plugins/animation_player_editor_plugin.cpp
+++ b/editor/plugins/animation_player_editor_plugin.cpp
@@ -121,11 +121,11 @@ void AnimationPlayerEditor::_notification(int p_what) {
Ref<Image> reset_img = reset_icon->get_image();
Ref<Image> autoplay_reset_img;
Size2 icon_size = Size2(autoplay_img->get_width(), autoplay_img->get_height());
- autoplay_reset_img.instance();
+ autoplay_reset_img.instantiate();
autoplay_reset_img->create(icon_size.x * 2, icon_size.y, false, autoplay_img->get_format());
autoplay_reset_img->blit_rect(autoplay_img, Rect2(Point2(), icon_size), Point2());
autoplay_reset_img->blit_rect(reset_img, Rect2(Point2(), icon_size), Point2(icon_size.x, 0));
- autoplay_reset_icon.instance();
+ autoplay_reset_icon.instantiate();
autoplay_reset_icon->create_from_image(autoplay_reset_img);
}
stop->set_icon(get_theme_icon("Stop", "EditorIcons"));
@@ -569,8 +569,8 @@ void AnimationPlayerEditor::_animation_blend() {
blend_editor.dialog->popup_centered(Size2(400, 400) * EDSCALE);
blend_editor.tree->set_hide_root(true);
- blend_editor.tree->set_column_min_width(0, 10);
- blend_editor.tree->set_column_min_width(1, 3);
+ blend_editor.tree->set_column_custom_minimum_width(0, 10);
+ blend_editor.tree->set_column_custom_minimum_width(1, 3);
List<StringName> anims;
player->get_animation_list(&anims);
diff --git a/editor/plugins/animation_state_machine_editor.cpp b/editor/plugins/animation_state_machine_editor.cpp
index fe5a0cab4d..94e526922d 100644
--- a/editor/plugins/animation_state_machine_editor.cpp
+++ b/editor/plugins/animation_state_machine_editor.cpp
@@ -257,7 +257,7 @@ void AnimationNodeStateMachineEditor::_state_machine_gui_input(const Ref<InputEv
} else {
Ref<AnimationNodeStateMachineTransition> tr;
- tr.instance();
+ tr.instantiate();
tr->set_switch_mode(AnimationNodeStateMachineTransition::SwitchMode(transition_mode->get_selected()));
updating = true;
@@ -423,7 +423,7 @@ void AnimationNodeStateMachineEditor::_add_menu_type(int p_index) {
} else {
String type = menu->get_item_metadata(p_index);
- Object *obj = ClassDB::instance(type);
+ Object *obj = ClassDB::instantiate(type);
ERR_FAIL_COND(!obj);
AnimationNode *an = Object::cast_to<AnimationNode>(obj);
ERR_FAIL_COND(!an);
@@ -462,7 +462,7 @@ void AnimationNodeStateMachineEditor::_add_menu_type(int p_index) {
void AnimationNodeStateMachineEditor::_add_animation_type(int p_index) {
Ref<AnimationNodeAnimation> anim;
- anim.instance();
+ anim.instantiate();
anim->set_animation(animations_to_add[p_index]);
@@ -1213,7 +1213,7 @@ AnimationNodeStateMachineEditor::AnimationNodeStateMachineEditor() {
add_child(top_hb);
Ref<ButtonGroup> bg;
- bg.instance();
+ bg.instantiate();
tool_select = memnew(Button);
tool_select->set_flat(true);
diff --git a/editor/plugins/animation_tree_editor_plugin.cpp b/editor/plugins/animation_tree_editor_plugin.cpp
index c33b06ff32..e90665f84d 100644
--- a/editor/plugins/animation_tree_editor_plugin.cpp
+++ b/editor/plugins/animation_tree_editor_plugin.cpp
@@ -76,7 +76,7 @@ void AnimationTreeEditor::_update_path() {
}
Ref<ButtonGroup> group;
- group.instance();
+ group.instantiate();
Button *b = memnew(Button);
b->set_text("Root");
diff --git a/editor/plugins/asset_library_editor_plugin.cpp b/editor/plugins/asset_library_editor_plugin.cpp
index 93bb170128..cd61ebd418 100644
--- a/editor/plugins/asset_library_editor_plugin.cpp
+++ b/editor/plugins/asset_library_editor_plugin.cpp
@@ -86,7 +86,7 @@ void EditorAssetLibraryItem::_bind_methods() {
EditorAssetLibraryItem::EditorAssetLibraryItem() {
Ref<StyleBoxEmpty> border;
- border.instance();
+ border.instantiate();
border->set_default_margin(SIDE_LEFT, 5 * EDSCALE);
border->set_default_margin(SIDE_RIGHT, 5 * EDSCALE);
border->set_default_margin(SIDE_BOTTOM, 5 * EDSCALE);
@@ -155,7 +155,7 @@ void EditorAssetLibraryItemDescription::set_image(int p_type, int p_index, const
thumbnail->blend_rect(overlay, overlay->get_used_rect(), overlay_pos);
Ref<ImageTexture> tex;
- tex.instance();
+ tex.instantiate();
tex->create_from_image(thumbnail);
preview_images[i].button->set_icon(tex);
@@ -761,7 +761,7 @@ void EditorAssetLibrary::_image_update(bool use_cache, bool final, const PackedB
}
Ref<ImageTexture> tex;
- tex.instance();
+ tex.instantiate();
tex->create_from_image(image);
obj->call("set_image", image_queue[p_queue_id].image_type, image_queue[p_queue_id].image_index, tex);
@@ -1098,11 +1098,9 @@ void EditorAssetLibrary::_http_request_completed(int p_status, int p_code, const
Dictionary d;
{
- Variant js;
- String errs;
- int errl;
- JSON::parse(str, js, errs, errl);
- d = js;
+ JSON json;
+ json.parse(str);
+ d = json.get_data();
}
RequestType requested = requesting;
@@ -1437,7 +1435,7 @@ EditorAssetLibrary::EditorAssetLibrary(bool p_templates_only) {
library_scroll_bg->add_child(library_scroll);
Ref<StyleBoxEmpty> border2;
- border2.instance();
+ border2.instantiate();
border2->set_default_margin(SIDE_LEFT, 15 * EDSCALE);
border2->set_default_margin(SIDE_RIGHT, 35 * EDSCALE);
border2->set_default_margin(SIDE_BOTTOM, 15 * EDSCALE);
diff --git a/editor/plugins/canvas_item_editor_plugin.cpp b/editor/plugins/canvas_item_editor_plugin.cpp
index 5d248176c1..25002fd995 100644
--- a/editor/plugins/canvas_item_editor_plugin.cpp
+++ b/editor/plugins/canvas_item_editor_plugin.cpp
@@ -1241,7 +1241,7 @@ bool CanvasItemEditor::_gui_input_zoom_or_pan(const Ref<InputEvent> &p_event, bo
Ref<InputEventPanGesture> pan_gesture = p_event;
if (pan_gesture.is_valid() && !p_already_accepted) {
- // If control key pressed, then zoom instead of pan
+ // If ctrl key pressed, then zoom instead of pan.
if (pan_gesture->is_ctrl_pressed()) {
const float factor = pan_gesture->get_delta().y;
@@ -4242,7 +4242,7 @@ void CanvasItemEditor::_insert_animation_keys(bool p_location, bool p_rotation,
AnimationPlayerEditor::singleton->get_track_editor()->insert_node_value_key(n2d, "position", n2d->get_position(), p_on_existing);
}
if (key_rot && p_rotation) {
- AnimationPlayerEditor::singleton->get_track_editor()->insert_node_value_key(n2d, "rotation_degrees", Math::rad2deg(n2d->get_rotation()), p_on_existing);
+ AnimationPlayerEditor::singleton->get_track_editor()->insert_node_value_key(n2d, "rotation", n2d->get_rotation(), p_on_existing);
}
if (key_scale && p_scale) {
AnimationPlayerEditor::singleton->get_track_editor()->insert_node_value_key(n2d, "scale", n2d->get_scale(), p_on_existing);
@@ -4274,7 +4274,7 @@ void CanvasItemEditor::_insert_animation_keys(bool p_location, bool p_rotation,
AnimationPlayerEditor::singleton->get_track_editor()->insert_node_value_key(F->get(), "position", F->get()->get_position(), p_on_existing);
}
if (key_rot) {
- AnimationPlayerEditor::singleton->get_track_editor()->insert_node_value_key(F->get(), "rotation_degrees", Math::rad2deg(F->get()->get_rotation()), p_on_existing);
+ AnimationPlayerEditor::singleton->get_track_editor()->insert_node_value_key(F->get(), "rotation", F->get()->get_rotation(), p_on_existing);
}
if (key_scale) {
AnimationPlayerEditor::singleton->get_track_editor()->insert_node_value_key(F->get(), "scale", F->get()->get_scale(), p_on_existing);
@@ -4290,7 +4290,7 @@ void CanvasItemEditor::_insert_animation_keys(bool p_location, bool p_rotation,
AnimationPlayerEditor::singleton->get_track_editor()->insert_node_value_key(ctrl, "rect_position", ctrl->get_position(), p_on_existing);
}
if (key_rot) {
- AnimationPlayerEditor::singleton->get_track_editor()->insert_node_value_key(ctrl, "rect_rotation", ctrl->get_rotation_degrees(), p_on_existing);
+ AnimationPlayerEditor::singleton->get_track_editor()->insert_node_value_key(ctrl, "rect_rotation", ctrl->get_rotation(), p_on_existing);
}
if (key_scale) {
AnimationPlayerEditor::singleton->get_track_editor()->insert_node_value_key(ctrl, "rect_size", ctrl->get_size(), p_on_existing);
@@ -4317,11 +4317,11 @@ void CanvasItemEditor::_button_toggle_anchor_mode(bool p_status) {
void CanvasItemEditor::_update_override_camera_button(bool p_game_running) {
if (p_game_running) {
override_camera_button->set_disabled(false);
- override_camera_button->set_tooltip(TTR("Game Camera Override\nOverrides game camera with editor viewport camera."));
+ override_camera_button->set_tooltip(TTR("Project Camera Override\nOverrides the running project's camera with the editor viewport camera."));
} else {
override_camera_button->set_disabled(true);
override_camera_button->set_pressed(false);
- override_camera_button->set_tooltip(TTR("Game Camera Override\nNo game instance running."));
+ override_camera_button->set_tooltip(TTR("Project Camera Override\nNo project instance running. Run the project from the editor to use this feature."));
}
}
@@ -5478,7 +5478,7 @@ CanvasItemEditor::CanvasItemEditor(EditorNode *p_editor) {
p = view_menu->get_popup();
p->set_hide_on_checkable_item_selection(false);
- p->add_check_shortcut(ED_SHORTCUT("canvas_item_editor/show_grid", TTR("Always Show Grid"), KEY_MASK_CTRL | KEY_G), SHOW_GRID);
+ p->add_check_shortcut(ED_SHORTCUT("canvas_item_editor/show_grid", TTR("Always Show Grid"), KEY_MASK_CMD | KEY_G), SHOW_GRID);
p->add_check_shortcut(ED_SHORTCUT("canvas_item_editor/show_helpers", TTR("Show Helpers"), KEY_H), SHOW_HELPERS);
p->add_check_shortcut(ED_SHORTCUT("canvas_item_editor/show_rulers", TTR("Show Rulers")), SHOW_RULERS);
p->add_check_shortcut(ED_SHORTCUT("canvas_item_editor/show_guides", TTR("Show Guides"), KEY_Y), SHOW_GUIDES);
@@ -5698,7 +5698,7 @@ void CanvasItemEditorViewport::_create_preview(const Vector<String> &files) cons
label_desc->show();
} else {
if (scene.is_valid()) {
- Node *instance = scene->instance();
+ Node *instance = scene->instantiate();
if (instance) {
preview_node->add_child(instance);
}
@@ -5811,26 +5811,26 @@ bool CanvasItemEditorViewport::_create_instance(Node *parent, String &path, cons
return false;
}
- Node *instanced_scene = sdata->instance(PackedScene::GEN_EDIT_STATE_INSTANCE);
- if (!instanced_scene) { // error on instancing
+ Node *instantiated_scene = sdata->instantiate(PackedScene::GEN_EDIT_STATE_INSTANCE);
+ if (!instantiated_scene) { // error on instancing
return false;
}
if (editor->get_edited_scene()->get_filename() != "") { // cyclical instancing
- if (_cyclical_dependency_exists(editor->get_edited_scene()->get_filename(), instanced_scene)) {
- memdelete(instanced_scene);
+ if (_cyclical_dependency_exists(editor->get_edited_scene()->get_filename(), instantiated_scene)) {
+ memdelete(instantiated_scene);
return false;
}
}
- instanced_scene->set_filename(ProjectSettings::get_singleton()->localize_path(path));
+ instantiated_scene->set_filename(ProjectSettings::get_singleton()->localize_path(path));
- editor_data->get_undo_redo().add_do_method(parent, "add_child", instanced_scene);
- editor_data->get_undo_redo().add_do_method(instanced_scene, "set_owner", editor->get_edited_scene());
- editor_data->get_undo_redo().add_do_reference(instanced_scene);
- editor_data->get_undo_redo().add_undo_method(parent, "remove_child", instanced_scene);
+ editor_data->get_undo_redo().add_do_method(parent, "add_child", instantiated_scene);
+ editor_data->get_undo_redo().add_do_method(instantiated_scene, "set_owner", editor->get_edited_scene());
+ editor_data->get_undo_redo().add_do_reference(instantiated_scene);
+ editor_data->get_undo_redo().add_undo_method(parent, "remove_child", instantiated_scene);
- String new_name = parent->validate_child_name(instanced_scene);
+ String new_name = parent->validate_child_name(instantiated_scene);
EditorDebuggerNode *ed = EditorDebuggerNode::get_singleton();
editor_data->get_undo_redo().add_do_method(ed, "live_debug_instance_node", editor->get_edited_scene()->get_path_to(parent), path, new_name);
editor_data->get_undo_redo().add_undo_method(ed, "live_debug_remove_node", NodePath(String(editor->get_edited_scene()->get_path_to(parent)) + "/" + new_name));
@@ -5841,11 +5841,11 @@ bool CanvasItemEditorViewport::_create_instance(Node *parent, String &path, cons
target_pos = canvas_item_editor->snap_point(target_pos);
target_pos = parent_ci->get_global_transform_with_canvas().affine_inverse().xform(target_pos);
// Preserve instance position of the original scene.
- CanvasItem *instance_ci = Object::cast_to<CanvasItem>(instanced_scene);
+ CanvasItem *instance_ci = Object::cast_to<CanvasItem>(instantiated_scene);
if (instance_ci) {
target_pos += instance_ci->_edit_get_position();
}
- editor_data->get_undo_redo().add_do_method(instanced_scene, "set_position", target_pos);
+ editor_data->get_undo_redo().add_do_method(instantiated_scene, "set_position", target_pos);
}
return true;
@@ -5928,7 +5928,7 @@ bool CanvasItemEditorViewport::can_drop_data(const Point2 &p_point, const Varian
if (d.has("type")) {
if (String(d["type"]) == "files") {
Vector<String> files = d["files"];
- bool can_instance = false;
+ bool can_instantiate = false;
for (int i = 0; i < files.size(); i++) { // check if dragged files contain resource or scene can be created at least once
RES res = ResourceLoader::load(files[i]);
if (res.is_null()) {
@@ -5937,11 +5937,11 @@ bool CanvasItemEditorViewport::can_drop_data(const Point2 &p_point, const Varian
String type = res->get_class();
if (type == "PackedScene") {
Ref<PackedScene> sdata = Ref<PackedScene>(Object::cast_to<PackedScene>(*res));
- Node *instanced_scene = sdata->instance(PackedScene::GEN_EDIT_STATE_INSTANCE);
- if (!instanced_scene) {
+ Node *instantiated_scene = sdata->instantiate(PackedScene::GEN_EDIT_STATE_INSTANCE);
+ if (!instantiated_scene) {
continue;
}
- memdelete(instanced_scene);
+ memdelete(instantiated_scene);
} else if (type == "Texture2D" ||
type == "ImageTexture" ||
type == "ViewportTexture" ||
@@ -5956,10 +5956,10 @@ bool CanvasItemEditorViewport::can_drop_data(const Point2 &p_point, const Varian
} else {
continue;
}
- can_instance = true;
+ can_instantiate = true;
break;
}
- if (can_instance) {
+ if (can_instantiate) {
if (!preview_node->get_parent()) { // create preview only once
_create_preview(files);
}
@@ -5967,7 +5967,7 @@ bool CanvasItemEditorViewport::can_drop_data(const Point2 &p_point, const Varian
preview_node->set_position((p_point - trans.get_origin()) / trans.get_scale().x);
label->set_text(vformat(TTR("Adding %s..."), default_type));
}
- return can_instance;
+ return can_instantiate;
}
}
label->hide();
@@ -6092,7 +6092,7 @@ CanvasItemEditorViewport::CanvasItemEditorViewport(EditorNode *p_node, CanvasIte
vbc->add_child(btn_group);
btn_group->set_h_size_flags(0);
- button_group.instance();
+ button_group.instantiate();
for (int i = 0; i < types.size(); i++) {
CheckBox *check = memnew(CheckBox);
btn_group->add_child(check);
diff --git a/editor/plugins/collision_polygon_3d_editor_plugin.cpp b/editor/plugins/collision_polygon_3d_editor_plugin.cpp
index a0df7e289e..6f90d278bd 100644
--- a/editor/plugins/collision_polygon_3d_editor_plugin.cpp
+++ b/editor/plugins/collision_polygon_3d_editor_plugin.cpp
@@ -358,9 +358,9 @@ void CollisionPolygon3DEditor::_polygon_draw() {
float depth = _get_depth() * 0.5;
- imgeom->clear();
+ imesh->clear_surfaces();
imgeom->set_material_override(line_material);
- imgeom->begin(Mesh::PRIMITIVE_LINES, Ref<Texture2D>());
+ imesh->surface_begin(Mesh::PRIMITIVE_LINES);
Rect2 rect;
@@ -382,10 +382,10 @@ void CollisionPolygon3DEditor::_polygon_draw() {
Vector3 point = Vector3(p.x, p.y, depth);
Vector3 next_point = Vector3(p2.x, p2.y, depth);
- imgeom->set_color(Color(1, 0.3, 0.1, 0.8));
- imgeom->add_vertex(point);
- imgeom->set_color(Color(1, 0.3, 0.1, 0.8));
- imgeom->add_vertex(next_point);
+ imesh->surface_set_color(Color(1, 0.3, 0.1, 0.8));
+ imesh->surface_add_vertex(point);
+ imesh->surface_set_color(Color(1, 0.3, 0.1, 0.8));
+ imesh->surface_add_vertex(next_point);
//Color col=Color(1,0.3,0.1,0.8);
//vpc->draw_line(point,next_point,col,2);
@@ -402,45 +402,43 @@ void CollisionPolygon3DEditor::_polygon_draw() {
r.size.y = rect.size.y;
r.size.z = 0;
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position);
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position + Vector3(0.3, 0, 0));
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position);
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position + Vector3(0.0, 0.3, 0));
-
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position + Vector3(r.size.x, 0, 0));
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position + Vector3(r.size.x, 0, 0) - Vector3(0.3, 0, 0));
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position + Vector3(r.size.x, 0, 0));
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position + Vector3(r.size.x, 0, 0) + Vector3(0, 0.3, 0));
-
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position + Vector3(0, r.size.y, 0));
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position + Vector3(0, r.size.y, 0) - Vector3(0, 0.3, 0));
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position + Vector3(0, r.size.y, 0));
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position + Vector3(0, r.size.y, 0) + Vector3(0.3, 0, 0));
-
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position + r.size);
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position + r.size - Vector3(0.3, 0, 0));
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position + r.size);
- imgeom->set_color(Color(0.8, 0.8, 0.8, 0.2));
- imgeom->add_vertex(r.position + r.size - Vector3(0.0, 0.3, 0));
-
- imgeom->end();
-
- m->clear_surfaces();
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position);
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position + Vector3(0.3, 0, 0));
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position);
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position + Vector3(0.0, 0.3, 0));
+
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position + Vector3(r.size.x, 0, 0));
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position + Vector3(r.size.x, 0, 0) - Vector3(0.3, 0, 0));
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position + Vector3(r.size.x, 0, 0));
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position + Vector3(r.size.x, 0, 0) + Vector3(0, 0.3, 0));
+
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position + Vector3(0, r.size.y, 0));
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position + Vector3(0, r.size.y, 0) - Vector3(0, 0.3, 0));
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position + Vector3(0, r.size.y, 0));
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position + Vector3(0, r.size.y, 0) + Vector3(0.3, 0, 0));
+
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position + r.size);
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position + r.size - Vector3(0.3, 0, 0));
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position + r.size);
+ imesh->surface_set_color(Color(0.8, 0.8, 0.8, 0.2));
+ imesh->surface_add_vertex(r.position + r.size - Vector3(0.0, 0.3, 0));
+
+ imesh->surface_end();
if (poly.size() == 0) {
return;
@@ -515,7 +513,9 @@ CollisionPolygon3DEditor::CollisionPolygon3DEditor(EditorNode *p_editor) {
mode = MODE_EDIT;
wip_active = false;
- imgeom = memnew(ImmediateGeometry3D);
+ imgeom = memnew(MeshInstance3D);
+ imesh.instantiate();
+ imgeom->set_mesh(imesh);
imgeom->set_transform(Transform3D(Basis(), Vector3(0, 0, 0.00001)));
line_material = Ref<StandardMaterial3D>(memnew(StandardMaterial3D));
@@ -537,7 +537,7 @@ CollisionPolygon3DEditor::CollisionPolygon3DEditor(EditorNode *p_editor) {
pointsm = memnew(MeshInstance3D);
imgeom->add_child(pointsm);
- m.instance();
+ m.instantiate();
pointsm->set_mesh(m);
pointsm->set_transform(Transform3D(Basis(), Vector3(0, 0, 0.00001)));
diff --git a/editor/plugins/collision_polygon_3d_editor_plugin.h b/editor/plugins/collision_polygon_3d_editor_plugin.h
index c66518e3e5..5db0f7308a 100644
--- a/editor/plugins/collision_polygon_3d_editor_plugin.h
+++ b/editor/plugins/collision_polygon_3d_editor_plugin.h
@@ -34,8 +34,8 @@
#include "editor/editor_node.h"
#include "editor/editor_plugin.h"
#include "scene/3d/collision_polygon_3d.h"
-#include "scene/3d/immediate_geometry_3d.h"
#include "scene/3d/mesh_instance_3d.h"
+#include "scene/resources/immediate_mesh.h"
class CanvasItemEditor;
@@ -60,7 +60,8 @@ class CollisionPolygon3DEditor : public HBoxContainer {
EditorNode *editor;
Panel *panel;
Node3D *node;
- ImmediateGeometry3D *imgeom;
+ Ref<ImmediateMesh> imesh;
+ MeshInstance3D *imgeom;
MeshInstance3D *pointsm;
Ref<ArrayMesh> m;
diff --git a/editor/plugins/cpu_particles_2d_editor_plugin.cpp b/editor/plugins/cpu_particles_2d_editor_plugin.cpp
index 3403aeceba..6a56cd31d1 100644
--- a/editor/plugins/cpu_particles_2d_editor_plugin.cpp
+++ b/editor/plugins/cpu_particles_2d_editor_plugin.cpp
@@ -74,7 +74,7 @@ void CPUParticles2DEditorPlugin::_menu_callback(int p_idx) {
void CPUParticles2DEditorPlugin::_generate_emission_mask() {
Ref<Image> img;
- img.instance();
+ img.instantiate();
Error err = ImageLoader::load_image(source_emission_file, img);
ERR_FAIL_COND_MSG(err != OK, "Error loading image '" + source_emission_file + "'.");
diff --git a/editor/plugins/curve_editor_plugin.cpp b/editor/plugins/curve_editor_plugin.cpp
index 7a38fd2bd5..706243fe25 100644
--- a/editor/plugins/curve_editor_plugin.cpp
+++ b/editor/plugins/curve_editor_plugin.cpp
@@ -127,6 +127,8 @@ void CurveEditor::on_gui_input(const Ref<InputEvent> &p_event) {
case MOUSE_BUTTON_LEFT:
_dragging = true;
break;
+ default:
+ break;
}
}
@@ -776,7 +778,7 @@ void EditorInspectorPluginCurve::parse_begin(Object *p_object) {
CurveEditorPlugin::CurveEditorPlugin(EditorNode *p_node) {
Ref<EditorInspectorPluginCurve> curve_plugin;
- curve_plugin.instance();
+ curve_plugin.instantiate();
EditorInspector::add_inspector_plugin(curve_plugin);
get_editor_interface()->get_resource_previewer()->add_preview_generator(memnew(CurvePreviewGenerator));
@@ -798,7 +800,7 @@ Ref<Texture2D> CurvePreviewGenerator::generate(const Ref<Resource> &p_from, cons
int thumbnail_size = EditorSettings::get_singleton()->get("filesystem/file_dialog/thumbnail_size");
thumbnail_size *= EDSCALE;
Ref<Image> img_ref;
- img_ref.instance();
+ img_ref.instantiate();
Image &im = **img_ref;
im.create(thumbnail_size, thumbnail_size / 2, false, Image::FORMAT_RGBA8);
diff --git a/editor/plugins/editor_preview_plugins.cpp b/editor/plugins/editor_preview_plugins.cpp
index 235ccb18cb..a233d66d82 100644
--- a/editor/plugins/editor_preview_plugins.cpp
+++ b/editor/plugins/editor_preview_plugins.cpp
@@ -174,7 +174,7 @@ Ref<Texture2D> EditorImagePreviewPlugin::generate(const RES &p_from, const Size2
post_process_preview(img);
Ref<ImageTexture> ptex;
- ptex.instance();
+ ptex.instantiate();
ptex->create_from_image(img);
return ptex;
@@ -219,7 +219,7 @@ Ref<Texture2D> EditorBitmapPreviewPlugin::generate(const RES &p_from, const Size
}
Ref<Image> img;
- img.instance();
+ img.instantiate();
img->create(bm->get_size().width, bm->get_size().height, false, Image::FORMAT_L8, data);
if (img->is_compressed()) {
@@ -278,7 +278,7 @@ Ref<Texture2D> EditorPackedScenePreviewPlugin::generate_from_path(const String &
}
Ref<Image> img;
- img.instance();
+ img.instantiate();
Error err = img->load(path);
if (err == OK) {
Ref<ImageTexture> ptex = Ref<ImageTexture>(memnew(ImageTexture));
@@ -501,7 +501,7 @@ Ref<Texture2D> EditorScriptPreviewPlugin::generate(const RES &p_from, const Size
int line = 0;
int col = 0;
Ref<Image> img;
- img.instance();
+ img.instantiate();
int thumbnail_size = MAX(p_size.x, p_size.y);
img->create(thumbnail_size, thumbnail_size, false, Image::FORMAT_RGBA8);
@@ -688,7 +688,7 @@ Ref<Texture2D> EditorAudioStreamPreviewPlugin::generate(const RES &p_from, const
Ref<ImageTexture> ptex = Ref<ImageTexture>(memnew(ImageTexture));
Ref<Image> image;
- image.instance();
+ image.instantiate();
image->create(w, h, false, Image::FORMAT_RGB8, img);
ptex->create_from_image(image);
return ptex;
@@ -881,7 +881,7 @@ Ref<Texture2D> EditorFontPreviewPlugin::generate_from_path(const String &p_path,
if (res->is_class("Font")) {
sampled_font = res->duplicate();
} else if (res->is_class("FontData")) {
- sampled_font.instance();
+ sampled_font.instantiate();
sampled_font->add_data(res->duplicate());
}
diff --git a/editor/plugins/font_editor_plugin.cpp b/editor/plugins/font_editor_plugin.cpp
index 8de7dc2447..9b0af37abb 100644
--- a/editor/plugins/font_editor_plugin.cpp
+++ b/editor/plugins/font_editor_plugin.cpp
@@ -119,7 +119,7 @@ void FontDataPreview::set_data(const Ref<FontData> &p_data) {
}
FontDataPreview::FontDataPreview() {
- line.instance();
+ line.instantiate();
}
/*************************************************************************/
@@ -326,6 +326,6 @@ bool EditorInspectorPluginFont::parse_property(Object *p_object, Variant::Type p
FontEditorPlugin::FontEditorPlugin(EditorNode *p_node) {
Ref<EditorInspectorPluginFont> fd_plugin;
- fd_plugin.instance();
+ fd_plugin.instantiate();
EditorInspector::add_inspector_plugin(fd_plugin);
}
diff --git a/editor/plugins/gpu_particles_2d_editor_plugin.cpp b/editor/plugins/gpu_particles_2d_editor_plugin.cpp
index b447304a3f..37f900280b 100644
--- a/editor/plugins/gpu_particles_2d_editor_plugin.cpp
+++ b/editor/plugins/gpu_particles_2d_editor_plugin.cpp
@@ -146,7 +146,7 @@ void GPUParticles2DEditorPlugin::_generate_emission_mask() {
}
Ref<Image> img;
- img.instance();
+ img.instantiate();
Error err = ImageLoader::load_image(source_emission_file, img);
ERR_FAIL_COND_MSG(err != OK, "Error loading image '" + source_emission_file + "'.");
@@ -270,11 +270,11 @@ void GPUParticles2DEditorPlugin::_generate_emission_mask() {
}
}
- img.instance();
+ img.instantiate();
img->create(w, h, false, Image::FORMAT_RGF, texdata);
Ref<ImageTexture> imgt;
- imgt.instance();
+ imgt.instantiate();
imgt->create_from_image(img);
pm->set_emission_point_texture(imgt);
@@ -291,10 +291,10 @@ void GPUParticles2DEditorPlugin::_generate_emission_mask() {
}
}
- img.instance();
+ img.instantiate();
img->create(w, h, false, Image::FORMAT_RGBA8, colordata);
- imgt.instance();
+ imgt.instantiate();
imgt->create_from_image(img);
pm->set_emission_color_texture(imgt);
}
@@ -314,10 +314,10 @@ void GPUParticles2DEditorPlugin::_generate_emission_mask() {
}
}
- img.instance();
+ img.instantiate();
img->create(w, h, false, Image::FORMAT_RGF, normdata);
- imgt.instance();
+ imgt.instantiate();
imgt->create_from_image(img);
pm->set_emission_normal_texture(imgt);
diff --git a/editor/plugins/gpu_particles_3d_editor_plugin.cpp b/editor/plugins/gpu_particles_3d_editor_plugin.cpp
index 17c7397729..571bcf9c4a 100644
--- a/editor/plugins/gpu_particles_3d_editor_plugin.cpp
+++ b/editor/plugins/gpu_particles_3d_editor_plugin.cpp
@@ -359,7 +359,7 @@ void GPUParticles3DEditor::_generate_emission_points() {
Ref<Image> image = memnew(Image(w, h, false, Image::FORMAT_RGBF, point_img));
Ref<ImageTexture> tex;
- tex.instance();
+ tex.instantiate();
Ref<ParticlesMaterial> material = node->get_process_material();
ERR_FAIL_COND(material.is_null());
@@ -387,7 +387,7 @@ void GPUParticles3DEditor::_generate_emission_points() {
Ref<Image> image2 = memnew(Image(w, h, false, Image::FORMAT_RGBF, point_img2));
Ref<ImageTexture> tex2;
- tex2.instance();
+ tex2.instantiate();
material->set_emission_normal_texture(tex2);
} else {
diff --git a/editor/plugins/gpu_particles_collision_sdf_editor_plugin.cpp b/editor/plugins/gpu_particles_collision_sdf_editor_plugin.cpp
index 8c4928b7cb..a2dee4a1dc 100644
--- a/editor/plugins/gpu_particles_collision_sdf_editor_plugin.cpp
+++ b/editor/plugins/gpu_particles_collision_sdf_editor_plugin.cpp
@@ -137,7 +137,7 @@ void GPUParticlesCollisionSDFEditorPlugin::_sdf_save_path_and_bake(const String
Ref<ConfigFile> config;
- config.instance();
+ config.instantiate();
if (FileAccess::exists(p_path + ".import")) {
config->load(p_path + ".import");
}
diff --git a/editor/plugins/gradient_editor_plugin.cpp b/editor/plugins/gradient_editor_plugin.cpp
index 46fa00f730..355bdb69d8 100644
--- a/editor/plugins/gradient_editor_plugin.cpp
+++ b/editor/plugins/gradient_editor_plugin.cpp
@@ -92,6 +92,6 @@ void EditorInspectorPluginGradient::parse_begin(Object *p_object) {
GradientEditorPlugin::GradientEditorPlugin(EditorNode *p_node) {
Ref<EditorInspectorPluginGradient> plugin;
- plugin.instance();
+ plugin.instantiate();
add_inspector_plugin(plugin);
}
diff --git a/editor/plugins/material_editor_plugin.cpp b/editor/plugins/material_editor_plugin.cpp
index 81f0ecacf2..17a634ee14 100644
--- a/editor/plugins/material_editor_plugin.cpp
+++ b/editor/plugins/material_editor_plugin.cpp
@@ -111,7 +111,7 @@ MaterialEditor::MaterialEditor() {
vc->set_anchors_and_offsets_preset(PRESET_WIDE);
viewport = memnew(SubViewport);
Ref<World3D> world_3d;
- world_3d.instance();
+ world_3d.instantiate();
viewport->set_world_3d(world_3d); //use own world
vc->add_child(viewport);
viewport->set_disable_input(true);
@@ -146,9 +146,9 @@ MaterialEditor::MaterialEditor() {
box_xform.origin.y = 0.2;
box_instance->set_transform(box_xform);
- sphere_mesh.instance();
+ sphere_mesh.instantiate();
sphere_instance->set_mesh(sphere_mesh);
- box_mesh.instance();
+ box_mesh.instantiate();
box_instance->set_mesh(box_mesh);
set_custom_minimum_size(Size2(1, 150) * EDSCALE);
@@ -223,7 +223,7 @@ void EditorInspectorPluginMaterial::parse_begin(Object *p_object) {
}
EditorInspectorPluginMaterial::EditorInspectorPluginMaterial() {
- env.instance();
+ env.instantiate();
Ref<Sky> sky = memnew(Sky());
env->set_sky(sky);
env->set_background(Environment::BG_COLOR);
@@ -233,7 +233,7 @@ EditorInspectorPluginMaterial::EditorInspectorPluginMaterial() {
MaterialEditorPlugin::MaterialEditorPlugin(EditorNode *p_node) {
Ref<EditorInspectorPluginMaterial> plugin;
- plugin.instance();
+ plugin.instantiate();
add_inspector_plugin(plugin);
}
@@ -251,10 +251,10 @@ Ref<Resource> StandardMaterial3DConversionPlugin::convert(const Ref<Resource> &p
ERR_FAIL_COND_V(!mat.is_valid(), Ref<Resource>());
Ref<ShaderMaterial> smat;
- smat.instance();
+ smat.instantiate();
Ref<Shader> shader;
- shader.instance();
+ shader.instantiate();
String code = RS::get_singleton()->shader_get_code(mat->get_shader_rid());
@@ -295,10 +295,10 @@ Ref<Resource> ParticlesMaterialConversionPlugin::convert(const Ref<Resource> &p_
ERR_FAIL_COND_V(!mat.is_valid(), Ref<Resource>());
Ref<ShaderMaterial> smat;
- smat.instance();
+ smat.instantiate();
Ref<Shader> shader;
- shader.instance();
+ shader.instantiate();
String code = RS::get_singleton()->shader_get_code(mat->get_shader_rid());
@@ -332,10 +332,10 @@ Ref<Resource> CanvasItemMaterialConversionPlugin::convert(const Ref<Resource> &p
ERR_FAIL_COND_V(!mat.is_valid(), Ref<Resource>());
Ref<ShaderMaterial> smat;
- smat.instance();
+ smat.instantiate();
Ref<Shader> shader;
- shader.instance();
+ shader.instantiate();
String code = RS::get_singleton()->shader_get_code(mat->get_shader_rid());
@@ -369,10 +369,10 @@ Ref<Resource> ProceduralSkyMaterialConversionPlugin::convert(const Ref<Resource>
ERR_FAIL_COND_V(!mat.is_valid(), Ref<Resource>());
Ref<ShaderMaterial> smat;
- smat.instance();
+ smat.instantiate();
Ref<Shader> shader;
- shader.instance();
+ shader.instantiate();
String code = RS::get_singleton()->shader_get_code(mat->get_shader_rid());
@@ -406,10 +406,10 @@ Ref<Resource> PanoramaSkyMaterialConversionPlugin::convert(const Ref<Resource> &
ERR_FAIL_COND_V(!mat.is_valid(), Ref<Resource>());
Ref<ShaderMaterial> smat;
- smat.instance();
+ smat.instantiate();
Ref<Shader> shader;
- shader.instance();
+ shader.instantiate();
String code = RS::get_singleton()->shader_get_code(mat->get_shader_rid());
@@ -443,10 +443,10 @@ Ref<Resource> PhysicalSkyMaterialConversionPlugin::convert(const Ref<Resource> &
ERR_FAIL_COND_V(!mat.is_valid(), Ref<Resource>());
Ref<ShaderMaterial> smat;
- smat.instance();
+ smat.instantiate();
Ref<Shader> shader;
- shader.instance();
+ shader.instantiate();
String code = RS::get_singleton()->shader_get_code(mat->get_shader_rid());
diff --git a/editor/plugins/mesh_editor_plugin.cpp b/editor/plugins/mesh_editor_plugin.cpp
index 8d488dce20..fcc6b84efb 100644
--- a/editor/plugins/mesh_editor_plugin.cpp
+++ b/editor/plugins/mesh_editor_plugin.cpp
@@ -110,7 +110,7 @@ void MeshEditor::_bind_methods() {
MeshEditor::MeshEditor() {
viewport = memnew(SubViewport);
Ref<World3D> world_3d;
- world_3d.instance();
+ world_3d.instantiate();
viewport->set_world_3d(world_3d); //use own world
add_child(viewport);
viewport->set_disable_input(true);
@@ -182,6 +182,6 @@ void EditorInspectorPluginMesh::parse_begin(Object *p_object) {
MeshEditorPlugin::MeshEditorPlugin(EditorNode *p_node) {
Ref<EditorInspectorPluginMesh> plugin;
- plugin.instance();
+ plugin.instantiate();
add_inspector_plugin(plugin);
}
diff --git a/editor/plugins/mesh_library_editor_plugin.cpp b/editor/plugins/mesh_library_editor_plugin.cpp
index e64992759d..5d1d29cbc8 100644
--- a/editor/plugins/mesh_library_editor_plugin.cpp
+++ b/editor/plugins/mesh_library_editor_plugin.cpp
@@ -193,7 +193,7 @@ void MeshLibraryEditor::_import_scene(Node *p_scene, Ref<MeshLibrary> p_library,
void MeshLibraryEditor::_import_scene_cbk(const String &p_str) {
Ref<PackedScene> ps = ResourceLoader::load(p_str, "PackedScene");
ERR_FAIL_COND(ps.is_null());
- Node *scene = ps->instance();
+ Node *scene = ps->instantiate();
ERR_FAIL_COND_MSG(!scene, "Cannot create an instance from PackedScene '" + p_str + "'.");
diff --git a/editor/plugins/node_3d_editor_plugin.cpp b/editor/plugins/node_3d_editor_plugin.cpp
index 3027246862..d964644d38 100644
--- a/editor/plugins/node_3d_editor_plugin.cpp
+++ b/editor/plugins/node_3d_editor_plugin.cpp
@@ -1398,6 +1398,8 @@ void Node3DEditorViewport::_sinput(const Ref<InputEvent> &p_event) {
}
} break;
+ default:
+ break;
}
}
@@ -2506,8 +2508,8 @@ void Node3DEditorViewport::_notification(int p_what) {
text += "X: " + rtos(current_camera->get_position().x).pad_decimals(1) + "\n";
text += "Y: " + rtos(current_camera->get_position().y).pad_decimals(1) + "\n";
text += "Z: " + rtos(current_camera->get_position().z).pad_decimals(1) + "\n";
- text += TTR("Pitch") + ": " + itos(Math::round(current_camera->get_rotation_degrees().x)) + "\n";
- text += TTR("Yaw") + ": " + itos(Math::round(current_camera->get_rotation_degrees().y)) + "\n\n";
+ text += TTR("Pitch") + ": " + itos(Math::round(Math::rad2deg(current_camera->get_rotation().x))) + "\n";
+ text += TTR("Yaw") + ": " + itos(Math::round(Math::rad2deg(current_camera->get_rotation().y))) + "\n\n";
text += TTR("Size") +
vformat(
@@ -3714,7 +3716,7 @@ void Node3DEditorViewport::_create_preview(const Vector<String> &files) const {
preview_node->add_child(mesh_instance);
} else {
if (scene.is_valid()) {
- Node *instance = scene->instance();
+ Node *instance = scene->instantiate();
if (instance) {
preview_node->add_child(instance);
}
@@ -3759,49 +3761,49 @@ bool Node3DEditorViewport::_create_instance(Node *parent, String &path, const Po
Ref<PackedScene> scene = Ref<PackedScene>(Object::cast_to<PackedScene>(*res));
Ref<Mesh> mesh = Ref<Mesh>(Object::cast_to<Mesh>(*res));
- Node *instanced_scene = nullptr;
+ Node *instantiated_scene = nullptr;
if (mesh != nullptr || scene != nullptr) {
if (mesh != nullptr) {
MeshInstance3D *mesh_instance = memnew(MeshInstance3D);
mesh_instance->set_mesh(mesh);
mesh_instance->set_name(path.get_file().get_basename());
- instanced_scene = mesh_instance;
+ instantiated_scene = mesh_instance;
} else {
if (!scene.is_valid()) { // invalid scene
return false;
} else {
- instanced_scene = scene->instance(PackedScene::GEN_EDIT_STATE_INSTANCE);
+ instantiated_scene = scene->instantiate(PackedScene::GEN_EDIT_STATE_INSTANCE);
}
}
}
- if (instanced_scene == nullptr) {
+ if (instantiated_scene == nullptr) {
return false;
}
if (editor->get_edited_scene()->get_filename() != "") { // cyclical instancing
- if (_cyclical_dependency_exists(editor->get_edited_scene()->get_filename(), instanced_scene)) {
- memdelete(instanced_scene);
+ if (_cyclical_dependency_exists(editor->get_edited_scene()->get_filename(), instantiated_scene)) {
+ memdelete(instantiated_scene);
return false;
}
}
if (scene != nullptr) {
- instanced_scene->set_filename(ProjectSettings::get_singleton()->localize_path(path));
+ instantiated_scene->set_filename(ProjectSettings::get_singleton()->localize_path(path));
}
- editor_data->get_undo_redo().add_do_method(parent, "add_child", instanced_scene);
- editor_data->get_undo_redo().add_do_method(instanced_scene, "set_owner", editor->get_edited_scene());
- editor_data->get_undo_redo().add_do_reference(instanced_scene);
- editor_data->get_undo_redo().add_undo_method(parent, "remove_child", instanced_scene);
+ editor_data->get_undo_redo().add_do_method(parent, "add_child", instantiated_scene);
+ editor_data->get_undo_redo().add_do_method(instantiated_scene, "set_owner", editor->get_edited_scene());
+ editor_data->get_undo_redo().add_do_reference(instantiated_scene);
+ editor_data->get_undo_redo().add_undo_method(parent, "remove_child", instantiated_scene);
- String new_name = parent->validate_child_name(instanced_scene);
+ String new_name = parent->validate_child_name(instantiated_scene);
EditorDebuggerNode *ed = EditorDebuggerNode::get_singleton();
editor_data->get_undo_redo().add_do_method(ed, "live_debug_instance_node", editor->get_edited_scene()->get_path_to(parent), path, new_name);
editor_data->get_undo_redo().add_undo_method(ed, "live_debug_remove_node", NodePath(String(editor->get_edited_scene()->get_path_to(parent)) + "/" + new_name));
- Node3D *node3d = Object::cast_to<Node3D>(instanced_scene);
+ Node3D *node3d = Object::cast_to<Node3D>(instantiated_scene);
if (node3d) {
Transform3D global_transform;
Node3D *parent_node3d = Object::cast_to<Node3D>(parent);
@@ -3812,7 +3814,7 @@ bool Node3DEditorViewport::_create_instance(Node *parent, String &path, const Po
global_transform.origin = spatial_editor->snap_point(_get_instance_position(p_point));
global_transform.basis *= node3d->get_transform().basis;
- editor_data->get_undo_redo().add_do_method(instanced_scene, "set_global_transform", global_transform);
+ editor_data->get_undo_redo().add_do_method(instantiated_scene, "set_global_transform", global_transform);
}
return true;
@@ -3855,7 +3857,7 @@ void Node3DEditorViewport::_perform_drop_data() {
}
bool Node3DEditorViewport::can_drop_data_fw(const Point2 &p_point, const Variant &p_data, Control *p_from) const {
- bool can_instance = false;
+ bool can_instantiate = false;
if (!preview_node->is_inside_tree()) {
Dictionary d = p_data;
@@ -3877,11 +3879,11 @@ bool Node3DEditorViewport::can_drop_data_fw(const Point2 &p_point, const Variant
String type = res->get_class();
if (type == "PackedScene") {
Ref<PackedScene> sdata = ResourceLoader::load(files[i]);
- Node *instanced_scene = sdata->instance(PackedScene::GEN_EDIT_STATE_INSTANCE);
- if (!instanced_scene) {
+ Node *instantiated_scene = sdata->instantiate(PackedScene::GEN_EDIT_STATE_INSTANCE);
+ if (!instantiated_scene) {
continue;
}
- memdelete(instanced_scene);
+ memdelete(instantiated_scene);
} else if (type == "Mesh" || type == "ArrayMesh" || type == "PrimitiveMesh") {
Ref<Mesh> mesh = ResourceLoader::load(files[i]);
if (!mesh.is_valid()) {
@@ -3890,24 +3892,24 @@ bool Node3DEditorViewport::can_drop_data_fw(const Point2 &p_point, const Variant
} else {
continue;
}
- can_instance = true;
+ can_instantiate = true;
break;
}
}
- if (can_instance) {
+ if (can_instantiate) {
_create_preview(files);
}
}
} else {
- can_instance = true;
+ can_instantiate = true;
}
- if (can_instance) {
+ if (can_instantiate) {
Transform3D global_transform = Transform3D(Basis(), _get_instance_position(p_point));
preview_node->set_global_transform(global_transform);
}
- return can_instance;
+ return can_instantiate;
}
void Node3DEditorViewport::drop_data_fw(const Point2 &p_point, const Variant &p_data, Control *p_from) {
@@ -5317,7 +5319,7 @@ void Node3DEditor::_init_indicators() {
origin_enabled = true;
grid_enabled = true;
- indicator_mat.instance();
+ indicator_mat.instantiate();
indicator_mat->set_shading_mode(StandardMaterial3D::SHADING_MODE_UNSHADED);
indicator_mat->set_flag(StandardMaterial3D::FLAG_ALBEDO_FROM_VERTEX_COLOR, true);
indicator_mat->set_flag(StandardMaterial3D::FLAG_SRGB_VERTEX_COLOR, true);
@@ -5397,7 +5399,7 @@ void Node3DEditor::_init_indicators() {
"}");
for (int i = 0; i < 3; i++) {
- grid_mat[i].instance();
+ grid_mat[i].instantiate();
grid_mat[i]->set_shader(grid_shader);
}
@@ -6371,7 +6373,7 @@ void Node3DEditor::_request_gizmo(Object *p_obj) {
if (!sp) {
return;
}
- if (editor->get_edited_scene() && (sp == editor->get_edited_scene() || (sp->get_owner() && editor->get_edited_scene()->is_a_parent_of(sp)))) {
+ if (editor->get_edited_scene() && (sp == editor->get_edited_scene() || (sp->get_owner() && editor->get_edited_scene()->is_ancestor_of(sp)))) {
Ref<EditorNode3DGizmo> seg;
for (int i = 0; i < gizmo_plugins_by_priority.size(); ++i) {
@@ -6445,7 +6447,7 @@ void Node3DEditor::_toggle_maximize_view(Object *p_viewport) {
}
void Node3DEditor::_node_added(Node *p_node) {
- if (EditorNode::get_singleton()->get_scene_root()->is_a_parent_of(p_node)) {
+ if (EditorNode::get_singleton()->get_scene_root()->is_ancestor_of(p_node)) {
if (Object::cast_to<WorldEnvironment>(p_node)) {
world_env_count++;
if (world_env_count == 1) {
@@ -6461,7 +6463,7 @@ void Node3DEditor::_node_added(Node *p_node) {
}
void Node3DEditor::_node_removed(Node *p_node) {
- if (EditorNode::get_singleton()->get_scene_root()->is_a_parent_of(p_node)) {
+ if (EditorNode::get_singleton()->get_scene_root()->is_ancestor_of(p_node)) {
if (Object::cast_to<WorldEnvironment>(p_node)) {
world_env_count--;
if (world_env_count == 0) {
@@ -6915,7 +6917,7 @@ Node3DEditor::Node3DEditor(EditorNode *p_editor) {
p->add_separator();
p->add_check_shortcut(ED_SHORTCUT("spatial_editor/view_origin", TTR("View Origin")), MENU_VIEW_ORIGIN);
- p->add_check_shortcut(ED_SHORTCUT("spatial_editor/view_grid", TTR("View Grid")), MENU_VIEW_GRID);
+ p->add_check_shortcut(ED_SHORTCUT("spatial_editor/view_grid", TTR("View Grid"), KEY_MASK_CMD + KEY_G), MENU_VIEW_GRID);
p->add_separator();
p->add_shortcut(ED_SHORTCUT("spatial_editor/settings", TTR("Settings...")), MENU_VIEW_CAMERA_SETTINGS);
@@ -7115,9 +7117,9 @@ Node3DEditor::Node3DEditor(EditorNode *p_editor) {
sun_direction->set_default_cursor_shape(CURSOR_MOVE);
String sun_dir_shader_code = "shader_type canvas_item; uniform vec3 sun_direction; uniform vec3 sun_color; void fragment() { vec3 n; n.xy = UV * 2.0 - 1.0; n.z = sqrt(max(0.0, 1.0 - dot(n.xy, n.xy))); COLOR.rgb = dot(n,sun_direction) * sun_color; COLOR.a = 1.0 - smoothstep(0.99,1.0,length(n.xy)); }";
- sun_direction_shader.instance();
+ sun_direction_shader.instantiate();
sun_direction_shader->set_code(sun_dir_shader_code);
- sun_direction_material.instance();
+ sun_direction_material.instantiate();
sun_direction_material->set_shader(sun_direction_shader);
sun_direction_material->set_shader_param("sun_direction", Vector3(0, 0, 1));
sun_direction_material->set_shader_param("sun_color", Vector3(1, 1, 1));
@@ -7248,11 +7250,11 @@ Node3DEditor::Node3DEditor(EditorNode *p_editor) {
preview_sun->set_shadow(true);
preview_sun->set_shadow_mode(DirectionalLight3D::SHADOW_PARALLEL_4_SPLITS);
preview_environment = memnew(WorldEnvironment);
- environment.instance();
+ environment.instantiate();
preview_environment->set_environment(environment);
Ref<Sky> sky;
- sky.instance();
- sky_material.instance();
+ sky.instantiate();
+ sky_material.instantiate();
sky->set_material(sky_material);
environment->set_sky(sky);
environment->set_background(Environment::BG_SKY);
@@ -7383,17 +7385,17 @@ Node3DEditorPlugin::~Node3DEditorPlugin() {
}
void EditorNode3DGizmoPlugin::create_material(const String &p_name, const Color &p_color, bool p_billboard, bool p_on_top, bool p_use_vertex_color) {
- Color instanced_color = EDITOR_DEF("editors/3d_gizmos/gizmo_colors/instanced", Color(0.7, 0.7, 0.7, 0.6));
+ Color instantiated_color = EDITOR_DEF("editors/3d_gizmos/gizmo_colors/instantiated", Color(0.7, 0.7, 0.7, 0.6));
Vector<Ref<StandardMaterial3D>> mats;
for (int i = 0; i < 4; i++) {
bool selected = i % 2 == 1;
- bool instanced = i < 2;
+ bool instantiated = i < 2;
Ref<StandardMaterial3D> material = Ref<StandardMaterial3D>(memnew(StandardMaterial3D));
- Color color = instanced ? instanced_color : p_color;
+ Color color = instantiated ? instantiated_color : p_color;
if (!selected) {
color.a *= 0.3;
@@ -7425,17 +7427,17 @@ void EditorNode3DGizmoPlugin::create_material(const String &p_name, const Color
}
void EditorNode3DGizmoPlugin::create_icon_material(const String &p_name, const Ref<Texture2D> &p_texture, bool p_on_top, const Color &p_albedo) {
- Color instanced_color = EDITOR_DEF("editors/3d_gizmos/gizmo_colors/instanced", Color(0.7, 0.7, 0.7, 0.6));
+ Color instantiated_color = EDITOR_DEF("editors/3d_gizmos/gizmo_colors/instantiated", Color(0.7, 0.7, 0.7, 0.6));
Vector<Ref<StandardMaterial3D>> icons;
for (int i = 0; i < 4; i++) {
bool selected = i % 2 == 1;
- bool instanced = i < 2;
+ bool instantiated = i < 2;
Ref<StandardMaterial3D> icon = Ref<StandardMaterial3D>(memnew(StandardMaterial3D));
- Color color = instanced ? instanced_color : p_albedo;
+ Color color = instantiated ? instantiated_color : p_albedo;
if (!selected) {
color.a *= 0.85;
@@ -7594,7 +7596,7 @@ Ref<EditorNode3DGizmo> EditorNode3DGizmoPlugin::create_gizmo(Node3D *p_spatial)
Ref<EditorNode3DGizmo> ref;
if (has_gizmo(p_spatial)) {
- ref.instance();
+ ref.instantiate();
}
return ref;
}
diff --git a/editor/plugins/node_3d_editor_plugin.h b/editor/plugins/node_3d_editor_plugin.h
index 6f03516409..02f89a12de 100644
--- a/editor/plugins/node_3d_editor_plugin.h
+++ b/editor/plugins/node_3d_editor_plugin.h
@@ -34,7 +34,6 @@
#include "editor/editor_node.h"
#include "editor/editor_plugin.h"
#include "editor/editor_scale.h"
-#include "scene/3d/immediate_geometry_3d.h"
#include "scene/3d/light_3d.h"
#include "scene/3d/visual_instance_3d.h"
#include "scene/3d/world_environment.h"
@@ -52,7 +51,7 @@ class EditorNode3DGizmo : public Node3DGizmo {
GDCLASS(EditorNode3DGizmo, Node3DGizmo);
bool selected;
- bool instanced;
+ bool instantiated;
public:
void set_selected(bool p_selected) { selected = p_selected; }
diff --git a/editor/plugins/occluder_instance_3d_editor_plugin.cpp b/editor/plugins/occluder_instance_3d_editor_plugin.cpp
index 0821f140b3..b0cafd83be 100644
--- a/editor/plugins/occluder_instance_3d_editor_plugin.cpp
+++ b/editor/plugins/occluder_instance_3d_editor_plugin.cpp
@@ -56,7 +56,7 @@ void OccluderInstance3DEditorPlugin::_bake_select_file(const String &p_file) {
} break;
case OccluderInstance3D::BAKE_ERROR_NO_MESHES: {
- EditorNode::get_singleton()->show_warning(TTR("No meshes to bake."));
+ EditorNode::get_singleton()->show_warning(TTR("No meshes to bake.\nMake sure there is at least one MeshInstance3D node in the scene whose visual layers are part of the OccluderInstance3D's Bake Mask property."));
break;
}
default: {
diff --git a/editor/plugins/ot_features_plugin.cpp b/editor/plugins/ot_features_plugin.cpp
index ebfdf2c7cd..baab9bc438 100644
--- a/editor/plugins/ot_features_plugin.cpp
+++ b/editor/plugins/ot_features_plugin.cpp
@@ -208,6 +208,6 @@ bool EditorInspectorPluginOpenTypeFeatures::parse_property(Object *p_object, Var
OpenTypeFeaturesEditorPlugin::OpenTypeFeaturesEditorPlugin(EditorNode *p_node) {
Ref<EditorInspectorPluginOpenTypeFeatures> ftr_plugin;
- ftr_plugin.instance();
+ ftr_plugin.instantiate();
EditorInspector::add_inspector_plugin(ftr_plugin);
}
diff --git a/editor/plugins/path_3d_editor_plugin.cpp b/editor/plugins/path_3d_editor_plugin.cpp
index b0eb13c3c6..82b51f8a06 100644
--- a/editor/plugins/path_3d_editor_plugin.cpp
+++ b/editor/plugins/path_3d_editor_plugin.cpp
@@ -554,7 +554,7 @@ Path3DEditorPlugin::Path3DEditorPlugin(EditorNode *p_node) {
mirror_handle_length = true;
Ref<Path3DGizmoPlugin> gizmo_plugin;
- gizmo_plugin.instance();
+ gizmo_plugin.instantiate();
Node3DEditor::get_singleton()->add_gizmo_plugin(gizmo_plugin);
sep = memnew(VSeparator);
diff --git a/editor/plugins/polygon_2d_editor_plugin.cpp b/editor/plugins/polygon_2d_editor_plugin.cpp
index 8a14db0cfd..1a13a028c8 100644
--- a/editor/plugins/polygon_2d_editor_plugin.cpp
+++ b/editor/plugins/polygon_2d_editor_plugin.cpp
@@ -162,7 +162,7 @@ void Polygon2DEditor::_update_bone_list() {
}
Ref<ButtonGroup> bg;
- bg.instance();
+ bg.instantiate();
for (int i = 0; i < node->get_bone_count(); i++) {
CheckBox *cb = memnew(CheckBox);
NodePath np = node->get_bone_path(i);
@@ -1231,7 +1231,7 @@ Polygon2DEditor::Polygon2DEditor(EditorNode *p_editor) :
uv_edit->add_child(uv_main_vb);
HBoxContainer *uv_mode_hb = memnew(HBoxContainer);
- uv_edit_group.instance();
+ uv_edit_group.instantiate();
uv_edit_mode[0] = memnew(Button);
uv_mode_hb->add_child(uv_edit_mode[0]);
diff --git a/editor/plugins/resource_preloader_editor_plugin.cpp b/editor/plugins/resource_preloader_editor_plugin.cpp
index b8b2c6d343..a7c11f8521 100644
--- a/editor/plugins/resource_preloader_editor_plugin.cpp
+++ b/editor/plugins/resource_preloader_editor_plugin.cpp
@@ -367,8 +367,8 @@ ResourcePreloaderEditor::ResourcePreloaderEditor() {
tree = memnew(Tree);
tree->connect("button_pressed", callable_mp(this, &ResourcePreloaderEditor::_cell_button_pressed));
tree->set_columns(2);
- tree->set_column_min_width(0, 2);
- tree->set_column_min_width(1, 3);
+ tree->set_column_custom_minimum_width(0, 2);
+ tree->set_column_custom_minimum_width(1, 3);
tree->set_column_expand(0, true);
tree->set_column_expand(1, true);
tree->set_v_size_flags(SIZE_EXPAND_FILL);
diff --git a/editor/plugins/script_editor_plugin.cpp b/editor/plugins/script_editor_plugin.cpp
index 0410ab3a45..498d5b0711 100644
--- a/editor/plugins/script_editor_plugin.cpp
+++ b/editor/plugins/script_editor_plugin.cpp
@@ -71,7 +71,7 @@ Array EditorSyntaxHighlighter::_get_supported_languages() const {
Ref<EditorSyntaxHighlighter> EditorSyntaxHighlighter::_create() const {
Ref<EditorSyntaxHighlighter> syntax_highlighter;
- syntax_highlighter.instance();
+ syntax_highlighter.instantiate();
if (get_script_instance()) {
syntax_highlighter->set_script(get_script_instance()->get_script());
}
@@ -201,7 +201,7 @@ void EditorStandardSyntaxHighlighter::_update_cache() {
Ref<EditorSyntaxHighlighter> EditorStandardSyntaxHighlighter::_create() const {
Ref<EditorStandardSyntaxHighlighter> syntax_highlighter;
- syntax_highlighter.instance();
+ syntax_highlighter.instantiate();
return syntax_highlighter;
}
@@ -209,7 +209,7 @@ Ref<EditorSyntaxHighlighter> EditorStandardSyntaxHighlighter::_create() const {
Ref<EditorSyntaxHighlighter> EditorPlainTextSyntaxHighlighter::_create() const {
Ref<EditorPlainTextSyntaxHighlighter> syntax_highlighter;
- syntax_highlighter.instance();
+ syntax_highlighter.instantiate();
return syntax_highlighter;
}
@@ -760,6 +760,7 @@ void ScriptEditor::_close_tab(int p_idx, bool p_save, bool p_history_back) {
_update_members_overview_visibility();
_update_help_overview_visibility();
_save_layout();
+ _update_find_replace_bar();
}
void ScriptEditor::_close_current_tab(bool p_save) {
@@ -829,6 +830,7 @@ void ScriptEditor::_close_all_tabs() {
_close_current_tab(false);
}
+ _update_find_replace_bar();
}
void ScriptEditor::_ask_close_current_unsaved_tab(ScriptEditorBase *current) {
@@ -1629,7 +1631,7 @@ void ScriptEditor::_help_overview_selected(int p_idx) {
}
void ScriptEditor::_script_selected(int p_idx) {
- grab_focus_block = !Input::get_singleton()->is_mouse_button_pressed(1); //amazing hack, simply amazing
+ grab_focus_block = !Input::get_singleton()->is_mouse_button_pressed(MOUSE_BUTTON_LEFT); //amazing hack, simply amazing
_go_to_tab(script_list->get_item_metadata(p_idx));
grab_focus_block = false;
@@ -1640,15 +1642,13 @@ void ScriptEditor::ensure_select_current() {
ScriptEditorBase *se = _get_current_editor();
if (se) {
se->enable_editor();
- se->set_find_replace_bar(find_replace_bar);
if (!grab_focus_block && is_visible_in_tree()) {
se->ensure_focus();
}
- } else {
- find_replace_bar->hide();
}
}
+ _update_find_replace_bar();
_update_selected_editor_menu();
}
@@ -2520,6 +2520,16 @@ void ScriptEditor::_file_removed(const String &p_removed_file) {
}
}
+void ScriptEditor::_update_find_replace_bar() {
+ ScriptEditorBase *se = _get_current_editor();
+ if (se) {
+ se->set_find_replace_bar(find_replace_bar);
+ } else {
+ find_replace_bar->set_text_edit(nullptr);
+ find_replace_bar->hide();
+ }
+}
+
void ScriptEditor::_autosave_scripts() {
save_all_scripts();
}
@@ -2771,6 +2781,8 @@ void ScriptEditor::_script_list_gui_input(const Ref<InputEvent> &ev) {
case MOUSE_BUTTON_RIGHT: {
_make_script_list_context_menu();
} break;
+ default:
+ break;
}
}
}
diff --git a/editor/plugins/script_editor_plugin.h b/editor/plugins/script_editor_plugin.h
index 1d379059d4..72a649ffbf 100644
--- a/editor/plugins/script_editor_plugin.h
+++ b/editor/plugins/script_editor_plugin.h
@@ -80,7 +80,7 @@ public:
virtual Ref<EditorSyntaxHighlighter> _create() const override;
- EditorStandardSyntaxHighlighter() { highlighter.instance(); }
+ EditorStandardSyntaxHighlighter() { highlighter.instantiate(); }
};
class EditorPlainTextSyntaxHighlighter : public EditorSyntaxHighlighter {
@@ -328,6 +328,7 @@ class ScriptEditor : public PanelContainer {
void _show_error_dialog(String p_path);
void _close_tab(int p_idx, bool p_save = true, bool p_history_back = true);
+ void _update_find_replace_bar();
void _close_current_tab(bool p_save = true);
void _close_discard_current_tab(const String &p_str);
diff --git a/editor/plugins/script_text_editor.cpp b/editor/plugins/script_text_editor.cpp
index 3ec20ae68e..5fc1f74089 100644
--- a/editor/plugins/script_text_editor.cpp
+++ b/editor/plugins/script_text_editor.cpp
@@ -109,13 +109,11 @@ ConnectionInfoDialog::ConnectionInfoDialog() {
////////////////////////////////////////////////////////////////////////////////
Vector<String> ScriptTextEditor::get_functions() {
- String errortxt;
- int line = -1, col;
CodeEdit *te = code_editor->get_text_editor();
String text = te->get_text();
List<String> fnc;
- if (script->get_language()->validate(text, line, col, errortxt, script->get_path(), &fnc)) {
+ if (script->get_language()->validate(text, script->get_path(), &fnc)) {
//if valid rewrite functions to latest
functions.clear();
for (List<String>::Element *E = fnc.front(); E; E = E->next()) {
@@ -168,7 +166,6 @@ void ScriptTextEditor::enable_editor() {
void ScriptTextEditor::_load_theme_settings() {
CodeEdit *text_edit = code_editor->get_text_editor();
- text_edit->clear_keywords();
Color updated_marked_line_color = EDITOR_GET("text_editor/highlighting/mark_color");
Color updated_safe_line_number_color = EDITOR_GET("text_editor/highlighting/safe_line_number_color");
@@ -222,47 +219,10 @@ void ScriptTextEditor::_set_theme_for_script() {
String end = comment.get_slice_count(" ") > 1 ? comment.get_slice(" ", 1) : String();
text_edit->add_comment_delimiter(beg, end, end == "");
}
+}
- /* add keywords for auto completion */
- // singleton autoloads (as types, just as engine singletons are)
- Map<StringName, ProjectSettings::AutoloadInfo> autoloads = ProjectSettings::get_singleton()->get_autoload_list();
- for (Map<StringName, ProjectSettings::AutoloadInfo>::Element *E = autoloads.front(); E; E = E->next()) {
- const ProjectSettings::AutoloadInfo &info = E->value();
- if (info.is_singleton) {
- text_edit->add_keyword(info.name);
- }
- }
-
- // engine types
- List<StringName> types;
- ClassDB::get_class_list(&types);
- for (List<StringName>::Element *E = types.front(); E; E = E->next()) {
- String n = E->get();
- if (n.begins_with("_")) {
- n = n.substr(1, n.length());
- }
- text_edit->add_keyword(n);
- }
-
- // user types
- List<StringName> global_classes;
- ScriptServer::get_global_class_list(&global_classes);
- for (List<StringName>::Element *E = global_classes.front(); E; E = E->next()) {
- text_edit->add_keyword(E->get());
- }
-
- List<String> keywords;
- script->get_language()->get_reserved_words(&keywords);
- for (List<String>::Element *E = keywords.front(); E; E = E->next()) {
- text_edit->add_keyword(E->get());
- }
-
- // core types
- List<String> core_types;
- script->get_language()->get_core_type_words(&core_types);
- for (List<String>::Element *E = core_types.front(); E; E = E->next()) {
- text_edit->add_keyword(E->get());
- }
+void ScriptTextEditor::_show_errors_panel(bool p_show) {
+ errors_panel->set_visible(p_show);
}
void ScriptTextEditor::_show_warnings_panel(bool p_show) {
@@ -279,6 +239,12 @@ void ScriptTextEditor::_warning_clicked(Variant p_line) {
}
}
+void ScriptTextEditor::_error_clicked(Variant p_line) {
+ if (p_line.get_type() == Variant::INT) {
+ code_editor->get_text_editor()->cursor_set_line(p_line.operator int64_t());
+ }
+}
+
void ScriptTextEditor::reload_text() {
ERR_FAIL_COND(script.is_null());
@@ -429,23 +395,21 @@ Ref<Texture2D> ScriptTextEditor::get_theme_icon() {
}
void ScriptTextEditor::_validate_script() {
- String errortxt;
- int line = -1, col;
CodeEdit *te = code_editor->get_text_editor();
String text = te->get_text();
List<String> fnc;
Set<int> safe_lines;
List<ScriptLanguage::Warning> warnings;
+ List<ScriptLanguage::ScriptError> errors;
- if (!script->get_language()->validate(text, line, col, errortxt, script->get_path(), &fnc, &warnings, &safe_lines)) {
- String error_text = "error(" + itos(line) + "," + itos(col) + "): " + errortxt;
+ if (!script->get_language()->validate(text, script->get_path(), &fnc, &errors, &warnings, &safe_lines)) {
+ String error_text = TTR("Error at ") + "(" + itos(errors[0].line) + "," + itos(errors[0].column) + "): " + errors[0].message;
code_editor->set_error(error_text);
- code_editor->set_error_pos(line - 1, col - 1);
+ code_editor->set_error_pos(errors[0].line - 1, errors[0].column - 1);
script_is_valid = false;
} else {
code_editor->set_error("");
- line = -1;
if (!script->is_tool()) {
script->set_source_code(text);
script->update_exports();
@@ -487,7 +451,8 @@ void ScriptTextEditor::_validate_script() {
}
}
- code_editor->set_warning_nb(warning_nb);
+ code_editor->set_error_count(errors.size());
+ code_editor->set_warning_count(warning_nb);
// Add script warnings.
warnings_panel->push_table(3);
@@ -521,23 +486,52 @@ void ScriptTextEditor::_validate_script() {
}
warnings_panel->pop(); // Table.
- line--;
+ errors_panel->clear();
+ errors_panel->push_table(2);
+ for (List<ScriptLanguage::ScriptError>::Element *E = errors.front(); E; E = E->next()) {
+ ScriptLanguage::ScriptError err = E->get();
+
+ errors_panel->push_cell();
+ errors_panel->push_meta(err.line - 1);
+ errors_panel->push_color(warnings_panel->get_theme_color("error_color", "Editor"));
+ errors_panel->add_text(TTR("Line") + " " + itos(err.line) + ":");
+ errors_panel->pop(); // Color.
+ errors_panel->pop(); // Meta goto.
+ errors_panel->pop(); // Cell.
+
+ errors_panel->push_cell();
+ errors_panel->add_text(err.message);
+ errors_panel->pop(); // Cell.
+ }
+ errors_panel->pop(); // Table
+
bool highlight_safe = EDITOR_DEF("text_editor/highlighting/highlight_type_safe_lines", true);
bool last_is_safe = false;
for (int i = 0; i < te->get_line_count(); i++) {
- te->set_line_background_color(i, (line == i) ? marked_line_color : Color(0, 0, 0, 0));
+ if (errors.is_empty()) {
+ te->set_line_background_color(i, Color(0, 0, 0, 0));
+ } else {
+ for (List<ScriptLanguage::ScriptError>::Element *E = errors.front(); E; E = E->next()) {
+ bool error_line = i == E->get().line - 1;
+ te->set_line_background_color(i, error_line ? marked_line_color : Color(0, 0, 0, 0));
+ if (error_line) {
+ break;
+ }
+ }
+ }
+
if (highlight_safe) {
if (safe_lines.has(i + 1)) {
te->set_line_gutter_item_color(i, line_number_gutter, safe_line_number_color);
last_is_safe = true;
- } else if (last_is_safe && (te->is_line_comment(i) || te->get_line(i).strip_edges().is_empty())) {
+ } else if (last_is_safe && (te->is_in_comment(i) != -1 || te->get_line(i).strip_edges().is_empty())) {
te->set_line_gutter_item_color(i, line_number_gutter, safe_line_number_color);
} else {
te->set_line_gutter_item_color(i, line_number_gutter, default_line_number_color);
last_is_safe = false;
}
} else {
- te->set_line_gutter_item_color(line, 1, default_line_number_color);
+ te->set_line_gutter_item_color(i, 1, default_line_number_color);
}
}
@@ -1044,7 +1038,7 @@ void ScriptTextEditor::_edit_option(int p_op) {
return;
}
- tx->indent_selected_lines_left();
+ tx->unindent_lines();
} break;
case EDIT_INDENT_RIGHT: {
Ref<Script> scr = script;
@@ -1052,7 +1046,7 @@ void ScriptTextEditor::_edit_option(int p_op) {
return;
}
- tx->indent_selected_lines_right();
+ tx->indent_lines();
} break;
case EDIT_DELETE_LINE: {
code_editor->delete_lines();
@@ -1675,6 +1669,7 @@ void ScriptTextEditor::_enable_code_editor() {
editor_box->set_v_size_flags(SIZE_EXPAND_FILL);
editor_box->add_child(code_editor);
+ code_editor->connect("show_errors_panel", callable_mp(this, &ScriptTextEditor::_show_errors_panel));
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));
@@ -1695,6 +1690,13 @@ void ScriptTextEditor::_enable_code_editor() {
"normal_font_size", EditorNode::get_singleton()->get_gui_base()->get_theme_font_size("main_size", "EditorFonts"));
warnings_panel->connect("meta_clicked", callable_mp(this, &ScriptTextEditor::_warning_clicked));
+ editor_box->add_child(errors_panel);
+ errors_panel->add_theme_font_override(
+ "normal_font", EditorNode::get_singleton()->get_gui_base()->get_theme_font("main", "EditorFonts"));
+ errors_panel->add_theme_font_size_override(
+ "normal_font_size", EditorNode::get_singleton()->get_gui_base()->get_theme_font_size("main_size", "EditorFonts"));
+ errors_panel->connect("meta_clicked", callable_mp(this, &ScriptTextEditor::_error_clicked));
+
add_child(context_menu);
context_menu->connect("id_pressed", callable_mp(this, &ScriptTextEditor::_edit_option));
@@ -1826,6 +1828,14 @@ ScriptTextEditor::ScriptTextEditor() {
warnings_panel->set_focus_mode(FOCUS_CLICK);
warnings_panel->hide();
+ errors_panel = memnew(RichTextLabel);
+ errors_panel->set_custom_minimum_size(Size2(0, 100 * EDSCALE));
+ errors_panel->set_h_size_flags(SIZE_EXPAND_FILL);
+ errors_panel->set_meta_underline(true);
+ errors_panel->set_selection_enabled(true);
+ errors_panel->set_focus_mode(FOCUS_CLICK);
+ errors_panel->hide();
+
update_settings();
code_editor->get_text_editor()->set_code_hint_draw_below(EditorSettings::get_singleton()->get("text_editor/completion/put_callhint_tooltip_below_current_line"));
@@ -1851,11 +1861,11 @@ ScriptTextEditor::ScriptTextEditor() {
highlighter_menu->set_name("highlighter_menu");
Ref<EditorPlainTextSyntaxHighlighter> plain_highlighter;
- plain_highlighter.instance();
+ plain_highlighter.instantiate();
add_syntax_highlighter(plain_highlighter);
Ref<EditorStandardSyntaxHighlighter> highlighter;
- highlighter.instance();
+ highlighter.instantiate();
add_syntax_highlighter(highlighter);
set_syntax_highlighter(highlighter);
@@ -1886,6 +1896,7 @@ ScriptTextEditor::~ScriptTextEditor() {
if (!editor_enabled) {
memdelete(code_editor);
memdelete(warnings_panel);
+ memdelete(errors_panel);
memdelete(context_menu);
memdelete(color_panel);
memdelete(edit_hb);
diff --git a/editor/plugins/script_text_editor.h b/editor/plugins/script_text_editor.h
index 7bb961bf19..8a8e9aa737 100644
--- a/editor/plugins/script_text_editor.h
+++ b/editor/plugins/script_text_editor.h
@@ -55,6 +55,7 @@ class ScriptTextEditor : public ScriptEditorBase {
CodeTextEditor *code_editor = nullptr;
RichTextLabel *warnings_panel = nullptr;
+ RichTextLabel *errors_panel = nullptr;
Ref<Script> script;
bool script_is_valid = false;
@@ -161,7 +162,9 @@ protected:
void _load_theme_settings();
void _set_theme_for_script();
+ void _show_errors_panel(bool p_show);
void _show_warnings_panel(bool p_show);
+ void _error_clicked(Variant p_line);
void _warning_clicked(Variant p_line);
void _notification(int p_what);
diff --git a/editor/plugins/shader_editor_plugin.cpp b/editor/plugins/shader_editor_plugin.cpp
index e4a5a3796e..173f1dd7fb 100644
--- a/editor/plugins/shader_editor_plugin.cpp
+++ b/editor/plugins/shader_editor_plugin.cpp
@@ -240,7 +240,7 @@ void ShaderTextEditor::_validate_script() {
warnings.sort_custom<WarningsComparator>();
_update_warning_panel();
} else {
- set_warning_nb(0);
+ set_warning_count(0);
}
emit_signal("script_changed");
}
@@ -280,14 +280,14 @@ void ShaderTextEditor::_update_warning_panel() {
}
warnings_panel->pop(); // Table.
- set_warning_nb(warning_count);
+ set_warning_count(warning_count);
}
void ShaderTextEditor::_bind_methods() {
}
ShaderTextEditor::ShaderTextEditor() {
- syntax_highlighter.instance();
+ syntax_highlighter.instantiate();
get_text_editor()->set_syntax_highlighter(syntax_highlighter);
}
@@ -323,19 +323,13 @@ void ShaderEditor::_menu_option(int p_option) {
if (shader.is_null()) {
return;
}
-
- CodeEdit *tx = shader_editor->get_text_editor();
- tx->indent_selected_lines_left();
-
+ shader_editor->get_text_editor()->unindent_lines();
} break;
case EDIT_INDENT_RIGHT: {
if (shader.is_null()) {
return;
}
-
- CodeEdit *tx = shader_editor->get_text_editor();
- tx->indent_selected_lines_right();
-
+ shader_editor->get_text_editor()->indent_lines();
} break;
case EDIT_DELETE_LINE: {
shader_editor->delete_lines();
diff --git a/editor/plugins/shader_file_editor_plugin.cpp b/editor/plugins/shader_file_editor_plugin.cpp
index 47d7f8204b..85ccc5b798 100644
--- a/editor/plugins/shader_file_editor_plugin.cpp
+++ b/editor/plugins/shader_file_editor_plugin.cpp
@@ -272,7 +272,7 @@ ShaderFileEditor::ShaderFileEditor(EditorNode *p_node) {
main_vb->add_child(stage_hb);
Ref<ButtonGroup> bg;
- bg.instance();
+ bg.instantiate();
for (int i = 0; i < RD::SHADER_STAGE_MAX; i++) {
Button *button = memnew(Button(stage_str[i]));
button->set_toggle_mode(true);
diff --git a/editor/plugins/skeleton_3d_editor_plugin.cpp b/editor/plugins/skeleton_3d_editor_plugin.cpp
index a97584ebce..0b04c2e50e 100644
--- a/editor/plugins/skeleton_3d_editor_plugin.cpp
+++ b/editor/plugins/skeleton_3d_editor_plugin.cpp
@@ -700,7 +700,7 @@ Skeleton3DEditorPlugin::Skeleton3DEditorPlugin(EditorNode *p_node) {
editor = p_node;
Ref<EditorInspectorPluginSkeleton> skeleton_plugin;
- skeleton_plugin.instance();
+ skeleton_plugin.instantiate();
skeleton_plugin->editor = editor;
EditorInspector::add_inspector_plugin(skeleton_plugin);
diff --git a/editor/plugins/sprite_2d_editor_plugin.cpp b/editor/plugins/sprite_2d_editor_plugin.cpp
index 4a7f6c0f7e..ef328bcfe2 100644
--- a/editor/plugins/sprite_2d_editor_plugin.cpp
+++ b/editor/plugins/sprite_2d_editor_plugin.cpp
@@ -186,7 +186,7 @@ void Sprite2DEditor::_update_mesh_data() {
}
Ref<BitMap> bm;
- bm.instance();
+ bm.instantiate();
bm->create_from_image_alpha(image);
int shrink = shrink_pixels->get_value();
@@ -322,7 +322,7 @@ void Sprite2DEditor::_convert_to_mesh_2d_node() {
}
Ref<ArrayMesh> mesh;
- mesh.instance();
+ mesh.instantiate();
Array a;
a.resize(Mesh::ARRAY_MAX);
@@ -435,7 +435,7 @@ void Sprite2DEditor::_create_light_occluder_2d_node() {
Vector<Vector2> outline = computed_outline_lines[i];
Ref<OccluderPolygon2D> polygon;
- polygon.instance();
+ polygon.instantiate();
PackedVector2Array a;
a.resize(outline.size());
diff --git a/editor/plugins/sprite_frames_editor_plugin.cpp b/editor/plugins/sprite_frames_editor_plugin.cpp
index af72f59c1c..70c7b3072b 100644
--- a/editor/plugins/sprite_frames_editor_plugin.cpp
+++ b/editor/plugins/sprite_frames_editor_plugin.cpp
@@ -227,7 +227,7 @@ void SpriteFramesEditor::_sheet_add_frames() {
int y = (yp * height) + region_rect.position.y;
Ref<AtlasTexture> at;
- at.instance();
+ at.instantiate();
at->set_atlas(split_sheet_preview->get_texture());
at->set_region(Rect2(x, y, width, height));
diff --git a/editor/plugins/style_box_editor_plugin.cpp b/editor/plugins/style_box_editor_plugin.cpp
index 64df982d5d..6954cacac6 100644
--- a/editor/plugins/style_box_editor_plugin.cpp
+++ b/editor/plugins/style_box_editor_plugin.cpp
@@ -93,6 +93,6 @@ StyleBoxPreview::StyleBoxPreview() {
StyleBoxEditorPlugin::StyleBoxEditorPlugin(EditorNode *p_node) {
Ref<EditorInspectorPluginStyleBox> inspector_plugin;
- inspector_plugin.instance();
+ inspector_plugin.instantiate();
add_inspector_plugin(inspector_plugin);
}
diff --git a/editor/plugins/text_editor.cpp b/editor/plugins/text_editor.cpp
index 621f843e6f..d62be993af 100644
--- a/editor/plugins/text_editor.cpp
+++ b/editor/plugins/text_editor.cpp
@@ -320,10 +320,10 @@ void TextEditor::_edit_option(int p_op) {
code_editor->move_lines_down();
} break;
case EDIT_INDENT_LEFT: {
- tx->indent_selected_lines_left();
+ tx->unindent_lines();
} break;
case EDIT_INDENT_RIGHT: {
- tx->indent_selected_lines_right();
+ tx->indent_lines();
} break;
case EDIT_DELETE_LINE: {
code_editor->delete_lines();
@@ -581,11 +581,11 @@ TextEditor::TextEditor() {
highlighter_menu->connect("id_pressed", callable_mp(this, &TextEditor::_change_syntax_highlighter));
Ref<EditorPlainTextSyntaxHighlighter> plain_highlighter;
- plain_highlighter.instance();
+ plain_highlighter.instantiate();
add_syntax_highlighter(plain_highlighter);
Ref<EditorStandardSyntaxHighlighter> highlighter;
- highlighter.instance();
+ highlighter.instantiate();
add_syntax_highlighter(highlighter);
set_syntax_highlighter(plain_highlighter);
diff --git a/editor/plugins/texture_3d_editor_plugin.cpp b/editor/plugins/texture_3d_editor_plugin.cpp
index 36297c8a4a..696aa88e23 100644
--- a/editor/plugins/texture_3d_editor_plugin.cpp
+++ b/editor/plugins/texture_3d_editor_plugin.cpp
@@ -85,9 +85,9 @@ void Texture3DEditor::_make_shaders() {
" COLOR = textureLod(tex,vec3(UV,layer),0.0);\n"
"}";
- shader.instance();
+ shader.instantiate();
shader->set_code(shader_3d);
- material.instance();
+ material.instantiate();
material->set_shader(shader);
}
@@ -207,6 +207,6 @@ void EditorInspectorPlugin3DTexture::parse_begin(Object *p_object) {
Texture3DEditorPlugin::Texture3DEditorPlugin(EditorNode *p_node) {
Ref<EditorInspectorPlugin3DTexture> plugin;
- plugin.instance();
+ plugin.instantiate();
add_inspector_plugin(plugin);
}
diff --git a/editor/plugins/texture_editor_plugin.cpp b/editor/plugins/texture_editor_plugin.cpp
index ecf7370834..10b942d9ee 100644
--- a/editor/plugins/texture_editor_plugin.cpp
+++ b/editor/plugins/texture_editor_plugin.cpp
@@ -160,6 +160,6 @@ void EditorInspectorPluginTexture::parse_begin(Object *p_object) {
TextureEditorPlugin::TextureEditorPlugin(EditorNode *p_node) {
Ref<EditorInspectorPluginTexture> plugin;
- plugin.instance();
+ plugin.instantiate();
add_inspector_plugin(plugin);
}
diff --git a/editor/plugins/texture_layered_editor_plugin.cpp b/editor/plugins/texture_layered_editor_plugin.cpp
index 89ed98d53e..3f46cd64a2 100644
--- a/editor/plugins/texture_layered_editor_plugin.cpp
+++ b/editor/plugins/texture_layered_editor_plugin.cpp
@@ -112,7 +112,7 @@ void TextureLayeredEditor::_make_shaders() {
" COLOR = textureLod(tex,vec3(UV,layer),0.0);\n"
"}";
- shaders[0].instance();
+ shaders[0].instantiate();
shaders[0]->set_code(shader_2d_array);
String shader_cube = ""
@@ -125,7 +125,7 @@ void TextureLayeredEditor::_make_shaders() {
" COLOR = textureLod(tex,n,0.0);\n"
"}";
- shaders[1].instance();
+ shaders[1].instantiate();
shaders[1]->set_code(shader_cube);
String shader_cube_array = ""
@@ -139,11 +139,11 @@ void TextureLayeredEditor::_make_shaders() {
" COLOR = textureLod(tex,vec4(n,layer),0.0);\n"
"}";
- shaders[2].instance();
+ shaders[2].instantiate();
shaders[2]->set_code(shader_cube_array);
for (int i = 0; i < 3; i++) {
- materials[i].instance();
+ materials[i].instantiate();
materials[i]->set_shader(shaders[i]);
}
}
@@ -271,6 +271,6 @@ void EditorInspectorPluginLayeredTexture::parse_begin(Object *p_object) {
TextureLayeredEditorPlugin::TextureLayeredEditorPlugin(EditorNode *p_node) {
Ref<EditorInspectorPluginLayeredTexture> plugin;
- plugin.instance();
+ plugin.instantiate();
add_inspector_plugin(plugin);
}
diff --git a/editor/plugins/theme_editor_plugin.cpp b/editor/plugins/theme_editor_plugin.cpp
index 22b39c59f5..99d7267eac 100644
--- a/editor/plugins/theme_editor_plugin.cpp
+++ b/editor/plugins/theme_editor_plugin.cpp
@@ -932,9 +932,9 @@ ThemeItemImportTree::ThemeItemImportTree() {
import_items_tree->set_column_expand(0, true);
import_items_tree->set_column_expand(IMPORT_ITEM, false);
import_items_tree->set_column_expand(IMPORT_ITEM_DATA, false);
- import_items_tree->set_column_min_width(0, 160 * EDSCALE);
- import_items_tree->set_column_min_width(IMPORT_ITEM, 80 * EDSCALE);
- import_items_tree->set_column_min_width(IMPORT_ITEM_DATA, 80 * EDSCALE);
+ import_items_tree->set_column_custom_minimum_width(0, 160 * EDSCALE);
+ import_items_tree->set_column_custom_minimum_width(IMPORT_ITEM, 80 * EDSCALE);
+ import_items_tree->set_column_custom_minimum_width(IMPORT_ITEM_DATA, 80 * EDSCALE);
ScrollContainer *import_bulk_sc = memnew(ScrollContainer);
import_bulk_sc->set_custom_minimum_size(Size2(260.0, 0.0) * EDSCALE);
@@ -2263,7 +2263,7 @@ void ThemeTypeEditor::_update_type_items() {
} else {
item_editor->set_edited_resource(RES());
}
- item_editor->connect("resource_selected", callable_mp(this, &ThemeTypeEditor::_edit_resource_item), varray(item_control));
+ item_editor->connect("resource_selected", callable_mp(this, &ThemeTypeEditor::_edit_resource_item));
item_editor->connect("resource_changed", callable_mp(this, &ThemeTypeEditor::_font_item_changed), varray(E.key()));
} else {
if (Theme::get_default()->has_font(E.key(), edited_type)) {
@@ -2334,7 +2334,7 @@ void ThemeTypeEditor::_update_type_items() {
} else {
item_editor->set_edited_resource(RES());
}
- item_editor->connect("resource_selected", callable_mp(this, &ThemeTypeEditor::_edit_resource_item), varray(item_control));
+ item_editor->connect("resource_selected", callable_mp(this, &ThemeTypeEditor::_edit_resource_item));
item_editor->connect("resource_changed", callable_mp(this, &ThemeTypeEditor::_icon_item_changed), varray(E.key()));
} else {
if (Theme::get_default()->has_icon(E.key(), edited_type)) {
@@ -2381,7 +2381,7 @@ void ThemeTypeEditor::_update_type_items() {
} else {
item_editor->set_edited_resource(RES());
}
- item_editor->connect("resource_selected", callable_mp(this, &ThemeTypeEditor::_edit_resource_item), varray(item_control));
+ item_editor->connect("resource_selected", callable_mp(this, &ThemeTypeEditor::_edit_resource_item));
item_editor->connect("resource_changed", callable_mp(this, &ThemeTypeEditor::_stylebox_item_changed), varray(leading_stylebox.item_name));
stylebox_items_list->add_child(item_control);
@@ -2408,7 +2408,7 @@ void ThemeTypeEditor::_update_type_items() {
} else {
item_editor->set_edited_resource(RES());
}
- item_editor->connect("resource_selected", callable_mp(this, &ThemeTypeEditor::_edit_resource_item), varray(item_control));
+ item_editor->connect("resource_selected", callable_mp(this, &ThemeTypeEditor::_edit_resource_item));
item_editor->connect("resource_changed", callable_mp(this, &ThemeTypeEditor::_stylebox_item_changed), varray(E.key()));
Button *pin_leader_button = memnew(Button);
@@ -2417,7 +2417,7 @@ void ThemeTypeEditor::_update_type_items() {
pin_leader_button->set_icon(get_theme_icon("Pin", "EditorIcons"));
pin_leader_button->set_tooltip(TTR("Pin this StyleBox as a main style. Editing its properties will update the same properties in all other StyleBoxes of this type."));
item_control->add_child(pin_leader_button);
- pin_leader_button->connect("pressed", callable_mp(this, &ThemeTypeEditor::_pin_leading_stylebox), varray(stylebox_value, E.key()));
+ pin_leader_button->connect("pressed", callable_mp(this, &ThemeTypeEditor::_pin_leading_stylebox), varray(item_editor, E.key()));
} else {
if (Theme::get_default()->has_stylebox(E.key(), edited_type)) {
item_editor->set_edited_resource(Theme::get_default()->get_stylebox(E.key(), edited_type));
@@ -2612,6 +2612,10 @@ void ThemeTypeEditor::_item_remove_cbk(int p_data_type, String p_item_name) {
} break;
case Theme::DATA_TYPE_STYLEBOX: {
edited_theme->clear_stylebox(p_item_name, edited_type);
+
+ if (leading_stylebox.pinned && leading_stylebox.item_name == p_item_name) {
+ _unpin_leading_stylebox();
+ }
} break;
}
}
@@ -2661,6 +2665,10 @@ void ThemeTypeEditor::_item_rename_confirmed(int p_data_type, String p_item_name
} break;
case Theme::DATA_TYPE_STYLEBOX: {
edited_theme->rename_stylebox(p_item_name, new_name, edited_type);
+
+ if (leading_stylebox.pinned && leading_stylebox.item_name == p_item_name) {
+ leading_stylebox.item_name = new_name;
+ }
} break;
}
}
@@ -2695,7 +2703,7 @@ void ThemeTypeEditor::_font_size_item_changed(float p_value, String p_item_name)
edited_theme->set_font_size(p_item_name, edited_type, int(p_value));
}
-void ThemeTypeEditor::_edit_resource_item(RES p_resource, Control *p_editor) {
+void ThemeTypeEditor::_edit_resource_item(RES p_resource) {
EditorNode::get_singleton()->edit_resource(p_resource);
}
@@ -2723,16 +2731,21 @@ void ThemeTypeEditor::_stylebox_item_changed(Ref<StyleBox> p_value, String p_ite
}
}
-void ThemeTypeEditor::_pin_leading_stylebox(Ref<StyleBox> p_stylebox, String p_item_name) {
+void ThemeTypeEditor::_pin_leading_stylebox(Control *p_editor, String p_item_name) {
if (leading_stylebox.stylebox.is_valid()) {
leading_stylebox.stylebox->disconnect("changed", callable_mp(this, &ThemeTypeEditor::_update_stylebox_from_leading));
}
+ Ref<StyleBox> stylebox;
+ if (Object::cast_to<EditorResourcePicker>(p_editor)) {
+ stylebox = Object::cast_to<EditorResourcePicker>(p_editor)->get_edited_resource();
+ }
+
LeadingStylebox leader;
leader.pinned = true;
leader.item_name = p_item_name;
- leader.stylebox = p_stylebox;
- leader.ref_stylebox = (p_stylebox.is_valid() ? p_stylebox->duplicate() : RES());
+ leader.stylebox = stylebox;
+ leader.ref_stylebox = (stylebox.is_valid() ? stylebox->duplicate() : RES());
leading_stylebox = leader;
if (leading_stylebox.stylebox.is_valid()) {
diff --git a/editor/plugins/theme_editor_plugin.h b/editor/plugins/theme_editor_plugin.h
index 77baf46395..cdedbbec8d 100644
--- a/editor/plugins/theme_editor_plugin.h
+++ b/editor/plugins/theme_editor_plugin.h
@@ -329,11 +329,11 @@ class ThemeTypeEditor : public MarginContainer {
void _color_item_changed(Color p_value, String p_item_name);
void _constant_item_changed(float p_value, String p_item_name);
void _font_size_item_changed(float p_value, String p_item_name);
- void _edit_resource_item(RES p_resource, Control *p_editor);
+ void _edit_resource_item(RES p_resource);
void _font_item_changed(Ref<Font> p_value, String p_item_name);
void _icon_item_changed(Ref<Texture2D> p_value, String p_item_name);
void _stylebox_item_changed(Ref<StyleBox> p_value, String p_item_name);
- void _pin_leading_stylebox(Ref<StyleBox> p_stylebox, String p_item_name);
+ void _pin_leading_stylebox(Control *p_editor, String p_item_name);
void _unpin_leading_stylebox();
void _update_stylebox_from_leading();
diff --git a/editor/plugins/theme_editor_preview.cpp b/editor/plugins/theme_editor_preview.cpp
index cb7b5949d1..0b02150444 100644
--- a/editor/plugins/theme_editor_preview.cpp
+++ b/editor/plugins/theme_editor_preview.cpp
@@ -403,7 +403,7 @@ void SceneThemeEditorPreview::_reload_scene() {
preview_content->remove_child(node);
}
- Node *instance = loaded_scene->instance();
+ Node *instance = loaded_scene->instantiate();
if (!instance || !Object::cast_to<Control>(instance)) {
EditorNode::get_singleton()->show_warning(TTR("Invalid PackedScene resource, must have a Control node at its root."));
emit_signal("scene_invalidated");
@@ -435,7 +435,7 @@ bool SceneThemeEditorPreview::set_preview_scene(const String &p_path) {
return false;
}
- Node *instance = loaded_scene->instance();
+ Node *instance = loaded_scene->instantiate();
if (!instance || !Object::cast_to<Control>(instance)) {
EditorNode::get_singleton()->show_warning(TTR("Invalid PackedScene resource, must have a Control node at its root."));
return false;
diff --git a/editor/plugins/tiles/tile_atlas_view.cpp b/editor/plugins/tiles/tile_atlas_view.cpp
index 78f181e321..374a255df3 100644
--- a/editor/plugins/tiles/tile_atlas_view.cpp
+++ b/editor/plugins/tiles/tile_atlas_view.cpp
@@ -33,7 +33,6 @@
#include "core/input/input.h"
#include "core/os/keyboard.h"
#include "scene/gui/box_container.h"
-#include "scene/gui/center_container.h"
#include "scene/gui/label.h"
#include "scene/gui/panel.h"
#include "scene/gui/texture_rect.h"
@@ -44,21 +43,41 @@
void TileAtlasView::_gui_input(const Ref<InputEvent> &p_event) {
bool ctrl = Input::get_singleton()->is_key_pressed(KEY_CTRL);
- Ref<InputEventMouseButton> b = p_event;
- if (b.is_valid()) {
- if (ctrl && b->is_pressed() && b->get_button_index() == MOUSE_BUTTON_WHEEL_DOWN) {
+ Ref<InputEventMouseButton> mb = p_event;
+ if (mb.is_valid()) {
+ drag_type = DRAG_TYPE_NONE;
+ if (ctrl && mb->is_pressed() && mb->get_button_index() == MOUSE_BUTTON_WHEEL_DOWN) {
// Zoom out
zoom_widget->set_zoom_by_increments(-2);
- emit_signal("transform_changed", zoom_widget->get_zoom(), Vector2(scroll_container->get_h_scroll(), scroll_container->get_v_scroll()));
- _update_zoom(zoom_widget->get_zoom(), true);
+ emit_signal("transform_changed", zoom_widget->get_zoom(), panning);
+ _update_zoom_and_panning(true);
accept_event();
}
- if (ctrl && b->is_pressed() && b->get_button_index() == MOUSE_BUTTON_WHEEL_UP) {
+ if (ctrl && mb->is_pressed() && mb->get_button_index() == MOUSE_BUTTON_WHEEL_UP) {
// Zoom in
zoom_widget->set_zoom_by_increments(2);
- emit_signal("transform_changed", zoom_widget->get_zoom(), Vector2(scroll_container->get_h_scroll(), scroll_container->get_v_scroll()));
- _update_zoom(zoom_widget->get_zoom(), true);
+ emit_signal("transform_changed", zoom_widget->get_zoom(), panning);
+ _update_zoom_and_panning(true);
+ accept_event();
+ }
+
+ if (mb->get_button_index() == MOUSE_BUTTON_MIDDLE || mb->get_button_index() == MOUSE_BUTTON_RIGHT) {
+ if (mb->is_pressed()) {
+ drag_type = DRAG_TYPE_PAN;
+ } else {
+ drag_type = DRAG_TYPE_NONE;
+ }
+ accept_event();
+ }
+ }
+
+ Ref<InputEventMouseMotion> mm = p_event;
+ if (mm.is_valid()) {
+ if (drag_type == DRAG_TYPE_PAN) {
+ panning += mm->get_relative();
+ _update_zoom_and_panning();
+ emit_signal("transform_changed", zoom_widget->get_zoom(), panning);
accept_event();
}
}
@@ -103,25 +122,27 @@ Size2i TileAtlasView::_compute_alternative_tiles_control_size() {
return size;
}
-void TileAtlasView::_update_zoom(float p_zoom, bool p_zoom_on_mouse_pos, Vector2i p_scroll) {
+void TileAtlasView::_update_zoom_and_panning(bool p_zoom_on_mouse_pos) {
+ float zoom = zoom_widget->get_zoom();
+
// Compute the minimum sizes.
Size2i base_tiles_control_size = _compute_base_tiles_control_size();
- base_tiles_root_control->set_custom_minimum_size(Vector2(base_tiles_control_size) * p_zoom);
+ base_tiles_root_control->set_custom_minimum_size(Vector2(base_tiles_control_size) * zoom);
Size2i alternative_tiles_control_size = _compute_alternative_tiles_control_size();
- alternative_tiles_root_control->set_custom_minimum_size(Vector2(alternative_tiles_control_size) * p_zoom);
+ alternative_tiles_root_control->set_custom_minimum_size(Vector2(alternative_tiles_control_size) * zoom);
// Set the texture for the base tiles.
Ref<Texture2D> texture = tile_set_atlas_source->get_texture();
// Set the scales.
if (base_tiles_control_size.x > 0 && base_tiles_control_size.y > 0) {
- base_tiles_drawing_root->set_scale(Vector2(p_zoom, p_zoom));
+ base_tiles_drawing_root->set_scale(Vector2(zoom, zoom));
} else {
base_tiles_drawing_root->set_scale(Vector2(1, 1));
}
if (alternative_tiles_control_size.x > 0 && alternative_tiles_control_size.y > 0) {
- alternative_tiles_drawing_root->set_scale(Vector2(p_zoom, p_zoom));
+ alternative_tiles_drawing_root->set_scale(Vector2(zoom, zoom));
} else {
alternative_tiles_drawing_root->set_scale(Vector2(1, 1));
}
@@ -129,64 +150,40 @@ void TileAtlasView::_update_zoom(float p_zoom, bool p_zoom_on_mouse_pos, Vector2
// Update the margin container's margins.
const char *constants[] = { "margin_left", "margin_top", "margin_right", "margin_bottom" };
for (int i = 0; i < 4; i++) {
- margin_container->add_theme_constant_override(constants[i], margin_container_paddings[i] * p_zoom);
+ margin_container->add_theme_constant_override(constants[i], margin_container_paddings[i] * zoom);
}
// Update the backgrounds.
background_left->update();
background_right->update();
- if (p_scroll != Vector2i(-1, -1)) {
- scroll_container->set_h_scroll(p_scroll.x);
- scroll_container->set_v_scroll(p_scroll.y);
- }
-
// Zoom on the position.
- if (previous_zoom != p_zoom) {
- // TODO: solve this.
- // There is however an issue with scrollcainter preventing this, as it seems
- // that the scrollbars are not updated right aways after its children update.
-
- // Compute point on previous area.
- /*Vector2 max = Vector2(scroll_container->get_h_scrollbar()->get_max(), scroll_container->get_v_scrollbar()->get_max());
- Vector2 min = Vector2(scroll_container->get_h_scrollbar()->get_min(), scroll_container->get_v_scrollbar()->get_min());
- Vector2 value = Vector2(scroll_container->get_h_scrollbar()->get_value(), scroll_container->get_v_scrollbar()->get_value());
-
- Vector2 old_max = max * previous_zoom / p_zoom;
-
- Vector2 max_pixel_change = max - old_max;
- Vector2 ratio = ((value + scroll_container->get_local_mouse_position()) / old_max).max(Vector2()).min(Vector2(1,1));
- Vector2 offset = max_pixel_change * ratio;
-
- print_line("--- ZOOMED ---");
- print_line(vformat("max: %s", max));
- print_line(vformat("min: %s", min));
- print_line(vformat("value: %s", value));
- print_line(vformat("size: %s", scroll_container->get_size()));
- print_line(vformat("mouse_pos: %s", scroll_container->get_local_mouse_position()));
-
- print_line(vformat("ratio: %s", ratio));
- print_line(vformat("max_pixel_change: %s", max_pixel_change));
- print_line(vformat("offset: %s", offset));
-
+ if (p_zoom_on_mouse_pos) {
+ // Offset the panning relative to the center of panel.
+ Vector2 relative_mpos = get_local_mouse_position() - get_size() / 2;
+ panning = (panning - relative_mpos) * zoom / previous_zoom + relative_mpos;
+ } else {
+ // Center of panel.
+ panning = panning * zoom / previous_zoom;
+ }
+ button_center_view->set_disabled(panning.is_equal_approx(Vector2()));
- print_line(vformat("value before: %s", Vector2(scroll_container->get_h_scroll(), scroll_container->get_v_scroll())));
- scroll_container->set_h_scroll(10000);//scroll_container->get_h_scroll()+offset.x);
- scroll_container->set_v_scroll(10000);//scroll_container->get_v_scroll()+offset.y);
- print_line(vformat("value after: %s", Vector2(scroll_container->get_h_scroll(), scroll_container->get_v_scroll())));
- */
+ previous_zoom = zoom;
- previous_zoom = p_zoom;
- }
+ center_container->set_begin(panning - center_container->get_minimum_size() / 2);
+ center_container->set_size(center_container->get_minimum_size());
}
-void TileAtlasView::_scroll_changed() {
- emit_signal("transform_changed", zoom_widget->get_zoom(), Vector2(scroll_container->get_h_scroll(), scroll_container->get_v_scroll()));
+void TileAtlasView::_zoom_widget_changed() {
+ _update_zoom_and_panning();
+ emit_signal("transform_changed", zoom_widget->get_zoom(), panning);
}
-void TileAtlasView::_zoom_widget_changed() {
- _update_zoom(zoom_widget->get_zoom());
- emit_signal("transform_changed", zoom_widget->get_zoom(), Vector2(scroll_container->get_h_scroll(), scroll_container->get_v_scroll()));
+void TileAtlasView::_center_view() {
+ panning = Vector2();
+ button_center_view->set_disabled(true);
+ _update_zoom_and_panning();
+ emit_signal("transform_changed", zoom_widget->get_zoom(), panning);
}
void TileAtlasView::_base_tiles_root_control_gui_input(const Ref<InputEvent> &p_event) {
@@ -415,7 +412,7 @@ void TileAtlasView::set_atlas_source(TileSet *p_tile_set, TileSetAtlasSource *p_
_update_alternative_tiles_rect_cache();
// Update everything.
- _update_zoom(zoom_widget->get_zoom());
+ _update_zoom_and_panning();
// Change children control size.
Size2i base_tiles_control_size = _compute_base_tiles_control_size();
@@ -448,9 +445,10 @@ float TileAtlasView::get_zoom() const {
return zoom_widget->get_zoom();
};
-void TileAtlasView::set_transform(float p_zoom, Vector2i p_scroll) {
+void TileAtlasView::set_transform(float p_zoom, Vector2i p_panning) {
zoom_widget->set_zoom(p_zoom);
- _update_zoom(zoom_widget->get_zoom(), false, p_scroll);
+ panning = p_panning;
+ _update_zoom_and_panning();
};
void TileAtlasView::set_padding(Side p_side, int p_padding) {
@@ -525,7 +523,7 @@ Rect2i TileAtlasView::get_alternative_tile_rect(const Vector2i p_coords, int p_a
}
void TileAtlasView::update() {
- scroll_container->update();
+ base_tiles_draw->update();
base_tiles_texture_grid->update();
base_tiles_shape_grid->update();
base_tiles_dark->update();
@@ -534,124 +532,149 @@ void TileAtlasView::update() {
background_right->update();
}
+void TileAtlasView::_notification(int p_what) {
+ switch (p_what) {
+ case NOTIFICATION_READY:
+ button_center_view->set_icon(get_theme_icon("CenterView", "EditorIcons"));
+ break;
+ }
+}
+
void TileAtlasView::_bind_methods() {
+ ClassDB::bind_method("_gui_input", &TileAtlasView::_gui_input);
+
ADD_SIGNAL(MethodInfo("transform_changed", PropertyInfo(Variant::FLOAT, "zoom"), PropertyInfo(Variant::VECTOR2, "scroll")));
}
TileAtlasView::TileAtlasView() {
- Panel *panel_container = memnew(Panel);
- panel_container->set_h_size_flags(SIZE_EXPAND_FILL);
- panel_container->set_v_size_flags(SIZE_EXPAND_FILL);
- panel_container->set_anchors_and_offsets_preset(Control::PRESET_WIDE);
- add_child(panel_container);
-
- //Scrolling
- scroll_container = memnew(ScrollContainer);
- scroll_container->get_h_scrollbar()->connect("value_changed", callable_mp(this, &TileAtlasView::_scroll_changed).unbind(1));
- scroll_container->get_v_scrollbar()->connect("value_changed", callable_mp(this, &TileAtlasView::_scroll_changed).unbind(1));
- panel_container->add_child(scroll_container);
- scroll_container->set_anchors_and_offsets_preset(Control::PRESET_WIDE);
+ set_texture_filter(CanvasItem::TEXTURE_FILTER_NEAREST);
+
+ Panel *panel = memnew(Panel);
+ panel->set_clip_contents(true);
+ panel->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
+ panel->set_anchors_and_offsets_preset(Control::PRESET_WIDE);
+ panel->set_h_size_flags(SIZE_EXPAND_FILL);
+ panel->set_v_size_flags(SIZE_EXPAND_FILL);
+ add_child(panel);
+ // Scrollingsc
zoom_widget = memnew(EditorZoomWidget);
add_child(zoom_widget);
zoom_widget->set_anchors_and_offsets_preset(Control::PRESET_TOP_LEFT, Control::PRESET_MODE_MINSIZE, 2 * EDSCALE);
zoom_widget->connect("zoom_changed", callable_mp(this, &TileAtlasView::_zoom_widget_changed).unbind(1));
- CenterContainer *center_container = memnew(CenterContainer);
- center_container->set_h_size_flags(SIZE_EXPAND_FILL);
- center_container->set_v_size_flags(SIZE_EXPAND_FILL);
+ button_center_view = memnew(Button);
+ button_center_view->set_icon(get_theme_icon("CenterView", "EditorIcons"));
+ button_center_view->set_anchors_and_offsets_preset(Control::PRESET_TOP_RIGHT, Control::PRESET_MODE_MINSIZE, 5);
+ button_center_view->connect("pressed", callable_mp(this, &TileAtlasView::_center_view));
+ button_center_view->set_flat(true);
+ button_center_view->set_disabled(true);
+ add_child(button_center_view);
+
+ center_container = memnew(CenterContainer);
+ center_container->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
+ center_container->set_anchors_preset(Control::PRESET_CENTER);
center_container->connect("gui_input", callable_mp(this, &TileAtlasView::_gui_input));
- scroll_container->add_child(center_container);
+ panel->add_child(center_container);
missing_source_label = memnew(Label);
missing_source_label->set_text(TTR("No atlas source with a valid texture selected."));
center_container->add_child(missing_source_label);
margin_container = memnew(MarginContainer);
+ margin_container->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
center_container->add_child(margin_container);
hbox = memnew(HBoxContainer);
+ hbox->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
hbox->add_theme_constant_override("separation", 10);
hbox->hide();
margin_container->add_child(hbox);
VBoxContainer *left_vbox = memnew(VBoxContainer);
+ left_vbox->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
hbox->add_child(left_vbox);
VBoxContainer *right_vbox = memnew(VBoxContainer);
+ right_vbox->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
hbox->add_child(right_vbox);
// Base tiles.
Label *base_tile_label = memnew(Label);
+ base_tile_label->set_mouse_filter(Control::MOUSE_FILTER_PASS);
base_tile_label->set_text(TTR("Base Tiles"));
base_tile_label->set_align(Label::ALIGN_CENTER);
left_vbox->add_child(base_tile_label);
base_tiles_root_control = memnew(Control);
+ base_tiles_root_control->set_mouse_filter(Control::MOUSE_FILTER_PASS);
base_tiles_root_control->set_v_size_flags(Control::SIZE_EXPAND_FILL);
base_tiles_root_control->connect("gui_input", callable_mp(this, &TileAtlasView::_base_tiles_root_control_gui_input));
left_vbox->add_child(base_tiles_root_control);
background_left = memnew(Control);
+ background_left->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
background_left->set_anchors_and_offsets_preset(Control::PRESET_WIDE);
background_left->set_texture_repeat(TextureRepeat::TEXTURE_REPEAT_ENABLED);
- background_left->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
background_left->connect("draw", callable_mp(this, &TileAtlasView::_draw_background_left));
base_tiles_root_control->add_child(background_left);
base_tiles_drawing_root = memnew(Control);
+ base_tiles_drawing_root->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
base_tiles_drawing_root->set_anchors_and_offsets_preset(Control::PRESET_WIDE);
base_tiles_drawing_root->set_texture_filter(TEXTURE_FILTER_NEAREST);
- base_tiles_drawing_root->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
base_tiles_root_control->add_child(base_tiles_drawing_root);
base_tiles_draw = memnew(Control);
+ base_tiles_draw->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
base_tiles_draw->set_anchors_and_offsets_preset(Control::PRESET_WIDE);
base_tiles_draw->connect("draw", callable_mp(this, &TileAtlasView::_draw_base_tiles));
- base_tiles_draw->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
base_tiles_drawing_root->add_child(base_tiles_draw);
base_tiles_texture_grid = memnew(Control);
+ base_tiles_texture_grid->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
base_tiles_texture_grid->set_anchors_and_offsets_preset(Control::PRESET_WIDE);
base_tiles_texture_grid->connect("draw", callable_mp(this, &TileAtlasView::_draw_base_tiles_texture_grid));
- base_tiles_texture_grid->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
base_tiles_drawing_root->add_child(base_tiles_texture_grid);
base_tiles_shape_grid = memnew(Control);
+ base_tiles_shape_grid->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
base_tiles_shape_grid->set_anchors_and_offsets_preset(Control::PRESET_WIDE);
base_tiles_shape_grid->connect("draw", callable_mp(this, &TileAtlasView::_draw_base_tiles_shape_grid));
- base_tiles_shape_grid->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
base_tiles_drawing_root->add_child(base_tiles_shape_grid);
base_tiles_dark = memnew(Control);
+ base_tiles_dark->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
base_tiles_dark->set_anchors_and_offsets_preset(Control::PRESET_WIDE);
base_tiles_dark->connect("draw", callable_mp(this, &TileAtlasView::_draw_base_tiles_dark));
- base_tiles_dark->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
base_tiles_drawing_root->add_child(base_tiles_dark);
// Alternative tiles.
Label *alternative_tiles_label = memnew(Label);
+ alternative_tiles_label->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
alternative_tiles_label->set_text(TTR("Alternative Tiles"));
alternative_tiles_label->set_align(Label::ALIGN_CENTER);
right_vbox->add_child(alternative_tiles_label);
alternative_tiles_root_control = memnew(Control);
+ alternative_tiles_root_control->set_mouse_filter(Control::MOUSE_FILTER_PASS);
alternative_tiles_root_control->connect("gui_input", callable_mp(this, &TileAtlasView::_alternative_tiles_root_control_gui_input));
right_vbox->add_child(alternative_tiles_root_control);
background_right = memnew(Control);
+ background_right->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
background_right->set_texture_repeat(TextureRepeat::TEXTURE_REPEAT_ENABLED);
background_right->connect("draw", callable_mp(this, &TileAtlasView::_draw_background_right));
- background_right->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
+
alternative_tiles_root_control->add_child(background_right);
alternative_tiles_drawing_root = memnew(Control);
- alternative_tiles_drawing_root->set_texture_filter(TEXTURE_FILTER_NEAREST);
alternative_tiles_drawing_root->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
+ alternative_tiles_drawing_root->set_texture_filter(TEXTURE_FILTER_NEAREST);
alternative_tiles_root_control->add_child(alternative_tiles_drawing_root);
alternatives_draw = memnew(Control);
- alternatives_draw->connect("draw", callable_mp(this, &TileAtlasView::_draw_alternatives));
alternatives_draw->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
+ alternatives_draw->connect("draw", callable_mp(this, &TileAtlasView::_draw_alternatives));
alternative_tiles_drawing_root->add_child(alternatives_draw);
}
diff --git a/editor/plugins/tiles/tile_atlas_view.h b/editor/plugins/tiles/tile_atlas_view.h
index 28fd3ed1e0..bafc2b3985 100644
--- a/editor/plugins/tiles/tile_atlas_view.h
+++ b/editor/plugins/tiles/tile_atlas_view.h
@@ -34,6 +34,7 @@
#include "editor/editor_zoom_widget.h"
#include "scene/gui/box_container.h"
#include "scene/gui/button.h"
+#include "scene/gui/center_container.h"
#include "scene/gui/label.h"
#include "scene/gui/margin_container.h"
#include "scene/gui/scroll_container.h"
@@ -48,17 +49,24 @@ private:
TileSetAtlasSource *tile_set_atlas_source;
int source_id = -1;
+ enum DragType {
+ DRAG_TYPE_NONE,
+ DRAG_TYPE_PAN,
+ };
+ DragType drag_type = DRAG_TYPE_NONE;
float previous_zoom = 1.0;
EditorZoomWidget *zoom_widget;
+ Button *button_center_view;
+ CenterContainer *center_container;
+ Vector2 panning;
+ void _update_zoom_and_panning(bool p_zoom_on_mouse_pos = false);
void _zoom_widget_changed();
- void _scroll_changed();
- void _update_zoom(float p_zoom, bool p_zoom_on_mouse_pos = false, Vector2i p_scroll = Vector2i(-1, -1));
+ void _center_view();
void _gui_input(const Ref<InputEvent> &p_event);
Map<Vector2, Map<int, Rect2i>> alternative_tiles_rect_cache;
void _update_alternative_tiles_rect_cache();
- ScrollContainer *scroll_container;
MarginContainer *margin_container;
int margin_container_paddings[4] = { 0, 0, 0, 0 };
HBoxContainer *hbox;
@@ -102,16 +110,15 @@ private:
Size2i _compute_alternative_tiles_control_size();
protected:
+ void _notification(int p_what);
static void _bind_methods();
public:
// Global.
void set_atlas_source(TileSet *p_tile_set, TileSetAtlasSource *p_tile_set_atlas_source, int p_source_id);
- ScrollContainer *get_scroll_container() { return scroll_container; };
-
float get_zoom() const;
- void set_transform(float p_zoom, Vector2i p_scroll);
+ void set_transform(float p_zoom, Vector2i p_panning);
void set_padding(Side p_side, int p_padding);
diff --git a/editor/plugins/tiles/tile_data_editors.cpp b/editor/plugins/tiles/tile_data_editors.cpp
index 191440bdb3..d9d0e48fb3 100644
--- a/editor/plugins/tiles/tile_data_editors.cpp
+++ b/editor/plugins/tiles/tile_data_editors.cpp
@@ -32,202 +32,2436 @@
#include "tile_set_editor.h"
-TileData *TileDataEditor::_get_tile_data(TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile) {
- ERR_FAIL_COND_V(!p_tile_set, nullptr);
- ERR_FAIL_COND_V(!p_tile_set->has_source(p_atlas_source_id), nullptr);
+#include "core/math/geometry_2d.h"
+#include "core/os/keyboard.h"
+
+#include "editor/editor_properties.h"
+#include "editor/editor_scale.h"
+
+void TileDataEditor::_call_tile_set_changed() {
+ _tile_set_changed();
+}
+
+TileData *TileDataEditor::_get_tile_data(TileMapCell p_cell) {
+ ERR_FAIL_COND_V(!tile_set.is_valid(), nullptr);
+ ERR_FAIL_COND_V(!tile_set->has_source(p_cell.source_id), nullptr);
TileData *td = nullptr;
- TileSetSource *source = *p_tile_set->get_source(p_atlas_source_id);
+ TileSetSource *source = *tile_set->get_source(p_cell.source_id);
TileSetAtlasSource *atlas_source = Object::cast_to<TileSetAtlasSource>(source);
if (atlas_source) {
- ERR_FAIL_COND_V(!atlas_source->has_tile(p_atlas_coords), nullptr);
- ERR_FAIL_COND_V(!atlas_source->has_alternative_tile(p_atlas_coords, p_alternative_tile), nullptr);
- td = Object::cast_to<TileData>(atlas_source->get_tile_data(p_atlas_coords, p_alternative_tile));
+ ERR_FAIL_COND_V(!atlas_source->has_tile(p_cell.get_atlas_coords()), nullptr);
+ ERR_FAIL_COND_V(!atlas_source->has_alternative_tile(p_cell.get_atlas_coords(), p_cell.alternative_tile), nullptr);
+ td = Object::cast_to<TileData>(atlas_source->get_tile_data(p_cell.get_atlas_coords(), p_cell.alternative_tile));
}
return td;
}
-void TileDataEditor::edit(TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) {
+void TileDataEditor::_bind_methods() {
+ ADD_SIGNAL(MethodInfo("needs_redraw"));
}
-void TileDataTextureOffsetEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) {
- TileData *tile_data = _get_tile_data(p_tile_set, p_atlas_source_id, p_atlas_coords, p_alternative_tile);
- ERR_FAIL_COND(!tile_data);
+void TileDataEditor::set_tile_set(Ref<TileSet> p_tile_set) {
+ if (tile_set.is_valid()) {
+ tile_set->disconnect("changed", callable_mp(this, &TileDataEditor::_call_tile_set_changed));
+ }
+ tile_set = p_tile_set;
+ if (tile_set.is_valid()) {
+ tile_set->connect("changed", callable_mp(this, &TileDataEditor::_call_tile_set_changed));
+ }
+ _call_tile_set_changed();
+}
- bool valid;
- Variant value = tile_data->get(p_property, &valid);
- if (!valid) {
- return;
+bool DummyObject::_set(const StringName &p_name, const Variant &p_value) {
+ if (properties.has(p_name)) {
+ properties[p_name] = p_value;
+ return true;
}
- ERR_FAIL_COND(value.get_type() != Variant::VECTOR2I);
+ return false;
+}
- Vector2i tile_set_tile_size = p_tile_set->get_tile_size();
- Rect2i rect = Rect2i(-tile_set_tile_size / 2, tile_set_tile_size);
- p_tile_set->draw_tile_shape(p_canvas_item, p_transform.xform(rect), Color(1.0, 0.0, 0.0));
+bool DummyObject::_get(const StringName &p_name, Variant &r_ret) const {
+ if (properties.has(p_name)) {
+ r_ret = properties[p_name];
+ return true;
+ }
+ return false;
+}
+
+bool DummyObject::has_dummy_property(StringName p_name) {
+ return properties.has(p_name);
+}
+
+void DummyObject::add_dummy_property(StringName p_name) {
+ ERR_FAIL_COND(properties.has(p_name));
+ properties[p_name] = Variant();
+}
+
+void DummyObject::remove_dummy_property(StringName p_name) {
+ ERR_FAIL_COND(!properties.has(p_name));
+ properties.erase(p_name);
+}
+
+void DummyObject::clear_dummy_properties() {
+ properties.clear();
+}
+
+void GenericTilePolygonEditor::_base_control_draw() {
+ ERR_FAIL_COND(!tile_set.is_valid());
+
+ real_t grab_threshold = EDITOR_GET("editors/poly_editor/point_grab_radius");
+
+ Color grid_color = EditorSettings::get_singleton()->get("editors/tiles_editor/grid_color");
+ const Ref<Texture2D> handle = get_theme_icon("EditorPathSharpHandle", "EditorIcons");
+ const Ref<Texture2D> add_handle = get_theme_icon("EditorHandleAdd", "EditorIcons");
+
+ Size2 tile_size = tile_set->get_tile_size();
+
+ Transform2D xform;
+ xform.set_origin(base_control->get_size() / 2 + panning);
+ xform.set_scale(Vector2(editor_zoom_widget->get_zoom(), editor_zoom_widget->get_zoom()));
+ base_control->draw_set_transform_matrix(xform);
+
+ // Draw the tile shape filled.
+ tile_set->draw_tile_shape(base_control, Rect2(-tile_size / 2, tile_size), Color(1.0, 1.0, 1.0, 0.3), true);
+
+ // Draw the background.
+ if (background_texture.is_valid()) {
+ base_control->draw_texture_rect_region(background_texture, Rect2(-background_region.size / 2 - background_offset, background_region.size), background_region, background_modulate, background_transpose);
+ }
+
+ // Draw the polygons.
+ for (unsigned int i = 0; i < polygons.size(); i++) {
+ const Vector<Vector2> &polygon = polygons[i];
+ Color color = polygon_color;
+ if (!in_creation_polygon.is_empty()) {
+ color = color.darkened(0.3);
+ }
+ color.a = 0.5;
+ Vector<Color> v_color;
+ v_color.push_back(color);
+ base_control->draw_polygon(polygon, v_color);
+
+ color.a = 0.7;
+ for (int j = 0; j < polygon.size(); j++) {
+ base_control->draw_line(polygon[j], polygon[(j + 1) % polygon.size()], color);
+ }
+ }
+
+ // Draw the polygon in creation.
+ if (!in_creation_polygon.is_empty()) {
+ for (int i = 0; i < in_creation_polygon.size() - 1; i++) {
+ base_control->draw_line(in_creation_polygon[i], in_creation_polygon[i + 1], Color(1.0, 1.0, 1.0));
+ }
+ }
+
+ Point2 in_creation_point = xform.affine_inverse().xform(base_control->get_local_mouse_position());
+ float in_creation_distance = grab_threshold * 2.0;
+ _snap_to_tile_shape(in_creation_point, in_creation_distance, grab_threshold / editor_zoom_widget->get_zoom());
+ if (button_pixel_snap->is_pressed()) {
+ _snap_to_half_pixel(in_creation_point);
+ }
+
+ if (drag_type == DRAG_TYPE_CREATE_POINT && !in_creation_polygon.is_empty()) {
+ base_control->draw_line(in_creation_polygon[in_creation_polygon.size() - 1], in_creation_point, Color(1.0, 1.0, 1.0));
+ }
+
+ // Draw the handles.
+ int tinted_polygon_index = -1;
+ int tinted_point_index = -1;
+ if (drag_type == DRAG_TYPE_DRAG_POINT) {
+ tinted_polygon_index = drag_polygon_index;
+ tinted_point_index = drag_point_index;
+ } else if (hovered_point_index >= 0) {
+ tinted_polygon_index = hovered_polygon_index;
+ tinted_point_index = hovered_point_index;
+ }
+
+ base_control->draw_set_transform_matrix(Transform2D());
+ if (!in_creation_polygon.is_empty()) {
+ for (int i = 0; i < in_creation_polygon.size(); i++) {
+ base_control->draw_texture(handle, xform.xform(in_creation_polygon[i]) - handle->get_size() / 2);
+ }
+ } else {
+ for (int i = 0; i < (int)polygons.size(); i++) {
+ const Vector<Vector2> &polygon = polygons[i];
+ for (int j = 0; j < polygon.size(); j++) {
+ const Color modulate = (tinted_polygon_index == i && tinted_point_index == j) ? Color(0.5, 1, 2) : Color(1, 1, 1);
+ base_control->draw_texture(handle, xform.xform(polygon[j]) - handle->get_size() / 2, modulate);
+ }
+ }
+ }
+
+ // Draw the text on top of the selected point.
+ if (tinted_polygon_index >= 0) {
+ Ref<Font> font = get_theme_font("font", "Label");
+ int font_size = get_theme_font_size("font_size", "Label");
+ String text = multiple_polygon_mode ? vformat("%d:%d", tinted_polygon_index, tinted_point_index) : vformat("%d", tinted_point_index);
+ Size2 text_size = font->get_string_size(text, font_size);
+ base_control->draw_string(font, xform.xform(polygons[tinted_polygon_index][tinted_point_index]) - text_size * 0.5, text, HALIGN_LEFT, -1, font_size, Color(1.0, 1.0, 1.0, 0.5));
+ }
+
+ if (drag_type == DRAG_TYPE_CREATE_POINT) {
+ base_control->draw_texture(handle, xform.xform(in_creation_point) - handle->get_size() / 2, Color(0.5, 1, 2));
+ }
+
+ // Draw the point creation preview in edit mode.
+ if (hovered_segment_index >= 0) {
+ base_control->draw_texture(add_handle, xform.xform(hovered_segment_point) - add_handle->get_size() / 2);
+ }
+
+ // Draw the tile shape line.
+ base_control->draw_set_transform_matrix(xform);
+ tile_set->draw_tile_shape(base_control, Rect2(-tile_size / 2, tile_size), grid_color, false);
+ base_control->draw_set_transform_matrix(Transform2D());
+}
+
+void GenericTilePolygonEditor::_center_view() {
+ panning = Vector2();
+ base_control->update();
+ button_center_view->set_disabled(true);
+}
+
+void GenericTilePolygonEditor::_zoom_changed() {
+ base_control->update();
+}
+
+void GenericTilePolygonEditor::_advanced_menu_item_pressed(int p_item_pressed) {
+ switch (p_item_pressed) {
+ case RESET_TO_DEFAULT_TILE:
+ undo_redo->create_action(TTR("Edit Polygons"));
+ undo_redo->add_do_method(this, "clear_polygons");
+ undo_redo->add_do_method(this, "add_polygon", tile_set->get_tile_shape_polygon());
+ undo_redo->add_do_method(base_control, "update");
+ undo_redo->add_do_method(this, "emit_signal", "polygons_changed");
+ undo_redo->add_undo_method(this, "clear_polygons");
+ for (unsigned int i = 0; i < polygons.size(); i++) {
+ undo_redo->add_undo_method(this, "add_polygon", polygons[i]);
+ }
+ undo_redo->add_undo_method(base_control, "update");
+ undo_redo->add_undo_method(this, "emit_signal", "polygons_changed");
+ undo_redo->commit_action(true);
+ break;
+ case CLEAR_TILE:
+ undo_redo->create_action(TTR("Edit Polygons"));
+ undo_redo->add_do_method(this, "clear_polygons");
+ undo_redo->add_do_method(base_control, "update");
+ undo_redo->add_do_method(this, "emit_signal", "polygons_changed");
+ undo_redo->add_undo_method(this, "clear_polygons");
+ for (unsigned int i = 0; i < polygons.size(); i++) {
+ undo_redo->add_undo_method(this, "add_polygon", polygons[i]);
+ }
+ undo_redo->add_undo_method(base_control, "update");
+ undo_redo->add_undo_method(this, "emit_signal", "polygons_changed");
+ undo_redo->commit_action(true);
+ break;
+ default:
+ break;
+ }
+}
+
+void GenericTilePolygonEditor::_grab_polygon_point(Vector2 p_pos, const Transform2D &p_polygon_xform, int &r_polygon_index, int &r_point_index) {
+ const real_t grab_threshold = EDITOR_GET("editors/poly_editor/point_grab_radius");
+ r_polygon_index = -1;
+ r_point_index = -1;
+ float closest_distance = grab_threshold + 1.0;
+ for (unsigned int i = 0; i < polygons.size(); i++) {
+ const Vector<Vector2> &polygon = polygons[i];
+ for (int j = 0; j < polygon.size(); j++) {
+ float distance = p_pos.distance_to(p_polygon_xform.xform(polygon[j]));
+ if (distance < grab_threshold && distance < closest_distance) {
+ r_polygon_index = i;
+ r_point_index = j;
+ closest_distance = distance;
+ }
+ }
+ }
+}
+
+void GenericTilePolygonEditor::_grab_polygon_segment_point(Vector2 p_pos, const Transform2D &p_polygon_xform, int &r_polygon_index, int &r_segment_index, Vector2 &r_point) {
+ const real_t grab_threshold = EDITOR_GET("editors/poly_editor/point_grab_radius");
+
+ Point2 point = p_polygon_xform.affine_inverse().xform(p_pos);
+ r_polygon_index = -1;
+ r_segment_index = -1;
+ float closest_distance = grab_threshold * 2.0;
+ for (unsigned int i = 0; i < polygons.size(); i++) {
+ const Vector<Vector2> &polygon = polygons[i];
+ for (int j = 0; j < polygon.size(); j++) {
+ Vector2 segment[2] = { polygon[j], polygon[(j + 1) % polygon.size()] };
+ Vector2 closest_point = Geometry2D::get_closest_point_to_segment(point, segment);
+ float distance = closest_point.distance_to(point);
+ if (distance < grab_threshold / editor_zoom_widget->get_zoom() && distance < closest_distance) {
+ r_polygon_index = i;
+ r_segment_index = j;
+ r_point = closest_point;
+ closest_distance = distance;
+ }
+ }
+ }
+}
+
+void GenericTilePolygonEditor::_snap_to_tile_shape(Point2 &r_point, float &r_current_snapped_dist, float p_snap_dist) {
+ ERR_FAIL_COND(!tile_set.is_valid());
+
+ Vector<Point2> polygon = tile_set->get_tile_shape_polygon();
+ Point2 snapped_point = r_point;
+
+ // Snap to polygon vertices.
+ bool snapped = false;
+ for (int i = 0; i < polygon.size(); i++) {
+ float distance = r_point.distance_to(polygon[i]);
+ if (distance < p_snap_dist && distance < r_current_snapped_dist) {
+ snapped_point = polygon[i];
+ r_current_snapped_dist = distance;
+ snapped = true;
+ }
+ }
+
+ // Snap to edges if we did not snap to vertices.
+ if (!snapped) {
+ for (int i = 0; i < polygon.size(); i++) {
+ Point2 segment[2] = { polygon[i], polygon[(i + 1) % polygon.size()] };
+ Point2 point = Geometry2D::get_closest_point_to_segment(r_point, segment);
+ float distance = r_point.distance_to(point);
+ if (distance < p_snap_dist && distance < r_current_snapped_dist) {
+ snapped_point = point;
+ r_current_snapped_dist = distance;
+ }
+ }
+ }
+
+ r_point = snapped_point;
+}
+
+void GenericTilePolygonEditor::_snap_to_half_pixel(Point2 &r_point) {
+ r_point = (r_point * 2).round() / 2.0;
+}
+
+void GenericTilePolygonEditor::_base_control_gui_input(Ref<InputEvent> p_event) {
+ real_t grab_threshold = EDITOR_GET("editors/poly_editor/point_grab_radius");
+
+ hovered_polygon_index = -1;
+ hovered_point_index = -1;
+ hovered_segment_index = -1;
+ hovered_segment_point = Vector2();
+
+ Transform2D xform;
+ xform.set_origin(base_control->get_size() / 2 + panning);
+ xform.set_scale(Vector2(editor_zoom_widget->get_zoom(), editor_zoom_widget->get_zoom()));
+
+ Ref<InputEventMouseMotion> mm = p_event;
+ if (mm.is_valid()) {
+ if (drag_type == DRAG_TYPE_DRAG_POINT) {
+ ERR_FAIL_INDEX(drag_polygon_index, (int)polygons.size());
+ ERR_FAIL_INDEX(drag_point_index, polygons[drag_polygon_index].size());
+ Point2 point = xform.affine_inverse().xform(mm->get_position());
+ float distance = grab_threshold * 2.0;
+ _snap_to_tile_shape(point, distance, grab_threshold / editor_zoom_widget->get_zoom());
+ if (button_pixel_snap->is_pressed()) {
+ _snap_to_half_pixel(point);
+ }
+ polygons[drag_polygon_index].write[drag_point_index] = point;
+ } else if (drag_type == DRAG_TYPE_PAN) {
+ panning += mm->get_position() - drag_last_pos;
+ drag_last_pos = mm->get_position();
+ button_center_view->set_disabled(panning.is_equal_approx(Vector2()));
+ } else {
+ // Update hovered point.
+ _grab_polygon_point(mm->get_position(), xform, hovered_polygon_index, hovered_point_index);
+
+ // If we have no hovered point, check if we hover a segment.
+ if (hovered_point_index == -1) {
+ _grab_polygon_segment_point(mm->get_position(), xform, hovered_polygon_index, hovered_segment_index, hovered_segment_point);
+ }
+ }
+ }
+
+ Ref<InputEventMouseButton> mb = p_event;
+ if (mb.is_valid()) {
+ if (mb->get_button_index() == MOUSE_BUTTON_WHEEL_UP && mb->is_ctrl_pressed()) {
+ editor_zoom_widget->set_zoom_by_increments(1);
+ _zoom_changed();
+ accept_event();
+ } else if (mb->get_button_index() == MOUSE_BUTTON_WHEEL_DOWN && mb->is_ctrl_pressed()) {
+ editor_zoom_widget->set_zoom_by_increments(-1);
+ _zoom_changed();
+ accept_event();
+ } else if (mb->get_button_index() == MOUSE_BUTTON_LEFT) {
+ if (mb->is_pressed()) {
+ if (tools_button_group->get_pressed_button() != button_create) {
+ in_creation_polygon.clear();
+ }
+ if (tools_button_group->get_pressed_button() == button_create) {
+ // Create points.
+ if (in_creation_polygon.size() >= 3 && mb->get_position().distance_to(xform.xform(in_creation_polygon[0])) < grab_threshold) {
+ // Closes and create polygon.
+ if (!multiple_polygon_mode) {
+ clear_polygons();
+ }
+ int added = add_polygon(in_creation_polygon);
+
+ in_creation_polygon.clear();
+ button_edit->set_pressed(true);
+ undo_redo->create_action(TTR("Edit Polygons"));
+ if (!multiple_polygon_mode) {
+ undo_redo->add_do_method(this, "clear_polygons");
+ }
+ undo_redo->add_do_method(this, "add_polygon", in_creation_polygon);
+ undo_redo->add_do_method(base_control, "update");
+ undo_redo->add_undo_method(this, "remove_polygon", added);
+ undo_redo->add_undo_method(base_control, "update");
+ undo_redo->commit_action(false);
+ emit_signal("polygons_changed");
+ } else {
+ // Create a new point.
+ drag_type = DRAG_TYPE_CREATE_POINT;
+ }
+ } else if (tools_button_group->get_pressed_button() == button_edit) {
+ // Edit points.
+ int closest_polygon;
+ int closest_point;
+ _grab_polygon_point(mb->get_position(), xform, closest_polygon, closest_point);
+ if (closest_polygon >= 0) {
+ drag_type = DRAG_TYPE_DRAG_POINT;
+ drag_polygon_index = closest_polygon;
+ drag_point_index = closest_point;
+ drag_old_polygon = polygons[drag_polygon_index];
+ } else {
+ // Create a point.
+ Vector2 point_to_create;
+ _grab_polygon_segment_point(mb->get_position(), xform, closest_polygon, closest_point, point_to_create);
+ if (closest_polygon >= 0) {
+ polygons[closest_polygon].insert(closest_point + 1, point_to_create);
+ drag_type = DRAG_TYPE_DRAG_POINT;
+ drag_polygon_index = closest_polygon;
+ drag_point_index = closest_point + 1;
+ drag_old_polygon = polygons[closest_polygon];
+ }
+ }
+ } else if (tools_button_group->get_pressed_button() == button_delete) {
+ // Remove point.
+ int closest_polygon;
+ int closest_point;
+ _grab_polygon_point(mb->get_position(), xform, closest_polygon, closest_point);
+ if (closest_polygon >= 0) {
+ PackedVector2Array old_polygon = polygons[closest_polygon];
+ polygons[closest_polygon].remove(closest_point);
+ undo_redo->create_action(TTR("Edit Polygons"));
+ if (polygons[closest_polygon].size() < 3) {
+ remove_polygon(closest_polygon);
+ undo_redo->add_do_method(this, "remove_polygon", closest_polygon);
+ undo_redo->add_undo_method(this, "add_polygon", old_polygon, closest_polygon);
+ } else {
+ undo_redo->add_do_method(this, "set_polygon", closest_polygon, polygons[closest_polygon]);
+ undo_redo->add_undo_method(this, "set_polygon", closest_polygon, old_polygon);
+ }
+ undo_redo->add_do_method(base_control, "update");
+ undo_redo->add_undo_method(base_control, "update");
+ undo_redo->commit_action(false);
+ emit_signal("polygons_changed");
+ }
+ }
+ } else {
+ if (drag_type == DRAG_TYPE_DRAG_POINT) {
+ undo_redo->create_action(TTR("Edit Polygons"));
+ undo_redo->add_do_method(this, "set_polygon", drag_polygon_index, polygons[drag_polygon_index]);
+ undo_redo->add_do_method(base_control, "update");
+ undo_redo->add_undo_method(this, "set_polygon", drag_polygon_index, drag_old_polygon);
+ undo_redo->add_undo_method(base_control, "update");
+ undo_redo->commit_action(false);
+ emit_signal("polygons_changed");
+ } else if (drag_type == DRAG_TYPE_CREATE_POINT) {
+ Point2 point = xform.affine_inverse().xform(mb->get_position());
+ float distance = grab_threshold * 2;
+ _snap_to_tile_shape(point, distance, grab_threshold / editor_zoom_widget->get_zoom());
+ if (button_pixel_snap->is_pressed()) {
+ _snap_to_half_pixel(point);
+ }
+ in_creation_polygon.push_back(point);
+ }
+ drag_type = DRAG_TYPE_NONE;
+ drag_point_index = -1;
+ }
+
+ } else if (mb->get_button_index() == MOUSE_BUTTON_RIGHT) {
+ if (mb->is_pressed()) {
+ if (tools_button_group->get_pressed_button() == button_edit) {
+ // Remove point or pan.
+ int closest_polygon;
+ int closest_point;
+ _grab_polygon_point(mb->get_position(), xform, closest_polygon, closest_point);
+ if (closest_polygon >= 0) {
+ PackedVector2Array old_polygon = polygons[closest_polygon];
+ polygons[closest_polygon].remove(closest_point);
+ undo_redo->create_action(TTR("Edit Polygons"));
+ if (polygons[closest_polygon].size() < 3) {
+ remove_polygon(closest_polygon);
+ undo_redo->add_do_method(this, "remove_polygon", closest_polygon);
+ undo_redo->add_undo_method(this, "add_polygon", old_polygon, closest_polygon);
+ } else {
+ undo_redo->add_do_method(this, "set_polygon", closest_polygon, polygons[closest_polygon]);
+ undo_redo->add_undo_method(this, "set_polygon", closest_polygon, old_polygon);
+ }
+ undo_redo->add_do_method(base_control, "update");
+ undo_redo->add_undo_method(base_control, "update");
+ undo_redo->commit_action(false);
+ emit_signal("polygons_changed");
+ } else {
+ drag_type = DRAG_TYPE_PAN;
+ drag_last_pos = mb->get_position();
+ }
+ } else {
+ drag_type = DRAG_TYPE_PAN;
+ drag_last_pos = mb->get_position();
+ }
+ } else {
+ drag_type = DRAG_TYPE_NONE;
+ }
+ } else if (mb->get_button_index() == MOUSE_BUTTON_MIDDLE) {
+ if (mb->is_pressed()) {
+ drag_type = DRAG_TYPE_PAN;
+ drag_last_pos = mb->get_position();
+ } else {
+ drag_type = DRAG_TYPE_NONE;
+ }
+ }
+ }
+
+ base_control->update();
+}
+
+void GenericTilePolygonEditor::set_tile_set(Ref<TileSet> p_tile_set) {
+ if (tile_set != p_tile_set) {
+ // Set the default tile shape
+ clear_polygons();
+ if (p_tile_set.is_valid()) {
+ add_polygon(p_tile_set->get_tile_shape_polygon());
+ }
+ }
+ tile_set = p_tile_set;
+}
+
+void GenericTilePolygonEditor::set_background(Ref<Texture2D> p_texture, Rect2 p_region, Vector2 p_offset, bool p_flip_h, bool p_flip_v, bool p_transpose, Color p_modulate) {
+ background_texture = p_texture;
+ background_region = p_region;
+ background_offset = p_offset;
+ background_h_flip = p_flip_h;
+ background_v_flip = p_flip_v;
+ background_transpose = p_transpose;
+ background_modulate = p_modulate;
+ base_control->update();
+}
+
+int GenericTilePolygonEditor::get_polygon_count() {
+ return polygons.size();
+}
+
+int GenericTilePolygonEditor::add_polygon(Vector<Point2> p_polygon, int p_index) {
+ ERR_FAIL_COND_V(p_polygon.size() < 3, -1);
+ ERR_FAIL_COND_V(!multiple_polygon_mode && polygons.size() >= 1, -1);
+
+ if (p_index < 0) {
+ polygons.push_back(p_polygon);
+ base_control->update();
+ button_edit->set_pressed(true);
+ return polygons.size() - 1;
+ } else {
+ polygons.insert(p_index, p_polygon);
+ button_edit->set_pressed(true);
+ base_control->update();
+ return p_index;
+ }
+}
+
+void GenericTilePolygonEditor::remove_polygon(int p_index) {
+ ERR_FAIL_INDEX(p_index, (int)polygons.size());
+ polygons.remove(p_index);
+
+ if (polygons.size() == 0) {
+ button_create->set_pressed(true);
+ }
+ base_control->update();
+}
+
+void GenericTilePolygonEditor::clear_polygons() {
+ polygons.clear();
+ base_control->update();
+}
+
+void GenericTilePolygonEditor::set_polygon(int p_polygon_index, Vector<Point2> p_polygon) {
+ ERR_FAIL_INDEX(p_polygon_index, (int)polygons.size());
+ ERR_FAIL_COND(p_polygon.size() < 3);
+ polygons[p_polygon_index] = p_polygon;
+ button_edit->set_pressed(true);
+ base_control->update();
}
-void TileDataIntegerEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) {
- TileData *tile_data = _get_tile_data(p_tile_set, p_atlas_source_id, p_atlas_coords, p_alternative_tile);
+Vector<Point2> GenericTilePolygonEditor::get_polygon(int p_polygon_index) {
+ ERR_FAIL_INDEX_V(p_polygon_index, (int)polygons.size(), Vector<Point2>());
+ return polygons[p_polygon_index];
+}
+
+void GenericTilePolygonEditor::set_polygons_color(Color p_color) {
+ polygon_color = p_color;
+ base_control->update();
+}
+
+void GenericTilePolygonEditor::set_multiple_polygon_mode(bool p_multiple_polygon_mode) {
+ multiple_polygon_mode = p_multiple_polygon_mode;
+}
+
+void GenericTilePolygonEditor::_notification(int p_what) {
+ switch (p_what) {
+ case NOTIFICATION_READY:
+ button_create->set_icon(EditorNode::get_singleton()->get_gui_base()->get_theme_icon("CurveCreate", "EditorIcons"));
+ button_edit->set_icon(EditorNode::get_singleton()->get_gui_base()->get_theme_icon("CurveEdit", "EditorIcons"));
+ button_delete->set_icon(EditorNode::get_singleton()->get_gui_base()->get_theme_icon("CurveDelete", "EditorIcons"));
+ button_center_view->set_icon(EditorNode::get_singleton()->get_gui_base()->get_theme_icon("CenterView", "EditorIcons"));
+ button_pixel_snap->set_icon(EditorNode::get_singleton()->get_gui_base()->get_theme_icon("Snap", "EditorIcons"));
+ button_advanced_menu->set_icon(EditorNode::get_singleton()->get_gui_base()->get_theme_icon("GuiTabMenu", "EditorIcons"));
+ break;
+ }
+}
+
+void GenericTilePolygonEditor::_bind_methods() {
+ ClassDB::bind_method(D_METHOD("get_polygon_count"), &GenericTilePolygonEditor::get_polygon_count);
+ ClassDB::bind_method(D_METHOD("add_polygon", "polygon", "index"), &GenericTilePolygonEditor::add_polygon, DEFVAL(-1));
+ ClassDB::bind_method(D_METHOD("remove_polygon", "index"), &GenericTilePolygonEditor::remove_polygon);
+ ClassDB::bind_method(D_METHOD("clear_polygons"), &GenericTilePolygonEditor::clear_polygons);
+ ClassDB::bind_method(D_METHOD("set_polygon", "index", "polygon"), &GenericTilePolygonEditor::set_polygon);
+ ClassDB::bind_method(D_METHOD("get_polygon", "index"), &GenericTilePolygonEditor::set_polygon);
+
+ ADD_SIGNAL(MethodInfo("polygons_changed"));
+}
+
+GenericTilePolygonEditor::GenericTilePolygonEditor() {
+ toolbar = memnew(HBoxContainer);
+ add_child(toolbar);
+
+ tools_button_group.instantiate();
+
+ button_create = memnew(Button);
+ button_create->set_flat(true);
+ button_create->set_toggle_mode(true);
+ button_create->set_button_group(tools_button_group);
+ button_create->set_pressed(true);
+ toolbar->add_child(button_create);
+
+ button_edit = memnew(Button);
+ button_edit->set_flat(true);
+ button_edit->set_toggle_mode(true);
+ button_edit->set_button_group(tools_button_group);
+ toolbar->add_child(button_edit);
+
+ button_delete = memnew(Button);
+ button_delete->set_flat(true);
+ button_delete->set_toggle_mode(true);
+ button_delete->set_button_group(tools_button_group);
+ toolbar->add_child(button_delete);
+
+ button_advanced_menu = memnew(MenuButton);
+ button_advanced_menu->set_flat(true);
+ button_advanced_menu->set_toggle_mode(true);
+ button_advanced_menu->get_popup()->add_item(TTR("Reset to default tile shape"), RESET_TO_DEFAULT_TILE);
+ button_advanced_menu->get_popup()->add_item(TTR("Clear"), CLEAR_TILE);
+ button_advanced_menu->get_popup()->connect("id_pressed", callable_mp(this, &GenericTilePolygonEditor::_advanced_menu_item_pressed));
+ toolbar->add_child(button_advanced_menu);
+
+ toolbar->add_child(memnew(VSeparator));
+
+ button_pixel_snap = memnew(Button);
+ button_pixel_snap->set_flat(true);
+ button_pixel_snap->set_toggle_mode(true);
+ button_pixel_snap->set_pressed(true);
+ toolbar->add_child(button_pixel_snap);
+
+ Control *root = memnew(Control);
+ root->set_h_size_flags(Control::SIZE_EXPAND_FILL);
+ root->set_custom_minimum_size(Size2(0, 200 * EDSCALE));
+ root->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
+ add_child(root);
+
+ panel = memnew(Panel);
+ panel->set_anchors_and_offsets_preset(Control::PRESET_WIDE);
+ panel->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
+ root->add_child(panel);
+
+ base_control = memnew(Control);
+ base_control->set_texture_filter(CanvasItem::TEXTURE_FILTER_NEAREST);
+ base_control->set_anchors_and_offsets_preset(Control::PRESET_WIDE);
+ base_control->connect("draw", callable_mp(this, &GenericTilePolygonEditor::_base_control_draw));
+ base_control->connect("gui_input", callable_mp(this, &GenericTilePolygonEditor::_base_control_gui_input));
+ base_control->set_clip_contents(true);
+ root->add_child(base_control);
+
+ editor_zoom_widget = memnew(EditorZoomWidget);
+ editor_zoom_widget->set_position(Vector2(5, 5));
+ editor_zoom_widget->connect("zoom_changed", callable_mp(this, &GenericTilePolygonEditor::_zoom_changed).unbind(1));
+ root->add_child(editor_zoom_widget);
+
+ button_center_view = memnew(Button);
+ button_center_view->set_icon(EditorNode::get_singleton()->get_gui_base()->get_theme_icon("CenterView", "EditorIcons"));
+ button_center_view->set_anchors_and_offsets_preset(Control::PRESET_TOP_RIGHT, Control::PRESET_MODE_MINSIZE, 5);
+ button_center_view->connect("pressed", callable_mp(this, &GenericTilePolygonEditor::_center_view));
+ button_center_view->set_flat(true);
+ button_center_view->set_disabled(true);
+ root->add_child(button_center_view);
+}
+
+void TileDataDefaultEditor::_property_value_changed(StringName p_property, Variant p_value, StringName p_field) {
+ ERR_FAIL_COND(!dummy_object);
+ dummy_object->set(p_property, p_value);
+}
+
+Variant TileDataDefaultEditor::_get_painted_value() {
+ ERR_FAIL_COND_V(!dummy_object, Variant());
+ return dummy_object->get(property);
+}
+
+void TileDataDefaultEditor::_set_painted_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(p_coords, p_alternative_tile));
ERR_FAIL_COND(!tile_data);
+ Variant value = tile_data->get(property);
+ dummy_object->set(property, value);
+ if (property_editor) {
+ property_editor->update_property();
+ }
+}
- bool valid;
- Variant value = tile_data->get(p_property, &valid);
- if (!valid) {
- return;
+void TileDataDefaultEditor::_set_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile, Variant p_value) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(p_coords, p_alternative_tile));
+ ERR_FAIL_COND(!tile_data);
+ tile_data->set(property, p_value);
+}
+
+Variant TileDataDefaultEditor::_get_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(p_coords, p_alternative_tile));
+ ERR_FAIL_COND_V(!tile_data, Variant());
+ return tile_data->get(property);
+}
+
+void TileDataDefaultEditor::_setup_undo_redo_action(TileSetAtlasSource *p_tile_set_atlas_source, Map<TileMapCell, Variant> p_previous_values, Variant p_new_value) {
+ for (Map<TileMapCell, Variant>::Element *E = p_previous_values.front(); E; E = E->next()) {
+ Vector2i coords = E->key().get_atlas_coords();
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/%s", coords.x, coords.y, E->key().alternative_tile, property), E->get());
+ undo_redo->add_do_property(p_tile_set_atlas_source, vformat("%d:%d/%d/%s", coords.x, coords.y, E->key().alternative_tile, property), p_new_value);
}
- ERR_FAIL_COND(value.get_type() != Variant::INT);
+}
- Ref<Font> font = TileSetEditor::get_singleton()->get_theme_font("bold", "EditorFonts");
- int height = font->get_height();
- int width = 200;
- p_canvas_item->draw_string(font, p_transform.get_origin() + Vector2i(-width / 2, height / 2), vformat("%d", value), HALIGN_CENTER, width, -1, Color(1, 1, 1), 1, Color(0, 0, 0, 1));
+void TileDataDefaultEditor::forward_draw_over_atlas(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_set_atlas_source, CanvasItem *p_canvas_item, Transform2D p_transform) {
+ if (drag_type == DRAG_TYPE_PAINT_RECT) {
+ Color grid_color = EditorSettings::get_singleton()->get("editors/tiles_editor/grid_color");
+ Color selection_color = Color().from_hsv(Math::fposmod(grid_color.get_h() + 0.5, 1.0), grid_color.get_s(), grid_color.get_v(), 1.0);
+
+ p_canvas_item->draw_set_transform_matrix(p_transform);
+
+ Rect2i rect;
+ rect.set_position(p_tile_atlas_view->get_atlas_tile_coords_at_pos(drag_start_pos));
+ rect.set_end(p_tile_atlas_view->get_atlas_tile_coords_at_pos(p_transform.affine_inverse().xform(p_canvas_item->get_local_mouse_position())));
+ rect = rect.abs();
+
+ Set<TileMapCell> edited;
+ for (int x = rect.get_position().x; x <= rect.get_end().x; x++) {
+ for (int y = rect.get_position().y; y <= rect.get_end().y; y++) {
+ Vector2i coords = Vector2i(x, y);
+ coords = p_tile_set_atlas_source->get_tile_at_coords(coords);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = 0;
+ edited.insert(cell);
+ }
+ }
+ }
+
+ for (Set<TileMapCell>::Element *E = edited.front(); E; E = E->next()) {
+ Vector2i coords = E->get().get_atlas_coords();
+ p_canvas_item->draw_rect(p_tile_set_atlas_source->get_tile_texture_region(coords), selection_color, false);
+ }
+ p_canvas_item->draw_set_transform_matrix(Transform2D());
+ }
+};
+
+void TileDataDefaultEditor::forward_draw_over_alternatives(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_set_atlas_source, CanvasItem *p_canvas_item, Transform2D p_transform){
+
+};
+
+void TileDataDefaultEditor::forward_painting_atlas_gui_input(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_set_atlas_source, const Ref<InputEvent> &p_event) {
+ Ref<InputEventMouseMotion> mm = p_event;
+ if (mm.is_valid()) {
+ if (drag_type == DRAG_TYPE_PAINT) {
+ Vector<Vector2i> line = Geometry2D::bresenham_line(p_tile_atlas_view->get_atlas_tile_coords_at_pos(drag_last_pos), p_tile_atlas_view->get_atlas_tile_coords_at_pos(mm->get_position()));
+ for (int i = 0; i < line.size(); i++) {
+ Vector2i coords = p_tile_set_atlas_source->get_tile_at_coords(line[i]);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = 0;
+ if (!drag_modified.has(cell)) {
+ drag_modified[cell] = _get_value(p_tile_set_atlas_source, coords, 0);
+ }
+ _set_value(p_tile_set_atlas_source, coords, 0, drag_painted_value);
+ }
+ }
+ drag_last_pos = mm->get_position();
+ }
+ }
+
+ Ref<InputEventMouseButton> mb = p_event;
+ if (mb.is_valid()) {
+ if (mb->get_button_index() == MOUSE_BUTTON_LEFT) {
+ if (mb->is_pressed()) {
+ if (picker_button->is_pressed()) {
+ Vector2i coords = p_tile_atlas_view->get_atlas_tile_coords_at_pos(mb->get_position());
+ coords = p_tile_set_atlas_source->get_tile_at_coords(coords);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ _set_painted_value(p_tile_set_atlas_source, coords, 0);
+ picker_button->set_pressed(false);
+ }
+ } else if (mb->is_ctrl_pressed()) {
+ drag_type = DRAG_TYPE_PAINT_RECT;
+ drag_modified.clear();
+ drag_painted_value = _get_painted_value();
+ drag_start_pos = mb->get_position();
+ } else {
+ drag_type = DRAG_TYPE_PAINT;
+ drag_modified.clear();
+ drag_painted_value = _get_painted_value();
+ Vector2i coords = p_tile_atlas_view->get_atlas_tile_coords_at_pos(mb->get_position());
+ coords = p_tile_set_atlas_source->get_tile_at_coords(coords);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = 0;
+ drag_modified[cell] = _get_value(p_tile_set_atlas_source, coords, 0);
+ _set_value(p_tile_set_atlas_source, coords, 0, drag_painted_value);
+ }
+ drag_last_pos = mb->get_position();
+ }
+ } else {
+ if (drag_type == DRAG_TYPE_PAINT_RECT) {
+ Rect2i rect;
+ rect.set_position(p_tile_atlas_view->get_atlas_tile_coords_at_pos(drag_start_pos));
+ rect.set_end(p_tile_atlas_view->get_atlas_tile_coords_at_pos(mb->get_position()));
+ rect = rect.abs();
+
+ drag_modified.clear();
+ for (int x = rect.get_position().x; x <= rect.get_end().x; x++) {
+ for (int y = rect.get_position().y; y <= rect.get_end().y; y++) {
+ Vector2i coords = Vector2i(x, y);
+ coords = p_tile_set_atlas_source->get_tile_at_coords(coords);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = 0;
+ drag_modified[cell] = _get_value(p_tile_set_atlas_source, coords, 0);
+ }
+ }
+ }
+ undo_redo->create_action(TTR("Painting Tiles Property"));
+ _setup_undo_redo_action(p_tile_set_atlas_source, drag_modified, drag_painted_value);
+ undo_redo->commit_action(true);
+ drag_type = DRAG_TYPE_NONE;
+ } else if (drag_type == DRAG_TYPE_PAINT) {
+ undo_redo->create_action(TTR("Painting Tiles Property"));
+ _setup_undo_redo_action(p_tile_set_atlas_source, drag_modified, drag_painted_value);
+ undo_redo->commit_action(false);
+ drag_type = DRAG_TYPE_NONE;
+ }
+ }
+ }
+ }
}
-void TileDataFloatEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) {
- TileData *tile_data = _get_tile_data(p_tile_set, p_atlas_source_id, p_atlas_coords, p_alternative_tile);
+void TileDataDefaultEditor::forward_painting_alternatives_gui_input(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_set_atlas_source, const Ref<InputEvent> &p_event) {
+ Ref<InputEventMouseMotion> mm = p_event;
+ if (mm.is_valid()) {
+ if (drag_type == DRAG_TYPE_PAINT) {
+ Vector3i tile = p_tile_atlas_view->get_alternative_tile_at_pos(mm->get_position());
+ Vector2i coords = Vector2i(tile.x, tile.y);
+ int alternative_tile = tile.z;
+
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = alternative_tile;
+ if (!drag_modified.has(cell)) {
+ drag_modified[cell] = _get_value(p_tile_set_atlas_source, coords, alternative_tile);
+ }
+ _set_value(p_tile_set_atlas_source, coords, alternative_tile, drag_painted_value);
+ }
+
+ drag_last_pos = mm->get_position();
+ }
+ }
+
+ Ref<InputEventMouseButton> mb = p_event;
+ if (mb.is_valid()) {
+ if (mb->get_button_index() == MOUSE_BUTTON_LEFT) {
+ if (mb->is_pressed()) {
+ if (picker_button->is_pressed()) {
+ Vector3i tile = p_tile_atlas_view->get_alternative_tile_at_pos(mb->get_position());
+ Vector2i coords = Vector2i(tile.x, tile.y);
+ int alternative_tile = tile.z;
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ _set_painted_value(p_tile_set_atlas_source, coords, alternative_tile);
+ picker_button->set_pressed(false);
+ }
+ } else {
+ drag_type = DRAG_TYPE_PAINT;
+ drag_modified.clear();
+ drag_painted_value = _get_painted_value();
+
+ Vector3i tile = p_tile_atlas_view->get_alternative_tile_at_pos(mb->get_position());
+ Vector2i coords = Vector2i(tile.x, tile.y);
+ int alternative_tile = tile.z;
+
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = alternative_tile;
+ drag_modified[cell] = _get_value(p_tile_set_atlas_source, coords, alternative_tile);
+ _set_value(p_tile_set_atlas_source, coords, alternative_tile, drag_painted_value);
+ }
+ drag_last_pos = mb->get_position();
+ }
+ } else {
+ undo_redo->create_action(TTR("Painting Tiles Property"));
+ _setup_undo_redo_action(p_tile_set_atlas_source, drag_modified, drag_painted_value);
+ undo_redo->commit_action(false);
+ drag_type = DRAG_TYPE_NONE;
+ }
+ }
+ }
+}
+
+void TileDataDefaultEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected) {
+ TileData *tile_data = _get_tile_data(p_cell);
ERR_FAIL_COND(!tile_data);
bool valid;
- Variant value = tile_data->get(p_property, &valid);
+ Variant value = tile_data->get(property, &valid);
if (!valid) {
return;
}
- ERR_FAIL_COND(value.get_type() != Variant::FLOAT);
- Ref<Font> font = TileSetEditor::get_singleton()->get_theme_font("bold", "EditorFonts");
- int height = font->get_height();
- int width = 200;
- p_canvas_item->draw_string(font, p_transform.get_origin() + Vector2i(-width / 2, height / 2), vformat("%.2f", value), HALIGN_CENTER, width, -1, Color(1, 1, 1), 1, Color(0, 0, 0, 1));
+ if (value.get_type() == Variant::BOOL) {
+ Ref<Texture2D> texture = (bool)value ? tile_bool_checked : tile_bool_unchecked;
+ int size = MIN(tile_set->get_tile_size().x, tile_set->get_tile_size().y) / 3;
+ Rect2 rect = p_transform.xform(Rect2(Vector2(-size / 2, -size / 2), Vector2(size, size)));
+ p_canvas_item->draw_texture_rect(texture, rect);
+ } else if (value.get_type() == Variant::COLOR) {
+ int size = MIN(tile_set->get_tile_size().x, tile_set->get_tile_size().y) / 3;
+ Rect2 rect = p_transform.xform(Rect2(Vector2(-size / 2, -size / 2), Vector2(size, size)));
+ p_canvas_item->draw_rect(rect, value);
+ } else {
+ Ref<Font> font = TileSetEditor::get_singleton()->get_theme_font("bold", "EditorFonts");
+ String text;
+ switch (value.get_type()) {
+ case Variant::INT:
+ text = vformat("%d", value);
+ break;
+ case Variant::FLOAT:
+ text = vformat("%.2f", value);
+ break;
+ case Variant::STRING:
+ case Variant::STRING_NAME:
+ text = value;
+ break;
+ default:
+ return;
+ break;
+ }
+
+ Color color = Color(1, 1, 1);
+ if (p_selected) {
+ Color grid_color = EditorSettings::get_singleton()->get("editors/tiles_editor/grid_color");
+ Color selection_color = Color().from_hsv(Math::fposmod(grid_color.get_h() + 0.5, 1.0), grid_color.get_s(), grid_color.get_v(), 1.0);
+ selection_color.set_v(0.9);
+ color = selection_color;
+ } else if (is_visible_in_tree()) {
+ Variant painted_value = _get_painted_value();
+ bool equal = (painted_value.get_type() == Variant::FLOAT && value.get_type() == Variant::FLOAT) ? Math::is_equal_approx(float(painted_value), float(value)) : painted_value == value;
+ if (equal) {
+ color = Color(0.7, 0.7, 0.7);
+ }
+ }
+
+ Vector2 string_size = font->get_string_size(text);
+ p_canvas_item->draw_string(font, p_transform.get_origin() + Vector2i(-string_size.x / 2, string_size.y / 2), text, HALIGN_CENTER, string_size.x, -1, color, 1, Color(0, 0, 0, 1));
+ }
}
-void TileDataPositionEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) {
- TileData *tile_data = _get_tile_data(p_tile_set, p_atlas_source_id, p_atlas_coords, p_alternative_tile);
+void TileDataDefaultEditor::setup_property_editor(Variant::Type p_type, String p_property, String p_label, Variant p_default_value) {
+ ERR_FAIL_COND_MSG(!property.is_empty(), "Cannot setup TileDataDefaultEditor twice");
+ property = p_property;
+
+ // Update everything.
+ if (property_editor) {
+ property_editor->queue_delete();
+ }
+
+ // Update the dummy object.
+ dummy_object->add_dummy_property(p_property);
+
+ // Get the default value for the type.
+ if (p_default_value == Variant()) {
+ Callable::CallError error;
+ Variant painted_value;
+ Variant::construct(p_type, painted_value, nullptr, 0, error);
+ dummy_object->set(p_property, painted_value);
+ } else {
+ dummy_object->set(p_property, p_default_value);
+ }
+
+ // Create and setup the property editor.
+ property_editor = EditorInspectorDefaultPlugin::get_editor_for_property(dummy_object, p_type, p_property, PROPERTY_HINT_NONE, "", PROPERTY_USAGE_DEFAULT);
+ property_editor->set_object_and_property(dummy_object, p_property);
+ if (p_label.is_empty()) {
+ property_editor->set_label(p_property);
+ } else {
+ property_editor->set_label(p_label);
+ }
+ property_editor->connect("property_changed", callable_mp(this, &TileDataDefaultEditor::_property_value_changed).unbind(1));
+ property_editor->update_property();
+ add_child(property_editor);
+}
+
+void TileDataDefaultEditor::_notification(int p_what) {
+ switch (p_what) {
+ case NOTIFICATION_ENTER_TREE:
+ case NOTIFICATION_THEME_CHANGED:
+ picker_button->set_icon(get_theme_icon("ColorPick", "EditorIcons"));
+ tile_bool_checked = get_theme_icon("TileChecked", "EditorIcons");
+ tile_bool_unchecked = get_theme_icon("TileUnchecked", "EditorIcons");
+ break;
+ default:
+ break;
+ }
+}
+
+TileDataDefaultEditor::TileDataDefaultEditor() {
+ label = memnew(Label);
+ label->set_text("Painting:");
+ add_child(label);
+
+ toolbar->add_child(memnew(VSeparator));
+
+ picker_button = memnew(Button);
+ picker_button->set_flat(true);
+ picker_button->set_toggle_mode(true);
+ picker_button->set_shortcut(ED_SHORTCUT("tiles_editor/picker", "Picker", KEY_P));
+ toolbar->add_child(picker_button);
+}
+
+TileDataDefaultEditor::~TileDataDefaultEditor() {
+ toolbar->queue_delete();
+ memdelete(dummy_object);
+}
+
+void TileDataTextureOffsetEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected) {
+ TileData *tile_data = _get_tile_data(p_cell);
+ ERR_FAIL_COND(!tile_data);
+
+ Vector2i tile_set_tile_size = tile_set->get_tile_size();
+ Rect2i rect = Rect2i(-tile_set_tile_size / 2, tile_set_tile_size);
+ Color color = Color(1.0, 0.0, 0.0);
+ if (p_selected) {
+ Color grid_color = EditorSettings::get_singleton()->get("editors/tiles_editor/grid_color");
+ Color selection_color = Color().from_hsv(Math::fposmod(grid_color.get_h() + 0.5, 1.0), grid_color.get_s(), grid_color.get_v(), 1.0);
+ color = selection_color;
+ }
+ tile_set->draw_tile_shape(p_canvas_item, p_transform.xform(rect), color);
+}
+
+void TileDataPositionEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected) {
+ TileData *tile_data = _get_tile_data(p_cell);
ERR_FAIL_COND(!tile_data);
bool valid;
- Variant value = tile_data->get(p_property, &valid);
+ Variant value = tile_data->get(property, &valid);
if (!valid) {
return;
}
ERR_FAIL_COND(value.get_type() != Variant::VECTOR2I && value.get_type() != Variant::VECTOR2);
+ Color color = Color(1.0, 1.0, 1.0);
+ if (p_selected) {
+ Color grid_color = EditorSettings::get_singleton()->get("editors/tiles_editor/grid_color");
+ Color selection_color = Color().from_hsv(Math::fposmod(grid_color.get_h() + 0.5, 1.0), grid_color.get_s(), grid_color.get_v(), 1.0);
+ color = selection_color;
+ }
Ref<Texture2D> position_icon = TileSetEditor::get_singleton()->get_theme_icon("EditorPosition", "EditorIcons");
- p_canvas_item->draw_texture(position_icon, p_transform.xform(Vector2(value)) - position_icon->get_size() / 2);
+ p_canvas_item->draw_texture(position_icon, p_transform.xform(Vector2(value)) - position_icon->get_size() / 2, color);
}
-void TileDataYSortEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) {
- TileData *tile_data = _get_tile_data(p_tile_set, p_atlas_source_id, p_atlas_coords, p_alternative_tile);
+void TileDataYSortEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected) {
+ TileData *tile_data = _get_tile_data(p_cell);
ERR_FAIL_COND(!tile_data);
- bool valid;
- Variant value = tile_data->get(p_property, &valid);
- if (!valid) {
- return;
+ Color color = Color(1.0, 1.0, 1.0);
+ if (p_selected) {
+ Color grid_color = EditorSettings::get_singleton()->get("editors/tiles_editor/grid_color");
+ Color selection_color = Color().from_hsv(Math::fposmod(grid_color.get_h() + 0.5, 1.0), grid_color.get_s(), grid_color.get_v(), 1.0);
+ color = selection_color;
}
- ERR_FAIL_COND(value.get_type() != Variant::INT);
-
Ref<Texture2D> position_icon = TileSetEditor::get_singleton()->get_theme_icon("EditorPosition", "EditorIcons");
- p_canvas_item->draw_texture(position_icon, p_transform.xform(Vector2(0, value)) - position_icon->get_size() / 2);
+ p_canvas_item->draw_texture(position_icon, p_transform.xform(Vector2(0, tile_data->get_y_sort_origin())) - position_icon->get_size() / 2, color);
}
-void TileDataOcclusionShapeEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) {
- TileData *tile_data = _get_tile_data(p_tile_set, p_atlas_source_id, p_atlas_coords, p_alternative_tile);
+void TileDataOcclusionShapeEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected) {
+ TileData *tile_data = _get_tile_data(p_cell);
ERR_FAIL_COND(!tile_data);
- Vector<String> components = String(p_property).split("/", true);
- if (components[0].begins_with("occlusion_layer_") && components[0].trim_prefix("occlusion_layer_").is_valid_int()) {
- int occlusion_layer = components[0].trim_prefix("occlusion_layer_").to_int();
- if (occlusion_layer >= 0 && occlusion_layer < p_tile_set->get_occlusion_layers_count()) {
- // Draw all shapes.
- Vector<Color> debug_occlusion_color;
- debug_occlusion_color.push_back(Color(0.5, 0, 0, 0.6));
+ Color grid_color = EditorSettings::get_singleton()->get("editors/tiles_editor/grid_color");
+ Color selection_color = Color().from_hsv(Math::fposmod(grid_color.get_h() + 0.5, 1.0), grid_color.get_s(), grid_color.get_v(), 1.0);
+ Color color = grid_color.darkened(0.2);
+ if (p_selected) {
+ color = selection_color.darkened(0.2);
+ }
+ color.a *= 0.5;
- RenderingServer::get_singleton()->canvas_item_add_set_transform(p_canvas_item->get_canvas_item(), p_transform);
- Ref<OccluderPolygon2D> occluder = tile_data->get_occluder(occlusion_layer);
- if (occluder.is_valid() && occluder->get_polygon().size() >= 3) {
- p_canvas_item->draw_polygon(Variant(occluder->get_polygon()), debug_occlusion_color);
- }
- RenderingServer::get_singleton()->canvas_item_add_set_transform(p_canvas_item->get_canvas_item(), Transform2D());
+ Vector<Color> debug_occlusion_color;
+ debug_occlusion_color.push_back(color);
+
+ RenderingServer::get_singleton()->canvas_item_add_set_transform(p_canvas_item->get_canvas_item(), p_transform);
+ Ref<OccluderPolygon2D> occluder = tile_data->get_occluder(occlusion_layer);
+ if (occluder.is_valid() && occluder->get_polygon().size() >= 3) {
+ p_canvas_item->draw_polygon(Variant(occluder->get_polygon()), debug_occlusion_color);
+ }
+ RenderingServer::get_singleton()->canvas_item_add_set_transform(p_canvas_item->get_canvas_item(), Transform2D());
+}
+
+Variant TileDataOcclusionShapeEditor::_get_painted_value() {
+ Ref<OccluderPolygon2D> occluder_polygon;
+ occluder_polygon.instantiate();
+ if (polygon_editor->get_polygon_count() >= 1) {
+ occluder_polygon->set_polygon(polygon_editor->get_polygon(0));
+ }
+ return occluder_polygon;
+}
+
+void TileDataOcclusionShapeEditor::_set_painted_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(p_coords, p_alternative_tile));
+ ERR_FAIL_COND(!tile_data);
+
+ Ref<OccluderPolygon2D> occluder_polygon = tile_data->get_occluder(occlusion_layer);
+ polygon_editor->clear_polygons();
+ if (occluder_polygon.is_valid()) {
+ polygon_editor->add_polygon(occluder_polygon->get_polygon());
+ }
+ polygon_editor->set_background(p_tile_set_atlas_source->get_texture(), p_tile_set_atlas_source->get_tile_texture_region(p_coords), p_tile_set_atlas_source->get_tile_effective_texture_offset(p_coords, p_alternative_tile), tile_data->get_flip_h(), tile_data->get_flip_v(), tile_data->get_transpose(), tile_data->get_modulate());
+}
+
+void TileDataOcclusionShapeEditor::_set_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile, Variant p_value) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(p_coords, p_alternative_tile));
+ ERR_FAIL_COND(!tile_data);
+ Ref<OccluderPolygon2D> occluder_polygon = p_value;
+ tile_data->set_occluder(occlusion_layer, occluder_polygon);
+
+ polygon_editor->set_background(p_tile_set_atlas_source->get_texture(), p_tile_set_atlas_source->get_tile_texture_region(p_coords), p_tile_set_atlas_source->get_tile_effective_texture_offset(p_coords, p_alternative_tile), tile_data->get_flip_h(), tile_data->get_flip_v(), tile_data->get_transpose(), tile_data->get_modulate());
+}
+
+Variant TileDataOcclusionShapeEditor::_get_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(p_coords, p_alternative_tile));
+ ERR_FAIL_COND_V(!tile_data, Variant());
+ return tile_data->get_occluder(occlusion_layer);
+}
+
+void TileDataOcclusionShapeEditor::_setup_undo_redo_action(TileSetAtlasSource *p_tile_set_atlas_source, Map<TileMapCell, Variant> p_previous_values, Variant p_new_value) {
+ for (Map<TileMapCell, Variant>::Element *E = p_previous_values.front(); E; E = E->next()) {
+ Vector2i coords = E->key().get_atlas_coords();
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/occlusion_layer_%d/polygon", coords.x, coords.y, E->key().alternative_tile, occlusion_layer), E->get());
+ undo_redo->add_do_property(p_tile_set_atlas_source, vformat("%d:%d/%d/occlusion_layer_%d/polygon", coords.x, coords.y, E->key().alternative_tile, occlusion_layer), p_new_value);
+ }
+}
+
+void TileDataOcclusionShapeEditor::_tile_set_changed() {
+ polygon_editor->set_tile_set(tile_set);
+}
+
+void TileDataOcclusionShapeEditor::_notification(int p_what) {
+ switch (p_what) {
+ case NOTIFICATION_ENTER_TREE:
+ polygon_editor->set_polygons_color(get_tree()->get_debug_collisions_color());
+ break;
+ default:
+ break;
+ }
+}
+
+TileDataOcclusionShapeEditor::TileDataOcclusionShapeEditor() {
+ polygon_editor = memnew(GenericTilePolygonEditor);
+ add_child(polygon_editor);
+}
+
+void TileDataCollisionEditor::_property_value_changed(StringName p_property, Variant p_value, StringName p_field) {
+ dummy_object->set(p_property, p_value);
+}
+
+void TileDataCollisionEditor::_polygons_changed() {
+ // Update the dummy object properties and their editors.
+ for (int i = 0; i < polygon_editor->get_polygon_count(); i++) {
+ StringName one_way_property = vformat("polygon_%d_one_way", i);
+ StringName one_way_margin_property = vformat("polygon_%d_one_way_margin", i);
+
+ if (!dummy_object->has_dummy_property(one_way_property)) {
+ dummy_object->add_dummy_property(one_way_property);
+ dummy_object->set(one_way_property, false);
}
+
+ if (!dummy_object->has_dummy_property(one_way_margin_property)) {
+ dummy_object->add_dummy_property(one_way_margin_property);
+ dummy_object->set(one_way_margin_property, 1.0);
+ }
+
+ if (!property_editors.has(one_way_property)) {
+ EditorProperty *one_way_property_editor = EditorInspectorDefaultPlugin::get_editor_for_property(dummy_object, Variant::BOOL, one_way_property, PROPERTY_HINT_NONE, "", PROPERTY_USAGE_DEFAULT);
+ one_way_property_editor->set_object_and_property(dummy_object, one_way_property);
+ one_way_property_editor->set_label(one_way_property);
+ one_way_property_editor->connect("property_changed", callable_mp(this, &TileDataCollisionEditor::_property_value_changed).unbind(1));
+ one_way_property_editor->update_property();
+ add_child(one_way_property_editor);
+ property_editors[one_way_property] = one_way_property_editor;
+ }
+
+ if (!property_editors.has(one_way_margin_property)) {
+ EditorProperty *one_way_margin_property_editor = EditorInspectorDefaultPlugin::get_editor_for_property(dummy_object, Variant::FLOAT, one_way_margin_property, PROPERTY_HINT_NONE, "", PROPERTY_USAGE_DEFAULT);
+ one_way_margin_property_editor->set_object_and_property(dummy_object, one_way_margin_property);
+ one_way_margin_property_editor->set_label(one_way_margin_property);
+ one_way_margin_property_editor->connect("property_changed", callable_mp(this, &TileDataCollisionEditor::_property_value_changed).unbind(1));
+ one_way_margin_property_editor->update_property();
+ add_child(one_way_margin_property_editor);
+ property_editors[one_way_margin_property] = one_way_margin_property_editor;
+ }
+ }
+
+ // Remove uneeded properties and their editors.
+ for (int i = polygon_editor->get_polygon_count(); dummy_object->has_dummy_property(vformat("polygon_%d_one_way", i)); i++) {
+ dummy_object->remove_dummy_property(vformat("polygon_%d_one_way", i));
+ }
+ for (int i = polygon_editor->get_polygon_count(); dummy_object->has_dummy_property(vformat("polygon_%d_one_way_margin", i)); i++) {
+ dummy_object->remove_dummy_property(vformat("polygon_%d_one_way_margin", i));
+ }
+ for (int i = polygon_editor->get_polygon_count(); property_editors.has(vformat("polygon_%d_one_way", i)); i++) {
+ property_editors[vformat("polygon_%d_one_way", i)]->queue_delete();
+ property_editors.erase(vformat("polygon_%d_one_way", i));
}
+ for (int i = polygon_editor->get_polygon_count(); property_editors.has(vformat("polygon_%d_one_way_margin", i)); i++) {
+ property_editors[vformat("polygon_%d_one_way_margin", i)]->queue_delete();
+ property_editors.erase(vformat("polygon_%d_one_way_margin", i));
+ }
+}
+
+Variant TileDataCollisionEditor::_get_painted_value() {
+ Array array;
+ for (int i = 0; i < polygon_editor->get_polygon_count(); i++) {
+ ERR_FAIL_COND_V(polygon_editor->get_polygon(i).size() < 3, Variant());
+ Dictionary dict;
+ dict["points"] = polygon_editor->get_polygon(i);
+ dict["one_way"] = dummy_object->get(vformat("polygon_%d_one_way", i));
+ dict["one_way_margin"] = dummy_object->get(vformat("polygon_%d_one_way_margin", i));
+ array.push_back(dict);
+ }
+
+ return array;
}
-void TileDataCollisionShapeEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) {
- TileData *tile_data = _get_tile_data(p_tile_set, p_atlas_source_id, p_atlas_coords, p_alternative_tile);
+void TileDataCollisionEditor::_set_painted_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(p_coords, p_alternative_tile));
ERR_FAIL_COND(!tile_data);
- Vector<String> components = String(p_property).split("/", true);
- if (components[0].begins_with("physics_layer_") && components[0].trim_prefix("physics_layer_").is_valid_int()) {
- int physics_layer = components[0].trim_prefix("physics_layer_").to_int();
- if (physics_layer >= 0 && physics_layer < p_tile_set->get_physics_layers_count()) {
- // Draw all shapes.
- Color debug_collision_color = p_canvas_item->get_tree()->get_debug_collisions_color();
- RenderingServer::get_singleton()->canvas_item_add_set_transform(p_canvas_item->get_canvas_item(), p_transform);
- for (int i = 0; i < tile_data->get_collision_shapes_count(physics_layer); i++) {
- Ref<Shape2D> shape = tile_data->get_collision_shape_shape(physics_layer, i);
- if (shape.is_valid()) {
- shape->draw(p_canvas_item->get_canvas_item(), debug_collision_color);
- }
- }
- RenderingServer::get_singleton()->canvas_item_add_set_transform(p_canvas_item->get_canvas_item(), Transform2D());
+ polygon_editor->clear_polygons();
+ for (int i = 0; i < tile_data->get_collision_polygons_count(physics_layer); i++) {
+ Vector<Vector2> polygon = tile_data->get_collision_polygon_points(physics_layer, i);
+ if (polygon.size() >= 3) {
+ polygon_editor->add_polygon(polygon);
}
}
+
+ _polygons_changed();
+ for (int i = 0; i < tile_data->get_collision_polygons_count(physics_layer); i++) {
+ dummy_object->set(vformat("polygon_%d_one_way", i), tile_data->is_collision_polygon_one_way(physics_layer, i));
+ dummy_object->set(vformat("polygon_%d_one_way_margin", i), tile_data->get_collision_polygon_one_way_margin(physics_layer, i));
+ }
+ for (Map<StringName, EditorProperty *>::Element *E = property_editors.front(); E; E = E->next()) {
+ E->get()->update_property();
+ }
+
+ polygon_editor->set_background(p_tile_set_atlas_source->get_texture(), p_tile_set_atlas_source->get_tile_texture_region(p_coords), p_tile_set_atlas_source->get_tile_effective_texture_offset(p_coords, p_alternative_tile), tile_data->get_flip_h(), tile_data->get_flip_v(), tile_data->get_transpose(), tile_data->get_modulate());
}
-void TileDataTerrainsEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) {
- TileData *tile_data = _get_tile_data(p_tile_set, p_atlas_source_id, p_atlas_coords, p_alternative_tile);
+void TileDataCollisionEditor::_set_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile, Variant p_value) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(p_coords, p_alternative_tile));
ERR_FAIL_COND(!tile_data);
- Vector<String> components = String(p_property).split("/", true);
- if (components[0] == "terrain_mode" || components[0] == "terrain" || components[0] == "terrains_peering_bit") {
- TileSetPluginAtlasTerrain::draw_terrains(p_canvas_item, p_transform, p_tile_set, tile_data);
+ Array array = p_value;
+ tile_data->set_collision_polygons_count(physics_layer, array.size());
+ for (int i = 0; i < array.size(); i++) {
+ Dictionary dict = array[i];
+ tile_data->set_collision_polygon_points(physics_layer, i, dict["points"]);
+ tile_data->set_collision_polygon_one_way(physics_layer, i, dict["one_way"]);
+ tile_data->set_collision_polygon_one_way_margin(physics_layer, i, dict["one_way_margin"]);
+ }
+
+ polygon_editor->set_background(p_tile_set_atlas_source->get_texture(), p_tile_set_atlas_source->get_tile_texture_region(p_coords), p_tile_set_atlas_source->get_tile_effective_texture_offset(p_coords, p_alternative_tile), tile_data->get_flip_h(), tile_data->get_flip_v(), tile_data->get_transpose(), tile_data->get_modulate());
+}
+
+Variant TileDataCollisionEditor::_get_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(p_coords, p_alternative_tile));
+ ERR_FAIL_COND_V(!tile_data, Variant());
+
+ Array array;
+ for (int i = 0; i < tile_data->get_collision_polygons_count(physics_layer); i++) {
+ Dictionary dict;
+ dict["points"] = tile_data->get_collision_polygon_points(physics_layer, i);
+ dict["one_way"] = tile_data->is_collision_polygon_one_way(physics_layer, i);
+ dict["one_way_margin"] = tile_data->get_collision_polygon_one_way_margin(physics_layer, i);
+ array.push_back(dict);
+ }
+ return array;
+}
+
+void TileDataCollisionEditor::_setup_undo_redo_action(TileSetAtlasSource *p_tile_set_atlas_source, Map<TileMapCell, Variant> p_previous_values, Variant p_new_value) {
+ Array new_array = p_new_value;
+ for (Map<TileMapCell, Variant>::Element *E = p_previous_values.front(); E; E = E->next()) {
+ Array old_array = E->get();
+
+ Vector2i coords = E->key().get_atlas_coords();
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/physics_layer_%d/polygons_count", coords.x, coords.y, E->key().alternative_tile, physics_layer), old_array.size());
+ for (int i = 0; i < old_array.size(); i++) {
+ Dictionary dict = old_array[i];
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/physics_layer_%d/polygon_%d/points", coords.x, coords.y, E->key().alternative_tile, physics_layer, i), dict["points"]);
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/physics_layer_%d/polygon_%d/one_way", coords.x, coords.y, E->key().alternative_tile, physics_layer, i), dict["one_way"]);
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/physics_layer_%d/polygon_%d/one_way_margin", coords.x, coords.y, E->key().alternative_tile, physics_layer, i), dict["one_way_margin"]);
+ }
+
+ undo_redo->add_do_property(p_tile_set_atlas_source, vformat("%d:%d/%d/physics_layer_%d/polygons_count", coords.x, coords.y, E->key().alternative_tile, physics_layer), new_array.size());
+ for (int i = 0; i < new_array.size(); i++) {
+ Dictionary dict = new_array[i];
+ undo_redo->add_do_property(p_tile_set_atlas_source, vformat("%d:%d/%d/physics_layer_%d/polygon_%d/points", coords.x, coords.y, E->key().alternative_tile, physics_layer, i), dict["points"]);
+ undo_redo->add_do_property(p_tile_set_atlas_source, vformat("%d:%d/%d/physics_layer_%d/polygon_%d/one_way", coords.x, coords.y, E->key().alternative_tile, physics_layer, i), dict["one_way"]);
+ undo_redo->add_do_property(p_tile_set_atlas_source, vformat("%d:%d/%d/physics_layer_%d/polygon_%d/one_way_margin", coords.x, coords.y, E->key().alternative_tile, physics_layer, i), dict["one_way_margin"]);
+ }
+ }
+}
+
+void TileDataCollisionEditor::_tile_set_changed() {
+ polygon_editor->set_tile_set(tile_set);
+ _polygons_changed();
+}
+
+void TileDataCollisionEditor::_notification(int p_what) {
+ switch (p_what) {
+ case NOTIFICATION_ENTER_TREE:
+ polygon_editor->set_polygons_color(get_tree()->get_debug_collisions_color());
+ break;
+ default:
+ break;
}
}
-void TileDataNavigationPolygonEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) {
- TileData *tile_data = _get_tile_data(p_tile_set, p_atlas_source_id, p_atlas_coords, p_alternative_tile);
+TileDataCollisionEditor::TileDataCollisionEditor() {
+ polygon_editor = memnew(GenericTilePolygonEditor);
+ polygon_editor->set_multiple_polygon_mode(true);
+ polygon_editor->connect("polygons_changed", callable_mp(this, &TileDataCollisionEditor::_polygons_changed));
+ add_child(polygon_editor);
+
+ _polygons_changed();
+}
+
+TileDataCollisionEditor::~TileDataCollisionEditor() {
+ memdelete(dummy_object);
+}
+
+void TileDataCollisionEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected) {
+ TileData *tile_data = _get_tile_data(p_cell);
ERR_FAIL_COND(!tile_data);
- Vector<String> components = String(p_property).split("/", true);
- if (components[0].begins_with("navigation_layer_") && components[0].trim_prefix("navigation_layer_").is_valid_int()) {
- int navigation_layer = components[0].trim_prefix("navigation_layer_").to_int();
- if (navigation_layer >= 0 && navigation_layer < p_tile_set->get_navigation_layers_count()) {
- // Draw all shapes.
- RenderingServer::get_singleton()->canvas_item_add_set_transform(p_canvas_item->get_canvas_item(), p_transform);
+ // Draw all shapes.
+ Vector<Color> color;
+ if (p_selected) {
+ Color grid_color = EditorSettings::get_singleton()->get("editors/tiles_editor/grid_color");
+ Color selection_color = Color().from_hsv(Math::fposmod(grid_color.get_h() + 0.5, 1.0), grid_color.get_s(), grid_color.get_v(), 1.0);
+ selection_color.a = 0.7;
+ color.push_back(selection_color);
+ } else {
+ Color debug_collision_color = p_canvas_item->get_tree()->get_debug_collisions_color();
+ color.push_back(debug_collision_color);
+ }
+
+ RenderingServer::get_singleton()->canvas_item_add_set_transform(p_canvas_item->get_canvas_item(), p_transform);
+ for (int i = 0; i < tile_data->get_collision_polygons_count(physics_layer); i++) {
+ Vector<Vector2> polygon = tile_data->get_collision_polygon_points(physics_layer, i);
+ if (polygon.size() >= 3) {
+ p_canvas_item->draw_polygon(polygon, color);
+ }
+ }
+ RenderingServer::get_singleton()->canvas_item_add_set_transform(p_canvas_item->get_canvas_item(), Transform2D());
+}
+
+void TileDataTerrainsEditor::_update_terrain_selector() {
+ ERR_FAIL_COND(!tile_set.is_valid());
+
+ // Update the terrain set selector.
+ Vector<String> options;
+ options.push_back(String(TTR("No terrains")) + String(":-1"));
+ for (int i = 0; i < tile_set->get_terrain_sets_count(); i++) {
+ options.push_back(vformat("Terrain Set %d", i));
+ }
+ terrain_set_property_editor->setup(options);
+ terrain_set_property_editor->update_property();
+
+ // Update the terrain selector.
+ int terrain_set = int(dummy_object->get("terrain_set"));
+ if (terrain_set == -1) {
+ terrain_property_editor->hide();
+ } else {
+ options.clear();
+ Vector<Vector<Ref<Texture2D>>> icons = tile_set->generate_terrains_icons(Size2(16, 16) * EDSCALE);
+ options.push_back(String(TTR("No terrain")) + String(":-1"));
+ for (int i = 0; i < tile_set->get_terrains_count(terrain_set); i++) {
+ String name = tile_set->get_terrain_name(terrain_set, i);
+ if (name.is_empty()) {
+ options.push_back(vformat("Terrain %d", i));
+ } else {
+ options.push_back(name);
+ }
+ }
+ terrain_property_editor->setup(options);
+ terrain_property_editor->update_property();
+
+ // Kind of a hack to set icons.
+ // We could provide a way to modify that in the EditorProperty.
+ OptionButton *option_button = Object::cast_to<OptionButton>(terrain_property_editor->get_child(0));
+ for (int terrain = 0; terrain < tile_set->get_terrains_count(terrain_set); terrain++) {
+ option_button->set_item_icon(terrain + 1, icons[terrain_set][terrain]);
+ }
+ terrain_property_editor->show();
+ }
+}
+
+void TileDataTerrainsEditor::_property_value_changed(StringName p_property, Variant p_value, StringName p_field) {
+ Variant old_value = dummy_object->get(p_property);
+ dummy_object->set(p_property, p_value);
+ if (p_property == "terrain_set") {
+ if (p_value != old_value) {
+ dummy_object->set("terrain", -1);
+ }
+ _update_terrain_selector();
+ }
+ emit_signal("needs_redraw");
+}
+
+void TileDataTerrainsEditor::_tile_set_changed() {
+ ERR_FAIL_COND(!tile_set.is_valid());
+
+ // Fix if wrong values are selected.
+ if (int(dummy_object->get("terrain_set")) > tile_set->get_terrain_sets_count()) {
+ dummy_object->set("terrain_set", -1);
+ }
+ int terrain_set = int(dummy_object->get("terrain"));
+ if (terrain_set >= 0) {
+ if (int(dummy_object->get("terrain")) > tile_set->get_terrains_count(terrain_set)) {
+ dummy_object->set("terrain", -1);
+ }
+ }
+
+ _update_terrain_selector();
+}
+
+void TileDataTerrainsEditor::forward_draw_over_atlas(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_set_atlas_source, CanvasItem *p_canvas_item, Transform2D p_transform) {
+ ERR_FAIL_COND(!tile_set.is_valid());
- Ref<NavigationPolygon> navigation_polygon = tile_data->get_navigation_polygon(navigation_layer);
- if (navigation_polygon.is_valid()) {
- Vector<Vector2> verts = navigation_polygon->get_vertices();
- if (verts.size() < 3) {
- return;
+ // Draw the hovered terrain bit, or the whole tile if it has the wrong terrain set.
+ Vector2i hovered_coords = TileSetSource::INVALID_ATLAS_COORDS;
+ if (drag_type == DRAG_TYPE_NONE) {
+ Vector2i mouse_pos = p_transform.affine_inverse().xform(p_canvas_item->get_local_mouse_position());
+ hovered_coords = p_tile_atlas_view->get_atlas_tile_coords_at_pos(mouse_pos);
+ hovered_coords = p_tile_set_atlas_source->get_tile_at_coords(hovered_coords);
+ if (hovered_coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(hovered_coords, 0));
+ int terrain_set = tile_data->get_terrain_set();
+ Rect2i texture_region = p_tile_set_atlas_source->get_tile_texture_region(hovered_coords);
+ Vector2i position = (texture_region.position + texture_region.get_end()) / 2 + p_tile_set_atlas_source->get_tile_effective_texture_offset(hovered_coords, 0);
+
+ if (terrain_set >= 0 && terrain_set == int(dummy_object->get("terrain_set"))) {
+ // Draw hovered bit.
+ Transform2D xform;
+ xform.set_origin(position);
+
+ Vector<Color> color;
+ color.push_back(Color(1.0, 1.0, 1.0, 0.5));
+
+ for (int i = 0; i < TileSet::CELL_NEIGHBOR_MAX; i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ if (tile_set->is_valid_peering_bit_terrain(terrain_set, bit)) {
+ Vector<Vector2> polygon = tile_set->get_terrain_bit_polygon(terrain_set, bit);
+ if (Geometry2D::is_point_in_polygon(xform.affine_inverse().xform(mouse_pos), polygon)) {
+ p_canvas_item->draw_set_transform_matrix(p_transform * xform);
+ p_canvas_item->draw_polygon(polygon, color);
+ }
+ }
}
+ } else {
+ // Draw hovered tile.
+ Vector2i tile_size = tile_set->get_tile_size();
+ Rect2i rect = p_transform.xform(Rect2i(position - tile_size / 2, tile_size));
+ tile_set->draw_tile_shape(p_canvas_item, rect, Color(1.0, 1.0, 1.0, 0.5), true);
+ }
+ }
+ }
+
+ // Dim terrains with wrong terrain set.
+ Ref<Font> font = TileSetEditor::get_singleton()->get_theme_font("bold", "EditorFonts");
+ for (int i = 0; i < p_tile_set_atlas_source->get_tiles_count(); i++) {
+ Vector2i coords = p_tile_set_atlas_source->get_tile_id(i);
+ if (coords != hovered_coords) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(coords, 0));
+ if (tile_data->get_terrain_set() != int(dummy_object->get("terrain_set"))) {
+ // Dimming
+ p_canvas_item->draw_set_transform_matrix(p_transform);
+ Rect2i rect = p_tile_set_atlas_source->get_tile_texture_region(coords);
+ p_canvas_item->draw_rect(rect, Color(0.0, 0.0, 0.0, 0.3));
+
+ // Text
+ p_canvas_item->draw_set_transform_matrix(Transform2D());
+ Rect2i texture_region = p_tile_set_atlas_source->get_tile_texture_region(coords);
+ Vector2i position = (texture_region.position + texture_region.get_end()) / 2 + p_tile_set_atlas_source->get_tile_effective_texture_offset(coords, 0);
+
+ Color color = Color(1, 1, 1);
+ String text;
+ if (tile_data->get_terrain_set() >= 0) {
+ text = vformat("%d", tile_data->get_terrain_set());
+ } else {
+ text = "-";
+ }
+ Vector2 string_size = font->get_string_size(text);
+ p_canvas_item->draw_string(font, p_transform.xform(position) + Vector2i(-string_size.x / 2, string_size.y / 2), text, HALIGN_CENTER, string_size.x, -1, color, 1, Color(0, 0, 0, 1));
+ }
+ }
+ }
+ p_canvas_item->draw_set_transform_matrix(Transform2D());
+
+ if (drag_type == DRAG_TYPE_PAINT_TERRAIN_SET_RECT) {
+ // Draw selection rectangle.
+ Color grid_color = EditorSettings::get_singleton()->get("editors/tiles_editor/grid_color");
+ Color selection_color = Color().from_hsv(Math::fposmod(grid_color.get_h() + 0.5, 1.0), grid_color.get_s(), grid_color.get_v(), 1.0);
+
+ p_canvas_item->draw_set_transform_matrix(p_transform);
- Color color = p_canvas_item->get_tree()->get_debug_navigation_color();
+ Rect2i rect;
+ rect.set_position(p_tile_atlas_view->get_atlas_tile_coords_at_pos(drag_start_pos));
+ rect.set_end(p_tile_atlas_view->get_atlas_tile_coords_at_pos(p_transform.affine_inverse().xform(p_canvas_item->get_local_mouse_position())));
+ rect = rect.abs();
- RandomPCG rand;
- for (int i = 0; i < navigation_polygon->get_polygon_count(); i++) {
- // An array of vertices for this polygon.
- Vector<int> polygon = navigation_polygon->get_polygon(i);
- Vector<Vector2> vertices;
- vertices.resize(polygon.size());
+ Set<TileMapCell> edited;
+ for (int x = rect.get_position().x; x <= rect.get_end().x; x++) {
+ for (int y = rect.get_position().y; y <= rect.get_end().y; y++) {
+ Vector2i coords = Vector2i(x, y);
+ coords = p_tile_set_atlas_source->get_tile_at_coords(coords);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = 0;
+ edited.insert(cell);
+ }
+ }
+ }
+
+ for (Set<TileMapCell>::Element *E = edited.front(); E; E = E->next()) {
+ Vector2i coords = E->get().get_atlas_coords();
+ p_canvas_item->draw_rect(p_tile_set_atlas_source->get_tile_texture_region(coords), selection_color, false);
+ }
+ p_canvas_item->draw_set_transform_matrix(Transform2D());
+ } else if (drag_type == DRAG_TYPE_PAINT_TERRAIN_BITS_RECT) {
+ // Highlight selected peering bits.
+ Dictionary painted = Dictionary(drag_painted_value);
+ int terrain_set = int(painted["terrain_set"]);
+
+ Rect2i rect;
+ rect.set_position(p_tile_atlas_view->get_atlas_tile_coords_at_pos(drag_start_pos));
+ rect.set_end(p_tile_atlas_view->get_atlas_tile_coords_at_pos(p_transform.affine_inverse().xform(p_canvas_item->get_local_mouse_position())));
+ rect = rect.abs();
+
+ Set<TileMapCell> edited;
+ for (int x = rect.get_position().x; x <= rect.get_end().x; x++) {
+ for (int y = rect.get_position().y; y <= rect.get_end().y; y++) {
+ Vector2i coords = Vector2i(x, y);
+ coords = p_tile_set_atlas_source->get_tile_at_coords(coords);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(coords, 0));
+ if (tile_data->get_terrain_set() == terrain_set) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = 0;
+ edited.insert(cell);
+ }
+ }
+ }
+ }
+
+ Vector2 end = p_transform.affine_inverse().xform(p_canvas_item->get_local_mouse_position());
+ Vector<Point2> mouse_pos_rect_polygon;
+ mouse_pos_rect_polygon.push_back(drag_start_pos);
+ mouse_pos_rect_polygon.push_back(Vector2(end.x, drag_start_pos.y));
+ mouse_pos_rect_polygon.push_back(end);
+ mouse_pos_rect_polygon.push_back(Vector2(drag_start_pos.x, end.y));
+
+ Vector<Color> color;
+ color.push_back(Color(1.0, 1.0, 1.0, 0.5));
+
+ p_canvas_item->draw_set_transform_matrix(p_transform);
+
+ for (Set<TileMapCell>::Element *E = edited.front(); E; E = E->next()) {
+ Vector2i coords = E->get().get_atlas_coords();
+
+ Rect2i texture_region = p_tile_set_atlas_source->get_tile_texture_region(coords);
+ Vector2i position = (texture_region.position + texture_region.get_end()) / 2 + p_tile_set_atlas_source->get_tile_effective_texture_offset(coords, 0);
+
+ for (int i = 0; i < TileSet::CELL_NEIGHBOR_MAX; i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ if (tile_set->is_valid_peering_bit_terrain(terrain_set, bit)) {
+ Vector<Vector2> polygon = tile_set->get_terrain_bit_polygon(terrain_set, bit);
for (int j = 0; j < polygon.size(); j++) {
- ERR_FAIL_INDEX(polygon[j], verts.size());
- vertices.write[j] = verts[polygon[j]];
+ polygon.write[j] += position;
+ }
+ if (!Geometry2D::intersect_polygons(polygon, mouse_pos_rect_polygon).is_empty()) {
+ // Draw bit.
+ p_canvas_item->draw_polygon(polygon, color);
+ }
+ }
+ }
+ }
+
+ p_canvas_item->draw_set_transform_matrix(Transform2D());
+ }
+}
+
+void TileDataTerrainsEditor::forward_draw_over_alternatives(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_set_atlas_source, CanvasItem *p_canvas_item, Transform2D p_transform) {
+ ERR_FAIL_COND(!tile_set.is_valid());
+
+ // Draw the hovered terrain bit, or the whole tile if it has the wrong terrain set.
+ Vector2i hovered_coords = TileSetSource::INVALID_ATLAS_COORDS;
+ int hovered_alternative = TileSetSource::INVALID_TILE_ALTERNATIVE;
+ if (drag_type == DRAG_TYPE_NONE) {
+ Vector2i mouse_pos = p_transform.affine_inverse().xform(p_canvas_item->get_local_mouse_position());
+ Vector3i hovered = p_tile_atlas_view->get_alternative_tile_at_pos(mouse_pos);
+ hovered_coords = Vector2i(hovered.x, hovered.y);
+ hovered_alternative = hovered.z;
+ if (hovered_coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(hovered_coords, hovered_alternative));
+ int terrain_set = tile_data->get_terrain_set();
+ Rect2i texture_region = p_tile_atlas_view->get_alternative_tile_rect(hovered_coords, hovered_alternative);
+ Vector2i position = (texture_region.position + texture_region.get_end()) / 2 + p_tile_set_atlas_source->get_tile_effective_texture_offset(hovered_coords, hovered_alternative);
+
+ if (terrain_set == int(dummy_object->get("terrain_set"))) {
+ // Draw hovered bit.
+ Transform2D xform;
+ xform.set_origin(position);
+
+ Vector<Color> color;
+ color.push_back(Color(1.0, 1.0, 1.0, 0.5));
+
+ for (int i = 0; i < TileSet::CELL_NEIGHBOR_MAX; i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ if (tile_set->is_valid_peering_bit_terrain(terrain_set, bit)) {
+ Vector<Vector2> polygon = tile_set->get_terrain_bit_polygon(terrain_set, bit);
+ if (Geometry2D::is_point_in_polygon(xform.affine_inverse().xform(mouse_pos), polygon)) {
+ p_canvas_item->draw_set_transform_matrix(p_transform * xform);
+ p_canvas_item->draw_polygon(polygon, color);
+ }
+ }
+ }
+ } else {
+ // Draw hovered tile.
+ Vector2i tile_size = tile_set->get_tile_size();
+ Rect2i rect = p_transform.xform(Rect2i(position - tile_size / 2, tile_size));
+ tile_set->draw_tile_shape(p_canvas_item, rect, Color(1.0, 1.0, 1.0, 0.5), true);
+ }
+ }
+ }
+
+ // Dim terrains with wrong terrain set.
+ Ref<Font> font = TileSetEditor::get_singleton()->get_theme_font("bold", "EditorFonts");
+ for (int i = 0; i < p_tile_set_atlas_source->get_tiles_count(); i++) {
+ Vector2i coords = p_tile_set_atlas_source->get_tile_id(i);
+ for (int j = 1; j < p_tile_set_atlas_source->get_alternative_tiles_count(coords); j++) {
+ int alternative_tile = p_tile_set_atlas_source->get_alternative_tile_id(coords, j);
+ if (coords != hovered_coords || alternative_tile != hovered_alternative) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(coords, alternative_tile));
+ if (tile_data->get_terrain_set() != int(dummy_object->get("terrain_set"))) {
+ // Dimming
+ p_canvas_item->draw_set_transform_matrix(p_transform);
+ Rect2i rect = p_tile_atlas_view->get_alternative_tile_rect(coords, alternative_tile);
+ p_canvas_item->draw_rect(rect, Color(0.0, 0.0, 0.0, 0.3));
+
+ // Text
+ p_canvas_item->draw_set_transform_matrix(Transform2D());
+ Rect2i texture_region = p_tile_atlas_view->get_alternative_tile_rect(coords, alternative_tile);
+ Vector2i position = (texture_region.position + texture_region.get_end()) / 2 + p_tile_set_atlas_source->get_tile_effective_texture_offset(coords, 0);
+
+ Color color = Color(1, 1, 1);
+ String text;
+ if (tile_data->get_terrain_set() >= 0) {
+ text = vformat("%d", tile_data->get_terrain_set());
+ } else {
+ text = "-";
+ }
+ Vector2 string_size = font->get_string_size(text);
+ p_canvas_item->draw_string(font, p_transform.xform(position) + Vector2i(-string_size.x / 2, string_size.y / 2), text, HALIGN_CENTER, string_size.x, -1, color, 1, Color(0, 0, 0, 1));
+ }
+ }
+ }
+ }
+
+ p_canvas_item->draw_set_transform_matrix(Transform2D());
+}
+
+void TileDataTerrainsEditor::forward_painting_atlas_gui_input(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_set_atlas_source, const Ref<InputEvent> &p_event) {
+ Ref<InputEventMouseMotion> mm = p_event;
+ if (mm.is_valid()) {
+ if (drag_type == DRAG_TYPE_PAINT_TERRAIN_SET) {
+ Vector<Vector2i> line = Geometry2D::bresenham_line(p_tile_atlas_view->get_atlas_tile_coords_at_pos(drag_last_pos), p_tile_atlas_view->get_atlas_tile_coords_at_pos(mm->get_position()));
+ for (int i = 0; i < line.size(); i++) {
+ Vector2i coords = p_tile_set_atlas_source->get_tile_at_coords(line[i]);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ int terrain_set = drag_painted_value;
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = 0;
+
+ // Save the old terrain_set and terrains bits.
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(coords, 0));
+ if (!drag_modified.has(cell)) {
+ Dictionary dict;
+ dict["terrain_set"] = tile_data->get_terrain_set();
+ Array array;
+ for (int j = 0; j < TileSet::CELL_NEIGHBOR_MAX; j++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(j);
+ array.push_back(tile_data->is_valid_peering_bit_terrain(bit) ? tile_data->get_peering_bit_terrain(bit) : -1);
+ }
+ dict["terrain_peering_bits"] = array;
+ drag_modified[cell] = dict;
+ }
+
+ // Set the terrain_set.
+ tile_data->set_terrain_set(terrain_set);
+ }
+ }
+ drag_last_pos = mm->get_position();
+ } else if (drag_type == DRAG_TYPE_PAINT_TERRAIN_BITS) {
+ int terrain_set = Dictionary(drag_painted_value)["terrain_set"];
+ int terrain = Dictionary(drag_painted_value)["terrain"];
+ Vector<Vector2i> line = Geometry2D::bresenham_line(p_tile_atlas_view->get_atlas_tile_coords_at_pos(drag_last_pos), p_tile_atlas_view->get_atlas_tile_coords_at_pos(mm->get_position()));
+ for (int i = 0; i < line.size(); i++) {
+ Vector2i coords = p_tile_set_atlas_source->get_tile_at_coords(line[i]);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = 0;
+
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(coords, 0));
+ if (tile_data->get_terrain_set() == terrain_set) {
+ // Save the old terrain_set and terrains bits.
+ if (!drag_modified.has(cell)) {
+ Dictionary dict;
+ dict["terrain_set"] = tile_data->get_terrain_set();
+ Array array;
+ for (int j = 0; j < TileSet::CELL_NEIGHBOR_MAX; j++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(j);
+ array.push_back(tile_data->is_valid_peering_bit_terrain(bit) ? tile_data->get_peering_bit_terrain(bit) : -1);
+ }
+ dict["terrain_peering_bits"] = array;
+ drag_modified[cell] = dict;
+ }
+
+ // Set the terrains bits.
+ Rect2i texture_region = p_tile_set_atlas_source->get_tile_texture_region(coords);
+ Vector2i position = (texture_region.position + texture_region.get_end()) / 2 + p_tile_set_atlas_source->get_tile_effective_texture_offset(coords, 0);
+ for (int j = 0; j < TileSet::CELL_NEIGHBOR_MAX; j++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(j);
+ if (tile_data->is_valid_peering_bit_terrain(bit)) {
+ Vector<Vector2> polygon = tile_set->get_terrain_bit_polygon(tile_data->get_terrain_set(), bit);
+ if (Geometry2D::is_segment_intersecting_polygon(mm->get_position() - position, drag_last_pos - position, polygon)) {
+ tile_data->set_peering_bit_terrain(bit, terrain);
+ }
+ }
+ }
+ }
+ }
+ }
+ drag_last_pos = mm->get_position();
+ }
+ }
+
+ Ref<InputEventMouseButton> mb = p_event;
+ if (mb.is_valid()) {
+ if (mb->get_button_index() == MOUSE_BUTTON_LEFT) {
+ if (mb->is_pressed()) {
+ if (picker_button->is_pressed()) {
+ Vector2i coords = p_tile_atlas_view->get_atlas_tile_coords_at_pos(mb->get_position());
+ coords = p_tile_set_atlas_source->get_tile_at_coords(coords);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(coords, 0));
+ int terrain_set = tile_data->get_terrain_set();
+ Rect2i texture_region = p_tile_set_atlas_source->get_tile_texture_region(coords);
+ Vector2i position = (texture_region.position + texture_region.get_end()) / 2 + p_tile_set_atlas_source->get_tile_effective_texture_offset(coords, 0);
+ dummy_object->set("terrain_set", terrain_set);
+ dummy_object->set("terrain", -1);
+ for (int i = 0; i < TileSet::CELL_NEIGHBOR_MAX; i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ if (tile_set->is_valid_peering_bit_terrain(terrain_set, bit)) {
+ Vector<Vector2> polygon = tile_set->get_terrain_bit_polygon(terrain_set, bit);
+ if (Geometry2D::is_point_in_polygon(mb->get_position() - position, polygon)) {
+ dummy_object->set("terrain", tile_data->get_peering_bit_terrain(bit));
+ }
+ }
+ }
+ terrain_set_property_editor->update_property();
+ _update_terrain_selector();
+ picker_button->set_pressed(false);
+ }
+ } else {
+ Vector2i coords = p_tile_atlas_view->get_atlas_tile_coords_at_pos(mb->get_position());
+ coords = p_tile_set_atlas_source->get_tile_at_coords(coords);
+ TileData *tile_data = nullptr;
+ if (coords != TileSetAtlasSource::INVALID_ATLAS_COORDS) {
+ tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(coords, 0));
+ }
+ int terrain_set = int(dummy_object->get("terrain_set"));
+ int terrain = int(dummy_object->get("terrain"));
+ if (terrain_set == -1 || !tile_data || tile_data->get_terrain_set() != terrain_set) {
+ if (mb->is_ctrl_pressed()) {
+ // Paint terrain set with rect.
+ drag_type = DRAG_TYPE_PAINT_TERRAIN_SET_RECT;
+ drag_modified.clear();
+ drag_painted_value = terrain_set;
+ drag_start_pos = mb->get_position();
+ } else {
+ // Paint terrain set.
+ drag_type = DRAG_TYPE_PAINT_TERRAIN_SET;
+ drag_modified.clear();
+ drag_painted_value = terrain_set;
+
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = 0;
+
+ // Save the old terrain_set and terrains bits.
+ Dictionary dict;
+ dict["terrain_set"] = tile_data->get_terrain_set();
+ Array array;
+ for (int i = 0; i < TileSet::CELL_NEIGHBOR_MAX; i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ array.push_back(tile_data->is_valid_peering_bit_terrain(bit) ? tile_data->get_peering_bit_terrain(bit) : -1);
+ }
+ dict["terrain_peering_bits"] = array;
+ drag_modified[cell] = dict;
+
+ // Set the terrain_set.
+ tile_data->set_terrain_set(terrain_set);
+ }
+ drag_last_pos = mb->get_position();
+ }
+ } else if (tile_data && tile_data->get_terrain_set() == terrain_set) {
+ if (mb->is_ctrl_pressed()) {
+ // Paint terrain set with rect.
+ drag_type = DRAG_TYPE_PAINT_TERRAIN_BITS_RECT;
+ drag_modified.clear();
+ Dictionary painted_dict;
+ painted_dict["terrain_set"] = terrain_set;
+ painted_dict["terrain"] = terrain;
+ drag_painted_value = painted_dict;
+ drag_start_pos = mb->get_position();
+ } else {
+ // Paint terrain bits.
+ drag_type = DRAG_TYPE_PAINT_TERRAIN_BITS;
+ drag_modified.clear();
+ Dictionary painted_dict;
+ painted_dict["terrain_set"] = terrain_set;
+ painted_dict["terrain"] = terrain;
+ drag_painted_value = painted_dict;
+
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = 0;
+
+ // Save the old terrain_set and terrains bits.
+ Dictionary dict;
+ dict["terrain_set"] = tile_data->get_terrain_set();
+ Array array;
+ for (int i = 0; i < TileSet::CELL_NEIGHBOR_MAX; i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ array.push_back(tile_data->is_valid_peering_bit_terrain(bit) ? tile_data->get_peering_bit_terrain(bit) : -1);
+ }
+ dict["terrain_peering_bits"] = array;
+ drag_modified[cell] = dict;
+
+ // Set the terrain bit.
+ Rect2i texture_region = p_tile_set_atlas_source->get_tile_texture_region(coords);
+ Vector2i position = (texture_region.position + texture_region.get_end()) / 2 + p_tile_set_atlas_source->get_tile_effective_texture_offset(coords, 0);
+
+ for (int i = 0; i < TileSet::CELL_NEIGHBOR_MAX; i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ if (tile_set->is_valid_peering_bit_terrain(terrain_set, bit)) {
+ Vector<Vector2> polygon = tile_set->get_terrain_bit_polygon(terrain_set, bit);
+ if (Geometry2D::is_point_in_polygon(mb->get_position() - position, polygon)) {
+ tile_data->set_peering_bit_terrain(bit, terrain);
+ }
+ }
+ }
+ }
+ drag_last_pos = mb->get_position();
+ }
+ }
+ }
+ } else {
+ if (drag_type == DRAG_TYPE_PAINT_TERRAIN_SET_RECT) {
+ Rect2i rect;
+ rect.set_position(p_tile_atlas_view->get_atlas_tile_coords_at_pos(drag_start_pos));
+ rect.set_end(p_tile_atlas_view->get_atlas_tile_coords_at_pos(mb->get_position()));
+ rect = rect.abs();
+
+ Set<TileMapCell> edited;
+ for (int x = rect.get_position().x; x <= rect.get_end().x; x++) {
+ for (int y = rect.get_position().y; y <= rect.get_end().y; y++) {
+ Vector2i coords = Vector2i(x, y);
+ coords = p_tile_set_atlas_source->get_tile_at_coords(coords);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = 0;
+ edited.insert(cell);
+ }
+ }
+ }
+ undo_redo->create_action(TTR("Painting Terrain Set"));
+ for (Set<TileMapCell>::Element *E = edited.front(); E; E = E->next()) {
+ Vector2i coords = E->get().get_atlas_coords();
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(coords, 0));
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/terrain_set", coords.x, coords.y, E->get().alternative_tile), tile_data->get_terrain_set());
+ undo_redo->add_do_property(p_tile_set_atlas_source, vformat("%d:%d/%d/terrain_set", coords.x, coords.y, E->get().alternative_tile), drag_painted_value);
+ for (int i = 0; i < TileSet::CELL_NEIGHBOR_MAX; i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ if (tile_data->is_valid_peering_bit_terrain(bit)) {
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/terrains_peering_bit/" + String(TileSet::CELL_NEIGHBOR_ENUM_TO_TEXT[i]), coords.x, coords.y, E->get().alternative_tile), tile_data->get_peering_bit_terrain(bit));
+ }
+ }
+ }
+ undo_redo->commit_action(true);
+ drag_type = DRAG_TYPE_NONE;
+ } else if (drag_type == DRAG_TYPE_PAINT_TERRAIN_SET) {
+ undo_redo->create_action(TTR("Painting Terrain Set"));
+ for (Map<TileMapCell, Variant>::Element *E = drag_modified.front(); E; E = E->next()) {
+ Dictionary dict = E->get();
+ Vector2i coords = E->key().get_atlas_coords();
+ undo_redo->add_do_property(p_tile_set_atlas_source, vformat("%d:%d/%d/terrain_set", coords.x, coords.y, E->key().alternative_tile), drag_painted_value);
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/terrain_set", coords.x, coords.y, E->key().alternative_tile), dict["terrain_set"]);
+ Array array = dict["terrain_peering_bits"];
+ for (int i = 0; i < array.size(); i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ if (tile_set->is_valid_peering_bit_terrain(dict["terrain_set"], bit)) {
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/terrains_peering_bit/" + String(TileSet::CELL_NEIGHBOR_ENUM_TO_TEXT[i]), coords.x, coords.y, E->key().alternative_tile), array[i]);
+ }
+ }
+ }
+ undo_redo->commit_action(false);
+ drag_type = DRAG_TYPE_NONE;
+ } else if (drag_type == DRAG_TYPE_PAINT_TERRAIN_BITS) {
+ Dictionary painted = Dictionary(drag_painted_value);
+ int terrain_set = int(painted["terrain_set"]);
+ int terrain = int(painted["terrain"]);
+ undo_redo->create_action(TTR("Painting Terrain"));
+ for (Map<TileMapCell, Variant>::Element *E = drag_modified.front(); E; E = E->next()) {
+ Dictionary dict = E->get();
+ Vector2i coords = E->key().get_atlas_coords();
+ Array array = dict["terrain_peering_bits"];
+ for (int i = 0; i < array.size(); i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ if (tile_set->is_valid_peering_bit_terrain(terrain_set, bit)) {
+ undo_redo->add_do_property(p_tile_set_atlas_source, vformat("%d:%d/%d/terrains_peering_bit/" + String(TileSet::CELL_NEIGHBOR_ENUM_TO_TEXT[i]), coords.x, coords.y, E->key().alternative_tile), terrain);
+ }
+ if (tile_set->is_valid_peering_bit_terrain(dict["terrain_set"], bit)) {
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/terrains_peering_bit/" + String(TileSet::CELL_NEIGHBOR_ENUM_TO_TEXT[i]), coords.x, coords.y, E->key().alternative_tile), array[i]);
+ }
+ }
+ }
+ undo_redo->commit_action(false);
+ drag_type = DRAG_TYPE_NONE;
+ } else if (drag_type == DRAG_TYPE_PAINT_TERRAIN_BITS_RECT) {
+ Dictionary painted = Dictionary(drag_painted_value);
+ int terrain_set = int(painted["terrain_set"]);
+ int terrain = int(painted["terrain"]);
+
+ Rect2i rect;
+ rect.set_position(p_tile_atlas_view->get_atlas_tile_coords_at_pos(drag_start_pos));
+ rect.set_end(p_tile_atlas_view->get_atlas_tile_coords_at_pos(mb->get_position()));
+ rect = rect.abs();
+
+ Set<TileMapCell> edited;
+ for (int x = rect.get_position().x; x <= rect.get_end().x; x++) {
+ for (int y = rect.get_position().y; y <= rect.get_end().y; y++) {
+ Vector2i coords = Vector2i(x, y);
+ coords = p_tile_set_atlas_source->get_tile_at_coords(coords);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(coords, 0));
+ if (tile_data->get_terrain_set() == terrain_set) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = 0;
+ edited.insert(cell);
+ }
+ }
+ }
+ }
+
+ Vector<Point2> mouse_pos_rect_polygon;
+ mouse_pos_rect_polygon.push_back(drag_start_pos);
+ mouse_pos_rect_polygon.push_back(Vector2(mb->get_position().x, drag_start_pos.y));
+ mouse_pos_rect_polygon.push_back(mb->get_position());
+ mouse_pos_rect_polygon.push_back(Vector2(drag_start_pos.x, mb->get_position().y));
+
+ undo_redo->create_action(TTR("Painting Terrain"));
+ for (Set<TileMapCell>::Element *E = edited.front(); E; E = E->next()) {
+ Vector2i coords = E->get().get_atlas_coords();
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(coords, 0));
+
+ for (int i = 0; i < TileSet::CELL_NEIGHBOR_MAX; i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ if (tile_set->is_valid_peering_bit_terrain(terrain_set, bit)) {
+ Rect2i texture_region = p_tile_set_atlas_source->get_tile_texture_region(coords);
+ Vector2i position = (texture_region.position + texture_region.get_end()) / 2 + p_tile_set_atlas_source->get_tile_effective_texture_offset(coords, 0);
+
+ Vector<Vector2> polygon = tile_set->get_terrain_bit_polygon(terrain_set, bit);
+ for (int j = 0; j < polygon.size(); j++) {
+ polygon.write[j] += position;
+ }
+ if (!Geometry2D::intersect_polygons(polygon, mouse_pos_rect_polygon).is_empty()) {
+ // Draw bit.
+ undo_redo->add_do_property(p_tile_set_atlas_source, vformat("%d:%d/%d/terrains_peering_bit/" + String(TileSet::CELL_NEIGHBOR_ENUM_TO_TEXT[i]), coords.x, coords.y, E->get().alternative_tile), terrain);
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/terrains_peering_bit/" + String(TileSet::CELL_NEIGHBOR_ENUM_TO_TEXT[i]), coords.x, coords.y, E->get().alternative_tile), tile_data->get_peering_bit_terrain(bit));
+ }
+ }
+ }
+ }
+ undo_redo->commit_action(true);
+ drag_type = DRAG_TYPE_NONE;
+ }
+ }
+ }
+ }
+}
+
+void TileDataTerrainsEditor::forward_painting_alternatives_gui_input(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_set_atlas_source, const Ref<InputEvent> &p_event) {
+ Ref<InputEventMouseMotion> mm = p_event;
+ if (mm.is_valid()) {
+ if (drag_type == DRAG_TYPE_PAINT_TERRAIN_SET) {
+ Vector3i tile = p_tile_atlas_view->get_alternative_tile_at_pos(mm->get_position());
+ Vector2i coords = Vector2i(tile.x, tile.y);
+ int alternative_tile = tile.z;
+
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = alternative_tile;
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(coords, alternative_tile));
+ if (!drag_modified.has(cell)) {
+ Dictionary dict;
+ dict["terrain_set"] = tile_data->get_terrain_set();
+ Array array;
+ for (int j = 0; j < TileSet::CELL_NEIGHBOR_MAX; j++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(j);
+ array.push_back(tile_data->is_valid_peering_bit_terrain(bit) ? tile_data->get_peering_bit_terrain(bit) : -1);
+ }
+ dict["terrain_peering_bits"] = array;
+ drag_modified[cell] = dict;
+ }
+ tile_data->set_terrain_set(drag_painted_value);
+ }
+
+ drag_last_pos = mm->get_position();
+ } else if (drag_type == DRAG_TYPE_PAINT_TERRAIN_BITS) {
+ Dictionary painted = Dictionary(drag_painted_value);
+ int terrain_set = int(painted["terrain_set"]);
+ int terrain = int(painted["terrain"]);
+
+ Vector3i tile = p_tile_atlas_view->get_alternative_tile_at_pos(mm->get_position());
+ Vector2i coords = Vector2i(tile.x, tile.y);
+ int alternative_tile = tile.z;
+
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = alternative_tile;
+
+ // Save the old terrain_set and terrains bits.
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(coords, alternative_tile));
+ if (tile_data->get_terrain_set() == terrain_set) {
+ if (!drag_modified.has(cell)) {
+ Dictionary dict;
+ dict["terrain_set"] = tile_data->get_terrain_set();
+ Array array;
+ for (int j = 0; j < TileSet::CELL_NEIGHBOR_MAX; j++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(j);
+ array.push_back(tile_data->is_valid_peering_bit_terrain(bit) ? tile_data->get_peering_bit_terrain(bit) : -1);
+ }
+ dict["terrain_peering_bits"] = array;
+ drag_modified[cell] = dict;
+ }
+
+ // Set the terrains bits.
+ Rect2i texture_region = p_tile_atlas_view->get_alternative_tile_rect(coords, alternative_tile);
+ Vector2i position = (texture_region.position + texture_region.get_end()) / 2 + p_tile_set_atlas_source->get_tile_effective_texture_offset(coords, alternative_tile);
+ for (int j = 0; j < TileSet::CELL_NEIGHBOR_MAX; j++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(j);
+ if (tile_data->is_valid_peering_bit_terrain(bit)) {
+ Vector<Vector2> polygon = tile_set->get_terrain_bit_polygon(tile_data->get_terrain_set(), bit);
+ if (Geometry2D::is_segment_intersecting_polygon(mm->get_position() - position, drag_last_pos - position, polygon)) {
+ tile_data->set_peering_bit_terrain(bit, terrain);
+ }
+ }
+ }
+ }
+ }
+ drag_last_pos = mm->get_position();
+ }
+ }
+
+ Ref<InputEventMouseButton> mb = p_event;
+ if (mb.is_valid()) {
+ if (mb->get_button_index() == MOUSE_BUTTON_LEFT) {
+ if (mb->is_pressed()) {
+ if (picker_button->is_pressed()) {
+ Vector3i tile = p_tile_atlas_view->get_alternative_tile_at_pos(mb->get_position());
+ Vector2i coords = Vector2i(tile.x, tile.y);
+ int alternative_tile = tile.z;
+
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(coords, alternative_tile));
+ int terrain_set = tile_data->get_terrain_set();
+ Rect2i texture_region = p_tile_atlas_view->get_alternative_tile_rect(coords, alternative_tile);
+ Vector2i position = (texture_region.position + texture_region.get_end()) / 2 + p_tile_set_atlas_source->get_tile_effective_texture_offset(coords, alternative_tile);
+ dummy_object->set("terrain_set", terrain_set);
+ dummy_object->set("terrain", -1);
+ for (int i = 0; i < TileSet::CELL_NEIGHBOR_MAX; i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ if (tile_set->is_valid_peering_bit_terrain(terrain_set, bit)) {
+ Vector<Vector2> polygon = tile_set->get_terrain_bit_polygon(terrain_set, bit);
+ if (Geometry2D::is_point_in_polygon(mb->get_position() - position, polygon)) {
+ dummy_object->set("terrain", tile_data->get_peering_bit_terrain(bit));
+ }
+ }
+ }
+ terrain_set_property_editor->update_property();
+ _update_terrain_selector();
+ picker_button->set_pressed(false);
}
+ } else {
+ int terrain_set = int(dummy_object->get("terrain_set"));
+ int terrain = int(dummy_object->get("terrain"));
+
+ Vector3i tile = p_tile_atlas_view->get_alternative_tile_at_pos(mb->get_position());
+ Vector2i coords = Vector2i(tile.x, tile.y);
+ int alternative_tile = tile.z;
- // Generate the polygon color, slightly randomly modified from the settings one.
- Color random_variation_color;
- random_variation_color.set_hsv(color.get_h() + rand.random(-1.0, 1.0) * 0.05, color.get_s(), color.get_v() + rand.random(-1.0, 1.0) * 0.1);
- random_variation_color.a = color.a;
- Vector<Color> colors;
- colors.push_back(random_variation_color);
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(coords, alternative_tile));
- RenderingServer::get_singleton()->canvas_item_add_polygon(p_canvas_item->get_canvas_item(), vertices, colors);
+ if (terrain_set == -1 || !tile_data || tile_data->get_terrain_set() != terrain_set) {
+ drag_type = DRAG_TYPE_PAINT_TERRAIN_SET;
+ drag_modified.clear();
+ drag_painted_value = int(dummy_object->get("terrain_set"));
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = alternative_tile;
+ Dictionary dict;
+ dict["terrain_set"] = tile_data->get_terrain_set();
+ Array array;
+ for (int i = 0; i < TileSet::CELL_NEIGHBOR_MAX; i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ array.push_back(tile_data->is_valid_peering_bit_terrain(bit) ? tile_data->get_peering_bit_terrain(bit) : -1);
+ }
+ dict["terrain_peering_bits"] = array;
+ drag_modified[cell] = dict;
+ tile_data->set_terrain_set(drag_painted_value);
+ }
+ drag_last_pos = mb->get_position();
+ } else if (tile_data && tile_data->get_terrain_set() == terrain_set) {
+ // Paint terrain bits.
+ drag_type = DRAG_TYPE_PAINT_TERRAIN_BITS;
+ drag_modified.clear();
+ Dictionary painted_dict;
+ painted_dict["terrain_set"] = terrain_set;
+ painted_dict["terrain"] = terrain;
+ drag_painted_value = painted_dict;
+
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ TileMapCell cell;
+ cell.source_id = 0;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = alternative_tile;
+
+ // Save the old terrain_set and terrains bits.
+ Dictionary dict;
+ dict["terrain_set"] = tile_data->get_terrain_set();
+ Array array;
+ for (int i = 0; i < TileSet::CELL_NEIGHBOR_MAX; i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ array.push_back(tile_data->is_valid_peering_bit_terrain(bit) ? tile_data->get_peering_bit_terrain(bit) : -1);
+ }
+ dict["terrain_peering_bits"] = array;
+ drag_modified[cell] = dict;
+
+ // Set the terrain bit.
+ Rect2i texture_region = p_tile_atlas_view->get_alternative_tile_rect(coords, alternative_tile);
+ Vector2i position = (texture_region.position + texture_region.get_end()) / 2 + p_tile_set_atlas_source->get_tile_effective_texture_offset(coords, alternative_tile);
+ for (int i = 0; i < TileSet::CELL_NEIGHBOR_MAX; i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ if (tile_set->is_valid_peering_bit_terrain(terrain_set, bit)) {
+ Vector<Vector2> polygon = tile_set->get_terrain_bit_polygon(terrain_set, bit);
+ if (Geometry2D::is_point_in_polygon(mb->get_position() - position, polygon)) {
+ tile_data->set_peering_bit_terrain(bit, terrain);
+ }
+ }
+ }
+ }
+ drag_last_pos = mb->get_position();
+ }
+ }
+ } else {
+ if (drag_type == DRAG_TYPE_PAINT_TERRAIN_SET) {
+ undo_redo->create_action(TTR("Painting Tiles Property"));
+ for (Map<TileMapCell, Variant>::Element *E = drag_modified.front(); E; E = E->next()) {
+ Dictionary dict = E->get();
+ Vector2i coords = E->key().get_atlas_coords();
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/terrain_set", coords.x, coords.y, E->key().alternative_tile), dict["terrain_set"]);
+ undo_redo->add_do_property(p_tile_set_atlas_source, vformat("%d:%d/%d/terrain_set", coords.x, coords.y, E->key().alternative_tile), drag_painted_value);
+ Array array = dict["terrain_peering_bits"];
+ for (int i = 0; i < array.size(); i++) {
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/terrains_peering_bit/" + String(TileSet::CELL_NEIGHBOR_ENUM_TO_TEXT[i]), coords.x, coords.y, E->key().alternative_tile), array[i]);
+ }
+ }
+ undo_redo->commit_action(false);
+ drag_type = DRAG_TYPE_NONE;
+ } else if (drag_type == DRAG_TYPE_PAINT_TERRAIN_BITS) {
+ Dictionary painted = Dictionary(drag_painted_value);
+ int terrain_set = int(painted["terrain_set"]);
+ int terrain = int(painted["terrain"]);
+ undo_redo->create_action(TTR("Painting Terrain"));
+ for (Map<TileMapCell, Variant>::Element *E = drag_modified.front(); E; E = E->next()) {
+ Dictionary dict = E->get();
+ Vector2i coords = E->key().get_atlas_coords();
+ Array array = dict["terrain_peering_bits"];
+ for (int i = 0; i < array.size(); i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ if (tile_set->is_valid_peering_bit_terrain(terrain_set, bit)) {
+ undo_redo->add_do_property(p_tile_set_atlas_source, vformat("%d:%d/%d/terrains_peering_bit/" + String(TileSet::CELL_NEIGHBOR_ENUM_TO_TEXT[i]), coords.x, coords.y, E->key().alternative_tile), terrain);
+ }
+ if (tile_set->is_valid_peering_bit_terrain(dict["terrain_set"], bit)) {
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/terrains_peering_bit/" + String(TileSet::CELL_NEIGHBOR_ENUM_TO_TEXT[i]), coords.x, coords.y, E->key().alternative_tile), array[i]);
+ }
+ }
+ }
+ undo_redo->commit_action(false);
+ drag_type = DRAG_TYPE_NONE;
}
}
+ }
+ }
+}
+
+void TileDataTerrainsEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected) {
+ TileData *tile_data = _get_tile_data(p_cell);
+ ERR_FAIL_COND(!tile_data);
- RenderingServer::get_singleton()->canvas_item_add_set_transform(p_canvas_item->get_canvas_item(), Transform2D());
+ tile_set->draw_terrains(p_canvas_item, p_transform, tile_data);
+}
+
+void TileDataTerrainsEditor::_notification(int p_what) {
+ switch (p_what) {
+ case NOTIFICATION_ENTER_TREE:
+ case NOTIFICATION_THEME_CHANGED:
+ picker_button->set_icon(get_theme_icon("ColorPick", "EditorIcons"));
+ break;
+ default:
+ break;
+ }
+}
+
+TileDataTerrainsEditor::TileDataTerrainsEditor() {
+ label = memnew(Label);
+ label->set_text("Painting:");
+ add_child(label);
+
+ // Toolbar
+ toolbar->add_child(memnew(VSeparator));
+
+ picker_button = memnew(Button);
+ picker_button->set_flat(true);
+ picker_button->set_toggle_mode(true);
+ picker_button->set_shortcut(ED_SHORTCUT("tiles_editor/picker", "Picker", KEY_P));
+ toolbar->add_child(picker_button);
+
+ // Setup
+ dummy_object->add_dummy_property("terrain_set");
+ dummy_object->set("terrain_set", -1);
+ dummy_object->add_dummy_property("terrain");
+ dummy_object->set("terrain", -1);
+
+ // Get the default value for the type.
+ terrain_set_property_editor = memnew(EditorPropertyEnum);
+ terrain_set_property_editor->set_object_and_property(dummy_object, "terrain_set");
+ terrain_set_property_editor->set_label("Terrain Set");
+ terrain_set_property_editor->connect("property_changed", callable_mp(this, &TileDataTerrainsEditor::_property_value_changed).unbind(1));
+ add_child(terrain_set_property_editor);
+
+ terrain_property_editor = memnew(EditorPropertyEnum);
+ terrain_property_editor->set_object_and_property(dummy_object, "terrain");
+ terrain_property_editor->set_label("Terrain");
+ terrain_property_editor->connect("property_changed", callable_mp(this, &TileDataTerrainsEditor::_property_value_changed).unbind(1));
+ add_child(terrain_property_editor);
+}
+
+TileDataTerrainsEditor::~TileDataTerrainsEditor() {
+ toolbar->queue_delete();
+ memdelete(dummy_object);
+}
+
+Variant TileDataNavigationEditor::_get_painted_value() {
+ Ref<NavigationPolygon> navigation_polygon;
+ navigation_polygon.instantiate();
+
+ for (int i = 0; i < polygon_editor->get_polygon_count(); i++) {
+ Vector<Vector2> polygon = polygon_editor->get_polygon(i);
+ navigation_polygon->add_outline(polygon);
+ }
+
+ navigation_polygon->make_polygons_from_outlines();
+ return navigation_polygon;
+}
+
+void TileDataNavigationEditor::_set_painted_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(p_coords, p_alternative_tile));
+ ERR_FAIL_COND(!tile_data);
+
+ Ref<NavigationPolygon> navigation_polygon = tile_data->get_navigation_polygon(navigation_layer);
+ polygon_editor->clear_polygons();
+ if (navigation_polygon.is_valid()) {
+ for (int i = 0; i < navigation_polygon->get_outline_count(); i++) {
+ polygon_editor->add_polygon(navigation_polygon->get_outline(i));
+ }
+ }
+ polygon_editor->set_background(p_tile_set_atlas_source->get_texture(), p_tile_set_atlas_source->get_tile_texture_region(p_coords), p_tile_set_atlas_source->get_tile_effective_texture_offset(p_coords, p_alternative_tile), tile_data->get_flip_h(), tile_data->get_flip_v(), tile_data->get_transpose(), tile_data->get_modulate());
+}
+
+void TileDataNavigationEditor::_set_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile, Variant p_value) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(p_coords, p_alternative_tile));
+ ERR_FAIL_COND(!tile_data);
+ Ref<NavigationPolygon> navigation_polygon = p_value;
+ tile_data->set_navigation_polygon(navigation_layer, navigation_polygon);
+
+ polygon_editor->set_background(p_tile_set_atlas_source->get_texture(), p_tile_set_atlas_source->get_tile_texture_region(p_coords), p_tile_set_atlas_source->get_tile_effective_texture_offset(p_coords, p_alternative_tile), tile_data->get_flip_h(), tile_data->get_flip_v(), tile_data->get_transpose(), tile_data->get_modulate());
+}
+
+Variant TileDataNavigationEditor::_get_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile) {
+ TileData *tile_data = Object::cast_to<TileData>(p_tile_set_atlas_source->get_tile_data(p_coords, p_alternative_tile));
+ ERR_FAIL_COND_V(!tile_data, Variant());
+ return tile_data->get_navigation_polygon(navigation_layer);
+}
+
+void TileDataNavigationEditor::_setup_undo_redo_action(TileSetAtlasSource *p_tile_set_atlas_source, Map<TileMapCell, Variant> p_previous_values, Variant p_new_value) {
+ for (Map<TileMapCell, Variant>::Element *E = p_previous_values.front(); E; E = E->next()) {
+ Vector2i coords = E->key().get_atlas_coords();
+ undo_redo->add_undo_property(p_tile_set_atlas_source, vformat("%d:%d/%d/navigation_layer_%d/polygon", coords.x, coords.y, E->key().alternative_tile, navigation_layer), E->get());
+ undo_redo->add_do_property(p_tile_set_atlas_source, vformat("%d:%d/%d/navigation_layer_%d/polygon", coords.x, coords.y, E->key().alternative_tile, navigation_layer), p_new_value);
+ }
+}
+
+void TileDataNavigationEditor::_tile_set_changed() {
+ polygon_editor->set_tile_set(tile_set);
+}
+
+void TileDataNavigationEditor::_notification(int p_what) {
+ switch (p_what) {
+ case NOTIFICATION_ENTER_TREE:
+ polygon_editor->set_polygons_color(get_tree()->get_debug_navigation_color());
+ break;
+ default:
+ break;
+ }
+}
+
+TileDataNavigationEditor::TileDataNavigationEditor() {
+ polygon_editor = memnew(GenericTilePolygonEditor);
+ polygon_editor->set_multiple_polygon_mode(true);
+ add_child(polygon_editor);
+}
+
+void TileDataNavigationEditor::draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected) {
+ TileData *tile_data = _get_tile_data(p_cell);
+ ERR_FAIL_COND(!tile_data);
+
+ // Draw all shapes.
+ RenderingServer::get_singleton()->canvas_item_add_set_transform(p_canvas_item->get_canvas_item(), p_transform);
+
+ Ref<NavigationPolygon> navigation_polygon = tile_data->get_navigation_polygon(navigation_layer);
+ if (navigation_polygon.is_valid()) {
+ Vector<Vector2> verts = navigation_polygon->get_vertices();
+ if (verts.size() < 3) {
+ return;
+ }
+
+ Color color = p_canvas_item->get_tree()->get_debug_navigation_color();
+ if (p_selected) {
+ Color grid_color = EditorSettings::get_singleton()->get("editors/tiles_editor/grid_color");
+ Color selection_color = Color().from_hsv(Math::fposmod(grid_color.get_h() + 0.5, 1.0), grid_color.get_s(), grid_color.get_v(), 1.0);
+ selection_color.a = 0.7;
+ color = selection_color;
+ }
+
+ RandomPCG rand;
+ for (int i = 0; i < navigation_polygon->get_polygon_count(); i++) {
+ // An array of vertices for this polygon.
+ Vector<int> polygon = navigation_polygon->get_polygon(i);
+ Vector<Vector2> vertices;
+ vertices.resize(polygon.size());
+ for (int j = 0; j < polygon.size(); j++) {
+ ERR_FAIL_INDEX(polygon[j], verts.size());
+ vertices.write[j] = verts[polygon[j]];
+ }
+
+ // Generate the polygon color, slightly randomly modified from the settings one.
+ Color random_variation_color;
+ random_variation_color.set_hsv(color.get_h() + rand.random(-1.0, 1.0) * 0.05, color.get_s(), color.get_v() + rand.random(-1.0, 1.0) * 0.1);
+ random_variation_color.a = color.a;
+ Vector<Color> colors;
+ colors.push_back(random_variation_color);
+
+ RenderingServer::get_singleton()->canvas_item_add_polygon(p_canvas_item->get_canvas_item(), vertices, colors);
}
}
+
+ RenderingServer::get_singleton()->canvas_item_add_set_transform(p_canvas_item->get_canvas_item(), Transform2D());
}
diff --git a/editor/plugins/tiles/tile_data_editors.h b/editor/plugins/tiles/tile_data_editors.h
index b82189e1ee..781f26cc02 100644
--- a/editor/plugins/tiles/tile_data_editors.h
+++ b/editor/plugins/tiles/tile_data_editors.h
@@ -31,87 +31,378 @@
#ifndef TILE_DATA_EDITORS_H
#define TILE_DATA_EDITORS_H
+#include "tile_atlas_view.h"
+
+#include "editor/editor_node.h"
+#include "editor/editor_properties.h"
+
+#include "scene/gui/box_container.h"
#include "scene/gui/control.h"
+#include "scene/gui/label.h"
#include "scene/resources/tile_set.h"
-class TileDataEditor : public Control {
- GDCLASS(TileDataEditor, Control);
+class TileDataEditor : public VBoxContainer {
+ GDCLASS(TileDataEditor, VBoxContainer);
+
+private:
+ void _call_tile_set_changed();
protected:
- TileData *tile_data;
- String property;
+ Ref<TileSet> tile_set;
+ TileData *_get_tile_data(TileMapCell p_cell);
+ virtual void _tile_set_changed(){};
- TileData *_get_tile_data(TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile);
+ static void _bind_methods();
public:
- // Edits a TileData property.
- void edit(TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property);
+ void set_tile_set(Ref<TileSet> p_tile_set);
+
+ // Input to handle painting.
+ virtual Control *get_toolbar() { return nullptr; };
+ virtual void forward_draw_over_atlas(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_atlas_source, CanvasItem *p_canvas_item, Transform2D p_transform){};
+ virtual void forward_draw_over_alternatives(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_atlas_source, CanvasItem *p_canvas_item, Transform2D p_transform){};
+ virtual void forward_painting_atlas_gui_input(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_atlas_source, const Ref<InputEvent> &p_event){};
+ virtual void forward_painting_alternatives_gui_input(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_atlas_source, const Ref<InputEvent> &p_event){};
- // Used to draw the value over a tile.
- virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property){};
+ // Used to draw the tile data property value over a tile.
+ virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected = false){};
};
-class TileDataTextureOffsetEditor : public TileDataEditor {
- GDCLASS(TileDataTextureOffsetEditor, TileDataEditor);
+class DummyObject : public Object {
+ GDCLASS(DummyObject, Object)
+private:
+ Map<String, Variant> properties;
+
+protected:
+ bool _set(const StringName &p_name, const Variant &p_value);
+ bool _get(const StringName &p_name, Variant &r_ret) const;
public:
- virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) override;
+ bool has_dummy_property(StringName p_name);
+ void add_dummy_property(StringName p_name);
+ void remove_dummy_property(StringName p_name);
+ void clear_dummy_properties();
};
-class TileDataIntegerEditor : public TileDataEditor {
- GDCLASS(TileDataIntegerEditor, TileDataEditor);
+class GenericTilePolygonEditor : public VBoxContainer {
+ GDCLASS(GenericTilePolygonEditor, VBoxContainer);
+
+private:
+ Ref<TileSet> tile_set;
+ LocalVector<Vector<Point2>> polygons;
+ bool multiple_polygon_mode = false;
+
+ UndoRedo *undo_redo = EditorNode::get_undo_redo();
+
+ // UI
+ int hovered_polygon_index = -1;
+ int hovered_point_index = -1;
+ int hovered_segment_index = -1;
+ Vector2 hovered_segment_point;
+
+ enum DragType {
+ DRAG_TYPE_NONE,
+ DRAG_TYPE_DRAG_POINT,
+ DRAG_TYPE_CREATE_POINT,
+ DRAG_TYPE_PAN,
+ };
+ DragType drag_type;
+ int drag_polygon_index;
+ int drag_point_index;
+ Vector2 drag_last_pos;
+ PackedVector2Array drag_old_polygon;
+
+ HBoxContainer *toolbar;
+ Ref<ButtonGroup> tools_button_group;
+ Button *button_create;
+ Button *button_edit;
+ Button *button_delete;
+ Button *button_pixel_snap;
+ MenuButton *button_advanced_menu;
+
+ Vector<Point2> in_creation_polygon;
+
+ Panel *panel;
+ Control *base_control;
+ EditorZoomWidget *editor_zoom_widget;
+ Button *button_center_view;
+ Vector2 panning;
+
+ Ref<Texture2D> background_texture;
+ Rect2 background_region;
+ Vector2 background_offset;
+ bool background_h_flip;
+ bool background_v_flip;
+ bool background_transpose;
+ Color background_modulate;
+
+ Color polygon_color = Color(1.0, 0.0, 0.0);
+
+ enum AdvancedMenuOption {
+ RESET_TO_DEFAULT_TILE,
+ CLEAR_TILE,
+ };
+
+ void _base_control_draw();
+ void _zoom_changed();
+ void _advanced_menu_item_pressed(int p_item_pressed);
+ void _center_view();
+ void _base_control_gui_input(Ref<InputEvent> p_event);
+
+ void _snap_to_tile_shape(Point2 &r_point, float &r_current_snapped_dist, float p_snap_dist);
+ void _snap_to_half_pixel(Point2 &r_point);
+ void _grab_polygon_point(Vector2 p_pos, const Transform2D &p_polygon_xform, int &r_polygon_index, int &r_point_index);
+ void _grab_polygon_segment_point(Vector2 p_pos, const Transform2D &p_polygon_xform, int &r_polygon_index, int &r_segment_index, Vector2 &r_point);
+
+protected:
+ void _notification(int p_what);
+ static void _bind_methods();
public:
- virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) override;
+ void set_tile_set(Ref<TileSet> p_tile_set);
+ void set_background(Ref<Texture2D> p_texture, Rect2 p_region = Rect2(), Vector2 p_offset = Vector2(), bool p_flip_h = false, bool p_flip_v = false, bool p_transpose = false, Color p_modulate = Color(1.0, 1.0, 1.0, 0.0));
+
+ int get_polygon_count();
+ int add_polygon(Vector<Point2> p_polygon, int p_index = -1);
+ void remove_polygon(int p_index);
+ void clear_polygons();
+ void set_polygon(int p_polygon_index, Vector<Point2> p_polygon);
+ Vector<Point2> get_polygon(int p_polygon_index);
+
+ void set_polygons_color(Color p_color);
+ void set_multiple_polygon_mode(bool p_multiple_polygon_mode);
+
+ GenericTilePolygonEditor();
};
-class TileDataFloatEditor : public TileDataEditor {
- GDCLASS(TileDataFloatEditor, TileDataEditor);
+class TileDataDefaultEditor : public TileDataEditor {
+ GDCLASS(TileDataDefaultEditor, TileDataEditor);
+
+private:
+ // Toolbar
+ HBoxContainer *toolbar = memnew(HBoxContainer);
+ Button *picker_button;
+
+ // UI
+ Ref<Texture2D> tile_bool_checked;
+ Ref<Texture2D> tile_bool_unchecked;
+ Label *label;
+
+ EditorProperty *property_editor = nullptr;
+
+ // Painting state.
+ enum DragType {
+ DRAG_TYPE_NONE = 0,
+ DRAG_TYPE_PAINT,
+ DRAG_TYPE_PAINT_RECT,
+ };
+ DragType drag_type = DRAG_TYPE_NONE;
+ Vector2 drag_start_pos;
+ Vector2 drag_last_pos;
+ Map<TileMapCell, Variant> drag_modified;
+ Variant drag_painted_value;
+
+ void _property_value_changed(StringName p_property, Variant p_value, StringName p_field);
+
+protected:
+ DummyObject *dummy_object = memnew(DummyObject);
+
+ UndoRedo *undo_redo = EditorNode::get_undo_redo();
+
+ StringName type;
+ String property;
+ void _notification(int p_what);
+
+ virtual Variant _get_painted_value();
+ virtual void _set_painted_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile);
+ virtual void _set_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile, Variant p_value);
+ virtual Variant _get_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile);
+ virtual void _setup_undo_redo_action(TileSetAtlasSource *p_tile_set_atlas_source, Map<TileMapCell, Variant> p_previous_values, Variant p_new_value);
public:
- virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) override;
+ virtual Control *get_toolbar() override { return toolbar; };
+ virtual void forward_draw_over_atlas(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_atlas_source, CanvasItem *p_canvas_item, Transform2D p_transform) override;
+ virtual void forward_draw_over_alternatives(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_atlas_source, CanvasItem *p_canvas_item, Transform2D p_transform) override;
+ virtual void forward_painting_atlas_gui_input(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_atlas_source, const Ref<InputEvent> &p_event) override;
+ virtual void forward_painting_alternatives_gui_input(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_atlas_source, const Ref<InputEvent> &p_event) override;
+ virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected = false) override;
+
+ void setup_property_editor(Variant::Type p_type, String p_property, String p_label = "", Variant p_default_value = Variant());
+
+ TileDataDefaultEditor();
+ ~TileDataDefaultEditor();
};
-class TileDataPositionEditor : public TileDataEditor {
- GDCLASS(TileDataPositionEditor, TileDataEditor);
+class TileDataTextureOffsetEditor : public TileDataDefaultEditor {
+ GDCLASS(TileDataTextureOffsetEditor, TileDataDefaultEditor);
public:
- virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) override;
+ virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected = false) override;
};
-class TileDataYSortEditor : public TileDataEditor {
- GDCLASS(TileDataYSortEditor, TileDataEditor);
+class TileDataPositionEditor : public TileDataDefaultEditor {
+ GDCLASS(TileDataPositionEditor, TileDataDefaultEditor);
public:
- virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) override;
+ virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected = false) override;
};
-class TileDataOcclusionShapeEditor : public TileDataEditor {
- GDCLASS(TileDataOcclusionShapeEditor, TileDataEditor);
+class TileDataYSortEditor : public TileDataDefaultEditor {
+ GDCLASS(TileDataYSortEditor, TileDataDefaultEditor);
public:
- virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) override;
+ virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected = false) override;
};
-class TileDataCollisionShapeEditor : public TileDataEditor {
- GDCLASS(TileDataCollisionShapeEditor, TileDataEditor);
+class TileDataOcclusionShapeEditor : public TileDataDefaultEditor {
+ GDCLASS(TileDataOcclusionShapeEditor, TileDataDefaultEditor);
+
+private:
+ int occlusion_layer = -1;
+
+ // UI
+ GenericTilePolygonEditor *polygon_editor;
+
+ void _polygon_changed(PackedVector2Array p_polygon);
+
+ virtual Variant _get_painted_value() override;
+ virtual void _set_painted_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile) override;
+ virtual void _set_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile, Variant p_value) override;
+ virtual Variant _get_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile) override;
+ virtual void _setup_undo_redo_action(TileSetAtlasSource *p_tile_set_atlas_source, Map<TileMapCell, Variant> p_previous_values, Variant p_new_value) override;
+
+protected:
+ UndoRedo *undo_redo = EditorNode::get_undo_redo();
+
+ virtual void _tile_set_changed() override;
+
+ void _notification(int p_what);
+
+public:
+ virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected = false) override;
+
+ void set_occlusion_layer(int p_occlusion_layer) { occlusion_layer = p_occlusion_layer; }
+
+ TileDataOcclusionShapeEditor();
+};
+
+class TileDataCollisionEditor : public TileDataDefaultEditor {
+ GDCLASS(TileDataCollisionEditor, TileDataDefaultEditor);
+
+ int physics_layer = -1;
+
+ // UI
+ GenericTilePolygonEditor *polygon_editor;
+ DummyObject *dummy_object = memnew(DummyObject);
+ Map<StringName, EditorProperty *> property_editors;
+
+ void _property_value_changed(StringName p_property, Variant p_value, StringName p_field);
+ void _polygons_changed();
+
+ virtual Variant _get_painted_value() override;
+ virtual void _set_painted_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile) override;
+ virtual void _set_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile, Variant p_value) override;
+ virtual Variant _get_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile) override;
+ virtual void _setup_undo_redo_action(TileSetAtlasSource *p_tile_set_atlas_source, Map<TileMapCell, Variant> p_previous_values, Variant p_new_value) override;
+
+protected:
+ UndoRedo *undo_redo = EditorNode::get_undo_redo();
+
+ virtual void _tile_set_changed() override;
+
+ void _notification(int p_what);
public:
- virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) override;
+ virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected = false) override;
+
+ void set_physics_layer(int p_physics_layer) { physics_layer = p_physics_layer; }
+
+ TileDataCollisionEditor();
+ ~TileDataCollisionEditor();
};
class TileDataTerrainsEditor : public TileDataEditor {
GDCLASS(TileDataTerrainsEditor, TileDataEditor);
+private:
+ // Toolbar
+ HBoxContainer *toolbar = memnew(HBoxContainer);
+ Button *picker_button;
+
+ // Painting state.
+ enum DragType {
+ DRAG_TYPE_NONE = 0,
+ DRAG_TYPE_PAINT_TERRAIN_SET,
+ DRAG_TYPE_PAINT_TERRAIN_SET_RECT,
+ DRAG_TYPE_PAINT_TERRAIN_BITS,
+ DRAG_TYPE_PAINT_TERRAIN_BITS_RECT,
+ };
+ DragType drag_type = DRAG_TYPE_NONE;
+ Vector2 drag_start_pos;
+ Vector2 drag_last_pos;
+ Map<TileMapCell, Variant> drag_modified;
+ Variant drag_painted_value;
+
+ // UI
+ Label *label;
+ DummyObject *dummy_object = memnew(DummyObject);
+ EditorPropertyEnum *terrain_set_property_editor = nullptr;
+ EditorPropertyEnum *terrain_property_editor = nullptr;
+
+ void _property_value_changed(StringName p_property, Variant p_value, StringName p_field);
+
+ void _update_terrain_selector();
+
+protected:
+ virtual void _tile_set_changed() override;
+
+ void _notification(int p_what);
+
+ UndoRedo *undo_redo = EditorNode::get_undo_redo();
+
public:
- virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) override;
+ virtual Control *get_toolbar() override { return toolbar; };
+ virtual void forward_draw_over_atlas(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_atlas_source, CanvasItem *p_canvas_item, Transform2D p_transform) override;
+ virtual void forward_draw_over_alternatives(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_atlas_source, CanvasItem *p_canvas_item, Transform2D p_transform) override;
+ virtual void forward_painting_atlas_gui_input(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_atlas_source, const Ref<InputEvent> &p_event) override;
+ virtual void forward_painting_alternatives_gui_input(TileAtlasView *p_tile_atlas_view, TileSetAtlasSource *p_tile_atlas_source, const Ref<InputEvent> &p_event) override;
+ virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected = false) override;
+
+ TileDataTerrainsEditor();
+ ~TileDataTerrainsEditor();
};
-class TileDataNavigationPolygonEditor : public TileDataEditor {
- GDCLASS(TileDataNavigationPolygonEditor, TileDataEditor);
+class TileDataNavigationEditor : public TileDataDefaultEditor {
+ GDCLASS(TileDataNavigationEditor, TileDataDefaultEditor);
+
+private:
+ int navigation_layer = -1;
+ PackedVector2Array navigation_polygon;
+
+ // UI
+ GenericTilePolygonEditor *polygon_editor;
+
+ void _polygon_changed(PackedVector2Array p_polygon);
+
+ virtual Variant _get_painted_value() override;
+ virtual void _set_painted_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile) override;
+ virtual void _set_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile, Variant p_value) override;
+ virtual Variant _get_value(TileSetAtlasSource *p_tile_set_atlas_source, Vector2 p_coords, int p_alternative_tile) override;
+ virtual void _setup_undo_redo_action(TileSetAtlasSource *p_tile_set_atlas_source, Map<TileMapCell, Variant> p_previous_values, Variant p_new_value) override;
+
+protected:
+ UndoRedo *undo_redo = EditorNode::get_undo_redo();
+
+ virtual void _tile_set_changed() override;
+
+ void _notification(int p_what);
public:
- virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileSet *p_tile_set, int p_atlas_source_id, Vector2i p_atlas_coords, int p_alternative_tile, String p_property) override;
+ virtual void draw_over_tile(CanvasItem *p_canvas_item, Transform2D p_transform, TileMapCell p_cell, bool p_selected = false) override;
+
+ void set_navigation_layer(int p_navigation_layer) { navigation_layer = p_navigation_layer; }
+
+ TileDataNavigationEditor();
};
#endif // TILE_DATA_EDITORS_H
diff --git a/editor/plugins/tiles/tile_map_editor.cpp b/editor/plugins/tiles/tile_map_editor.cpp
index ef13d8ea12..86bd115ac2 100644
--- a/editor/plugins/tiles/tile_map_editor.cpp
+++ b/editor/plugins/tiles/tile_map_editor.cpp
@@ -1756,7 +1756,7 @@ TileMapEditorTilesPlugin::TileMapEditorTilesPlugin() {
HBoxContainer *tilemap_tiles_tools_buttons = memnew(HBoxContainer);
- tool_buttons_group.instance();
+ tool_buttons_group.instantiate();
select_tool_button = memnew(Button);
select_tool_button->set_flat(true);
@@ -2989,6 +2989,7 @@ void TileMapEditorTerrainsPlugin::_update_terrains_tree() {
}
// Fill in the terrain list.
+ Vector<Vector<Ref<Texture2D>>> icons = tile_set->generate_terrains_icons(Size2(16, 16) * EDSCALE);
for (int terrain_set_index = 0; terrain_set_index < tile_set->get_terrain_sets_count(); terrain_set_index++) {
// Add an item for the terrain set.
TreeItem *terrain_set_tree_item = terrains_tree->create_item();
@@ -3007,58 +3008,12 @@ void TileMapEditorTerrainsPlugin::_update_terrains_tree() {
terrain_set_tree_item->set_selectable(0, false);
for (int terrain_index = 0; terrain_index < tile_set->get_terrains_count(terrain_set_index); terrain_index++) {
- // Compute the terrains_tile_pattern used for terrain preview (whenever possible).
- TerrainsTilePattern terrains_tile_pattern;
- int max_bit_count = -1;
- for (Set<TerrainsTilePattern>::Element *E = per_terrain_terrains_tile_patterns[terrain_set_index][terrain_index].front(); E; E = E->next()) {
- int count = 0;
- for (int i = 0; i < E->get().size(); i++) {
- if (int(E->get()[i]) == terrain_index) {
- count++;
- }
- }
- if (count > max_bit_count) {
- terrains_tile_pattern = E->get();
- max_bit_count = count;
- }
- }
-
- // Get the preview.
- Ref<Texture2D> icon;
- Rect2 region;
- if (max_bit_count >= 0) {
- double max_probability = -1.0;
- for (Set<TileMapCell>::Element *E = per_terrain_terrains_tile_patterns_tiles[terrain_set_index][terrains_tile_pattern].front(); E; E = E->next()) {
- Ref<TileSetSource> source = tile_set->get_source(E->get().source_id);
-
- Ref<TileSetAtlasSource> atlas_source = source;
- if (atlas_source.is_valid()) {
- TileData *tile_data = Object::cast_to<TileData>(atlas_source->get_tile_data(E->get().get_atlas_coords(), E->get().alternative_tile));
- if (tile_data->get_probability() > max_probability) {
- icon = atlas_source->get_texture();
- region = atlas_source->get_tile_texture_region(E->get().get_atlas_coords());
- max_probability = tile_data->get_probability();
- }
- }
- }
- } else {
- Ref<Image> image;
- image.instance();
- image->create(1, 1, false, Image::FORMAT_RGBA8);
- image->set_pixel(0, 0, tile_set->get_terrain_color(terrain_set_index, terrain_index));
- Ref<ImageTexture> image_texture;
- image_texture.instance();
- image_texture->create_from_image(image);
- image_texture->set_size_override(Size2(32, 32) * EDSCALE);
- icon = image_texture;
- }
-
// Add the item to the terrain list.
TreeItem *terrain_tree_item = terrains_tree->create_item(terrain_set_tree_item);
terrain_tree_item->set_text(0, tile_set->get_terrain_name(terrain_set_index, terrain_index));
terrain_tree_item->set_icon_max_width(0, 32 * EDSCALE);
- terrain_tree_item->set_icon(0, icon);
- terrain_tree_item->set_icon_region(0, region);
+ terrain_tree_item->set_icon(0, icons[terrain_set_index][terrain_index]);
+
Dictionary metadata_dict;
metadata_dict["terrain_set"] = terrain_set_index;
metadata_dict["terrain_id"] = terrain_index;
@@ -3188,7 +3143,7 @@ TileMapEditorTerrainsPlugin::TileMapEditorTerrainsPlugin() {
HBoxContainer *tilemap_tiles_tools_buttons = memnew(HBoxContainer);
- tool_buttons_group.instance();
+ tool_buttons_group.instantiate();
paint_tool_button = memnew(Button);
paint_tool_button->set_flat(true);
diff --git a/editor/plugins/tiles/tile_set_atlas_source_editor.cpp b/editor/plugins/tiles/tile_set_atlas_source_editor.cpp
index eb52aff318..9d849a0df5 100644
--- a/editor/plugins/tiles/tile_set_atlas_source_editor.cpp
+++ b/editor/plugins/tiles/tile_set_atlas_source_editor.cpp
@@ -357,6 +357,7 @@ void TileSetAtlasSourceEditor::AtlasTileProxyObject::_bind_methods() {
void TileSetAtlasSourceEditor::_inspector_property_selected(String p_property) {
selected_property = p_property;
_update_atlas_view();
+ _update_current_tile_data_editor();
}
void TileSetAtlasSourceEditor::_update_tile_id_label() {
@@ -398,17 +399,315 @@ void TileSetAtlasSourceEditor::_update_fix_selected_and_hovered_tiles() {
}
}
+void TileSetAtlasSourceEditor::_update_atlas_source_inspector() {
+ // Update visibility.
+ bool visible = tools_button_group->get_pressed_button() == tool_setup_atlas_source_button;
+ atlas_source_inspector_label->set_visible(visible);
+ atlas_source_inspector->set_visible(visible);
+}
+
void TileSetAtlasSourceEditor::_update_tile_inspector() {
- bool has_atlas_tile_selected = (tools_button_group->get_pressed_button() == tool_select_button) && !selection.is_empty();
+ // Update visibility.
+ if (tools_button_group->get_pressed_button() == tool_select_button) {
+ if (!selection.is_empty()) {
+ tile_proxy_object->edit(tile_set_atlas_source, selection);
+ }
+ tile_inspector_label->show();
+ tile_inspector->set_visible(!selection.is_empty());
+ tile_inspector_no_tile_selected_label->set_visible(selection.is_empty());
+ } else {
+ tile_inspector_label->hide();
+ tile_inspector->hide();
+ tile_inspector_no_tile_selected_label->hide();
+ }
+}
- // Update the proxy object.
- if (has_atlas_tile_selected) {
- tile_proxy_object->edit(tile_set_atlas_source, selection);
+void TileSetAtlasSourceEditor::_update_tile_data_editors() {
+ String previously_selected;
+ if (tile_data_editors_tree && tile_data_editors_tree->get_selected()) {
+ previously_selected = tile_data_editors_tree->get_selected()->get_metadata(0);
+ }
+
+ tile_data_editors_tree->clear();
+
+ TreeItem *root = tile_data_editors_tree->create_item();
+
+ TreeItem *group;
+#define ADD_TILE_DATA_EDITOR_GROUP(text) \
+ group = tile_data_editors_tree->create_item(root); \
+ group->set_custom_bg_color(0, group_color); \
+ group->set_selectable(0, false); \
+ group->set_disable_folding(true); \
+ group->set_text(0, text);
+
+ TreeItem *item;
+#define ADD_TILE_DATA_EDITOR(parent, text, property) \
+ item = tile_data_editors_tree->create_item(parent); \
+ item->set_text(0, text); \
+ item->set_metadata(0, property); \
+ if (property == previously_selected) { \
+ item->select(0); \
+ }
+
+ // Theming.
+ tile_data_editors_tree->add_theme_constant_override("vseparation", 1);
+ tile_data_editors_tree->add_theme_constant_override("hseparation", 3);
+
+ Color group_color = get_theme_color("prop_category", "Editor");
+
+ // List of editors.
+ // --- Rendering ---
+ ADD_TILE_DATA_EDITOR_GROUP("Rendering");
+
+ ADD_TILE_DATA_EDITOR(group, "Texture Offset", "texture_offset");
+ if (!tile_data_editors.has("texture_offset")) {
+ TileDataTextureOffsetEditor *tile_data_texture_offset_editor = memnew(TileDataTextureOffsetEditor);
+ tile_data_texture_offset_editor->hide();
+ tile_data_texture_offset_editor->setup_property_editor(Variant::VECTOR2, "texture_offset");
+ tile_data_texture_offset_editor->connect("needs_redraw", callable_mp((CanvasItem *)tile_atlas_control_unscaled, &Control::update));
+ tile_data_texture_offset_editor->connect("needs_redraw", callable_mp((CanvasItem *)alternative_tiles_control_unscaled, &Control::update));
+ tile_data_editors["texture_offset"] = tile_data_texture_offset_editor;
+ }
+
+ ADD_TILE_DATA_EDITOR(group, "Modulate", "modulate");
+ if (!tile_data_editors.has("modulate")) {
+ TileDataDefaultEditor *tile_data_modulate_editor = memnew(TileDataDefaultEditor());
+ tile_data_modulate_editor->hide();
+ tile_data_modulate_editor->setup_property_editor(Variant::COLOR, "modulate", "", Color(1.0, 1.0, 1.0, 1.0));
+ tile_data_modulate_editor->connect("needs_redraw", callable_mp((CanvasItem *)tile_atlas_control_unscaled, &Control::update));
+ tile_data_modulate_editor->connect("needs_redraw", callable_mp((CanvasItem *)alternative_tiles_control_unscaled, &Control::update));
+ tile_data_editors["modulate"] = tile_data_modulate_editor;
+ }
+
+ ADD_TILE_DATA_EDITOR(group, "Z Index", "z_index");
+ if (!tile_data_editors.has("z_index")) {
+ TileDataDefaultEditor *tile_data_z_index_editor = memnew(TileDataDefaultEditor());
+ tile_data_z_index_editor->hide();
+ tile_data_z_index_editor->setup_property_editor(Variant::INT, "z_index");
+ tile_data_z_index_editor->connect("needs_redraw", callable_mp((CanvasItem *)tile_atlas_control_unscaled, &Control::update));
+ tile_data_z_index_editor->connect("needs_redraw", callable_mp((CanvasItem *)alternative_tiles_control_unscaled, &Control::update));
+ tile_data_editors["z_index"] = tile_data_z_index_editor;
+ }
+
+ ADD_TILE_DATA_EDITOR(group, "Y Sort Origin", "y_sort_origin");
+ if (!tile_data_editors.has("y_sort_origin")) {
+ TileDataYSortEditor *tile_data_y_sort_editor = memnew(TileDataYSortEditor);
+ tile_data_y_sort_editor->hide();
+ tile_data_y_sort_editor->setup_property_editor(Variant::INT, "y_sort_origin");
+ tile_data_y_sort_editor->connect("needs_redraw", callable_mp((CanvasItem *)tile_atlas_control_unscaled, &Control::update));
+ tile_data_y_sort_editor->connect("needs_redraw", callable_mp((CanvasItem *)alternative_tiles_control_unscaled, &Control::update));
+ tile_data_editors["y_sort_origin"] = tile_data_y_sort_editor;
+ }
+
+ for (int i = 0; i < tile_set->get_occlusion_layers_count(); i++) {
+ ADD_TILE_DATA_EDITOR(group, vformat("Occlusion Layer %d", i), vformat("occlusion_layer_%d", i));
+ if (!tile_data_editors.has(vformat("occlusion_layer_%d", i))) {
+ TileDataOcclusionShapeEditor *tile_data_occlusion_shape_editor = memnew(TileDataOcclusionShapeEditor());
+ tile_data_occlusion_shape_editor->hide();
+ tile_data_occlusion_shape_editor->set_occlusion_layer(i);
+ tile_data_occlusion_shape_editor->connect("needs_redraw", callable_mp((CanvasItem *)tile_atlas_control_unscaled, &Control::update));
+ tile_data_occlusion_shape_editor->connect("needs_redraw", callable_mp((CanvasItem *)alternative_tiles_control_unscaled, &Control::update));
+ tile_data_editors[vformat("occlusion_layer_%d", i)] = tile_data_occlusion_shape_editor;
+ }
+ }
+ for (int i = tile_set->get_occlusion_layers_count(); tile_data_editors.has(vformat("occlusion_layer_%d", i)); i++) {
+ tile_data_editors[vformat("occlusion_layer_%d", i)]->queue_delete();
+ tile_data_editors.erase(vformat("occlusion_layer_%d", i));
+ }
+
+ // --- Rendering ---
+ ADD_TILE_DATA_EDITOR(root, "Terrains", "terrain_set");
+ if (!tile_data_editors.has("terrain_set")) {
+ TileDataTerrainsEditor *tile_data_terrains_editor = memnew(TileDataTerrainsEditor);
+ tile_data_terrains_editor->hide();
+ tile_data_terrains_editor->connect("needs_redraw", callable_mp((CanvasItem *)tile_atlas_control_unscaled, &Control::update));
+ tile_data_terrains_editor->connect("needs_redraw", callable_mp((CanvasItem *)alternative_tiles_control_unscaled, &Control::update));
+ tile_data_editors["terrain_set"] = tile_data_terrains_editor;
+ }
+
+ // --- Miscellaneous ---
+ ADD_TILE_DATA_EDITOR(root, "Probability", "probability");
+ if (!tile_data_editors.has("probability")) {
+ TileDataDefaultEditor *tile_data_probability_editor = memnew(TileDataDefaultEditor());
+ tile_data_probability_editor->hide();
+ tile_data_probability_editor->setup_property_editor(Variant::FLOAT, "probability", "", 1.0);
+ tile_data_probability_editor->connect("needs_redraw", callable_mp((CanvasItem *)tile_atlas_control_unscaled, &Control::update));
+ tile_data_probability_editor->connect("needs_redraw", callable_mp((CanvasItem *)alternative_tiles_control_unscaled, &Control::update));
+ tile_data_editors["probability"] = tile_data_probability_editor;
+ }
+
+ // --- Physics ---
+ ADD_TILE_DATA_EDITOR_GROUP("Physics");
+ for (int i = 0; i < tile_set->get_physics_layers_count(); i++) {
+ ADD_TILE_DATA_EDITOR(group, vformat("Physics Layer %d", i), vformat("physics_layer_%d", i));
+ if (!tile_data_editors.has(vformat("physics_layer_%d", i))) {
+ TileDataCollisionEditor *tile_data_collision_editor = memnew(TileDataCollisionEditor());
+ tile_data_collision_editor->hide();
+ tile_data_collision_editor->set_physics_layer(i);
+ tile_data_collision_editor->connect("needs_redraw", callable_mp((CanvasItem *)tile_atlas_control_unscaled, &Control::update));
+ tile_data_collision_editor->connect("needs_redraw", callable_mp((CanvasItem *)alternative_tiles_control_unscaled, &Control::update));
+ tile_data_editors[vformat("physics_layer_%d", i)] = tile_data_collision_editor;
+ }
+ }
+ for (int i = tile_set->get_physics_layers_count(); tile_data_editors.has(vformat("physics_layer_%d", i)); i++) {
+ tile_data_editors[vformat("physics_layer_%d", i)]->queue_delete();
+ tile_data_editors.erase(vformat("physics_layer_%d", i));
+ }
+
+ // --- Navigation ---
+ ADD_TILE_DATA_EDITOR_GROUP("Navigation");
+ for (int i = 0; i < tile_set->get_navigation_layers_count(); i++) {
+ ADD_TILE_DATA_EDITOR(group, vformat("Navigation Layer %d", i), vformat("navigation_layer_%d", i));
+ if (!tile_data_editors.has(vformat("navigation_layer_%d", i))) {
+ TileDataNavigationEditor *tile_data_navigation_editor = memnew(TileDataNavigationEditor());
+ tile_data_navigation_editor->hide();
+ tile_data_navigation_editor->set_navigation_layer(i);
+ tile_data_navigation_editor->connect("needs_redraw", callable_mp((CanvasItem *)tile_atlas_control_unscaled, &Control::update));
+ tile_data_navigation_editor->connect("needs_redraw", callable_mp((CanvasItem *)alternative_tiles_control_unscaled, &Control::update));
+ tile_data_editors[vformat("navigation_layer_%d", i)] = tile_data_navigation_editor;
+ }
+ }
+ for (int i = tile_set->get_navigation_layers_count(); tile_data_editors.has(vformat("navigation_layer_%d", i)); i++) {
+ tile_data_editors[vformat("navigation_layer_%d", i)]->queue_delete();
+ tile_data_editors.erase(vformat("navigation_layer_%d", i));
+ }
+
+ // --- Custom Data ---
+ ADD_TILE_DATA_EDITOR_GROUP("Custom Data");
+ for (int i = 0; i < tile_set->get_custom_data_layers_count(); i++) {
+ if (tile_set->get_custom_data_name(i).is_empty()) {
+ ADD_TILE_DATA_EDITOR(group, vformat("Custom Data %d", i), vformat("custom_data_%d", i));
+ } else {
+ ADD_TILE_DATA_EDITOR(group, tile_set->get_custom_data_name(i), vformat("custom_data_%d", i));
+ }
+ if (!tile_data_editors.has(vformat("custom_data_%d", i))) {
+ TileDataDefaultEditor *tile_data_custom_data_editor = memnew(TileDataDefaultEditor());
+ tile_data_custom_data_editor->hide();
+ tile_data_custom_data_editor->setup_property_editor(tile_set->get_custom_data_type(i), vformat("custom_data_%d", i), tile_set->get_custom_data_name(i));
+ tile_data_custom_data_editor->connect("needs_redraw", callable_mp((CanvasItem *)tile_atlas_control_unscaled, &Control::update));
+ tile_data_custom_data_editor->connect("needs_redraw", callable_mp((CanvasItem *)alternative_tiles_control_unscaled, &Control::update));
+ tile_data_editors[vformat("custom_data_%d", i)] = tile_data_custom_data_editor;
+ }
+ }
+ for (int i = tile_set->get_custom_data_layers_count(); tile_data_editors.has(vformat("custom_data_%d", i)); i++) {
+ tile_data_editors[vformat("custom_data_%d", i)]->queue_delete();
+ tile_data_editors.erase(vformat("custom_data_%d", i));
+ }
+
+#undef ADD_TILE_DATA_EDITOR_GROUP
+#undef ADD_TILE_DATA_EDITOR
+
+ // Add tile data editors as children.
+ for (Map<String, TileDataEditor *>::Element *E = tile_data_editors.front(); E; E = E->next()) {
+ // Tile Data Editor.
+ TileDataEditor *tile_data_editor = E->get();
+ if (!tile_data_editor->is_inside_tree()) {
+ tile_data_painting_editor_container->add_child(tile_data_editor);
+ }
+ tile_data_editor->set_tile_set(tile_set);
+
+ // Toolbar.
+ Control *toolbar = tile_data_editor->get_toolbar();
+ if (!toolbar->is_inside_tree()) {
+ tool_settings_tile_data_toolbar_container->add_child(toolbar);
+ }
+ toolbar->hide();
}
// Update visibility.
- tile_inspector_label->set_visible(has_atlas_tile_selected);
- tile_inspector->set_visible(has_atlas_tile_selected);
+ bool is_visible = tools_button_group->get_pressed_button() == tool_paint_button;
+ tile_data_editor_dropdown_button->set_visible(is_visible);
+ tile_data_editor_dropdown_button->set_text(TTR("Select a property editor"));
+ tile_data_editors_label->set_visible(is_visible);
+}
+
+void TileSetAtlasSourceEditor::_update_current_tile_data_editor() {
+ // Find the property to use.
+ String property;
+ if (tools_button_group->get_pressed_button() == tool_select_button && tile_inspector->is_visible() && !tile_inspector->get_selected_path().is_empty()) {
+ Vector<String> components = tile_inspector->get_selected_path().split("/");
+ if (components.size() >= 1) {
+ property = components[0];
+
+ // Workaround for terrains as they don't have a common first component.
+ if (property.begins_with("terrains_")) {
+ property = "terrain_set";
+ }
+ }
+ } else if (tools_button_group->get_pressed_button() == tool_paint_button && tile_data_editors_tree->get_selected()) {
+ property = tile_data_editors_tree->get_selected()->get_metadata(0);
+ tile_data_editor_dropdown_button->set_text(tile_data_editors_tree->get_selected()->get_text(0));
+ }
+
+ // Hide all editors but the current one.
+ for (Map<String, TileDataEditor *>::Element *E = tile_data_editors.front(); E; E = E->next()) {
+ E->get()->hide();
+ E->get()->get_toolbar()->hide();
+ }
+ if (tile_data_editors.has(property)) {
+ current_tile_data_editor = tile_data_editors[property];
+ } else {
+ current_tile_data_editor = nullptr;
+ }
+
+ // Get the correct editor for the TileData's property.
+ if (current_tile_data_editor) {
+ current_tile_data_editor_toolbar = current_tile_data_editor->get_toolbar();
+ current_property = property;
+ current_tile_data_editor->set_visible(tools_button_group->get_pressed_button() == tool_paint_button);
+ current_tile_data_editor_toolbar->set_visible(tools_button_group->get_pressed_button() == tool_paint_button);
+ }
+}
+
+void TileSetAtlasSourceEditor::_tile_data_editor_dropdown_button_draw() {
+ if (!has_theme_icon("arrow", "OptionButton")) {
+ return;
+ }
+
+ RID ci = tile_data_editor_dropdown_button->get_canvas_item();
+ Ref<Texture2D> arrow = Control::get_theme_icon("arrow", "OptionButton");
+ Color clr = Color(1, 1, 1);
+ if (get_theme_constant("modulate_arrow")) {
+ switch (tile_data_editor_dropdown_button->get_draw_mode()) {
+ case BaseButton::DRAW_PRESSED:
+ clr = get_theme_color("font_pressed_color");
+ break;
+ case BaseButton::DRAW_HOVER:
+ clr = get_theme_color("font_hover_color");
+ break;
+ case BaseButton::DRAW_DISABLED:
+ clr = get_theme_color("font_disabled_color");
+ break;
+ default:
+ clr = get_theme_color("font_color");
+ }
+ }
+
+ Size2 size = tile_data_editor_dropdown_button->get_size();
+
+ Point2 ofs;
+ if (is_layout_rtl()) {
+ ofs = Point2(get_theme_constant("arrow_margin", "OptionButton"), int(Math::abs((size.height - arrow->get_height()) / 2)));
+ } else {
+ ofs = Point2(size.width - arrow->get_width() - get_theme_constant("arrow_margin", "OptionButton"), int(Math::abs((size.height - arrow->get_height()) / 2)));
+ }
+ arrow->draw(ci, ofs, clr);
+}
+
+void TileSetAtlasSourceEditor::_tile_data_editor_dropdown_button_pressed() {
+ Size2 size = tile_data_editor_dropdown_button->get_size();
+ tile_data_editors_popup->set_position(tile_data_editor_dropdown_button->get_screen_position() + Size2(0, size.height * get_global_transform().get_scale().y));
+ tile_data_editors_popup->set_size(Size2(size.width, 0));
+ tile_data_editors_popup->popup();
+}
+
+void TileSetAtlasSourceEditor::_tile_data_editors_tree_selected() {
+ tile_data_editors_popup->call_deferred("hide");
+ _update_current_tile_data_editor();
+ tile_atlas_control->update();
+ tile_atlas_control_unscaled->update();
+ alternative_tiles_control->update();
+ alternative_tiles_control_unscaled->update();
}
void TileSetAtlasSourceEditor::_update_atlas_view() {
@@ -467,19 +766,28 @@ void TileSetAtlasSourceEditor::_update_atlas_view() {
}
void TileSetAtlasSourceEditor::_update_toolbar() {
- // Hide all settings.
- for (int i = 0; i < tool_settings->get_child_count(); i++) {
- Object::cast_to<CanvasItem>(tool_settings->get_child(i))->hide();
- }
-
- // SHow only the correct settings.
- if (tools_button_group->get_pressed_button() == tool_select_button) {
- } else if (tools_button_group->get_pressed_button() == tool_add_remove_button) {
- tool_settings_vsep->show();
- tools_settings_erase_button->show();
- } else if (tools_button_group->get_pressed_button() == tool_add_remove_rect_button) {
+ // Show the tools and settings.
+ if (tools_button_group->get_pressed_button() == tool_setup_atlas_source_button) {
+ if (current_tile_data_editor_toolbar) {
+ current_tile_data_editor_toolbar->hide();
+ }
tool_settings_vsep->show();
tools_settings_erase_button->show();
+ tool_advanced_menu_buttom->show();
+ } else if (tools_button_group->get_pressed_button() == tool_select_button) {
+ if (current_tile_data_editor_toolbar) {
+ current_tile_data_editor_toolbar->hide();
+ }
+ tool_settings_vsep->hide();
+ tools_settings_erase_button->hide();
+ tool_advanced_menu_buttom->hide();
+ } else if (tools_button_group->get_pressed_button() == tool_paint_button) {
+ if (current_tile_data_editor_toolbar) {
+ current_tile_data_editor_toolbar->show();
+ }
+ tool_settings_vsep->hide();
+ tools_settings_erase_button->hide();
+ tool_advanced_menu_buttom->hide();
}
}
@@ -499,357 +807,336 @@ void TileSetAtlasSourceEditor::_tile_atlas_control_gui_input(const Ref<InputEven
// Update the hovered coords.
hovered_base_tile_coords = tile_atlas_view->get_atlas_tile_coords_at_pos(tile_atlas_control->get_local_mouse_position());
- // Handle the event.
- Ref<InputEventMouseMotion> mm = p_event;
- if (mm.is_valid()) {
- Vector2i start_base_tiles_coords = tile_atlas_view->get_atlas_tile_coords_at_pos(drag_start_mouse_pos);
- Vector2i last_base_tiles_coords = tile_atlas_view->get_atlas_tile_coords_at_pos(drag_last_mouse_pos);
- Vector2i new_base_tiles_coords = tile_atlas_view->get_atlas_tile_coords_at_pos(tile_atlas_control->get_local_mouse_position());
+ // Forward the event to the current tile data editor if we are in the painting mode.
+ if (tools_button_group->get_pressed_button() == tool_paint_button) {
+ if (current_tile_data_editor) {
+ current_tile_data_editor->forward_painting_atlas_gui_input(tile_atlas_view, tile_set_atlas_source, p_event);
+ }
+ // Update only what's needed.
+ tile_set_atlas_source_changed_needs_update = false;
- Vector2i grid_size = tile_set_atlas_source->get_atlas_grid_size();
+ tile_atlas_control->update();
+ tile_atlas_control_unscaled->update();
+ alternative_tiles_control->update();
+ alternative_tiles_control_unscaled->update();
+ tile_atlas_view->update();
+ return;
+ } else {
+ // Handle the event.
+ Ref<InputEventMouseMotion> mm = p_event;
+ if (mm.is_valid()) {
+ Vector2i start_base_tiles_coords = tile_atlas_view->get_atlas_tile_coords_at_pos(drag_start_mouse_pos);
+ Vector2i last_base_tiles_coords = tile_atlas_view->get_atlas_tile_coords_at_pos(drag_last_mouse_pos);
+ Vector2i new_base_tiles_coords = tile_atlas_view->get_atlas_tile_coords_at_pos(tile_atlas_control->get_local_mouse_position());
- if (drag_type == DRAG_TYPE_NONE) {
- if (selection.size() == 1) {
- // Change the cursor depending on the hovered thing.
- TileSelection selected = selection.front()->get();
- if (selected.tile != TileSetSource::INVALID_ATLAS_COORDS && selected.alternative == 0) {
- Vector2 mouse_local_pos = tile_atlas_control->get_local_mouse_position();
- Vector2i size_in_atlas = tile_set_atlas_source->get_tile_size_in_atlas(selected.tile);
- Rect2 region = tile_set_atlas_source->get_tile_texture_region(selected.tile);
- Size2 zoomed_size = resize_handle->get_size() / tile_atlas_view->get_zoom();
- Rect2 rect = region.grow_individual(zoomed_size.x, zoomed_size.y, 0, 0);
- const Vector2i coords[] = { Vector2i(0, 0), Vector2i(1, 0), Vector2i(1, 1), Vector2i(0, 1) };
- const Vector2i directions[] = { Vector2i(0, -1), Vector2i(1, 0), Vector2i(0, 1), Vector2i(-1, 0) };
- CursorShape cursor_shape = CURSOR_ARROW;
- bool can_grow[4];
- for (int i = 0; i < 4; i++) {
- can_grow[i] = tile_set_atlas_source->can_move_tile_in_atlas(selected.tile, selected.tile + directions[i]);
- can_grow[i] |= (i % 2 == 0) ? size_in_atlas.y > 1 : size_in_atlas.x > 1;
- }
- for (int i = 0; i < 4; i++) {
- Vector2 pos = rect.position + Vector2(rect.size.x, rect.size.y) * coords[i];
- if (can_grow[i] && can_grow[(i + 3) % 4] && Rect2(pos, zoomed_size).has_point(mouse_local_pos)) {
- cursor_shape = (i % 2) ? CURSOR_BDIAGSIZE : CURSOR_FDIAGSIZE;
+ Vector2i grid_size = tile_set_atlas_source->get_atlas_grid_size();
+
+ if (drag_type == DRAG_TYPE_NONE) {
+ if (selection.size() == 1) {
+ // Change the cursor depending on the hovered thing.
+ TileSelection selected = selection.front()->get();
+ if (selected.tile != TileSetSource::INVALID_ATLAS_COORDS && selected.alternative == 0) {
+ Vector2 mouse_local_pos = tile_atlas_control->get_local_mouse_position();
+ Vector2i size_in_atlas = tile_set_atlas_source->get_tile_size_in_atlas(selected.tile);
+ Rect2 region = tile_set_atlas_source->get_tile_texture_region(selected.tile);
+ Size2 zoomed_size = resize_handle->get_size() / tile_atlas_view->get_zoom();
+ Rect2 rect = region.grow_individual(zoomed_size.x, zoomed_size.y, 0, 0);
+ const Vector2i coords[] = { Vector2i(0, 0), Vector2i(1, 0), Vector2i(1, 1), Vector2i(0, 1) };
+ const Vector2i directions[] = { Vector2i(0, -1), Vector2i(1, 0), Vector2i(0, 1), Vector2i(-1, 0) };
+ CursorShape cursor_shape = CURSOR_ARROW;
+ bool can_grow[4];
+ for (int i = 0; i < 4; i++) {
+ can_grow[i] = tile_set_atlas_source->can_move_tile_in_atlas(selected.tile, selected.tile + directions[i]);
+ can_grow[i] |= (i % 2 == 0) ? size_in_atlas.y > 1 : size_in_atlas.x > 1;
}
- Vector2 next_pos = rect.position + Vector2(rect.size.x, rect.size.y) * coords[(i + 1) % 4];
- if (can_grow[i] && Rect2((pos + next_pos) / 2.0, zoomed_size).has_point(mouse_local_pos)) {
- cursor_shape = (i % 2) ? CURSOR_HSIZE : CURSOR_VSIZE;
+ for (int i = 0; i < 4; i++) {
+ Vector2 pos = rect.position + Vector2(rect.size.x, rect.size.y) * coords[i];
+ if (can_grow[i] && can_grow[(i + 3) % 4] && Rect2(pos, zoomed_size).has_point(mouse_local_pos)) {
+ cursor_shape = (i % 2) ? CURSOR_BDIAGSIZE : CURSOR_FDIAGSIZE;
+ }
+ Vector2 next_pos = rect.position + Vector2(rect.size.x, rect.size.y) * coords[(i + 1) % 4];
+ if (can_grow[i] && Rect2((pos + next_pos) / 2.0, zoomed_size).has_point(mouse_local_pos)) {
+ cursor_shape = (i % 2) ? CURSOR_HSIZE : CURSOR_VSIZE;
+ }
}
+ tile_atlas_control->set_default_cursor_shape(cursor_shape);
}
- tile_atlas_control->set_default_cursor_shape(cursor_shape);
}
- }
- } else if (drag_type == DRAG_TYPE_CREATE_BIG_TILE) {
- // Create big tile.
- new_base_tiles_coords = new_base_tiles_coords.max(Vector2i(0, 0)).min(grid_size - Vector2i(1, 1));
-
- Rect2i new_rect = Rect2i(start_base_tiles_coords, new_base_tiles_coords - start_base_tiles_coords).abs();
- new_rect.size += Vector2i(1, 1);
- // Check if the new tile can fit in the new rect.
- if (tile_set_atlas_source->can_move_tile_in_atlas(drag_current_tile, new_rect.position, new_rect.size)) {
- // Move and resize the tile.
- tile_set_atlas_source->move_tile_in_atlas(drag_current_tile, new_rect.position, new_rect.size);
- drag_current_tile = new_rect.position;
- }
- } else if (drag_type == DRAG_TYPE_CREATE_TILES) {
- // Create tiles.
- last_base_tiles_coords = last_base_tiles_coords.max(Vector2i(0, 0)).min(grid_size - Vector2i(1, 1));
- new_base_tiles_coords = new_base_tiles_coords.max(Vector2i(0, 0)).min(grid_size - Vector2i(1, 1));
-
- Vector<Point2i> line = Geometry2D::bresenham_line(last_base_tiles_coords, new_base_tiles_coords);
- for (int i = 0; i < line.size(); i++) {
- if (tile_set_atlas_source->get_tile_at_coords(line[i]) == TileSetSource::INVALID_ATLAS_COORDS) {
- tile_set_atlas_source->create_tile(line[i]);
- drag_modified_tiles.insert(line[i]);
+ } else if (drag_type == DRAG_TYPE_CREATE_BIG_TILE) {
+ // Create big tile.
+ new_base_tiles_coords = new_base_tiles_coords.max(Vector2i(0, 0)).min(grid_size - Vector2i(1, 1));
+
+ Rect2i new_rect = Rect2i(start_base_tiles_coords, new_base_tiles_coords - start_base_tiles_coords).abs();
+ new_rect.size += Vector2i(1, 1);
+ // Check if the new tile can fit in the new rect.
+ if (tile_set_atlas_source->can_move_tile_in_atlas(drag_current_tile, new_rect.position, new_rect.size)) {
+ // Move and resize the tile.
+ tile_set_atlas_source->move_tile_in_atlas(drag_current_tile, new_rect.position, new_rect.size);
+ drag_current_tile = new_rect.position;
+ }
+ } else if (drag_type == DRAG_TYPE_CREATE_TILES) {
+ // Create tiles.
+ last_base_tiles_coords = last_base_tiles_coords.max(Vector2i(0, 0)).min(grid_size - Vector2i(1, 1));
+ new_base_tiles_coords = new_base_tiles_coords.max(Vector2i(0, 0)).min(grid_size - Vector2i(1, 1));
+
+ Vector<Point2i> line = Geometry2D::bresenham_line(last_base_tiles_coords, new_base_tiles_coords);
+ for (int i = 0; i < line.size(); i++) {
+ if (tile_set_atlas_source->get_tile_at_coords(line[i]) == TileSetSource::INVALID_ATLAS_COORDS) {
+ tile_set_atlas_source->create_tile(line[i]);
+ drag_modified_tiles.insert(line[i]);
+ }
}
- }
- drag_last_mouse_pos = tile_atlas_control->get_local_mouse_position();
+ drag_last_mouse_pos = tile_atlas_control->get_local_mouse_position();
- } else if (drag_type == DRAG_TYPE_REMOVE_TILES) {
- // Remove tiles.
- last_base_tiles_coords = last_base_tiles_coords.max(Vector2i(0, 0)).min(grid_size - Vector2i(1, 1));
- new_base_tiles_coords = new_base_tiles_coords.max(Vector2i(0, 0)).min(grid_size - Vector2i(1, 1));
+ } else if (drag_type == DRAG_TYPE_REMOVE_TILES) {
+ // Remove tiles.
+ last_base_tiles_coords = last_base_tiles_coords.max(Vector2i(0, 0)).min(grid_size - Vector2i(1, 1));
+ new_base_tiles_coords = new_base_tiles_coords.max(Vector2i(0, 0)).min(grid_size - Vector2i(1, 1));
- Vector<Point2i> line = Geometry2D::bresenham_line(last_base_tiles_coords, new_base_tiles_coords);
- for (int i = 0; i < line.size(); i++) {
- Vector2i base_tile_coords = tile_set_atlas_source->get_tile_at_coords(line[i]);
- if (base_tile_coords != TileSetSource::INVALID_ATLAS_COORDS) {
- drag_modified_tiles.insert(base_tile_coords);
+ Vector<Point2i> line = Geometry2D::bresenham_line(last_base_tiles_coords, new_base_tiles_coords);
+ for (int i = 0; i < line.size(); i++) {
+ Vector2i base_tile_coords = tile_set_atlas_source->get_tile_at_coords(line[i]);
+ if (base_tile_coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ drag_modified_tiles.insert(base_tile_coords);
+ }
}
- }
- drag_last_mouse_pos = tile_atlas_control->get_local_mouse_position();
- } else if (drag_type == DRAG_TYPE_MOVE_TILE) {
- // Move tile.
- Vector2 mouse_offset = (Vector2(tile_set_atlas_source->get_tile_size_in_atlas(drag_current_tile)) / 2.0 - Vector2(0.5, 0.5)) * tile_set->get_tile_size();
- Vector2i coords = tile_atlas_view->get_atlas_tile_coords_at_pos(tile_atlas_control->get_local_mouse_position() - mouse_offset);
- coords = coords.max(Vector2i(0, 0)).min(grid_size - Vector2i(1, 1));
- if (drag_current_tile != coords && tile_set_atlas_source->can_move_tile_in_atlas(drag_current_tile, coords)) {
- tile_set_atlas_source->move_tile_in_atlas(drag_current_tile, coords);
- selection.clear();
- selection.insert({ coords, 0 });
- drag_current_tile = coords;
+ drag_last_mouse_pos = tile_atlas_control->get_local_mouse_position();
+ } else if (drag_type == DRAG_TYPE_MOVE_TILE) {
+ // Move tile.
+ Vector2 mouse_offset = (Vector2(tile_set_atlas_source->get_tile_size_in_atlas(drag_current_tile)) / 2.0 - Vector2(0.5, 0.5)) * tile_set->get_tile_size();
+ Vector2i coords = tile_atlas_view->get_atlas_tile_coords_at_pos(tile_atlas_control->get_local_mouse_position() - mouse_offset);
+ coords = coords.max(Vector2i(0, 0)).min(grid_size - Vector2i(1, 1));
+ if (drag_current_tile != coords && tile_set_atlas_source->can_move_tile_in_atlas(drag_current_tile, coords)) {
+ tile_set_atlas_source->move_tile_in_atlas(drag_current_tile, coords);
+ selection.clear();
+ selection.insert({ coords, 0 });
+ drag_current_tile = coords;
- // Update only what's needed.
- tile_set_atlas_source_changed_needs_update = false;
- _update_tile_inspector();
- _update_atlas_view();
- _update_tile_id_label();
- }
- } else if (drag_type >= DRAG_TYPE_RESIZE_TOP_LEFT && drag_type <= DRAG_TYPE_RESIZE_LEFT) {
- // Resizing a tile.
- new_base_tiles_coords = new_base_tiles_coords.max(Vector2i(-1, -1)).min(grid_size);
+ // Update only what's needed.
+ tile_set_atlas_source_changed_needs_update = false;
+ _update_tile_inspector();
+ _update_atlas_view();
+ _update_tile_id_label();
+ _update_current_tile_data_editor();
+ }
+ } else if (drag_type == DRAG_TYPE_MAY_POPUP_MENU) {
+ if (Vector2(drag_start_mouse_pos).distance_to(tile_atlas_control->get_local_mouse_position()) > 5.0 * EDSCALE) {
+ drag_type = DRAG_TYPE_NONE;
+ }
+ } else if (drag_type >= DRAG_TYPE_RESIZE_TOP_LEFT && drag_type <= DRAG_TYPE_RESIZE_LEFT) {
+ // Resizing a tile.
+ new_base_tiles_coords = new_base_tiles_coords.max(Vector2i(-1, -1)).min(grid_size);
- Rect2i old_rect = Rect2i(drag_current_tile, tile_set_atlas_source->get_tile_size_in_atlas(drag_current_tile));
- Rect2i new_rect = old_rect;
+ Rect2i old_rect = Rect2i(drag_current_tile, tile_set_atlas_source->get_tile_size_in_atlas(drag_current_tile));
+ Rect2i new_rect = old_rect;
- if (drag_type == DRAG_TYPE_RESIZE_LEFT || drag_type == DRAG_TYPE_RESIZE_TOP_LEFT || drag_type == DRAG_TYPE_RESIZE_BOTTOM_LEFT) {
- new_rect.position.x = MIN(new_base_tiles_coords.x + 1, old_rect.get_end().x - 1);
- new_rect.size.x = old_rect.get_end().x - new_rect.position.x;
- }
- if (drag_type == DRAG_TYPE_RESIZE_TOP || drag_type == DRAG_TYPE_RESIZE_TOP_LEFT || drag_type == DRAG_TYPE_RESIZE_TOP_RIGHT) {
- new_rect.position.y = MIN(new_base_tiles_coords.y + 1, old_rect.get_end().y - 1);
- new_rect.size.y = old_rect.get_end().y - new_rect.position.y;
- }
+ if (drag_type == DRAG_TYPE_RESIZE_LEFT || drag_type == DRAG_TYPE_RESIZE_TOP_LEFT || drag_type == DRAG_TYPE_RESIZE_BOTTOM_LEFT) {
+ new_rect.position.x = MIN(new_base_tiles_coords.x + 1, old_rect.get_end().x - 1);
+ new_rect.size.x = old_rect.get_end().x - new_rect.position.x;
+ }
+ if (drag_type == DRAG_TYPE_RESIZE_TOP || drag_type == DRAG_TYPE_RESIZE_TOP_LEFT || drag_type == DRAG_TYPE_RESIZE_TOP_RIGHT) {
+ new_rect.position.y = MIN(new_base_tiles_coords.y + 1, old_rect.get_end().y - 1);
+ new_rect.size.y = old_rect.get_end().y - new_rect.position.y;
+ }
- if (drag_type == DRAG_TYPE_RESIZE_RIGHT || drag_type == DRAG_TYPE_RESIZE_TOP_RIGHT || drag_type == DRAG_TYPE_RESIZE_BOTTOM_RIGHT) {
- new_rect.set_end(Vector2i(MAX(new_base_tiles_coords.x, old_rect.position.x + 1), new_rect.get_end().y));
- }
- if (drag_type == DRAG_TYPE_RESIZE_BOTTOM || drag_type == DRAG_TYPE_RESIZE_BOTTOM_LEFT || drag_type == DRAG_TYPE_RESIZE_BOTTOM_RIGHT) {
- new_rect.set_end(Vector2i(new_rect.get_end().x, MAX(new_base_tiles_coords.y, old_rect.position.y + 1)));
- }
+ if (drag_type == DRAG_TYPE_RESIZE_RIGHT || drag_type == DRAG_TYPE_RESIZE_TOP_RIGHT || drag_type == DRAG_TYPE_RESIZE_BOTTOM_RIGHT) {
+ new_rect.set_end(Vector2i(MAX(new_base_tiles_coords.x, old_rect.position.x + 1), new_rect.get_end().y));
+ }
+ if (drag_type == DRAG_TYPE_RESIZE_BOTTOM || drag_type == DRAG_TYPE_RESIZE_BOTTOM_LEFT || drag_type == DRAG_TYPE_RESIZE_BOTTOM_RIGHT) {
+ new_rect.set_end(Vector2i(new_rect.get_end().x, MAX(new_base_tiles_coords.y, old_rect.position.y + 1)));
+ }
- if (tile_set_atlas_source->can_move_tile_in_atlas(drag_current_tile, new_rect.position, new_rect.size)) {
- tile_set_atlas_source->move_tile_in_atlas(drag_current_tile, new_rect.position, new_rect.size);
- selection.clear();
- selection.insert({ new_rect.position, 0 });
- drag_current_tile = new_rect.position;
+ if (tile_set_atlas_source->can_move_tile_in_atlas(drag_current_tile, new_rect.position, new_rect.size)) {
+ tile_set_atlas_source->move_tile_in_atlas(drag_current_tile, new_rect.position, new_rect.size);
+ selection.clear();
+ selection.insert({ new_rect.position, 0 });
+ drag_current_tile = new_rect.position;
- // Update only what's needed.
- tile_set_atlas_source_changed_needs_update = false;
- _update_tile_inspector();
- _update_atlas_view();
- _update_tile_id_label();
+ // Update only what's needed.
+ tile_set_atlas_source_changed_needs_update = false;
+ _update_tile_inspector();
+ _update_atlas_view();
+ _update_tile_id_label();
+ _update_current_tile_data_editor();
+ }
}
+
+ // Redraw for the hovered tile.
+ tile_atlas_control->update();
+ tile_atlas_control_unscaled->update();
+ alternative_tiles_control->update();
+ alternative_tiles_control_unscaled->update();
+ tile_atlas_view->update();
+ return;
}
- // Redraw for the hovered tile.
- tile_atlas_control->update();
- tile_atlas_control_unscaled->update();
- alternative_tiles_control->update();
- alternative_tiles_control_unscaled->update();
- tile_atlas_view->update();
- return;
- }
+ Ref<InputEventMouseButton> mb = p_event;
+ if (mb.is_valid()) {
+ Vector2 mouse_local_pos = tile_atlas_control->get_local_mouse_position();
+ if (mb->get_button_index() == MOUSE_BUTTON_LEFT) {
+ if (mb->is_pressed()) {
+ // Left click pressed.
+ if (tools_button_group->get_pressed_button() == tool_setup_atlas_source_button) {
+ if (tools_settings_erase_button->is_pressed()) {
+ // Erasing
+ if (mb->is_ctrl_pressed() || mb->is_shift_pressed()) {
+ // Remove tiles using rect.
+
+ // Setup the dragging info.
+ drag_type = DRAG_TYPE_REMOVE_TILES_USING_RECT;
+ drag_start_mouse_pos = mouse_local_pos;
+ drag_last_mouse_pos = drag_start_mouse_pos;
+ } else {
+ // Remove tiles.
- Ref<InputEventMouseButton> mb = p_event;
- if (mb.is_valid()) {
- Vector2 mouse_local_pos = tile_atlas_control->get_local_mouse_position();
- if (mb->get_button_index() == MOUSE_BUTTON_LEFT) {
- if (mb->is_pressed()) {
- // Left click pressed.
- if (tools_button_group->get_pressed_button() == tool_add_remove_button) {
- if (tools_settings_erase_button->is_pressed()) {
- // Remove tiles.
-
- // Setup the dragging info.
- drag_type = DRAG_TYPE_REMOVE_TILES;
- drag_start_mouse_pos = mouse_local_pos;
- drag_last_mouse_pos = drag_start_mouse_pos;
-
- // Remove a first tile.
- Vector2i coords = tile_atlas_view->get_atlas_tile_coords_at_pos(drag_start_mouse_pos);
- if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
- coords = tile_set_atlas_source->get_tile_at_coords(coords);
- }
- if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
- drag_modified_tiles.insert(coords);
- }
- } else {
- if (mb->is_shift_pressed()) {
- // Create a big tile.
- Vector2i coords = tile_atlas_view->get_atlas_tile_coords_at_pos(mouse_local_pos);
- if (coords != TileSetSource::INVALID_ATLAS_COORDS && tile_set_atlas_source->get_tile_at_coords(coords) == TileSetSource::INVALID_ATLAS_COORDS) {
- // Setup the dragging info, only if we start on an empty tile.
- drag_type = DRAG_TYPE_CREATE_BIG_TILE;
+ // Setup the dragging info.
+ drag_type = DRAG_TYPE_REMOVE_TILES;
drag_start_mouse_pos = mouse_local_pos;
drag_last_mouse_pos = drag_start_mouse_pos;
- drag_current_tile = coords;
- // Create a tile.
- tile_set_atlas_source->create_tile(coords);
+ // Remove a first tile.
+ Vector2i coords = tile_atlas_view->get_atlas_tile_coords_at_pos(drag_start_mouse_pos);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ coords = tile_set_atlas_source->get_tile_at_coords(coords);
+ }
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ drag_modified_tiles.insert(coords);
+ }
}
} else {
- // Create tiles.
-
- // Setup the dragging info.
- drag_type = DRAG_TYPE_CREATE_TILES;
- drag_start_mouse_pos = mouse_local_pos;
- drag_last_mouse_pos = drag_start_mouse_pos;
-
- // Create a first tile if needed.
- Vector2i coords = tile_atlas_view->get_atlas_tile_coords_at_pos(drag_start_mouse_pos);
- if (coords != TileSetSource::INVALID_ATLAS_COORDS && tile_set_atlas_source->get_tile_at_coords(coords) == TileSetSource::INVALID_ATLAS_COORDS) {
- tile_set_atlas_source->create_tile(coords);
- drag_modified_tiles.insert(coords);
- }
- }
- }
- } else if (tools_button_group->get_pressed_button() == tool_add_remove_rect_button) {
- if (tools_settings_erase_button->is_pressed()) {
- // Remove tiles using rect.
-
- // Setup the dragging info.
- drag_type = DRAG_TYPE_REMOVE_TILES_USING_RECT;
- drag_start_mouse_pos = mouse_local_pos;
- drag_last_mouse_pos = drag_start_mouse_pos;
- } else {
- if (mb->is_shift_pressed()) {
- // Create a big tile.
- Vector2i coords = tile_atlas_view->get_atlas_tile_coords_at_pos(mouse_local_pos);
- if (coords != TileSetSource::INVALID_ATLAS_COORDS && tile_set_atlas_source->get_tile_at_coords(coords) == TileSetSource::INVALID_ATLAS_COORDS) {
- // Setup the dragging info, only if we start on an empty tile.
- drag_type = DRAG_TYPE_CREATE_BIG_TILE;
+ // Creating
+ if (mb->is_shift_pressed()) {
+ // Create a big tile.
+ Vector2i coords = tile_atlas_view->get_atlas_tile_coords_at_pos(mouse_local_pos);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS && tile_set_atlas_source->get_tile_at_coords(coords) == TileSetSource::INVALID_ATLAS_COORDS) {
+ // Setup the dragging info, only if we start on an empty tile.
+ drag_type = DRAG_TYPE_CREATE_BIG_TILE;
+ drag_start_mouse_pos = mouse_local_pos;
+ drag_last_mouse_pos = drag_start_mouse_pos;
+ drag_current_tile = coords;
+
+ // Create a tile.
+ tile_set_atlas_source->create_tile(coords);
+ }
+ } else if (mb->is_ctrl_pressed()) {
+ // Create tiles using rect.
+ drag_type = DRAG_TYPE_CREATE_TILES_USING_RECT;
drag_start_mouse_pos = mouse_local_pos;
drag_last_mouse_pos = drag_start_mouse_pos;
- drag_current_tile = coords;
+ } else {
+ // Create tiles.
- // Create a tile.
- tile_set_atlas_source->create_tile(coords);
+ // Setup the dragging info.
+ drag_type = DRAG_TYPE_CREATE_TILES;
+ drag_start_mouse_pos = mouse_local_pos;
+ drag_last_mouse_pos = drag_start_mouse_pos;
+
+ // Create a first tile if needed.
+ Vector2i coords = tile_atlas_view->get_atlas_tile_coords_at_pos(drag_start_mouse_pos);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS && tile_set_atlas_source->get_tile_at_coords(coords) == TileSetSource::INVALID_ATLAS_COORDS) {
+ tile_set_atlas_source->create_tile(coords);
+ drag_modified_tiles.insert(coords);
+ }
}
- } else {
- // Create tiles using rect.
- drag_type = DRAG_TYPE_CREATE_TILES_USING_RECT;
- drag_start_mouse_pos = mouse_local_pos;
- drag_last_mouse_pos = drag_start_mouse_pos;
}
- }
- } else if (tools_button_group->get_pressed_button() == tool_select_button) {
- // Dragging a handle.
- drag_type = DRAG_TYPE_NONE;
- if (selection.size() == 1) {
- TileSelection selected = selection.front()->get();
- if (selected.tile != TileSetSource::INVALID_ATLAS_COORDS && selected.alternative == 0) {
- Vector2i size_in_atlas = tile_set_atlas_source->get_tile_size_in_atlas(selected.tile);
- Rect2 region = tile_set_atlas_source->get_tile_texture_region(selected.tile);
- Size2 zoomed_size = resize_handle->get_size() / tile_atlas_view->get_zoom();
- Rect2 rect = region.grow_individual(zoomed_size.x, zoomed_size.y, 0, 0);
- const Vector2i coords[] = { Vector2i(0, 0), Vector2i(1, 0), Vector2i(1, 1), Vector2i(0, 1) };
- const Vector2i directions[] = { Vector2i(0, -1), Vector2i(1, 0), Vector2i(0, 1), Vector2i(-1, 0) };
- CursorShape cursor_shape = CURSOR_ARROW;
- bool can_grow[4];
- for (int i = 0; i < 4; i++) {
- can_grow[i] = tile_set_atlas_source->can_move_tile_in_atlas(selected.tile, selected.tile + directions[i]);
- can_grow[i] |= (i % 2 == 0) ? size_in_atlas.y > 1 : size_in_atlas.x > 1;
- }
- for (int i = 0; i < 4; i++) {
- Vector2 pos = rect.position + Vector2(rect.size.x, rect.size.y) * coords[i];
- if (can_grow[i] && can_grow[(i + 3) % 4] && Rect2(pos, zoomed_size).has_point(mouse_local_pos)) {
- drag_type = (DragType)((int)DRAG_TYPE_RESIZE_TOP_LEFT + i * 2);
- drag_start_mouse_pos = mouse_local_pos;
- drag_last_mouse_pos = drag_start_mouse_pos;
- drag_current_tile = selected.tile;
- drag_start_tile_shape = Rect2i(selected.tile, tile_set_atlas_source->get_tile_size_in_atlas(selected.tile));
- cursor_shape = (i % 2) ? CURSOR_BDIAGSIZE : CURSOR_FDIAGSIZE;
+ } else if (tools_button_group->get_pressed_button() == tool_select_button) {
+ // Dragging a handle.
+ drag_type = DRAG_TYPE_NONE;
+ if (selection.size() == 1) {
+ TileSelection selected = selection.front()->get();
+ if (selected.tile != TileSetSource::INVALID_ATLAS_COORDS && selected.alternative == 0) {
+ Vector2i size_in_atlas = tile_set_atlas_source->get_tile_size_in_atlas(selected.tile);
+ Rect2 region = tile_set_atlas_source->get_tile_texture_region(selected.tile);
+ Size2 zoomed_size = resize_handle->get_size() / tile_atlas_view->get_zoom();
+ Rect2 rect = region.grow_individual(zoomed_size.x, zoomed_size.y, 0, 0);
+ const Vector2i coords[] = { Vector2i(0, 0), Vector2i(1, 0), Vector2i(1, 1), Vector2i(0, 1) };
+ const Vector2i directions[] = { Vector2i(0, -1), Vector2i(1, 0), Vector2i(0, 1), Vector2i(-1, 0) };
+ CursorShape cursor_shape = CURSOR_ARROW;
+ bool can_grow[4];
+ for (int i = 0; i < 4; i++) {
+ can_grow[i] = tile_set_atlas_source->can_move_tile_in_atlas(selected.tile, selected.tile + directions[i]);
+ can_grow[i] |= (i % 2 == 0) ? size_in_atlas.y > 1 : size_in_atlas.x > 1;
}
- Vector2 next_pos = rect.position + Vector2(rect.size.x, rect.size.y) * coords[(i + 1) % 4];
- if (can_grow[i] && Rect2((pos + next_pos) / 2.0, zoomed_size).has_point(mouse_local_pos)) {
- drag_type = (DragType)((int)DRAG_TYPE_RESIZE_TOP + i * 2);
- drag_start_mouse_pos = mouse_local_pos;
- drag_last_mouse_pos = drag_start_mouse_pos;
- drag_current_tile = selected.tile;
- drag_start_tile_shape = Rect2i(selected.tile, tile_set_atlas_source->get_tile_size_in_atlas(selected.tile));
- cursor_shape = (i % 2) ? CURSOR_HSIZE : CURSOR_VSIZE;
+ for (int i = 0; i < 4; i++) {
+ Vector2 pos = rect.position + Vector2(rect.size.x, rect.size.y) * coords[i];
+ if (can_grow[i] && can_grow[(i + 3) % 4] && Rect2(pos, zoomed_size).has_point(mouse_local_pos)) {
+ drag_type = (DragType)((int)DRAG_TYPE_RESIZE_TOP_LEFT + i * 2);
+ drag_start_mouse_pos = mouse_local_pos;
+ drag_last_mouse_pos = drag_start_mouse_pos;
+ drag_current_tile = selected.tile;
+ drag_start_tile_shape = Rect2i(selected.tile, tile_set_atlas_source->get_tile_size_in_atlas(selected.tile));
+ cursor_shape = (i % 2) ? CURSOR_BDIAGSIZE : CURSOR_FDIAGSIZE;
+ }
+ Vector2 next_pos = rect.position + Vector2(rect.size.x, rect.size.y) * coords[(i + 1) % 4];
+ if (can_grow[i] && Rect2((pos + next_pos) / 2.0, zoomed_size).has_point(mouse_local_pos)) {
+ drag_type = (DragType)((int)DRAG_TYPE_RESIZE_TOP + i * 2);
+ drag_start_mouse_pos = mouse_local_pos;
+ drag_last_mouse_pos = drag_start_mouse_pos;
+ drag_current_tile = selected.tile;
+ drag_start_tile_shape = Rect2i(selected.tile, tile_set_atlas_source->get_tile_size_in_atlas(selected.tile));
+ cursor_shape = (i % 2) ? CURSOR_HSIZE : CURSOR_VSIZE;
+ }
}
+ tile_atlas_control->set_default_cursor_shape(cursor_shape);
}
- tile_atlas_control->set_default_cursor_shape(cursor_shape);
}
- }
- // Selecting then dragging a tile.
- if (drag_type == DRAG_TYPE_NONE) {
- TileSelection selected = { TileSetSource::INVALID_ATLAS_COORDS, TileSetSource::INVALID_TILE_ALTERNATIVE };
- Vector2i coords = tile_atlas_view->get_atlas_tile_coords_at_pos(mouse_local_pos);
- if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
- coords = tile_set_atlas_source->get_tile_at_coords(coords);
+ // Selecting then dragging a tile.
+ if (drag_type == DRAG_TYPE_NONE) {
+ TileSelection selected = { TileSetSource::INVALID_ATLAS_COORDS, TileSetSource::INVALID_TILE_ALTERNATIVE };
+ Vector2i coords = tile_atlas_view->get_atlas_tile_coords_at_pos(mouse_local_pos);
if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
- selected = { coords, 0 };
+ coords = tile_set_atlas_source->get_tile_at_coords(coords);
+ if (coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ selected = { coords, 0 };
+ }
}
- }
- bool shift = mb->is_shift_pressed();
- if (!shift && selection.size() == 1 && selected.tile != TileSetSource::INVALID_ATLAS_COORDS && selection.has(selected)) {
- // Start move dragging.
- drag_type = DRAG_TYPE_MOVE_TILE;
- drag_start_mouse_pos = mouse_local_pos;
- drag_last_mouse_pos = drag_start_mouse_pos;
- drag_current_tile = selected.tile;
- drag_start_tile_shape = Rect2i(selected.tile, tile_set_atlas_source->get_tile_size_in_atlas(selected.tile));
- tile_atlas_control->set_default_cursor_shape(CURSOR_MOVE);
- } else {
- // Start selection dragging.
- drag_type = DRAG_TYPE_RECT_SELECT;
- drag_start_mouse_pos = mouse_local_pos;
- drag_last_mouse_pos = drag_start_mouse_pos;
+ bool shift = mb->is_shift_pressed();
+ if (!shift && selection.size() == 1 && selected.tile != TileSetSource::INVALID_ATLAS_COORDS && selection.has(selected)) {
+ // Start move dragging.
+ drag_type = DRAG_TYPE_MOVE_TILE;
+ drag_start_mouse_pos = mouse_local_pos;
+ drag_last_mouse_pos = drag_start_mouse_pos;
+ drag_current_tile = selected.tile;
+ drag_start_tile_shape = Rect2i(selected.tile, tile_set_atlas_source->get_tile_size_in_atlas(selected.tile));
+ tile_atlas_control->set_default_cursor_shape(CURSOR_MOVE);
+ } else {
+ // Start selection dragging.
+ drag_type = DRAG_TYPE_RECT_SELECT;
+ drag_start_mouse_pos = mouse_local_pos;
+ drag_last_mouse_pos = drag_start_mouse_pos;
+ }
}
}
+ } else {
+ // Left click released.
+ _end_dragging();
}
- } else {
- // Left click released.
- _end_dragging();
- }
- tile_atlas_control->update();
- tile_atlas_control_unscaled->update();
- alternative_tiles_control->update();
- alternative_tiles_control_unscaled->update();
- tile_atlas_view->update();
- return;
- } else if (mb->get_button_index() == MOUSE_BUTTON_RIGHT) {
- if (mb->is_pressed()) {
+ tile_atlas_control->update();
+ tile_atlas_control_unscaled->update();
+ alternative_tiles_control->update();
+ alternative_tiles_control_unscaled->update();
+ tile_atlas_view->update();
+ return;
+ } else if (mb->get_button_index() == MOUSE_BUTTON_RIGHT) {
// Right click pressed.
-
- TileSelection selected = { tile_atlas_view->get_atlas_tile_coords_at_pos(mouse_local_pos), 0 };
- if (selected.tile != TileSetSource::INVALID_ATLAS_COORDS) {
- selected.tile = tile_set_atlas_source->get_tile_at_coords(selected.tile);
- }
-
- // Set the selection if needed.
- if (selection.size() <= 1) {
- if (selected.tile != TileSetSource::INVALID_ATLAS_COORDS) {
- undo_redo->create_action(TTR("Select tiles"));
- undo_redo->add_undo_method(this, "_set_selection_from_array", _get_selection_as_array());
- selection.clear();
- selection.insert(selected);
- undo_redo->add_do_method(this, "_set_selection_from_array", _get_selection_as_array());
- undo_redo->commit_action(false);
- _update_tile_inspector();
- _update_tile_id_label();
- }
- }
-
- // Pops up the correct menu, depending on whether we have a tile or not.
- if (selected.tile != TileSetSource::INVALID_ATLAS_COORDS && selection.has(selected)) {
- // We have a tile.
- menu_option_coords = selected.tile;
- menu_option_alternative = 0;
- base_tile_popup_menu->popup(Rect2i(get_global_mouse_position(), Size2i()));
- } else if (hovered_base_tile_coords != TileSetSource::INVALID_ATLAS_COORDS) {
- // We don't have a tile, but can create one.
- menu_option_coords = hovered_base_tile_coords;
- menu_option_alternative = TileSetSource::INVALID_TILE_ALTERNATIVE;
- empty_base_tile_popup_menu->popup(Rect2i(get_global_mouse_position(), Size2i()));
+ if (mb->is_pressed()) {
+ drag_type = DRAG_TYPE_MAY_POPUP_MENU;
+ drag_start_mouse_pos = tile_atlas_control->get_local_mouse_position();
+ } else {
+ // Right click released.
+ _end_dragging();
}
- } else {
- // Right click released.
- _end_dragging();
+ tile_atlas_control->update();
+ tile_atlas_control_unscaled->update();
+ alternative_tiles_control->update();
+ alternative_tiles_control_unscaled->update();
+ tile_atlas_view->update();
+ return;
}
- tile_atlas_control->update();
- tile_atlas_control_unscaled->update();
- alternative_tiles_control->update();
- alternative_tiles_control_unscaled->update();
- tile_atlas_view->update();
- return;
}
}
}
@@ -1000,10 +1287,45 @@ void TileSetAtlasSourceEditor::_end_dragging() {
}
_update_tile_inspector();
_update_tile_id_label();
+ _update_current_tile_data_editor();
undo_redo->add_do_method(this, "_set_selection_from_array", _get_selection_as_array());
undo_redo->commit_action(false);
- break;
- }
+ } break;
+ case DRAG_TYPE_MAY_POPUP_MENU: {
+ Vector2 mouse_local_pos = tile_atlas_control->get_local_mouse_position();
+ TileSelection selected = { tile_atlas_view->get_atlas_tile_coords_at_pos(mouse_local_pos), 0 };
+ if (selected.tile != TileSetSource::INVALID_ATLAS_COORDS) {
+ selected.tile = tile_set_atlas_source->get_tile_at_coords(selected.tile);
+ }
+
+ // Set the selection if needed.
+ if (selection.size() <= 1) {
+ if (selected.tile != TileSetSource::INVALID_ATLAS_COORDS) {
+ undo_redo->create_action(TTR("Select tiles"));
+ undo_redo->add_undo_method(this, "_set_selection_from_array", _get_selection_as_array());
+ selection.clear();
+ selection.insert(selected);
+ undo_redo->add_do_method(this, "_set_selection_from_array", _get_selection_as_array());
+ undo_redo->commit_action(false);
+ _update_tile_inspector();
+ _update_tile_id_label();
+ _update_current_tile_data_editor();
+ }
+ }
+
+ // Pops up the correct menu, depending on whether we have a tile or not.
+ if (selected.tile != TileSetSource::INVALID_ATLAS_COORDS && selection.has(selected)) {
+ // We have a tile.
+ menu_option_coords = selected.tile;
+ menu_option_alternative = 0;
+ base_tile_popup_menu->popup(Rect2i(get_global_mouse_position(), Size2i()));
+ } else if (hovered_base_tile_coords != TileSetSource::INVALID_ATLAS_COORDS) {
+ // We don't have a tile, but can create one.
+ menu_option_coords = hovered_base_tile_coords;
+ menu_option_alternative = TileSetSource::INVALID_TILE_ALTERNATIVE;
+ empty_base_tile_popup_menu->popup(Rect2i(get_global_mouse_position(), Size2i()));
+ }
+ } break;
case DRAG_TYPE_RESIZE_TOP_LEFT:
case DRAG_TYPE_RESIZE_TOP:
case DRAG_TYPE_RESIZE_TOP_RIGHT:
@@ -1166,6 +1488,7 @@ void TileSetAtlasSourceEditor::_set_selection_from_array(Array p_selection) {
_update_tile_inspector();
_update_tile_id_label();
_update_atlas_view();
+ _update_current_tile_data_editor();
}
Array TileSetAtlasSourceEditor::_get_selection_as_array() {
@@ -1297,7 +1620,7 @@ void TileSetAtlasSourceEditor::_tile_atlas_control_draw() {
tile_atlas_control->draw_rect(tile_set_atlas_source->get_tile_texture_region(hovered_tile), Color(1.0, 1.0, 1.0), false);
} else {
// Draw empty tile, only in add/remove tiles mode.
- if (tools_button_group->get_pressed_button() == tool_add_remove_button || tools_button_group->get_pressed_button() == tool_add_remove_rect_button) {
+ if (tools_button_group->get_pressed_button() == tool_setup_atlas_source_button) {
Vector2i margins = tile_set_atlas_source->get_margins();
Vector2i separation = tile_set_atlas_source->get_separation();
Vector2i tile_size = tile_set_atlas_source->get_texture_region_size();
@@ -1310,9 +1633,8 @@ void TileSetAtlasSourceEditor::_tile_atlas_control_draw() {
}
void TileSetAtlasSourceEditor::_tile_atlas_control_unscaled_draw() {
- // Draw the preview of the selected property.
- TileDataEditor *tile_data_editor = TileSetEditor::get_singleton()->get_tile_data_editor(selected_property);
- if (tile_data_editor && tile_inspector->is_visible_in_tree()) {
+ if (current_tile_data_editor) {
+ // Draw the preview of the selected property.
for (int i = 0; i < tile_set_atlas_source->get_tiles_count(); i++) {
Vector2i coords = tile_set_atlas_source->get_tile_id(i);
Rect2i texture_region = tile_set_atlas_source->get_tile_texture_region(coords);
@@ -1321,7 +1643,41 @@ void TileSetAtlasSourceEditor::_tile_atlas_control_unscaled_draw() {
Transform2D xform = tile_atlas_control->get_parent_control()->get_transform();
xform.translate(position);
- tile_data_editor->draw_over_tile(tile_atlas_control_unscaled, xform, *tile_set, tile_set_atlas_source_id, coords, 0, selected_property);
+ if (tools_button_group->get_pressed_button() == tool_select_button && selection.has({ coords, 0 })) {
+ continue;
+ }
+
+ TileMapCell cell;
+ cell.source_id = tile_set_atlas_source_id;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = 0;
+ current_tile_data_editor->draw_over_tile(tile_atlas_control_unscaled, xform, cell);
+ }
+
+ // Draw the selection on top of other.
+ if (tools_button_group->get_pressed_button() == tool_select_button) {
+ for (Set<TileSelection>::Element *E = selection.front(); E; E = E->next()) {
+ if (E->get().alternative != 0) {
+ continue;
+ }
+ Rect2i texture_region = tile_set_atlas_source->get_tile_texture_region(E->get().tile);
+ Vector2i position = (texture_region.position + texture_region.get_end()) / 2 + tile_set_atlas_source->get_tile_effective_texture_offset(E->get().tile, 0);
+
+ Transform2D xform = tile_atlas_control->get_parent_control()->get_transform();
+ xform.translate(position);
+
+ TileMapCell cell;
+ cell.source_id = tile_set_atlas_source_id;
+ cell.set_atlas_coords(E->get().tile);
+ cell.alternative_tile = 0;
+ current_tile_data_editor->draw_over_tile(tile_atlas_control_unscaled, xform, cell, true);
+ }
+ }
+
+ // Call the TileData's editor custom draw function.
+ if (tools_button_group->get_pressed_button() == tool_paint_button) {
+ Transform2D xform = tile_atlas_control->get_parent_control()->get_transform();
+ current_tile_data_editor->forward_draw_over_atlas(tile_atlas_view, tile_set_atlas_source, tile_atlas_control_unscaled, xform);
}
}
}
@@ -1330,6 +1686,19 @@ void TileSetAtlasSourceEditor::_tile_alternatives_control_gui_input(const Ref<In
// Update the hovered alternative tile.
hovered_alternative_tile_coords = tile_atlas_view->get_alternative_tile_at_pos(alternative_tiles_control->get_local_mouse_position());
+ // Forward the event to the current tile data editor if we are in the painting mode.
+ if (tools_button_group->get_pressed_button() == tool_paint_button) {
+ if (current_tile_data_editor) {
+ current_tile_data_editor->forward_painting_alternatives_gui_input(tile_atlas_view, tile_set_atlas_source, p_event);
+ }
+ tile_atlas_control->update();
+ tile_atlas_control_unscaled->update();
+ alternative_tiles_control->update();
+ alternative_tiles_control_unscaled->update();
+ tile_atlas_view->update();
+ return;
+ }
+
Ref<InputEventMouseMotion> mm = p_event;
if (mm.is_valid()) {
tile_atlas_control->update();
@@ -1425,7 +1794,60 @@ void TileSetAtlasSourceEditor::_tile_alternatives_control_draw() {
}
void TileSetAtlasSourceEditor::_tile_alternatives_control_unscaled_draw() {
- //TODO
+ // Draw the preview of the selected property.
+ if (current_tile_data_editor) {
+ // Draw the preview of the currently selected property.
+ for (int i = 0; i < tile_set_atlas_source->get_tiles_count(); i++) {
+ Vector2i coords = tile_set_atlas_source->get_tile_id(i);
+ for (int j = 0; j < tile_set_atlas_source->get_alternative_tiles_count(coords); j++) {
+ int alternative_tile = tile_set_atlas_source->get_alternative_tile_id(coords, j);
+ if (alternative_tile == 0) {
+ continue;
+ }
+ Rect2i rect = tile_atlas_view->get_alternative_tile_rect(coords, alternative_tile);
+ Vector2 position = (rect.get_position() + rect.get_end()) / 2;
+
+ Transform2D xform = alternative_tiles_control->get_parent_control()->get_transform();
+ xform.translate(position);
+
+ if (tools_button_group->get_pressed_button() == tool_select_button && selection.has({ coords, alternative_tile })) {
+ continue;
+ }
+
+ TileMapCell cell;
+ cell.source_id = tile_set_atlas_source_id;
+ cell.set_atlas_coords(coords);
+ cell.alternative_tile = alternative_tile;
+ current_tile_data_editor->draw_over_tile(alternative_tiles_control_unscaled, xform, cell);
+ }
+ }
+
+ // Draw the selection on top of other.
+ if (tools_button_group->get_pressed_button() == tool_select_button) {
+ for (Set<TileSelection>::Element *E = selection.front(); E; E = E->next()) {
+ if (E->get().alternative == 0) {
+ continue;
+ }
+ Rect2i rect = tile_atlas_view->get_alternative_tile_rect(E->get().tile, E->get().alternative);
+ Vector2 position = (rect.get_position() + rect.get_end()) / 2;
+
+ Transform2D xform = alternative_tiles_control->get_parent_control()->get_transform();
+ xform.translate(position);
+
+ TileMapCell cell;
+ cell.source_id = tile_set_atlas_source_id;
+ cell.set_atlas_coords(E->get().tile);
+ cell.alternative_tile = E->get().alternative;
+ current_tile_data_editor->draw_over_tile(alternative_tiles_control_unscaled, xform, cell, true);
+ }
+ }
+
+ // Call the TileData's editor custom draw function.
+ if (tools_button_group->get_pressed_button() == tool_paint_button) {
+ Transform2D xform = tile_atlas_control->get_parent_control()->get_transform();
+ current_tile_data_editor->forward_draw_over_alternatives(tile_atlas_view, tile_set_atlas_source, alternative_tiles_control_unscaled, xform);
+ }
+ }
}
void TileSetAtlasSourceEditor::_tile_set_atlas_source_changed() {
@@ -1449,15 +1871,23 @@ void TileSetAtlasSourceEditor::_undo_redo_inspector_callback(Object *p_undo_redo
AtlasTileProxyObject *tile_data = Object::cast_to<AtlasTileProxyObject>(p_edited);
if (tile_data) {
Vector<String> components = String(p_property).split("/", true, 2);
- if (components.size() == 2 && components[1] == "shapes_count") {
+ if (components.size() == 2 && components[1] == "polygons_count") {
int layer_index = components[0].trim_prefix("physics_layer_").to_int();
- int new_shapes_count = p_new_value;
- int old_shapes_count = tile_data->get(vformat("physics_layer_%d/shapes_count", layer_index));
- if (new_shapes_count < old_shapes_count) {
- for (int i = new_shapes_count - 1; i < old_shapes_count; i++) {
- ADD_UNDO(tile_data, vformat("physics_layer_%d/shape_%d/shape", layer_index, i));
- ADD_UNDO(tile_data, vformat("physics_layer_%d/shape_%d/one_way", layer_index, i));
- ADD_UNDO(tile_data, vformat("physics_layer_%d/shape_%d/one_way_margin", layer_index, i));
+ int new_polygons_count = p_new_value;
+ int old_polygons_count = tile_data->get(vformat("physics_layer_%d/polygons_count", layer_index));
+ if (new_polygons_count < old_polygons_count) {
+ for (int i = new_polygons_count - 1; i < old_polygons_count; i++) {
+ ADD_UNDO(tile_data, vformat("physics_layer_%d/polygon_%d/points", layer_index, i));
+ ADD_UNDO(tile_data, vformat("physics_layer_%d/polygon_%d/one_way", layer_index, i));
+ ADD_UNDO(tile_data, vformat("physics_layer_%d/polygon_%d/one_way_margin", layer_index, i));
+ }
+ }
+ } else if (p_property == "terrain_set") {
+ int current_terrain_set = tile_data->get("terrain_set");
+ for (int i = 0; i < TileSet::CELL_NEIGHBOR_MAX; i++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(i);
+ if (tile_set->is_valid_peering_bit_terrain(current_terrain_set, bit)) {
+ ADD_UNDO(tile_data, "terrains_peering_bit/" + String(TileSet::CELL_NEIGHBOR_ENUM_TO_TEXT[i]));
}
}
}
@@ -1500,7 +1930,10 @@ void TileSetAtlasSourceEditor::edit(Ref<TileSet> p_tile_set, TileSetAtlasSource
_update_fix_selected_and_hovered_tiles();
_update_tile_id_label();
_update_atlas_view();
+ _update_atlas_source_inspector();
_update_tile_inspector();
+ _update_tile_data_editors();
+ _update_current_tile_data_editor();
}
void TileSetAtlasSourceEditor::init_source() {
@@ -1616,13 +2049,13 @@ void TileSetAtlasSourceEditor::_notification(int p_what) {
switch (p_what) {
case NOTIFICATION_ENTER_TREE:
case NOTIFICATION_THEME_CHANGED:
+ tool_setup_atlas_source_button->set_icon(get_theme_icon("Tools", "EditorIcons"));
tool_select_button->set_icon(get_theme_icon("ToolSelect", "EditorIcons"));
- tool_add_remove_button->set_icon(get_theme_icon("EditAddRemove", "EditorIcons"));
- tool_add_remove_rect_button->set_icon(get_theme_icon("RectangleAddRemove", "EditorIcons"));
+ tool_paint_button->set_icon(get_theme_icon("CanvasItem", "EditorIcons"));
tools_settings_erase_button->set_icon(get_theme_icon("Eraser", "EditorIcons"));
- tool_advanced_menu_buttom->set_icon(get_theme_icon("Tools", "EditorIcons"));
+ tool_advanced_menu_buttom->set_icon(get_theme_icon("GuiTabMenu", "EditorIcons"));
resize_handle = get_theme_icon("EditorHandle", "EditorIcons");
resize_handle_disabled = get_theme_icon("EditorHandleDisabled", "EditorIcons");
@@ -1636,7 +2069,10 @@ void TileSetAtlasSourceEditor::_notification(int p_what) {
_update_fix_selected_and_hovered_tiles();
_update_tile_id_label();
_update_atlas_view();
+ _update_atlas_source_inspector();
_update_tile_inspector();
+ _update_tile_data_editors();
+ _update_current_tile_data_editor();
tile_set_atlas_source_changed_needs_update = false;
}
@@ -1675,7 +2111,6 @@ TileSetAtlasSourceEditor::TileSetAtlasSourceEditor() {
// Tile inspector.
tile_inspector_label = memnew(Label);
tile_inspector_label->set_text(TTR("Tile Properties:"));
- tile_inspector_label->hide();
middle_vbox_container->add_child(tile_inspector_label);
tile_proxy_object = memnew(AtlasTileProxyObject(this));
@@ -1689,6 +2124,36 @@ TileSetAtlasSourceEditor::TileSetAtlasSourceEditor() {
tile_inspector->connect("property_selected", callable_mp(this, &TileSetAtlasSourceEditor::_inspector_property_selected));
middle_vbox_container->add_child(tile_inspector);
+ tile_inspector_no_tile_selected_label = memnew(Label);
+ tile_inspector_no_tile_selected_label->set_align(Label::ALIGN_CENTER);
+ tile_inspector_no_tile_selected_label->set_text(TTR("No tile selected."));
+ middle_vbox_container->add_child(tile_inspector_no_tile_selected_label);
+
+ // Property values palette.
+ tile_data_editors_popup = memnew(Popup);
+
+ tile_data_editors_label = memnew(Label);
+ tile_data_editors_label->set_text(TTR("Paint Properties:"));
+ middle_vbox_container->add_child(tile_data_editors_label);
+
+ tile_data_editor_dropdown_button = memnew(Button);
+ tile_data_editor_dropdown_button->connect("draw", callable_mp(this, &TileSetAtlasSourceEditor::_tile_data_editor_dropdown_button_draw));
+ tile_data_editor_dropdown_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_tile_data_editor_dropdown_button_pressed));
+ middle_vbox_container->add_child(tile_data_editor_dropdown_button);
+ tile_data_editor_dropdown_button->add_child(tile_data_editors_popup);
+
+ tile_data_editors_tree = memnew(Tree);
+ tile_data_editors_tree->set_hide_root(true);
+ tile_data_editors_tree->set_anchors_and_offsets_preset(Control::PRESET_WIDE);
+ tile_data_editors_tree->set_h_scroll_enabled(false);
+ tile_data_editors_tree->set_v_scroll_enabled(false);
+ tile_data_editors_tree->connect("item_selected", callable_mp(this, &TileSetAtlasSourceEditor::_tile_data_editors_tree_selected));
+ tile_data_editors_popup->add_child(tile_data_editors_tree);
+
+ tile_data_painting_editor_container = memnew(VBoxContainer);
+ tile_data_painting_editor_container->set_h_size_flags(SIZE_EXPAND_FILL);
+ middle_vbox_container->add_child(tile_data_painting_editor_container);
+
// Atlas source inspector.
atlas_source_inspector_label = memnew(Label);
atlas_source_inspector_label->set_text(TTR("Atlas Properties:"));
@@ -1719,47 +2184,41 @@ TileSetAtlasSourceEditor::TileSetAtlasSourceEditor() {
add_child(confirm_auto_create_tiles);
// -- Toolbox --
- tools_button_group.instance();
+ tools_button_group.instantiate();
+ tools_button_group->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_fix_selected_and_hovered_tiles).unbind(1));
+ tools_button_group->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_tile_id_label).unbind(1));
+ tools_button_group->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_atlas_source_inspector).unbind(1));
+ tools_button_group->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_tile_inspector).unbind(1));
+ tools_button_group->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_tile_data_editors).unbind(1));
+ tools_button_group->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_current_tile_data_editor).unbind(1));
+ tools_button_group->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_atlas_view).unbind(1));
+ tools_button_group->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_toolbar).unbind(1));
toolbox = memnew(HBoxContainer);
right_panel->add_child(toolbox);
+ tool_setup_atlas_source_button = memnew(Button);
+ tool_setup_atlas_source_button->set_flat(true);
+ tool_setup_atlas_source_button->set_toggle_mode(true);
+ tool_setup_atlas_source_button->set_pressed(true);
+ tool_setup_atlas_source_button->set_button_group(tools_button_group);
+ tool_setup_atlas_source_button->set_tooltip(TTR("Atlas Setup. Add/Remove tiles tool (use the shift key to create big tiles, control for rectangle editing)."));
+ toolbox->add_child(tool_setup_atlas_source_button);
+
tool_select_button = memnew(Button);
tool_select_button->set_flat(true);
tool_select_button->set_toggle_mode(true);
- tool_select_button->set_pressed(true);
+ tool_select_button->set_pressed(false);
tool_select_button->set_button_group(tools_button_group);
tool_select_button->set_tooltip(TTR("Select tiles."));
- tool_select_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_fix_selected_and_hovered_tiles));
- tool_select_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_tile_id_label));
- tool_select_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_tile_inspector));
- tool_select_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_atlas_view));
- tool_select_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_toolbar));
toolbox->add_child(tool_select_button);
- tool_add_remove_button = memnew(Button);
- tool_add_remove_button->set_flat(true);
- tool_add_remove_button->set_toggle_mode(true);
- tool_add_remove_button->set_button_group(tools_button_group);
- tool_add_remove_button->set_tooltip(TTR("Add/Remove tiles tool (use the shift key to create big tiles)."));
- tool_add_remove_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_fix_selected_and_hovered_tiles));
- tool_add_remove_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_tile_id_label));
- tool_add_remove_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_tile_inspector));
- tool_add_remove_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_atlas_view));
- tool_add_remove_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_toolbar));
- toolbox->add_child(tool_add_remove_button);
-
- tool_add_remove_rect_button = memnew(Button);
- tool_add_remove_rect_button->set_flat(true);
- tool_add_remove_rect_button->set_toggle_mode(true);
- tool_add_remove_rect_button->set_button_group(tools_button_group);
- tool_add_remove_rect_button->set_tooltip(TTR("Add/Remove tiles rectangle tool (use the shift key to create big tiles)."));
- tool_add_remove_rect_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_fix_selected_and_hovered_tiles));
- tool_add_remove_rect_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_tile_id_label));
- tool_add_remove_rect_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_tile_inspector));
- tool_add_remove_rect_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_atlas_view));
- tool_add_remove_rect_button->connect("pressed", callable_mp(this, &TileSetAtlasSourceEditor::_update_toolbar));
- toolbox->add_child(tool_add_remove_rect_button);
+ tool_paint_button = memnew(Button);
+ tool_paint_button->set_flat(true);
+ tool_paint_button->set_toggle_mode(true);
+ tool_paint_button->set_button_group(tools_button_group);
+ tool_paint_button->set_tooltip(TTR("Paint properties."));
+ toolbox->add_child(tool_paint_button);
// Tool settings.
tool_settings = memnew(HBoxContainer);
@@ -1768,6 +2227,9 @@ TileSetAtlasSourceEditor::TileSetAtlasSourceEditor() {
tool_settings_vsep = memnew(VSeparator);
tool_settings->add_child(tool_settings_vsep);
+ tool_settings_tile_data_toolbar_container = memnew(HBoxContainer);
+ tool_settings->add_child(tool_settings_tile_data_toolbar_container);
+
tools_settings_erase_button = memnew(Button);
tools_settings_erase_button->set_flat(true);
tools_settings_erase_button->set_toggle_mode(true);
@@ -1775,9 +2237,6 @@ TileSetAtlasSourceEditor::TileSetAtlasSourceEditor() {
tools_settings_erase_button->set_shortcut_context(this);
tool_settings->add_child(tools_settings_erase_button);
- VSeparator *tool_advanced_vsep = memnew(VSeparator);
- toolbox->add_child(tool_advanced_vsep);
-
tool_advanced_menu_buttom = memnew(MenuButton);
tool_advanced_menu_buttom->set_flat(true);
tool_advanced_menu_buttom->get_popup()->add_item(TTR("Cleanup Tiles Outside Texture"), ADVANCED_CLEANUP_TILES_OUTSIDE_TEXTURE);
@@ -1844,7 +2303,7 @@ TileSetAtlasSourceEditor::TileSetAtlasSourceEditor() {
alternative_tiles_control_unscaled = memnew(Control);
alternative_tiles_control_unscaled->set_anchors_and_offsets_preset(Control::PRESET_WIDE);
alternative_tiles_control_unscaled->connect("draw", callable_mp(this, &TileSetAtlasSourceEditor::_tile_alternatives_control_unscaled_draw));
- tile_atlas_view->add_control_over_atlas_tiles(alternative_tiles_control_unscaled, false);
+ tile_atlas_view->add_control_over_alternative_tiles(alternative_tiles_control_unscaled, false);
alternative_tiles_control_unscaled->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
tile_atlas_view_missing_source_label = memnew(Label);
diff --git a/editor/plugins/tiles/tile_set_atlas_source_editor.h b/editor/plugins/tiles/tile_set_atlas_source_editor.h
index 70f2cdbe01..dbb0756a16 100644
--- a/editor/plugins/tiles/tile_set_atlas_source_editor.h
+++ b/editor/plugins/tiles/tile_set_atlas_source_editor.h
@@ -32,6 +32,7 @@
#define TILE_SET_ATLAS_SOURCE_EDITOR_H
#include "tile_atlas_view.h"
+#include "tile_data_editors.h"
#include "editor/editor_node.h"
#include "scene/gui/split_container.h"
@@ -113,10 +114,27 @@ private:
bool tile_set_atlas_source_changed_needs_update = false;
+ // -- Properties painting --
+ VBoxContainer *tile_data_painting_editor_container;
+ Label *tile_data_editors_label;
+ Button *tile_data_editor_dropdown_button;
+ Popup *tile_data_editors_popup;
+ Tree *tile_data_editors_tree;
+ void _tile_data_editor_dropdown_button_draw();
+ void _tile_data_editor_dropdown_button_pressed();
+
+ // -- Tile data editors --
+ String current_property;
+ Control *current_tile_data_editor_toolbar = nullptr;
+ Map<String, TileDataEditor *> tile_data_editors;
+ TileDataEditor *current_tile_data_editor = nullptr;
+ void _tile_data_editors_tree_selected();
+
// -- Inspector --
AtlasTileProxyObject *tile_proxy_object;
Label *tile_inspector_label;
EditorInspector *tile_inspector;
+ Label *tile_inspector_no_tile_selected_label;
String selected_property;
void _inspector_property_selected(String p_property);
@@ -142,6 +160,8 @@ private:
DRAG_TYPE_RECT_SELECT,
+ DRAG_TYPE_MAY_POPUP_MENU,
+
// Warning: keep in this order.
DRAG_TYPE_RESIZE_TOP_LEFT,
DRAG_TYPE_RESIZE_TOP,
@@ -179,15 +199,16 @@ private:
// Tool buttons.
Ref<ButtonGroup> tools_button_group;
+ Button *tool_setup_atlas_source_button;
Button *tool_select_button;
- Button *tool_add_remove_button;
- Button *tool_add_remove_rect_button;
+ Button *tool_paint_button;
Label *tool_tile_id_label;
+ // Tool settings.
HBoxContainer *tool_settings;
VSeparator *tool_settings_vsep;
+ HBoxContainer *tool_settings_tile_data_toolbar_container;
Button *tools_settings_erase_button;
-
MenuButton *tool_advanced_menu_buttom;
// Selection.
@@ -226,7 +247,10 @@ private:
void _update_tile_id_label();
void _update_source_inspector();
void _update_fix_selected_and_hovered_tiles();
+ void _update_atlas_source_inspector();
void _update_tile_inspector();
+ void _update_tile_data_editors();
+ void _update_current_tile_data_editor();
void _update_manage_tile_properties_button();
void _update_atlas_view();
void _update_toolbar();
diff --git a/editor/plugins/tiles/tile_set_editor.cpp b/editor/plugins/tiles/tile_set_editor.cpp
index ae5620a4e3..2c2ebd107f 100644
--- a/editor/plugins/tiles/tile_set_editor.cpp
+++ b/editor/plugins/tiles/tile_set_editor.cpp
@@ -347,11 +347,11 @@ void TileSetEditor::_undo_redo_inspector_callback(Object *p_undo_redo, Object *p
int old_layer_count = tile_set->get_physics_layers_count();
if (new_layer_count < old_layer_count) {
for (int physics_layer_index = new_layer_count - 1; physics_layer_index < old_layer_count; physics_layer_index++) {
- ADD_UNDO(tile_data, vformat("physics_layer_%d/shapes_count", physics_layer_index));
- for (int shape_index = 0; shape_index < tile_data->get_collision_shapes_count(physics_layer_index); shape_index++) {
- ADD_UNDO(tile_data, vformat("physics_layer_%d/shape_%d/shape", physics_layer_index, shape_index));
- ADD_UNDO(tile_data, vformat("physics_layer_%d/shape_%d/one_way", physics_layer_index, shape_index));
- ADD_UNDO(tile_data, vformat("physics_layer_%d/shape_%d/one_way_margin", physics_layer_index, shape_index));
+ ADD_UNDO(tile_data, vformat("physics_layer_%d/polygons_count", physics_layer_index));
+ for (int polygon_index = 0; polygon_index < tile_data->get_collision_polygons_count(physics_layer_index); polygon_index++) {
+ ADD_UNDO(tile_data, vformat("physics_layer_%d/polygon_%d/points", physics_layer_index, polygon_index));
+ ADD_UNDO(tile_data, vformat("physics_layer_%d/polygon_%d/one_way", physics_layer_index, polygon_index));
+ ADD_UNDO(tile_data, vformat("physics_layer_%d/polygon_%d/one_way_margin", physics_layer_index, polygon_index));
}
}
}
@@ -359,53 +359,11 @@ void TileSetEditor::_undo_redo_inspector_callback(Object *p_undo_redo, Object *p
(components.size() == 2 && components[0].begins_with("terrain_set_") && components[0].trim_prefix("terrain_set_").is_valid_int() && components[1] == "mode") ||
(components.size() == 2 && components[0].begins_with("terrain_set_") && components[0].trim_prefix("terrain_set_").is_valid_int() && components[1] == "terrains_count" && tile_data->get_terrain_set() == components[0].trim_prefix("terrain_set_").to_int() && (int)p_new_value < tile_set->get_terrains_count(tile_data->get_terrain_set()))) {
ADD_UNDO(tile_data, "terrain_set");
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_RIGHT_SIDE)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/right_side");
- }
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_RIGHT_CORNER)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/right_corner");
- }
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_BOTTOM_RIGHT_SIDE)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/bottom_right_side");
- }
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_BOTTOM_RIGHT_CORNER)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/bottom_right_corner");
- }
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_BOTTOM_SIDE)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/bottom_side");
- }
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_BOTTOM_CORNER)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/bottom_corner");
- }
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_BOTTOM_LEFT_SIDE)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/bottom_left_side");
- }
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_BOTTOM_LEFT_CORNER)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/bottom_left_corner");
- }
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_LEFT_SIDE)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/left_side");
- }
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_LEFT_CORNER)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/left_corner");
- }
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_TOP_LEFT_SIDE)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/top_left_side");
- }
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_TOP_LEFT_CORNER)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/top_left_corner");
- }
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_TOP_SIDE)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/top_side");
- }
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_TOP_CORNER)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/top_corner");
- }
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_TOP_RIGHT_SIDE)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/top_right_side");
- }
- if (tile_data->is_valid_peering_bit_terrain(TileSet::CELL_NEIGHBOR_TOP_RIGHT_CORNER)) {
- ADD_UNDO(tile_data, "terrains_peering_bit/top_right_corner");
+ for (int l = 0; l < TileSet::CELL_NEIGHBOR_MAX; l++) {
+ TileSet::CellNeighbor bit = TileSet::CellNeighbor(l);
+ if (tile_data->is_valid_peering_bit_terrain(bit)) {
+ ADD_UNDO(tile_data, "terrains_peering_bit/" + String(TileSet::CELL_NEIGHBOR_ENUM_TO_TEXT[l]));
+ }
}
} else if (p_property == "navigation_layers_count") {
int new_layer_count = p_new_value;
@@ -440,30 +398,6 @@ void TileSetEditor::_bind_methods() {
ClassDB::bind_method(D_METHOD("_drop_data_fw"), &TileSetEditor::drop_data_fw);
}
-TileDataEditor *TileSetEditor::get_tile_data_editor(String p_property) {
- Vector<String> components = String(p_property).split("/", true);
-
- if (p_property == "z_index") {
- return tile_data_integer_editor;
- } else if (p_property == "probability") {
- return tile_data_float_editor;
- } else if (p_property == "y_sort_origin") {
- return tile_data_y_sort_editor;
- } else if (p_property == "texture_offset") {
- return tile_data_texture_offset_editor;
- } else if (components.size() >= 1 && components[0].begins_with("occlusion_layer_")) {
- return tile_data_occlusion_shape_editor;
- } else if (components.size() >= 1 && components[0].begins_with("physics_layer_")) {
- return tile_data_collision_shape_editor;
- } else if (p_property == "mode" || p_property == "terrain" || (components.size() >= 1 && components[0] == "terrains_peering_bit")) {
- return tile_data_terrains_editor;
- } else if (components.size() >= 1 && components[0].begins_with("navigation_layer_")) {
- return tile_data_navigation_polygon_editor;
- }
-
- return nullptr;
-}
-
void TileSetEditor::edit(Ref<TileSet> p_tile_set) {
if (p_tile_set == tile_set) {
return;
@@ -575,14 +509,4 @@ TileSetEditor::~TileSetEditor() {
if (tile_set.is_valid()) {
tile_set->disconnect("changed", callable_mp(this, &TileSetEditor::_tile_set_changed));
}
-
- // Delete tile data editors.
- memdelete(tile_data_texture_offset_editor);
- memdelete(tile_data_y_sort_editor);
- memdelete(tile_data_integer_editor);
- memdelete(tile_data_float_editor);
- memdelete(tile_data_occlusion_shape_editor);
- memdelete(tile_data_collision_shape_editor);
- memdelete(tile_data_terrains_editor);
- memdelete(tile_data_navigation_polygon_editor);
}
diff --git a/editor/plugins/tiles/tile_set_editor.h b/editor/plugins/tiles/tile_set_editor.h
index f584c043cc..9e50aca62f 100644
--- a/editor/plugins/tiles/tile_set_editor.h
+++ b/editor/plugins/tiles/tile_set_editor.h
@@ -33,7 +33,6 @@
#include "scene/gui/box_container.h"
#include "scene/resources/tile_set.h"
-#include "tile_data_editors.h"
#include "tile_set_atlas_source_editor.h"
#include "tile_set_scenes_collection_source_editor.h"
@@ -54,16 +53,6 @@ private:
void _update_atlas_sources_list(int force_selected_id = -1);
- // List of tile data editors.
- TileDataTextureOffsetEditor *tile_data_texture_offset_editor = memnew(TileDataTextureOffsetEditor);
- TileDataYSortEditor *tile_data_y_sort_editor = memnew(TileDataYSortEditor);
- TileDataIntegerEditor *tile_data_integer_editor = memnew(TileDataIntegerEditor);
- TileDataFloatEditor *tile_data_float_editor = memnew(TileDataFloatEditor);
- TileDataOcclusionShapeEditor *tile_data_occlusion_shape_editor = memnew(TileDataOcclusionShapeEditor);
- TileDataCollisionShapeEditor *tile_data_collision_shape_editor = memnew(TileDataCollisionShapeEditor);
- TileDataTerrainsEditor *tile_data_terrains_editor = memnew(TileDataTerrainsEditor);
- TileDataNavigationPolygonEditor *tile_data_navigation_polygon_editor = memnew(TileDataNavigationPolygonEditor);
-
// -- Sources management --
Button *sources_delete_button;
MenuButton *sources_add_button;
@@ -84,7 +73,6 @@ protected:
public:
_FORCE_INLINE_ static TileSetEditor *get_singleton() { return singleton; }
- TileDataEditor *get_tile_data_editor(String property);
void edit(Ref<TileSet> p_tile_set);
void drop_data_fw(const Point2 &p_point, const Variant &p_data, Control *p_from);
bool can_drop_data_fw(const Point2 &p_point, const Variant &p_data, Control *p_from) const;
diff --git a/editor/plugins/visual_shader_editor_plugin.cpp b/editor/plugins/visual_shader_editor_plugin.cpp
index e393f960bd..16d36ad053 100644
--- a/editor/plugins/visual_shader_editor_plugin.cpp
+++ b/editor/plugins/visual_shader_editor_plugin.cpp
@@ -818,7 +818,7 @@ void VisualShaderGraphPlugin::add_node(VisualShader::Type p_type, int p_id) {
if (is_expression) {
CodeEdit *expression_box = memnew(CodeEdit);
Ref<CodeHighlighter> expression_syntax_highlighter;
- expression_syntax_highlighter.instance();
+ expression_syntax_highlighter.instantiate();
expression_node->set_ctrl_pressed(expression_box, 0);
node->add_child(expression_box);
register_expression_edit(p_id, expression_box);
@@ -1053,7 +1053,7 @@ void VisualShaderEditor::update_custom_nodes() {
Ref<Script> script = Ref<Script>(res);
Ref<VisualShaderNodeCustom> ref;
- ref.instance();
+ ref.instantiate();
ref->set_script(script);
String name;
@@ -2209,7 +2209,7 @@ void VisualShaderEditor::_add_node(int p_idx, int p_op_idx, String p_resource_pa
bool is_custom = add_options[p_idx].is_custom;
if (!is_custom && add_options[p_idx].type != String()) {
- VisualShaderNode *vsn = Object::cast_to<VisualShaderNode>(ClassDB::instance(add_options[p_idx].type));
+ VisualShaderNode *vsn = Object::cast_to<VisualShaderNode>(ClassDB::instantiate(add_options[p_idx].type));
ERR_FAIL_COND(!vsn);
VisualShaderNodeFloatConstant *constant = Object::cast_to<VisualShaderNodeFloatConstant>(vsn);
@@ -2234,7 +2234,7 @@ void VisualShaderEditor::_add_node(int p_idx, int p_op_idx, String p_resource_pa
} else {
ERR_FAIL_COND(add_options[p_idx].script.is_null());
String base_type = add_options[p_idx].script->get_instance_base_type();
- VisualShaderNode *vsn = Object::cast_to<VisualShaderNode>(ClassDB::instance(base_type));
+ VisualShaderNode *vsn = Object::cast_to<VisualShaderNode>(ClassDB::instantiate(base_type));
ERR_FAIL_COND(!vsn);
vsnode = Ref<VisualShaderNode>(vsn);
vsnode->set_script(add_options[p_idx].script);
@@ -2315,6 +2315,13 @@ void VisualShaderEditor::_add_node(int p_idx, int p_op_idx, String p_resource_pa
undo_redo->add_do_method(graph_plugin.ptr(), "connect_nodes", type, _from_node, _from_slot, to_node, to_slot);
undo_redo->add_undo_method(graph_plugin.ptr(), "disconnect_nodes", type, _from_node, _from_slot, to_node, to_slot);
} else {
+ // Need to setting up Input node properly before committing since `is_port_types_compatible` (calling below) is using `mode` and `shader_type`.
+ VisualShaderNodeInput *input = Object::cast_to<VisualShaderNodeInput>(vsnode.ptr());
+ if (input) {
+ input->set_shader_mode(visual_shader->get_mode());
+ input->set_shader_type(visual_shader->get_shader_type());
+ }
+
// Attempting to connect to the first correct port.
for (int i = 0; i < vsnode->get_output_port_count(); i++) {
if (visual_shader->is_port_types_compatible(vsnode->get_output_port_type(i), input_port_type)) {
@@ -3835,7 +3842,7 @@ VisualShaderEditor::VisualShaderEditor() {
preview_vbox->add_theme_constant_override("separation", 0);
preview_text = memnew(CodeEdit);
- syntax_highlighter.instance();
+ syntax_highlighter.instantiate();
preview_vbox->add_child(preview_text);
preview_text->set_v_size_flags(Control::SIZE_EXPAND_FILL);
preview_text->set_syntax_highlighter(syntax_highlighter);
@@ -4427,10 +4434,10 @@ VisualShaderEditor::VisualShaderEditor() {
undo_redo = EditorNode::get_singleton()->get_undo_redo();
Ref<VisualShaderNodePluginDefault> default_plugin;
- default_plugin.instance();
+ default_plugin.instantiate();
add_plugin(default_plugin);
- graph_plugin.instance();
+ graph_plugin.instantiate();
property_editor = memnew(CustomPropertyEditor);
add_child(property_editor);
@@ -4885,14 +4892,14 @@ void VisualShaderNodePortPreview::_shader_changed() {
String shader_code = shader->generate_preview_shader(type, node, port, default_textures);
Ref<Shader> preview_shader;
- preview_shader.instance();
+ preview_shader.instantiate();
preview_shader->set_code(shader_code);
for (int i = 0; i < default_textures.size(); i++) {
preview_shader->set_default_texture_param(default_textures[i].name, default_textures[i].param);
}
Ref<ShaderMaterial> material;
- material.instance();
+ material.instantiate();
material->set_shader(preview_shader);
//find if a material is also being edited and copy parameters to this one
@@ -4977,7 +4984,7 @@ Ref<Resource> VisualShaderConversionPlugin::convert(const Ref<Resource> &p_resou
ERR_FAIL_COND_V(!vshader.is_valid(), Ref<Resource>());
Ref<Shader> shader;
- shader.instance();
+ shader.instantiate();
String code = vshader->get_code();
shader->set_code(code);
diff --git a/editor/project_export.cpp b/editor/project_export.cpp
index ec65694772..75736a0723 100644
--- a/editor/project_export.cpp
+++ b/editor/project_export.cpp
@@ -1110,9 +1110,9 @@ ProjectExportDialog::ProjectExportDialog() {
exclude_filters->connect("text_changed", callable_mp(this, &ProjectExportDialog::_filter_changed));
script_mode = memnew(OptionButton);
- resources_vb->add_margin_child(TTR("Script Export Mode:"), script_mode);
+ resources_vb->add_margin_child(TTR("GDScript Export Mode:"), script_mode);
script_mode->add_item(TTR("Text"), (int)EditorExportPreset::MODE_SCRIPT_TEXT);
- script_mode->add_item(TTR("Compiled"), (int)EditorExportPreset::MODE_SCRIPT_COMPILED);
+ script_mode->add_item(TTR("Compiled Bytecode (Faster Loading)"), (int)EditorExportPreset::MODE_SCRIPT_COMPILED);
script_mode->connect("item_selected", callable_mp(this, &ProjectExportDialog::_script_export_mode_changed));
// Feature tags.
@@ -1137,12 +1137,12 @@ ProjectExportDialog::ProjectExportDialog() {
enc_pck = memnew(CheckButton);
enc_pck->connect("toggled", callable_mp(this, &ProjectExportDialog::_enc_pck_changed));
- enc_pck->set_text(TTR("Encrypt exported PCK"));
+ enc_pck->set_text(TTR("Encrypt Exported PCK"));
sec_vb->add_child(enc_pck);
enc_directory = memnew(CheckButton);
enc_directory->connect("toggled", callable_mp(this, &ProjectExportDialog::_enc_directory_changed));
- enc_directory->set_text("Encrypt index (file names and info).");
+ enc_directory->set_text("Encrypt Index (File Names and Info)");
sec_vb->add_child(enc_directory);
enc_in_filters = memnew(LineEdit);
@@ -1160,9 +1160,9 @@ ProjectExportDialog::ProjectExportDialog() {
script_key = memnew(LineEdit);
script_key->connect("text_changed", callable_mp(this, &ProjectExportDialog::_script_encryption_key_changed));
script_key_error = memnew(Label);
- script_key_error->set_text("- " + TTR("Invalid Encryption Key (must be 64 characters long)"));
+ script_key_error->set_text("- " + TTR("Invalid Encryption Key (must be 64 hexadecimal characters long)"));
script_key_error->add_theme_color_override("font_color", EditorNode::get_singleton()->get_gui_base()->get_theme_color("error_color", "Editor"));
- sec_vb->add_margin_child(TTR("Encryption Key (256-bits as hex):"), script_key);
+ sec_vb->add_margin_child(TTR("Encryption Key (256-bits as hexadecimal):"), script_key);
sec_vb->add_child(script_key_error);
sections->add_child(sec_vb);
diff --git a/editor/project_manager.cpp b/editor/project_manager.cpp
index fdd114bb1e..50a763f05a 100644
--- a/editor/project_manager.cpp
+++ b/editor/project_manager.cpp
@@ -862,7 +862,7 @@ public:
rasterizer_container->add_child(l);
Container *rshb = memnew(HBoxContainer);
rasterizer_container->add_child(rshb);
- rasterizer_button_group.instance();
+ rasterizer_button_group.instantiate();
Container *rvb = memnew(VBoxContainer);
rvb->set_h_size_flags(Control::SIZE_EXPAND_FILL);
@@ -1145,7 +1145,7 @@ void ProjectList::load_project_icon(int p_index) {
Ref<Texture2D> icon;
if (item.icon != "") {
Ref<Image> img;
- img.instance();
+ img.instantiate();
Error err = img->load(item.icon.replace_first("res://", item.path + "/"));
if (err == OK) {
img->resize(default_icon->get_width(), default_icon->get_height(), Image::INTERPOLATE_LANCZOS);
diff --git a/editor/property_editor.cpp b/editor/property_editor.cpp
index ba3c9aafb4..7414c2d8e6 100644
--- a/editor/property_editor.cpp
+++ b/editor/property_editor.cpp
@@ -192,7 +192,7 @@ void CustomPropertyEditor::_menu_option(int p_which) {
String orig_type = res_orig->get_class();
- Object *inst = ClassDB::instance(orig_type);
+ Object *inst = ClassDB::instantiate(orig_type);
Ref<Resource> res = Ref<Resource>(Object::cast_to<Resource>(inst));
@@ -262,7 +262,7 @@ void CustomPropertyEditor::_menu_option(int p_which) {
return;
}
- Variant obj = ClassDB::instance(intype);
+ Variant obj = ClassDB::instantiate(intype);
if (!obj) {
if (ScriptServer::is_global_class(intype)) {
@@ -908,7 +908,7 @@ bool CustomPropertyEditor::edit(Object *p_owner, const String &p_name, Variant::
}
}
- if (!is_custom_resource && !ClassDB::can_instance(t)) {
+ if (!is_custom_resource && !ClassDB::can_instantiate(t)) {
continue;
}
@@ -1078,7 +1078,7 @@ void CustomPropertyEditor::_type_create_selected(int p_idx) {
String intype = inheritors_array[p_idx];
- Variant obj = ClassDB::instance(intype);
+ Variant obj = ClassDB::instantiate(intype);
if (!obj) {
if (ScriptServer::is_global_class(intype)) {
@@ -1111,7 +1111,7 @@ void CustomPropertyEditor::_node_path_selected(NodePath p_path) {
}
Ref<ViewportTexture> vt;
- vt.instance();
+ vt.instantiate();
vt->set_viewport_path_in_scene(get_tree()->get_edited_scene_root()->get_path_to(to_node));
vt->setup_local_to_scene();
v = vt;
@@ -1268,7 +1268,7 @@ void CustomPropertyEditor::_action_pressed(int p_which) {
String intype = inheritors_array[0];
if (hint == PROPERTY_HINT_RESOURCE_TYPE) {
- Variant obj = ClassDB::instance(intype);
+ Variant obj = ClassDB::instantiate(intype);
if (!obj) {
if (ScriptServer::is_global_class(intype)) {
@@ -1332,7 +1332,7 @@ void CustomPropertyEditor::_action_pressed(int p_which) {
propvalues.push_back(p);
}
- Ref<Resource> res = Ref<Resource>(ClassDB::instance(res_orig->get_class()));
+ Ref<Resource> res = Ref<Resource>(ClassDB::instantiate(res_orig->get_class()));
ERR_FAIL_COND(res.is_null());
@@ -1453,7 +1453,7 @@ void CustomPropertyEditor::_modified(String p_string) {
case Variant::INT: {
String text = TS->parse_number(value_editor[0]->get_text());
Ref<Expression> expr;
- expr.instance();
+ expr.instantiate();
Error err = expr->parse(text);
if (err != OK) {
v = value_editor[0]->get_text().to_int();
@@ -1629,7 +1629,7 @@ void CustomPropertyEditor::_modified(String p_string) {
real_t CustomPropertyEditor::_parse_real_expression(String text) {
Ref<Expression> expr;
- expr.instance();
+ expr.instantiate();
Error err = expr->parse(text);
real_t out;
if (err != OK) {
diff --git a/editor/scene_tree_dock.cpp b/editor/scene_tree_dock.cpp
index 8d6b7f3389..e63818ef07 100644
--- a/editor/scene_tree_dock.cpp
+++ b/editor/scene_tree_dock.cpp
@@ -58,7 +58,7 @@ void SceneTreeDock::_nodes_drag_begin() {
}
void SceneTreeDock::_quick_open() {
- instance_scenes(quick_open->get_selected_files(), scene_tree->get_selected());
+ instantiate_scenes(quick_open->get_selected_files(), scene_tree->get_selected());
}
void SceneTreeDock::_input(Ref<InputEvent> p_event) {
@@ -89,7 +89,7 @@ void SceneTreeDock::_unhandled_key_input(Ref<InputEvent> p_event) {
} else if (ED_IS_SHORTCUT("scene_tree/add_child_node", p_event)) {
_tool_selected(TOOL_NEW);
} else if (ED_IS_SHORTCUT("scene_tree/instance_scene", p_event)) {
- _tool_selected(TOOL_INSTANCE);
+ _tool_selected(TOOL_INSTANTIATE);
} else if (ED_IS_SHORTCUT("scene_tree/expand_collapse_all", p_event)) {
_tool_selected(TOOL_EXPAND_COLLAPSE);
} else if (ED_IS_SHORTCUT("scene_tree/cut_node", p_event)) {
@@ -128,13 +128,13 @@ void SceneTreeDock::_unhandled_key_input(Ref<InputEvent> p_event) {
accept_event();
}
-void SceneTreeDock::instance(const String &p_file) {
+void SceneTreeDock::instantiate(const String &p_file) {
Vector<String> scenes;
scenes.push_back(p_file);
- instance_scenes(scenes, scene_tree->get_selected());
+ instantiate_scenes(scenes, scene_tree->get_selected());
}
-void SceneTreeDock::instance_scenes(const Vector<String> &p_files, Node *p_parent) {
+void SceneTreeDock::instantiate_scenes(const Vector<String> &p_files, Node *p_parent) {
Node *parent = p_parent;
if (!parent) {
@@ -147,18 +147,18 @@ void SceneTreeDock::instance_scenes(const Vector<String> &p_files, Node *p_paren
if (!parent) {
if (p_files.size() == 1) {
- accept->set_text(TTR("No parent to instance a child at."));
+ accept->set_text(TTR("No parent to instantiate a child at."));
} else {
- accept->set_text(TTR("No parent to instance the scenes at."));
+ accept->set_text(TTR("No parent to instantiate the scenes at."));
}
accept->popup_centered();
return;
};
- _perform_instance_scenes(p_files, parent, -1);
+ _perform_instantiate_scenes(p_files, parent, -1);
}
-void SceneTreeDock::_perform_instance_scenes(const Vector<String> &p_files, Node *parent, int p_pos) {
+void SceneTreeDock::_perform_instantiate_scenes(const Vector<String> &p_files, Node *parent, int p_pos) {
ERR_FAIL_COND(!parent);
Vector<Node *> instances;
@@ -175,8 +175,8 @@ void SceneTreeDock::_perform_instance_scenes(const Vector<String> &p_files, Node
break;
}
- Node *instanced_scene = sdata->instance(PackedScene::GEN_EDIT_STATE_INSTANCE);
- if (!instanced_scene) {
+ Node *instantiated_scene = sdata->instantiate(PackedScene::GEN_EDIT_STATE_INSTANCE);
+ if (!instantiated_scene) {
current_option = -1;
accept->set_text(vformat(TTR("Error instancing scene from %s"), p_files[i]));
accept->popup_centered();
@@ -185,7 +185,7 @@ void SceneTreeDock::_perform_instance_scenes(const Vector<String> &p_files, Node
}
if (edited_scene->get_filename() != "") {
- if (_cyclical_dependency_exists(edited_scene->get_filename(), instanced_scene)) {
+ if (_cyclical_dependency_exists(edited_scene->get_filename(), instantiated_scene)) {
accept->set_text(vformat(TTR("Cannot instance the scene '%s' because the current scene exists within one of its nodes."), p_files[i]));
accept->popup_centered();
error = true;
@@ -193,9 +193,9 @@ void SceneTreeDock::_perform_instance_scenes(const Vector<String> &p_files, Node
}
}
- instanced_scene->set_filename(ProjectSettings::get_singleton()->localize_path(p_files[i]));
+ instantiated_scene->set_filename(ProjectSettings::get_singleton()->localize_path(p_files[i]));
- instances.push_back(instanced_scene);
+ instances.push_back(instantiated_scene);
}
if (error) {
@@ -208,19 +208,19 @@ void SceneTreeDock::_perform_instance_scenes(const Vector<String> &p_files, Node
editor_data->get_undo_redo().create_action(TTR("Instance Scene(s)"));
for (int i = 0; i < instances.size(); i++) {
- Node *instanced_scene = instances[i];
+ Node *instantiated_scene = instances[i];
- editor_data->get_undo_redo().add_do_method(parent, "add_child", instanced_scene);
+ editor_data->get_undo_redo().add_do_method(parent, "add_child", instantiated_scene);
if (p_pos >= 0) {
- editor_data->get_undo_redo().add_do_method(parent, "move_child", instanced_scene, p_pos + i);
+ editor_data->get_undo_redo().add_do_method(parent, "move_child", instantiated_scene, p_pos + i);
}
- editor_data->get_undo_redo().add_do_method(instanced_scene, "set_owner", edited_scene);
+ editor_data->get_undo_redo().add_do_method(instantiated_scene, "set_owner", edited_scene);
editor_data->get_undo_redo().add_do_method(editor_selection, "clear");
- editor_data->get_undo_redo().add_do_method(editor_selection, "add_node", instanced_scene);
- editor_data->get_undo_redo().add_do_reference(instanced_scene);
- editor_data->get_undo_redo().add_undo_method(parent, "remove_child", instanced_scene);
+ editor_data->get_undo_redo().add_do_method(editor_selection, "add_node", instantiated_scene);
+ editor_data->get_undo_redo().add_do_reference(instantiated_scene);
+ editor_data->get_undo_redo().add_undo_method(parent, "remove_child", instantiated_scene);
- String new_name = parent->validate_child_name(instanced_scene);
+ String new_name = parent->validate_child_name(instantiated_scene);
EditorDebuggerNode *ed = EditorDebuggerNode::get_singleton();
editor_data->get_undo_redo().add_do_method(ed, "live_debug_instance_node", edited_scene->get_path_to(parent), p_files[i], new_name);
editor_data->get_undo_redo().add_undo_method(ed, "live_debug_remove_node", NodePath(String(edited_scene->get_path_to(parent)).plus_file(new_name)));
@@ -241,8 +241,8 @@ void SceneTreeDock::_replace_with_branch_scene(const String &p_file, Node *base)
return;
}
- Node *instanced_scene = sdata->instance(PackedScene::GEN_EDIT_STATE_INSTANCE);
- if (!instanced_scene) {
+ Node *instantiated_scene = sdata->instantiate(PackedScene::GEN_EDIT_STATE_INSTANCE);
+ if (!instantiated_scene) {
accept->set_text(vformat(TTR("Error instancing scene from %s"), p_file));
accept->popup_centered();
return;
@@ -254,10 +254,10 @@ void SceneTreeDock::_replace_with_branch_scene(const String &p_file, Node *base)
Node *parent = base->get_parent();
int pos = base->get_index();
undo_redo->add_do_method(parent, "remove_child", base);
- undo_redo->add_undo_method(parent, "remove_child", instanced_scene);
- undo_redo->add_do_method(parent, "add_child", instanced_scene);
+ undo_redo->add_undo_method(parent, "remove_child", instantiated_scene);
+ undo_redo->add_do_method(parent, "add_child", instantiated_scene);
undo_redo->add_undo_method(parent, "add_child", base);
- undo_redo->add_do_method(parent, "move_child", instanced_scene, pos);
+ undo_redo->add_do_method(parent, "move_child", instantiated_scene, pos);
undo_redo->add_undo_method(parent, "move_child", base, pos);
List<Node *> owned;
@@ -266,17 +266,17 @@ void SceneTreeDock::_replace_with_branch_scene(const String &p_file, Node *base)
for (List<Node *>::Element *F = owned.front(); F; F = F->next()) {
owners.push_back(F->get());
}
- undo_redo->add_do_method(instanced_scene, "set_owner", edited_scene);
+ undo_redo->add_do_method(instantiated_scene, "set_owner", edited_scene);
undo_redo->add_undo_method(this, "_set_owners", edited_scene, owners);
undo_redo->add_do_method(editor_selection, "clear");
undo_redo->add_undo_method(editor_selection, "clear");
- undo_redo->add_do_method(editor_selection, "add_node", instanced_scene);
+ undo_redo->add_do_method(editor_selection, "add_node", instantiated_scene);
undo_redo->add_undo_method(editor_selection, "add_node", base);
- undo_redo->add_do_property(scene_tree, "set_selected", instanced_scene);
+ undo_redo->add_do_property(scene_tree, "set_selected", instantiated_scene);
undo_redo->add_undo_property(scene_tree, "set_selected", base);
- undo_redo->add_do_reference(instanced_scene);
+ undo_redo->add_do_reference(instantiated_scene);
undo_redo->add_undo_reference(base);
undo_redo->commit_action();
}
@@ -313,7 +313,7 @@ bool SceneTreeDock::_track_inherit(const String &p_target_scene_path, Node *p_de
String path = ss->get_path();
Ref<PackedScene> data = ResourceLoader::load(path);
if (data.is_valid()) {
- p = data->instance(PackedScene::GEN_EDIT_STATE_INSTANCE);
+ p = data->instantiate(PackedScene::GEN_EDIT_STATE_INSTANCE);
if (!p) {
continue;
}
@@ -388,7 +388,7 @@ void SceneTreeDock::_tool_selected(int p_tool, bool p_confirm_override) {
emit_signal("add_node_used");
}
} break;
- case TOOL_INSTANCE: {
+ case TOOL_INSTANTIATE: {
if (!profile_allow_editing) {
break;
}
@@ -400,7 +400,7 @@ void SceneTreeDock::_tool_selected(int p_tool, bool p_confirm_override) {
}
quick_open->popup_dialog("PackedScene", true);
- quick_open->set_title(TTR("Instance Child Scene"));
+ quick_open->set_title(TTR("Instantiate Child Scene"));
if (!p_confirm_override) {
emit_signal("add_node_used");
}
@@ -881,7 +881,7 @@ void SceneTreeDock::_tool_selected(int p_tool, bool p_confirm_override) {
if (node == editor_data->get_edited_scene_root()) {
msg = vformat(TTR("Delete the root node \"%s\"?"), node->get_name());
} else if (node->get_filename() == "" && node->get_child_count() > 0) {
- // Display this message only for non-instanced scenes
+ // Display this message only for non-instantiated scenes
msg = vformat(TTR("Delete node \"%s\" and its children?"), node->get_name());
} else {
msg = vformat(TTR("Delete node \"%s\"?"), node->get_name());
@@ -922,13 +922,13 @@ void SceneTreeDock::_tool_selected(int p_tool, bool p_confirm_override) {
Node *tocopy = selection.front()->get();
if (tocopy == scene) {
- accept->set_text(TTR("Can't save the root node branch as an instanced scene.\nTo create an editable copy of the current scene, duplicate it using the FileSystem dock context menu\nor create an inherited scene using Scene > New Inherited Scene... instead."));
+ accept->set_text(TTR("Can't save the root node branch as an instantiated scene.\nTo create an editable copy of the current scene, duplicate it using the FileSystem dock context menu\nor create an inherited scene using Scene > New Inherited Scene... instead."));
accept->popup_centered();
break;
}
if (tocopy != editor_data->get_edited_scene_root() && tocopy->get_filename() != "") {
- accept->set_text(TTR("Can't save the branch of an already instanced scene.\nTo create a variation of a scene, you can make an inherited scene based on the instanced scene using Scene > New Inherited Scene... instead."));
+ accept->set_text(TTR("Can't save the branch of an already instantiated scene.\nTo create a variation of a scene, you can make an inherited scene based on the instantiated scene using Scene > New Inherited Scene... instead."));
accept->popup_centered();
break;
}
@@ -1103,14 +1103,14 @@ void SceneTreeDock::_tool_selected(int p_tool, bool p_confirm_override) {
if (TOOL_CREATE_FAVORITE == p_tool) {
String name = selected_favorite_root.get_slicec(' ', 0);
if (ScriptServer::is_global_class(name)) {
- new_node = Object::cast_to<Node>(ClassDB::instance(ScriptServer::get_global_class_native_base(name)));
+ new_node = Object::cast_to<Node>(ClassDB::instantiate(ScriptServer::get_global_class_native_base(name)));
Ref<Script> script = ResourceLoader::load(ScriptServer::get_global_class_path(name), "Script");
if (new_node && script.is_valid()) {
new_node->set_script(script);
new_node->set_name(name);
}
} else {
- new_node = Object::cast_to<Node>(ClassDB::instance(selected_favorite_root));
+ new_node = Object::cast_to<Node>(ClassDB::instantiate(selected_favorite_root));
}
if (!new_node) {
@@ -1409,9 +1409,102 @@ void SceneTreeDock::fill_path_renames(Node *p_node, Node *p_new_parent, List<Pai
_fill_path_renames(base_path, new_base_path, p_node, p_renames);
}
+bool SceneTreeDock::_update_node_path(const NodePath &p_root_path, NodePath &p_node_path, List<Pair<NodePath, NodePath>> *p_renames) {
+ NodePath root_path_new = p_root_path;
+ for (List<Pair<NodePath, NodePath>>::Element *F = p_renames->front(); F; F = F->next()) {
+ if (p_root_path == F->get().first) {
+ root_path_new = F->get().second;
+ break;
+ }
+ }
+
+ // Goes through all paths to check if it's matching.
+ for (List<Pair<NodePath, NodePath>>::Element *F = p_renames->front(); F; F = F->next()) {
+ NodePath rel_path_old = p_root_path.rel_path_to(F->get().first);
+
+ // If old path detected, then it needs to be replaced with the new one.
+ if (p_node_path == rel_path_old) {
+ NodePath rel_path_new = F->get().second;
+
+ // If not empty, get new relative path.
+ if (!rel_path_new.is_empty()) {
+ rel_path_new = root_path_new.rel_path_to(rel_path_new);
+ }
+
+ p_node_path = rel_path_new;
+ return true;
+ }
+
+ // Update the node itself if it has a valid node path and has not been deleted.
+ if (p_root_path == F->get().first && p_node_path != NodePath() && F->get().second != NodePath()) {
+ NodePath abs_path = NodePath(String(root_path_new).plus_file(p_node_path)).simplified();
+ NodePath rel_path_new = F->get().second.rel_path_to(abs_path);
+
+ p_node_path = rel_path_new;
+ return true;
+ }
+ }
+
+ return false;
+}
+
+bool SceneTreeDock::_check_node_path_recursive(const NodePath &p_root_path, Variant &p_variant, List<Pair<NodePath, NodePath>> *p_renames) {
+ switch (p_variant.get_type()) {
+ case Variant::NODE_PATH: {
+ NodePath node_path = p_variant;
+ if (_update_node_path(p_root_path, node_path, p_renames)) {
+ p_variant = node_path;
+ return true;
+ }
+ } break;
+
+ case Variant::ARRAY: {
+ Array a = p_variant;
+ bool updated = false;
+ for (int i = 0; i < a.size(); i++) {
+ Variant value = a[i];
+ if (_check_node_path_recursive(p_root_path, value, p_renames)) {
+ if (!updated) {
+ a = a.duplicate(); // Need to duplicate for undo-redo to work.
+ updated = true;
+ }
+ a[i] = value;
+ }
+ }
+ if (updated) {
+ p_variant = a;
+ return true;
+ }
+ } break;
+
+ case Variant::DICTIONARY: {
+ Dictionary d = p_variant;
+ bool updated = false;
+ for (int i = 0; i < d.size(); i++) {
+ Variant value = d.get_value_at_index(i);
+ if (_check_node_path_recursive(p_root_path, value, p_renames)) {
+ if (!updated) {
+ d = d.duplicate(); // Need to duplicate for undo-redo to work.
+ updated = true;
+ }
+ d[d.get_key_at_index(i)] = value;
+ }
+ }
+ if (updated) {
+ p_variant = d;
+ return true;
+ }
+ } break;
+
+ default: {
+ }
+ }
+
+ return false;
+}
+
void SceneTreeDock::perform_node_renames(Node *p_base, List<Pair<NodePath, NodePath>> *p_renames, Map<Ref<Animation>, Set<int>> *r_rem_anims) {
Map<Ref<Animation>, Set<int>> rem_anims;
-
if (!r_rem_anims) {
r_rem_anims = &rem_anims;
}
@@ -1424,60 +1517,22 @@ void SceneTreeDock::perform_node_renames(Node *p_base, List<Pair<NodePath, NodeP
return;
}
- // Renaming node paths used in script instances
- if (p_base->get_script_instance()) {
- ScriptInstance *si = p_base->get_script_instance();
-
- if (si) {
- List<PropertyInfo> properties;
- si->get_property_list(&properties);
- NodePath root_path = p_base->get_path();
-
- for (List<PropertyInfo>::Element *E = properties.front(); E; E = E->next()) {
- String propertyname = E->get().name;
- Variant p = p_base->get(propertyname);
- if (p.get_type() == Variant::NODE_PATH) {
- NodePath root_path_new = root_path;
- for (List<Pair<NodePath, NodePath>>::Element *F = p_renames->front(); F; F = F->next()) {
- if (root_path == F->get().first) {
- root_path_new = F->get().second;
- break;
- }
- }
-
- // Goes through all paths to check if its matching
- for (List<Pair<NodePath, NodePath>>::Element *F = p_renames->front(); F; F = F->next()) {
- NodePath rel_path_old = root_path.rel_path_to(F->get().first);
+ // Renaming node paths used in node properties.
+ List<PropertyInfo> properties;
+ p_base->get_property_list(&properties);
+ NodePath base_root_path = p_base->get_path();
- // if old path detected, then it needs to be replaced with the new one
- if (p == rel_path_old) {
- NodePath rel_path_new = F->get().second;
-
- // if not empty, get new relative path
- if (!rel_path_new.is_empty()) {
- rel_path_new = root_path_new.rel_path_to(F->get().second);
- }
-
- editor_data->get_undo_redo().add_do_property(p_base, propertyname, rel_path_new);
- editor_data->get_undo_redo().add_undo_property(p_base, propertyname, rel_path_old);
-
- p_base->set(propertyname, rel_path_new);
- break;
- }
-
- // update the node itself if it has a valid node path and has not been deleted
- if (root_path == F->get().first && p != NodePath() && F->get().second != NodePath()) {
- NodePath abs_path = NodePath(String(root_path).plus_file(p)).simplified();
- NodePath rel_path_new = F->get().second.rel_path_to(abs_path);
-
- editor_data->get_undo_redo().add_do_property(p_base, propertyname, rel_path_new);
- editor_data->get_undo_redo().add_undo_property(p_base, propertyname, p);
-
- p_base->set(propertyname, rel_path_new);
- }
- }
- }
- }
+ for (List<PropertyInfo>::Element *E = properties.front(); E; E = E->next()) {
+ if (!(E->get().usage & (PROPERTY_USAGE_STORAGE | PROPERTY_USAGE_EDITOR))) {
+ continue;
+ }
+ String propertyname = E->get().name;
+ Variant old_variant = p_base->get(propertyname);
+ Variant updated_variant = old_variant;
+ if (_check_node_path_recursive(base_root_path, updated_variant, p_renames)) {
+ editor_data->get_undo_redo().add_do_property(p_base, propertyname, updated_variant);
+ editor_data->get_undo_redo().add_undo_property(p_base, propertyname, old_variant);
+ p_base->set(propertyname, updated_variant);
}
}
@@ -1640,7 +1695,7 @@ bool SceneTreeDock::_validate_no_instance() {
for (List<Node *>::Element *E = selection.front(); E; E = E->next()) {
if (E->get() != edited_scene && E->get()->get_filename() != "") {
- accept->set_text(TTR("This operation can't be done on instanced scenes."));
+ accept->set_text(TTR("This operation can't be done on instantiated scenes."));
accept->popup_centered();
return false;
}
@@ -2218,7 +2273,7 @@ void SceneTreeDock::replace_node(Node *p_node, Node *p_by_node, bool p_keep_prop
Node *newnode = p_by_node;
if (p_keep_properties) {
- Node *default_oldnode = Object::cast_to<Node>(ClassDB::instance(n->get_class()));
+ Node *default_oldnode = Object::cast_to<Node>(ClassDB::instantiate(n->get_class()));
List<PropertyInfo> pinfo;
n->get_property_list(&pinfo);
@@ -2459,7 +2514,7 @@ void SceneTreeDock::_files_dropped(Vector<String> p_files, NodePath p_to, int p_
int to_pos = -1;
_normalize_drop(node, to_pos, p_type);
- _perform_instance_scenes(p_files, node, to_pos);
+ _perform_instantiate_scenes(p_files, node, to_pos);
}
void SceneTreeDock::_script_dropped(String p_file, NodePath p_to) {
@@ -2542,7 +2597,7 @@ void SceneTreeDock::_tree_rmb(const Vector2 &p_menu_pos) {
menu->clear();
if (profile_allow_editing) {
menu->add_icon_shortcut(get_theme_icon("Add", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/add_child_node"), TOOL_NEW);
- menu->add_icon_shortcut(get_theme_icon("Instance", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/instance_scene"), TOOL_INSTANCE);
+ menu->add_icon_shortcut(get_theme_icon("Instance", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/instance_scene"), TOOL_INSTANTIATE);
}
menu->set_size(Size2(1, 1));
@@ -2575,7 +2630,7 @@ void SceneTreeDock::_tree_rmb(const Vector2 &p_menu_pos) {
}
menu->add_icon_shortcut(get_theme_icon("Add", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/add_child_node"), TOOL_NEW);
- menu->add_icon_shortcut(get_theme_icon("Instance", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/instance_scene"), TOOL_INSTANCE);
+ menu->add_icon_shortcut(get_theme_icon("Instance", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/instance_scene"), TOOL_INSTANTIATE);
}
menu->add_icon_shortcut(get_theme_icon("Collapse", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/expand_collapse_all"), TOOL_EXPAND_COLLAPSE);
menu->add_separator();
@@ -2813,7 +2868,7 @@ void SceneTreeDock::open_add_child_dialog() {
}
void SceneTreeDock::open_instance_child_dialog() {
- _tool_selected(TOOL_INSTANCE, true);
+ _tool_selected(TOOL_INSTANTIATE, true);
}
void SceneTreeDock::add_remote_tree_editor(Control *p_remote) {
@@ -2959,7 +3014,7 @@ void SceneTreeDock::_clear_clipboard() {
void SceneTreeDock::_create_remap_for_node(Node *p_node, Map<RES, RES> &r_remap) {
List<PropertyInfo> props;
p_node->get_property_list(&props);
- bool is_instanced = EditorPropertyRevert::may_node_be_in_instance(p_node);
+ bool is_instantiated = EditorPropertyRevert::may_node_be_in_instance(p_node);
for (List<PropertyInfo>::Element *E = props.front(); E; E = E->next()) {
if (!(E->get().usage & PROPERTY_USAGE_STORAGE)) {
@@ -2970,9 +3025,9 @@ void SceneTreeDock::_create_remap_for_node(Node *p_node, Map<RES, RES> &r_remap)
if (v.is_ref()) {
RES res = v;
if (res.is_valid()) {
- if (is_instanced) {
+ if (is_instantiated) {
Variant orig;
- if (EditorPropertyRevert::get_instanced_node_original_property(p_node, E->get().name, orig)) {
+ if (EditorPropertyRevert::get_instantiated_node_original_property(p_node, E->get().name, orig)) {
if (!EditorPropertyRevert::is_node_property_different(p_node, v, orig)) {
continue;
}
@@ -3020,7 +3075,7 @@ void SceneTreeDock::_bind_methods() {
ClassDB::bind_method(D_METHOD("_input"), &SceneTreeDock::_input);
ClassDB::bind_method(D_METHOD("_update_script_button"), &SceneTreeDock::_update_script_button);
- ClassDB::bind_method(D_METHOD("instance"), &SceneTreeDock::instance);
+ ClassDB::bind_method(D_METHOD("instantiate"), &SceneTreeDock::instantiate);
ClassDB::bind_method(D_METHOD("get_tree_editor"), &SceneTreeDock::get_tree_editor);
ClassDB::bind_method(D_METHOD("replace_node"), &SceneTreeDock::replace_node);
@@ -3054,7 +3109,7 @@ SceneTreeDock::SceneTreeDock(EditorNode *p_editor, Node *p_scene_root, EditorSel
ED_SHORTCUT("scene_tree/rename", TTR("Rename"), KEY_F2);
ED_SHORTCUT("scene_tree/batch_rename", TTR("Batch Rename"), KEY_MASK_SHIFT | KEY_F2);
ED_SHORTCUT("scene_tree/add_child_node", TTR("Add Child Node"), KEY_MASK_CMD | KEY_A);
- ED_SHORTCUT("scene_tree/instance_scene", TTR("Instance Child Scene"), KEY_MASK_CMD | KEY_MASK_SHIFT | KEY_A);
+ ED_SHORTCUT("scene_tree/instance_scene", TTR("Instantiate Child Scene"), KEY_MASK_CMD | KEY_MASK_SHIFT | KEY_A);
ED_SHORTCUT("scene_tree/expand_collapse_all", TTR("Expand/Collapse All"));
ED_SHORTCUT("scene_tree/cut_node", TTR("Cut"), KEY_MASK_CMD | KEY_X);
ED_SHORTCUT("scene_tree/copy_node", TTR("Copy"), KEY_MASK_CMD | KEY_C);
@@ -3083,8 +3138,8 @@ SceneTreeDock::SceneTreeDock(EditorNode *p_editor, Node *p_scene_root, EditorSel
button_instance = memnew(Button);
button_instance->set_flat(true);
- button_instance->connect("pressed", callable_mp(this, &SceneTreeDock::_tool_selected), make_binds(TOOL_INSTANCE, false));
- button_instance->set_tooltip(TTR("Instance a scene file as a Node. Creates an inherited scene if no root node exists."));
+ button_instance->connect("pressed", callable_mp(this, &SceneTreeDock::_tool_selected), make_binds(TOOL_INSTANTIATE, false));
+ button_instance->set_tooltip(TTR("Instantiate a scene file as a Node. Creates an inherited scene if no root node exists."));
button_instance->set_shortcut(ED_GET_SHORTCUT("scene_tree/instance_scene"));
filter_hbc->add_child(button_instance);
diff --git a/editor/scene_tree_dock.h b/editor/scene_tree_dock.h
index 53f31375f8..d2a68ebd2e 100644
--- a/editor/scene_tree_dock.h
+++ b/editor/scene_tree_dock.h
@@ -55,7 +55,7 @@ class SceneTreeDock : public VBoxContainer {
enum Tool {
TOOL_NEW,
- TOOL_INSTANCE,
+ TOOL_INSTANTIATE,
TOOL_EXPAND_COLLAPSE,
TOOL_CUT,
TOOL_COPY,
@@ -224,7 +224,7 @@ class SceneTreeDock : public VBoxContainer {
void _filter_changed(const String &p_filter);
- void _perform_instance_scenes(const Vector<String> &p_files, Node *parent, int p_pos);
+ void _perform_instantiate_scenes(const Vector<String> &p_files, Node *parent, int p_pos);
void _replace_with_branch_scene(const String &p_file, Node *base);
void _file_selected(String p_file);
@@ -247,6 +247,9 @@ class SceneTreeDock : public VBoxContainer {
static SceneTreeDock *singleton;
static void _update_configuration_warning();
+ static bool _update_node_path(const NodePath &p_root_path, NodePath &p_node_path, List<Pair<NodePath, NodePath>> *p_renames);
+ static bool _check_node_path_recursive(const NodePath &p_root_path, Variant &p_variant, List<Pair<NodePath, NodePath>> *p_renames);
+
protected:
void _notification(int p_what);
static void _bind_methods();
@@ -259,8 +262,8 @@ public:
void import_subscene();
void set_edited_scene(Node *p_scene);
- void instance(const String &p_file);
- void instance_scenes(const Vector<String> &p_files, Node *p_parent = nullptr);
+ void instantiate(const String &p_file);
+ void instantiate_scenes(const Vector<String> &p_files, Node *p_parent = nullptr);
void set_selected(Node *p_node, bool p_emit_selected = false);
void fill_path_renames(Node *p_node, Node *p_new_parent, List<Pair<NodePath, NodePath>> *p_renames);
void perform_node_renames(Node *p_base, List<Pair<NodePath, NodePath>> *p_renames, Map<Ref<Animation>, Set<int>> *r_rem_anims = nullptr);
diff --git a/editor/scene_tree_editor.cpp b/editor/scene_tree_editor.cpp
index a5620f8cc5..3aa04e4dc3 100644
--- a/editor/scene_tree_editor.cpp
+++ b/editor/scene_tree_editor.cpp
@@ -944,7 +944,7 @@ Variant SceneTreeEditor::get_drag_data_fw(const Point2 &p_point, Control *p_from
Node *n = get_node(np);
if (n) {
- // Only allow selection if not part of an instanced scene.
+ // Only allow selection if not part of an instantiated scene.
if (!n->get_owner() || n->get_owner() == get_scene_node() || n->get_owner()->get_filename() == String()) {
selected.push_back(n);
icons.push_back(next->get_icon(0));
diff --git a/editor/script_create_dialog.cpp b/editor/script_create_dialog.cpp
index 01743bccab..fdbde8dc5c 100644
--- a/editor/script_create_dialog.cpp
+++ b/editor/script_create_dialog.cpp
@@ -784,6 +784,7 @@ ScriptCreateDialog::ScriptCreateDialog() {
status_panel = memnew(PanelContainer);
status_panel->set_h_size_flags(Control::SIZE_FILL);
+ status_panel->set_v_size_flags(Control::SIZE_EXPAND_FILL);
status_panel->add_child(vb);
/* Spacing */
@@ -795,10 +796,7 @@ ScriptCreateDialog::ScriptCreateDialog() {
vb->add_child(gc);
vb->add_child(spacing);
vb->add_child(status_panel);
- HBoxContainer *hb = memnew(HBoxContainer);
- hb->add_child(vb);
-
- add_child(hb);
+ add_child(vb);
/* Language */
@@ -827,7 +825,7 @@ ScriptCreateDialog::ScriptCreateDialog() {
base_type = "Object";
- hb = memnew(HBoxContainer);
+ HBoxContainer *hb = memnew(HBoxContainer);
hb->set_h_size_flags(Control::SIZE_EXPAND_FILL);
parent_name = memnew(LineEdit);
parent_name->connect("text_changed", callable_mp(this, &ScriptCreateDialog::_parent_name_changed));
diff --git a/editor/settings_config_dialog.cpp b/editor/settings_config_dialog.cpp
index c05a3c2f89..c2c99ed17f 100644
--- a/editor/settings_config_dialog.cpp
+++ b/editor/settings_config_dialog.cpp
@@ -285,7 +285,7 @@ void EditorSettingsDialog::_update_shortcuts() {
event_strings.push_back(I->get()->as_text());
// Only check if the events have been the same so far - once one fails, we don't need to check any more.
- if (same_as_defaults && !key_default_events[count]->shortcut_match(I->get())) {
+ if (same_as_defaults && !key_default_events[count]->is_match(I->get())) {
same_as_defaults = false;
}
count++;
diff --git a/editor/translations/ca.po b/editor/translations/ca.po
index 26e9ac5a45..e9dc4400fc 100644
--- a/editor/translations/ca.po
+++ b/editor/translations/ca.po
@@ -15,12 +15,13 @@
# Carles Pastor Badosa <cpbadosa@gmail.com>, 2021.
# Roberto Pérez <djleizar@gmail.com>, 2021.
# Joel Garcia Cascalló <jocsencat@gmail.com>, 2021.
+# DFC <damiafluixacanals28@gmail.com>, 2021.
msgid ""
msgstr ""
"Project-Id-Version: Godot Engine editor\n"
"POT-Creation-Date: \n"
-"PO-Revision-Date: 2021-05-14 11:19+0000\n"
-"Last-Translator: Joel Garcia Cascalló <jocsencat@gmail.com>\n"
+"PO-Revision-Date: 2021-06-29 12:48+0000\n"
+"Last-Translator: DFC <damiafluixacanals28@gmail.com>\n"
"Language-Team: Catalan <https://hosted.weblate.org/projects/godot-engine/"
"godot/ca/>\n"
"Language: ca\n"
@@ -28,7 +29,7 @@ msgstr ""
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=2; plural=n != 1;\n"
-"X-Generator: Weblate 4.7-dev\n"
+"X-Generator: Weblate 4.7.1-dev\n"
#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp
#: modules/visual_script/visual_script_builtin_funcs.cpp
@@ -1129,7 +1130,7 @@ msgstr "Gràcies de la part de la Comunitat del Godot!"
#: editor/editor_about.cpp editor/editor_node.cpp editor/project_manager.cpp
msgid "Click to copy."
-msgstr ""
+msgstr "Fes click per a copiar."
#: editor/editor_about.cpp
msgid "Godot Engine contributors"
@@ -2331,6 +2332,8 @@ msgid ""
"An error occurred while trying to save the editor layout.\n"
"Make sure the editor's user data path is writable."
msgstr ""
+"S'ha produit un error al desar el diseny de l'editor.\n"
+"Assegura't de que el directori de dades d'usuari de l'editor és editable."
#: editor/editor_node.cpp
msgid ""
@@ -2338,6 +2341,9 @@ msgid ""
"To restore the Default layout to its base settings, use the Delete Layout "
"option and delete the Default layout."
msgstr ""
+"S'ha anulat el diseny per defecte de l'editor.\n"
+"Per a restaurar el Diseny per defecte a la seva configuració base, usa la "
+"opció d'Esborrar el Diseny i esborra el Diseny per defecte."
#: editor/editor_node.cpp
msgid "Layout name not found!"
@@ -2401,7 +2407,7 @@ msgstr "No s'ha definit cap escena per executar."
#: editor/editor_node.cpp
msgid "Save scene before running..."
-msgstr ""
+msgstr "Desar l'escena abans de executar-la..."
#: editor/editor_node.cpp
msgid "Could not start subprocess!"
@@ -3022,7 +3028,7 @@ msgstr "Quant a"
#: editor/editor_node.cpp
msgid "Support Godot Development"
-msgstr ""
+msgstr "Contribueix a el Desenvolupament de Godot"
#: editor/editor_node.cpp
msgid "Play the project."
@@ -3726,6 +3732,8 @@ msgstr "Estat: No s'ha pogut importar. Corregiu el fitxer i torneu a importar."
msgid ""
"Importing has been disabled for this file, so it can't be opened for editing."
msgstr ""
+"La importació s'ha desactivat per a aquest fitxer, per tant aquest no pot "
+"ser obert per a editar."
#: editor/filesystem_dock.cpp
msgid "Cannot move/rename resources root."
@@ -3772,6 +3780,12 @@ msgid ""
"\n"
"Do you wish to overwrite them?"
msgstr ""
+"Els fitxers o directoris següents entren en conflicte amb els elements de la "
+"ubicació de destí '%s':\n"
+"\n"
+"%s\n"
+"\n"
+"Vols reemplaçar-los?"
#: editor/filesystem_dock.cpp
msgid "Renaming file:"
@@ -4136,7 +4150,7 @@ msgstr "Carrega Valors predeterminats"
#: editor/import_dock.cpp
msgid "Keep File (No Import)"
-msgstr ""
+msgstr "Mantenir Fitxer (No Importar)"
#: editor/import_dock.cpp
msgid "%d Files"
diff --git a/editor/translations/cs.po b/editor/translations/cs.po
index 8f1e930115..2557308828 100644
--- a/editor/translations/cs.po
+++ b/editor/translations/cs.po
@@ -30,8 +30,8 @@ msgid ""
msgstr ""
"Project-Id-Version: Godot Engine editor\n"
"POT-Creation-Date: \n"
-"PO-Revision-Date: 2021-05-21 11:33+0000\n"
-"Last-Translator: swifterik <blaha.j502@gmail.com>\n"
+"PO-Revision-Date: 2021-06-25 02:57+0000\n"
+"Last-Translator: Vojtěch Šamla <auzkok@seznam.cz>\n"
"Language-Team: Czech <https://hosted.weblate.org/projects/godot-engine/godot/"
"cs/>\n"
"Language: cs\n"
@@ -39,7 +39,7 @@ msgstr ""
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=3; plural=(n==1) ? 0 : (n>=2 && n<=4) ? 1 : 2;\n"
-"X-Generator: Weblate 4.7-dev\n"
+"X-Generator: Weblate 4.7.1-dev\n"
#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp
#: modules/visual_script/visual_script_builtin_funcs.cpp
@@ -5224,11 +5224,11 @@ msgstr ""
"čtvercové oblasti [0.0, 1.0]."
#: editor/plugins/baked_lightmap_editor_plugin.cpp
-#, fuzzy
msgid ""
"Godot editor was built without ray tracing support, lightmaps can't be baked."
msgstr ""
-"Godot byl sestaven bez podpory ray tracingu, světelné mapy nelze zapéct."
+"Editor Godot byl sestaven bez podpory ray tracingu, světelné mapy nelze "
+"zapéct."
#: editor/plugins/baked_lightmap_editor_plugin.cpp
msgid "Bake Lightmaps"
diff --git a/editor/translations/de.po b/editor/translations/de.po
index 89ffa6e87c..fcf5522011 100644
--- a/editor/translations/de.po
+++ b/editor/translations/de.po
@@ -69,12 +69,14 @@
# El Captian <elcaptian@posteo.me>, 2021.
# Ron Eric Hackländer <mail@roneric.net>, 2021.
# Stephan Kerbl <stephankerbl@gmail.com>, 2021.
+# Philipp Wabnitz <philipp.wabnitz@s2011.tu-chemnitz.de>, 2021.
+# jmih03 <joerni@mail.de>, 2021.
msgid ""
msgstr ""
"Project-Id-Version: Godot Engine editor\n"
"POT-Creation-Date: \n"
-"PO-Revision-Date: 2021-06-07 23:43+0000\n"
-"Last-Translator: Linux User <no-ads@mail.de>\n"
+"PO-Revision-Date: 2021-06-28 22:34+0000\n"
+"Last-Translator: jmih03 <joerni@mail.de>\n"
"Language-Team: German <https://hosted.weblate.org/projects/godot-engine/"
"godot/de/>\n"
"Language: de\n"
@@ -82,7 +84,7 @@ msgstr ""
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=2; plural=n != 1;\n"
-"X-Generator: Weblate 4.7-dev\n"
+"X-Generator: Weblate 4.7.1-dev\n"
#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp
#: modules/visual_script/visual_script_builtin_funcs.cpp
@@ -1189,7 +1191,7 @@ msgstr "Die Godot-Gemeinschaft bedankt sich!"
#: editor/editor_about.cpp editor/editor_node.cpp editor/project_manager.cpp
msgid "Click to copy."
-msgstr ""
+msgstr "Zum kopieren klicken."
#: editor/editor_about.cpp
msgid "Godot Engine contributors"
@@ -7153,7 +7155,7 @@ msgstr ""
#: editor/plugins/script_editor_plugin.cpp editor/script_editor_debugger.cpp
msgid "Debugger"
-msgstr "Testhilfsprogramm"
+msgstr "Debugger"
#: editor/plugins/script_editor_plugin.cpp
msgid "Search Results"
@@ -7416,6 +7418,7 @@ msgid "Play IK"
msgstr "IK abspielen"
#: editor/plugins/spatial_editor_plugin.cpp
+#, fuzzy
msgid "Orthogonal"
msgstr "Orthogonal"
@@ -7661,7 +7664,7 @@ msgid ""
"To zoom further, change the camera's clipping planes (View -> Settings...)"
msgstr ""
"Um weiter zoomen zu können müssen die Kameraausschnittebenen geändert werden "
-"(Anzeige -> Einstellungen… )"
+"(Ansicht -> Einstellungen… )"
#: editor/plugins/spatial_editor_plugin.cpp
msgid ""
@@ -10353,7 +10356,7 @@ msgstr "Ereignis hinzufügen"
#: editor/project_settings_editor.cpp
msgid "Button"
-msgstr "Knopf"
+msgstr "Button"
#: editor/project_settings_editor.cpp
msgid "Left Button."
@@ -12330,6 +12333,8 @@ msgid ""
"Either Debug Keystore, Debug User AND Debug Password settings must be "
"configured OR none of them."
msgstr ""
+"Die drei Einstellungen Debug Keystore, Debug User und Debug Password müssen "
+"entweder alle angegeben, oder alle nicht angegeben sein."
#: platform/android/export/export.cpp
msgid "Debug keystore not configured in the Editor Settings nor in the preset."
@@ -12342,6 +12347,8 @@ msgid ""
"Either Release Keystore, Release User AND Release Password settings must be "
"configured OR none of them."
msgstr ""
+"Die drei Einstellungen Release Keystore, Release User und Release Password "
+"müssen entweder alle angegeben, oder alle nicht angegeben sein."
#: platform/android/export/export.cpp
msgid "Release keystore incorrectly configured in the export preset."
diff --git a/editor/translations/es.po b/editor/translations/es.po
index 660e17420d..7d3288527c 100644
--- a/editor/translations/es.po
+++ b/editor/translations/es.po
@@ -64,12 +64,15 @@
# Juan camilo <jugarciago01@gmail.com>, 2021.
# Manuel González <mgoopazo@gmail.com>, 2021.
# softonicblip <blazeawardspace@gmail.com>, 2021.
+# Ib Quezada <ib@ibquezada.com>, 2021.
+# hiking <joaquinfc@protonmail.com>, 2021.
+# pabloggomez <pgg2733@gmail.com>, 2021.
msgid ""
msgstr ""
"Project-Id-Version: Godot Engine editor\n"
"POT-Creation-Date: \n"
-"PO-Revision-Date: 2021-06-03 22:23+0000\n"
-"Last-Translator: softonicblip <blazeawardspace@gmail.com>\n"
+"PO-Revision-Date: 2021-06-23 21:56+0000\n"
+"Last-Translator: pabloggomez <pgg2733@gmail.com>\n"
"Language-Team: Spanish <https://hosted.weblate.org/projects/godot-engine/"
"godot/es/>\n"
"Language: es\n"
@@ -77,7 +80,7 @@ msgstr ""
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=2; plural=n != 1;\n"
-"X-Generator: Weblate 4.7-dev\n"
+"X-Generator: Weblate 4.7.1-dev\n"
#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp
#: modules/visual_script/visual_script_builtin_funcs.cpp
@@ -1188,7 +1191,7 @@ msgstr "¡Muchas gracias de parte de la comunidad de Godot!"
#: editor/editor_about.cpp editor/editor_node.cpp editor/project_manager.cpp
msgid "Click to copy."
-msgstr ""
+msgstr "Clic para copiar."
#: editor/editor_about.cpp
msgid "Godot Engine contributors"
@@ -4929,8 +4932,8 @@ msgstr "Eliminar el nodo o transición seleccionado/a."
#: editor/plugins/animation_state_machine_editor.cpp
msgid "Toggle autoplay this animation on start, restart or seek to zero."
msgstr ""
-"Act./Desact. reproducción automática de esta animación al comenzar, "
-"reiniciar o hacer seek hasta el cero."
+"Alternar reproducción automática de esta animación al comenzar, reiniciar o "
+"hacer puesta a cero."
#: editor/plugins/animation_state_machine_editor.cpp
msgid "Set the end animation. This is useful for sub-transitions."
@@ -12328,6 +12331,8 @@ msgid ""
"Either Debug Keystore, Debug User AND Debug Password settings must be "
"configured OR none of them."
msgstr ""
+"Deben configurarse los ajustes de Depuración de Claves, Depuración de "
+"Usuarios Y Depuración de Contraseñas O ninguno de ellos."
#: platform/android/export/export.cpp
msgid "Debug keystore not configured in the Editor Settings nor in the preset."
@@ -12339,6 +12344,8 @@ msgid ""
"Either Release Keystore, Release User AND Release Password settings must be "
"configured OR none of them."
msgstr ""
+"Deben configurarse los ajustes de Liberación del Almacén de Claves, "
+"Liberación del Usuario Y Liberación de la Contraseña O ninguno de ellos."
#: platform/android/export/export.cpp
msgid "Release keystore incorrectly configured in the export preset."
diff --git a/editor/translations/es_AR.po b/editor/translations/es_AR.po
index 3c3174f6c8..4bac2d84e9 100644
--- a/editor/translations/es_AR.po
+++ b/editor/translations/es_AR.po
@@ -21,7 +21,7 @@ msgid ""
msgstr ""
"Project-Id-Version: Godot Engine editor\n"
"POT-Creation-Date: \n"
-"PO-Revision-Date: 2021-05-29 13:49+0000\n"
+"PO-Revision-Date: 2021-06-20 13:35+0000\n"
"Last-Translator: Lisandro Lorea <lisandrolorea@gmail.com>\n"
"Language-Team: Spanish (Argentina) <https://hosted.weblate.org/projects/"
"godot-engine/godot/es_AR/>\n"
@@ -30,7 +30,7 @@ msgstr ""
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=2; plural=n != 1;\n"
-"X-Generator: Weblate 4.7-dev\n"
+"X-Generator: Weblate 4.7\n"
#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp
#: modules/visual_script/visual_script_builtin_funcs.cpp
@@ -1138,7 +1138,7 @@ msgstr "Gracias de parte de la comunidad Godot!"
#: editor/editor_about.cpp editor/editor_node.cpp editor/project_manager.cpp
msgid "Click to copy."
-msgstr ""
+msgstr "Click para copiar."
#: editor/editor_about.cpp
msgid "Godot Engine contributors"
@@ -12265,6 +12265,8 @@ msgid ""
"Either Debug Keystore, Debug User AND Debug Password settings must be "
"configured OR none of them."
msgstr ""
+"Deben estar configurados o bien Debug Keystore, Debug User Y Debug Password "
+"o bien ninguno de ellos."
#: platform/android/export/export.cpp
msgid "Debug keystore not configured in the Editor Settings nor in the preset."
@@ -12276,6 +12278,8 @@ msgid ""
"Either Release Keystore, Release User AND Release Password settings must be "
"configured OR none of them."
msgstr ""
+"Deben estar configurados o bien Release Keystore, Release User y Release "
+"Passoword o bien ninguno de ellos."
#: platform/android/export/export.cpp
msgid "Release keystore incorrectly configured in the export preset."
diff --git a/editor/translations/eu.po b/editor/translations/eu.po
index e21c8ce5ba..0f8ef2de33 100644
--- a/editor/translations/eu.po
+++ b/editor/translations/eu.po
@@ -8,7 +8,7 @@
msgid ""
msgstr ""
"Project-Id-Version: Godot Engine editor\n"
-"PO-Revision-Date: 2021-06-14 12:34+0000\n"
+"PO-Revision-Date: 2021-06-20 13:35+0000\n"
"Last-Translator: Erik Zubiria <erik@ezsd.net>\n"
"Language-Team: Basque <https://hosted.weblate.org/projects/godot-engine/"
"godot/eu/>\n"
@@ -16,7 +16,7 @@ msgstr ""
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8-bit\n"
"Plural-Forms: nplurals=2; plural=n != 1;\n"
-"X-Generator: Weblate 4.7-dev\n"
+"X-Generator: Weblate 4.7\n"
#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp
#: modules/visual_script/visual_script_builtin_funcs.cpp
@@ -259,93 +259,93 @@ msgstr "Interpolazio mota"
#: editor/animation_track_editor.cpp
msgid "Loop Wrap Mode (Interpolate end with beginning on loop)"
-msgstr ""
+msgstr "Loop Modu Bildua (bukaera interpolatu looparen hasierarekin)"
#: editor/animation_track_editor.cpp
msgid "Remove this track."
-msgstr ""
+msgstr "Pista hau ezabatu."
#: editor/animation_track_editor.cpp
msgid "Time (s): "
-msgstr ""
+msgstr "Denbora (s): "
#: editor/animation_track_editor.cpp
msgid "Toggle Track Enabled"
-msgstr ""
+msgstr "Pista Akt./Desakt."
#: editor/animation_track_editor.cpp
msgid "Continuous"
-msgstr ""
+msgstr "Etengabea"
#: editor/animation_track_editor.cpp
msgid "Discrete"
-msgstr ""
+msgstr "Diskretua"
#: editor/animation_track_editor.cpp
msgid "Trigger"
-msgstr ""
+msgstr "Kakoa"
#: editor/animation_track_editor.cpp
msgid "Capture"
-msgstr ""
+msgstr "Kaptura"
#: editor/animation_track_editor.cpp
msgid "Nearest"
-msgstr ""
+msgstr "Gertukoena"
#: editor/animation_track_editor.cpp editor/plugins/curve_editor_plugin.cpp
#: editor/property_editor.cpp
msgid "Linear"
-msgstr ""
+msgstr "Lineal"
#: editor/animation_track_editor.cpp
msgid "Cubic"
-msgstr ""
+msgstr "Kubiko"
#: editor/animation_track_editor.cpp
msgid "Clamp Loop Interp"
-msgstr ""
+msgstr "Loop Ebakitzailearen Interp"
#: editor/animation_track_editor.cpp
msgid "Wrap Loop Interp"
-msgstr ""
+msgstr "Loop Inguratzailearen Interp"
#: editor/animation_track_editor.cpp
#: editor/plugins/canvas_item_editor_plugin.cpp
msgid "Insert Key"
-msgstr ""
+msgstr "Sartu Giltza"
#: editor/animation_track_editor.cpp
msgid "Duplicate Key(s)"
-msgstr ""
+msgstr "Bikoiztu Giltza(k)"
#: editor/animation_track_editor.cpp
msgid "Delete Key(s)"
-msgstr ""
+msgstr "Ezabatu Giltza(k)"
#: editor/animation_track_editor.cpp
msgid "Change Animation Update Mode"
-msgstr ""
+msgstr "Animazioaren Eguneraketa Modua Aldatu"
#: editor/animation_track_editor.cpp
msgid "Change Animation Interpolation Mode"
-msgstr ""
+msgstr "Animazioaren Interpolazio Modua Aldatu"
#: editor/animation_track_editor.cpp
msgid "Change Animation Loop Mode"
-msgstr ""
+msgstr "Animazioaren Loop Modua Aldatu"
#: editor/animation_track_editor.cpp
msgid "Remove Anim Track"
-msgstr ""
+msgstr "Ezabatu Animazio Pista"
#: editor/animation_track_editor.cpp
msgid "Create NEW track for %s and insert key?"
-msgstr ""
+msgstr "%s-rentzat pista berria sortu eta giltza sartu?"
#: editor/animation_track_editor.cpp
msgid "Create %d NEW tracks and insert keys?"
-msgstr ""
+msgstr "%d pista berri sortu eta giltzak sartu?"
#: editor/animation_track_editor.cpp editor/create_dialog.cpp
#: editor/editor_audio_buses.cpp editor/editor_feature_profile.cpp
@@ -357,39 +357,41 @@ msgstr ""
#: editor/script_create_dialog.cpp
#: modules/visual_script/visual_script_editor.cpp
msgid "Create"
-msgstr ""
+msgstr "Sortu"
#: editor/animation_track_editor.cpp
msgid "Anim Insert"
-msgstr ""
+msgstr "Animazioa Sartu"
#: editor/animation_track_editor.cpp
msgid "AnimationPlayer can't animate itself, only other players."
-msgstr ""
+msgstr "AnimationPlayer bat ezin da norbera animatu, soilik beste playerrak."
#: editor/animation_track_editor.cpp
msgid "Anim Create & Insert"
-msgstr ""
+msgstr "Animazioa Sortu eta Txertatu"
#: editor/animation_track_editor.cpp
msgid "Anim Insert Track & Key"
-msgstr ""
+msgstr "Pista eta Animazio Giltza Sartu"
#: editor/animation_track_editor.cpp
msgid "Anim Insert Key"
-msgstr ""
+msgstr "Animazio Giltza Sartu"
#: editor/animation_track_editor.cpp
msgid "Change Animation Step"
-msgstr ""
+msgstr "Animazioaren Urratsa Aldatu"
#: editor/animation_track_editor.cpp
msgid "Rearrange Tracks"
-msgstr ""
+msgstr "Pistak Berrantolatu"
#: editor/animation_track_editor.cpp
msgid "Transform tracks only apply to Spatial-based nodes."
msgstr ""
+"Transformazio pistak Spatial-en oinarritutako nodoetan bakarrik aplikatzen "
+"dira."
#: editor/animation_track_editor.cpp
msgid ""
@@ -398,38 +400,42 @@ msgid ""
"-AudioStreamPlayer2D\n"
"-AudioStreamPlayer3D"
msgstr ""
+"Audio pistek era hontako nodoak bakarrik apunta ditzakete:\n"
+"-AudioStreamPlayer\n"
+"-AudioStreamPlayer2D\n"
+"-AudioStreamPlayer3D"
#: editor/animation_track_editor.cpp
msgid "Animation tracks can only point to AnimationPlayer nodes."
-msgstr ""
+msgstr "Animazio pistek AnimationPlayer nodoak bakarrik apunta ditzakete."
#: editor/animation_track_editor.cpp
msgid "An animation player can't animate itself, only other players."
-msgstr ""
+msgstr "Animazio irakurgailua ezin da norbera animatu, bakarrik beste batzuk."
#: editor/animation_track_editor.cpp
msgid "Not possible to add a new track without a root"
-msgstr ""
+msgstr "Ez da posiblea pista berri bat gehitzea sustrairik gabe"
#: editor/animation_track_editor.cpp
msgid "Invalid track for Bezier (no suitable sub-properties)"
-msgstr ""
+msgstr "Bezier-entzat pista baliogabea (ez dago azpipropietate egokirik)"
#: editor/animation_track_editor.cpp
msgid "Add Bezier Track"
-msgstr ""
+msgstr "Gehitu Bezier Pista"
#: editor/animation_track_editor.cpp
msgid "Track path is invalid, so can't add a key."
-msgstr ""
+msgstr "Pistaren bidea baliogabea da, beraz ezin da giltzarik gehitu."
#: editor/animation_track_editor.cpp
msgid "Track is not of type Spatial, can't insert key"
-msgstr ""
+msgstr "Pista ez da Spatial erakoa, ezin da giltza txertatu"
#: editor/animation_track_editor.cpp
msgid "Add Transform Track Key"
-msgstr ""
+msgstr "Gehitu Pistaren Transformazio Giltza"
#: editor/animation_track_editor.cpp
msgid "Add Track Key"
diff --git a/editor/translations/fi.po b/editor/translations/fi.po
index 4b7aad362e..9b0cb63c86 100644
--- a/editor/translations/fi.po
+++ b/editor/translations/fi.po
@@ -16,7 +16,7 @@ msgid ""
msgstr ""
"Project-Id-Version: Godot Engine editor\n"
"POT-Creation-Date: \n"
-"PO-Revision-Date: 2021-05-19 20:16+0000\n"
+"PO-Revision-Date: 2021-06-20 13:35+0000\n"
"Last-Translator: Tapani Niemi <tapani.niemi@kapsi.fi>\n"
"Language-Team: Finnish <https://hosted.weblate.org/projects/godot-engine/"
"godot/fi/>\n"
@@ -25,7 +25,7 @@ msgstr ""
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=2; plural=n != 1;\n"
-"X-Generator: Weblate 4.7-dev\n"
+"X-Generator: Weblate 4.7\n"
#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp
#: modules/visual_script/visual_script_builtin_funcs.cpp
@@ -1120,7 +1120,7 @@ msgstr "Kiitos Godot-yhteisöltä!"
#: editor/editor_about.cpp editor/editor_node.cpp editor/project_manager.cpp
msgid "Click to copy."
-msgstr ""
+msgstr "Napsauta kopioidaksesi."
#: editor/editor_about.cpp
msgid "Godot Engine contributors"
@@ -12204,6 +12204,8 @@ msgid ""
"Either Debug Keystore, Debug User AND Debug Password settings must be "
"configured OR none of them."
msgstr ""
+"Joko Debug Keystore, Debug User JA Debug Password asetukset on kaikki "
+"konfiguroitava TAI ei mitään niistä."
#: platform/android/export/export.cpp
msgid "Debug keystore not configured in the Editor Settings nor in the preset."
@@ -12215,6 +12217,8 @@ msgid ""
"Either Release Keystore, Release User AND Release Password settings must be "
"configured OR none of them."
msgstr ""
+"Joko Release Keystore, Release User JA Release Password asetukset on kaikki "
+"konfiguroitava TAI ei mitään niistä."
#: platform/android/export/export.cpp
msgid "Release keystore incorrectly configured in the export preset."
diff --git a/editor/translations/fr.po b/editor/translations/fr.po
index 577c44aff0..129ab4f687 100644
--- a/editor/translations/fr.po
+++ b/editor/translations/fr.po
@@ -73,7 +73,7 @@
# Kevin Bouancheau <kevin.bouancheau@gmail.com>, 2020.
# LaurentOngaro <laurent@gameamea.com>, 2020.
# Julien Humbert <julroy67@gmail.com>, 2020.
-# Nathan <bonnemainsnathan@gmail.com>, 2020.
+# Nathan <bonnemainsnathan@gmail.com>, 2020, 2021.
# Léo Vincent <l009.vincent@gmail.com>, 2020.
# Joseph Boudou <joseph.boudou@matabio.net>, 2020.
# Vincent Foulon <vincent.foulon80@gmail.com>, 2020.
@@ -84,8 +84,8 @@ msgid ""
msgstr ""
"Project-Id-Version: Godot Engine editor\n"
"POT-Creation-Date: \n"
-"PO-Revision-Date: 2021-04-30 23:03+0000\n"
-"Last-Translator: Julien Vanelian <julienvanelian@hotmail.com>\n"
+"PO-Revision-Date: 2021-06-20 13:35+0000\n"
+"Last-Translator: Nathan <bonnemainsnathan@gmail.com>\n"
"Language-Team: French <https://hosted.weblate.org/projects/godot-engine/"
"godot/fr/>\n"
"Language: fr\n"
@@ -93,7 +93,7 @@ msgstr ""
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=2; plural=n > 1;\n"
-"X-Generator: Weblate 4.7-dev\n"
+"X-Generator: Weblate 4.7\n"
#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp
#: modules/visual_script/visual_script_builtin_funcs.cpp
@@ -1203,7 +1203,7 @@ msgstr "La communauté Godot vous dit merci !"
#: editor/editor_about.cpp editor/editor_node.cpp editor/project_manager.cpp
msgid "Click to copy."
-msgstr ""
+msgstr "Cliquez pour copier."
#: editor/editor_about.cpp
msgid "Godot Engine contributors"
@@ -12370,6 +12370,8 @@ msgid ""
"Either Debug Keystore, Debug User AND Debug Password settings must be "
"configured OR none of them."
msgstr ""
+"Il faut configurer soit les paramètres Debug Keystore, Debug User ET Debug "
+"Password, soit aucun d'entre eux."
#: platform/android/export/export.cpp
msgid "Debug keystore not configured in the Editor Settings nor in the preset."
@@ -12382,6 +12384,8 @@ msgid ""
"Either Release Keystore, Release User AND Release Password settings must be "
"configured OR none of them."
msgstr ""
+"Il faut configurer soit les paramètres Release Keystore, Release User ET "
+"Release Password, soit aucun d'entre eux."
#: platform/android/export/export.cpp
msgid "Release keystore incorrectly configured in the export preset."
diff --git a/editor/translations/ko.po b/editor/translations/ko.po
index f2f3ac1562..9224ef5e65 100644
--- a/editor/translations/ko.po
+++ b/editor/translations/ko.po
@@ -27,8 +27,8 @@ msgid ""
msgstr ""
"Project-Id-Version: Godot Engine editor\n"
"POT-Creation-Date: \n"
-"PO-Revision-Date: 2021-06-11 14:49+0000\n"
-"Last-Translator: Postive_ Cloud <postive12@gmail.com>\n"
+"PO-Revision-Date: 2021-06-20 13:35+0000\n"
+"Last-Translator: Myeongjin Lee <aranet100@gmail.com>\n"
"Language-Team: Korean <https://hosted.weblate.org/projects/godot-engine/"
"godot/ko/>\n"
"Language: ko\n"
@@ -36,7 +36,7 @@ msgstr ""
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=1; plural=0;\n"
-"X-Generator: Weblate 4.7-dev\n"
+"X-Generator: Weblate 4.7\n"
#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp
#: modules/visual_script/visual_script_builtin_funcs.cpp
@@ -1134,7 +1134,7 @@ msgstr "Godot 커뮤니티에서 감사드립니다!"
#: editor/editor_about.cpp editor/editor_node.cpp editor/project_manager.cpp
msgid "Click to copy."
-msgstr ""
+msgstr "클릭하여 복사합니다."
#: editor/editor_about.cpp
msgid "Godot Engine contributors"
@@ -12124,6 +12124,8 @@ msgid ""
"Either Debug Keystore, Debug User AND Debug Password settings must be "
"configured OR none of them."
msgstr ""
+"Debug Keystore, Debug User 및 Debug Password 설정을 구성하거나 그 중 어느 것"
+"도 없어야 합니다."
#: platform/android/export/export.cpp
msgid "Debug keystore not configured in the Editor Settings nor in the preset."
@@ -12134,6 +12136,8 @@ msgid ""
"Either Release Keystore, Release User AND Release Password settings must be "
"configured OR none of them."
msgstr ""
+"Release Keystore, Release User 및 Release Password 설정을 구성하거나 그 중 어"
+"느 것도 없어야 합니다."
#: platform/android/export/export.cpp
msgid "Release keystore incorrectly configured in the export preset."
diff --git a/editor/translations/pl.po b/editor/translations/pl.po
index 9ae69c3d75..83d36da5bb 100644
--- a/editor/translations/pl.po
+++ b/editor/translations/pl.po
@@ -52,7 +52,7 @@ msgid ""
msgstr ""
"Project-Id-Version: Godot Engine editor\n"
"POT-Creation-Date: \n"
-"PO-Revision-Date: 2021-05-19 20:16+0000\n"
+"PO-Revision-Date: 2021-06-20 13:35+0000\n"
"Last-Translator: Tomek <kobewi4e@gmail.com>\n"
"Language-Team: Polish <https://hosted.weblate.org/projects/godot-engine/"
"godot/pl/>\n"
@@ -62,7 +62,7 @@ msgstr ""
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=3; plural=n==1 ? 0 : n%10>=2 && n%10<=4 && (n%100<10 "
"|| n%100>=20) ? 1 : 2;\n"
-"X-Generator: Weblate 4.7-dev\n"
+"X-Generator: Weblate 4.7\n"
#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp
#: modules/visual_script/visual_script_builtin_funcs.cpp
@@ -86,7 +86,7 @@ msgstr "Niewłaściwe dane %i (nie przekazane) w wyrażeniu"
#: core/math/expression.cpp
msgid "self can't be used because instance is null (not passed)"
msgstr ""
-"self nie może być użyte, ponieważ instancja jest nullem (nie przekazano)"
+"self nie może zostać użyte, ponieważ instancja jest nullem (nie przekazana)"
#: core/math/expression.cpp
msgid "Invalid operands to operator %s, %s and %s."
@@ -1159,7 +1159,7 @@ msgstr "Podziękowania od społeczności Godota!"
#: editor/editor_about.cpp editor/editor_node.cpp editor/project_manager.cpp
msgid "Click to copy."
-msgstr ""
+msgstr "Kliknij, by skopiować."
#: editor/editor_about.cpp
msgid "Godot Engine contributors"
@@ -12236,6 +12236,8 @@ msgid ""
"Either Debug Keystore, Debug User AND Debug Password settings must be "
"configured OR none of them."
msgstr ""
+"Albo ustawienia Debug Keystore, Debug User ORAZ Debug Password muszą być "
+"skonfigurowane, ALBO żadne z nich."
#: platform/android/export/export.cpp
msgid "Debug keystore not configured in the Editor Settings nor in the preset."
@@ -12248,6 +12250,8 @@ msgid ""
"Either Release Keystore, Release User AND Release Password settings must be "
"configured OR none of them."
msgstr ""
+"Albo ustawienia Release Keystore, Release User ORAZ Release Password muszą "
+"być skonfigurowane, ALBO żadne z nich."
#: platform/android/export/export.cpp
msgid "Release keystore incorrectly configured in the export preset."
diff --git a/editor/translations/pt_BR.po b/editor/translations/pt_BR.po
index 1fae91fc0d..49a7b43571 100644
--- a/editor/translations/pt_BR.po
+++ b/editor/translations/pt_BR.po
@@ -117,12 +117,13 @@
# Arthur Phillip D. Silva <artphil.dev@gmail.com>, 2021.
# Gustavo HM 102 <gustavohm102@gmail.com>, 2021.
# Douglas Leão <djlsplays@gmail.com>, 2021.
+# PauloFRs <paulofr1@hotmail.com>, 2021.
msgid ""
msgstr ""
"Project-Id-Version: Godot Engine editor\n"
"POT-Creation-Date: 2016-05-30\n"
-"PO-Revision-Date: 2021-06-12 01:23+0000\n"
-"Last-Translator: Douglas Leão <djlsplays@gmail.com>\n"
+"PO-Revision-Date: 2021-06-29 08:04+0000\n"
+"Last-Translator: PauloFRs <paulofr1@hotmail.com>\n"
"Language-Team: Portuguese (Brazil) <https://hosted.weblate.org/projects/"
"godot-engine/godot/pt_BR/>\n"
"Language: pt_BR\n"
@@ -130,7 +131,7 @@ msgstr ""
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=2; plural=n > 1;\n"
-"X-Generator: Weblate 4.7-dev\n"
+"X-Generator: Weblate 4.7.1-dev\n"
#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp
#: modules/visual_script/visual_script_builtin_funcs.cpp
@@ -153,7 +154,7 @@ msgstr "Entrada inválida %i (não passada) na expressão"
#: core/math/expression.cpp
msgid "self can't be used because instance is null (not passed)"
-msgstr "self não pode ser usado porque a instância é nula (não passada)"
+msgstr "self não pode ser usado porque sua instância é null (não passado)"
#: core/math/expression.cpp
msgid "Invalid operands to operator %s, %s and %s."
@@ -1230,7 +1231,7 @@ msgstr "Agradecimentos da comunidade Godot!"
#: editor/editor_about.cpp editor/editor_node.cpp editor/project_manager.cpp
msgid "Click to copy."
-msgstr ""
+msgstr "Clique para copiar."
#: editor/editor_about.cpp
msgid "Godot Engine contributors"
@@ -1911,7 +1912,7 @@ msgstr "Gerenciar perfis de recurso do editor"
#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp
msgid "Select Current Folder"
-msgstr "Selecione a Pasta Atual"
+msgstr "Selecionar a Pasta Atual"
#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp
msgid "File Exists, Overwrite?"
@@ -12328,6 +12329,8 @@ msgid ""
"Either Debug Keystore, Debug User AND Debug Password settings must be "
"configured OR none of them."
msgstr ""
+"As configurações Debug Keystore, Debug User E Debug Password devem ser "
+"configuradas OU nenhuma delas."
#: platform/android/export/export.cpp
msgid "Debug keystore not configured in the Editor Settings nor in the preset."
@@ -12340,6 +12343,8 @@ msgid ""
"Either Release Keystore, Release User AND Release Password settings must be "
"configured OR none of them."
msgstr ""
+"As configurações de Release Keystore, Release User AND Release Password "
+"devem ser definidas OU nenhuma delas."
#: platform/android/export/export.cpp
msgid "Release keystore incorrectly configured in the export preset."
diff --git a/editor/translations/ru.po b/editor/translations/ru.po
index fe4b510539..0da9285077 100644
--- a/editor/translations/ru.po
+++ b/editor/translations/ru.po
@@ -95,12 +95,13 @@
# nec-trou <darya.bilyalova@gmail.com>, 2021.
# IindinAndEdresia <kapitan_pol@inbox.ru>, 2021.
# Bualma Show <appleaidar6@gmail.com>, 2021.
+# enderlorde <madel.laboratories@gmail.com>, 2021.
msgid ""
msgstr ""
"Project-Id-Version: Godot Engine editor\n"
"POT-Creation-Date: \n"
-"PO-Revision-Date: 2021-06-07 23:43+0000\n"
-"Last-Translator: Bualma Show <appleaidar6@gmail.com>\n"
+"PO-Revision-Date: 2021-06-27 07:10+0000\n"
+"Last-Translator: Danil Alexeev <danil@alexeev.xyz>\n"
"Language-Team: Russian <https://hosted.weblate.org/projects/godot-engine/"
"godot/ru/>\n"
"Language: ru\n"
@@ -109,7 +110,7 @@ msgstr ""
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=3; plural=n%10==1 && n%100!=11 ? 0 : n%10>=2 && n"
"%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2;\n"
-"X-Generator: Weblate 4.7-dev\n"
+"X-Generator: Weblate 4.7.1-dev\n"
#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp
#: modules/visual_script/visual_script_builtin_funcs.cpp
@@ -1207,7 +1208,7 @@ msgstr "Спасибо от сообщества Godot!"
#: editor/editor_about.cpp editor/editor_node.cpp editor/project_manager.cpp
msgid "Click to copy."
-msgstr ""
+msgstr "Нажмите, чтобы скопировать."
#: editor/editor_about.cpp
msgid "Godot Engine contributors"
@@ -3154,7 +3155,7 @@ msgstr "Инспектор"
#: editor/editor_node.cpp
msgid "Expand Bottom Panel"
-msgstr "Расширить боковую панель"
+msgstr "Развернуть нижнюю панель"
#: editor/editor_node.cpp
msgid "Output"
@@ -5813,7 +5814,7 @@ msgstr "Кадрировать выбранное"
#: editor/plugins/canvas_item_editor_plugin.cpp
msgid "Preview Canvas Scale"
-msgstr "Предпросмотр Canvas Scale"
+msgstr "Предпросмотр масштаба холста"
#: editor/plugins/canvas_item_editor_plugin.cpp
msgid "Translation mask for inserting keys."
@@ -8437,7 +8438,7 @@ msgstr "Приоритет"
#: editor/plugins/tile_set_editor_plugin.cpp
msgid "Z Index"
-msgstr "Положение по оси Z"
+msgstr "Z-индекс"
#: editor/plugins/tile_set_editor_plugin.cpp
msgid "Region Mode"
@@ -12287,6 +12288,8 @@ msgid ""
"Either Debug Keystore, Debug User AND Debug Password settings must be "
"configured OR none of them."
msgstr ""
+"ЛИБО должны быть заданы настройки Debug Keystore, Debug User И Debug "
+"Password, ЛИБО ни одна из них."
#: platform/android/export/export.cpp
msgid "Debug keystore not configured in the Editor Settings nor in the preset."
@@ -12299,6 +12302,8 @@ msgid ""
"Either Release Keystore, Release User AND Release Password settings must be "
"configured OR none of them."
msgstr ""
+"ЛИБО должны быть заданы настройки Release Keystore, Release User И Release "
+"Password, ЛИБО ни одна из них."
#: platform/android/export/export.cpp
msgid "Release keystore incorrectly configured in the export preset."
diff --git a/editor/translations/uk.po b/editor/translations/uk.po
index 67f369bb15..5f0fe3d721 100644
--- a/editor/translations/uk.po
+++ b/editor/translations/uk.po
@@ -20,7 +20,7 @@ msgid ""
msgstr ""
"Project-Id-Version: Ukrainian (Godot Engine)\n"
"POT-Creation-Date: \n"
-"PO-Revision-Date: 2021-05-18 14:51+0000\n"
+"PO-Revision-Date: 2021-06-20 13:35+0000\n"
"Last-Translator: Yuri Chornoivan <yurchor@ukr.net>\n"
"Language-Team: Ukrainian <https://hosted.weblate.org/projects/godot-engine/"
"godot/uk/>\n"
@@ -30,7 +30,7 @@ msgstr ""
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=3; plural=n%10==1 && n%100!=11 ? 0 : n%10>=2 && n"
"%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2;\n"
-"X-Generator: Weblate 4.7-dev\n"
+"X-Generator: Weblate 4.7\n"
#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp
#: modules/visual_script/visual_script_builtin_funcs.cpp
@@ -1137,7 +1137,7 @@ msgstr "Спасибі від спільноти Godot!"
#: editor/editor_about.cpp editor/editor_node.cpp editor/project_manager.cpp
msgid "Click to copy."
-msgstr ""
+msgstr "Клацніть, щоб скопіювати."
#: editor/editor_about.cpp
msgid "Godot Engine contributors"
@@ -12244,6 +12244,8 @@ msgid ""
"Either Debug Keystore, Debug User AND Debug Password settings must be "
"configured OR none of them."
msgstr ""
+"Має бути налаштовано діагностику сховища ключів, діагностику користувача АБО "
+"діагностику пароля АБО не налаштовано діагностику жодного з цих компонентів."
#: platform/android/export/export.cpp
msgid "Debug keystore not configured in the Editor Settings nor in the preset."
@@ -12256,6 +12258,8 @@ msgid ""
"Either Release Keystore, Release User AND Release Password settings must be "
"configured OR none of them."
msgstr ""
+"Має бути налаштовано параметри сховища ключів випуску, користувача випуску і "
+"пароля випуску або не налаштовано жоден з цих параметрів."
#: platform/android/export/export.cpp
msgid "Release keystore incorrectly configured in the export preset."
diff --git a/editor/translations/zh_CN.po b/editor/translations/zh_CN.po
index 53259bcc6f..6994841e78 100644
--- a/editor/translations/zh_CN.po
+++ b/editor/translations/zh_CN.po
@@ -83,7 +83,7 @@ msgid ""
msgstr ""
"Project-Id-Version: Chinese (Simplified) (Godot Engine)\n"
"POT-Creation-Date: 2018-01-20 12:15+0200\n"
-"PO-Revision-Date: 2021-05-29 13:49+0000\n"
+"PO-Revision-Date: 2021-06-20 13:35+0000\n"
"Last-Translator: Haoyu Qiu <timothyqiu32@gmail.com>\n"
"Language-Team: Chinese (Simplified) <https://hosted.weblate.org/projects/"
"godot-engine/godot/zh_Hans/>\n"
@@ -92,7 +92,7 @@ msgstr ""
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=1; plural=0;\n"
-"X-Generator: Weblate 4.7-dev\n"
+"X-Generator: Weblate 4.7\n"
#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp
#: modules/visual_script/visual_script_builtin_funcs.cpp
@@ -1179,7 +1179,7 @@ msgstr "Godot 社区感谢你!"
#: editor/editor_about.cpp editor/editor_node.cpp editor/project_manager.cpp
msgid "Click to copy."
-msgstr ""
+msgstr "点击复制。"
#: editor/editor_about.cpp
msgid "Godot Engine contributors"
@@ -12043,7 +12043,7 @@ msgstr "未在项目中安装 Android 构建模板。从项目菜单安装它。
msgid ""
"Either Debug Keystore, Debug User AND Debug Password settings must be "
"configured OR none of them."
-msgstr ""
+msgstr "Debug Keystore、Debug User、Debug Password 必须全部填写或者全部留空。"
#: platform/android/export/export.cpp
msgid "Debug keystore not configured in the Editor Settings nor in the preset."
@@ -12054,6 +12054,7 @@ msgid ""
"Either Release Keystore, Release User AND Release Password settings must be "
"configured OR none of them."
msgstr ""
+"Release Keystore、Release User、Release Password 必须全部填写或者全部留空。"
#: platform/android/export/export.cpp
msgid "Release keystore incorrectly configured in the export preset."