diff options
62 files changed, 749 insertions, 658 deletions
diff --git a/core/variant_call.cpp b/core/variant_call.cpp index 6e593a308d..f6ecc506a4 100644 --- a/core/variant_call.cpp +++ b/core/variant_call.cpp @@ -1187,31 +1187,6 @@ Variant Variant::construct(const Variant::Type p_type, const Variant **p_args, i default: return Variant(); } - } else if (p_argcount > 1) { - - _VariantCall::ConstructFunc &c = _VariantCall::construct_funcs[p_type]; - - for (List<_VariantCall::ConstructData>::Element *E = c.constructors.front(); E; E = E->next()) { - const _VariantCall::ConstructData &cd = E->get(); - - if (cd.arg_count != p_argcount) - continue; - - //validate parameters - for (int i = 0; i < cd.arg_count; i++) { - if (!Variant::can_convert(p_args[i]->type, cd.arg_types[i])) { - r_error.error = Variant::CallError::CALL_ERROR_INVALID_ARGUMENT; //no such constructor - r_error.argument = i; - r_error.expected = cd.arg_types[i]; - return Variant(); - } - } - - Variant v; - cd.func(v, p_args); - return v; - } - } else if (p_argcount == 1 && p_args[0]->type == p_type) { return *p_args[0]; //copy construct } else if (p_argcount == 1 && (!p_strict || Variant::can_convert(p_args[0]->type, p_type))) { @@ -1268,6 +1243,30 @@ Variant Variant::construct(const Variant::Type p_type, const Variant **p_args, i case POOL_COLOR_ARRAY: return (PoolColorArray(*p_args[0])); default: return Variant(); } + } else if (p_argcount >= 1) { + + _VariantCall::ConstructFunc &c = _VariantCall::construct_funcs[p_type]; + + for (List<_VariantCall::ConstructData>::Element *E = c.constructors.front(); E; E = E->next()) { + const _VariantCall::ConstructData &cd = E->get(); + + if (cd.arg_count != p_argcount) + continue; + + //validate parameters + for (int i = 0; i < cd.arg_count; i++) { + if (!Variant::can_convert(p_args[i]->type, cd.arg_types[i])) { + r_error.error = Variant::CallError::CALL_ERROR_INVALID_ARGUMENT; //no such constructor + r_error.argument = i; + r_error.expected = cd.arg_types[i]; + return Variant(); + } + } + + Variant v; + cd.func(v, p_args); + return v; + } } r_error.error = Variant::CallError::CALL_ERROR_INVALID_METHOD; //no such constructor return Variant(); diff --git a/doc/classes/CharFXTransform.xml b/doc/classes/CharFXTransform.xml index 399530bb5d..ef9a366c86 100644 --- a/doc/classes/CharFXTransform.xml +++ b/doc/classes/CharFXTransform.xml @@ -11,17 +11,6 @@ <link>https://github.com/Eoin-ONeill-Yokai/Godot-Rich-Text-Effect-Test-Project</link> </tutorials> <methods> - <method name="get_value_or"> - <return type="Variant"> - </return> - <argument index="0" name="key" type="String"> - </argument> - <argument index="1" name="default_value" type="Variant"> - </argument> - <description> - Returns the value for [code]key[/code] in the [member env] [Dictionary], or [code]default_value[/code] if [code]key[/code] isn't defined in [member env]. If the value's type doesn't match [code]default_value[/code]'s type, this method will return [code]default_value[/code]. - </description> - </method> </methods> <members> <member name="absolute_index" type="int" setter="set_absolute_index" getter="get_absolute_index" default="0"> diff --git a/doc/classes/HTTPClient.xml b/doc/classes/HTTPClient.xml index 57d2c6ff96..3a63b2dc07 100644 --- a/doc/classes/HTTPClient.xml +++ b/doc/classes/HTTPClient.xml @@ -112,13 +112,13 @@ Generates a GET/POST application/x-www-form-urlencoded style query string from a provided dictionary, e.g.: [codeblock] var fields = {"username": "user", "password": "pass"} - String query_string = http_client.query_string_from_dict(fields) + var query_string = http_client.query_string_from_dict(fields) # Returns "username=user&password=pass" [/codeblock] Furthermore, if a key has a [code]null[/code] value, only the key itself is added, without equal sign and value. If the value is an array, for each value in it a pair with the same key is added. [codeblock] var fields = {"single": 123, "not_valued": null, "multiple": [22, 33, 44]} - String query_string = http_client.query_string_from_dict(fields) + var query_string = http_client.query_string_from_dict(fields) # Returns "single=123&not_valued&multiple=22&multiple=33&multiple=44" [/codeblock] </description> diff --git a/doc/classes/Mesh.xml b/doc/classes/Mesh.xml index f7b3b0d7ea..d4804930e1 100644 --- a/doc/classes/Mesh.xml +++ b/doc/classes/Mesh.xml @@ -40,6 +40,14 @@ Generate a [TriangleMesh] from the mesh. </description> </method> + <method name="get_aabb" qualifiers="const"> + <return type="AABB"> + </return> + <description> + Returns the smallest [AABB] enclosing this mesh. Not affected by [code]custom_aabb[/code]. + [b]Note:[/b] This is only implemented for [ArrayMesh] and [PrimitiveMesh]. + </description> + </method> <method name="get_faces" qualifiers="const"> <return type="PoolVector3Array"> </return> diff --git a/doc/classes/ProjectSettings.xml b/doc/classes/ProjectSettings.xml index 1d00bb5712..57940a2507 100644 --- a/doc/classes/ProjectSettings.xml +++ b/doc/classes/ProjectSettings.xml @@ -348,7 +348,7 @@ <member name="debug/gdscript/warnings/unused_argument" type="bool" setter="" getter="" default="true"> If [code]true[/code], enables warnings when a function parameter is unused. </member> - <member name="debug/gdscript/warnings/unused_class_variable" type="bool" setter="" getter="" default="true"> + <member name="debug/gdscript/warnings/unused_class_variable" type="bool" setter="" getter="" default="false"> If [code]true[/code], enables warnings when a member variable is unused. </member> <member name="debug/gdscript/warnings/unused_signal" type="bool" setter="" getter="" default="true"> diff --git a/drivers/gles2/rasterizer_canvas_gles2.cpp b/drivers/gles2/rasterizer_canvas_gles2.cpp index 1db1625194..3b2851fbcd 100644 --- a/drivers/gles2/rasterizer_canvas_gles2.cpp +++ b/drivers/gles2/rasterizer_canvas_gles2.cpp @@ -1898,9 +1898,20 @@ void RasterizerCanvasGLES2::canvas_light_shadow_buffer_update(RID p_buffer, cons } state.canvas_shadow_shader.set_uniform(CanvasShadowShaderGLES2::WORLD_MATRIX, instance->xform_cache); - if (cull != instance->cull_cache) { - cull = instance->cull_cache; + VS::CanvasOccluderPolygonCullMode transformed_cull_cache = instance->cull_cache; + + if (transformed_cull_cache != VS::CANVAS_OCCLUDER_POLYGON_CULL_DISABLED && + (p_light_xform.basis_determinant() * instance->xform_cache.basis_determinant()) < 0) { + transformed_cull_cache = + transformed_cull_cache == VS::CANVAS_OCCLUDER_POLYGON_CULL_CLOCKWISE ? + VS::CANVAS_OCCLUDER_POLYGON_CULL_COUNTER_CLOCKWISE : + VS::CANVAS_OCCLUDER_POLYGON_CULL_CLOCKWISE; + } + + if (cull != transformed_cull_cache) { + + cull = transformed_cull_cache; switch (cull) { case VS::CANVAS_OCCLUDER_POLYGON_CULL_DISABLED: { diff --git a/drivers/gles2/shader_compiler_gles2.cpp b/drivers/gles2/shader_compiler_gles2.cpp index 7e9b6fdb82..94cb286b0e 100644 --- a/drivers/gles2/shader_compiler_gles2.cpp +++ b/drivers/gles2/shader_compiler_gles2.cpp @@ -911,7 +911,7 @@ ShaderCompilerGLES2::ShaderCompilerGLES2() { actions[VS::SHADER_CANVAS_ITEM].renames["VERTEX"] = "outvec.xy"; actions[VS::SHADER_CANVAS_ITEM].renames["UV"] = "uv"; - actions[VS::SHADER_CANVAS_ITEM].renames["POINT_SIZE"] = "gl_PointSize"; + actions[VS::SHADER_CANVAS_ITEM].renames["POINT_SIZE"] = "point_size"; actions[VS::SHADER_CANVAS_ITEM].renames["WORLD_MATRIX"] = "modelview_matrix"; actions[VS::SHADER_CANVAS_ITEM].renames["PROJECTION_MATRIX"] = "projection_matrix"; @@ -986,7 +986,7 @@ ShaderCompilerGLES2::ShaderCompilerGLES2() { actions[VS::SHADER_SPATIAL].renames["UV"] = "uv_interp"; actions[VS::SHADER_SPATIAL].renames["UV2"] = "uv2_interp"; actions[VS::SHADER_SPATIAL].renames["COLOR"] = "color_interp"; - actions[VS::SHADER_SPATIAL].renames["POINT_SIZE"] = "gl_PointSize"; + actions[VS::SHADER_SPATIAL].renames["POINT_SIZE"] = "point_size"; // gl_InstanceID is not available in OpenGL ES 2.0 actions[VS::SHADER_SPATIAL].renames["INSTANCE_ID"] = "0"; diff --git a/drivers/gles2/shaders/canvas.glsl b/drivers/gles2/shaders/canvas.glsl index 08548ded17..afce403a9f 100644 --- a/drivers/gles2/shaders/canvas.glsl +++ b/drivers/gles2/shaders/canvas.glsl @@ -149,6 +149,8 @@ void main() { uv = uv_attrib; #endif + float point_size = 1.0; + { vec2 src_vtx = outvec.xy; /* clang-format off */ @@ -158,6 +160,8 @@ VERTEX_SHADER_CODE /* clang-format on */ } + gl_PointSize = point_size; + #if !defined(SKIP_TRANSFORM_USED) outvec = extra_matrix_instance * outvec; outvec = modelview_matrix * outvec; diff --git a/drivers/gles2/shaders/scene.glsl b/drivers/gles2/shaders/scene.glsl index 930d3cd9d4..63eee4eb87 100644 --- a/drivers/gles2/shaders/scene.glsl +++ b/drivers/gles2/shaders/scene.glsl @@ -423,6 +423,8 @@ void main() { #define projection_matrix local_projection_matrix #define world_transform world_matrix + float point_size = 1.0; + { /* clang-format off */ @@ -431,6 +433,7 @@ VERTEX_SHADER_CODE /* clang-format on */ } + gl_PointSize = point_size; vec4 outvec = vertex; // use local coordinates diff --git a/drivers/gles3/rasterizer_canvas_gles3.cpp b/drivers/gles3/rasterizer_canvas_gles3.cpp index c798dff839..1803a3dbbe 100644 --- a/drivers/gles3/rasterizer_canvas_gles3.cpp +++ b/drivers/gles3/rasterizer_canvas_gles3.cpp @@ -1887,9 +1887,20 @@ void RasterizerCanvasGLES3::canvas_light_shadow_buffer_update(RID p_buffer, cons } state.canvas_shadow_shader.set_uniform(CanvasShadowShaderGLES3::WORLD_MATRIX, instance->xform_cache); - if (cull != instance->cull_cache) { - cull = instance->cull_cache; + VS::CanvasOccluderPolygonCullMode transformed_cull_cache = instance->cull_cache; + + if (transformed_cull_cache != VS::CANVAS_OCCLUDER_POLYGON_CULL_DISABLED && + (p_light_xform.basis_determinant() * instance->xform_cache.basis_determinant()) < 0) { + transformed_cull_cache = + transformed_cull_cache == VS::CANVAS_OCCLUDER_POLYGON_CULL_CLOCKWISE ? + VS::CANVAS_OCCLUDER_POLYGON_CULL_COUNTER_CLOCKWISE : + VS::CANVAS_OCCLUDER_POLYGON_CULL_CLOCKWISE; + } + + if (cull != transformed_cull_cache) { + + cull = transformed_cull_cache; switch (cull) { case VS::CANVAS_OCCLUDER_POLYGON_CULL_DISABLED: { diff --git a/drivers/gles3/shader_compiler_gles3.cpp b/drivers/gles3/shader_compiler_gles3.cpp index 7499962da3..e78ecbae34 100644 --- a/drivers/gles3/shader_compiler_gles3.cpp +++ b/drivers/gles3/shader_compiler_gles3.cpp @@ -913,7 +913,7 @@ ShaderCompilerGLES3::ShaderCompilerGLES3() { actions[VS::SHADER_CANVAS_ITEM].renames["VERTEX"] = "outvec.xy"; actions[VS::SHADER_CANVAS_ITEM].renames["UV"] = "uv"; - actions[VS::SHADER_CANVAS_ITEM].renames["POINT_SIZE"] = "gl_PointSize"; + actions[VS::SHADER_CANVAS_ITEM].renames["POINT_SIZE"] = "point_size"; actions[VS::SHADER_CANVAS_ITEM].renames["WORLD_MATRIX"] = "modelview_matrix"; actions[VS::SHADER_CANVAS_ITEM].renames["PROJECTION_MATRIX"] = "projection_matrix"; @@ -970,7 +970,7 @@ ShaderCompilerGLES3::ShaderCompilerGLES3() { actions[VS::SHADER_SPATIAL].renames["UV"] = "uv_interp"; actions[VS::SHADER_SPATIAL].renames["UV2"] = "uv2_interp"; actions[VS::SHADER_SPATIAL].renames["COLOR"] = "color_interp"; - actions[VS::SHADER_SPATIAL].renames["POINT_SIZE"] = "gl_PointSize"; + actions[VS::SHADER_SPATIAL].renames["POINT_SIZE"] = "point_size"; actions[VS::SHADER_SPATIAL].renames["INSTANCE_ID"] = "gl_InstanceID"; //builtins diff --git a/drivers/gles3/shaders/canvas.glsl b/drivers/gles3/shaders/canvas.glsl index 7255b0425c..53f84abf51 100644 --- a/drivers/gles3/shaders/canvas.glsl +++ b/drivers/gles3/shaders/canvas.glsl @@ -150,6 +150,7 @@ void main() { #define extra_matrix extra_matrix_instance + float point_size = 1.0; //for compatibility with the fragment shader we need to use uv here vec2 uv = uv_interp; { @@ -160,6 +161,7 @@ VERTEX_SHADER_CODE /* clang-format on */ } + gl_PointSize = point_size; uv_interp = uv; #ifdef USE_NINEPATCH diff --git a/drivers/gles3/shaders/scene.glsl b/drivers/gles3/shaders/scene.glsl index b4ceb7dcfd..549a36817e 100644 --- a/drivers/gles3/shaders/scene.glsl +++ b/drivers/gles3/shaders/scene.glsl @@ -432,6 +432,8 @@ void main() { } #endif + float point_size = 1.0; + highp mat4 modelview = camera_inverse_matrix * world_matrix; { /* clang-format off */ @@ -441,6 +443,8 @@ VERTEX_SHADER_CODE /* clang-format on */ } + gl_PointSize = point_size; + // using local coordinates (default) #if !defined(SKIP_TRANSFORM_USED) && !defined(VERTEX_WORLD_COORDS_USED) diff --git a/editor/editor_themes.cpp b/editor/editor_themes.cpp index f05c7709d4..6b71ee14d5 100644 --- a/editor/editor_themes.cpp +++ b/editor/editor_themes.cpp @@ -587,11 +587,24 @@ Ref<Theme> create_editor_theme(const Ref<Theme> p_theme) { theme->set_color("icon_color_pressed", "Button", icon_color_pressed); // OptionButton - theme->set_stylebox("normal", "OptionButton", style_widget); - theme->set_stylebox("hover", "OptionButton", style_widget_hover); - theme->set_stylebox("pressed", "OptionButton", style_widget_pressed); - theme->set_stylebox("focus", "OptionButton", style_widget_focus); - theme->set_stylebox("disabled", "OptionButton", style_widget_disabled); + Ref<StyleBoxFlat> style_option_button_normal = style_widget->duplicate(); + Ref<StyleBoxFlat> style_option_button_hover = style_widget_hover->duplicate(); + Ref<StyleBoxFlat> style_option_button_pressed = style_widget_pressed->duplicate(); + Ref<StyleBoxFlat> style_option_button_focus = style_widget_focus->duplicate(); + Ref<StyleBoxFlat> style_option_button_disabled = style_widget_disabled->duplicate(); + + int option_button_arrow_margin = theme->get_icon("GuiOptionArrow", "EditorIcons")->get_size().width + (default_margin_size + 4) * EDSCALE; + style_option_button_normal->set_default_margin(MARGIN_RIGHT, option_button_arrow_margin); + style_option_button_hover->set_default_margin(MARGIN_RIGHT, option_button_arrow_margin); + style_option_button_pressed->set_default_margin(MARGIN_RIGHT, option_button_arrow_margin); + style_option_button_focus->set_default_margin(MARGIN_RIGHT, option_button_arrow_margin); + style_option_button_disabled->set_default_margin(MARGIN_RIGHT, option_button_arrow_margin); + + theme->set_stylebox("normal", "OptionButton", style_option_button_normal); + theme->set_stylebox("hover", "OptionButton", style_option_button_hover); + theme->set_stylebox("pressed", "OptionButton", style_option_button_pressed); + theme->set_stylebox("focus", "OptionButton", style_option_button_focus); + theme->set_stylebox("disabled", "OptionButton", style_option_button_disabled); theme->set_color("font_color", "OptionButton", font_color); theme->set_color("font_color_hover", "OptionButton", font_color_hl); diff --git a/editor/export_template_manager.cpp b/editor/export_template_manager.cpp index 318fee01f2..68ce709090 100644 --- a/editor/export_template_manager.cpp +++ b/editor/export_template_manager.cpp @@ -691,7 +691,7 @@ ExportTemplateManager::ExportTemplateManager() { template_open = memnew(FileDialog); template_open->set_title(TTR("Select Template File")); - template_open->add_filter("*.tpz ; Godot Export Templates"); + template_open->add_filter("*.tpz ; " + TTR("Godot Export Templates")); template_open->set_access(FileDialog::ACCESS_FILESYSTEM); template_open->set_mode(FileDialog::MODE_OPEN_FILE); template_open->connect("file_selected", this, "_install_from_file", varray(true)); diff --git a/editor/plugins/asset_library_editor_plugin.cpp b/editor/plugins/asset_library_editor_plugin.cpp index 95767a96d8..b261ca4712 100644 --- a/editor/plugins/asset_library_editor_plugin.cpp +++ b/editor/plugins/asset_library_editor_plugin.cpp @@ -652,12 +652,12 @@ const char *EditorAssetLibrary::sort_key[SORT_MAX] = { }; const char *EditorAssetLibrary::sort_text[SORT_MAX] = { - "Recently Updated", - "Least Recently Updated", - "Name (A-Z)", - "Name (Z-A)", - "License (A-Z)", // "cost" stores the SPDX license name in the Godot Asset Library. - "License (Z-A)", // "cost" stores the SPDX license name in the Godot Asset Library. + TTRC("Recently Updated"), + TTRC("Least Recently Updated"), + TTRC("Name (A-Z)"), + TTRC("Name (Z-A)"), + TTRC("License (A-Z)"), // "cost" stores the SPDX license name in the Godot Asset Library. + TTRC("License (Z-A)"), // "cost" stores the SPDX license name in the Godot Asset Library. }; const char *EditorAssetLibrary::support_key[SUPPORT_MAX] = { @@ -1383,7 +1383,7 @@ EditorAssetLibrary::EditorAssetLibrary(bool p_templates_only) { search_hb2->add_child(memnew(Label(TTR("Sort:") + " "))); sort = memnew(OptionButton); for (int i = 0; i < SORT_MAX; i++) { - sort->add_item(sort_text[i]); + sort->add_item(TTRGET(sort_text[i])); } search_hb2->add_child(sort); diff --git a/editor/plugins/tile_set_editor_plugin.cpp b/editor/plugins/tile_set_editor_plugin.cpp index 9e873b641b..66935d047b 100644 --- a/editor/plugins/tile_set_editor_plugin.cpp +++ b/editor/plugins/tile_set_editor_plugin.cpp @@ -1176,6 +1176,31 @@ void TileSetEditor::_on_workspace_overlay_draw() { } } +int TileSetEditor::get_grabbed_point(const Vector2 &p_mouse_pos, real_t p_grab_threshold) { + Transform2D xform = workspace->get_transform(); + + int grabbed_point = -1; + real_t min_distance = 1e10; + + for (int i = 0; i < current_shape.size(); i++) { + const real_t distance = xform.xform(current_shape[i]).distance_to(xform.xform(p_mouse_pos)); + if (distance < p_grab_threshold && distance < min_distance) { + min_distance = distance; + grabbed_point = i; + } + } + + return grabbed_point; +} + +bool TileSetEditor::is_within_grabbing_distance_of_first_point(const Vector2 &p_pos, real_t p_grab_threshold) { + Transform2D xform = workspace->get_transform(); + + const real_t distance = xform.xform(current_shape[0]).distance_to(xform.xform(p_pos)); + + return distance < p_grab_threshold; +} + void TileSetEditor::_on_workspace_input(const Ref<InputEvent> &p_ie) { if (tileset.is_null() || !get_current_texture().is_valid()) @@ -1528,18 +1553,19 @@ void TileSetEditor::_on_workspace_input(const Ref<InputEvent> &p_ie) { shape_anchor.x *= (size.x + spacing); shape_anchor.y *= (size.y + spacing); } + const real_t grab_threshold = EDITOR_GET("editors/poly_editor/point_grab_radius"); shape_anchor += current_tile_region.position; if (tools[TOOL_SELECT]->is_pressed()) { if (mb.is_valid()) { if (mb->is_pressed() && mb->get_button_index() == BUTTON_LEFT) { if (edit_mode != EDITMODE_PRIORITY && current_shape.size() > 0) { - for (int i = 0; i < current_shape.size(); i++) { - if ((current_shape[i] - mb->get_position()).length_squared() <= grab_threshold) { - dragging_point = i; - workspace->update(); - return; - } + int grabbed_point = get_grabbed_point(mb->get_position(), grab_threshold); + + if (grabbed_point >= 0) { + dragging_point = grabbed_point; + workspace->update(); + return; } } if ((tileset->tile_get_tile_mode(get_current_tile()) == TileSet::AUTO_TILE || tileset->tile_get_tile_mode(get_current_tile()) == TileSet::ATLAS_TILE) && current_tile_region.has_point(mb->get_position())) { @@ -1633,13 +1659,12 @@ void TileSetEditor::_on_workspace_input(const Ref<InputEvent> &p_ie) { Vector2 pos = mb->get_position(); pos = snap_point(pos); if (creating_shape) { - if (current_shape.size() > 0) { - if ((pos - current_shape[0]).length_squared() <= grab_threshold) { - if (current_shape.size() > 2) { - close_shape(shape_anchor); - workspace->update(); - return; - } + if (current_shape.size() > 2) { + + if (is_within_grabbing_distance_of_first_point(mb->get_position(), grab_threshold)) { + close_shape(shape_anchor); + workspace->update(); + return; } } current_shape.push_back(pos); @@ -1685,12 +1710,15 @@ void TileSetEditor::_on_workspace_input(const Ref<InputEvent> &p_ie) { } } else if (!mb->is_pressed() && mb->get_button_index() == BUTTON_LEFT) { if (creating_shape) { - if ((current_shape[0] - current_shape[1]).length_squared() <= grab_threshold) { + + // if the first two corners are within grabbing distance of one another, expand the rect to fill the tile + if (is_within_grabbing_distance_of_first_point(current_shape[1], grab_threshold)) { current_shape.set(0, snap_point(shape_anchor)); current_shape.set(1, snap_point(shape_anchor + Vector2(current_tile_region.size.x, 0))); current_shape.set(2, snap_point(shape_anchor + current_tile_region.size)); current_shape.set(3, snap_point(shape_anchor + Vector2(0, current_tile_region.size.y))); } + close_shape(shape_anchor); workspace->update(); return; diff --git a/editor/plugins/tile_set_editor_plugin.h b/editor/plugins/tile_set_editor_plugin.h index 944dc04e4e..5ff86000c5 100644 --- a/editor/plugins/tile_set_editor_plugin.h +++ b/editor/plugins/tile_set_editor_plugin.h @@ -244,6 +244,8 @@ private: void update_workspace_tile_mode(); void update_workspace_minsize(); void update_edited_region(const Vector2 &end_point); + int get_grabbed_point(const Vector2 &p_mouse_pos, real_t grab_threshold); + bool is_within_grabbing_distance_of_first_point(const Vector2 &p_pos, real_t p_grab_threshold); int get_current_tile() const; void set_current_tile(int p_id); diff --git a/editor/project_export.cpp b/editor/project_export.cpp index 617ad62d4a..0a9ecca79c 100644 --- a/editor/project_export.cpp +++ b/editor/project_export.cpp @@ -253,9 +253,9 @@ void ProjectExportDialog::_edit_preset(int p_index) { TreeItem *patch_add = patches->create_item(patch_root); patch_add->set_metadata(0, patchlist.size()); if (patchlist.size() == 0) - patch_add->set_text(0, "Add initial export..."); + patch_add->set_text(0, TTR("Add initial export...")); else - patch_add->set_text(0, "Add previous patches..."); + patch_add->set_text(0, TTR("Add previous patches...")); patch_add->add_button(0, get_icon("folder", "FileDialog"), 1); diff --git a/editor/settings_config_dialog.cpp b/editor/settings_config_dialog.cpp index a38c6b98cc..a780b117e1 100644 --- a/editor/settings_config_dialog.cpp +++ b/editor/settings_config_dialog.cpp @@ -233,14 +233,23 @@ void EditorSettingsDialog::_update_shortcuts() { section->set_custom_bg_color(1, get_color("prop_subsection", "Editor")); } - if (shortcut_filter.is_subsequence_ofi(sc->get_name()) || shortcut_filter.is_subsequence_ofi(sc->get_as_text())) { + // Don't match unassigned shortcuts when searching for assigned keys in search results. + // This prevents all unassigned shortcuts from appearing when searching a string like "no". + if (shortcut_filter.is_subsequence_ofi(sc->get_name()) || (sc->get_as_text() != "None" && shortcut_filter.is_subsequence_ofi(sc->get_as_text()))) { TreeItem *item = shortcuts->create_item(section); item->set_text(0, sc->get_name()); item->set_text(1, sc->get_as_text()); + if (!sc->is_shortcut(original) && !(sc->get_shortcut().is_null() && original.is_null())) { item->add_button(1, get_icon("Reload", "EditorIcons"), 2); } + + if (sc->get_as_text() == "None") { + // Fade out unassigned shortcut labels for easier visual grepping. + item->set_custom_color(1, get_color("font_color", "Label") * Color(1, 1, 1, 0.5)); + } + item->add_button(1, get_icon("Edit", "EditorIcons"), 0); item->add_button(1, get_icon("Close", "EditorIcons"), 1); item->set_tooltip(0, E->get()); diff --git a/modules/gdscript/doc_classes/@GDScript.xml b/modules/gdscript/doc_classes/@GDScript.xml index d1f52d2422..502a68cd61 100644 --- a/modules/gdscript/doc_classes/@GDScript.xml +++ b/modules/gdscript/doc_classes/@GDScript.xml @@ -616,9 +616,10 @@ Loads a resource from the filesystem located at [code]path[/code]. [b]Note:[/b] Resource paths can be obtained by right-clicking on a resource in the FileSystem dock and choosing [b]Copy Path[/b]. [codeblock] - # Load a scene called main located in the root of the project directory + # Load a scene called main located in the root of the project directory. var main = load("res://main.tscn") [/codeblock] + [b]Important:[/b] The path must be absolute, a local path will just return [code]null[/code]. </description> </method> <method name="log"> @@ -786,7 +787,7 @@ Returns a resource from the filesystem that is loaded during script parsing. [b]Note:[/b] Resource paths can be obtained by right clicking on a resource in the Assets Panel and choosing "Copy Path". [codeblock] - # Load a scene called main located in the root of the project directory + # Load a scene called main located in the root of the project directory. var main = preload("res://main.tscn") [/codeblock] </description> diff --git a/modules/gdscript/gdscript_editor.cpp b/modules/gdscript/gdscript_editor.cpp index 280bc37dc0..97b8dda6d0 100644 --- a/modules/gdscript/gdscript_editor.cpp +++ b/modules/gdscript/gdscript_editor.cpp @@ -744,6 +744,14 @@ static bool _guess_expression_type(GDScriptCompletionContext &p_context, const G r_type.type.kind = GDScriptParser::DataType::BUILTIN; r_type.type.builtin_type = Variant::ARRAY; } break; + case GDScriptParser::Node::TYPE_CAST: { + const GDScriptParser::CastNode *cn = static_cast<const GDScriptParser::CastNode *>(p_expression); + GDScriptCompletionIdentifier value; + if (_guess_expression_type(p_context, cn->source_node, r_type)) { + r_type.type = cn->get_datatype(); + found = true; + } + } break; case GDScriptParser::Node::TYPE_OPERATOR: { const GDScriptParser::OperatorNode *op = static_cast<const GDScriptParser::OperatorNode *>(p_expression); switch (op->op) { @@ -1232,6 +1240,9 @@ static bool _guess_identifier_type(GDScriptCompletionContext &p_context, const S c.line = last_assign_line; r_type.assigned_expression = last_assigned_expression; if (_guess_expression_type(c, last_assigned_expression, r_type)) { + if (var_type.has_type) { + r_type.type = var_type; + } return true; } } diff --git a/modules/mono/editor/GodotTools/GodotTools.BuildLogger/GodotBuildLogger.cs b/modules/mono/editor/GodotTools/GodotTools.BuildLogger/GodotBuildLogger.cs index a0f6f1ff32..6015cb22b6 100644 --- a/modules/mono/editor/GodotTools/GodotTools.BuildLogger/GodotBuildLogger.cs +++ b/modules/mono/editor/GodotTools/GodotTools.BuildLogger/GodotBuildLogger.cs @@ -18,7 +18,7 @@ namespace GodotTools.BuildLogger if (null == Parameters) throw new LoggerException("Log directory was not set."); - var parameters = Parameters.Split(new[] {';'}); + var parameters = Parameters.Split(new[] { ';' }); string logDir = parameters[0]; diff --git a/modules/mono/editor/GodotTools/GodotTools.BuildLogger/GodotTools.BuildLogger.csproj b/modules/mono/editor/GodotTools/GodotTools.BuildLogger/GodotTools.BuildLogger.csproj index dcfdd83831..1eaa36c1aa 100644 --- a/modules/mono/editor/GodotTools/GodotTools.BuildLogger/GodotTools.BuildLogger.csproj +++ b/modules/mono/editor/GodotTools/GodotTools.BuildLogger/GodotTools.BuildLogger.csproj @@ -1,4 +1,4 @@ -<?xml version="1.0" encoding="utf-8"?> +<?xml version="1.0" encoding="utf-8"?> <Project ToolsVersion="4.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> <Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" /> <PropertyGroup> diff --git a/modules/mono/editor/GodotTools/GodotTools.Core/GodotTools.Core.csproj b/modules/mono/editor/GodotTools/GodotTools.Core/GodotTools.Core.csproj index 24c7cb1573..1974220f2f 100644 --- a/modules/mono/editor/GodotTools/GodotTools.Core/GodotTools.Core.csproj +++ b/modules/mono/editor/GodotTools/GodotTools.Core/GodotTools.Core.csproj @@ -1,4 +1,4 @@ -<?xml version="1.0" encoding="utf-8"?> +<?xml version="1.0" encoding="utf-8"?> <Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> <PropertyGroup> <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration> diff --git a/modules/mono/editor/GodotTools/GodotTools.Core/StringExtensions.cs b/modules/mono/editor/GodotTools/GodotTools.Core/StringExtensions.cs index 8cd7e76303..b531b6aeee 100644 --- a/modules/mono/editor/GodotTools/GodotTools.Core/StringExtensions.cs +++ b/modules/mono/editor/GodotTools/GodotTools.Core/StringExtensions.cs @@ -26,7 +26,7 @@ namespace GodotTools.Core path = path.Replace('\\', '/'); - string[] parts = path.Split(new[] {'/'}, StringSplitOptions.RemoveEmptyEntries); + string[] parts = path.Split(new[] { '/' }, StringSplitOptions.RemoveEmptyEntries); path = string.Join(Path.DirectorySeparatorChar.ToString(), parts).Trim(); @@ -44,7 +44,7 @@ namespace GodotTools.Core public static string CsvEscape(this string value, char delimiter = ',') { - bool hasSpecialChar = value.IndexOfAny(new char[] {'\"', '\n', '\r', delimiter}) != -1; + bool hasSpecialChar = value.IndexOfAny(new char[] { '\"', '\n', '\r', delimiter }) != -1; if (hasSpecialChar) return "\"" + value.Replace("\"", "\"\"") + "\""; @@ -54,8 +54,8 @@ namespace GodotTools.Core public static string ToSafeDirName(this string dirName, bool allowDirSeparator) { - var invalidChars = new List<string> {":", "*", "?", "\"", "<", ">", "|"}; - + var invalidChars = new List<string> { ":", "*", "?", "\"", "<", ">", "|" }; + if (allowDirSeparator) { // Directory separators are allowed, but disallow ".." to avoid going up the filesystem diff --git a/modules/mono/editor/GodotTools/GodotTools.IdeConnection/GodotIdeClient.cs b/modules/mono/editor/GodotTools/GodotTools.IdeConnection/GodotIdeClient.cs index 4f56a8d71b..2bf3b83c75 100644 --- a/modules/mono/editor/GodotTools/GodotTools.IdeConnection/GodotIdeClient.cs +++ b/modules/mono/editor/GodotTools/GodotTools.IdeConnection/GodotIdeClient.cs @@ -106,7 +106,7 @@ namespace GodotTools.IdeConnection try { Logger.LogInfo("Connecting to Godot Ide Server"); - + tcpClient.Connect(IPAddress.Loopback, GodotIdeMetadata.Port); Logger.LogInfo("Connection open with Godot Ide Server"); @@ -130,7 +130,7 @@ namespace GodotTools.IdeConnection public void Start() { Logger.LogInfo("Starting Godot Ide Client"); - + fsWatcher.Changed += OnMetaFileChanged; fsWatcher.Deleted += OnMetaFileDeleted; fsWatcher.EnableRaisingEvents = true; diff --git a/modules/mono/editor/GodotTools/GodotTools.IdeConnection/GodotIdeConnection.cs b/modules/mono/editor/GodotTools/GodotTools.IdeConnection/GodotIdeConnection.cs index e7e81f175e..6441be8d6e 100644 --- a/modules/mono/editor/GodotTools/GodotTools.IdeConnection/GodotIdeConnection.cs +++ b/modules/mono/editor/GodotTools/GodotTools.IdeConnection/GodotIdeConnection.cs @@ -149,7 +149,7 @@ namespace GodotTools.IdeConnection public bool WriteMessage(Message message) { Logger.LogDebug($"Sending message {message}"); - + var messageComposer = new MessageComposer(); messageComposer.AddArgument(message.Id); @@ -201,7 +201,7 @@ namespace GodotTools.IdeConnection clientReader?.Dispose(); clientWriter?.Dispose(); - ((IDisposable) tcpClient)?.Dispose(); + ((IDisposable)tcpClient)?.Dispose(); } } } diff --git a/modules/mono/editor/GodotTools/GodotTools.IdeConnection/GodotTools.IdeConnection.csproj b/modules/mono/editor/GodotTools/GodotTools.IdeConnection/GodotTools.IdeConnection.csproj index 94e525715b..427a26508f 100644 --- a/modules/mono/editor/GodotTools/GodotTools.IdeConnection/GodotTools.IdeConnection.csproj +++ b/modules/mono/editor/GodotTools/GodotTools.IdeConnection/GodotTools.IdeConnection.csproj @@ -1,4 +1,4 @@ -<?xml version="1.0" encoding="utf-8"?> +<?xml version="1.0" encoding="utf-8"?> <Project ToolsVersion="4.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> <Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" /> <PropertyGroup> diff --git a/modules/mono/editor/GodotTools/GodotTools.IdeConnection/MessageComposer.cs b/modules/mono/editor/GodotTools/GodotTools.IdeConnection/MessageComposer.cs index 9e4cd6ec1a..30ffe7a06e 100644 --- a/modules/mono/editor/GodotTools/GodotTools.IdeConnection/MessageComposer.cs +++ b/modules/mono/editor/GodotTools/GodotTools.IdeConnection/MessageComposer.cs @@ -22,14 +22,14 @@ namespace GodotTools.IdeConnection if (quoted) { stringBuilder.Append('"'); - + foreach (char @char in argument) { if (CharsToEscape.Contains(@char)) stringBuilder.Append('\\'); stringBuilder.Append(@char); } - + stringBuilder.Append('"'); } else diff --git a/modules/mono/editor/GodotTools/GodotTools.IdeConnection/MessageParser.cs b/modules/mono/editor/GodotTools/GodotTools.IdeConnection/MessageParser.cs index ed691e481f..4365d69989 100644 --- a/modules/mono/editor/GodotTools/GodotTools.IdeConnection/MessageParser.cs +++ b/modules/mono/editor/GodotTools/GodotTools.IdeConnection/MessageParser.cs @@ -37,7 +37,7 @@ namespace GodotTools.IdeConnection while (i < messageLine.Length) { @char = messageLine[i]; - + if (quoted && @char == '"') { i++; @@ -60,10 +60,10 @@ namespace GodotTools.IdeConnection { stringBuilder.Append(@char); } - + i++; } - + arguments.Add(stringBuilder.ToString()); stringBuilder.Clear(); diff --git a/modules/mono/editor/GodotTools/GodotTools.ProjectEditor/ProjectGenerator.cs b/modules/mono/editor/GodotTools/GodotTools.ProjectEditor/ProjectGenerator.cs index 4f21871f1a..b40d985d51 100644 --- a/modules/mono/editor/GodotTools/GodotTools.ProjectEditor/ProjectGenerator.cs +++ b/modules/mono/editor/GodotTools/GodotTools.ProjectEditor/ProjectGenerator.cs @@ -26,8 +26,8 @@ namespace GodotTools.ProjectEditor mainGroup.SetProperty("BaseIntermediateOutputPath", "obj"); GenAssemblyInfoFile(root, dir, CoreApiProjectName, - new[] {"[assembly: InternalsVisibleTo(\"" + EditorApiProjectName + "\")]"}, - new[] {"System.Runtime.CompilerServices"}); + new[] { "[assembly: InternalsVisibleTo(\"" + EditorApiProjectName + "\")]" }, + new[] { "System.Runtime.CompilerServices" }); foreach (var item in compileItems) { diff --git a/modules/mono/editor/GodotTools/GodotTools.ProjectEditor/packages.config b/modules/mono/editor/GodotTools/GodotTools.ProjectEditor/packages.config index 13915000e4..2db030f9d8 100644 --- a/modules/mono/editor/GodotTools/GodotTools.ProjectEditor/packages.config +++ b/modules/mono/editor/GodotTools/GodotTools.ProjectEditor/packages.config @@ -1,4 +1,4 @@ -<?xml version="1.0" encoding="utf-8"?> +<?xml version="1.0" encoding="utf-8"?> <packages> <package id="DotNet.Glob" version="2.1.1" targetFramework="net45" /> -</packages>
\ No newline at end of file +</packages> diff --git a/modules/mono/editor/GodotTools/GodotTools/BottomPanel.cs b/modules/mono/editor/GodotTools/GodotTools/BottomPanel.cs index 44813f962c..4c76d2abf1 100644 --- a/modules/mono/editor/GodotTools/GodotTools/BottomPanel.cs +++ b/modules/mono/editor/GodotTools/GodotTools/BottomPanel.cs @@ -34,7 +34,7 @@ namespace GodotTools for (int i = 0; i < buildTabs.GetChildCount(); i++) { - var tab = (BuildTab) buildTabs.GetChild(i); + var tab = (BuildTab)buildTabs.GetChild(i); if (tab == null) continue; @@ -120,7 +120,7 @@ namespace GodotTools if (currentTab < 0 || currentTab >= buildTabs.GetTabCount()) throw new InvalidOperationException("No tab selected"); - var buildTab = (BuildTab) buildTabs.GetChild(currentTab); + var buildTab = (BuildTab)buildTabs.GetChild(currentTab); buildTab.WarningsVisible = pressed; buildTab.UpdateIssuesList(); } @@ -132,7 +132,7 @@ namespace GodotTools if (currentTab < 0 || currentTab >= buildTabs.GetTabCount()) throw new InvalidOperationException("No tab selected"); - var buildTab = (BuildTab) buildTabs.GetChild(currentTab); + var buildTab = (BuildTab)buildTabs.GetChild(currentTab); buildTab.ErrorsVisible = pressed; buildTab.UpdateIssuesList(); } @@ -193,7 +193,7 @@ namespace GodotTools int selectedItem = selectedItems[0]; - var buildTab = (BuildTab) buildTabs.GetTabControl(selectedItem); + var buildTab = (BuildTab)buildTabs.GetTabControl(selectedItem); OS.ShellOpen(Path.Combine(buildTab.BuildInfo.LogsDirPath, BuildManager.MsBuildLogFileName)); } @@ -249,14 +249,14 @@ namespace GodotTools var editorBaseControl = editorInterface.GetBaseControl(); - SizeFlagsVertical = (int) SizeFlags.ExpandFill; + SizeFlagsVertical = (int)SizeFlags.ExpandFill; SetAnchorsAndMarginsPreset(LayoutPreset.Wide); panelTabs = new TabContainer { TabAlign = TabContainer.TabAlignEnum.Left, RectMinSize = new Vector2(0, 228) * EditorScale, - SizeFlagsVertical = (int) SizeFlags.ExpandFill + SizeFlagsVertical = (int)SizeFlags.ExpandFill }; panelTabs.AddStyleboxOverride("panel", editorBaseControl.GetStylebox("DebuggerPanel", "EditorStyles")); panelTabs.AddStyleboxOverride("tab_fg", editorBaseControl.GetStylebox("DebuggerTabFG", "EditorStyles")); @@ -268,11 +268,11 @@ namespace GodotTools panelBuildsTab = new VBoxContainer { Name = "Builds".TTR(), - SizeFlagsHorizontal = (int) SizeFlags.ExpandFill + SizeFlagsHorizontal = (int)SizeFlags.ExpandFill }; panelTabs.AddChild(panelBuildsTab); - var toolBarHBox = new HBoxContainer {SizeFlagsHorizontal = (int) SizeFlags.ExpandFill}; + var toolBarHBox = new HBoxContainer { SizeFlagsHorizontal = (int)SizeFlags.ExpandFill }; panelBuildsTab.AddChild(toolBarHBox); var buildProjectBtn = new Button @@ -320,12 +320,12 @@ namespace GodotTools var hsc = new HSplitContainer { - SizeFlagsHorizontal = (int) SizeFlags.ExpandFill, - SizeFlagsVertical = (int) SizeFlags.ExpandFill + SizeFlagsHorizontal = (int)SizeFlags.ExpandFill, + SizeFlagsVertical = (int)SizeFlags.ExpandFill }; panelBuildsTab.AddChild(hsc); - buildTabsList = new ItemList {SizeFlagsHorizontal = (int) SizeFlags.ExpandFill}; + buildTabsList = new ItemList { SizeFlagsHorizontal = (int)SizeFlags.ExpandFill }; buildTabsList.Connect("item_selected", this, nameof(_BuildTabsItemSelected)); buildTabsList.Connect("nothing_selected", this, nameof(_BuildTabsNothingSelected)); hsc.AddChild(buildTabsList); @@ -333,7 +333,7 @@ namespace GodotTools buildTabs = new TabContainer { TabAlign = TabContainer.TabAlignEnum.Left, - SizeFlagsHorizontal = (int) SizeFlags.ExpandFill, + SizeFlagsHorizontal = (int)SizeFlags.ExpandFill, TabsVisible = false }; hsc.AddChild(buildTabs); diff --git a/modules/mono/editor/GodotTools/GodotTools/Build/BuildSystem.cs b/modules/mono/editor/GodotTools/GodotTools/Build/BuildSystem.cs index da90c960e5..43c96d2e30 100644 --- a/modules/mono/editor/GodotTools/GodotTools/Build/BuildSystem.cs +++ b/modules/mono/editor/GodotTools/GodotTools/Build/BuildSystem.cs @@ -46,7 +46,7 @@ namespace GodotTools.Build { if (OS.IsWindows) { - return (BuildManager.BuildTool) EditorSettings.GetSetting("mono/builds/build_tool") + return (BuildManager.BuildTool)EditorSettings.GetSetting("mono/builds/build_tool") == BuildManager.BuildTool.MsBuildMono; } @@ -55,7 +55,7 @@ namespace GodotTools.Build } private static bool PrintBuildOutput => - (bool) EditorSettings.GetSetting("mono/builds/print_build_output"); + (bool)EditorSettings.GetSetting("mono/builds/print_build_output"); private static Process LaunchBuild(string solution, string config, string loggerOutputDir, IEnumerable<string> customProperties = null) { @@ -90,7 +90,7 @@ namespace GodotTools.Build // Needed when running from Developer Command Prompt for VS RemovePlatformVariable(startInfo.EnvironmentVariables); - var process = new Process {StartInfo = startInfo}; + var process = new Process { StartInfo = startInfo }; process.Start(); diff --git a/modules/mono/editor/GodotTools/GodotTools/Build/MsBuildFinder.cs b/modules/mono/editor/GodotTools/GodotTools/Build/MsBuildFinder.cs index ad8a6516ab..c3db52aa9e 100644 --- a/modules/mono/editor/GodotTools/GodotTools/Build/MsBuildFinder.cs +++ b/modules/mono/editor/GodotTools/GodotTools/Build/MsBuildFinder.cs @@ -19,7 +19,7 @@ namespace GodotTools.Build public static string FindMsBuild() { var editorSettings = GodotSharpEditor.Instance.GetEditorInterface().GetEditorSettings(); - var buildTool = (BuildManager.BuildTool) editorSettings.GetSetting("mono/builds/build_tool"); + var buildTool = (BuildManager.BuildTool)editorSettings.GetSetting("mono/builds/build_tool"); if (OS.IsWindows) { @@ -136,11 +136,11 @@ namespace GodotTools.Build string vsWherePath = Environment.GetEnvironmentVariable(Internal.GodotIs32Bits() ? "ProgramFiles" : "ProgramFiles(x86)"); vsWherePath += "\\Microsoft Visual Studio\\Installer\\vswhere.exe"; - var vsWhereArgs = new[] {"-latest", "-products", "*", "-requires", "Microsoft.Component.MSBuild"}; + var vsWhereArgs = new[] { "-latest", "-products", "*", "-requires", "Microsoft.Component.MSBuild" }; var outputArray = new Godot.Collections.Array<string>(); int exitCode = Godot.OS.Execute(vsWherePath, vsWhereArgs, - blocking: true, output: (Godot.Collections.Array) outputArray); + blocking: true, output: (Godot.Collections.Array)outputArray); if (exitCode != 0) return string.Empty; diff --git a/modules/mono/editor/GodotTools/GodotTools/BuildManager.cs b/modules/mono/editor/GodotTools/GodotTools/BuildManager.cs index 217bf5c144..fa6bf4dafd 100644 --- a/modules/mono/editor/GodotTools/GodotTools/BuildManager.cs +++ b/modules/mono/editor/GodotTools/GodotTools/BuildManager.cs @@ -172,7 +172,7 @@ namespace GodotTools } var editorSettings = GodotSharpEditor.Instance.GetEditorInterface().GetEditorSettings(); - var buildTool = (BuildTool) editorSettings.GetSetting("mono/builds/build_tool"); + var buildTool = (BuildTool)editorSettings.GetSetting("mono/builds/build_tool"); using (var pr = new EditorProgress("mono_project_debug_build", "Building project solution...", 1)) { diff --git a/modules/mono/editor/GodotTools/GodotTools/BuildTab.cs b/modules/mono/editor/GodotTools/GodotTools/BuildTab.cs index 807a20d9a1..727581daab 100644 --- a/modules/mono/editor/GodotTools/GodotTools/BuildTab.cs +++ b/modules/mono/editor/GodotTools/GodotTools/BuildTab.cs @@ -113,7 +113,7 @@ namespace GodotTools throw new IndexOutOfRangeException("Item list index out of range"); // Get correct issue idx from issue list - int issueIndex = (int) issuesList.GetItemMetadata(idx); + int issueIndex = (int)issuesList.GetItemMetadata(idx); if (idx < 0 || idx >= issues.Count) throw new IndexOutOfRangeException("Issue index out of range"); @@ -134,7 +134,7 @@ namespace GodotTools if (file.StartsWith("res://")) { - var script = (Script) ResourceLoader.Load(file, typeHint: Internal.CSharpLanguageType); + var script = (Script)ResourceLoader.Load(file, typeHint: Internal.CSharpLanguageType); if (script != null && Internal.ScriptEditorEdit(script, issue.Line, issue.Column)) Internal.EditorNodeShowScriptScreen(); @@ -220,7 +220,7 @@ namespace GodotTools issuesList.Clear(); - var issue = new BuildIssue {Message = cause, Warning = false}; + var issue = new BuildIssue { Message = cause, Warning = false }; ErrorCount += 1; issues.Add(issue); @@ -250,7 +250,7 @@ namespace GodotTools { base._Ready(); - issuesList = new ItemList {SizeFlagsVertical = (int) SizeFlags.ExpandFill}; + issuesList = new ItemList { SizeFlagsVertical = (int)SizeFlags.ExpandFill }; issuesList.Connect("item_activated", this, nameof(_IssueActivated)); AddChild(issuesList); } diff --git a/modules/mono/editor/GodotTools/GodotTools/CsProjOperations.cs b/modules/mono/editor/GodotTools/GodotTools/CsProjOperations.cs index c021a9051e..174509dc5b 100644 --- a/modules/mono/editor/GodotTools/GodotTools/CsProjOperations.cs +++ b/modules/mono/editor/GodotTools/GodotTools/CsProjOperations.cs @@ -26,7 +26,7 @@ namespace GodotTools public static void AddItem(string projectPath, string itemType, string include) { - if (!(bool) GlobalDef("mono/project/auto_update_project", true)) + if (!(bool)GlobalDef("mono/project/auto_update_project", true)) return; ProjectUtils.AddItemToProjectChecked(projectPath, itemType, include); @@ -49,7 +49,7 @@ namespace GodotTools private static ulong ConvertToTimestamp(this DateTime value) { TimeSpan elapsedTime = value - Epoch; - return (ulong) elapsedTime.TotalSeconds; + return (ulong)elapsedTime.TotalSeconds; } public static void GenerateScriptsMetadata(string projectPath, string outputPath) @@ -68,7 +68,7 @@ namespace GodotTools if (oldDict.TryGetValue(projectIncludeFile, out var oldFileVar)) { - var oldFileDict = (Dictionary) oldFileVar; + var oldFileDict = (Dictionary)oldFileVar; if (ulong.TryParse(oldFileDict["modified_time"] as string, out ulong storedModifiedTime)) { @@ -108,7 +108,7 @@ namespace GodotTools if (classDict.Count == 0) continue; // Not found - newDict[projectIncludeFile] = new Dictionary {["modified_time"] = $"{modifiedTime}", ["class"] = classDict}; + newDict[projectIncludeFile] = new Dictionary { ["modified_time"] = $"{modifiedTime}", ["class"] = classDict }; } if (newDict.Count > 0) diff --git a/modules/mono/editor/GodotTools/GodotTools/Export/ExportPlugin.cs b/modules/mono/editor/GodotTools/GodotTools/Export/ExportPlugin.cs index c7e8ea511a..b17a3f4491 100644 --- a/modules/mono/editor/GodotTools/GodotTools/Export/ExportPlugin.cs +++ b/modules/mono/editor/GodotTools/GodotTools/Export/ExportPlugin.cs @@ -54,7 +54,7 @@ namespace GodotTools.Export // TODO What if the source file is not part of the game's C# project - bool includeScriptsContent = (bool) ProjectSettings.GetSetting("mono/export/include_scripts_content"); + bool includeScriptsContent = (bool)ProjectSettings.GetSetting("mono/export/include_scripts_content"); if (!includeScriptsContent) { @@ -114,7 +114,7 @@ namespace GodotTools.Export var dependencies = new Godot.Collections.Dictionary<string, string>(); - var projectDllName = (string) ProjectSettings.GetSetting("application/config/name"); + var projectDllName = (string)ProjectSettings.GetSetting("application/config/name"); if (projectDllName.Empty()) { projectDllName = "UnnamedProject"; @@ -147,7 +147,7 @@ namespace GodotTools.Export string apiConfig = isDebug ? "Debug" : "Release"; string resAssembliesDir = Path.Combine(GodotSharpDirs.ResAssembliesBaseDir, apiConfig); - bool assembliesInsidePck = (bool) ProjectSettings.GetSetting("mono/export/export_assemblies_inside_pck") || outputDataDir == null; + bool assembliesInsidePck = (bool)ProjectSettings.GetSetting("mono/export/export_assemblies_inside_pck") || outputDataDir == null; if (!assembliesInsidePck) { @@ -174,7 +174,7 @@ namespace GodotTools.Export // AOT - if ((bool) ProjectSettings.GetSetting("mono/export/aot/enabled")) + if ((bool)ProjectSettings.GetSetting("mono/export/aot/enabled")) { AotCompileDependencies(features, platform, isDebug, outputDir, outputDataDir, dependencies); } @@ -336,7 +336,7 @@ namespace GodotTools.Export AotCompileAssembly(platform, isDebug, data, assemblyPath, outputFilePathForThisAbi); - AddSharedObject(outputFilePathForThisAbi, tags: new[] {abi}); + AddSharedObject(outputFilePathForThisAbi, tags: new[] { abi }); } } else @@ -377,7 +377,7 @@ namespace GodotTools.Export string compilerCommand = Path.Combine(monoCrossBin, $"{toolPrefix}{monoExeName}{exeExt}"); - bool fullAot = (bool) ProjectSettings.GetSetting("mono/export/aot/full_aot"); + bool fullAot = (bool)ProjectSettings.GetSetting("mono/export/aot/full_aot"); string EscapeOption(string option) => option.Contains(',') ? $"\"{option}\"" : option; string OptionsToString(IEnumerable<string> options) => string.Join(",", options.Select(EscapeOption)); @@ -394,7 +394,7 @@ namespace GodotTools.Export { string abi = data["abi"]; - string androidToolchain = (string) ProjectSettings.GetSetting("mono/export/aot/android_toolchain_path"); + string androidToolchain = (string)ProjectSettings.GetSetting("mono/export/aot/android_toolchain_path"); if (string.IsNullOrEmpty(androidToolchain)) { @@ -419,13 +419,13 @@ namespace GodotTools.Export aotOptions.Add("tool-prefix=" + Path.Combine(androidToolchain, "bin", androidToolPrefixes[abi])); string triple = GetAndroidTriple(abi); - aotOptions.Add ($"mtriple={triple}"); + aotOptions.Add($"mtriple={triple}"); } aotOptions.Add($"outfile={outputFilePath}"); - var extraAotOptions = (string[]) ProjectSettings.GetSetting("mono/export/aot/extra_aot_options"); - var extraOptimizerOptions = (string[]) ProjectSettings.GetSetting("mono/export/aot/extra_optimizer_options"); + var extraAotOptions = (string[])ProjectSettings.GetSetting("mono/export/aot/extra_aot_options"); + var extraOptimizerOptions = (string[])ProjectSettings.GetSetting("mono/export/aot/extra_optimizer_options"); if (extraAotOptions.Length > 0) aotOptions.AddRange(extraAotOptions); @@ -575,7 +575,7 @@ namespace GodotTools.Export private static bool PlatformHasTemplateDir(string platform) { // OSX export templates are contained in a zip, so we place our custom template inside it and let Godot do the rest. - return !new[] {OS.Platforms.OSX, OS.Platforms.Android, OS.Platforms.HTML5}.Contains(platform); + return !new[] { OS.Platforms.OSX, OS.Platforms.Android, OS.Platforms.HTML5 }.Contains(platform); } private static string DeterminePlatformFromFeatures(IEnumerable<string> features) @@ -623,7 +623,7 @@ namespace GodotTools.Export /// </summary> private static bool PlatformRequiresCustomBcl(string platform) { - if (new[] {OS.Platforms.Android, OS.Platforms.HTML5}.Contains(platform)) + if (new[] { OS.Platforms.Android, OS.Platforms.HTML5 }.Contains(platform)) return true; // The 'net_4_x' BCL is not compatible between Windows and the other platforms. @@ -663,7 +663,7 @@ namespace GodotTools.Export { get { - var appName = (string) ProjectSettings.GetSetting("application/config/name"); + var appName = (string)ProjectSettings.GetSetting("application/config/name"); string appNameSafe = appName.ToSafeDirName(allowDirSeparator: false); return $"data_{appNameSafe}"; } diff --git a/modules/mono/editor/GodotTools/GodotTools/GodotSharpEditor.cs b/modules/mono/editor/GodotTools/GodotTools/GodotSharpEditor.cs index 660971d912..147bc95bb8 100644 --- a/modules/mono/editor/GodotTools/GodotTools/GodotSharpEditor.cs +++ b/modules/mono/editor/GodotTools/GodotTools/GodotSharpEditor.cs @@ -44,7 +44,7 @@ namespace GodotTools string resourceDir = ProjectSettings.GlobalizePath("res://"); string path = resourceDir; - string name = (string) ProjectSettings.GetSetting("application/config/name"); + string name = (string)ProjectSettings.GetSetting("application/config/name"); if (name.Empty()) name = "UnnamedProject"; @@ -61,7 +61,7 @@ namespace GodotTools { Guid = guid, PathRelativeToSolution = name + ".csproj", - Configs = new List<string> {"Debug", "Release", "Tools"} + Configs = new List<string> { "Debug", "Release", "Tools" } }; solution.AddNewProject(name, projectInfo); @@ -110,20 +110,20 @@ namespace GodotTools private void _RemoveCreateSlnMenuOption() { - menuPopup.RemoveItem(menuPopup.GetItemIndex((int) MenuOptions.CreateSln)); + menuPopup.RemoveItem(menuPopup.GetItemIndex((int)MenuOptions.CreateSln)); bottomPanelBtn.Show(); } private void _ShowAboutDialog() { - bool showOnStart = (bool) editorSettings.GetSetting("mono/editor/show_info_on_start"); + bool showOnStart = (bool)editorSettings.GetSetting("mono/editor/show_info_on_start"); aboutDialogCheckBox.Pressed = showOnStart; aboutDialog.PopupCenteredMinsize(); } private void _ToggleAboutDialogOnStart(bool enabled) { - bool showOnStart = (bool) editorSettings.GetSetting("mono/editor/show_info_on_start"); + bool showOnStart = (bool)editorSettings.GetSetting("mono/editor/show_info_on_start"); if (showOnStart != enabled) editorSettings.SetSetting("mono/editor/show_info_on_start", enabled); } @@ -160,7 +160,7 @@ namespace GodotTools if (what == NotificationReady) { - bool showInfoDialog = (bool) editorSettings.GetSetting("mono/editor/show_info_on_start"); + bool showInfoDialog = (bool)editorSettings.GetSetting("mono/editor/show_info_on_start"); if (showInfoDialog) { aboutDialog.PopupExclusive = true; @@ -194,7 +194,7 @@ namespace GodotTools [UsedImplicitly] public Error OpenInExternalEditor(Script script, int line, int col) { - var editor = (ExternalEditorId) editorSettings.GetSetting("mono/editor/external_editor"); + var editor = (ExternalEditorId)editorSettings.GetSetting("mono/editor/external_editor"); switch (editor) { @@ -318,7 +318,7 @@ namespace GodotTools [UsedImplicitly] public bool OverridesExternalEditor() { - return (ExternalEditorId) editorSettings.GetSetting("mono/editor/external_editor") != ExternalEditorId.None; + return (ExternalEditorId)editorSettings.GetSetting("mono/editor/external_editor") != ExternalEditorId.None; } public override bool Build() @@ -346,7 +346,7 @@ namespace GodotTools bottomPanelBtn = AddControlToBottomPanel(BottomPanel, "Mono".TTR()); - AddChild(new HotReloadAssemblyWatcher {Name = "HotReloadAssemblyWatcher"}); + AddChild(new HotReloadAssemblyWatcher { Name = "HotReloadAssemblyWatcher" }); menuPopup = new PopupMenu(); menuPopup.Hide(); @@ -356,7 +356,7 @@ namespace GodotTools // TODO: Remove or edit this info dialog once Mono support is no longer in alpha { - menuPopup.AddItem("About C# support".TTR(), (int) MenuOptions.AboutCSharp); + menuPopup.AddItem("About C# support".TTR(), (int)MenuOptions.AboutCSharp); aboutDialog = new AcceptDialog(); editorBaseControl.AddChild(aboutDialog); aboutDialog.WindowTitle = "Important: C# support is not feature-complete"; @@ -379,7 +379,7 @@ namespace GodotTools var aboutLabel = new Label(); aboutHBox.AddChild(aboutLabel); aboutLabel.RectMinSize = new Vector2(600, 150) * EditorScale; - aboutLabel.SizeFlagsVertical = (int) Control.SizeFlags.ExpandFill; + aboutLabel.SizeFlagsVertical = (int)Control.SizeFlags.ExpandFill; aboutLabel.Autowrap = true; aboutLabel.Text = "C# support in Godot Engine is in late alpha stage and, while already usable, " + @@ -394,7 +394,7 @@ namespace GodotTools EditorDef("mono/editor/show_info_on_start", true); // CheckBox in main container - aboutDialogCheckBox = new CheckBox {Text = "Show this warning when starting the editor"}; + aboutDialogCheckBox = new CheckBox { Text = "Show this warning when starting the editor" }; aboutDialogCheckBox.Connect("toggled", this, nameof(_ToggleAboutDialogOnStart)); aboutVBox.AddChild(aboutDialogCheckBox); } @@ -407,7 +407,7 @@ namespace GodotTools else { bottomPanelBtn.Hide(); - menuPopup.AddItem("Create C# solution".TTR(), (int) MenuOptions.CreateSln); + menuPopup.AddItem("Create C# solution".TTR(), (int)MenuOptions.CreateSln); } menuPopup.Connect("id_pressed", this, nameof(_MenuOptionPressed)); @@ -428,22 +428,22 @@ namespace GodotTools if (OS.IsWindows) { - settingsHintStr += $",MonoDevelop:{(int) ExternalEditorId.MonoDevelop}" + - $",Visual Studio Code:{(int) ExternalEditorId.VsCode}" + - $",JetBrains Rider:{(int) ExternalEditorId.Rider}"; + settingsHintStr += $",MonoDevelop:{(int)ExternalEditorId.MonoDevelop}" + + $",Visual Studio Code:{(int)ExternalEditorId.VsCode}" + + $",JetBrains Rider:{(int)ExternalEditorId.Rider}"; } else if (OS.IsOSX) { - settingsHintStr += $",Visual Studio:{(int) ExternalEditorId.VisualStudioForMac}" + - $",MonoDevelop:{(int) ExternalEditorId.MonoDevelop}" + - $",Visual Studio Code:{(int) ExternalEditorId.VsCode}" + - $",JetBrains Rider:{(int) ExternalEditorId.Rider}"; + settingsHintStr += $",Visual Studio:{(int)ExternalEditorId.VisualStudioForMac}" + + $",MonoDevelop:{(int)ExternalEditorId.MonoDevelop}" + + $",Visual Studio Code:{(int)ExternalEditorId.VsCode}" + + $",JetBrains Rider:{(int)ExternalEditorId.Rider}"; } else if (OS.IsUnixLike()) { - settingsHintStr += $",MonoDevelop:{(int) ExternalEditorId.MonoDevelop}" + - $",Visual Studio Code:{(int) ExternalEditorId.VsCode}" + - $",JetBrains Rider:{(int) ExternalEditorId.Rider}"; + settingsHintStr += $",MonoDevelop:{(int)ExternalEditorId.MonoDevelop}" + + $",Visual Studio Code:{(int)ExternalEditorId.VsCode}" + + $",JetBrains Rider:{(int)ExternalEditorId.Rider}"; } editorSettings.AddPropertyInfo(new Godot.Collections.Dictionary diff --git a/modules/mono/editor/GodotTools/GodotTools/GodotTools.csproj b/modules/mono/editor/GodotTools/GodotTools/GodotTools.csproj index be2b70529e..dbd774a66a 100644 --- a/modules/mono/editor/GodotTools/GodotTools/GodotTools.csproj +++ b/modules/mono/editor/GodotTools/GodotTools/GodotTools.csproj @@ -1,4 +1,4 @@ -<?xml version="1.0" encoding="utf-8"?> +<?xml version="1.0" encoding="utf-8"?> <Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> <PropertyGroup> <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration> diff --git a/modules/mono/editor/GodotTools/GodotTools/HotReloadAssemblyWatcher.cs b/modules/mono/editor/GodotTools/GodotTools/HotReloadAssemblyWatcher.cs index 0f6f5ffadc..0ed567afd1 100644 --- a/modules/mono/editor/GodotTools/GodotTools/HotReloadAssemblyWatcher.cs +++ b/modules/mono/editor/GodotTools/GodotTools/HotReloadAssemblyWatcher.cs @@ -38,7 +38,7 @@ namespace GodotTools watchTimer = new Timer { OneShot = false, - WaitTime = (float) EditorDef("mono/assembly_watch_interval_sec", 0.5) + WaitTime = (float)EditorDef("mono/assembly_watch_interval_sec", 0.5) }; watchTimer.Connect("timeout", this, nameof(TimerTimeout)); AddChild(watchTimer); diff --git a/modules/mono/editor/GodotTools/GodotTools/Ides/GodotIdeManager.cs b/modules/mono/editor/GodotTools/GodotTools/Ides/GodotIdeManager.cs index 3213de0127..54f0ffab96 100644 --- a/modules/mono/editor/GodotTools/GodotTools/Ides/GodotIdeManager.cs +++ b/modules/mono/editor/GodotTools/GodotTools/Ides/GodotIdeManager.cs @@ -64,7 +64,7 @@ namespace GodotTools.Ides private void LaunchIde() { - var editor = (ExternalEditorId) GodotSharpEditor.Instance.GetEditorInterface() + var editor = (ExternalEditorId)GodotSharpEditor.Instance.GetEditorInterface() .GetEditorSettings().GetSetting("mono/editor/external_editor"); switch (editor) diff --git a/modules/mono/editor/GodotTools/GodotTools/Ides/GodotIdeServer.cs b/modules/mono/editor/GodotTools/GodotTools/Ides/GodotIdeServer.cs index 309b917c71..72676a8b24 100644 --- a/modules/mono/editor/GodotTools/GodotTools/Ides/GodotIdeServer.cs +++ b/modules/mono/editor/GodotTools/GodotTools/Ides/GodotIdeServer.cs @@ -45,7 +45,7 @@ namespace GodotTools.Ides listener = new TcpListener(new IPEndPoint(IPAddress.Loopback, port: 0)); listener.Start(); - int port = ((IPEndPoint) listener.Server.LocalEndPoint).Port; + int port = ((IPEndPoint)listener.Server.LocalEndPoint).Port; using (var metaFileWriter = new StreamWriter(metaFile, Encoding.UTF8)) { metaFileWriter.WriteLine(port); @@ -57,7 +57,7 @@ namespace GodotTools.Ides public void StartServer() { - var serverThread = new Thread(RunServerThread) {Name = "Godot Ide Connection Server"}; + var serverThread = new Thread(RunServerThread) { Name = "Godot Ide Connection Server" }; serverThread.Start(); } diff --git a/modules/mono/editor/GodotTools/GodotTools/Ides/Rider/.editorconfig b/modules/mono/editor/GodotTools/GodotTools/Ides/Rider/.editorconfig deleted file mode 100644 index aca19790ca..0000000000 --- a/modules/mono/editor/GodotTools/GodotTools/Ides/Rider/.editorconfig +++ /dev/null @@ -1,6 +0,0 @@ -root = true - -[*] -indent_style = space -indent_size = 2 -end_of_line = lf
\ No newline at end of file diff --git a/modules/mono/editor/GodotTools/GodotTools/Ides/Rider/RiderPathLocator.cs b/modules/mono/editor/GodotTools/GodotTools/Ides/Rider/RiderPathLocator.cs index 901ade71e3..b752535dcb 100644 --- a/modules/mono/editor/GodotTools/GodotTools/Ides/Rider/RiderPathLocator.cs +++ b/modules/mono/editor/GodotTools/GodotTools/Ides/Rider/RiderPathLocator.cs @@ -1,4 +1,4 @@ -using System; +using System; using System.Collections.Generic; using System.IO; using System.Linq; @@ -14,403 +14,403 @@ using OS = GodotTools.Utils.OS; namespace GodotTools.Ides.Rider { - /// <summary> - /// This code is a modified version of the JetBrains resharper-unity plugin listed under Apache License 2.0 license: - /// https://github.com/JetBrains/resharper-unity/blob/master/unity/JetBrains.Rider.Unity.Editor/EditorPlugin/RiderPathLocator.cs - /// </summary> - public static class RiderPathLocator - { - public static RiderInfo[] GetAllRiderPaths() + /// <summary> + /// This code is a modified version of the JetBrains resharper-unity plugin listed under Apache License 2.0 license: + /// https://github.com/JetBrains/resharper-unity/blob/master/unity/JetBrains.Rider.Unity.Editor/EditorPlugin/RiderPathLocator.cs + /// </summary> + public static class RiderPathLocator { - try - { - if (OS.IsWindows) + public static RiderInfo[] GetAllRiderPaths() { - return CollectRiderInfosWindows(); - } - if (OS.IsOSX) - { - return CollectRiderInfosMac(); - } - if (OS.IsUnixLike()) - { - return CollectAllRiderPathsLinux(); - } - throw new Exception("Unexpected OS."); - } - catch (Exception e) - { - GD.PushWarning(e.Message); - } - - return new RiderInfo[0]; - } + try + { + if (OS.IsWindows) + { + return CollectRiderInfosWindows(); + } + if (OS.IsOSX) + { + return CollectRiderInfosMac(); + } + if (OS.IsUnixLike()) + { + return CollectAllRiderPathsLinux(); + } + throw new Exception("Unexpected OS."); + } + catch (Exception e) + { + GD.PushWarning(e.Message); + } - private static RiderInfo[] CollectAllRiderPathsLinux() - { - var installInfos = new List<RiderInfo>(); - var home = Environment.GetEnvironmentVariable("HOME"); - if (!string.IsNullOrEmpty(home)) - { - var toolboxRiderRootPath = GetToolboxBaseDir(); - installInfos.AddRange(CollectPathsFromToolbox(toolboxRiderRootPath, "bin", "rider.sh", false) - .Select(a => new RiderInfo(a, true)).ToList()); - - //$Home/.local/share/applications/jetbrains-rider.desktop - var shortcut = new FileInfo(Path.Combine(home, @".local/share/applications/jetbrains-rider.desktop")); - - if (shortcut.Exists) - { - var lines = File.ReadAllLines(shortcut.FullName); - foreach (var line in lines) - { - if (!line.StartsWith("Exec=\"")) - continue; - var path = line.Split('"').Where((item, index) => index == 1).SingleOrDefault(); - if (string.IsNullOrEmpty(path)) - continue; - - if (installInfos.Any(a => a.Path == path)) // avoid adding similar build as from toolbox - continue; - installInfos.Add(new RiderInfo(path, false)); - } + return new RiderInfo[0]; } - } - - // snap install - var snapInstallPath = "/snap/rider/current/bin/rider.sh"; - if (new FileInfo(snapInstallPath).Exists) - installInfos.Add(new RiderInfo(snapInstallPath, false)); - - return installInfos.ToArray(); - } - private static RiderInfo[] CollectRiderInfosMac() - { - var installInfos = new List<RiderInfo>(); - // "/Applications/*Rider*.app" - var folder = new DirectoryInfo("/Applications"); - if (folder.Exists) - { - installInfos.AddRange(folder.GetDirectories("*Rider*.app") - .Select(a => new RiderInfo(a.FullName, false)) - .ToList()); - } - - // /Users/user/Library/Application Support/JetBrains/Toolbox/apps/Rider/ch-1/181.3870.267/Rider EAP.app - var toolboxRiderRootPath = GetToolboxBaseDir(); - var paths = CollectPathsFromToolbox(toolboxRiderRootPath, "", "Rider*.app", true) - .Select(a => new RiderInfo(a, true)); - installInfos.AddRange(paths); - - return installInfos.ToArray(); - } + private static RiderInfo[] CollectAllRiderPathsLinux() + { + var installInfos = new List<RiderInfo>(); + var home = Environment.GetEnvironmentVariable("HOME"); + if (!string.IsNullOrEmpty(home)) + { + var toolboxRiderRootPath = GetToolboxBaseDir(); + installInfos.AddRange(CollectPathsFromToolbox(toolboxRiderRootPath, "bin", "rider.sh", false) + .Select(a => new RiderInfo(a, true)).ToList()); + + //$Home/.local/share/applications/jetbrains-rider.desktop + var shortcut = new FileInfo(Path.Combine(home, @".local/share/applications/jetbrains-rider.desktop")); + + if (shortcut.Exists) + { + var lines = File.ReadAllLines(shortcut.FullName); + foreach (var line in lines) + { + if (!line.StartsWith("Exec=\"")) + continue; + var path = line.Split('"').Where((item, index) => index == 1).SingleOrDefault(); + if (string.IsNullOrEmpty(path)) + continue; + + if (installInfos.Any(a => a.Path == path)) // avoid adding similar build as from toolbox + continue; + installInfos.Add(new RiderInfo(path, false)); + } + } + } - private static RiderInfo[] CollectRiderInfosWindows() - { - var installInfos = new List<RiderInfo>(); - var toolboxRiderRootPath = GetToolboxBaseDir(); - var installPathsToolbox = CollectPathsFromToolbox(toolboxRiderRootPath, "bin", "rider64.exe", false).ToList(); - installInfos.AddRange(installPathsToolbox.Select(a => new RiderInfo(a, true)).ToList()); - - var installPaths = new List<string>(); - const string registryKey = @"SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall"; - CollectPathsFromRegistry(registryKey, installPaths); - const string wowRegistryKey = @"SOFTWARE\WOW6432Node\Microsoft\Windows\CurrentVersion\Uninstall"; - CollectPathsFromRegistry(wowRegistryKey, installPaths); - - installInfos.AddRange(installPaths.Select(a => new RiderInfo(a, false)).ToList()); - - return installInfos.ToArray(); - } + // snap install + var snapInstallPath = "/snap/rider/current/bin/rider.sh"; + if (new FileInfo(snapInstallPath).Exists) + installInfos.Add(new RiderInfo(snapInstallPath, false)); - private static string GetToolboxBaseDir() - { - if (OS.IsWindows) - { - var localAppData = Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData); - return Path.Combine(localAppData, @"JetBrains\Toolbox\apps\Rider"); - } - - if (OS.IsOSX) - { - var home = Environment.GetEnvironmentVariable("HOME"); - if (!string.IsNullOrEmpty(home)) - { - return Path.Combine(home, @"Library/Application Support/JetBrains/Toolbox/apps/Rider"); + return installInfos.ToArray(); } - } - if (OS.IsUnixLike()) - { - var home = Environment.GetEnvironmentVariable("HOME"); - if (!string.IsNullOrEmpty(home)) + private static RiderInfo[] CollectRiderInfosMac() { - return Path.Combine(home, @".local/share/JetBrains/Toolbox/apps/Rider"); + var installInfos = new List<RiderInfo>(); + // "/Applications/*Rider*.app" + var folder = new DirectoryInfo("/Applications"); + if (folder.Exists) + { + installInfos.AddRange(folder.GetDirectories("*Rider*.app") + .Select(a => new RiderInfo(a.FullName, false)) + .ToList()); + } + + // /Users/user/Library/Application Support/JetBrains/Toolbox/apps/Rider/ch-1/181.3870.267/Rider EAP.app + var toolboxRiderRootPath = GetToolboxBaseDir(); + var paths = CollectPathsFromToolbox(toolboxRiderRootPath, "", "Rider*.app", true) + .Select(a => new RiderInfo(a, true)); + installInfos.AddRange(paths); + + return installInfos.ToArray(); } - } - throw new Exception("Unexpected OS."); - } - - internal static ProductInfo GetBuildVersion(string path) - { - var buildTxtFileInfo = new FileInfo(Path.Combine(path, GetRelativePathToBuildTxt())); - var dir = buildTxtFileInfo.DirectoryName; - if (!Directory.Exists(dir)) - return null; - var buildVersionFile = new FileInfo(Path.Combine(dir, "product-info.json")); - if (!buildVersionFile.Exists) - return null; - var json = File.ReadAllText(buildVersionFile.FullName); - return ProductInfo.GetProductInfo(json); - } - - internal static Version GetBuildNumber(string path) - { - var file = new FileInfo(Path.Combine(path, GetRelativePathToBuildTxt())); - if (!file.Exists) - return null; - var text = File.ReadAllText(file.FullName); - if (text.Length <= 3) - return null; - - var versionText = text.Substring(3); - return Version.TryParse(versionText, out var v) ? v : null; - } + private static RiderInfo[] CollectRiderInfosWindows() + { + var installInfos = new List<RiderInfo>(); + var toolboxRiderRootPath = GetToolboxBaseDir(); + var installPathsToolbox = CollectPathsFromToolbox(toolboxRiderRootPath, "bin", "rider64.exe", false).ToList(); + installInfos.AddRange(installPathsToolbox.Select(a => new RiderInfo(a, true)).ToList()); - internal static bool IsToolbox(string path) - { - return path.StartsWith(GetToolboxBaseDir()); - } + var installPaths = new List<string>(); + const string registryKey = @"SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall"; + CollectPathsFromRegistry(registryKey, installPaths); + const string wowRegistryKey = @"SOFTWARE\WOW6432Node\Microsoft\Windows\CurrentVersion\Uninstall"; + CollectPathsFromRegistry(wowRegistryKey, installPaths); - private static string GetRelativePathToBuildTxt() - { - if (OS.IsWindows || OS.IsUnixLike()) - return "../../build.txt"; - if (OS.IsOSX) - return "Contents/Resources/build.txt"; - throw new Exception("Unknown OS."); - } + installInfos.AddRange(installPaths.Select(a => new RiderInfo(a, false)).ToList()); - private static void CollectPathsFromRegistry(string registryKey, List<string> installPaths) - { - using (var key = Registry.LocalMachine.OpenSubKey(registryKey)) - { - if (key == null) return; - foreach (var subkeyName in key.GetSubKeyNames().Where(a => a.Contains("Rider"))) - { - using (var subkey = key.OpenSubKey(subkeyName)) - { - var folderObject = subkey?.GetValue("InstallLocation"); - if (folderObject == null) continue; - var folder = folderObject.ToString(); - var possiblePath = Path.Combine(folder, @"bin\rider64.exe"); - if (File.Exists(possiblePath)) - installPaths.Add(possiblePath); - } + return installInfos.ToArray(); } - } - } - - private static string[] CollectPathsFromToolbox(string toolboxRiderRootPath, string dirName, string searchPattern, - bool isMac) - { - if (!Directory.Exists(toolboxRiderRootPath)) - return new string[0]; - var channelDirs = Directory.GetDirectories(toolboxRiderRootPath); - var paths = channelDirs.SelectMany(channelDir => + private static string GetToolboxBaseDir() { - try - { - // use history.json - last entry stands for the active build https://jetbrains.slack.com/archives/C07KNP99D/p1547807024066500?thread_ts=1547731708.057700&cid=C07KNP99D - var historyFile = Path.Combine(channelDir, ".history.json"); - if (File.Exists(historyFile)) + if (OS.IsWindows) { - var json = File.ReadAllText(historyFile); - var build = ToolboxHistory.GetLatestBuildFromJson(json); - if (build != null) - { - var buildDir = Path.Combine(channelDir, build); - var executablePaths = GetExecutablePaths(dirName, searchPattern, isMac, buildDir); - if (executablePaths.Any()) - return executablePaths; - } + var localAppData = Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData); + return Path.Combine(localAppData, @"JetBrains\Toolbox\apps\Rider"); } - var channelFile = Path.Combine(channelDir, ".channel.settings.json"); - if (File.Exists(channelFile)) + if (OS.IsOSX) { - var json = File.ReadAllText(channelFile).Replace("active-application", "active_application"); - var build = ToolboxInstallData.GetLatestBuildFromJson(json); - if (build != null) - { - var buildDir = Path.Combine(channelDir, build); - var executablePaths = GetExecutablePaths(dirName, searchPattern, isMac, buildDir); - if (executablePaths.Any()) - return executablePaths; - } + var home = Environment.GetEnvironmentVariable("HOME"); + if (!string.IsNullOrEmpty(home)) + { + return Path.Combine(home, @"Library/Application Support/JetBrains/Toolbox/apps/Rider"); + } } - // changes in toolbox json files format may brake the logic above, so return all found Rider installations - return Directory.GetDirectories(channelDir) - .SelectMany(buildDir => GetExecutablePaths(dirName, searchPattern, isMac, buildDir)); - } - catch (Exception e) - { - // do not write to Debug.Log, just log it. - Logger.Warn($"Failed to get RiderPath from {channelDir}", e); - } - - return new string[0]; - }) - .Where(c => !string.IsNullOrEmpty(c)) - .ToArray(); - return paths; - } - - private static string[] GetExecutablePaths(string dirName, string searchPattern, bool isMac, string buildDir) - { - var folder = new DirectoryInfo(Path.Combine(buildDir, dirName)); - if (!folder.Exists) - return new string[0]; - - if (!isMac) - return new[] {Path.Combine(folder.FullName, searchPattern)}.Where(File.Exists).ToArray(); - return folder.GetDirectories(searchPattern).Select(f => f.FullName) - .Where(Directory.Exists).ToArray(); - } - - // Disable the "field is never assigned" compiler warning. We never assign it, but Unity does. - // Note that Unity disable this warning in the generated C# projects -#pragma warning disable 0649 + if (OS.IsUnixLike()) + { + var home = Environment.GetEnvironmentVariable("HOME"); + if (!string.IsNullOrEmpty(home)) + { + return Path.Combine(home, @".local/share/JetBrains/Toolbox/apps/Rider"); + } + } - [Serializable] - class ToolboxHistory - { - public List<ItemNode> history; + throw new Exception("Unexpected OS."); + } - public static string GetLatestBuildFromJson(string json) - { - try + internal static ProductInfo GetBuildVersion(string path) { - return JsonConvert.DeserializeObject<ToolboxHistory>(json).history.LastOrDefault()?.item.build; + var buildTxtFileInfo = new FileInfo(Path.Combine(path, GetRelativePathToBuildTxt())); + var dir = buildTxtFileInfo.DirectoryName; + if (!Directory.Exists(dir)) + return null; + var buildVersionFile = new FileInfo(Path.Combine(dir, "product-info.json")); + if (!buildVersionFile.Exists) + return null; + var json = File.ReadAllText(buildVersionFile.FullName); + return ProductInfo.GetProductInfo(json); } - catch (Exception) + + internal static Version GetBuildNumber(string path) { - Logger.Warn($"Failed to get latest build from json {json}"); + var file = new FileInfo(Path.Combine(path, GetRelativePathToBuildTxt())); + if (!file.Exists) + return null; + var text = File.ReadAllText(file.FullName); + if (text.Length <= 3) + return null; + + var versionText = text.Substring(3); + return Version.TryParse(versionText, out var v) ? v : null; } - return null; - } - } - - [Serializable] - class ItemNode - { - public BuildNode item; - } + internal static bool IsToolbox(string path) + { + return path.StartsWith(GetToolboxBaseDir()); + } - [Serializable] - class BuildNode - { - public string build; - } + private static string GetRelativePathToBuildTxt() + { + if (OS.IsWindows || OS.IsUnixLike()) + return "../../build.txt"; + if (OS.IsOSX) + return "Contents/Resources/build.txt"; + throw new Exception("Unknown OS."); + } - [Serializable] - public class ProductInfo - { - public string version; - public string versionSuffix; + private static void CollectPathsFromRegistry(string registryKey, List<string> installPaths) + { + using (var key = Registry.LocalMachine.OpenSubKey(registryKey)) + { + if (key == null) return; + foreach (var subkeyName in key.GetSubKeyNames().Where(a => a.Contains("Rider"))) + { + using (var subkey = key.OpenSubKey(subkeyName)) + { + var folderObject = subkey?.GetValue("InstallLocation"); + if (folderObject == null) continue; + var folder = folderObject.ToString(); + var possiblePath = Path.Combine(folder, @"bin\rider64.exe"); + if (File.Exists(possiblePath)) + installPaths.Add(possiblePath); + } + } + } + } - [CanBeNull] - internal static ProductInfo GetProductInfo(string json) - { - try + private static string[] CollectPathsFromToolbox(string toolboxRiderRootPath, string dirName, string searchPattern, + bool isMac) { - var productInfo = JsonConvert.DeserializeObject<ProductInfo>(json); - return productInfo; + if (!Directory.Exists(toolboxRiderRootPath)) + return new string[0]; + + var channelDirs = Directory.GetDirectories(toolboxRiderRootPath); + var paths = channelDirs.SelectMany(channelDir => + { + try + { + // use history.json - last entry stands for the active build https://jetbrains.slack.com/archives/C07KNP99D/p1547807024066500?thread_ts=1547731708.057700&cid=C07KNP99D + var historyFile = Path.Combine(channelDir, ".history.json"); + if (File.Exists(historyFile)) + { + var json = File.ReadAllText(historyFile); + var build = ToolboxHistory.GetLatestBuildFromJson(json); + if (build != null) + { + var buildDir = Path.Combine(channelDir, build); + var executablePaths = GetExecutablePaths(dirName, searchPattern, isMac, buildDir); + if (executablePaths.Any()) + return executablePaths; + } + } + + var channelFile = Path.Combine(channelDir, ".channel.settings.json"); + if (File.Exists(channelFile)) + { + var json = File.ReadAllText(channelFile).Replace("active-application", "active_application"); + var build = ToolboxInstallData.GetLatestBuildFromJson(json); + if (build != null) + { + var buildDir = Path.Combine(channelDir, build); + var executablePaths = GetExecutablePaths(dirName, searchPattern, isMac, buildDir); + if (executablePaths.Any()) + return executablePaths; + } + } + + // changes in toolbox json files format may brake the logic above, so return all found Rider installations + return Directory.GetDirectories(channelDir) + .SelectMany(buildDir => GetExecutablePaths(dirName, searchPattern, isMac, buildDir)); + } + catch (Exception e) + { + // do not write to Debug.Log, just log it. + Logger.Warn($"Failed to get RiderPath from {channelDir}", e); + } + + return new string[0]; + }) + .Where(c => !string.IsNullOrEmpty(c)) + .ToArray(); + return paths; } - catch (Exception) + + private static string[] GetExecutablePaths(string dirName, string searchPattern, bool isMac, string buildDir) { - Logger.Warn($"Failed to get version from json {json}"); + var folder = new DirectoryInfo(Path.Combine(buildDir, dirName)); + if (!folder.Exists) + return new string[0]; + + if (!isMac) + return new[] { Path.Combine(folder.FullName, searchPattern) }.Where(File.Exists).ToArray(); + return folder.GetDirectories(searchPattern).Select(f => f.FullName) + .Where(Directory.Exists).ToArray(); } - return null; - } - } + // Disable the "field is never assigned" compiler warning. We never assign it, but Unity does. + // Note that Unity disable this warning in the generated C# projects +#pragma warning disable 0649 - // ReSharper disable once ClassNeverInstantiated.Global - [Serializable] - class ToolboxInstallData - { - // ReSharper disable once InconsistentNaming - public ActiveApplication active_application; + [Serializable] + class ToolboxHistory + { + public List<ItemNode> history; + + public static string GetLatestBuildFromJson(string json) + { + try + { + return JsonConvert.DeserializeObject<ToolboxHistory>(json).history.LastOrDefault()?.item.build; + } + catch (Exception) + { + Logger.Warn($"Failed to get latest build from json {json}"); + } + + return null; + } + } - [CanBeNull] - public static string GetLatestBuildFromJson(string json) - { - try + [Serializable] + class ItemNode { - var toolbox = JsonConvert.DeserializeObject<ToolboxInstallData>(json); - var builds = toolbox.active_application.builds; - if (builds != null && builds.Any()) - return builds.First(); + public BuildNode item; } - catch (Exception) + + [Serializable] + class BuildNode { - Logger.Warn($"Failed to get latest build from json {json}"); + public string build; } - return null; - } - } + [Serializable] + public class ProductInfo + { + public string version; + public string versionSuffix; - [Serializable] - class ActiveApplication - { - // ReSharper disable once InconsistentNaming - public List<string> builds; - } + [CanBeNull] + internal static ProductInfo GetProductInfo(string json) + { + try + { + var productInfo = JsonConvert.DeserializeObject<ProductInfo>(json); + return productInfo; + } + catch (Exception) + { + Logger.Warn($"Failed to get version from json {json}"); + } + + return null; + } + } -#pragma warning restore 0649 + // ReSharper disable once ClassNeverInstantiated.Global + [Serializable] + class ToolboxInstallData + { + // ReSharper disable once InconsistentNaming + public ActiveApplication active_application; - public struct RiderInfo - { - public bool IsToolbox; - public string Presentation; - public Version BuildNumber; - public ProductInfo ProductInfo; - public string Path; - - public RiderInfo(string path, bool isToolbox) - { - BuildNumber = GetBuildNumber(path); - ProductInfo = GetBuildVersion(path); - Path = new FileInfo(path).FullName; // normalize separators - var presentation = $"Rider {BuildNumber}"; - - if (ProductInfo != null && !string.IsNullOrEmpty(ProductInfo.version)) + [CanBeNull] + public static string GetLatestBuildFromJson(string json) + { + try + { + var toolbox = JsonConvert.DeserializeObject<ToolboxInstallData>(json); + var builds = toolbox.active_application.builds; + if (builds != null && builds.Any()) + return builds.First(); + } + catch (Exception) + { + Logger.Warn($"Failed to get latest build from json {json}"); + } + + return null; + } + } + + [Serializable] + class ActiveApplication { - var suffix = string.IsNullOrEmpty(ProductInfo.versionSuffix) ? "" : $" {ProductInfo.versionSuffix}"; - presentation = $"Rider {ProductInfo.version}{suffix}"; + // ReSharper disable once InconsistentNaming + public List<string> builds; } - if (isToolbox) - presentation += " (JetBrains Toolbox)"; +#pragma warning restore 0649 - Presentation = presentation; - IsToolbox = isToolbox; - } - } + public struct RiderInfo + { + public bool IsToolbox; + public string Presentation; + public Version BuildNumber; + public ProductInfo ProductInfo; + public string Path; - private static class Logger - { - internal static void Warn(string message, Exception e = null) - { - throw new Exception(message, e); - } + public RiderInfo(string path, bool isToolbox) + { + BuildNumber = GetBuildNumber(path); + ProductInfo = GetBuildVersion(path); + Path = new FileInfo(path).FullName; // normalize separators + var presentation = $"Rider {BuildNumber}"; + + if (ProductInfo != null && !string.IsNullOrEmpty(ProductInfo.version)) + { + var suffix = string.IsNullOrEmpty(ProductInfo.versionSuffix) ? "" : $" {ProductInfo.versionSuffix}"; + presentation = $"Rider {ProductInfo.version}{suffix}"; + } + + if (isToolbox) + presentation += " (JetBrains Toolbox)"; + + Presentation = presentation; + IsToolbox = isToolbox; + } + } + + private static class Logger + { + internal static void Warn(string message, Exception e = null) + { + throw new Exception(message, e); + } + } } - } } diff --git a/modules/mono/editor/GodotTools/GodotTools/Ides/Rider/RiderPathManager.cs b/modules/mono/editor/GodotTools/GodotTools/Ides/Rider/RiderPathManager.cs index b7dba13bbe..558a242bf9 100644 --- a/modules/mono/editor/GodotTools/GodotTools/Ides/Rider/RiderPathManager.cs +++ b/modules/mono/editor/GodotTools/GodotTools/Ides/Rider/RiderPathManager.cs @@ -7,111 +7,111 @@ using GodotTools.Internals; namespace GodotTools.Ides.Rider { - public static class RiderPathManager - { - private static readonly string editorPathSettingName= "mono/editor/editor_path_optional"; - - private static string GetRiderPathFromSettings() - { - var editorSettings = GodotSharpEditor.Instance.GetEditorInterface().GetEditorSettings(); - if (editorSettings.HasSetting(editorPathSettingName)) - return (string) editorSettings.GetSetting(editorPathSettingName); - return null; - } - - public static void Initialize() + public static class RiderPathManager { - var editorSettings = GodotSharpEditor.Instance.GetEditorInterface().GetEditorSettings(); - var editor = (ExternalEditorId) editorSettings.GetSetting("mono/editor/external_editor"); - if (editor == ExternalEditorId.Rider) - { - if (!editorSettings.HasSetting(editorPathSettingName)) + private static readonly string editorPathSettingName = "mono/editor/editor_path_optional"; + + private static string GetRiderPathFromSettings() { - Globals.EditorDef(editorPathSettingName, "Optional"); - editorSettings.AddPropertyInfo(new Godot.Collections.Dictionary - { - ["type"] = Variant.Type.String, - ["name"] = editorPathSettingName, - ["hint"] = PropertyHint.File, - ["hint_string"] = "" - }); + var editorSettings = GodotSharpEditor.Instance.GetEditorInterface().GetEditorSettings(); + if (editorSettings.HasSetting(editorPathSettingName)) + return (string)editorSettings.GetSetting(editorPathSettingName); + return null; } - var riderPath = (string) editorSettings.GetSetting(editorPathSettingName); - if (IsRiderAndExists(riderPath)) + public static void Initialize() { - Globals.EditorDef(editorPathSettingName, riderPath); - return; + var editorSettings = GodotSharpEditor.Instance.GetEditorInterface().GetEditorSettings(); + var editor = (ExternalEditorId)editorSettings.GetSetting("mono/editor/external_editor"); + if (editor == ExternalEditorId.Rider) + { + if (!editorSettings.HasSetting(editorPathSettingName)) + { + Globals.EditorDef(editorPathSettingName, "Optional"); + editorSettings.AddPropertyInfo(new Godot.Collections.Dictionary + { + ["type"] = Variant.Type.String, + ["name"] = editorPathSettingName, + ["hint"] = PropertyHint.File, + ["hint_string"] = "" + }); + } + + var riderPath = (string)editorSettings.GetSetting(editorPathSettingName); + if (IsRiderAndExists(riderPath)) + { + Globals.EditorDef(editorPathSettingName, riderPath); + return; + } + + var paths = RiderPathLocator.GetAllRiderPaths(); + + if (!paths.Any()) + return; + + var newPath = paths.Last().Path; + Globals.EditorDef(editorPathSettingName, newPath); + editorSettings.SetSetting(editorPathSettingName, newPath); + } } - var paths = RiderPathLocator.GetAllRiderPaths(); + private static bool IsRider(string path) + { + if (string.IsNullOrEmpty(path)) + { + return false; + } - if (!paths.Any()) - return; + var fileInfo = new FileInfo(path); + var filename = fileInfo.Name.ToLowerInvariant(); + return filename.StartsWith("rider", StringComparison.Ordinal); + } - var newPath = paths.Last().Path; - Globals.EditorDef(editorPathSettingName, newPath); - editorSettings.SetSetting(editorPathSettingName, newPath); - } - } + private static string CheckAndUpdatePath(string riderPath) + { + if (IsRiderAndExists(riderPath)) + { + return riderPath; + } - private static bool IsRider(string path) - { - if (string.IsNullOrEmpty(path)) - { - return false; - } - - var fileInfo = new FileInfo(path); - var filename = fileInfo.Name.ToLowerInvariant(); - return filename.StartsWith("rider", StringComparison.Ordinal); - } + var editorSettings = GodotSharpEditor.Instance.GetEditorInterface().GetEditorSettings(); + var paths = RiderPathLocator.GetAllRiderPaths(); - private static string CheckAndUpdatePath(string riderPath) - { - if (IsRiderAndExists(riderPath)) - { - return riderPath; - } - - var editorSettings = GodotSharpEditor.Instance.GetEditorInterface().GetEditorSettings(); - var paths = RiderPathLocator.GetAllRiderPaths(); - - if (!paths.Any()) - return null; - - var newPath = paths.Last().Path; - editorSettings.SetSetting(editorPathSettingName, newPath); - Globals.EditorDef(editorPathSettingName, newPath); - return newPath; - } + if (!paths.Any()) + return null; - private static bool IsRiderAndExists(string riderPath) - { - return !string.IsNullOrEmpty(riderPath) && IsRider(riderPath) && new FileInfo(riderPath).Exists; - } + var newPath = paths.Last().Path; + editorSettings.SetSetting(editorPathSettingName, newPath); + Globals.EditorDef(editorPathSettingName, newPath); + return newPath; + } - public static void OpenFile(string slnPath, string scriptPath, int line) - { - var pathFromSettings = GetRiderPathFromSettings(); - var path = CheckAndUpdatePath(pathFromSettings); - - var args = new List<string>(); - args.Add(slnPath); - if (line >= 0) - { - args.Add("--line"); - args.Add(line.ToString()); - } - args.Add(scriptPath); - try - { - Utils.OS.RunProcess(path, args); - } - catch (Exception e) - { - GD.PushError($"Error when trying to run code editor: JetBrains Rider. Exception message: '{e.Message}'"); - } + private static bool IsRiderAndExists(string riderPath) + { + return !string.IsNullOrEmpty(riderPath) && IsRider(riderPath) && new FileInfo(riderPath).Exists; + } + + public static void OpenFile(string slnPath, string scriptPath, int line) + { + var pathFromSettings = GetRiderPathFromSettings(); + var path = CheckAndUpdatePath(pathFromSettings); + + var args = new List<string>(); + args.Add(slnPath); + if (line >= 0) + { + args.Add("--line"); + args.Add(line.ToString()); + } + args.Add(scriptPath); + try + { + Utils.OS.RunProcess(path, args); + } + catch (Exception e) + { + GD.PushError($"Error when trying to run code editor: JetBrains Rider. Exception message: '{e.Message}'"); + } + } } - } } diff --git a/modules/mono/editor/GodotTools/GodotTools/Internals/GodotSharpDirs.cs b/modules/mono/editor/GodotTools/GodotTools/Internals/GodotSharpDirs.cs index ddf3b829b5..6893bc1974 100644 --- a/modules/mono/editor/GodotTools/GodotTools/Internals/GodotSharpDirs.cs +++ b/modules/mono/editor/GodotTools/GodotTools/Internals/GodotSharpDirs.cs @@ -33,10 +33,10 @@ namespace GodotTools.Internals #region Windows-only public static string DataMonoBinDir => internal_DataMonoBinDir(); #endregion - - + + #region Internal - + [MethodImpl(MethodImplOptions.InternalCall)] private static extern string internal_ResDataDir(); [MethodImpl(MethodImplOptions.InternalCall)] @@ -85,7 +85,7 @@ namespace GodotTools.Internals [MethodImpl(MethodImplOptions.InternalCall)] private static extern string internal_DataMonoBinDir(); #endregion - + #endregion } } diff --git a/modules/mono/editor/GodotTools/GodotTools/Internals/ScriptClassParser.cs b/modules/mono/editor/GodotTools/GodotTools/Internals/ScriptClassParser.cs index 2497d276a9..80e45b3a3c 100644 --- a/modules/mono/editor/GodotTools/GodotTools/Internals/ScriptClassParser.cs +++ b/modules/mono/editor/GodotTools/GodotTools/Internals/ScriptClassParser.cs @@ -39,10 +39,10 @@ namespace GodotTools.Internals foreach (var classDeclDict in classesArray) { classesList.Add(new ClassDecl( - (string) classDeclDict["name"], - (string) classDeclDict["namespace"], - (bool) classDeclDict["nested"], - (int) classDeclDict["base_count"] + (string)classDeclDict["name"], + (string)classDeclDict["namespace"], + (bool)classDeclDict["nested"], + (int)classDeclDict["base_count"] )); } diff --git a/modules/mono/editor/GodotTools/GodotTools/Utils/OS.cs b/modules/mono/editor/GodotTools/GodotTools/Utils/OS.cs index 1fe07e0bb6..5a867b7f8b 100644 --- a/modules/mono/editor/GodotTools/GodotTools/Utils/OS.cs +++ b/modules/mono/editor/GodotTools/GodotTools/Utils/OS.cs @@ -75,7 +75,7 @@ namespace GodotTools.Utils public static bool IsHTML5 => _isHTML5.Value; private static bool? _isUnixCache; - private static readonly string[] UnixLikePlatforms = {Names.OSX, Names.X11, Names.Server, Names.Haiku, Names.Android}; + private static readonly string[] UnixLikePlatforms = { Names.OSX, Names.X11, Names.Server, Names.Haiku, Names.Android }; public static bool IsUnixLike() { @@ -113,10 +113,10 @@ namespace GodotTools.Utils return searchDirs.Select(dir => Path.Combine(dir, name)).FirstOrDefault(File.Exists); return (from dir in searchDirs - select Path.Combine(dir, name) + select Path.Combine(dir, name) into path - from ext in windowsExts - select path + ext).FirstOrDefault(File.Exists); + from ext in windowsExts + select path + ext).FirstOrDefault(File.Exists); } private static string PathWhichUnix(string name) @@ -157,7 +157,7 @@ namespace GodotTools.Utils process.BeginOutputReadLine(); process.BeginErrorReadLine(); - if (IsWindows && process.Id>0) + if (IsWindows && process.Id > 0) User32Dll.AllowSetForegroundWindow(process.Id); // allows application to focus itself } } diff --git a/modules/mono/editor/GodotTools/GodotTools/packages.config b/modules/mono/editor/GodotTools/GodotTools/packages.config index 2db4b4acc6..dd3de2865a 100644 --- a/modules/mono/editor/GodotTools/GodotTools/packages.config +++ b/modules/mono/editor/GodotTools/GodotTools/packages.config @@ -1,5 +1,5 @@ -<?xml version="1.0" encoding="utf-8"?> +<?xml version="1.0" encoding="utf-8"?> <packages> <package id="JetBrains.Annotations" version="2019.1.3" targetFramework="net45" /> <package id="Newtonsoft.Json" version="12.0.3" targetFramework="net45" /> -</packages>
\ No newline at end of file +</packages> diff --git a/modules/mono/glue/Managed/Files/StringExtensions.cs b/modules/mono/glue/Managed/Files/StringExtensions.cs index 6045c83e95..079e9912d6 100644 --- a/modules/mono/glue/Managed/Files/StringExtensions.cs +++ b/modules/mono/glue/Managed/Files/StringExtensions.cs @@ -18,7 +18,7 @@ namespace Godot int pos = 0; int slices = 1; - while ((pos = instance.Find(splitter, pos)) >= 0) + while ((pos = instance.Find(splitter, true, pos)) >= 0) { slices++; pos += splitter.Length; @@ -325,17 +325,17 @@ namespace Godot // <summary> // Find the first occurrence of a substring, return the starting position of the substring or -1 if not found. Optionally, the initial search index can be passed. // </summary> - public static int Find(this string instance, string what, int from = 0) + public static int Find(this string instance, string what, bool caseSensitive = true, int from = 0) { - return instance.IndexOf(what, StringComparison.OrdinalIgnoreCase); + return instance.IndexOf(what, from, caseSensitive ? StringComparison.Ordinal : StringComparison.OrdinalIgnoreCase); } // <summary> // Find the last occurrence of a substring, return the starting position of the substring or -1 if not found. Optionally, the initial search index can be passed. // </summary> - public static int FindLast(this string instance, string what) + public static int FindLast(this string instance, string what, bool caseSensitive = true, int from = 0) { - return instance.LastIndexOf(what, StringComparison.OrdinalIgnoreCase); + return instance.LastIndexOf(what, from, caseSensitive ? StringComparison.Ordinal : StringComparison.OrdinalIgnoreCase); } // <summary> @@ -343,7 +343,7 @@ namespace Godot // </summary> public static int FindN(this string instance, string what, int from = 0) { - return instance.IndexOf(what, StringComparison.Ordinal); + return instance.IndexOf(what, from, StringComparison.OrdinalIgnoreCase); } // <summary> @@ -928,7 +928,7 @@ namespace Godot while (true) { - int end = instance.Find(divisor, from); + int end = instance.Find(divisor, true, from); if (end < 0) end = len; if (allowEmpty || end > from) diff --git a/modules/mono/glue/Managed/Managed.csproj b/modules/mono/glue/Managed/Managed.csproj index c8eca71199..8bde3b6d22 100644 --- a/modules/mono/glue/Managed/Managed.csproj +++ b/modules/mono/glue/Managed/Managed.csproj @@ -1,4 +1,4 @@ -<?xml version="1.0" encoding="utf-8"?> +<?xml version="1.0" encoding="utf-8"?> <Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> <PropertyGroup> <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration> diff --git a/scene/gui/button.cpp b/scene/gui/button.cpp index ca4c255855..a68462f4d4 100644 --- a/scene/gui/button.cpp +++ b/scene/gui/button.cpp @@ -190,6 +190,13 @@ void Button::_notification(int p_what) { Point2 icon_ofs = !_icon.is_null() ? Point2(icon_region.size.width + get_constant("hseparation"), 0) : Point2(); int text_clip = size.width - style->get_minimum_size().width - icon_ofs.width; + if (_internal_margin[MARGIN_LEFT] > 0) { + text_clip -= _internal_margin[MARGIN_LEFT] + get_constant("hseparation"); + } + if (_internal_margin[MARGIN_RIGHT] > 0) { + text_clip -= _internal_margin[MARGIN_RIGHT] + get_constant("hseparation"); + } + Point2 text_ofs = (size - style->get_minimum_size() - icon_ofs - font->get_string_size(xl_text) - Point2(_internal_margin[MARGIN_RIGHT] - _internal_margin[MARGIN_LEFT], 0)) / 2.0; switch (align) { diff --git a/scene/gui/popup_menu.cpp b/scene/gui/popup_menu.cpp index 08faaf7d45..cffea527a5 100644 --- a/scene/gui/popup_menu.cpp +++ b/scene/gui/popup_menu.cpp @@ -191,16 +191,20 @@ void PopupMenu::_submenu_timeout() { void PopupMenu::_scroll(float p_factor, const Point2 &p_over) { - const float global_y = get_global_position().y; - int vseparation = get_constant("vseparation"); Ref<Font> font = get_font("font"); float dy = (vseparation + font->get_height()) * 3 * p_factor * get_global_transform().get_scale().y; - if (dy > 0 && global_y < 0) - dy = MIN(dy, -global_y - 1); - else if (dy < 0 && global_y + get_size().y * get_global_transform().get_scale().y > get_viewport_rect().size.y) - dy = -MIN(-dy, global_y + get_size().y * get_global_transform().get_scale().y - get_viewport_rect().size.y - 1); + if (dy > 0) { + const float global_top = get_global_position().y; + const float limit = global_top < 0 ? -global_top : 0; + dy = MIN(dy, limit); + } else if (dy < 0) { + const float global_bottom = get_global_position().y + get_size().y * get_global_transform().get_scale().y; + const float viewport_height = get_viewport_rect().size.y; + const float limit = global_bottom > viewport_height ? global_bottom - viewport_height: 0; + dy = -MIN(-dy, limit); + } set_position(get_position() + Vector2(0, dy)); Ref<InputEventMouseMotion> ie; diff --git a/scene/gui/rich_text_effect.cpp b/scene/gui/rich_text_effect.cpp index f9e0be5b31..ab2f8d2172 100644 --- a/scene/gui/rich_text_effect.cpp +++ b/scene/gui/rich_text_effect.cpp @@ -89,8 +89,6 @@ void CharFXTransform::_bind_methods() { ClassDB::bind_method(D_METHOD("get_character"), &CharFXTransform::get_character); ClassDB::bind_method(D_METHOD("set_character", "character"), &CharFXTransform::set_character); - ClassDB::bind_method(D_METHOD("get_value_or", "key", "default_value"), &CharFXTransform::get_value_or); - ADD_PROPERTY(PropertyInfo(Variant::INT, "relative_index"), "set_relative_index", "get_relative_index"); ADD_PROPERTY(PropertyInfo(Variant::INT, "absolute_index"), "set_absolute_index", "get_absolute_index"); ADD_PROPERTY(PropertyInfo(Variant::REAL, "elapsed_time"), "set_elapsed_time", "get_elapsed_time"); @@ -101,17 +99,6 @@ void CharFXTransform::_bind_methods() { ADD_PROPERTY(PropertyInfo(Variant::INT, "character"), "set_character", "get_character"); } -Variant CharFXTransform::get_value_or(String p_key, Variant p_default_value) { - if (!this->environment.has(p_key)) - return p_default_value; - - Variant r = environment[p_key]; - if (r.get_type() != p_default_value.get_type()) - return p_default_value; - - return r; -} - CharFXTransform::CharFXTransform() { relative_index = 0; absolute_index = 0; diff --git a/scene/gui/rich_text_effect.h b/scene/gui/rich_text_effect.h index 4330cebfe6..9e0065b199 100644 --- a/scene/gui/rich_text_effect.h +++ b/scene/gui/rich_text_effect.h @@ -82,8 +82,6 @@ public: void set_character(int p_char) { character = (CharType)p_char; } Dictionary get_environment() { return environment; } void set_environment(Dictionary p_environment) { environment = p_environment; } - - Variant get_value_or(String p_key, Variant p_default_value); }; #endif // RICH_TEXT_EFFECT_H diff --git a/scene/gui/rich_text_label.cpp b/scene/gui/rich_text_label.cpp index 0331046492..abca865ae0 100644 --- a/scene/gui/rich_text_label.cpp +++ b/scene/gui/rich_text_label.cpp @@ -1701,6 +1701,9 @@ bool RichTextLabel::remove_line(const int p_line) { if (!was_newline) { current_frame->lines.remove(p_line); + if (current_frame->lines.size() == 0) { + current_frame->lines.resize(1); + } } if (p_line == 0 && current->subitems.size() > 0) diff --git a/scene/resources/mesh.cpp b/scene/resources/mesh.cpp index 4afb07cb6f..0d94d4dbf4 100644 --- a/scene/resources/mesh.cpp +++ b/scene/resources/mesh.cpp @@ -483,6 +483,7 @@ void Mesh::_bind_methods() { ClassDB::bind_method(D_METHOD("set_lightmap_size_hint", "size"), &Mesh::set_lightmap_size_hint); ClassDB::bind_method(D_METHOD("get_lightmap_size_hint"), &Mesh::get_lightmap_size_hint); + ClassDB::bind_method(D_METHOD("get_aabb"), &Mesh::get_aabb); ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "lightmap_size_hint"), "set_lightmap_size_hint", "get_lightmap_size_hint"); diff --git a/scene/resources/visual_shader_nodes.cpp b/scene/resources/visual_shader_nodes.cpp index a94fdd9d7b..6e4b5d9af0 100644 --- a/scene/resources/visual_shader_nodes.cpp +++ b/scene/resources/visual_shader_nodes.cpp @@ -715,6 +715,7 @@ void VisualShaderNodeTexture::_bind_methods() { BIND_ENUM_CONSTANT(SOURCE_2D_TEXTURE); BIND_ENUM_CONSTANT(SOURCE_2D_NORMAL); BIND_ENUM_CONSTANT(SOURCE_DEPTH); + BIND_ENUM_CONSTANT(SOURCE_PORT); BIND_ENUM_CONSTANT(TYPE_DATA); BIND_ENUM_CONSTANT(TYPE_COLOR); BIND_ENUM_CONSTANT(TYPE_NORMALMAP); diff --git a/servers/audio/effects/audio_effect_record.cpp b/servers/audio/effects/audio_effect_record.cpp index 83d78daff4..3b6b1de806 100644 --- a/servers/audio/effects/audio_effect_record.cpp +++ b/servers/audio/effects/audio_effect_record.cpp @@ -192,10 +192,11 @@ void AudioEffectRecord::set_recording_active(bool p_record) { } ensure_thread_stopped(); + recording_active = true; current_instance->init(); + } else { + recording_active = false; } - - recording_active = p_record; } bool AudioEffectRecord::is_recording_active() const { |