diff options
365 files changed, 17352 insertions, 3167 deletions
diff --git a/.gitattributes b/.gitattributes index 47ba2b45bb..f2cf6ab63a 100644 --- a/.gitattributes +++ b/.gitattributes @@ -1,12 +1,6 @@ # Properly detect languages on Github *.h linguist-language=cpp *.inc linguist-language=cpp -drivers/* linguist-vendored +thirdparty/* linguist-vendored -*.cpp eol=lf -*.mm eol=lf -*.h eol=lf -*.py eol=lf -*.hpp eol=lf -*.xml eol=lf -*.natvis eol=lf +* text=auto eol=lf diff --git a/.travis.yml b/.travis.yml index 727567b8e7..b8e02a5be8 100644 --- a/.travis.yml +++ b/.travis.yml @@ -23,9 +23,9 @@ matrix: addons: apt: sources: - - llvm-toolchain-xenial-6.0 + - llvm-toolchain-xenial-8 packages: - - clang-format-6.0 + - clang-format-8 - env: PLATFORM=x11 TOOLS=yes TARGET=debug CACHE_NAME=${PLATFORM}-tools-mono-gcc-8 MATRIX_EVAL="CC=gcc-8 && CXX=g++-8" EXTRA_ARGS="module_mono_enabled=yes mono_glue=no warnings=extra werror=yes" os: linux diff --git a/SConstruct b/SConstruct index 3ff6bb739a..88bb43fbc7 100644 --- a/SConstruct +++ b/SConstruct @@ -562,7 +562,7 @@ if 'env' in locals(): # (filename, size, weight). current_time = time.time() file_stat = [(x[0], x[1][0], (current_time - x[1][1])) for x in file_stat] - # Sort by the most resently accessed files (most sensible to keep) first + # Sort by the most recently accessed files (most sensible to keep) first file_stat.sort(key=lambda x: x[2]) # Search for the first entry where the storage limit is # reached diff --git a/core/SCsub b/core/SCsub index 06efc8408d..166b7083e4 100644 --- a/core/SCsub +++ b/core/SCsub @@ -58,6 +58,7 @@ thirdparty_misc_sources = [ "md5.cpp", "pcg.cpp", "triangulator.cpp", + "clipper.cpp", ] thirdparty_misc_sources = [thirdparty_misc_dir + file for file in thirdparty_misc_sources] env_thirdparty.add_source_files(env.core_sources, thirdparty_misc_sources) diff --git a/core/bind/core_bind.cpp b/core/bind/core_bind.cpp index ba595b9627..ddb60e1345 100644 --- a/core/bind/core_bind.cpp +++ b/core/bind/core_bind.cpp @@ -1491,11 +1491,21 @@ PoolVector<Vector3> _Geometry::segment_intersects_convex(const Vector3 &p_from, return r; } +bool _Geometry::is_polygon_clockwise(const Vector<Vector2> &p_polygon) { + + return Geometry::is_polygon_clockwise(p_polygon); +} + Vector<int> _Geometry::triangulate_polygon(const Vector<Vector2> &p_polygon) { return Geometry::triangulate_polygon(p_polygon); } +Vector<int> _Geometry::triangulate_delaunay_2d(const Vector<Vector2> &p_points) { + + return Geometry::triangulate_delaunay_2d(p_points); +} + Vector<Point2> _Geometry::convex_hull_2d(const Vector<Point2> &p_points) { return Geometry::convex_hull_2d(p_points); @@ -1506,6 +1516,107 @@ Vector<Vector3> _Geometry::clip_polygon(const Vector<Vector3> &p_points, const P return Geometry::clip_polygon(p_points, p_plane); } +Array _Geometry::merge_polygons_2d(const Vector<Vector2> &p_polygon_a, const Vector<Vector2> &p_polygon_b) { + + Vector<Vector<Point2> > polys = Geometry::merge_polygons_2d(p_polygon_a, p_polygon_b); + + Array ret; + + for (int i = 0; i < polys.size(); ++i) { + ret.push_back(polys[i]); + } + return ret; +} + +Array _Geometry::clip_polygons_2d(const Vector<Vector2> &p_polygon_a, const Vector<Vector2> &p_polygon_b) { + + Vector<Vector<Point2> > polys = Geometry::clip_polygons_2d(p_polygon_a, p_polygon_b); + + Array ret; + + for (int i = 0; i < polys.size(); ++i) { + ret.push_back(polys[i]); + } + return ret; +} + +Array _Geometry::intersect_polygons_2d(const Vector<Vector2> &p_polygon_a, const Vector<Vector2> &p_polygon_b) { + + Vector<Vector<Point2> > polys = Geometry::intersect_polygons_2d(p_polygon_a, p_polygon_b); + + Array ret; + + for (int i = 0; i < polys.size(); ++i) { + ret.push_back(polys[i]); + } + return ret; +} + +Array _Geometry::exclude_polygons_2d(const Vector<Vector2> &p_polygon_a, const Vector<Vector2> &p_polygon_b) { + + Vector<Vector<Point2> > polys = Geometry::exclude_polygons_2d(p_polygon_a, p_polygon_b); + + Array ret; + + for (int i = 0; i < polys.size(); ++i) { + ret.push_back(polys[i]); + } + return ret; +} + +Array _Geometry::clip_polyline_with_polygon_2d(const Vector<Vector2> &p_polyline, const Vector<Vector2> &p_polygon) { + + Vector<Vector<Point2> > polys = Geometry::clip_polyline_with_polygon_2d(p_polyline, p_polygon); + + Array ret; + + for (int i = 0; i < polys.size(); ++i) { + ret.push_back(polys[i]); + } + return ret; +} + +Array _Geometry::intersect_polyline_with_polygon_2d(const Vector<Vector2> &p_polyline, const Vector<Vector2> &p_polygon) { + + Vector<Vector<Point2> > polys = Geometry::intersect_polyline_with_polygon_2d(p_polyline, p_polygon); + + Array ret; + + for (int i = 0; i < polys.size(); ++i) { + ret.push_back(polys[i]); + } + return ret; +} + +Array _Geometry::offset_polygon_2d(const Vector<Vector2> &p_polygon, real_t p_delta, PolyJoinType p_join_type) { + + Vector<Vector<Point2> > polys = Geometry::offset_polygon_2d(p_polygon, p_delta, Geometry::PolyJoinType(p_join_type)); + + Array ret; + + for (int i = 0; i < polys.size(); ++i) { + ret.push_back(polys[i]); + } + return ret; +} + +Array _Geometry::offset_polyline_2d(const Vector<Vector2> &p_polygon, real_t p_delta, PolyJoinType p_join_type, PolyEndType p_end_type) { + + Vector<Vector<Point2> > polys = Geometry::offset_polyline_2d(p_polygon, p_delta, Geometry::PolyJoinType(p_join_type), Geometry::PolyEndType(p_end_type)); + + Array ret; + + for (int i = 0; i < polys.size(); ++i) { + ret.push_back(polys[i]); + } + return ret; +} + +Vector<Point2> _Geometry::transform_points_2d(const Vector<Point2> &p_points, const Transform2D &p_mat) { + + return Geometry::transform_points_2d(p_points, p_mat); +} + Dictionary _Geometry::make_atlas(const Vector<Size2> &p_rects) { Dictionary ret; @@ -1566,11 +1677,41 @@ void _Geometry::_bind_methods() { ClassDB::bind_method(D_METHOD("segment_intersects_convex", "from", "to", "planes"), &_Geometry::segment_intersects_convex); ClassDB::bind_method(D_METHOD("point_is_inside_triangle", "point", "a", "b", "c"), &_Geometry::point_is_inside_triangle); + ClassDB::bind_method(D_METHOD("is_polygon_clockwise", "polygon"), &_Geometry::is_polygon_clockwise); ClassDB::bind_method(D_METHOD("triangulate_polygon", "polygon"), &_Geometry::triangulate_polygon); + ClassDB::bind_method(D_METHOD("triangulate_delaunay_2d", "points"), &_Geometry::triangulate_delaunay_2d); ClassDB::bind_method(D_METHOD("convex_hull_2d", "points"), &_Geometry::convex_hull_2d); ClassDB::bind_method(D_METHOD("clip_polygon", "points", "plane"), &_Geometry::clip_polygon); + ClassDB::bind_method(D_METHOD("merge_polygons_2d", "polygon_a", "polygon_b"), &_Geometry::merge_polygons_2d); + ClassDB::bind_method(D_METHOD("clip_polygons_2d", "polygon_a", "polygon_b"), &_Geometry::clip_polygons_2d); + ClassDB::bind_method(D_METHOD("intersect_polygons_2d", "polygon_a", "polygon_b"), &_Geometry::intersect_polygons_2d); + ClassDB::bind_method(D_METHOD("exclude_polygons_2d", "polygon_a", "polygon_b"), &_Geometry::exclude_polygons_2d); + + ClassDB::bind_method(D_METHOD("clip_polyline_with_polygon_2d", "polyline", "polygon"), &_Geometry::clip_polyline_with_polygon_2d); + ClassDB::bind_method(D_METHOD("intersect_polyline_with_polygon_2d", "polyline", "polygon"), &_Geometry::intersect_polyline_with_polygon_2d); + + ClassDB::bind_method(D_METHOD("offset_polygon_2d", "polygon", "delta", "join_type"), &_Geometry::offset_polygon_2d, DEFVAL(JOIN_SQUARE)); + ClassDB::bind_method(D_METHOD("offset_polyline_2d", "polyline", "delta", "join_type", "end_type"), &_Geometry::offset_polyline_2d, DEFVAL(JOIN_SQUARE), DEFVAL(END_SQUARE)); + + ClassDB::bind_method(D_METHOD("transform_points_2d", "points", "transform"), &_Geometry::transform_points_2d); + ClassDB::bind_method(D_METHOD("make_atlas", "sizes"), &_Geometry::make_atlas); + + BIND_ENUM_CONSTANT(OPERATION_UNION); + BIND_ENUM_CONSTANT(OPERATION_DIFFERENCE); + BIND_ENUM_CONSTANT(OPERATION_INTERSECTION); + BIND_ENUM_CONSTANT(OPERATION_XOR); + + BIND_ENUM_CONSTANT(JOIN_SQUARE); + BIND_ENUM_CONSTANT(JOIN_ROUND); + BIND_ENUM_CONSTANT(JOIN_MITER); + + BIND_ENUM_CONSTANT(END_POLYGON); + BIND_ENUM_CONSTANT(END_JOINED); + BIND_ENUM_CONSTANT(END_BUTT); + BIND_ENUM_CONSTANT(END_SQUARE); + BIND_ENUM_CONSTANT(END_ROUND); } _Geometry::_Geometry() { diff --git a/core/bind/core_bind.h b/core/bind/core_bind.h index 2906de4a4a..d4fa3bc735 100644 --- a/core/bind/core_bind.h +++ b/core/bind/core_bind.h @@ -402,15 +402,55 @@ public: real_t segment_intersects_circle(const Vector2 &p_from, const Vector2 &p_to, const Vector2 &p_circle_pos, real_t p_circle_radius); int get_uv84_normal_bit(const Vector3 &p_vector); + bool is_polygon_clockwise(const Vector<Vector2> &p_polygon); Vector<int> triangulate_polygon(const Vector<Vector2> &p_polygon); + Vector<int> triangulate_delaunay_2d(const Vector<Vector2> &p_points); Vector<Point2> convex_hull_2d(const Vector<Point2> &p_points); Vector<Vector3> clip_polygon(const Vector<Vector3> &p_points, const Plane &p_plane); + enum PolyBooleanOperation { + OPERATION_UNION, + OPERATION_DIFFERENCE, + OPERATION_INTERSECTION, + OPERATION_XOR + }; + // 2D polygon boolean operations + Array merge_polygons_2d(const Vector<Vector2> &p_polygon_a, const Vector<Vector2> &p_polygon_b); // union (add) + Array clip_polygons_2d(const Vector<Vector2> &p_polygon_a, const Vector<Vector2> &p_polygon_b); // difference (subtract) + Array intersect_polygons_2d(const Vector<Vector2> &p_polygon_a, const Vector<Vector2> &p_polygon_b); // common area (multiply) + Array exclude_polygons_2d(const Vector<Vector2> &p_polygon_a, const Vector<Vector2> &p_polygon_b); // all but common area (xor) + + // 2D polyline vs polygon operations + Array clip_polyline_with_polygon_2d(const Vector<Vector2> &p_polyline, const Vector<Vector2> &p_polygon); // cut + Array intersect_polyline_with_polygon_2d(const Vector<Vector2> &p_polyline, const Vector<Vector2> &p_polygon); // chop + + // 2D offset polygons/polylines + enum PolyJoinType { + JOIN_SQUARE, + JOIN_ROUND, + JOIN_MITER + }; + enum PolyEndType { + END_POLYGON, + END_JOINED, + END_BUTT, + END_SQUARE, + END_ROUND + }; + Array offset_polygon_2d(const Vector<Vector2> &p_polygon, real_t p_delta, PolyJoinType p_join_type = JOIN_SQUARE); + Array offset_polyline_2d(const Vector<Vector2> &p_polygon, real_t p_delta, PolyJoinType p_join_type = JOIN_SQUARE, PolyEndType p_end_type = END_SQUARE); + + Vector<Point2> transform_points_2d(const Vector<Point2> &p_points, const Transform2D &p_mat); + Dictionary make_atlas(const Vector<Size2> &p_rects); _Geometry(); }; +VARIANT_ENUM_CAST(_Geometry::PolyBooleanOperation); +VARIANT_ENUM_CAST(_Geometry::PolyJoinType); +VARIANT_ENUM_CAST(_Geometry::PolyEndType); + class _File : public Reference { GDCLASS(_File, Reference); diff --git a/core/color_names.inc b/core/color_names.inc index e126bfe0f8..b0ef507d92 100644 --- a/core/color_names.inc +++ b/core/color_names.inc @@ -143,6 +143,7 @@ static void _populate_named_colors() { _named_colors.insert("thistle", Color(0.85, 0.75, 0.85)); _named_colors.insert("tomato", Color(1.00, 0.39, 0.28)); _named_colors.insert("turquoise", Color(0.25, 0.88, 0.82)); + _named_colors.insert("transparent", Color(1.00, 1.00, 1.00, 0.00)); _named_colors.insert("violet", Color(0.93, 0.51, 0.93)); _named_colors.insert("wheat", Color(0.96, 0.87, 0.70)); _named_colors.insert("white", Color(1.00, 1.00, 1.00)); diff --git a/core/core_string_names.cpp b/core/core_string_names.cpp index 1b59508abf..eeaae96754 100644 --- a/core/core_string_names.cpp +++ b/core/core_string_names.cpp @@ -44,6 +44,7 @@ CoreStringNames::CoreStringNames() : _iter_next(StaticCString::create("_iter_next")), _iter_get(StaticCString::create("_iter_get")), get_rid(StaticCString::create("get_rid")), + _to_string(StaticCString::create("_to_string")), #ifdef TOOLS_ENABLED _sections_unfolded(StaticCString::create("_sections_unfolded")), #endif diff --git a/core/core_string_names.h b/core/core_string_names.h index 6fea40e1b2..85f8bb7f62 100644 --- a/core/core_string_names.h +++ b/core/core_string_names.h @@ -62,6 +62,7 @@ public: StringName _iter_next; StringName _iter_get; StringName get_rid; + StringName _to_string; #ifdef TOOLS_ENABLED StringName _sections_unfolded; #endif diff --git a/core/error_macros.h b/core/error_macros.h index 78e29551d4..f72e987e23 100644 --- a/core/error_macros.h +++ b/core/error_macros.h @@ -41,7 +41,7 @@ */ /** - * Pointer to the error macro priting function. Reassign to any function to have errors printed + * Pointer to the error macro printing function. Reassign to any function to have errors printed */ /** Function used by the error macros */ diff --git a/core/io/http_client.cpp b/core/io/http_client.cpp index e5c6d2a4f2..ce2054db36 100644 --- a/core/io/http_client.cpp +++ b/core/io/http_client.cpp @@ -429,7 +429,7 @@ Error HTTPClient::poll() { response_num = RESPONSE_OK; // Per the HTTP 1.1 spec, keep-alive is the default. - // Not following that specification breaks standard implemetations. + // Not following that specification breaks standard implementations. // Broken web servers should be fixed. bool keep_alive = true; diff --git a/core/io/marshalls.cpp b/core/io/marshalls.cpp index 81b3829ffc..d1b6b82cf0 100644 --- a/core/io/marshalls.cpp +++ b/core/io/marshalls.cpp @@ -1231,11 +1231,15 @@ Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len, bo buf += 4; PoolVector<uint8_t>::Read r = data.read(); copymem(buf, &r[0], datalen * datasize); + buf += datalen * datasize; } r_len += 4 + datalen * datasize; - while (r_len % 4) + while (r_len % 4) { r_len++; + if (buf) + *(buf++) = 0; + } } break; case Variant::POOL_INT_ARRAY: { diff --git a/core/io/resource_importer.cpp b/core/io/resource_importer.cpp index 038a34ed51..4a58d37ca5 100644 --- a/core/io/resource_importer.cpp +++ b/core/io/resource_importer.cpp @@ -301,8 +301,7 @@ String ResourceFormatImporter::get_import_group_file(const String &p_path) const bool valid = true; PathAndType pat; _get_path_and_type(p_path, pat, &valid); - return valid?pat.group_file:String(); - + return valid ? pat.group_file : String(); } bool ResourceFormatImporter::is_import_valid(const String &p_path) const { diff --git a/core/io/resource_importer.h b/core/io/resource_importer.h index bdbdde6df6..2e01989564 100644 --- a/core/io/resource_importer.h +++ b/core/io/resource_importer.h @@ -126,7 +126,7 @@ public: virtual Error import(const String &p_source_file, const String &p_save_path, const Map<StringName, Variant> &p_options, List<String> *r_platform_variants, List<String> *r_gen_files = NULL, Variant *r_metadata = NULL) = 0; - virtual Error import_group_file(const String& p_group_file,const Map<String,Map<StringName, Variant> >&p_source_file_options, const Map<String,String>& p_base_paths) { return ERR_UNAVAILABLE; } + virtual Error import_group_file(const String &p_group_file, const Map<String, Map<StringName, Variant> > &p_source_file_options, const Map<String, String> &p_base_paths) { return ERR_UNAVAILABLE; } virtual bool are_import_settings_valid(const String &p_path) const { return true; } virtual String get_import_settings_string() const { return String(); } }; diff --git a/core/io/zip_io.h b/core/io/zip_io.h index fb63878a4c..4eb1c8b46c 100644 --- a/core/io/zip_io.h +++ b/core/io/zip_io.h @@ -33,7 +33,7 @@ #include "core/os/file_access.h" -// Not direclty used in this header, but assumed available in downstream users +// Not directly used in this header, but assumed available in downstream users // like platform/*/export/export.cpp. Could be fixed, but probably better to have // thirdparty includes in as little headers as possible. #include "thirdparty/minizip/unzip.h" diff --git a/core/math/geometry.cpp b/core/math/geometry.cpp index 0ab8707d3a..8314cb827c 100644 --- a/core/math/geometry.cpp +++ b/core/math/geometry.cpp @@ -31,8 +31,11 @@ #include "geometry.h" #include "core/print_string.h" +#include "thirdparty/misc/clipper.hpp" #include "thirdparty/misc/triangulator.h" +#define SCALE_FACTOR 100000.0 // based on CMP_EPSILON + /* this implementation is very inefficient, commenting unless bugs happen. See the other one. bool Geometry::is_point_in_polygon(const Vector2 &p_point, const Vector<Vector2> &p_polygon) { @@ -1134,3 +1137,106 @@ void Geometry::make_atlas(const Vector<Size2i> &p_rects, Vector<Point2i> &r_resu r_size = Size2(results[best].max_w, results[best].max_h); } + +Vector<Vector<Point2> > Geometry::_polypaths_do_operation(PolyBooleanOperation p_op, const Vector<Point2> &p_polypath_a, const Vector<Point2> &p_polypath_b, bool is_a_open) { + + using namespace ClipperLib; + + ClipType op = ctUnion; + + switch (p_op) { + case OPERATION_UNION: op = ctUnion; break; + case OPERATION_DIFFERENCE: op = ctDifference; break; + case OPERATION_INTERSECTION: op = ctIntersection; break; + case OPERATION_XOR: op = ctXor; break; + } + Path path_a, path_b; + + // Need to scale points (Clipper's requirement for robust computation) + for (int i = 0; i != p_polypath_a.size(); ++i) { + path_a << IntPoint(p_polypath_a[i].x * SCALE_FACTOR, p_polypath_a[i].y * SCALE_FACTOR); + } + for (int i = 0; i != p_polypath_b.size(); ++i) { + path_b << IntPoint(p_polypath_b[i].x * SCALE_FACTOR, p_polypath_b[i].y * SCALE_FACTOR); + } + Clipper clp; + clp.AddPath(path_a, ptSubject, !is_a_open); // forward compatible with Clipper 10.0.0 + clp.AddPath(path_b, ptClip, true); // polylines cannot be set as clip + + Paths paths; + + if (is_a_open) { + PolyTree tree; // needed to populate polylines + clp.Execute(op, tree); + OpenPathsFromPolyTree(tree, paths); + } else { + clp.Execute(op, paths); // works on closed polygons only + } + // Have to scale points down now + Vector<Vector<Point2> > polypaths; + + for (Paths::size_type i = 0; i < paths.size(); ++i) { + Vector<Vector2> polypath; + + const Path &scaled_path = paths[i]; + + for (Paths::size_type j = 0; j < scaled_path.size(); ++j) { + polypath.push_back(Point2( + static_cast<real_t>(scaled_path[j].X) / SCALE_FACTOR, + static_cast<real_t>(scaled_path[j].Y) / SCALE_FACTOR)); + } + polypaths.push_back(polypath); + } + return polypaths; +} + +Vector<Vector<Point2> > Geometry::_polypath_offset(const Vector<Point2> &p_polypath, real_t p_delta, PolyJoinType p_join_type, PolyEndType p_end_type) { + + using namespace ClipperLib; + + JoinType jt = jtSquare; + + switch (p_join_type) { + case JOIN_SQUARE: jt = jtSquare; break; + case JOIN_ROUND: jt = jtRound; break; + case JOIN_MITER: jt = jtMiter; break; + } + + EndType et = etClosedPolygon; + + switch (p_end_type) { + case END_POLYGON: et = etClosedPolygon; break; + case END_JOINED: et = etClosedLine; break; + case END_BUTT: et = etOpenButt; break; + case END_SQUARE: et = etOpenSquare; break; + case END_ROUND: et = etOpenRound; break; + } + ClipperOffset co; + Path path; + + // Need to scale points (Clipper's requirement for robust computation) + for (int i = 0; i != p_polypath.size(); ++i) { + path << IntPoint(p_polypath[i].x * SCALE_FACTOR, p_polypath[i].y * SCALE_FACTOR); + } + co.AddPath(path, jt, et); + + Paths paths; + co.Execute(paths, p_delta * SCALE_FACTOR); // inflate/deflate + + // Have to scale points down now + Vector<Vector<Point2> > polypaths; + + for (Paths::size_type i = 0; i < paths.size(); ++i) { + Vector<Vector2> polypath; + + const Path &scaled_path = paths[i]; + + for (Paths::size_type j = 0; j < scaled_path.size(); ++j) { + polypath.push_back(Point2( + static_cast<real_t>(scaled_path[j].X) / SCALE_FACTOR, + static_cast<real_t>(scaled_path[j].Y) / SCALE_FACTOR)); + } + polypaths.push_back(polypath); + } + return polypaths; +} diff --git a/core/math/geometry.h b/core/math/geometry.h index f3a671aa9a..0e144e491f 100644 --- a/core/math/geometry.h +++ b/core/math/geometry.h @@ -31,6 +31,7 @@ #ifndef GEOMETRY_H #define GEOMETRY_H +#include "core/math/delaunay.h" #include "core/math/face3.h" #include "core/math/rect2.h" #include "core/math/triangulate.h" @@ -785,6 +786,91 @@ public: return clipped; } + enum PolyBooleanOperation { + OPERATION_UNION, + OPERATION_DIFFERENCE, + OPERATION_INTERSECTION, + OPERATION_XOR + }; + enum PolyJoinType { + JOIN_SQUARE, + JOIN_ROUND, + JOIN_MITER + }; + enum PolyEndType { + END_POLYGON, + END_JOINED, + END_BUTT, + END_SQUARE, + END_ROUND + }; + + static Vector<Vector<Point2> > merge_polygons_2d(const Vector<Point2> &p_polygon_a, const Vector<Point2> &p_polygon_b) { + + return _polypaths_do_operation(OPERATION_UNION, p_polygon_a, p_polygon_b); + } + + static Vector<Vector<Point2> > clip_polygons_2d(const Vector<Point2> &p_polygon_a, const Vector<Point2> &p_polygon_b) { + + return _polypaths_do_operation(OPERATION_DIFFERENCE, p_polygon_a, p_polygon_b); + } + + static Vector<Vector<Point2> > intersect_polygons_2d(const Vector<Point2> &p_polygon_a, const Vector<Point2> &p_polygon_b) { + + return _polypaths_do_operation(OPERATION_INTERSECTION, p_polygon_a, p_polygon_b); + } + + static Vector<Vector<Point2> > exclude_polygons_2d(const Vector<Point2> &p_polygon_a, const Vector<Point2> &p_polygon_b) { + + return _polypaths_do_operation(OPERATION_XOR, p_polygon_a, p_polygon_b); + } + + static Vector<Vector<Point2> > clip_polyline_with_polygon_2d(const Vector<Vector2> &p_polyline, const Vector<Vector2> &p_polygon) { + + return _polypaths_do_operation(OPERATION_DIFFERENCE, p_polyline, p_polygon, true); + } + + static Vector<Vector<Point2> > intersect_polyline_with_polygon_2d(const Vector<Vector2> &p_polyline, const Vector<Vector2> &p_polygon) { + + return _polypaths_do_operation(OPERATION_INTERSECTION, p_polyline, p_polygon, true); + } + + static Vector<Vector<Point2> > offset_polygon_2d(const Vector<Vector2> &p_polygon, real_t p_delta, PolyJoinType p_join_type) { + + return _polypath_offset(p_polygon, p_delta, p_join_type, END_POLYGON); + } + + static Vector<Vector<Point2> > offset_polyline_2d(const Vector<Vector2> &p_polygon, real_t p_delta, PolyJoinType p_join_type, PolyEndType p_end_type) { + + ERR_EXPLAIN("Attempt to offset a polyline like a polygon (use offset_polygon_2d instead)."); + ERR_FAIL_COND_V(p_end_type == END_POLYGON, Vector<Vector<Point2> >()); + + return _polypath_offset(p_polygon, p_delta, p_join_type, p_end_type); + } + + static Vector<Point2> transform_points_2d(const Vector<Point2> &p_points, const Transform2D &p_mat) { + + Vector<Point2> points; + + for (int i = 0; i < p_points.size(); ++i) { + points.push_back(p_mat.xform(p_points[i])); + } + return points; + } + + static Vector<int> triangulate_delaunay_2d(const Vector<Vector2> &p_points) { + + Vector<Delaunay2D::Triangle> tr = Delaunay2D::triangulate(p_points); + Vector<int> triangles; + + for (int i = 0; i < tr.size(); i++) { + triangles.push_back(tr[i].points[0]); + triangles.push_back(tr[i].points[1]); + triangles.push_back(tr[i].points[2]); + } + return triangles; + } + static Vector<int> triangulate_polygon(const Vector<Vector2> &p_polygon) { Vector<int> triangles; @@ -833,7 +919,7 @@ public: further_away_opposite.y = MIN(p[i].y, further_away_opposite.y); } - further_away += (further_away - further_away_opposite) * Vector2(1.221313, 1.512312); // make point outside that wont intersect with points in segment from p_point + further_away += (further_away - further_away_opposite) * Vector2(1.221313, 1.512312); // make point outside that won't intersect with points in segment from p_point int intersections = 0; for (int i = 0; i < c; i++) { @@ -951,7 +1037,6 @@ public: H.resize(k); return H; } - static Vector<Vector<Vector2> > decompose_polygon_in_convex(Vector<Point2> polygon); static MeshData build_convex_mesh(const PoolVector<Plane> &p_planes); @@ -961,6 +1046,10 @@ public: static PoolVector<Plane> build_capsule_planes(real_t p_radius, real_t p_height, int p_sides, int p_lats, Vector3::Axis p_axis = Vector3::AXIS_Z); static void make_atlas(const Vector<Size2i> &p_rects, Vector<Point2i> &r_result, Size2i &r_size); + +private: + static Vector<Vector<Point2> > _polypaths_do_operation(PolyBooleanOperation p_op, const Vector<Point2> &p_polypath_a, const Vector<Point2> &p_polypath_b, bool is_a_open = false); + static Vector<Vector<Point2> > _polypath_offset(const Vector<Point2> &p_polypath, real_t p_delta, PolyJoinType p_join_type, PolyEndType p_end_type); }; #endif diff --git a/core/object.cpp b/core/object.cpp index 2a4ab93a6d..64f55f08a9 100644 --- a/core/object.cpp +++ b/core/object.cpp @@ -954,6 +954,16 @@ void Object::notification(int p_notification, bool p_reversed) { } } +String Object::to_string() { + if (script_instance) { + bool valid; + String ret = script_instance->to_string(&valid); + if (valid) + return ret; + } + return "[" + get_class() + ":" + itos(get_instance_id()) + "]"; +} + void Object::_changed_callback(Object *p_changed, const char *p_prop) { } @@ -1687,6 +1697,7 @@ void Object::_bind_methods() { ClassDB::bind_method(D_METHOD("get_property_list"), &Object::_get_property_list_bind); ClassDB::bind_method(D_METHOD("get_method_list"), &Object::_get_method_list_bind); ClassDB::bind_method(D_METHOD("notification", "what", "reversed"), &Object::notification, DEFVAL(false)); + ClassDB::bind_method(D_METHOD("to_string"), &Object::to_string); ClassDB::bind_method(D_METHOD("get_instance_id"), &Object::get_instance_id); ClassDB::bind_method(D_METHOD("set_script", "script"), &Object::set_script); @@ -1774,6 +1785,7 @@ void Object::_bind_methods() { #endif BIND_VMETHOD(MethodInfo("_init")); + BIND_VMETHOD(MethodInfo(Variant::STRING, "_to_string")); BIND_CONSTANT(NOTIFICATION_POSTINITIALIZE); BIND_CONSTANT(NOTIFICATION_PREDELETE); diff --git a/core/object.h b/core/object.h index 57ebb32392..4394c1c3da 100644 --- a/core/object.h +++ b/core/object.h @@ -659,6 +659,7 @@ public: void call_multilevel(const StringName &p_name, VARIANT_ARG_LIST); // C++ helper void notification(int p_notification, bool p_reversed = false); + String to_string(); //used mainly by script, get and set all INCLUDING string virtual Variant getvar(const Variant &p_key, bool *r_valid = NULL) const; diff --git a/core/os/os.h b/core/os/os.h index 4ae8a354e5..07865b636e 100644 --- a/core/os/os.h +++ b/core/os/os.h @@ -273,7 +273,7 @@ public: virtual String get_environment(const String &p_var) const = 0; virtual bool set_environment(const String &p_var, const String &p_value) const = 0; - virtual String get_name() = 0; + virtual String get_name() const = 0; virtual List<String> get_cmdline_args() const { return _cmdline; } virtual String get_model_name() const; diff --git a/core/script_language.cpp b/core/script_language.cpp index 4a6f904f9d..97758ced66 100644 --- a/core/script_language.cpp +++ b/core/script_language.cpp @@ -30,6 +30,7 @@ #include "script_language.h" +#include "core/core_string_names.h" #include "core/project_settings.h" ScriptLanguage *ScriptServer::_languages[MAX_LANGUAGES]; diff --git a/core/script_language.h b/core/script_language.h index 005e21e2cc..b2dab666c4 100644 --- a/core/script_language.h +++ b/core/script_language.h @@ -173,6 +173,11 @@ public: virtual void call_multilevel(const StringName &p_method, const Variant **p_args, int p_argcount); virtual void call_multilevel_reversed(const StringName &p_method, const Variant **p_args, int p_argcount); virtual void notification(int p_notification) = 0; + virtual String to_string(bool *r_valid) { + if (r_valid) + *r_valid = false; + return String(); + } //this is used by script languages that keep a reference counter of their own //you can make make Ref<> not die when it reaches zero, so deleting the reference diff --git a/core/undo_redo.cpp b/core/undo_redo.cpp index 69581e4115..f7ca6d3bde 100644 --- a/core/undo_redo.cpp +++ b/core/undo_redo.cpp @@ -239,8 +239,8 @@ void UndoRedo::_pop_history_tail() { } } -bool UndoRedo::is_commiting_action() const { - return commiting > 0; +bool UndoRedo::is_committing_action() const { + return committing > 0; } void UndoRedo::commit_action() { @@ -255,9 +255,9 @@ void UndoRedo::commit_action() { merging = false; } - commiting++; + committing++; redo(); // perform action - commiting--; + committing--; if (callback && actions.size() > 0) { callback(callback_ud, actions[actions.size() - 1].name); } @@ -396,7 +396,7 @@ void UndoRedo::set_property_notify_callback(PropertyNotifyCallback p_property_ca UndoRedo::UndoRedo() { - commiting = 0; + committing = 0; version = 1; action_level = 0; current_action = -1; @@ -496,10 +496,8 @@ void UndoRedo::_bind_methods() { ClassDB::bind_method(D_METHOD("create_action", "name", "merge_mode"), &UndoRedo::create_action, DEFVAL(MERGE_DISABLE)); ClassDB::bind_method(D_METHOD("commit_action"), &UndoRedo::commit_action); - ClassDB::bind_method(D_METHOD("is_commiting_action"), &UndoRedo::is_commiting_action); - - //ClassDB::bind_method(D_METHOD("add_do_method","p_object", "p_method", "VARIANT_ARG_LIST"),&UndoRedo::add_do_method); - //ClassDB::bind_method(D_METHOD("add_undo_method","p_object", "p_method", "VARIANT_ARG_LIST"),&UndoRedo::add_undo_method); + // FIXME: Typo in "commiting", fix in 4.0 when breaking compat. + ClassDB::bind_method(D_METHOD("is_commiting_action"), &UndoRedo::is_committing_action); { MethodInfo mi; diff --git a/core/undo_redo.h b/core/undo_redo.h index 6293e77acc..e2cc6c659b 100644 --- a/core/undo_redo.h +++ b/core/undo_redo.h @@ -95,7 +95,7 @@ private: MethodNotifyCallback method_callback; PropertyNotifyCallback property_callback; - int commiting; + int committing; protected: static void _bind_methods(); @@ -110,7 +110,7 @@ public: void add_do_reference(Object *p_object); void add_undo_reference(Object *p_object); - bool is_commiting_action() const; + bool is_committing_action() const; void commit_action(); bool redo(); diff --git a/core/variant.cpp b/core/variant.cpp index 1bc3cff505..6eadf59fce 100644 --- a/core/variant.cpp +++ b/core/variant.cpp @@ -1601,7 +1601,7 @@ String Variant::stringify(List<const void *> &stack) const { }; }; #endif - return "[" + _get_obj().obj->get_class() + ":" + itos(_get_obj().obj->get_instance_id()) + "]"; + return _get_obj().obj->to_string(); } else return "[Object:null]"; diff --git a/doc/classes/AcceptDialog.xml b/doc/classes/AcceptDialog.xml index 4adf515abc..db35b2f352 100644 --- a/doc/classes/AcceptDialog.xml +++ b/doc/classes/AcceptDialog.xml @@ -36,14 +36,14 @@ <return type="Label"> </return> <description> - Return the label used for built-in text. + Returns the label used for built-in text. </description> </method> <method name="get_ok"> <return type="Button"> </return> <description> - Return the OK Button. + Returns the OK Button. </description> </method> <method name="register_text_enter"> diff --git a/doc/classes/AnimatedSprite.xml b/doc/classes/AnimatedSprite.xml index 5e63f8aec0..da85f91367 100644 --- a/doc/classes/AnimatedSprite.xml +++ b/doc/classes/AnimatedSprite.xml @@ -13,7 +13,7 @@ <return type="bool"> </return> <description> - Return [code]true[/code] if an animation if currently being played. + Returns [code]true[/code] if an animation if currently being played. </description> </method> <method name="play"> diff --git a/doc/classes/AnimatedSprite3D.xml b/doc/classes/AnimatedSprite3D.xml index 4c6868d807..96196f7601 100644 --- a/doc/classes/AnimatedSprite3D.xml +++ b/doc/classes/AnimatedSprite3D.xml @@ -13,7 +13,7 @@ <return type="bool"> </return> <description> - Return [code]true[/code] if an animation if currently being played. + Returns [code]true[/code] if an animation if currently being played. </description> </method> <method name="play"> diff --git a/doc/classes/Animation.xml b/doc/classes/Animation.xml index af3abed256..9b322ac3f7 100644 --- a/doc/classes/Animation.xml +++ b/doc/classes/Animation.xml @@ -263,14 +263,14 @@ <argument index="0" name="path" type="NodePath"> </argument> <description> - Return the index of the specified track. If the track is not found, return -1. + Returns the index of the specified track. If the track is not found, return -1. </description> </method> <method name="get_track_count" qualifiers="const"> <return type="int"> </return> <description> - Return the amount of tracks in the animation. + Returns the amount of tracks in the animation. </description> </method> <method name="method_track_get_key_indices" qualifiers="const"> @@ -283,7 +283,7 @@ <argument index="2" name="delta" type="float"> </argument> <description> - Return all the key indices of a method track, given a position and delta time. + Returns all the key indices of a method track, given a position and delta time. </description> </method> <method name="method_track_get_name" qualifiers="const"> @@ -294,7 +294,7 @@ <argument index="1" name="key_idx" type="int"> </argument> <description> - Return the method name of a method track. + Returns the method name of a method track. </description> </method> <method name="method_track_get_params" qualifiers="const"> @@ -305,7 +305,7 @@ <argument index="1" name="key_idx" type="int"> </argument> <description> - Return the arguments values to be called on a method track for a given key in a given track. + Returns the arguments values to be called on a method track for a given key in a given track. </description> </method> <method name="remove_track"> @@ -345,7 +345,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the interpolation type of a given track, from the INTERPOLATION_* enum. + Returns the interpolation type of a given track, from the INTERPOLATION_* enum. </description> </method> <method name="track_get_key_count" qualifiers="const"> @@ -354,7 +354,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the amount of keys in a given track. + Returns the amount of keys in a given track. </description> </method> <method name="track_get_key_time" qualifiers="const"> @@ -365,7 +365,7 @@ <argument index="1" name="key_idx" type="int"> </argument> <description> - Return the time at which the key is located. + Returns the time at which the key is located. </description> </method> <method name="track_get_key_transition" qualifiers="const"> @@ -376,7 +376,7 @@ <argument index="1" name="key_idx" type="int"> </argument> <description> - Return the transition curve (easing) for a specific key (see built-in math function "ease"). + Returns the transition curve (easing) for a specific key (see built-in math function "ease"). </description> </method> <method name="track_get_key_value" qualifiers="const"> @@ -387,7 +387,7 @@ <argument index="1" name="key_idx" type="int"> </argument> <description> - Return the value of a given key in a given track. + Returns the value of a given key in a given track. </description> </method> <method name="track_get_path" qualifiers="const"> @@ -438,7 +438,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return [code]true[/code] if the given track is imported. Else, return [code]false[/code]. + Returns [code]true[/code] if the given track is imported. Else, return [code]false[/code]. </description> </method> <method name="track_move_down"> @@ -598,7 +598,7 @@ <argument index="1" name="time_sec" type="float"> </argument> <description> - Return the interpolated value of a transform track at a given time (in seconds). An array consisting of 3 elements: position ([Vector3]), rotation ([Quat]) and scale ([Vector3]). + Returns the interpolated value of a transform track at a given time (in seconds). An array consisting of 3 elements: position ([Vector3]), rotation ([Quat]) and scale ([Vector3]). </description> </method> <method name="value_track_get_key_indices" qualifiers="const"> @@ -611,7 +611,7 @@ <argument index="2" name="delta" type="float"> </argument> <description> - Return all the key indices of a value track, given a position and delta time. + Returns all the key indices of a value track, given a position and delta time. </description> </method> <method name="value_track_get_update_mode" qualifiers="const"> @@ -620,7 +620,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the update mode of a value track. + Returns the update mode of a value track. </description> </method> <method name="value_track_set_update_mode"> diff --git a/doc/classes/AnimationNode.xml b/doc/classes/AnimationNode.xml index e61fe374fa..9854d4c27e 100644 --- a/doc/classes/AnimationNode.xml +++ b/doc/classes/AnimationNode.xml @@ -144,7 +144,7 @@ <return type="String"> </return> <description> - Return [code]true[/code] whether you want the blend tree editor to display filter editing on this node. + Returns [code]true[/code] whether you want the blend tree editor to display filter editing on this node. </description> </method> <method name="is_path_filtered" qualifiers="const"> @@ -153,7 +153,7 @@ <argument index="0" name="path" type="NodePath"> </argument> <description> - Return [code]true[/code] wether a given path is filtered. + Returns [code]true[/code] whether a given path is filtered. </description> </method> <method name="process" qualifiers="virtual"> @@ -204,7 +204,7 @@ </methods> <members> <member name="filter_enabled" type="bool" setter="set_filter_enabled" getter="is_filter_enabled"> - Return whether filtering is enabled. + Returns whether filtering is enabled. </member> </members> <signals> diff --git a/doc/classes/AnimationNodeStateMachine.xml b/doc/classes/AnimationNodeStateMachine.xml index e46a40c4de..2834f83d2f 100644 --- a/doc/classes/AnimationNodeStateMachine.xml +++ b/doc/classes/AnimationNodeStateMachine.xml @@ -1,12 +1,13 @@ <?xml version="1.0" encoding="UTF-8" ?> <class name="AnimationNodeStateMachine" inherits="AnimationRootNode" category="Core" version="3.2"> <brief_description> + State machine for control of animations. </brief_description> <description> - Contains multiple root nodes as children in a graph. Each node is used as a state, and provides multiple functions to alternate between states. Retrieve the AnimationNodeStateMachinePlayback object from the [AnimationTree] node to control it programatically. + Contains multiple nodes representing animation states, connected in a graph. Nodes transitions can be configured to happen automatically or via code, using a shortest-path algorithm. Retrieve the AnimationNodeStateMachinePlayback object from the [AnimationTree] node to control it programatically. Example: [codeblock] - var state_machine = anim_tree["parameters/StateMachine/playback"] - state_machine.travel("SomeState") + var state_machine = $AnimationTree.get("parameters/playback") + state_machine.travel("some_state") [/codeblock] </description> <tutorials> @@ -22,6 +23,7 @@ <argument index="2" name="position" type="Vector2" default="Vector2( 0, 0 )"> </argument> <description> + Adds a new node to the graph. The [code]position[/code] is used for display in the editor. </description> </method> <method name="add_transition"> @@ -34,18 +36,21 @@ <argument index="2" name="transition" type="AnimationNodeStateMachineTransition"> </argument> <description> + Adds a transition between the given nodes. </description> </method> <method name="get_end_node" qualifiers="const"> <return type="String"> </return> <description> + Returns the graph's end node. </description> </method> <method name="get_graph_offset" qualifiers="const"> <return type="Vector2"> </return> <description> + Returns the draw offset of the graph. Used for display in the editor. </description> </method> <method name="get_node" qualifiers="const"> @@ -54,6 +59,7 @@ <argument index="0" name="name" type="String"> </argument> <description> + Returns the animation node with the given name. </description> </method> <method name="get_node_name" qualifiers="const"> @@ -62,6 +68,7 @@ <argument index="0" name="node" type="AnimationNode"> </argument> <description> + Returns the given animation node's name. </description> </method> <method name="get_node_position" qualifiers="const"> @@ -70,12 +77,14 @@ <argument index="0" name="name" type="String"> </argument> <description> + Returns the given node's coordinates. Used for display in the editor. </description> </method> <method name="get_start_node" qualifiers="const"> <return type="String"> </return> <description> + Returns the graph's end node. </description> </method> <method name="get_transition" qualifiers="const"> @@ -84,12 +93,14 @@ <argument index="0" name="idx" type="int"> </argument> <description> + Returns the given transition. </description> </method> <method name="get_transition_count" qualifiers="const"> <return type="int"> </return> <description> + Returns the number of connections in the graph. </description> </method> <method name="get_transition_from" qualifiers="const"> @@ -98,6 +109,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> + Returns the given transition's start node. </description> </method> <method name="get_transition_to" qualifiers="const"> @@ -106,6 +118,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> + Returns the given transition's end node. </description> </method> <method name="has_node" qualifiers="const"> @@ -114,6 +127,7 @@ <argument index="0" name="name" type="String"> </argument> <description> + Returns [code]true[/code] if the graph contains the given node. </description> </method> <method name="has_transition" qualifiers="const"> @@ -124,6 +138,7 @@ <argument index="1" name="to" type="String"> </argument> <description> + Returns [code]true[/code] if there is a transition between the given nodes. </description> </method> <method name="remove_node"> @@ -132,6 +147,7 @@ <argument index="0" name="name" type="String"> </argument> <description> + Deletes the given node from the graph. </description> </method> <method name="remove_transition"> @@ -142,6 +158,7 @@ <argument index="1" name="to" type="String"> </argument> <description> + Deletes the given transition. </description> </method> <method name="remove_transition_by_index"> @@ -150,6 +167,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> + Deletes the given transition. </description> </method> <method name="rename_node"> @@ -160,6 +178,7 @@ <argument index="1" name="new_name" type="String"> </argument> <description> + Renames the given node. </description> </method> <method name="set_end_node"> @@ -168,6 +187,7 @@ <argument index="0" name="name" type="String"> </argument> <description> + Sets the given node as the graph end point. </description> </method> <method name="set_graph_offset"> @@ -176,6 +196,7 @@ <argument index="0" name="offset" type="Vector2"> </argument> <description> + Sets the draw offset of the graph. Used for display in the editor. </description> </method> <method name="set_node_position"> @@ -186,6 +207,7 @@ <argument index="1" name="position" type="Vector2"> </argument> <description> + Sets the node's coordinates. Used for display in the editor. </description> </method> <method name="set_start_node"> @@ -194,6 +216,7 @@ <argument index="0" name="name" type="String"> </argument> <description> + Sets the given node as the graph start point. </description> </method> </methods> diff --git a/doc/classes/AnimationNodeStateMachinePlayback.xml b/doc/classes/AnimationNodeStateMachinePlayback.xml index fd38c28b16..796d92d7d6 100644 --- a/doc/classes/AnimationNodeStateMachinePlayback.xml +++ b/doc/classes/AnimationNodeStateMachinePlayback.xml @@ -1,8 +1,14 @@ <?xml version="1.0" encoding="UTF-8" ?> <class name="AnimationNodeStateMachinePlayback" inherits="Resource" category="Core" version="3.2"> <brief_description> + Playback control for AnimationNodeStateMachine. </brief_description> <description> + Allows control of [AnimationTree] state machines created with [AnimationNodeStateMachine]. Retrieve with [code]$AnimationTree.get("parameters/playback")[/code]. Example: + [codeblock] + var state_machine = $AnimationTree.get("parameters/playback") + state_machine.travel("some_state") + [/codeblock] </description> <tutorials> </tutorials> @@ -11,6 +17,7 @@ <return type="String"> </return> <description> + Returns the currently playing animation state. </description> </method> <method name="get_travel_path" qualifiers="const"> @@ -23,6 +30,7 @@ <return type="bool"> </return> <description> + Returns [code]true[/code] if an animation is playing. </description> </method> <method name="start"> @@ -31,12 +39,14 @@ <argument index="0" name="node" type="String"> </argument> <description> + Starts playing the given animation. </description> </method> <method name="stop"> <return type="void"> </return> <description> + Stops the currently playing animation. </description> </method> <method name="travel"> @@ -45,7 +55,7 @@ <argument index="0" name="to_node" type="String"> </argument> <description> - Transition from the current state to another one, while visiting all the intermediate ones. This is done via the A* algorithm. + Transitions from the current state to another one, following the shortest path. </description> </method> </methods> diff --git a/doc/classes/AnimationNodeStateMachineTransition.xml b/doc/classes/AnimationNodeStateMachineTransition.xml index a21ee50949..aeb44a789b 100644 --- a/doc/classes/AnimationNodeStateMachineTransition.xml +++ b/doc/classes/AnimationNodeStateMachineTransition.xml @@ -10,7 +10,10 @@ </methods> <members> <member name="advance_condition" type="String" setter="set_advance_condition" getter="get_advance_condition"> - Turn on auto advance when this condition is set. This is a custom text field that can be filled with a variable name. The variable can be modified from code. + Turn on auto advance when this condition is set. The provided name will become a boolean parameter on the [AnimationTree] that can be controlled from code (see [url=https://docs.godotengine.org/en/latest/tutorials/animation/animation_tree.html#controlling-from-code][/url]). For example, if [member AnimationTree.tree_root] is an [AnimationNodeStateMachine] and [member advance_condition] is set to "idle": + [codeblock] + $animation_tree["parameters/conditions/idle"] = is_on_floor and linear_velocity.x == 0 + [/codeblock] </member> <member name="auto_advance" type="bool" setter="set_auto_advance" getter="has_auto_advance"> Turn on the transition automatically when this state is reached. This works best with [code]SWITCH_MODE_AT_END[/code]. diff --git a/doc/classes/AnimationTreePlayer.xml b/doc/classes/AnimationTreePlayer.xml index 6160b44076..818565e0dc 100644 --- a/doc/classes/AnimationTreePlayer.xml +++ b/doc/classes/AnimationTreePlayer.xml @@ -256,7 +256,7 @@ <argument index="0" name="id" type="String"> </argument> <description> - Return the input count for a given node. Different types of nodes have different amount of inputs. + Returns the input count for a given node. Different types of nodes have different amount of inputs. </description> </method> <method name="node_get_input_source" qualifiers="const"> @@ -267,7 +267,7 @@ <argument index="1" name="idx" type="int"> </argument> <description> - Return the input source for a given node input. + Returns the input source for a given node input. </description> </method> <method name="node_get_position" qualifiers="const"> diff --git a/doc/classes/Area2D.xml b/doc/classes/Area2D.xml index 2400efe0d3..8d28ddc889 100644 --- a/doc/classes/Area2D.xml +++ b/doc/classes/Area2D.xml @@ -15,7 +15,7 @@ <argument index="0" name="bit" type="int"> </argument> <description> - Return an individual bit on the layer mask. Describes whether other areas will collide with this one on the given layer. + Returns an individual bit on the layer mask. Describes whether other areas will collide with this one on the given layer. </description> </method> <method name="get_collision_mask_bit" qualifiers="const"> @@ -24,7 +24,7 @@ <argument index="0" name="bit" type="int"> </argument> <description> - Return an individual bit on the collision mask. Describes whether this area will collide with others on the given layer. + Returns an individual bit on the collision mask. Describes whether this area will collide with others on the given layer. </description> </method> <method name="get_overlapping_areas" qualifiers="const"> diff --git a/doc/classes/ArrayMesh.xml b/doc/classes/ArrayMesh.xml index db0fc77b25..1707ea07e0 100644 --- a/doc/classes/ArrayMesh.xml +++ b/doc/classes/ArrayMesh.xml @@ -98,7 +98,7 @@ <argument index="0" name="name" type="String"> </argument> <description> - Return the index of the first surface with this name held within this [ArrayMesh]. If none are found -1 is returned. + Returns the index of the first surface with this name held within this [ArrayMesh]. If none are found -1 is returned. </description> </method> <method name="surface_get_array_index_len" qualifiers="const"> @@ -107,7 +107,7 @@ <argument index="0" name="surf_idx" type="int"> </argument> <description> - Return the length in indices of the index array in the requested surface (see [method add_surface_from_arrays]). + Returns the length in indices of the index array in the requested surface (see [method add_surface_from_arrays]). </description> </method> <method name="surface_get_array_len" qualifiers="const"> @@ -116,7 +116,7 @@ <argument index="0" name="surf_idx" type="int"> </argument> <description> - Return the length in vertices of the vertex array in the requested surface (see [method add_surface_from_arrays]). + Returns the length in vertices of the vertex array in the requested surface (see [method add_surface_from_arrays]). </description> </method> <method name="surface_get_format" qualifiers="const"> @@ -125,7 +125,7 @@ <argument index="0" name="surf_idx" type="int"> </argument> <description> - Return the format mask of the requested surface (see [method add_surface_from_arrays]). + Returns the format mask of the requested surface (see [method add_surface_from_arrays]). </description> </method> <method name="surface_get_name" qualifiers="const"> @@ -143,7 +143,7 @@ <argument index="0" name="surf_idx" type="int"> </argument> <description> - Return the primitive type of the requested surface (see [method add_surface_from_arrays]). + Returns the primitive type of the requested surface (see [method add_surface_from_arrays]). </description> </method> <method name="surface_remove"> diff --git a/doc/classes/BaseButton.xml b/doc/classes/BaseButton.xml index 7bd346ed5a..6d1a7a8f87 100644 --- a/doc/classes/BaseButton.xml +++ b/doc/classes/BaseButton.xml @@ -29,14 +29,14 @@ <return type="int" enum="BaseButton.DrawMode"> </return> <description> - Return the visual state used to draw the button. This is useful mainly when implementing your own draw code by either overriding _draw() or connecting to "draw" signal. The visual state of the button is defined by the DRAW_* enum. + Returns the visual state used to draw the button. This is useful mainly when implementing your own draw code by either overriding _draw() or connecting to "draw" signal. The visual state of the button is defined by the DRAW_* enum. </description> </method> <method name="is_hovered" qualifiers="const"> <return type="bool"> </return> <description> - Return [code]true[/code] if the mouse has entered the button and has not left it yet. + Returns [code]true[/code] if the mouse has entered the button and has not left it yet. </description> </method> </methods> diff --git a/doc/classes/Basis.xml b/doc/classes/Basis.xml index cee3035eab..ae7a3ff323 100644 --- a/doc/classes/Basis.xml +++ b/doc/classes/Basis.xml @@ -57,7 +57,7 @@ <return type="float"> </return> <description> - Return the determinant of the matrix. + Returns the determinant of the matrix. </description> </method> <method name="get_euler"> @@ -91,7 +91,7 @@ <return type="Basis"> </return> <description> - Return the inverse of the matrix. + Returns the inverse of the matrix. </description> </method> <method name="is_equal_approx"> @@ -108,7 +108,7 @@ <return type="Basis"> </return> <description> - Return the orthonormalized version of the matrix (useful to call from time to time to avoid rounding error for orthogonal matrices). This performs a Gram-Schmidt orthonormalization on the basis of the matrix. + Returns the orthonormalized version of the matrix (useful to call from time to time to avoid rounding error for orthogonal matrices). This performs a Gram-Schmidt orthonormalization on the basis of the matrix. </description> </method> <method name="rotated"> @@ -173,7 +173,7 @@ <return type="Basis"> </return> <description> - Return the transposed version of the matrix. + Returns the transposed version of the matrix. </description> </method> <method name="xform"> @@ -182,7 +182,7 @@ <argument index="0" name="v" type="Vector3"> </argument> <description> - Return a vector transformed (multiplied) by the matrix. + Returns a vector transformed (multiplied) by the matrix. </description> </method> <method name="xform_inv"> @@ -191,7 +191,7 @@ <argument index="0" name="v" type="Vector3"> </argument> <description> - Return a vector transformed (multiplied) by the transposed matrix. Note that this results in a multiplication by the inverse of the matrix only if it represents a rotation-reflection. + Returns a vector transformed (multiplied) by the transposed matrix. Note that this results in a multiplication by the inverse of the matrix only if it represents a rotation-reflection. </description> </method> </methods> diff --git a/doc/classes/Camera2D.xml b/doc/classes/Camera2D.xml index e5d1649c29..fcc99123d2 100644 --- a/doc/classes/Camera2D.xml +++ b/doc/classes/Camera2D.xml @@ -35,7 +35,7 @@ <return type="Vector2"> </return> <description> - Return the camera position. + Returns the camera position. </description> </method> <method name="get_camera_screen_center" qualifiers="const"> diff --git a/doc/classes/CanvasItem.xml b/doc/classes/CanvasItem.xml index 8ba3990933..2426471a49 100644 --- a/doc/classes/CanvasItem.xml +++ b/doc/classes/CanvasItem.xml @@ -342,14 +342,14 @@ <return type="RID"> </return> <description> - Return the [RID] of the [World2D] canvas where this item is in. + Returns the [RID] of the [World2D] canvas where this item is in. </description> </method> <method name="get_canvas_item" qualifiers="const"> <return type="RID"> </return> <description> - Return the canvas item RID used by [VisualServer] for this item. + Returns the canvas item RID used by [VisualServer] for this item. </description> </method> <method name="get_canvas_transform" qualifiers="const"> diff --git a/doc/classes/ClassDB.xml b/doc/classes/ClassDB.xml index b029c85409..ddbe66380a 100644 --- a/doc/classes/ClassDB.xml +++ b/doc/classes/ClassDB.xml @@ -121,7 +121,7 @@ <argument index="1" name="name" type="String"> </argument> <description> - Return whether 'class' or its ancestry has an integer constant called 'name' or not. + Returns whether 'class' or its ancestry has an integer constant called 'name' or not. </description> </method> <method name="class_has_method" qualifiers="const"> @@ -134,7 +134,7 @@ <argument index="2" name="no_inheritance" type="bool" default="false"> </argument> <description> - Return whether 'class' (or its ancestry if 'no_inheritance' is false) has a method called 'method' or not. + Returns whether 'class' (or its ancestry if 'no_inheritance' is false) has a method called 'method' or not. </description> </method> <method name="class_has_signal" qualifiers="const"> @@ -145,7 +145,7 @@ <argument index="1" name="signal" type="String"> </argument> <description> - Return whether 'class' or its ancestry has a signal called 'signal' or not. + Returns whether 'class' or its ancestry has a signal called 'signal' or not. </description> </method> <method name="class_set_property" qualifiers="const"> diff --git a/doc/classes/ColorPicker.xml b/doc/classes/ColorPicker.xml index a58edb5ca8..32e6014c75 100644 --- a/doc/classes/ColorPicker.xml +++ b/doc/classes/ColorPicker.xml @@ -31,7 +31,7 @@ <return type="PoolColorArray"> </return> <description> - Return the list of colors in the presets of the color picker. + Returns the list of colors in the presets of the color picker. </description> </method> </methods> diff --git a/doc/classes/ConcavePolygonShape.xml b/doc/classes/ConcavePolygonShape.xml index afc6ce74a5..62d42f4eb4 100644 --- a/doc/classes/ConcavePolygonShape.xml +++ b/doc/classes/ConcavePolygonShape.xml @@ -13,7 +13,7 @@ <return type="PoolVector3Array"> </return> <description> - Return the faces (an array of triangles). + Returns the faces (an array of triangles). </description> </method> <method name="set_faces"> diff --git a/doc/classes/ConfirmationDialog.xml b/doc/classes/ConfirmationDialog.xml index f39915f4b7..6124bc29b0 100644 --- a/doc/classes/ConfirmationDialog.xml +++ b/doc/classes/ConfirmationDialog.xml @@ -13,7 +13,7 @@ <return type="Button"> </return> <description> - Return the cancel button. + Returns the cancel button. </description> </method> </methods> diff --git a/doc/classes/Control.xml b/doc/classes/Control.xml index f7fbdf08ed..22061322c8 100644 --- a/doc/classes/Control.xml +++ b/doc/classes/Control.xml @@ -221,7 +221,7 @@ <argument index="0" name="position" type="Vector2"> </argument> <description> - Godot calls this method to get data that can be dragged and dropped onto controls that expect drop data. Return null if there is no data to drag. Controls that want to receive drop data should implement [method can_drop_data] and [method drop_data]. [code]position[/code] is local to this control. Drag may be forced with [method force_drag]. + Godot calls this method to get data that can be dragged and dropped onto controls that expect drop data. Returns null if there is no data to drag. Controls that want to receive drop data should implement [method can_drop_data] and [method drop_data]. [code]position[/code] is local to this control. Drag may be forced with [method force_drag]. A preview that will follow the mouse that should represent the data can be set with [method set_drag_preview]. A good time to set the preview is in this method. [codeblock] extends Control @@ -512,7 +512,7 @@ </return> <argument index="0" name="preset" type="int" enum="Control.LayoutPreset"> </argument> - <argument index="1" name="keep_margin" type="bool" default="false"> + <argument index="1" name="keep_margins" type="bool" default="false"> </argument> <description> </description> @@ -574,6 +574,16 @@ Sets [member margin_right] and [member margin_bottom] at the same time. </description> </method> + <method name="set_global_position"> + <return type="void"> + </return> + <argument index="0" name="position" type="Vector2"> + </argument> + <argument index="1" name="keep_margins" type="bool" default="false"> + </argument> + <description> + </description> + </method> <method name="set_margins_preset"> <return type="void"> </return> @@ -586,6 +596,16 @@ <description> </description> </method> + <method name="set_position"> + <return type="void"> + </return> + <argument index="0" name="position" type="Vector2"> + </argument> + <argument index="1" name="keep_margins" type="bool" default="false"> + </argument> + <description> + </description> + </method> <method name="set_rotation"> <return type="void"> </return> @@ -595,6 +615,16 @@ Sets the rotation (in radians). </description> </method> + <method name="set_size"> + <return type="void"> + </return> + <argument index="0" name="size" type="Vector2"> + </argument> + <argument index="1" name="keep_margins" type="bool" default="false"> + </argument> + <description> + </description> + </method> <method name="show_modal"> <return type="void"> </return> diff --git a/doc/classes/Dictionary.xml b/doc/classes/Dictionary.xml index b6b17d03fb..ec70fd311b 100644 --- a/doc/classes/Dictionary.xml +++ b/doc/classes/Dictionary.xml @@ -38,7 +38,7 @@ <return type="bool"> </return> <description> - Return [code]true[/code] if the dictionary is empty. + Returns [code]true[/code] if the dictionary is empty. </description> </method> <method name="erase"> @@ -67,7 +67,7 @@ <argument index="0" name="key" type="Variant"> </argument> <description> - Return [code]true[/code] if the dictionary has a given key. + Returns [code]true[/code] if the dictionary has a given key. </description> </method> <method name="has_all"> @@ -76,35 +76,35 @@ <argument index="0" name="keys" type="Array"> </argument> <description> - Return [code]true[/code] if the dictionary has all of the keys in the given array. + Returns [code]true[/code] if the dictionary has all of the keys in the given array. </description> </method> <method name="hash"> <return type="int"> </return> <description> - Return a hashed integer value representing the dictionary contents. + Returns a hashed integer value representing the dictionary contents. </description> </method> <method name="keys"> <return type="Array"> </return> <description> - Return the list of keys in the [Dictionary]. + Returns the list of keys in the [Dictionary]. </description> </method> <method name="size"> <return type="int"> </return> <description> - Return the size of the dictionary (in pairs). + Returns the size of the dictionary (in pairs). </description> </method> <method name="values"> <return type="Array"> </return> <description> - Return the list of values in the [Dictionary]. + Returns the list of values in the [Dictionary]. </description> </method> </methods> diff --git a/doc/classes/Directory.xml b/doc/classes/Directory.xml index 8a81695198..54aac33652 100644 --- a/doc/classes/Directory.xml +++ b/doc/classes/Directory.xml @@ -52,7 +52,7 @@ <return type="bool"> </return> <description> - Return whether the current item processed with the last [method get_next] call is a directory ([code].[/code] and [code]..[/code] are considered directories). + Returns whether the current item processed with the last [method get_next] call is a directory ([code].[/code] and [code]..[/code] are considered directories). </description> </method> <method name="dir_exists"> @@ -61,7 +61,7 @@ <argument index="0" name="path" type="String"> </argument> <description> - Return whether the target directory exists. The argument can be relative to the current directory, or an absolute path. + Returns whether the target directory exists. The argument can be relative to the current directory, or an absolute path. </description> </method> <method name="file_exists"> @@ -70,14 +70,14 @@ <argument index="0" name="path" type="String"> </argument> <description> - Return whether the target file exists. The argument can be relative to the current directory, or an absolute path. + Returns whether the target file exists. The argument can be relative to the current directory, or an absolute path. </description> </method> <method name="get_current_dir"> <return type="String"> </return> <description> - Return the absolute path to the currently opened directory (e.g. [code]res://folder[/code] or [code]C:\tmp\folder[/code]). + Returns the absolute path to the currently opened directory (e.g. [code]res://folder[/code] or [code]C:\tmp\folder[/code]). </description> </method> <method name="get_current_drive"> @@ -107,7 +107,7 @@ <return type="String"> </return> <description> - Return the next element (file or directory) in the current directory (including [code].[/code] and [code]..[/code], unless [code]skip_navigational[/code] was given to [method list_dir_begin]). + Returns the next element (file or directory) in the current directory (including [code].[/code] and [code]..[/code], unless [code]skip_navigational[/code] was given to [method list_dir_begin]). The name of the file or directory is returned (and not its full path). Once the stream has been fully processed, the method returns an empty String and closes the stream automatically (i.e. [method list_dir_end] would not be mandatory in such a case). </description> </method> @@ -155,7 +155,7 @@ </argument> <description> Create a target directory and all necessary intermediate directories in its path, by calling [method make_dir] recursively. The argument can be relative to the current directory, or an absolute path. - Return one of the error code constants defined in [@GlobalScope] (OK, FAILED or ERR_*). + Returns one of the error code constants defined in [@GlobalScope] (OK, FAILED or ERR_*). </description> </method> <method name="open"> @@ -175,7 +175,7 @@ </argument> <description> Delete the target file or an empty directory. The argument can be relative to the current directory, or an absolute path. If the target directory is not empty, the operation will fail. - Return one of the error code constants defined in [@GlobalScope] (OK or FAILED). + Returns one of the error code constants defined in [@GlobalScope] (OK or FAILED). </description> </method> <method name="rename"> @@ -187,7 +187,7 @@ </argument> <description> Rename (move) the [i]from[/i] file to the [i]to[/i] destination. Both arguments should be paths to files, either relative or absolute. If the destination file exists and is not access-protected, it will be overwritten. - Return one of the error code constants defined in [@GlobalScope] (OK or FAILED). + Returns one of the error code constants defined in [@GlobalScope] (OK or FAILED). </description> </method> </methods> diff --git a/doc/classes/EditorExportPlugin.xml b/doc/classes/EditorExportPlugin.xml index 998b05d495..4e4e29dc4e 100644 --- a/doc/classes/EditorExportPlugin.xml +++ b/doc/classes/EditorExportPlugin.xml @@ -21,6 +21,12 @@ <description> </description> </method> + <method name="_export_end" qualifiers="virtual"> + <return type="void"> + </return> + <description> + </description> + </method> <method name="_export_file" qualifiers="virtual"> <return type="void"> </return> diff --git a/doc/classes/EditorFileSystem.xml b/doc/classes/EditorFileSystem.xml index 531af4c4e0..1c7a68fc0b 100644 --- a/doc/classes/EditorFileSystem.xml +++ b/doc/classes/EditorFileSystem.xml @@ -38,14 +38,14 @@ <return type="float"> </return> <description> - Return the scan progress for 0 to 1 if the FS is being scanned. + Returns the scan progress for 0 to 1 if the FS is being scanned. </description> </method> <method name="is_scanning" qualifiers="const"> <return type="bool"> </return> <description> - Return [code]true[/code] of the filesystem is being scanned. + Returns [code]true[/code] of the filesystem is being scanned. </description> </method> <method name="scan"> diff --git a/doc/classes/EditorInspectorPlugin.xml b/doc/classes/EditorInspectorPlugin.xml index f2dcd2177c..c2b13ff89e 100644 --- a/doc/classes/EditorInspectorPlugin.xml +++ b/doc/classes/EditorInspectorPlugin.xml @@ -21,7 +21,7 @@ <argument index="0" name="control" type="Control"> </argument> <description> - Add a custom control, not necesarily a property editor. + Add a custom control, not necessarily a property editor. </description> </method> <method name="add_property_editor"> @@ -54,7 +54,7 @@ <argument index="0" name="object" type="Object"> </argument> <description> - Return true if this object can be handled by this plugin. + Returns true if this object can be handled by this plugin. </description> </method> <method name="parse_begin" qualifiers="virtual"> diff --git a/doc/classes/EditorPlugin.xml b/doc/classes/EditorPlugin.xml index 5763d26561..97ad4f6829 100644 --- a/doc/classes/EditorPlugin.xml +++ b/doc/classes/EditorPlugin.xml @@ -241,7 +241,7 @@ <return type="EditorInterface"> </return> <description> - Return the [EditorInterface] object that gives you control over Godot editor's window and its functionalities. + Returns the [EditorInterface] object that gives you control over Godot editor's window and its functionalities. </description> </method> <method name="get_plugin_icon" qualifiers="virtual"> @@ -299,7 +299,7 @@ <return type="bool"> </return> <description> - Return [code]true[/code] if this is a main screen editor plugin (it goes in the workspaces selector together with '2D', '3D', and 'Script'). + Returns [code]true[/code] if this is a main screen editor plugin (it goes in the workspaces selector together with '2D', '3D', and 'Script'). </description> </method> <method name="hide_bottom_panel"> diff --git a/doc/classes/EditorResourcePreviewGenerator.xml b/doc/classes/EditorResourcePreviewGenerator.xml index 6592ffd1a8..156cc62941 100644 --- a/doc/classes/EditorResourcePreviewGenerator.xml +++ b/doc/classes/EditorResourcePreviewGenerator.xml @@ -9,6 +9,14 @@ <tutorials> </tutorials> <methods> + <method name="can_generate_small_preview" qualifiers="virtual"> + <return type="bool"> + </return> + <description> + If this function returns true the generator will call [method generate] or [method generate_from_path] for small previews too. + By default it returns false. + </description> + </method> <method name="generate" qualifiers="virtual"> <return type="Texture"> </return> @@ -35,13 +43,21 @@ Care must be taken because this function is always called from a thread (not the main thread). </description> </method> + <method name="generate_small_preview_automatically" qualifiers="virtual"> + <return type="bool"> + </return> + <description> + If this function returns true the generator will automatically generate the small previews from the normal preview texture generated by the methods [method generate] or [method generate_from_path]. + By default it returns false. + </description> + </method> <method name="handles" qualifiers="virtual"> <return type="bool"> </return> <argument index="0" name="type" type="String"> </argument> <description> - Return if your generator supports this resource type. + Returns if your generator supports this resource type. </description> </method> </methods> diff --git a/doc/classes/EditorSpatialGizmo.xml b/doc/classes/EditorSpatialGizmo.xml index da7fee1cf7..5d5c37b212 100644 --- a/doc/classes/EditorSpatialGizmo.xml +++ b/doc/classes/EditorSpatialGizmo.xml @@ -123,7 +123,7 @@ <return type="EditorSpatialGizmoPlugin"> </return> <description> - Return the [EditorSpatialGizmoPlugin] that owns this gizmo. It's useful to retrieve materials using [method EditorSpatialGizmoPlugin.get_material]. + Returns the [EditorSpatialGizmoPlugin] that owns this gizmo. It's useful to retrieve materials using [method EditorSpatialGizmoPlugin.get_material]. </description> </method> <method name="get_spatial_node" qualifiers="const"> diff --git a/doc/classes/FileDialog.xml b/doc/classes/FileDialog.xml index 66e6fa5314..953f364bdb 100644 --- a/doc/classes/FileDialog.xml +++ b/doc/classes/FileDialog.xml @@ -43,7 +43,7 @@ <return type="VBoxContainer"> </return> <description> - Return the vertical box container of the dialog, custom controls can be added to it. + Returns the vertical box container of the dialog, custom controls can be added to it. </description> </method> <method name="invalidate"> diff --git a/doc/classes/Font.xml b/doc/classes/Font.xml index 5792b539e0..d65dad9fe1 100644 --- a/doc/classes/Font.xml +++ b/doc/classes/Font.xml @@ -51,21 +51,21 @@ <return type="float"> </return> <description> - Return the font ascent (number of pixels above the baseline). + Returns the font ascent (number of pixels above the baseline). </description> </method> <method name="get_descent" qualifiers="const"> <return type="float"> </return> <description> - Return the font descent (number of pixels below the baseline). + Returns the font descent (number of pixels below the baseline). </description> </method> <method name="get_height" qualifiers="const"> <return type="float"> </return> <description> - Return the total font height (ascent plus descent) in pixels. + Returns the total font height (ascent plus descent) in pixels. </description> </method> <method name="get_string_size" qualifiers="const"> @@ -74,7 +74,7 @@ <argument index="0" name="string" type="String"> </argument> <description> - Return the size of a string, taking kerning and advance into account. + Returns the size of a string, taking kerning and advance into account. </description> </method> <method name="get_wordwrap_string_size" qualifiers="const"> diff --git a/doc/classes/Geometry.xml b/doc/classes/Geometry.xml index 68539d7ecb..e2ba3fb7b0 100644 --- a/doc/classes/Geometry.xml +++ b/doc/classes/Geometry.xml @@ -59,6 +59,29 @@ Clips the polygon defined by the points in [code]points[/code] against the [code]plane[/code] and returns the points of the clipped polygon. </description> </method> + <method name="clip_polygons_2d"> + <return type="Array"> + </return> + <argument index="0" name="polygon_a" type="PoolVector2Array"> + </argument> + <argument index="1" name="polygon_b" type="PoolVector2Array"> + </argument> + <description> + Clips [code]polygon_a[/code] against [code]polygon_b[/code] and returns an array of clipped polygons. This performs [code]OPERATION_DIFFERENCE[/code] between polygons. Returns an empty array if [code]polygon_b[/code] completely overlaps [code]polygon_a[/code]. + If [code]polygon_b[/code] is enclosed by [code]polygon_a[/code], returns an outer polygon (boundary) and inner polygon (hole) which could be distiguished by calling [method is_polygon_clockwise]. + </description> + </method> + <method name="clip_polyline_with_polygon_2d"> + <return type="Array"> + </return> + <argument index="0" name="polyline" type="PoolVector2Array"> + </argument> + <argument index="1" name="polygon" type="PoolVector2Array"> + </argument> + <description> + Clips [code]polyline[/code] against [code]polygon[/code] and returns an array of clipped polylines. This performs [code]OPERATION_DIFFERENCE[/code] between the polyline and the polygon. This operation can be thought of as cutting a line with a closed shape. + </description> + </method> <method name="convex_hull_2d"> <return type="PoolVector2Array"> </return> @@ -68,6 +91,18 @@ Given an array of [Vector2]s, returns the convex hull as a list of points in counter-clockwise order. The last point is the same as the first one. </description> </method> + <method name="exclude_polygons_2d"> + <return type="Array"> + </return> + <argument index="0" name="polygon_a" type="PoolVector2Array"> + </argument> + <argument index="1" name="polygon_b" type="PoolVector2Array"> + </argument> + <description> + Mutually excludes common area defined by intersection of [code]polygon_a[/code] and [code]polygon_b[/code] (see [method intersect_polygons_2d]) and returns an array of excluded polygons. This performs [code]OPERATION_XOR[/code] between polygons. In other words, returns all but common area between polygons. + The operation may result in an outer polygon (boundary) and inner polygon (hole) produced which could be distiguished by calling [method is_polygon_clockwise]. + </description> + </method> <method name="get_closest_point_to_segment"> <return type="Vector3"> </return> @@ -158,6 +193,38 @@ <description> </description> </method> + <method name="intersect_polygons_2d"> + <return type="Array"> + </return> + <argument index="0" name="polygon_a" type="PoolVector2Array"> + </argument> + <argument index="1" name="polygon_b" type="PoolVector2Array"> + </argument> + <description> + Intersects [code]polygon_a[/code] with [code]polygon_b[/code] and returns an array of intersected polygons. This performs [code]OPERATION_INTERSECTION[/code] between polygons. In other words, returns common area shared by polygons. Returns an empty array if no intersection occurs. + The operation may result in an outer polygon (boundary) and inner polygon (hole) produced which could be distiguished by calling [method is_polygon_clockwise]. + </description> + </method> + <method name="intersect_polyline_with_polygon_2d"> + <return type="Array"> + </return> + <argument index="0" name="polyline" type="PoolVector2Array"> + </argument> + <argument index="1" name="polygon" type="PoolVector2Array"> + </argument> + <description> + Intersects [code]polyline[/code] with [code]polygon[/code] and returns an array of intersected polylines. This performs [code]OPERATION_INTERSECTION[/code] between the polyline and the polygon. This operation can be thought of as chopping a line with a closed shape. + </description> + </method> + <method name="is_polygon_clockwise"> + <return type="bool"> + </return> + <argument index="0" name="polygon" type="PoolVector2Array"> + </argument> + <description> + Returns [code]true[/code] if [code]polygon[/code]'s vertices are ordered in clockwise order, otherwise returns [code]false[/code]. + </description> + </method> <method name="line_intersects_line_2d"> <return type="Variant"> </return> @@ -182,6 +249,51 @@ Given an array of [Vector2]s representing tiles, builds an atlas. The returned dictionary has two keys: [code]points[/code] is a vector of [Vector2] that specifies the positions of each tile, [code]size[/code] contains the overall size of the whole atlas as [Vector2]. </description> </method> + <method name="merge_polygons_2d"> + <return type="Array"> + </return> + <argument index="0" name="polygon_a" type="PoolVector2Array"> + </argument> + <argument index="1" name="polygon_b" type="PoolVector2Array"> + </argument> + <description> + Merges (combines) [code]polygon_a[/code] and [code]polygon_b[/code] and returns an array of merged polygons. This performs [code]OPERATION_UNION[/code] between polygons. + The operation may result in an outer polygon (boundary) and inner polygon (hole) produced which could be distiguished by calling [method is_polygon_clockwise]. + </description> + </method> + <method name="offset_polygon_2d"> + <return type="Array"> + </return> + <argument index="0" name="polygon" type="PoolVector2Array"> + </argument> + <argument index="1" name="delta" type="float"> + </argument> + <argument index="2" name="join_type" type="int" enum="Geometry.PolyJoinType" default="0"> + </argument> + <description> + Inflates or deflates [code]polygon[/code] by [code]delta[/code] units (pixels). If [code]delta[/code] is positive, makes the polygon grow outward. If [code]delta[/code] is negative, shrinks the polygon inward. Returns an array of polygons because inflating/deflating may result in multiple discrete polygons. Returns an empty array if [code]delta[/code] is negative and the absolute value of it approximately exceeds the minimum bounding rectangle dimensions of the polygon. + Each polygon's vertices will be rounded as determined by [code]join_type[/code], see [enum Geometry.PolyJoinType]. + The operation may result in an outer polygon (boundary) and inner polygon (hole) produced which could be distiguished by calling [method is_polygon_clockwise]. + </description> + </method> + <method name="offset_polyline_2d"> + <return type="Array"> + </return> + <argument index="0" name="polyline" type="PoolVector2Array"> + </argument> + <argument index="1" name="delta" type="float"> + </argument> + <argument index="2" name="join_type" type="int" enum="Geometry.PolyJoinType" default="0"> + </argument> + <argument index="3" name="end_type" type="int" enum="Geometry.PolyEndType" default="3"> + </argument> + <description> + Inflates or deflates [code]polyline[/code] by [code]delta[/code] units (pixels), producing polygons. If [code]delta[/code] is positive, makes the polyline grow outward. Returns an array of polygons because inflating/deflating may result in multiple discrete polygons. If [code]delta[/code] is negative, returns an empty array. + Each polygon's vertices will be rounded as determined by [code]join_type[/code], see [enum Geometry.PolyJoinType]. + Each polygon's endpoints will be rounded as determined by [code]end_type[/code], see [enum Geometry.PolyEndType]. + The operation may result in an outer polygon (boundary) and inner polygon (hole) produced which could be distiguished by calling [method is_polygon_clockwise]. + </description> + </method> <method name="point_is_inside_triangle" qualifiers="const"> <return type="bool"> </return> @@ -304,6 +416,27 @@ Tests if the segment ([code]from[/code], [code]to[/code]) intersects the triangle [code]a[/code], [code]b[/code], [code]c[/code]. If yes, returns the point of intersection as [Vector3]. If no intersection takes place, an empty [Variant] is returned. </description> </method> + <method name="transform_points_2d"> + <return type="PoolVector2Array"> + </return> + <argument index="0" name="points" type="PoolVector2Array"> + </argument> + <argument index="1" name="transform" type="Transform2D"> + </argument> + <description> + Transforms an array of points by [code]transform[/code] and returns the result. + Can be useful in conjuction with performing polygon boolean operations in CSG manner, see [method merge_polygons_2d], [method clip_polygons_2d], [method intersect_polygons_2d], [method exclude_polygons_2d]. + </description> + </method> + <method name="triangulate_delaunay_2d"> + <return type="PoolIntArray"> + </return> + <argument index="0" name="points" type="PoolVector2Array"> + </argument> + <description> + Triangulates the area specified by discrete set of [code]points[/code] such that no point is inside the circumcircle of any resulting triangle. Returns a [PoolIntArray] where each triangle consists of three consecutive point indices into [code]points[/code] (i.e. the returned array will have [code]n * 3[/code] elements, with [code]n[/code] being the number of found triangles). If the triangulation did not succeed, an empty [PoolIntArray] is returned. + </description> + </method> <method name="triangulate_polygon"> <return type="PoolIntArray"> </return> @@ -315,5 +448,41 @@ </method> </methods> <constants> + <constant name="OPERATION_UNION" value="0" enum="PolyBooleanOperation"> + Create regions where either subject or clip polygons (or both) are filled. + </constant> + <constant name="OPERATION_DIFFERENCE" value="1" enum="PolyBooleanOperation"> + Create regions where subject polygons are filled except where clip polygons are filled. + </constant> + <constant name="OPERATION_INTERSECTION" value="2" enum="PolyBooleanOperation"> + Create regions where both subject and clip polygons are filled. + </constant> + <constant name="OPERATION_XOR" value="3" enum="PolyBooleanOperation"> + Create regions where either subject or clip polygons are filled but not where both are filled. + </constant> + <constant name="JOIN_SQUARE" value="0" enum="PolyJoinType"> + Squaring is applied uniformally at all convex edge joins at [code]1 * delta[/code]. + </constant> + <constant name="JOIN_ROUND" value="1" enum="PolyJoinType"> + While flattened paths can never perfectly trace an arc, they are approximated by a series of arc chords. + </constant> + <constant name="JOIN_MITER" value="2" enum="PolyJoinType"> + There's a necessary limit to mitered joins since offsetting edges that join at very acute angles will produce excessively long and narrow 'spikes'. For any given edge join, when miter offsetting would exceed that maximum distance, 'square' joining is applied. + </constant> + <constant name="END_POLYGON" value="0" enum="PolyEndType"> + Endpoints are joined using the [enum PolyJoinType] value and the path filled as a polygon. + </constant> + <constant name="END_JOINED" value="1" enum="PolyEndType"> + Endpoints are joined using the [enum PolyJoinType] value and the path filled as a polyline. + </constant> + <constant name="END_BUTT" value="2" enum="PolyEndType"> + Endpoints are squared off with no extension. + </constant> + <constant name="END_SQUARE" value="3" enum="PolyEndType"> + Endpoints are squared off and extended by [code]delta[/code] units. + </constant> + <constant name="END_ROUND" value="4" enum="PolyEndType"> + Endpoints are rounded off and extended by [code]delta[/code] units. + </constant> </constants> </class> diff --git a/doc/classes/GraphEdit.xml b/doc/classes/GraphEdit.xml index 145cd243bc..db186eab35 100644 --- a/doc/classes/GraphEdit.xml +++ b/doc/classes/GraphEdit.xml @@ -80,7 +80,7 @@ <return type="Array"> </return> <description> - Return an Array containing the list of connections. A connection consists in a structure of the form {from_port: 0, from: "GraphNode name 0", to_port: 1, to: "GraphNode name 1" } + Returns an Array containing the list of connections. A connection consists in a structure of the form {from_port: 0, from: "GraphNode name 0", to_port: 1, to: "GraphNode name 1" } </description> </method> <method name="get_zoom_hbox"> @@ -101,7 +101,7 @@ <argument index="3" name="to_port" type="int"> </argument> <description> - Return [code]true[/code] if the 'from_port' slot of 'from' GraphNode is connected to the 'to_port' slot of 'to' GraphNode. + Returns [code]true[/code] if the 'from_port' slot of 'from' GraphNode is connected to the 'to_port' slot of 'to' GraphNode. </description> </method> <method name="is_valid_connection_type" qualifiers="const"> diff --git a/doc/classes/GraphNode.xml b/doc/classes/GraphNode.xml index 4d6f3180d0..a19676798b 100644 --- a/doc/classes/GraphNode.xml +++ b/doc/classes/GraphNode.xml @@ -31,14 +31,14 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the color of the input connection 'idx'. + Returns the color of the input connection 'idx'. </description> </method> <method name="get_connection_input_count"> <return type="int"> </return> <description> - Return the number of enabled input slots (connections) to the GraphNode. + Returns the number of enabled input slots (connections) to the GraphNode. </description> </method> <method name="get_connection_input_position"> @@ -47,7 +47,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the position of the input connection 'idx'. + Returns the position of the input connection 'idx'. </description> </method> <method name="get_connection_input_type"> @@ -56,7 +56,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the type of the input connection 'idx'. + Returns the type of the input connection 'idx'. </description> </method> <method name="get_connection_output_color"> @@ -65,14 +65,14 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the color of the output connection 'idx'. + Returns the color of the output connection 'idx'. </description> </method> <method name="get_connection_output_count"> <return type="int"> </return> <description> - Return the number of enabled output slots (connections) of the GraphNode. + Returns the number of enabled output slots (connections) of the GraphNode. </description> </method> <method name="get_connection_output_position"> @@ -81,7 +81,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the position of the output connection 'idx'. + Returns the position of the output connection 'idx'. </description> </method> <method name="get_connection_output_type"> @@ -90,7 +90,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the type of the output connection 'idx'. + Returns the type of the output connection 'idx'. </description> </method> <method name="get_slot_color_left" qualifiers="const"> @@ -99,7 +99,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the color set to 'idx' left (input) slot. + Returns the color set to 'idx' left (input) slot. </description> </method> <method name="get_slot_color_right" qualifiers="const"> @@ -108,7 +108,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the color set to 'idx' right (output) slot. + Returns the color set to 'idx' right (output) slot. </description> </method> <method name="get_slot_type_left" qualifiers="const"> @@ -117,7 +117,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the (integer) type of left (input) 'idx' slot. + Returns the (integer) type of left (input) 'idx' slot. </description> </method> <method name="get_slot_type_right" qualifiers="const"> @@ -126,7 +126,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the (integer) type of right (output) 'idx' slot. + Returns the (integer) type of right (output) 'idx' slot. </description> </method> <method name="is_slot_enabled_left" qualifiers="const"> @@ -135,7 +135,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return [code]true[/code] if left (input) slot 'idx' is enabled, [code]false[/code] otherwise. + Returns [code]true[/code] if left (input) slot 'idx' is enabled, [code]false[/code] otherwise. </description> </method> <method name="is_slot_enabled_right" qualifiers="const"> @@ -144,7 +144,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return [code]true[/code] if right (output) slot 'idx' is enabled, [code]false[/code] otherwise. + Returns [code]true[/code] if right (output) slot 'idx' is enabled, [code]false[/code] otherwise. </description> </method> <method name="set_slot"> diff --git a/doc/classes/ImageTexture.xml b/doc/classes/ImageTexture.xml index 15ecd4ee6d..e5a8fee767 100644 --- a/doc/classes/ImageTexture.xml +++ b/doc/classes/ImageTexture.xml @@ -40,7 +40,7 @@ <return type="int" enum="Image.Format"> </return> <description> - Return the format of the [ImageTexture], one of [enum Image.Format]. + Returns the format of the [ImageTexture], one of [enum Image.Format]. </description> </method> <method name="load"> diff --git a/doc/classes/Input.xml b/doc/classes/Input.xml index 319f84b8d2..9c41e4bf1d 100644 --- a/doc/classes/Input.xml +++ b/doc/classes/Input.xml @@ -194,7 +194,7 @@ <return type="int" enum="Input.MouseMode"> </return> <description> - Return the mouse mode. See the constants for more information. + Returns the mouse mode. See the constants for more information. </description> </method> <method name="is_action_just_pressed" qualifiers="const"> diff --git a/doc/classes/ItemList.xml b/doc/classes/ItemList.xml index 663eeda77a..ba3a7fe6d8 100644 --- a/doc/classes/ItemList.xml +++ b/doc/classes/ItemList.xml @@ -64,7 +64,7 @@ <return type="int"> </return> <description> - Return count of items currently in the item list. + Returns count of items currently in the item list. </description> </method> <method name="get_item_custom_bg_color" qualifiers="const"> @@ -122,7 +122,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the text for specified item index. + Returns the text for specified item index. </description> </method> <method name="get_item_tooltip" qualifiers="const"> @@ -131,7 +131,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return tooltip hint for specified item index. + Returns tooltip hint for specified item index. </description> </method> <method name="get_selected_items"> diff --git a/doc/classes/Marshalls.xml b/doc/classes/Marshalls.xml index 0d07d8b649..c7118a4d9f 100644 --- a/doc/classes/Marshalls.xml +++ b/doc/classes/Marshalls.xml @@ -15,7 +15,7 @@ <argument index="0" name="base64_str" type="String"> </argument> <description> - Return [PoolByteArray] of a given base64 encoded String. + Returns [PoolByteArray] of a given base64 encoded String. </description> </method> <method name="base64_to_utf8"> @@ -24,7 +24,7 @@ <argument index="0" name="base64_str" type="String"> </argument> <description> - Return utf8 String of a given base64 encoded String. + Returns utf8 String of a given base64 encoded String. </description> </method> <method name="base64_to_variant"> @@ -35,7 +35,7 @@ <argument index="1" name="allow_objects" type="bool" default="false"> </argument> <description> - Return [Variant] of a given base64 encoded String. When [code]allow_objects[/code] is [code]true[/code] decoding objects is allowed. + Returns [Variant] of a given base64 encoded String. When [code]allow_objects[/code] is [code]true[/code] decoding objects is allowed. [b]WARNING:[/b] Deserialized object can contain code which gets executed. Do not use this option if the serialized object comes from untrusted sources to avoid potential security threats (remote code execution). </description> </method> @@ -45,7 +45,7 @@ <argument index="0" name="array" type="PoolByteArray"> </argument> <description> - Return base64 encoded String of a given [PoolByteArray]. + Returns base64 encoded String of a given [PoolByteArray]. </description> </method> <method name="utf8_to_base64"> @@ -54,7 +54,7 @@ <argument index="0" name="utf8_str" type="String"> </argument> <description> - Return base64 encoded String of a given utf8 String. + Returns base64 encoded String of a given utf8 String. </description> </method> <method name="variant_to_base64"> @@ -65,7 +65,7 @@ <argument index="1" name="full_objects" type="bool" default="false"> </argument> <description> - Return base64 encoded String of a given [Variant]. When [code]full_objects[/code] is [code]true[/code] encoding objects is allowed (and can potentially include code). + Returns base64 encoded String of a given [Variant]. When [code]full_objects[/code] is [code]true[/code] encoding objects is allowed (and can potentially include code). </description> </method> </methods> diff --git a/doc/classes/MenuButton.xml b/doc/classes/MenuButton.xml index dadc31b794..1043aa1087 100644 --- a/doc/classes/MenuButton.xml +++ b/doc/classes/MenuButton.xml @@ -13,7 +13,7 @@ <return type="PopupMenu"> </return> <description> - Return the [PopupMenu] contained in this button. + Returns the [PopupMenu] contained in this button. </description> </method> <method name="set_disable_shortcuts"> diff --git a/doc/classes/Mesh.xml b/doc/classes/Mesh.xml index ae035341f6..b8bc5cbd11 100644 --- a/doc/classes/Mesh.xml +++ b/doc/classes/Mesh.xml @@ -50,7 +50,7 @@ <return type="int"> </return> <description> - Return the amount of surfaces that the [Mesh] holds. + Returns the amount of surfaces that the [Mesh] holds. </description> </method> <method name="surface_get_arrays" qualifiers="const"> @@ -77,7 +77,7 @@ <argument index="0" name="surf_idx" type="int"> </argument> <description> - Return a [Material] in a given surface. Surface is rendered using this material. + Returns a [Material] in a given surface. Surface is rendered using this material. </description> </method> </methods> diff --git a/doc/classes/MeshLibrary.xml b/doc/classes/MeshLibrary.xml index de4f6cdf72..ad5824640d 100644 --- a/doc/classes/MeshLibrary.xml +++ b/doc/classes/MeshLibrary.xml @@ -37,7 +37,7 @@ <return type="PoolIntArray"> </return> <description> - Return the list of items. + Returns the list of items. </description> </method> <method name="get_item_mesh" qualifiers="const"> @@ -46,7 +46,7 @@ <argument index="0" name="id" type="int"> </argument> <description> - Return the mesh of the item. + Returns the mesh of the item. </description> </method> <method name="get_item_name" qualifiers="const"> @@ -55,7 +55,7 @@ <argument index="0" name="id" type="int"> </argument> <description> - Return the name of the item. + Returns the name of the item. </description> </method> <method name="get_item_navmesh" qualifiers="const"> diff --git a/doc/classes/MultiMesh.xml b/doc/classes/MultiMesh.xml index 1532fac206..0784fc3a42 100644 --- a/doc/classes/MultiMesh.xml +++ b/doc/classes/MultiMesh.xml @@ -17,7 +17,7 @@ <return type="AABB"> </return> <description> - Return the visibility AABB. + Returns the visibility AABB. </description> </method> <method name="get_instance_color" qualifiers="const"> @@ -35,7 +35,7 @@ <argument index="0" name="instance" type="int"> </argument> <description> - Return the custom data that has been set for a specific instance. + Returns the custom data that has been set for a specific instance. </description> </method> <method name="get_instance_transform" qualifiers="const"> @@ -44,7 +44,7 @@ <argument index="0" name="instance" type="int"> </argument> <description> - Return the [Transform] of a specific instance. + Returns the [Transform] of a specific instance. </description> </method> <method name="get_instance_transform_2d" qualifiers="const"> @@ -53,7 +53,7 @@ <argument index="0" name="instance" type="int"> </argument> <description> - Return the [Transform2D] of a specific instance. + Returns the [Transform2D] of a specific instance. </description> </method> <method name="set_as_bulk_array"> diff --git a/doc/classes/NodePath.xml b/doc/classes/NodePath.xml index 73739ba79a..554858d895 100644 --- a/doc/classes/NodePath.xml +++ b/doc/classes/NodePath.xml @@ -68,14 +68,14 @@ <return type="bool"> </return> <description> - Return [code]true[/code] if the node path is absolute (not relative). + Returns [code]true[/code] if the node path is absolute (not relative). </description> </method> <method name="is_empty"> <return type="bool"> </return> <description> - Return [code]true[/code] if the node path is empty. + Returns [code]true[/code] if the node path is empty. </description> </method> </methods> diff --git a/doc/classes/Object.xml b/doc/classes/Object.xml index 9c2a65ce5b..dbbd974b04 100644 --- a/doc/classes/Object.xml +++ b/doc/classes/Object.xml @@ -57,6 +57,14 @@ Sets a property. Returns [code]true[/code] if the [code]property[/code] exists. </description> </method> + <method name="_to_string" qualifiers="virtual"> + <return type="String"> + </return> + <description> + Returns a [String] representing the object. Default is [code]"[ClassName:RID]"[/code]. + Override this method to customize the [String] representation of the object when it's being converted to a string, for example: [code]print(obj)[/code]. + </description> + </method> <method name="add_user_signal"> <return type="void"> </return> @@ -404,6 +412,14 @@ Set a script into the object, scripts extend the object functionality. </description> </method> + <method name="to_string"> + <return type="String"> + </return> + <description> + Returns a [String] representing the object. Default is [code]"[ClassName:RID]"[/code]. + Override the method [method _to_string] to customize the [String] representation. + </description> + </method> <method name="tr" qualifiers="const"> <return type="String"> </return> diff --git a/doc/classes/OptionButton.xml b/doc/classes/OptionButton.xml index 06b4cb165e..1f714656de 100644 --- a/doc/classes/OptionButton.xml +++ b/doc/classes/OptionButton.xml @@ -51,7 +51,7 @@ <return type="int"> </return> <description> - Return the amount of items in the OptionButton. + Returns the amount of items in the OptionButton. </description> </method> <method name="get_item_icon" qualifiers="const"> @@ -60,7 +60,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the icon of the item at index "idx". + Returns the icon of the item at index "idx". </description> </method> <method name="get_item_id" qualifiers="const"> @@ -69,7 +69,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the ID of the item at index [code]idx[/code]. + Returns the ID of the item at index [code]idx[/code]. </description> </method> <method name="get_item_index" qualifiers="const"> @@ -78,7 +78,7 @@ <argument index="0" name="id" type="int"> </argument> <description> - Return the index of the item with the given [code]id[/code]. + Returns the index of the item with the given [code]id[/code]. </description> </method> <method name="get_item_metadata" qualifiers="const"> @@ -95,14 +95,14 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the text of the item at index "idx". + Returns the text of the item at index "idx". </description> </method> <method name="get_popup" qualifiers="const"> <return type="PopupMenu"> </return> <description> - Return the [PopupMenu] contained in this button. + Returns the [PopupMenu] contained in this button. </description> </method> <method name="get_selected_id" qualifiers="const"> diff --git a/doc/classes/PacketPeer.xml b/doc/classes/PacketPeer.xml index 5a54c7ba1c..4109d9d462 100644 --- a/doc/classes/PacketPeer.xml +++ b/doc/classes/PacketPeer.xml @@ -13,7 +13,7 @@ <return type="int"> </return> <description> - Return the number of packets currently available in the ring-buffer. + Returns the number of packets currently available in the ring-buffer. </description> </method> <method name="get_packet"> @@ -27,7 +27,7 @@ <return type="int" enum="Error"> </return> <description> - Return the error state of the last packet received (via [method get_packet] and [method get_var]). + Returns the error state of the last packet received (via [method get_packet] and [method get_var]). </description> </method> <method name="get_var"> diff --git a/doc/classes/PacketPeerUDP.xml b/doc/classes/PacketPeerUDP.xml index 5892eb17b7..9843c16108 100644 --- a/doc/classes/PacketPeerUDP.xml +++ b/doc/classes/PacketPeerUDP.xml @@ -20,21 +20,21 @@ <return type="String"> </return> <description> - Return the IP of the remote peer that sent the last packet(that was received with [method PacketPeer.get_packet] or [method PacketPeer.get_var]). + Returns the IP of the remote peer that sent the last packet(that was received with [method PacketPeer.get_packet] or [method PacketPeer.get_var]). </description> </method> <method name="get_packet_port" qualifiers="const"> <return type="int"> </return> <description> - Return the port of the remote peer that sent the last packet(that was received with [method PacketPeer.get_packet] or [method PacketPeer.get_var]). + Returns the port of the remote peer that sent the last packet(that was received with [method PacketPeer.get_packet] or [method PacketPeer.get_var]). </description> </method> <method name="is_listening" qualifiers="const"> <return type="bool"> </return> <description> - Return whether this [PacketPeerUDP] is listening. + Returns whether this [PacketPeerUDP] is listening. </description> </method> <method name="listen"> diff --git a/doc/classes/PhysicsBody.xml b/doc/classes/PhysicsBody.xml index 4d94c57ad1..fc4f2e18fd 100644 --- a/doc/classes/PhysicsBody.xml +++ b/doc/classes/PhysicsBody.xml @@ -32,7 +32,7 @@ <argument index="0" name="bit" type="int"> </argument> <description> - Returns an individual bit on the collision mask. + Returns an individual bit on the [member collision_layer]. </description> </method> <method name="get_collision_mask_bit" qualifiers="const"> @@ -41,7 +41,7 @@ <argument index="0" name="bit" type="int"> </argument> <description> - Returns an individual bit on the collision mask. + Returns an individual bit on the [member collision_mask]. </description> </method> <method name="remove_collision_exception_with"> @@ -61,7 +61,7 @@ <argument index="1" name="value" type="bool"> </argument> <description> - Sets individual bits on the layer mask. Use this if you only need to change one layer's value. + Sets individual bits on the [member collision_layer] bitmask. Use this if you only need to change one layer's value. </description> </method> <method name="set_collision_mask_bit"> @@ -72,18 +72,20 @@ <argument index="1" name="value" type="bool"> </argument> <description> - Sets individual bits on the collision mask. Use this if you only need to change one layer's value. + Sets individual bits on the [member collision_mask] bitmask. Use this if you only need to change one layer's value. </description> </method> </methods> <members> <member name="collision_layer" type="int" setter="set_collision_layer" getter="get_collision_layer"> The physics layers this area is in. - Collidable objects can exist in any of 32 different layers. These layers work like a tagging system, and are not visual. A collidable can use these layers to select with which objects it can collide, using the collision_mask property. + Collidable objects can exist in any of 32 different layers. These layers work like a tagging system, and are not visual. A collidable can use these layers to select with which objects it can collide, using the [member collision_mask] property. A contact is detected if object A is in any of the layers that object B scans, or object B is in any layer scanned by object A. + Default value: 1 (the first layer/bit is enabled). </member> <member name="collision_mask" type="int" setter="set_collision_mask" getter="get_collision_mask"> The physics layers this area scans for collisions. + Default value: 1 (the first layer/bit is enabled). </member> </members> <constants> diff --git a/doc/classes/PhysicsBody2D.xml b/doc/classes/PhysicsBody2D.xml index faa992ef7a..a5024c2432 100644 --- a/doc/classes/PhysicsBody2D.xml +++ b/doc/classes/PhysicsBody2D.xml @@ -32,7 +32,7 @@ <argument index="0" name="bit" type="int"> </argument> <description> - Returns an individual bit on the collision mask. + Returns an individual bit on the [member collision_layer]. </description> </method> <method name="get_collision_mask_bit" qualifiers="const"> @@ -41,7 +41,7 @@ <argument index="0" name="bit" type="int"> </argument> <description> - Returns an individual bit on the collision mask. + Returns an individual bit on the [member collision_mask]. </description> </method> <method name="remove_collision_exception_with"> @@ -61,7 +61,7 @@ <argument index="1" name="value" type="bool"> </argument> <description> - Sets individual bits on the layer mask. Use this if you only need to change one layer's value. + Sets individual bits on the [member collision_layer] bitmask. Use this if you only need to change one layer's value. </description> </method> <method name="set_collision_mask_bit"> @@ -72,18 +72,20 @@ <argument index="1" name="value" type="bool"> </argument> <description> - Sets individual bits on the collision mask. Use this if you only need to change one layer's value. + Sets individual bits on the [member collision_mask] bitmask. Use this if you only need to change one layer's value. </description> </method> </methods> <members> <member name="collision_layer" type="int" setter="set_collision_layer" getter="get_collision_layer"> The physics layers this area is in. - Collidable objects can exist in any of 32 different layers. These layers work like a tagging system, and are not visual. A collidable can use these layers to select with which objects it can collide, using the collision_mask property. + Collidable objects can exist in any of 32 different layers. These layers work like a tagging system, and are not visual. A collidable can use these layers to select with which objects it can collide, using the [member collision_mask] property. A contact is detected if object A is in any of the layers that object B scans, or object B is in any layer scanned by object A. + Default value: 1 (the first layer/bit is enabled). </member> <member name="collision_mask" type="int" setter="set_collision_mask" getter="get_collision_mask"> The physics layers this area scans for collisions. + Default value: 1 (the first layer/bit is enabled). </member> <member name="layers" type="int" setter="_set_layers" getter="_get_layers"> Both [member collision_layer] and [member collision_mask]. Returns [member collision_layer] when accessed. Updates [member collision_layer] and [member collision_mask] when modified. diff --git a/doc/classes/PoolByteArray.xml b/doc/classes/PoolByteArray.xml index f46cb243d7..cb99b660ae 100644 --- a/doc/classes/PoolByteArray.xml +++ b/doc/classes/PoolByteArray.xml @@ -116,14 +116,14 @@ <return type="String"> </return> <description> - Return SHA256 string of the PoolByteArray. + Returns SHA256 string of the PoolByteArray. </description> </method> <method name="size"> <return type="int"> </return> <description> - Return the size of the array. + Returns the size of the array. </description> </method> <method name="subarray"> diff --git a/doc/classes/PoolColorArray.xml b/doc/classes/PoolColorArray.xml index d16029a8d7..efc3582ba4 100644 --- a/doc/classes/PoolColorArray.xml +++ b/doc/classes/PoolColorArray.xml @@ -82,7 +82,7 @@ <return type="int"> </return> <description> - Return the size of the array. + Returns the size of the array. </description> </method> </methods> diff --git a/doc/classes/PoolIntArray.xml b/doc/classes/PoolIntArray.xml index 83d73c8a24..fca1083c25 100644 --- a/doc/classes/PoolIntArray.xml +++ b/doc/classes/PoolIntArray.xml @@ -82,7 +82,7 @@ <return type="int"> </return> <description> - Return the array size. + Returns the array size. </description> </method> </methods> diff --git a/doc/classes/PoolRealArray.xml b/doc/classes/PoolRealArray.xml index e1da99519c..c5f6062175 100644 --- a/doc/classes/PoolRealArray.xml +++ b/doc/classes/PoolRealArray.xml @@ -82,7 +82,7 @@ <return type="int"> </return> <description> - Return the size of the array. + Returns the size of the array. </description> </method> </methods> diff --git a/doc/classes/PoolStringArray.xml b/doc/classes/PoolStringArray.xml index 6ef4222996..01dca93be3 100644 --- a/doc/classes/PoolStringArray.xml +++ b/doc/classes/PoolStringArray.xml @@ -91,7 +91,7 @@ <return type="int"> </return> <description> - Return the size of the array. + Returns the size of the array. </description> </method> </methods> diff --git a/doc/classes/PoolVector2Array.xml b/doc/classes/PoolVector2Array.xml index 50ded06b90..45f619dc5d 100644 --- a/doc/classes/PoolVector2Array.xml +++ b/doc/classes/PoolVector2Array.xml @@ -82,7 +82,7 @@ <return type="int"> </return> <description> - Return the size of the array. + Returns the size of the array. </description> </method> </methods> diff --git a/doc/classes/PoolVector3Array.xml b/doc/classes/PoolVector3Array.xml index 69b4e54692..0a682e2baf 100644 --- a/doc/classes/PoolVector3Array.xml +++ b/doc/classes/PoolVector3Array.xml @@ -82,7 +82,7 @@ <return type="int"> </return> <description> - Return the size of the array. + Returns the size of the array. </description> </method> </methods> diff --git a/doc/classes/PopupMenu.xml b/doc/classes/PopupMenu.xml index a91f765d41..d4f4834a66 100644 --- a/doc/classes/PopupMenu.xml +++ b/doc/classes/PopupMenu.xml @@ -178,14 +178,14 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the accelerator of the item at index "idx". Accelerators are special combinations of keys that activate the item, no matter which control is focused. + Returns the accelerator of the item at index "idx". Accelerators are special combinations of keys that activate the item, no matter which control is focused. </description> </method> <method name="get_item_count" qualifiers="const"> <return type="int"> </return> <description> - Return the amount of items. + Returns the amount of items. </description> </method> <method name="get_item_icon" qualifiers="const"> @@ -194,7 +194,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the icon of the item at index "idx". + Returns the icon of the item at index "idx". </description> </method> <method name="get_item_id" qualifiers="const"> @@ -203,7 +203,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the id of the item at index "idx". + Returns the id of the item at index "idx". </description> </method> <method name="get_item_index" qualifiers="const"> @@ -221,7 +221,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the metadata of an item, which might be of any type. You can set it with [method set_item_metadata], which provides a simple way of assigning context data to items. + Returns the metadata of an item, which might be of any type. You can set it with [method set_item_metadata], which provides a simple way of assigning context data to items. </description> </method> <method name="get_item_shortcut" qualifiers="const"> @@ -238,7 +238,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the submenu name of the item at index "idx". + Returns the submenu name of the item at index "idx". </description> </method> <method name="get_item_text" qualifiers="const"> @@ -247,7 +247,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return the text of the item at index "idx". + Returns the text of the item at index "idx". </description> </method> <method name="get_item_tooltip" qualifiers="const"> @@ -270,7 +270,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return whether the item at index "idx" is checkable in some way, i.e., whether has a checkbox or radio button. Note that checkable items just display a checkmark or radio button, but don't have any built-in checking behavior and must be checked/unchecked manually. + Returns whether the item at index "idx" is checkable in some way, i.e., whether has a checkbox or radio button. Note that checkable items just display a checkmark or radio button, but don't have any built-in checking behavior and must be checked/unchecked manually. </description> </method> <method name="is_item_checked" qualifiers="const"> @@ -279,7 +279,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return whether the item at index "idx" is checked. + Returns whether the item at index "idx" is checked. </description> </method> <method name="is_item_disabled" qualifiers="const"> @@ -288,7 +288,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return whether the item at index "idx" is disabled. When it is disabled it can't be selected, or its action invoked. + Returns whether the item at index "idx" is disabled. When it is disabled it can't be selected, or its action invoked. </description> </method> <method name="is_item_radio_checkable" qualifiers="const"> @@ -297,7 +297,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return whether the item at index "idx" has radio-button-style checkability. Remember this is just cosmetic and you have to add the logic for checking/unchecking items in radio groups. + Returns whether the item at index "idx" has radio-button-style checkability. Remember this is just cosmetic and you have to add the logic for checking/unchecking items in radio groups. </description> </method> <method name="is_item_separator" qualifiers="const"> @@ -306,7 +306,7 @@ <argument index="0" name="idx" type="int"> </argument> <description> - Return whether the item is a separator. If it is, it would be displayed as a line. + Returns whether the item is a separator. If it is, it would be displayed as a line. </description> </method> <method name="is_item_shortcut_disabled" qualifiers="const"> diff --git a/doc/classes/PrismMesh.xml b/doc/classes/PrismMesh.xml index 0d0f330647..4c282c5e8d 100644 --- a/doc/classes/PrismMesh.xml +++ b/doc/classes/PrismMesh.xml @@ -12,7 +12,7 @@ </methods> <members> <member name="left_to_right" type="float" setter="set_left_to_right" getter="get_left_to_right"> - Displacement of the upper edge along the x-axis. 0.0 positions edge straight above the bottome left edge. Defaults to 0.5 (positioned on the midpoint). + Displacement of the upper edge along the x-axis. 0.0 positions edge straight above the bottom left edge. Defaults to 0.5 (positioned on the midpoint). </member> <member name="size" type="Vector3" setter="set_size" getter="get_size"> Size of the prism. Defaults to (2.0, 2.0, 2.0). diff --git a/doc/classes/Quat.xml b/doc/classes/Quat.xml index f7134e580d..3ef65e1edb 100644 --- a/doc/classes/Quat.xml +++ b/doc/classes/Quat.xml @@ -84,7 +84,7 @@ <return type="Vector3"> </return> <description> - Return Euler angles (in the YXZ convention: first Z, then X, and Y last) corresponding to the rotation represented by the unit quaternion. Returned vector contains the rotation angles in the format (X-angle, Y-angle, Z-angle). + Returns Euler angles (in the YXZ convention: first Z, then X, and Y last) corresponding to the rotation represented by the unit quaternion. Returned vector contains the rotation angles in the format (X-angle, Y-angle, Z-angle). </description> </method> <method name="inverse"> diff --git a/doc/classes/RayCast.xml b/doc/classes/RayCast.xml index 1d2999a1ed..1368143b67 100644 --- a/doc/classes/RayCast.xml +++ b/doc/classes/RayCast.xml @@ -50,7 +50,7 @@ <return type="Object"> </return> <description> - Return the first object that the ray intersects, or [code]null[/code] if no object is intersecting the ray (i.e. [method is_colliding] returns [code]false[/code]). + Returns the first object that the ray intersects, or [code]null[/code] if no object is intersecting the ray (i.e. [method is_colliding] returns [code]false[/code]). </description> </method> <method name="get_collider_shape" qualifiers="const"> @@ -87,7 +87,7 @@ <return type="bool"> </return> <description> - Return whether any object is intersecting with the ray's vector (considering the vector length). + Returns whether any object is intersecting with the ray's vector (considering the vector length). </description> </method> <method name="remove_exception"> diff --git a/doc/classes/RayCast2D.xml b/doc/classes/RayCast2D.xml index 7a16e9e5e0..90e0178ddb 100644 --- a/doc/classes/RayCast2D.xml +++ b/doc/classes/RayCast2D.xml @@ -49,7 +49,7 @@ <return type="Object"> </return> <description> - Return the first object that the ray intersects, or [code]null[/code] if no object is intersecting the ray (i.e. [method is_colliding] returns [code]false[/code]). + Returns the first object that the ray intersects, or [code]null[/code] if no object is intersecting the ray (i.e. [method is_colliding] returns [code]false[/code]). </description> </method> <method name="get_collider_shape" qualifiers="const"> @@ -65,7 +65,7 @@ <argument index="0" name="bit" type="int"> </argument> <description> - Return an individual bit on the collision mask. + Returns an individual bit on the collision mask. </description> </method> <method name="get_collision_normal" qualifiers="const"> @@ -86,7 +86,7 @@ <return type="bool"> </return> <description> - Return whether any object is intersecting with the ray's vector (considering the vector length). + Returns whether any object is intersecting with the ray's vector (considering the vector length). </description> </method> <method name="remove_exception"> diff --git a/doc/classes/ResourceInteractiveLoader.xml b/doc/classes/ResourceInteractiveLoader.xml index 6b37cb25fb..bb9826999c 100644 --- a/doc/classes/ResourceInteractiveLoader.xml +++ b/doc/classes/ResourceInteractiveLoader.xml @@ -13,21 +13,21 @@ <return type="Resource"> </return> <description> - Return the loaded resource (only if loaded). Otherwise, returns null. + Returns the loaded resource (only if loaded). Otherwise, returns null. </description> </method> <method name="get_stage" qualifiers="const"> <return type="int"> </return> <description> - Return the load stage. The total amount of stages can be queried with [method get_stage_count] + Returns the load stage. The total amount of stages can be queried with [method get_stage_count] </description> </method> <method name="get_stage_count" qualifiers="const"> <return type="int"> </return> <description> - Return the total amount of stages (calls to [method poll]) needed to completely load this resource. + Returns the total amount of stages (calls to [method poll]) needed to completely load this resource. </description> </method> <method name="poll"> diff --git a/doc/classes/ResourceLoader.xml b/doc/classes/ResourceLoader.xml index 70deb4509f..76b7c39191 100644 --- a/doc/classes/ResourceLoader.xml +++ b/doc/classes/ResourceLoader.xml @@ -33,7 +33,7 @@ <argument index="0" name="type" type="String"> </argument> <description> - Return the list of recognized extensions for a resource type. + Returns the list of recognized extensions for a resource type. </description> </method> <method name="has"> diff --git a/doc/classes/RigidBody.xml b/doc/classes/RigidBody.xml index 25b896ec3a..9ea6bb0fe1 100644 --- a/doc/classes/RigidBody.xml +++ b/doc/classes/RigidBody.xml @@ -86,7 +86,7 @@ <return type="Array"> </return> <description> - Return a list of the bodies colliding with this one. By default, number of max contacts reported is at 0, see the [member contacts_reported] property to increase it. Note that the result of this test is not immediate after moving objects. For performance, list of collisions is updated once per frame and before the physics step. Consider using signals instead. + Returns a list of the bodies colliding with this one. By default, number of max contacts reported is at 0, see the [member contacts_reported] property to increase it. Note that the result of this test is not immediate after moving objects. For performance, list of collisions is updated once per frame and before the physics step. Consider using signals instead. </description> </method> <method name="set_axis_velocity"> diff --git a/doc/classes/Shape2D.xml b/doc/classes/Shape2D.xml index dec3c2b43c..c887e23de0 100644 --- a/doc/classes/Shape2D.xml +++ b/doc/classes/Shape2D.xml @@ -52,7 +52,7 @@ <argument index="4" name="shape_motion" type="Vector2"> </argument> <description> - Return whether this shape would collide with another, if a given movement was applied. + Returns whether this shape would collide with another, if a given movement was applied. This method needs the transformation matrix for this shape ([code]local_xform[/code]), the movement to test on this shape ([code]local_motion[/code]), the shape to check collisions with ([code]with_shape[/code]), the transformation matrix of that shape ([code]shape_xform[/code]), and the movement to test onto the other object ([code]shape_motion[/code]). </description> </method> diff --git a/doc/classes/Skeleton.xml b/doc/classes/Skeleton.xml index 8fab778a48..b693ee0a5e 100644 --- a/doc/classes/Skeleton.xml +++ b/doc/classes/Skeleton.xml @@ -44,14 +44,14 @@ <argument index="0" name="name" type="String"> </argument> <description> - Return the bone index that matches "name" as its name. + Returns the bone index that matches "name" as its name. </description> </method> <method name="get_bone_count" qualifiers="const"> <return type="int"> </return> <description> - Return the amount of bones in the skeleton. + Returns the amount of bones in the skeleton. </description> </method> <method name="get_bone_custom_pose" qualifiers="const"> @@ -60,7 +60,7 @@ <argument index="0" name="bone_idx" type="int"> </argument> <description> - Return the custom pose of the specified bone. Custom pose is applied on top of the rest pose. + Returns the custom pose of the specified bone. Custom pose is applied on top of the rest pose. </description> </method> <method name="get_bone_global_pose" qualifiers="const"> @@ -69,7 +69,7 @@ <argument index="0" name="bone_idx" type="int"> </argument> <description> - Return the overall transform of the specified bone, with respect to the skeleton. Being relative to the skeleton frame, this is not the actual "global" transform of the bone. + Returns the overall transform of the specified bone, with respect to the skeleton. Being relative to the skeleton frame, this is not the actual "global" transform of the bone. </description> </method> <method name="get_bone_name" qualifiers="const"> @@ -78,7 +78,7 @@ <argument index="0" name="bone_idx" type="int"> </argument> <description> - Return the name of the bone at index "index". + Returns the name of the bone at index "index". </description> </method> <method name="get_bone_parent" qualifiers="const"> @@ -87,7 +87,7 @@ <argument index="0" name="bone_idx" type="int"> </argument> <description> - Return the bone index which is the parent of the bone at "bone_idx". If -1, then bone has no parent. Note that the parent bone returned will always be less than "bone_idx". + Returns the bone index which is the parent of the bone at "bone_idx". If -1, then bone has no parent. Note that the parent bone returned will always be less than "bone_idx". </description> </method> <method name="get_bone_pose" qualifiers="const"> @@ -96,7 +96,7 @@ <argument index="0" name="bone_idx" type="int"> </argument> <description> - Return the pose transform of the specified bone. Pose is applied on top of the custom pose, which is applied on top the rest pose. + Returns the pose transform of the specified bone. Pose is applied on top of the custom pose, which is applied on top the rest pose. </description> </method> <method name="get_bone_rest" qualifiers="const"> @@ -105,7 +105,7 @@ <argument index="0" name="bone_idx" type="int"> </argument> <description> - Return the rest transform for a bone "bone_idx". + Returns the rest transform for a bone "bone_idx". </description> </method> <method name="get_bone_transform" qualifiers="const"> @@ -114,7 +114,7 @@ <argument index="0" name="bone_idx" type="int"> </argument> <description> - Return the combination of custom pose and pose. The returned transform is in skeleton's reference frame. + Returns the combination of custom pose and pose. The returned transform is in skeleton's reference frame. </description> </method> <method name="get_bound_child_nodes_to_bone" qualifiers="const"> @@ -229,7 +229,7 @@ <argument index="1" name="pose" type="Transform"> </argument> <description> - Return the pose transform for bone "bone_idx". + Returns the pose transform for bone "bone_idx". </description> </method> <method name="set_bone_rest"> diff --git a/doc/classes/StreamPeer.xml b/doc/classes/StreamPeer.xml index af8e43944c..d278312fc3 100644 --- a/doc/classes/StreamPeer.xml +++ b/doc/classes/StreamPeer.xml @@ -41,7 +41,7 @@ <return type="int"> </return> <description> - Return the amount of bytes this [StreamPeer] has available. + Returns the amount of bytes this [StreamPeer] has available. </description> </method> <method name="get_data"> @@ -50,7 +50,7 @@ <argument index="0" name="bytes" type="int"> </argument> <description> - Return a chunk data with the received bytes. The amount of bytes to be received can be requested in the "bytes" argument. If not enough bytes are available, the function will block until the desired amount is received. This function returns two values, an Error code and a data array. + Returns a chunk data with the received bytes. The amount of bytes to be received can be requested in the "bytes" argument. If not enough bytes are available, the function will block until the desired amount is received. This function returns two values, an Error code and a data array. </description> </method> <method name="get_double"> @@ -73,7 +73,7 @@ <argument index="0" name="bytes" type="int"> </argument> <description> - Return a chunk data with the received bytes. The amount of bytes to be received can be requested in the "bytes" argument. If not enough bytes are available, the function will return how many were actually received. This function returns two values, an Error code, and a data array. + Returns a chunk data with the received bytes. The amount of bytes to be received can be requested in the "bytes" argument. If not enough bytes are available, the function will return how many were actually received. This function returns two values, an Error code, and a data array. </description> </method> <method name="get_string"> diff --git a/doc/classes/StreamPeerSSL.xml b/doc/classes/StreamPeerSSL.xml index f7fd36ed58..f28e6e5544 100644 --- a/doc/classes/StreamPeerSSL.xml +++ b/doc/classes/StreamPeerSSL.xml @@ -42,7 +42,7 @@ <return type="int" enum="StreamPeerSSL.Status"> </return> <description> - Return the status of the connection, one of STATUS_* enum. + Returns the status of the connection, one of STATUS_* enum. </description> </method> <method name="poll"> diff --git a/doc/classes/StreamPeerTCP.xml b/doc/classes/StreamPeerTCP.xml index 16bf69110d..0edea42521 100644 --- a/doc/classes/StreamPeerTCP.xml +++ b/doc/classes/StreamPeerTCP.xml @@ -31,21 +31,21 @@ <return type="String"> </return> <description> - Return the IP of this peer. + Returns the IP of this peer. </description> </method> <method name="get_connected_port" qualifiers="const"> <return type="int"> </return> <description> - Return the port of this peer. + Returns the port of this peer. </description> </method> <method name="get_status"> <return type="int" enum="StreamPeerTCP.Status"> </return> <description> - Return the status of the connection, see [enum StreamPeerTCP.Status]. + Returns the status of the connection, see [enum StreamPeerTCP.Status]. </description> </method> <method name="is_connected_to_host" qualifiers="const"> diff --git a/doc/classes/StyleBox.xml b/doc/classes/StyleBox.xml index 40cb2632b6..a156f134e7 100644 --- a/doc/classes/StyleBox.xml +++ b/doc/classes/StyleBox.xml @@ -37,7 +37,7 @@ <argument index="0" name="margin" type="int" enum="Margin"> </argument> <description> - Return the content margin offset for the specified margin + Returns the content margin offset for the specified margin Positive values reduce size inwards, unlike [Control]'s margin values. </description> </method> @@ -45,14 +45,14 @@ <return type="Vector2"> </return> <description> - Return the minimum size that this stylebox can be shrunk to. + Returns the minimum size that this stylebox can be shrunk to. </description> </method> <method name="get_offset" qualifiers="const"> <return type="Vector2"> </return> <description> - Return the "offset" of a stylebox, this is a helper function, like writing [code]Vector2(style.get_margin(MARGIN_LEFT), style.get_margin(MARGIN_TOP))[/code]. + Returns the "offset" of a stylebox, this is a helper function, like writing [code]Vector2(style.get_margin(MARGIN_LEFT), style.get_margin(MARGIN_TOP))[/code]. </description> </method> <method name="test_mask" qualifiers="const"> diff --git a/doc/classes/TCP_Server.xml b/doc/classes/TCP_Server.xml index ac9b33bc34..663d3248e8 100644 --- a/doc/classes/TCP_Server.xml +++ b/doc/classes/TCP_Server.xml @@ -13,7 +13,7 @@ <return type="bool"> </return> <description> - Return [code]true[/code] if a connection is available for taking. + Returns [code]true[/code] if a connection is available for taking. </description> </method> <method name="listen"> diff --git a/doc/classes/TextEdit.xml b/doc/classes/TextEdit.xml index dd0461f4db..eb70d7a1c3 100644 --- a/doc/classes/TextEdit.xml +++ b/doc/classes/TextEdit.xml @@ -69,14 +69,14 @@ <return type="int"> </return> <description> - Return the column the editing cursor is at. + Returns the column the editing cursor is at. </description> </method> <method name="cursor_get_line" qualifiers="const"> <return type="int"> </return> <description> - Return the line the editing cursor is at. + Returns the line the editing cursor is at. </description> </method> <method name="cursor_set_column"> @@ -137,7 +137,7 @@ <return type="Array"> </return> <description> - Return an array containing the line number of each breakpoint. + Returns an array containing the line number of each breakpoint. </description> </method> <method name="get_keyword_color" qualifiers="const"> @@ -154,14 +154,14 @@ <argument index="0" name="line" type="int"> </argument> <description> - Return the text of a specific line. + Returns the text of a specific line. </description> </method> <method name="get_line_count" qualifiers="const"> <return type="int"> </return> <description> - Return the amount of total lines in the text. + Returns the amount of total lines in the text. </description> </method> <method name="get_menu" qualifiers="const"> @@ -175,35 +175,35 @@ <return type="int"> </return> <description> - Return the selection begin column. + Returns the selection begin column. </description> </method> <method name="get_selection_from_line" qualifiers="const"> <return type="int"> </return> <description> - Return the selection begin line. + Returns the selection begin line. </description> </method> <method name="get_selection_text" qualifiers="const"> <return type="String"> </return> <description> - Return the text inside the selection. + Returns the text inside the selection. </description> </method> <method name="get_selection_to_column" qualifiers="const"> <return type="int"> </return> <description> - Return the selection end column. + Returns the selection end column. </description> </method> <method name="get_selection_to_line" qualifiers="const"> <return type="int"> </return> <description> - Return the selection end line. + Returns the selection end line. </description> </method> <method name="get_word_under_cursor" qualifiers="const"> @@ -250,7 +250,7 @@ <return type="bool"> </return> <description> - Return [code]true[/code] if the selection is active. + Returns [code]true[/code] if the selection is active. </description> </method> <method name="menu_option"> @@ -382,12 +382,12 @@ <member name="context_menu_enabled" type="bool" setter="set_context_menu_enabled" getter="is_context_menu_enabled"> If [code]true[/code], a right click displays the context menu. </member> - <member name="draw_tabs" type="bool" setter="set_draw_tabs" getter="is_drawing_tabs"> - If [code]true[/code], the "tab" character will have a visible representation. - </member> <member name="draw_spaces" type="bool" setter="set_draw_spaces" getter="is_drawing_spaces"> If [code]true[/code], the "space" character will have a visible representation. </member> + <member name="draw_tabs" type="bool" setter="set_draw_tabs" getter="is_drawing_tabs"> + If [code]true[/code], the "tab" character will have a visible representation. + </member> <member name="fold_gutter" type="bool" setter="set_fold_gutter_enabled" getter="is_fold_gutter_enabled"> If [code]true[/code], the fold gutter is visible. This enables folding groups of indented lines. </member> @@ -497,6 +497,8 @@ <theme_items> <theme_item name="background_color" type="Color"> </theme_item> + <theme_item name="bookmark_color" type="Color"> + </theme_item> <theme_item name="brace_mismatch_color" type="Color"> </theme_item> <theme_item name="breakpoint_color" type="Color"> @@ -561,6 +563,8 @@ </theme_item> <theme_item name="selection_color" type="Color"> </theme_item> + <theme_item name="space" type="Texture"> + </theme_item> <theme_item name="symbol_color" type="Color"> </theme_item> <theme_item name="tab" type="Texture"> diff --git a/doc/classes/Texture.xml b/doc/classes/Texture.xml index 39f3ee447c..4418a6ce8f 100644 --- a/doc/classes/Texture.xml +++ b/doc/classes/Texture.xml @@ -74,21 +74,21 @@ <return type="int"> </return> <description> - Return the texture height. + Returns the texture height. </description> </method> <method name="get_size" qualifiers="const"> <return type="Vector2"> </return> <description> - Return the texture size. + Returns the texture size. </description> </method> <method name="get_width" qualifiers="const"> <return type="int"> </return> <description> - Return the texture width. + Returns the texture width. </description> </method> <method name="has_alpha" qualifiers="const"> diff --git a/doc/classes/Viewport.xml b/doc/classes/Viewport.xml index b48dc9de35..53e66cee74 100644 --- a/doc/classes/Viewport.xml +++ b/doc/classes/Viewport.xml @@ -253,6 +253,9 @@ <member name="physics_object_picking" type="bool" setter="set_physics_object_picking" getter="get_physics_object_picking"> If [code]true[/code], the objects rendered by viewport become subjects of mouse picking process. Default value: [code]false[/code]. </member> + <member name="render_direct_to_screen" type="bool" setter="set_use_render_direct_to_screen" getter="is_using_render_direct_to_screen"> + If [code]true[/code], renders the Viewport directly to the screen instead of to the root viewport. Only available in GLES2. This is a low-level optimization and should not be used in most cases. If used, reading from the Viewport or from [code]SCREEN_TEXTURE[/code] becomes unavailable. For more information see [method VisualServer.viewport_set_render_direct_to_screen]. Default value: [code]false[/code]. + </member> <member name="render_target_clear_mode" type="int" setter="set_clear_mode" getter="get_clear_mode" enum="Viewport.ClearMode"> The clear mode when viewport used as a render target. Default value: [code]CLEAR_MODE_ALWAYS[/code]. </member> diff --git a/doc/classes/VisualServer.xml b/doc/classes/VisualServer.xml index dae120f09b..3563120f0f 100644 --- a/doc/classes/VisualServer.xml +++ b/doc/classes/VisualServer.xml @@ -3590,7 +3590,14 @@ <argument index="2" name="screen" type="int" default="0"> </argument> <description> - Attaches a viewport to a screen. + Copies viewport to a region of the screen specified by [code]rect[/code]. If Viewport.[member Viewport.render_direct_to_screen] is [code]true[/code], then viewport does not use a framebuffer and the contents of the viewport are rendered directly to screen. However, note that the root viewport is drawn last, therefore it will draw over the screen. Accordingly, you must set the root viewport to an area that does not cover the area that you have attached this viewport to. + For example, you can set the root viewport to not render at all with the following code: + [codeblock] + func _ready(): + get_viewport().set_attach_to_screen_rect(Rect2()) + $Viewport.set_attach_to_screen_rect(Rect2(0, 0, 600, 600)) + [/codeblock] + Using this can result in significant optimization, especially on lower-end devices. However, it comes at the cost of having to manage your viewports manually. For a further optimization see, [method set_render_direct_to_screen]. </description> </method> <method name="viewport_create"> @@ -3789,6 +3796,17 @@ Sets the viewport's parent to another viewport. </description> </method> + <method name="viewport_set_render_direct_to_screen"> + <return type="void"> + </return> + <argument index="0" name="viewport" type="RID"> + </argument> + <argument index="1" name="enabled" type="bool"> + </argument> + <description> + If [code]true[/code], render the contents of the viewport directly to screen. This allows a low-level optimization where you can skip drawing a viewport to the root viewport. While this optimization can result in a significant increase in speed (especially on older devices), it comes at a cost of usability. When this is enabled, you cannot read from the viewport or from the [code]SCREEN_TEXTURE[/code]. You also lose the benefit of certain window settings, such as the various stretch modes. Another consequence to be aware of is that in 2D the rendering happens in window coordinates, so if you have a viewport that is double the size of the window, and you set this, then only the portion that fits within the window will be drawn, no automatic scaling is possible, even if your game scene is significantly larger than the window size. + </description> + </method> <method name="viewport_set_scenario"> <return type="void"> </return> diff --git a/modules/gdnative/doc_classes/WebRTCPeerGDNative.xml b/doc/classes/VisualShaderNodeFresnel.xml index 478889e031..2484a44fcd 100644 --- a/modules/gdnative/doc_classes/WebRTCPeerGDNative.xml +++ b/doc/classes/VisualShaderNodeFresnel.xml @@ -1,5 +1,5 @@ <?xml version="1.0" encoding="UTF-8" ?> -<class name="WebRTCPeerGDNative" inherits="WebRTCPeer" category="Core" version="3.2"> +<class name="VisualShaderNodeFresnel" inherits="VisualShaderNode" category="Core" version="3.2"> <brief_description> </brief_description> <description> diff --git a/doc/classes/VisualShaderNodeScalarFunc.xml b/doc/classes/VisualShaderNodeScalarFunc.xml index 163276b3bc..b0ee422bbd 100644 --- a/doc/classes/VisualShaderNodeScalarFunc.xml +++ b/doc/classes/VisualShaderNodeScalarFunc.xml @@ -75,5 +75,7 @@ </constant> <constant name="FUNC_TRUNC" value="30" enum="Function"> </constant> + <constant name="FUNC_ONEMINUS" value="31" enum="Function"> + </constant> </constants> </class> diff --git a/doc/classes/VisualShaderNodeVectorFunc.xml b/doc/classes/VisualShaderNodeVectorFunc.xml index 71ce32c04e..e67cb2e07f 100644 --- a/doc/classes/VisualShaderNodeVectorFunc.xml +++ b/doc/classes/VisualShaderNodeVectorFunc.xml @@ -81,5 +81,7 @@ </constant> <constant name="FUNC_TRUNC" value="33" enum="Function"> </constant> + <constant name="FUNC_ONEMINUS" value="34" enum="Function"> + </constant> </constants> </class> diff --git a/doc/classes/WindowDialog.xml b/doc/classes/WindowDialog.xml index 16b7bd84ad..c5d66af984 100644 --- a/doc/classes/WindowDialog.xml +++ b/doc/classes/WindowDialog.xml @@ -13,7 +13,7 @@ <return type="TextureButton"> </return> <description> - Return the close [TextureButton]. + Returns the close [TextureButton]. </description> </method> </methods> diff --git a/drivers/dummy/rasterizer_dummy.h b/drivers/dummy/rasterizer_dummy.h index 3b31da1dd7..253936ca34 100644 --- a/drivers/dummy/rasterizer_dummy.h +++ b/drivers/dummy/rasterizer_dummy.h @@ -692,6 +692,7 @@ public: /* RENDER TARGET */ RID render_target_create() { return RID(); } + void render_target_set_position(RID p_render_target, int p_x, int p_y) {} void render_target_set_size(RID p_render_target, int p_width, int p_height) {} RID render_target_get_texture(RID p_render_target) const { return RID(); } void render_target_set_external_texture(RID p_render_target, unsigned int p_texture_id) {} diff --git a/drivers/gles2/rasterizer_canvas_gles2.cpp b/drivers/gles2/rasterizer_canvas_gles2.cpp index 7232d2d95a..ee722e9d6c 100644 --- a/drivers/gles2/rasterizer_canvas_gles2.cpp +++ b/drivers/gles2/rasterizer_canvas_gles2.cpp @@ -113,9 +113,22 @@ void RasterizerCanvasGLES2::canvas_begin() { state.canvas_shader.bind(); state.using_transparent_rt = false; + int viewport_x, viewport_y, viewport_width, viewport_height; + if (storage->frame.current_rt) { glBindFramebuffer(GL_FRAMEBUFFER, storage->frame.current_rt->fbo); state.using_transparent_rt = storage->frame.current_rt->flags[RasterizerStorage::RENDER_TARGET_TRANSPARENT]; + + if (storage->frame.current_rt->flags[RasterizerStorage::RENDER_TARGET_DIRECT_TO_SCREEN]) { + // set Viewport and Scissor when rendering directly to screen + viewport_width = storage->frame.current_rt->width; + viewport_height = storage->frame.current_rt->height; + viewport_x = storage->frame.current_rt->x; + viewport_y = OS::get_singleton()->get_window_size().height - viewport_height - storage->frame.current_rt->y; + glScissor(viewport_x, viewport_y, viewport_width, viewport_height); + glViewport(viewport_x, viewport_y, viewport_width, viewport_height); + glEnable(GL_SCISSOR_TEST); + } } if (storage->frame.clear_request) { @@ -179,6 +192,14 @@ void RasterizerCanvasGLES2::canvas_end() { glDisableVertexAttribArray(i); } + if (storage->frame.current_rt && storage->frame.current_rt->flags[RasterizerStorage::RENDER_TARGET_DIRECT_TO_SCREEN]) { + //reset viewport to full window size + int viewport_width = OS::get_singleton()->get_window_size().width; + int viewport_height = OS::get_singleton()->get_window_size().height; + glViewport(0, 0, viewport_width, viewport_height); + glScissor(0, 0, viewport_width, viewport_height); + } + state.using_texture_rect = false; state.using_skeleton = false; state.using_ninepatch = false; @@ -1192,6 +1213,11 @@ void RasterizerCanvasGLES2::_canvas_item_render_commands(Item *p_item, Item *cur void RasterizerCanvasGLES2::_copy_screen(const Rect2 &p_rect) { + if (storage->frame.current_rt->flags[RasterizerStorage::RENDER_TARGET_DIRECT_TO_SCREEN]) { + ERR_PRINT_ONCE("Cannot use screen texture copying in render target set to render direct to screen"); + return; + } + if (storage->frame.current_rt->copy_screen_effect.color == 0) { ERR_EXPLAIN("Can't use screen texture copying in a render target configured without copy buffers"); ERR_FAIL(); diff --git a/drivers/gles2/rasterizer_scene_gles2.cpp b/drivers/gles2/rasterizer_scene_gles2.cpp index 3b3fbf9ed5..268b0f1c90 100644 --- a/drivers/gles2/rasterizer_scene_gles2.cpp +++ b/drivers/gles2/rasterizer_scene_gles2.cpp @@ -580,7 +580,7 @@ bool RasterizerSceneGLES2::reflection_probe_instance_begin_render(RID p_instance //the approach below is fatal for powervr - // Set the initial (empty) mipmaps, all need to be set for this to work in GLES2, even if later wont be used. + // Set the initial (empty) mipmaps, all need to be set for this to work in GLES2, even if they won't be used later. while (size >= 1) { for (int i = 0; i < 6; i++) { @@ -1011,7 +1011,7 @@ void RasterizerSceneGLES2::_add_geometry_with_material(RasterizerStorageGLES2::G has_alpha = false; } - RenderList::Element *e = has_alpha ? render_list.add_alpha_element() : render_list.add_element(); + RenderList::Element *e = (has_alpha || p_material->shader->spatial.no_depth_test) ? render_list.add_alpha_element() : render_list.add_element(); if (!e) { return; @@ -2695,6 +2695,7 @@ void RasterizerSceneGLES2::render_scene(const Transform &p_cam_transform, const Environment *env = NULL; int viewport_width, viewport_height; + int viewport_x, viewport_y; bool probe_interior = false; bool reverse_cull = false; @@ -2734,6 +2735,13 @@ void RasterizerSceneGLES2::render_scene(const Transform &p_cam_transform, const viewport_width = storage->frame.current_rt->width; viewport_height = storage->frame.current_rt->height; + viewport_x = storage->frame.current_rt->x; + + if (storage->frame.current_rt->flags[RasterizerStorage::RENDER_TARGET_DIRECT_TO_SCREEN]) { + viewport_y = OS::get_singleton()->get_window_size().height - viewport_height - storage->frame.current_rt->y; + } else { + viewport_y = storage->frame.current_rt->y; + } } state.used_screen_texture = false; @@ -2799,7 +2807,13 @@ void RasterizerSceneGLES2::render_scene(const Transform &p_cam_transform, const // other stuff glBindFramebuffer(GL_FRAMEBUFFER, current_fb); - glViewport(0, 0, viewport_width, viewport_height); + glViewport(viewport_x, viewport_y, viewport_width, viewport_height); + + if (storage->frame.current_rt && storage->frame.current_rt->flags[RasterizerStorage::RENDER_TARGET_DIRECT_TO_SCREEN]) { + + glScissor(viewport_x, viewport_y, viewport_width, viewport_height); + glEnable(GL_SCISSOR_TEST); + } glDepthFunc(GL_LEQUAL); glDepthMask(GL_TRUE); @@ -2834,6 +2848,10 @@ void RasterizerSceneGLES2::render_scene(const Transform &p_cam_transform, const glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + if (storage->frame.current_rt && storage->frame.current_rt->flags[RasterizerStorage::RENDER_TARGET_DIRECT_TO_SCREEN]) { + glDisable(GL_SCISSOR_TEST); + } + glVertexAttrib4f(VS::ARRAY_COLOR, 1, 1, 1, 1); glBlendEquation(GL_FUNC_ADD); @@ -2860,13 +2878,6 @@ void RasterizerSceneGLES2::render_scene(const Transform &p_cam_transform, const } } - if (env && env->bg_mode == VS::ENV_BG_SKY && (!storage->frame.current_rt || !storage->frame.current_rt->flags[RasterizerStorage::RENDER_TARGET_TRANSPARENT])) { - - if (sky && sky->panorama.is_valid()) { - _draw_sky(sky, p_cam_projection, cam_transform, false, env->sky_custom_fov, env->bg_energy, env->sky_orientation); - } - } - if (probe_interior) { env_radiance_tex = 0; //do not use radiance texture on interiors state.default_ambient = Color(0, 0, 0, 1); //black as default ambient for interior @@ -2877,6 +2888,14 @@ void RasterizerSceneGLES2::render_scene(const Transform &p_cam_transform, const render_list.sort_by_key(false); _render_render_list(render_list.elements, render_list.element_count, cam_transform, p_cam_projection, p_shadow_atlas, env, env_radiance_tex, 0.0, 0.0, reverse_cull, false, false); + // then draw the sky after + if (env && env->bg_mode == VS::ENV_BG_SKY && (!storage->frame.current_rt || !storage->frame.current_rt->flags[RasterizerStorage::RENDER_TARGET_TRANSPARENT])) { + + if (sky && sky->panorama.is_valid()) { + _draw_sky(sky, p_cam_projection, cam_transform, false, env->sky_custom_fov, env->bg_energy, env->sky_orientation); + } + } + if (storage->frame.current_rt && state.used_screen_texture) { //copy screen texture diff --git a/drivers/gles2/rasterizer_scene_gles2.h b/drivers/gles2/rasterizer_scene_gles2.h index d805984dca..bd1a61688c 100644 --- a/drivers/gles2/rasterizer_scene_gles2.h +++ b/drivers/gles2/rasterizer_scene_gles2.h @@ -603,12 +603,10 @@ public: struct SortByReverseDepthAndPriority { _FORCE_INLINE_ bool operator()(const Element *A, const Element *B) const { - uint32_t layer_A = uint32_t(A->sort_key >> SORT_KEY_PRIORITY_SHIFT); - uint32_t layer_B = uint32_t(B->sort_key >> SORT_KEY_PRIORITY_SHIFT); - if (layer_A == layer_B) { + if (A->priority == B->priority) { return A->instance->depth > B->instance->depth; } else { - return layer_A < layer_B; + return A->priority < B->priority; } } }; diff --git a/drivers/gles2/rasterizer_storage_gles2.cpp b/drivers/gles2/rasterizer_storage_gles2.cpp index d709056709..c610f31bc1 100644 --- a/drivers/gles2/rasterizer_storage_gles2.cpp +++ b/drivers/gles2/rasterizer_storage_gles2.cpp @@ -4568,9 +4568,16 @@ void RasterizerStorageGLES2::instance_remove_dependency(RID p_base, RasterizerSc void RasterizerStorageGLES2::_render_target_allocate(RenderTarget *rt) { + // do not allocate a render target with no size if (rt->width <= 0 || rt->height <= 0) return; + // do not allocate a render target that is attached to the screen + if (rt->flags[RENDER_TARGET_DIRECT_TO_SCREEN]) { + rt->fbo = RasterizerStorageGLES2::system_fbo; + return; + } + GLuint color_internal_format; GLuint color_format; GLuint color_type = GL_UNSIGNED_BYTE; @@ -4779,6 +4786,10 @@ void RasterizerStorageGLES2::_render_target_allocate(RenderTarget *rt) { void RasterizerStorageGLES2::_render_target_clear(RenderTarget *rt) { + // there is nothing to clear when DIRECT_TO_SCREEN is used + if (rt->flags[RENDER_TARGET_DIRECT_TO_SCREEN]) + return; + if (rt->fbo) { glDeleteFramebuffers(1, &rt->fbo); glDeleteTextures(1, &rt->color); @@ -4873,6 +4884,15 @@ RID RasterizerStorageGLES2::render_target_create() { return render_target_owner.make_rid(rt); } +void RasterizerStorageGLES2::render_target_set_position(RID p_render_target, int p_x, int p_y) { + + RenderTarget *rt = render_target_owner.getornull(p_render_target); + ERR_FAIL_COND(!rt); + + rt->x = p_x; + rt->y = p_y; +} + void RasterizerStorageGLES2::render_target_set_size(RID p_render_target, int p_width, int p_height) { RenderTarget *rt = render_target_owner.getornull(p_render_target); @@ -5002,6 +5022,14 @@ void RasterizerStorageGLES2::render_target_set_flag(RID p_render_target, RenderT RenderTarget *rt = render_target_owner.getornull(p_render_target); ERR_FAIL_COND(!rt); + // When setting DIRECT_TO_SCREEN, you need to clear before the value is set, but allocate after as + // those functions change how they operate depending on the value of DIRECT_TO_SCREEN + if (p_flag == RENDER_TARGET_DIRECT_TO_SCREEN && p_value != rt->flags[RENDER_TARGET_DIRECT_TO_SCREEN]) { + _render_target_clear(rt); + rt->flags[p_flag] = p_value; + _render_target_allocate(rt); + } + rt->flags[p_flag] = p_value; switch (p_flag) { diff --git a/drivers/gles2/rasterizer_storage_gles2.h b/drivers/gles2/rasterizer_storage_gles2.h index 3134082e2a..af57aa3d9b 100644 --- a/drivers/gles2/rasterizer_storage_gles2.h +++ b/drivers/gles2/rasterizer_storage_gles2.h @@ -1175,7 +1175,7 @@ public: } } external; - int width, height; + int x, y, width, height; bool flags[RENDER_TARGET_FLAG_MAX]; @@ -1192,6 +1192,8 @@ public: multisample_color(0), multisample_depth(0), multisample_active(false), + x(0), + y(0), width(0), height(0), used_in_frame(false), @@ -1209,6 +1211,7 @@ public: void _render_target_allocate(RenderTarget *rt); virtual RID render_target_create(); + virtual void render_target_set_position(RID p_render_target, int p_x, int p_y); virtual void render_target_set_size(RID p_render_target, int p_width, int p_height); virtual RID render_target_get_texture(RID p_render_target) const; virtual void render_target_set_external_texture(RID p_render_target, unsigned int p_texture_id); diff --git a/drivers/gles2/shader_compiler_gles2.cpp b/drivers/gles2/shader_compiler_gles2.cpp index d00b03fb8a..6ba4004f20 100644 --- a/drivers/gles2/shader_compiler_gles2.cpp +++ b/drivers/gles2/shader_compiler_gles2.cpp @@ -934,6 +934,7 @@ ShaderCompilerGLES2::ShaderCompilerGLES2() { actions[VS::SHADER_SPATIAL].render_mode_defines["specular_disabled"] = "#define SPECULAR_DISABLED\n"; actions[VS::SHADER_SPATIAL].render_mode_defines["shadows_disabled"] = "#define SHADOWS_DISABLED\n"; actions[VS::SHADER_SPATIAL].render_mode_defines["ambient_light_disabled"] = "#define AMBIENT_LIGHT_DISABLED\n"; + actions[VS::SHADER_SPATIAL].render_mode_defines["shadow_to_opacity"] = "#define USE_SHADOW_TO_OPACITY\n"; // No defines for particle shaders in GLES2, there are no GPU particles diff --git a/drivers/gles2/shaders/canvas.glsl b/drivers/gles2/shaders/canvas.glsl index 7ba2856216..7dce784f52 100644 --- a/drivers/gles2/shaders/canvas.glsl +++ b/drivers/gles2/shaders/canvas.glsl @@ -347,7 +347,7 @@ void main() { vec4 color = color_interp; vec2 uv = uv_interp; #ifdef USE_FORCE_REPEAT - //needs to use this to workaround GLES2/WebGL1 forcing tiling that textures that dont support it + //needs to use this to workaround GLES2/WebGL1 forcing tiling that textures that don't support it uv = mod(uv, vec2(1.0, 1.0)); #endif diff --git a/drivers/gles2/shaders/scene.glsl b/drivers/gles2/shaders/scene.glsl index 0fa290e57c..2aef913ae8 100644 --- a/drivers/gles2/shaders/scene.glsl +++ b/drivers/gles2/shaders/scene.glsl @@ -1151,7 +1151,8 @@ void light_compute( float clearcoat_gloss, float anisotropy, inout vec3 diffuse_light, - inout vec3 specular_light) { + inout vec3 specular_light, + inout float alpha) { //this makes lights behave closer to linear, but then addition of lights looks bad //better left disabled @@ -1306,10 +1307,10 @@ LIGHT_SHADER_CODE // shlick+ggx as default #if defined(LIGHT_USE_ANISOTROPY) - float alpha = roughness * roughness; + float alpha_ggx = roughness * roughness; float aspect = sqrt(1.0 - anisotropy * 0.9); - float ax = alpha / aspect; - float ay = alpha * aspect; + float ax = alpha_ggx / aspect; + float ay = alpha_ggx * aspect; float XdotH = dot(T, H); float YdotH = dot(B, H); float D = D_GGX_anisotropic(cNdotH, ax, ay, XdotH, YdotH, cNdotH); @@ -1317,10 +1318,10 @@ LIGHT_SHADER_CODE float G = V_GGX_anisotropic(ax, ay, dot(T, V), dot(T, L), dot(B, V), dot(B, L), cNdotV, cNdotL); #else - float alpha = roughness * roughness; - float D = D_GGX(cNdotH, alpha); - //float G = G_GGX_2cos(cNdotL, alpha) * G_GGX_2cos(cNdotV, alpha); - float G = V_GGX(cNdotL, cNdotV, alpha); + float alpha_ggx = roughness * roughness; + float D = D_GGX(cNdotH, alpha_ggx); + //float G = G_GGX_2cos(cNdotL, alpha_ggx) * G_GGX_2cos(cNdotV, alpha_ggx); + float G = V_GGX(cNdotL, cNdotV, alpha_ggx); #endif // F vec3 f0 = F0(metallic, specular, diffuse_color); @@ -1350,6 +1351,10 @@ LIGHT_SHADER_CODE #endif } +#ifdef USE_SHADOW_TO_OPACITY + alpha = min(alpha, clamp(1.0 - length(attenuation), 0.0, 1.0)); +#endif + #endif //defined(USE_LIGHT_SHADER_CODE) } @@ -1535,17 +1540,21 @@ FRAGMENT_SHADER_CODE vec3 eye_position = view; +#if !defined(USE_SHADOW_TO_OPACITY) + #if defined(ALPHA_SCISSOR_USED) if (alpha < alpha_scissor) { discard; } -#endif +#endif // ALPHA_SCISSOR_USED #ifdef USE_DEPTH_PREPASS if (alpha < 0.99) { discard; } -#endif +#endif // USE_DEPTH_PREPASS + +#endif // !USE_SHADOW_TO_OPACITY #ifdef BASE_PASS //none @@ -2061,13 +2070,32 @@ FRAGMENT_SHADER_CODE clearcoat_gloss, anisotropy, diffuse_light, - specular_light); + specular_light, + alpha); #endif //vertex lighting #endif //USE_LIGHTING //compute and merge +#ifdef USE_SHADOW_TO_OPACITY + + alpha = min(alpha, clamp(length(ambient_light), 0.0, 1.0)); + +#if defined(ALPHA_SCISSOR_USED) + if (alpha < alpha_scissor) { + discard; + } +#endif // ALPHA_SCISSOR_USED + +#ifdef USE_DEPTH_PREPASS + if (alpha < 0.99) { + discard; + } +#endif // USE_DEPTH_PREPASS + +#endif // !USE_SHADOW_TO_OPACITY + #ifndef RENDER_DEPTH #ifdef SHADELESS @@ -2105,8 +2133,6 @@ FRAGMENT_SHADER_CODE #endif // gl_FragColor = vec4(normal, 1.0); -#endif //unshaded - //apply fog #if defined(FOG_DEPTH_ENABLED) || defined(FOG_HEIGHT_ENABLED) @@ -2161,6 +2187,8 @@ FRAGMENT_SHADER_CODE #endif // defined(FOG_DEPTH_ENABLED) || defined(FOG_HEIGHT_ENABLED) +#endif //unshaded + #else // not RENDER_DEPTH //depth render #ifdef USE_RGBA_SHADOWS diff --git a/drivers/gles3/rasterizer_scene_gles3.cpp b/drivers/gles3/rasterizer_scene_gles3.cpp index 9aec348291..4552fddfe8 100644 --- a/drivers/gles3/rasterizer_scene_gles3.cpp +++ b/drivers/gles3/rasterizer_scene_gles3.cpp @@ -2374,7 +2374,7 @@ void RasterizerSceneGLES3::_add_geometry_with_material(RasterizerStorageGLES3::G has_alpha = false; } - RenderList::Element *e = has_alpha ? render_list.add_alpha_element() : render_list.add_element(); + RenderList::Element *e = (has_alpha || p_material->shader->spatial.no_depth_test) ? render_list.add_alpha_element() : render_list.add_element(); if (!e) return; diff --git a/drivers/gles3/rasterizer_storage_gles3.cpp b/drivers/gles3/rasterizer_storage_gles3.cpp index 661be28e6b..247b30811e 100644 --- a/drivers/gles3/rasterizer_storage_gles3.cpp +++ b/drivers/gles3/rasterizer_storage_gles3.cpp @@ -7268,6 +7268,10 @@ RID RasterizerStorageGLES3::render_target_create() { return render_target_owner.make_rid(rt); } +void RasterizerStorageGLES3::render_target_set_position(RID p_render_target, int p_x, int p_y) { + //only used in GLES2 +} + void RasterizerStorageGLES3::render_target_set_size(RID p_render_target, int p_width, int p_height) { RenderTarget *rt = render_target_owner.getornull(p_render_target); diff --git a/drivers/gles3/rasterizer_storage_gles3.h b/drivers/gles3/rasterizer_storage_gles3.h index a4cc84ef02..99aa34e1ce 100644 --- a/drivers/gles3/rasterizer_storage_gles3.h +++ b/drivers/gles3/rasterizer_storage_gles3.h @@ -1394,6 +1394,7 @@ public: void _render_target_allocate(RenderTarget *rt); virtual RID render_target_create(); + virtual void render_target_set_position(RID p_render_target, int p_x, int p_y); virtual void render_target_set_size(RID p_render_target, int p_width, int p_height); virtual RID render_target_get_texture(RID p_render_target) const; virtual void render_target_set_external_texture(RID p_render_target, unsigned int p_texture_id); diff --git a/drivers/gles3/shader_compiler_gles3.cpp b/drivers/gles3/shader_compiler_gles3.cpp index ad26294527..e8417900ea 100644 --- a/drivers/gles3/shader_compiler_gles3.cpp +++ b/drivers/gles3/shader_compiler_gles3.cpp @@ -944,6 +944,7 @@ ShaderCompilerGLES3::ShaderCompilerGLES3() { actions[VS::SHADER_SPATIAL].render_mode_defines["specular_disabled"] = "#define SPECULAR_DISABLED\n"; actions[VS::SHADER_SPATIAL].render_mode_defines["shadows_disabled"] = "#define SHADOWS_DISABLED\n"; actions[VS::SHADER_SPATIAL].render_mode_defines["ambient_light_disabled"] = "#define AMBIENT_LIGHT_DISABLED\n"; + actions[VS::SHADER_SPATIAL].render_mode_defines["shadow_to_opacity"] = "#define USE_SHADOW_TO_OPACITY\n"; /* PARTICLES SHADER */ diff --git a/drivers/gles3/shaders/scene.glsl b/drivers/gles3/shaders/scene.glsl index def924cd49..f08d3f4d23 100644 --- a/drivers/gles3/shaders/scene.glsl +++ b/drivers/gles3/shaders/scene.glsl @@ -993,7 +993,7 @@ vec3 F0(float metallic, float specular, vec3 albedo) { return mix(vec3(dielectric), albedo, vec3(metallic)); } -void light_compute(vec3 N, vec3 L, vec3 V, vec3 B, vec3 T, vec3 light_color, vec3 attenuation, vec3 diffuse_color, vec3 transmission, float specular_blob_intensity, float roughness, float metallic, float specular, float rim, float rim_tint, float clearcoat, float clearcoat_gloss, float anisotropy, inout vec3 diffuse_light, inout vec3 specular_light) { +void light_compute(vec3 N, vec3 L, vec3 V, vec3 B, vec3 T, vec3 light_color, vec3 attenuation, vec3 diffuse_color, vec3 transmission, float specular_blob_intensity, float roughness, float metallic, float specular, float rim, float rim_tint, float clearcoat, float clearcoat_gloss, float anisotropy, inout vec3 diffuse_light, inout vec3 specular_light, inout float alpha) { #if defined(USE_LIGHT_SHADER_CODE) // light is written by the light shader @@ -1135,19 +1135,19 @@ LIGHT_SHADER_CODE #if defined(LIGHT_USE_ANISOTROPY) - float alpha = roughness * roughness; + float alpha_ggx = roughness * roughness; float aspect = sqrt(1.0 - anisotropy * 0.9); - float ax = alpha / aspect; - float ay = alpha * aspect; + float ax = alpha_ggx / aspect; + float ay = alpha_ggx * aspect; float XdotH = dot(T, H); float YdotH = dot(B, H); float D = D_GGX_anisotropic(cNdotH, ax, ay, XdotH, YdotH); float G = G_GGX_anisotropic_2cos(cNdotL, ax, ay, XdotH, YdotH) * G_GGX_anisotropic_2cos(cNdotV, ax, ay, XdotH, YdotH); #else - float alpha = roughness * roughness; - float D = D_GGX(cNdotH, alpha); - float G = G_GGX_2cos(cNdotL, alpha) * G_GGX_2cos(cNdotV, alpha); + float alpha_ggx = roughness * roughness; + float D = D_GGX(cNdotH, alpha_ggx); + float G = G_GGX_2cos(cNdotL, alpha_ggx) * G_GGX_2cos(cNdotV, alpha_ggx); #endif // F vec3 f0 = F0(metallic, specular, diffuse_color); @@ -1174,6 +1174,10 @@ LIGHT_SHADER_CODE #endif } +#ifdef USE_SHADOW_TO_OPACITY + alpha = min(alpha, clamp(1.0 - length(attenuation), 0.0, 1.0)); +#endif + #endif //defined(USE_LIGHT_SHADER_CODE) } @@ -1250,7 +1254,7 @@ vec3 light_transmittance(float translucency,vec3 light_vec, vec3 normal, vec3 po } #endif -void light_process_omni(int idx, vec3 vertex, vec3 eye_vec, vec3 normal, vec3 binormal, vec3 tangent, vec3 albedo, vec3 transmission, float roughness, float metallic, float specular, float rim, float rim_tint, float clearcoat, float clearcoat_gloss, float anisotropy, float p_blob_intensity, inout vec3 diffuse_light, inout vec3 specular_light) { +void light_process_omni(int idx, vec3 vertex, vec3 eye_vec, vec3 normal, vec3 binormal, vec3 tangent, vec3 albedo, vec3 transmission, float roughness, float metallic, float specular, float rim, float rim_tint, float clearcoat, float clearcoat_gloss, float anisotropy, float p_blob_intensity, inout vec3 diffuse_light, inout vec3 specular_light, inout float alpha) { vec3 light_rel_vec = omni_lights[idx].light_pos_inv_radius.xyz - vertex; float light_length = length(light_rel_vec); @@ -1304,10 +1308,10 @@ void light_process_omni(int idx, vec3 vertex, vec3 eye_vec, vec3 normal, vec3 bi light_attenuation *= mix(omni_lights[idx].shadow_color_contact.rgb, vec3(1.0), shadow); } #endif //SHADOWS_DISABLED - light_compute(normal, normalize(light_rel_vec), eye_vec, binormal, tangent, omni_lights[idx].light_color_energy.rgb, light_attenuation, albedo, transmission, omni_lights[idx].light_params.z * p_blob_intensity, roughness, metallic, specular, rim * omni_attenuation, rim_tint, clearcoat, clearcoat_gloss, anisotropy, diffuse_light, specular_light); + light_compute(normal, normalize(light_rel_vec), eye_vec, binormal, tangent, omni_lights[idx].light_color_energy.rgb, light_attenuation, albedo, transmission, omni_lights[idx].light_params.z * p_blob_intensity, roughness, metallic, specular, rim * omni_attenuation, rim_tint, clearcoat, clearcoat_gloss, anisotropy, diffuse_light, specular_light, alpha); } -void light_process_spot(int idx, vec3 vertex, vec3 eye_vec, vec3 normal, vec3 binormal, vec3 tangent, vec3 albedo, vec3 transmission, float roughness, float metallic, float specular, float rim, float rim_tint, float clearcoat, float clearcoat_gloss, float anisotropy, float p_blob_intensity, inout vec3 diffuse_light, inout vec3 specular_light) { +void light_process_spot(int idx, vec3 vertex, vec3 eye_vec, vec3 normal, vec3 binormal, vec3 tangent, vec3 albedo, vec3 transmission, float roughness, float metallic, float specular, float rim, float rim_tint, float clearcoat, float clearcoat_gloss, float anisotropy, float p_blob_intensity, inout vec3 diffuse_light, inout vec3 specular_light, inout float alpha) { vec3 light_rel_vec = spot_lights[idx].light_pos_inv_radius.xyz - vertex; float light_length = length(light_rel_vec); @@ -1339,7 +1343,7 @@ void light_process_spot(int idx, vec3 vertex, vec3 eye_vec, vec3 normal, vec3 bi } #endif //SHADOWS_DISABLED - light_compute(normal, normalize(light_rel_vec), eye_vec, binormal, tangent, spot_lights[idx].light_color_energy.rgb, light_attenuation, albedo, transmission, spot_lights[idx].light_params.z * p_blob_intensity, roughness, metallic, specular, rim * spot_attenuation, rim_tint, clearcoat, clearcoat_gloss, anisotropy, diffuse_light, specular_light); + light_compute(normal, normalize(light_rel_vec), eye_vec, binormal, tangent, spot_lights[idx].light_color_energy.rgb, light_attenuation, albedo, transmission, spot_lights[idx].light_params.z * p_blob_intensity, roughness, metallic, specular, rim * spot_attenuation, rim_tint, clearcoat, clearcoat_gloss, anisotropy, diffuse_light, specular_light, alpha); } void reflection_process(int idx, vec3 vertex, vec3 normal, vec3 binormal, vec3 tangent, float roughness, float anisotropy, vec3 ambient, vec3 skybox, inout highp vec4 reflection_accum, inout highp vec4 ambient_accum) { @@ -1705,11 +1709,13 @@ FRAGMENT_SHADER_CODE /* clang-format on */ } +#if !defined(USE_SHADOW_TO_OPACITY) + #if defined(ALPHA_SCISSOR_USED) if (alpha < alpha_scissor) { discard; } -#endif +#endif // ALPHA_SCISSOR_USED #ifdef USE_OPAQUE_PREPASS @@ -1717,7 +1723,9 @@ FRAGMENT_SHADER_CODE discard; } -#endif +#endif // USE_OPAQUE_PREPASS + +#endif // !USE_SHADOW_TO_OPACITY #if defined(ENABLE_NORMALMAP) @@ -1810,23 +1818,97 @@ FRAGMENT_SHADER_CODE ambient_light *= ambient_energy; float specular_blob_intensity = 1.0; + #if defined(SPECULAR_TOON) specular_blob_intensity *= specular * 2.0; #endif - // scales the specular reflections, needs to be be computed before lighting happens, - // but after environment and reflection probes are added - // Environment brdf approximation (Lazarov 2013) - // see https://www.unrealengine.com/en-US/blog/physically-based-shading-on-mobile - const vec4 c0 = vec4(-1.0, -0.0275, -0.572, 0.022); - const vec4 c1 = vec4(1.0, 0.0425, 1.04, -0.04); - vec4 r = roughness * c0 + c1; - float ndotv = clamp(dot(normal, eye_vec), 0.0, 1.0); - float a004 = min(r.x * r.x, exp2(-9.28 * ndotv)) * r.x + r.y; - vec2 env = vec2(-1.04, 1.04) * a004 + r.zw; +#ifdef USE_GI_PROBES + gi_probes_compute(vertex, normal, roughness, env_reflection_light, ambient_light); + +#endif + +#ifdef USE_LIGHTMAP + ambient_light = texture(lightmap, uv2).rgb * lightmap_energy; +#endif + +#ifdef USE_LIGHTMAP_CAPTURE + { + vec3 cone_dirs[12] = vec3[]( + vec3(0.0, 0.0, 1.0), + vec3(0.866025, 0.0, 0.5), + vec3(0.267617, 0.823639, 0.5), + vec3(-0.700629, 0.509037, 0.5), + vec3(-0.700629, -0.509037, 0.5), + vec3(0.267617, -0.823639, 0.5), + vec3(0.0, 0.0, -1.0), + vec3(0.866025, 0.0, -0.5), + vec3(0.267617, 0.823639, -0.5), + vec3(-0.700629, 0.509037, -0.5), + vec3(-0.700629, -0.509037, -0.5), + vec3(0.267617, -0.823639, -0.5)); + + vec3 local_normal = normalize(camera_matrix * vec4(normal, 0.0)).xyz; + vec4 captured = vec4(0.0); + float sum = 0.0; + for (int i = 0; i < 12; i++) { + float amount = max(0.0, dot(local_normal, cone_dirs[i])); //not correct, but creates a nice wrap around effect + captured += lightmap_captures[i] * amount; + sum += amount; + } + + captured /= sum; + + if (lightmap_capture_sky) { + ambient_light = mix(ambient_light, captured.rgb, captured.a); + } else { + ambient_light = captured.rgb; + } + } +#endif + +#ifdef USE_FORWARD_LIGHTING - vec3 f0 = F0(metallic, specular, albedo); - env_reflection_light *= env.x * f0 + env.y; + highp vec4 reflection_accum = vec4(0.0, 0.0, 0.0, 0.0); + highp vec4 ambient_accum = vec4(0.0, 0.0, 0.0, 0.0); + for (int i = 0; i < reflection_count; i++) { + reflection_process(reflection_indices[i], vertex, normal, binormal, tangent, roughness, anisotropy, ambient_light, env_reflection_light, reflection_accum, ambient_accum); + } + + if (reflection_accum.a > 0.0) { + specular_light += reflection_accum.rgb / reflection_accum.a; + } else { + specular_light += env_reflection_light; + } +#if !defined(USE_LIGHTMAP) && !defined(USE_LIGHTMAP_CAPTURE) + if (ambient_accum.a > 0.0) { + ambient_light = ambient_accum.rgb / ambient_accum.a; + } +#endif +#endif + + { + +#if defined(DIFFUSE_TOON) + //simplify for toon, as + specular_light *= specular * metallic * albedo * 2.0; +#else + + // scales the specular reflections, needs to be be computed before lighting happens, + // but after environment, GI, and reflection probes are added + // Environment brdf approximation (Lazarov 2013) + // see https://www.unrealengine.com/en-US/blog/physically-based-shading-on-mobile + const vec4 c0 = vec4(-1.0, -0.0275, -0.572, 0.022); + const vec4 c1 = vec4(1.0, 0.0425, 1.04, -0.04); + vec4 r = roughness * c0 + c1; + float ndotv = clamp(dot(normal, eye_vec), 0.0, 1.0); + float a004 = min(r.x * r.x, exp2(-9.28 * ndotv)) * r.x + r.y; + vec2 env = vec2(-1.04, 1.04) * a004 + r.zw; + + vec3 f0 = F0(metallic, specular, albedo); + specular_light *= env.x * f0 + env.y; +#endif + } #if defined(USE_LIGHT_DIRECTIONAL) @@ -1970,91 +2052,49 @@ FRAGMENT_SHADER_CODE specular_light *= mix(vec3(1.0), light_attenuation, specular_light_interp.a); #else - light_compute(normal, -light_direction_attenuation.xyz, eye_vec, binormal, tangent, light_color_energy.rgb, light_attenuation, albedo, transmission, light_params.z * specular_blob_intensity, roughness, metallic, specular, rim, rim_tint, clearcoat, clearcoat_gloss, anisotropy, diffuse_light, specular_light); + light_compute(normal, -light_direction_attenuation.xyz, eye_vec, binormal, tangent, light_color_energy.rgb, light_attenuation, albedo, transmission, light_params.z * specular_blob_intensity, roughness, metallic, specular, rim, rim_tint, clearcoat, clearcoat_gloss, anisotropy, diffuse_light, specular_light, alpha); #endif #endif //#USE_LIGHT_DIRECTIONAL -#ifdef USE_GI_PROBES - gi_probes_compute(vertex, normal, roughness, env_reflection_light, ambient_light); - -#endif - -#ifdef USE_LIGHTMAP - ambient_light = texture(lightmap, uv2).rgb * lightmap_energy; -#endif - -#ifdef USE_LIGHTMAP_CAPTURE - { - vec3 cone_dirs[12] = vec3[]( - vec3(0.0, 0.0, 1.0), - vec3(0.866025, 0.0, 0.5), - vec3(0.267617, 0.823639, 0.5), - vec3(-0.700629, 0.509037, 0.5), - vec3(-0.700629, -0.509037, 0.5), - vec3(0.267617, -0.823639, 0.5), - vec3(0.0, 0.0, -1.0), - vec3(0.866025, 0.0, -0.5), - vec3(0.267617, 0.823639, -0.5), - vec3(-0.700629, 0.509037, -0.5), - vec3(-0.700629, -0.509037, -0.5), - vec3(0.267617, -0.823639, -0.5)); - - vec3 local_normal = normalize(camera_matrix * vec4(normal, 0.0)).xyz; - vec4 captured = vec4(0.0); - float sum = 0.0; - for (int i = 0; i < 12; i++) { - float amount = max(0.0, dot(local_normal, cone_dirs[i])); //not correct, but creates a nice wrap around effect - captured += lightmap_captures[i] * amount; - sum += amount; - } - - captured /= sum; - - if (lightmap_capture_sky) { - ambient_light = mix(ambient_light, captured.rgb, captured.a); - } else { - ambient_light = captured.rgb; - } - } -#endif - #ifdef USE_FORWARD_LIGHTING - highp vec4 reflection_accum = vec4(0.0, 0.0, 0.0, 0.0); - highp vec4 ambient_accum = vec4(0.0, 0.0, 0.0, 0.0); - for (int i = 0; i < reflection_count; i++) { - reflection_process(reflection_indices[i], vertex, normal, binormal, tangent, roughness, anisotropy, ambient_light, env_reflection_light, reflection_accum, ambient_accum); - } - - if (reflection_accum.a > 0.0) { - specular_light += reflection_accum.rgb / reflection_accum.a; - } else { - specular_light += env_reflection_light; - } -#if !defined(USE_LIGHTMAP) && !defined(USE_LIGHTMAP_CAPTURE) - if (ambient_accum.a > 0.0) { - ambient_light = ambient_accum.rgb / ambient_accum.a; - } -#endif - #ifdef USE_VERTEX_LIGHTING diffuse_light *= albedo; #else for (int i = 0; i < omni_light_count; i++) { - light_process_omni(omni_light_indices[i], vertex, eye_vec, normal, binormal, tangent, albedo, transmission, roughness, metallic, specular, rim, rim_tint, clearcoat, clearcoat_gloss, anisotropy, specular_blob_intensity, diffuse_light, specular_light); + light_process_omni(omni_light_indices[i], vertex, eye_vec, normal, binormal, tangent, albedo, transmission, roughness, metallic, specular, rim, rim_tint, clearcoat, clearcoat_gloss, anisotropy, specular_blob_intensity, diffuse_light, specular_light, alpha); } for (int i = 0; i < spot_light_count; i++) { - light_process_spot(spot_light_indices[i], vertex, eye_vec, normal, binormal, tangent, albedo, transmission, roughness, metallic, specular, rim, rim_tint, clearcoat, clearcoat_gloss, anisotropy, specular_blob_intensity, diffuse_light, specular_light); + light_process_spot(spot_light_indices[i], vertex, eye_vec, normal, binormal, tangent, albedo, transmission, roughness, metallic, specular, rim, rim_tint, clearcoat, clearcoat_gloss, anisotropy, specular_blob_intensity, diffuse_light, specular_light, alpha); } #endif //USE_VERTEX_LIGHTING #endif +#ifdef USE_SHADOW_TO_OPACITY + alpha = min(alpha, clamp(length(ambient_light), 0.0, 1.0)); + +#if defined(ALPHA_SCISSOR_USED) + if (alpha < alpha_scissor) { + discard; + } +#endif // ALPHA_SCISSOR_USED + +#ifdef USE_OPAQUE_PREPASS + + if (alpha < opaque_prepass_threshold) { + discard; + } + +#endif // USE_OPAQUE_PREPASS + +#endif // USE_SHADOW_TO_OPACITY + #ifdef RENDER_DEPTH //nothing happens, so a tree-ssa optimizer will result in no fragment shader :) #else @@ -2073,14 +2113,6 @@ FRAGMENT_SHADER_CODE diffuse_light *= 1.0 - metallic; // TODO: avoid all diffuse and ambient light calculations when metallic == 1 up to this point ambient_light *= 1.0 - metallic; - { - -#if defined(DIFFUSE_TOON) - //simplify for toon, as - specular_light *= specular * metallic * albedo * 2.0; -#endif - } - if (fog_color_enabled.a > 0.5) { float fog_amount = 0.0; diff --git a/drivers/unix/os_unix.cpp b/drivers/unix/os_unix.cpp index 25cdc8d8a0..4de910ee1c 100644 --- a/drivers/unix/os_unix.cpp +++ b/drivers/unix/os_unix.cpp @@ -170,7 +170,7 @@ String OS_Unix::get_stdin_string(bool p_block) { return ""; } -String OS_Unix::get_name() { +String OS_Unix::get_name() const { return "Unix"; } diff --git a/drivers/unix/os_unix.h b/drivers/unix/os_unix.h index 6a05877a8c..53446a6b6f 100644 --- a/drivers/unix/os_unix.h +++ b/drivers/unix/os_unix.h @@ -76,7 +76,7 @@ public: virtual Error set_cwd(const String &p_cwd); - virtual String get_name(); + virtual String get_name() const; virtual Date get_date(bool utc) const; virtual Time get_time(bool utc) const; diff --git a/editor/SCsub b/editor/SCsub index 82a4ecb6c0..7d48e47c9f 100644 --- a/editor/SCsub +++ b/editor/SCsub @@ -79,9 +79,6 @@ if env['tools']: env.CommandNoCache('#editor/builtin_fonts.gen.h', flist, run_in_subprocess(editor_builders.make_fonts_header)) env.add_source_files(env.editor_sources, "*.cpp") - env_thirdparty = env.Clone() - env_thirdparty.disable_warnings() - env_thirdparty.add_source_files(env.editor_sources, ["#thirdparty/misc/clipper.cpp"]) SConscript('collada/SCsub') SConscript('doc/SCsub') diff --git a/editor/animation_track_editor.cpp b/editor/animation_track_editor.cpp index 61244ab78c..1985c91f31 100644 --- a/editor/animation_track_editor.cpp +++ b/editor/animation_track_editor.cpp @@ -3520,7 +3520,7 @@ void AnimationTrackEditor::_update_tracks() { void AnimationTrackEditor::_animation_changed() { if (animation_changing_awaiting_update) { - return; //all will be updated, dont bother with anything + return; //all will be updated, don't bother with anything } if (key_edit && key_edit->setting) { @@ -3656,7 +3656,8 @@ void AnimationTrackEditor::_update_step(double p_new_step) { step->set_block_signals(true); undo_redo->commit_action(); step->set_block_signals(false); - emit_signal("animation_step_changed", step_value); + emit_signal("animation_step_changed", p_new_step); + animation->_change_notify("step"); } void AnimationTrackEditor::_update_length(double p_new_len) { @@ -4931,7 +4932,6 @@ void AnimationTrackEditor::_bind_methods() { ClassDB::bind_method("_update_scroll", &AnimationTrackEditor::_update_scroll); ClassDB::bind_method("_update_tracks", &AnimationTrackEditor::_update_tracks); ClassDB::bind_method("_update_step", &AnimationTrackEditor::_update_step); - ClassDB::bind_method("_update_length", &AnimationTrackEditor::_update_length); ClassDB::bind_method("_dropped_track", &AnimationTrackEditor::_dropped_track); ClassDB::bind_method("_add_track", &AnimationTrackEditor::_add_track); ClassDB::bind_method("_new_track_node_selected", &AnimationTrackEditor::_new_track_node_selected); @@ -4992,7 +4992,6 @@ AnimationTrackEditor::AnimationTrackEditor() { timeline->connect("name_limit_changed", this, "_name_limit_changed"); timeline->connect("track_added", this, "_add_track"); timeline->connect("value_changed", this, "_timeline_value_changed"); - timeline->connect("length_changed", this, "_update_length"); scroll = memnew(ScrollContainer); timeline_vbox->add_child(scroll); diff --git a/editor/code_editor.cpp b/editor/code_editor.cpp index 7fd7b8dac3..695560ca34 100644 --- a/editor/code_editor.cpp +++ b/editor/code_editor.cpp @@ -765,6 +765,7 @@ void CodeTextEditor::update_editor_settings() { text_editor->set_highlight_current_line(EditorSettings::get_singleton()->get("text_editor/highlighting/highlight_current_line")); text_editor->cursor_set_blink_enabled(EditorSettings::get_singleton()->get("text_editor/cursor/caret_blink")); text_editor->cursor_set_blink_speed(EditorSettings::get_singleton()->get("text_editor/cursor/caret_blink_speed")); + text_editor->set_bookmark_gutter_enabled(EditorSettings::get_singleton()->get("text_editor/line_numbers/show_bookmark_gutter")); text_editor->set_breakpoint_gutter_enabled(EditorSettings::get_singleton()->get("text_editor/line_numbers/show_breakpoint_gutter")); text_editor->set_hiding_enabled(EditorSettings::get_singleton()->get("text_editor/line_numbers/code_folding")); text_editor->set_draw_fold_gutter(EditorSettings::get_singleton()->get("text_editor/line_numbers/code_folding")); @@ -1204,6 +1205,7 @@ Variant CodeTextEditor::get_edit_state() { state["folded_lines"] = text_editor->get_folded_lines(); state["breakpoints"] = text_editor->get_breakpoints_array(); + state["bookmarks"] = text_editor->get_bookmarks_array(); state["syntax_highlighter"] = TTR("Standard"); SyntaxHighlighter *syntax_highlighter = text_editor->_get_syntax_highlighting(); @@ -1241,6 +1243,13 @@ void CodeTextEditor::set_edit_state(const Variant &p_state) { } } + if (state.has("bookmarks")) { + Array bookmarks = state["bookmarks"]; + for (int i = 0; i < bookmarks.size(); i++) { + text_editor->set_line_as_bookmark(bookmarks[i], true); + } + } + text_editor->grab_focus(); } @@ -1358,6 +1367,70 @@ void CodeTextEditor::set_warning_nb(int p_warning_nb) { _set_show_warnings_panel(false); } +void CodeTextEditor::toggle_bookmark() { + + int line = text_editor->cursor_get_line(); + text_editor->set_line_as_bookmark(line, !text_editor->is_line_set_as_bookmark(line)); +} + +void CodeTextEditor::goto_next_bookmark() { + + List<int> bmarks; + text_editor->get_bookmarks(&bmarks); + if (bmarks.size() <= 0) { + return; + } + + int line = text_editor->cursor_get_line(); + if (line >= bmarks[bmarks.size() - 1]) { + text_editor->unfold_line(bmarks[0]); + text_editor->cursor_set_line(bmarks[0]); + } else { + for (List<int>::Element *E = bmarks.front(); E; E = E->next()) { + int bline = E->get(); + if (bline > line) { + text_editor->unfold_line(bline); + text_editor->cursor_set_line(bline); + return; + } + } + } +} + +void CodeTextEditor::goto_prev_bookmark() { + + List<int> bmarks; + text_editor->get_bookmarks(&bmarks); + if (bmarks.size() <= 0) { + return; + } + + int line = text_editor->cursor_get_line(); + if (line <= bmarks[0]) { + text_editor->unfold_line(bmarks[bmarks.size() - 1]); + text_editor->cursor_set_line(bmarks[bmarks.size() - 1]); + } else { + for (List<int>::Element *E = bmarks.back(); E; E = E->prev()) { + int bline = E->get(); + if (bline < line) { + text_editor->unfold_line(bline); + text_editor->cursor_set_line(bline); + return; + } + } + } +} + +void CodeTextEditor::remove_all_bookmarks() { + + List<int> bmarks; + text_editor->get_bookmarks(&bmarks); + + for (List<int>::Element *E = bmarks.front(); E; E = E->next()) { + text_editor->set_line_as_bookmark(E->get(), false); + } +} + void CodeTextEditor::_bind_methods() { ClassDB::bind_method("_text_editor_gui_input", &CodeTextEditor::_text_editor_gui_input); diff --git a/editor/code_editor.h b/editor/code_editor.h index b98af377ce..5c6b54ae44 100644 --- a/editor/code_editor.h +++ b/editor/code_editor.h @@ -234,6 +234,11 @@ public: virtual void apply_code() {} void goto_error(); + void toggle_bookmark(); + void goto_next_bookmark(); + void goto_prev_bookmark(); + void remove_all_bookmarks(); + void set_code_complete_func(CodeTextEditorCodeCompleteFunc p_code_complete_func, void *p_ud); CodeTextEditor(); diff --git a/editor/doc/doc_dump.cpp b/editor/doc/doc_dump.cpp index 6ccf0e26ea..866d57e054 100644 --- a/editor/doc/doc_dump.cpp +++ b/editor/doc/doc_dump.cpp @@ -111,7 +111,7 @@ void DocDump::dump(const String &p_file) { for (List<MethodInfo>::Element *E = method_list.front(); E; E = E->next()) { if (E->get().name == "" || E->get().name[0] == '_') - continue; //hiden + continue; //hidden MethodBind *m = ClassDB::get_method(name, E->get().name); diff --git a/editor/editor_audio_buses.cpp b/editor/editor_audio_buses.cpp index 2beb0153f4..9cd7d781a4 100644 --- a/editor/editor_audio_buses.cpp +++ b/editor/editor_audio_buses.cpp @@ -322,13 +322,13 @@ void EditorAudioBus::_volume_changed(float p_normalized) { float EditorAudioBus::_normalized_volume_to_scaled_db(float normalized) { /* There are three different formulas for the conversion from normalized - * values to relative decibal values. - * One formula is an exponential graph which intends to counteract - * the logorithmic nature of human hearing. This is an approximation - * of the behaviour of a 'logarithmic potentiometer' found on most - * musical instruments and also emulated in popular software. - * The other two equations are hand-tuned linear tapers that intend to - * try to ease the exponential equation in areas where it makes sense.*/ + * values to relative decibal values. + * One formula is an exponential graph which intends to counteract + * the logorithmic nature of human hearing. This is an approximation + * of the behaviour of a 'logarithmic potentiometer' found on most + * musical instruments and also emulated in popular software. + * The other two equations are hand-tuned linear tapers that intend to + * try to ease the exponential equation in areas where it makes sense.*/ if (normalized > 0.6f) { return 22.22f * normalized - 16.2f; @@ -341,16 +341,16 @@ float EditorAudioBus::_normalized_volume_to_scaled_db(float normalized) { float EditorAudioBus::_scaled_db_to_normalized_volume(float db) { /* Inversion of equations found in _normalized_volume_to_scaled_db. - * IMPORTANT: If one function changes, the other much change to reflect it. */ + * IMPORTANT: If one function changes, the other much change to reflect it. */ if (db > -2.88) { return (db + 16.2f) / 22.22f; } else if (db < -38.602f) { return (db + 80.00f) / 830.72f; } else { if (db < 0.0) { - /* To acommodate for NaN on negative numbers for root, we will mirror the - * results of the postive db range in order to get the desired numerical - * value on the negative side. */ + /* To accommodate for NaN on negative numbers for root, we will mirror the + * results of the positive db range in order to get the desired numerical + * value on the negative side. */ float positive_x = Math::pow(Math::abs(db) / 45.0f, 1.0f / 3.0f) + 1.0f; Vector2 translation = Vector2(1.0f, 0.0f) - Vector2(positive_x, Math::abs(db)); Vector2 reflected_position = Vector2(1.0, 0.0f) + translation; diff --git a/editor/editor_export.cpp b/editor/editor_export.cpp index 6751e58bb2..df481e0855 100644 --- a/editor/editor_export.cpp +++ b/editor/editor_export.cpp @@ -615,6 +615,7 @@ void EditorExportPlugin::_bind_methods() { BIND_VMETHOD(MethodInfo("_export_file", PropertyInfo(Variant::STRING, "path"), PropertyInfo(Variant::STRING, "type"), PropertyInfo(Variant::POOL_STRING_ARRAY, "features"))); BIND_VMETHOD(MethodInfo("_export_begin", PropertyInfo(Variant::POOL_STRING_ARRAY, "features"), PropertyInfo(Variant::BOOL, "is_debug"), PropertyInfo(Variant::STRING, "path"), PropertyInfo(Variant::INT, "flags"))); + BIND_VMETHOD(MethodInfo("_export_end")); } EditorExportPlugin::EditorExportPlugin() { diff --git a/editor/editor_file_system.cpp b/editor/editor_file_system.cpp index abd3bea951..4ddb28b440 100644 --- a/editor/editor_file_system.cpp +++ b/editor/editor_file_system.cpp @@ -218,7 +218,7 @@ void EditorFileSystem::_scan_filesystem() { if (first_scan) { // only use this on first scan, afterwards it gets ignored // this is so on first reimport we synchronize versions, then - // we dont care until editor restart. This is for usability mainly so + // we don't care until editor restart. This is for usability mainly so // your workflow is not killed after changing a setting by forceful reimporting // everything there is. filesystem_settings_version_for_import = l.strip_edges(); @@ -844,7 +844,7 @@ void EditorFileSystem::_scan_fs_changes(EditorFileSystemDirectory *p_dir, const bool updated_dir = false; String cd = p_dir->get_path(); - if (current_mtime != p_dir->modified_time || using_fat_32) { + if (current_mtime != p_dir->modified_time || using_fat32_or_exfat) { updated_dir = true; p_dir->modified_time = current_mtime; @@ -2140,8 +2140,8 @@ EditorFileSystem::EditorFileSystem() { if (da->change_dir("res://.import") != OK) { da->make_dir("res://.import"); } - //this should probably also work on Unix and use the string it returns for FAT32 - using_fat_32 = da->get_filesystem_type() == "FAT32"; + // This should probably also work on Unix and use the string it returns for FAT32 or exFAT + using_fat32_or_exfat = (da->get_filesystem_type() == "FAT32" || da->get_filesystem_type() == "exFAT"); memdelete(da); scan_total = 0; diff --git a/editor/editor_file_system.h b/editor/editor_file_system.h index 8943706202..72d9489f21 100644 --- a/editor/editor_file_system.h +++ b/editor/editor_file_system.h @@ -237,7 +237,7 @@ class EditorFileSystem : public Node { static Error _resource_import(const String &p_path); - bool using_fat_32; //workaround for projects in FAT32 filesystem (pendrives, most of the time) + bool using_fat32_or_exfat; // Workaround for projects in FAT32 or exFAT filesystem (pendrives, most of the time) void _find_group_files(EditorFileSystemDirectory *efd, Map<String, Vector<String> > &group_files, Set<String> &groups_to_reimport); diff --git a/editor/editor_folding.cpp b/editor/editor_folding.cpp index f6079624de..96653fec70 100644 --- a/editor/editor_folding.cpp +++ b/editor/editor_folding.cpp @@ -92,7 +92,7 @@ void EditorFolding::load_resource_folding(RES p_resource, const String &p_path) _set_unfolds(p_resource.ptr(), unfolds); } -void EditorFolding::_fill_folds(const Node *p_root, const Node *p_node, Array &p_folds, Array &resource_folds, Array& nodes_folded,Set<RES> &resources) { +void EditorFolding::_fill_folds(const Node *p_root, const Node *p_node, Array &p_folds, Array &resource_folds, Array &nodes_folded, Set<RES> &resources) { if (p_root != p_node) { if (!p_node->get_owner()) { return; //not owned, bye @@ -130,7 +130,7 @@ void EditorFolding::_fill_folds(const Node *p_root, const Node *p_node, Array &p } for (int i = 0; i < p_node->get_child_count(); i++) { - _fill_folds(p_root, p_node->get_child(i), p_folds, resource_folds, nodes_folded,resources); + _fill_folds(p_root, p_node->get_child(i), p_folds, resource_folds, nodes_folded, resources); } } void EditorFolding::save_scene_folding(const Node *p_scene, const String &p_path) { @@ -205,7 +205,7 @@ void EditorFolding::load_scene_folding(Node *p_scene, const String &p_path) { _set_unfolds(res.ptr(), unfolds2); } - for(int i=0;i<nodes_folded.size();i++) { + for (int i = 0; i < nodes_folded.size(); i++) { NodePath fold_path = nodes_folded[i]; if (p_scene->has_node(fold_path)) { Node *node = p_scene->get_node(fold_path); diff --git a/editor/editor_fonts.cpp b/editor/editor_fonts.cpp index fa4172cded..5b16b8f6d5 100644 --- a/editor/editor_fonts.cpp +++ b/editor/editor_fonts.cpp @@ -239,6 +239,9 @@ void editor_register_fonts(Ref<Theme> p_theme) { MAKE_SOURCE_FONT(df_code, int(EditorSettings::get_singleton()->get("interface/editor/code_font_size")) * EDSCALE); p_theme->set_font("source", "EditorFonts", df_code); + MAKE_SOURCE_FONT(df_expression, (int(EditorSettings::get_singleton()->get("interface/editor/code_font_size")) - 1) * EDSCALE); + p_theme->set_font("expression", "EditorFonts", df_expression); + MAKE_SOURCE_FONT(df_output_code, int(EDITOR_DEF("run/output/font_size", 13)) * EDSCALE); p_theme->set_font("output_source", "EditorFonts", df_output_code); diff --git a/editor/editor_node.cpp b/editor/editor_node.cpp index 907d43b26f..82e7a37f19 100644 --- a/editor/editor_node.cpp +++ b/editor/editor_node.cpp @@ -6403,7 +6403,7 @@ EditorNode::EditorNode() { ED_SHORTCUT("editor/editor_2d", TTR("Open 2D Editor"), KEY_F1); ED_SHORTCUT("editor/editor_3d", TTR("Open 3D Editor"), KEY_F2); ED_SHORTCUT("editor/editor_script", TTR("Open Script Editor"), KEY_F3); //hack needed for script editor F3 search to work :) Assign like this or don't use F3 - ED_SHORTCUT("editor/editor_help", TTR("Search Help"), KEY_F4); + ED_SHORTCUT("editor/editor_help", TTR("Search Help"), KEY_MASK_SHIFT | KEY_F1); #endif ED_SHORTCUT("editor/editor_assetlib", TTR("Open Asset Library")); ED_SHORTCUT("editor/editor_next", TTR("Open the next Editor")); diff --git a/editor/editor_properties_array_dict.cpp b/editor/editor_properties_array_dict.cpp index e3dc517a39..5f18959689 100644 --- a/editor/editor_properties_array_dict.cpp +++ b/editor/editor_properties_array_dict.cpp @@ -645,7 +645,7 @@ void EditorPropertyDictionary::update_property() { page->set_h_size_flags(SIZE_EXPAND_FILL); page->connect("value_changed", this, "_page_changed"); } else { - // Queue childs for deletion, delete immediately might cause errors. + // Queue children for deletion, deleting immediately might cause errors. for (int i = 1; i < vbox->get_child_count(); i++) { vbox->get_child(i)->queue_delete(); } diff --git a/editor/editor_resource_preview.cpp b/editor/editor_resource_preview.cpp index 173333dac9..2baad8c904 100644 --- a/editor/editor_resource_preview.cpp +++ b/editor/editor_resource_preview.cpp @@ -71,7 +71,21 @@ Ref<Texture> EditorResourcePreviewGenerator::generate_from_path(const String &p_ return generate(res, p_size); } -bool EditorResourcePreviewGenerator::should_generate_small_preview() const { +bool EditorResourcePreviewGenerator::generate_small_preview_automatically() const { + + if (get_script_instance() && get_script_instance()->has_method("generate_small_preview_automatically")) { + return get_script_instance()->call("generate_small_preview_automatically"); + } + + return false; +} + +bool EditorResourcePreviewGenerator::can_generate_small_preview() const { + + if (get_script_instance() && get_script_instance()->has_method("can_generate_small_preview")) { + return get_script_instance()->call("can_generate_small_preview"); + } + return false; } @@ -80,6 +94,8 @@ void EditorResourcePreviewGenerator::_bind_methods() { ClassDB::add_virtual_method(get_class_static(), MethodInfo(Variant::BOOL, "handles", PropertyInfo(Variant::STRING, "type"))); ClassDB::add_virtual_method(get_class_static(), MethodInfo(CLASS_INFO(Texture), "generate", PropertyInfo(Variant::OBJECT, "from", PROPERTY_HINT_RESOURCE_TYPE, "Resource"), PropertyInfo(Variant::VECTOR2, "size"))); ClassDB::add_virtual_method(get_class_static(), MethodInfo(CLASS_INFO(Texture), "generate_from_path", PropertyInfo(Variant::STRING, "path", PROPERTY_HINT_FILE), PropertyInfo(Variant::VECTOR2, "size"))); + ClassDB::add_virtual_method(get_class_static(), MethodInfo(Variant::BOOL, "generate_small_preview_automatically")); + ClassDB::add_virtual_method(get_class_static(), MethodInfo(Variant::BOOL, "can_generate_small_preview")); } EditorResourcePreviewGenerator::EditorResourcePreviewGenerator() { @@ -154,16 +170,27 @@ void EditorResourcePreview::_generate_preview(Ref<ImageTexture> &r_texture, Ref< } r_texture = generated; - if (r_texture.is_valid() && preview_generators[i]->should_generate_small_preview()) { - int small_thumbnail_size = EditorNode::get_singleton()->get_theme_base()->get_icon("Object", "EditorIcons")->get_width(); // Kind of a workaround to retrieve the default icon size - small_thumbnail_size *= EDSCALE; + int small_thumbnail_size = EditorNode::get_singleton()->get_theme_base()->get_icon("Object", "EditorIcons")->get_width(); // Kind of a workaround to retrieve the default icon size + small_thumbnail_size *= EDSCALE; + if (preview_generators[i]->can_generate_small_preview()) { + Ref<Texture> generated_small; + if (p_item.resource.is_valid()) { + generated_small = preview_generators[i]->generate(p_item.resource, Vector2(small_thumbnail_size, small_thumbnail_size)); + } else { + generated_small = preview_generators[i]->generate_from_path(p_item.path, Vector2(small_thumbnail_size, small_thumbnail_size)); + } + r_small_texture = generated_small; + } + + if (!r_small_texture.is_valid() && r_texture.is_valid() && preview_generators[i]->generate_small_preview_automatically()) { Ref<Image> small_image = r_texture->get_data(); small_image = small_image->duplicate(); small_image->resize(small_thumbnail_size, small_thumbnail_size, Image::INTERPOLATE_CUBIC); r_small_texture.instance(); r_small_texture->create_from_image(small_image); } + break; } diff --git a/editor/editor_resource_preview.h b/editor/editor_resource_preview.h index 9b9223a818..e0fd54c924 100644 --- a/editor/editor_resource_preview.h +++ b/editor/editor_resource_preview.h @@ -48,7 +48,8 @@ public: virtual Ref<Texture> generate(const RES &p_from, const Size2 p_size) const; virtual Ref<Texture> generate_from_path(const String &p_path, const Size2 p_size) const; - virtual bool should_generate_small_preview() const; + virtual bool generate_small_preview_automatically() const; + virtual bool can_generate_small_preview() const; EditorResourcePreviewGenerator(); }; diff --git a/editor/editor_settings.cpp b/editor/editor_settings.cpp index 193b2b7a88..79dcbca7a2 100644 --- a/editor/editor_settings.cpp +++ b/editor/editor_settings.cpp @@ -268,6 +268,11 @@ void EditorSettings::_load_defaults(Ref<ConfigFile> p_extra_config) { String host_lang = OS::get_singleton()->get_locale(); host_lang = TranslationServer::standardize_locale(host_lang); + // Some locales are not properly supported currently in Godot due to lack of font shaping + // (e.g. Arabic or Hindi), so even though we have work in progress translations for them, + // we skip them as they don't render properly. (GH-28577) + const Vector<String> locales_to_skip = String("ar,bn,fa,he,hi,ml,si,ta,te,ur").split(","); + String best; EditorTranslationList *etl = _editor_translations; @@ -275,6 +280,15 @@ void EditorSettings::_load_defaults(Ref<ConfigFile> p_extra_config) { while (etl->data) { const String &locale = etl->lang; + + // Skip locales which we can't render properly (see above comment). + // Test against language code without regional variants (e.g. ur_PK). + String lang_code = locale.get_slice("_", 0); + if (locales_to_skip.find(lang_code) != -1) { + etl++; + continue; + } + lang_hint += ","; lang_hint += locale; @@ -430,6 +444,7 @@ void EditorSettings::_load_defaults(Ref<ConfigFile> p_extra_config) { // Line numbers _initial_set("text_editor/line_numbers/show_line_numbers", true); _initial_set("text_editor/line_numbers/line_numbers_zero_padded", false); + _initial_set("text_editor/line_numbers/show_bookmark_gutter", true); _initial_set("text_editor/line_numbers/show_breakpoint_gutter", true); _initial_set("text_editor/line_numbers/show_info_gutter", true); _initial_set("text_editor/line_numbers/code_folding", true); @@ -546,7 +561,6 @@ void EditorSettings::_load_defaults(Ref<ConfigFile> p_extra_config) { _initial_set("editors/2d/bone_ik_color", Color(0.9, 0.9, 0.45, 0.9)); _initial_set("editors/2d/bone_outline_color", Color(0.35, 0.35, 0.35)); _initial_set("editors/2d/bone_outline_size", 2); - _initial_set("editors/2d/keep_margins_when_changing_anchors", false); _initial_set("editors/2d/viewport_border_color", Color(0.4, 0.4, 1.0, 0.4)); _initial_set("editors/2d/warped_mouse_panning", true); _initial_set("editors/2d/simple_spacebar_panning", false); @@ -648,6 +662,7 @@ void EditorSettings::_load_default_text_editor_theme() { _initial_set("text_editor/highlighting/function_color", Color::html("66a2ce")); _initial_set("text_editor/highlighting/member_variable_color", Color::html("e64e59")); _initial_set("text_editor/highlighting/mark_color", Color(1.0, 0.4, 0.4, 0.4)); + _initial_set("text_editor/highlighting/bookmark_color", Color(0.08, 0.49, 0.98)); _initial_set("text_editor/highlighting/breakpoint_color", Color(0.8, 0.8, 0.4, 0.2)); _initial_set("text_editor/highlighting/executing_line_color", Color(0.2, 0.8, 0.2, 0.4)); _initial_set("text_editor/highlighting/code_folding_color", Color(0.8, 0.8, 0.8, 0.8)); diff --git a/editor/editor_themes.cpp b/editor/editor_themes.cpp index ba4dd9d7e2..ff38b4b650 100644 --- a/editor/editor_themes.cpp +++ b/editor/editor_themes.cpp @@ -1118,6 +1118,7 @@ Ref<Theme> create_editor_theme(const Ref<Theme> p_theme) { const Color function_color = main_color; const Color member_variable_color = main_color.linear_interpolate(mono_color, 0.6); const Color mark_color = Color(error_color.r, error_color.g, error_color.b, 0.3); + const Color bookmark_color = Color(0.08, 0.49, 0.98); const Color breakpoint_color = error_color; const Color executing_line_color = Color(0.2, 0.8, 0.2, 0.4); const Color code_folding_color = alpha3; @@ -1154,6 +1155,7 @@ Ref<Theme> create_editor_theme(const Ref<Theme> p_theme) { setting->set_initial_value("text_editor/highlighting/function_color", function_color, true); setting->set_initial_value("text_editor/highlighting/member_variable_color", member_variable_color, true); setting->set_initial_value("text_editor/highlighting/mark_color", mark_color, true); + setting->set_initial_value("text_editor/highlighting/bookmark_color", bookmark_color, true); setting->set_initial_value("text_editor/highlighting/breakpoint_color", breakpoint_color, true); setting->set_initial_value("text_editor/highlighting/executing_line_color", executing_line_color, true); setting->set_initial_value("text_editor/highlighting/code_folding_color", code_folding_color, true); diff --git a/editor/export_template_manager.cpp b/editor/export_template_manager.cpp index ed6d6578ad..4e499021f9 100644 --- a/editor/export_template_manager.cpp +++ b/editor/export_template_manager.cpp @@ -566,7 +566,7 @@ Error ExportTemplateManager::install_android_template() { f->close(); } { - //add version, to ensure building wont work if template and Godot version are mismatch + //add version, to ensure building won't work if template and Godot version don't match FileAccessRef f = FileAccess::open("res://android/.build_version", FileAccess::WRITE); ERR_FAIL_COND_V(!f, ERR_CANT_CREATE); f->store_line(VERSION_FULL_CONFIG); @@ -636,7 +636,7 @@ Error ExportTemplateManager::install_android_template() { FileAccess::set_unix_permissions(to_write, (info.external_fa >> 16) & 0x01FF); #endif } else { - ERR_PRINTS("Cant uncompress file: " + to_write); + ERR_PRINTS("Can't uncompress file: " + to_write); } } diff --git a/editor/filesystem_dock.cpp b/editor/filesystem_dock.cpp index 5ce22154e0..52ed94e428 100644 --- a/editor/filesystem_dock.cpp +++ b/editor/filesystem_dock.cpp @@ -90,7 +90,7 @@ bool FileSystemDock::_create_tree(TreeItem *p_parent, EditorFileSystemDirectory String file_type = p_dir->get_file_type(i); if (_is_file_type_disabled_by_feature_profile(file_type)) { - //if type is disabled, file wont be displayed. + //if type is disabled, file won't be displayed. continue; } String file_name = p_dir->get_file(i); @@ -756,7 +756,7 @@ void FileSystemDock::_update_file_list(bool p_keep_selection) { Ref<Texture> type_icon; Ref<Texture> big_icon; - String tooltip = fname; + String tooltip = fpath; // Select the icons if (!finfo->import_broken) { diff --git a/editor/find_in_files.cpp b/editor/find_in_files.cpp index 4dbba952bf..11af9fc2eb 100644 --- a/editor/find_in_files.cpp +++ b/editor/find_in_files.cpp @@ -751,7 +751,6 @@ void FindInFilesPanel::_on_replace_text_changed(String text) { void FindInFilesPanel::_on_replace_all_clicked() { String replace_text = get_replace_text(); - ERR_FAIL_COND(replace_text.empty()); PoolStringArray modified_files; @@ -887,7 +886,7 @@ String FindInFilesPanel::get_replace_text() { void FindInFilesPanel::update_replace_buttons() { String text = get_replace_text(); - bool disabled = text.empty() || _finder->is_searching(); + bool disabled = _finder->is_searching(); _replace_all_button->set_disabled(disabled); } diff --git a/editor/import/resource_importer_texture.cpp b/editor/import/resource_importer_texture.cpp index d72de3de48..5865ceb3af 100644 --- a/editor/import/resource_importer_texture.cpp +++ b/editor/import/resource_importer_texture.cpp @@ -81,7 +81,7 @@ void ResourceImporterTexture::_texture_reimport_normal(const Ref<StreamTexture> void ResourceImporterTexture::update_imports() { if (EditorFileSystem::get_singleton()->is_scanning() || EditorFileSystem::get_singleton()->is_importing()) { - return; // do nothing for noe + return; // do nothing for now } mutex->lock(); diff --git a/editor/plugins/animation_player_editor_plugin.cpp b/editor/plugins/animation_player_editor_plugin.cpp index 0a9436952b..c6b7df56a0 100644 --- a/editor/plugins/animation_player_editor_plugin.cpp +++ b/editor/plugins/animation_player_editor_plugin.cpp @@ -293,25 +293,40 @@ void AnimationPlayerEditor::_pause_pressed() { //player->set_pause( pause->is_pressed() ); } -void AnimationPlayerEditor::_animation_selected(int p_which) { - if (updating) - return; +String AnimationPlayerEditor::_get_current_animation() const { + // when selecting an animation, the idea is that the only interesting behavior // ui-wise is that it should play/blend the next one if currently playing - String current; if (animation->get_selected() >= 0 && animation->get_selected() < animation->get_item_count()) { - current = animation->get_item_text(animation->get_selected()); + return animation->get_item_text(animation->get_selected()); } - if (current != "") { + return ""; +} - player->set_assigned_animation(current); +void AnimationPlayerEditor::_animation_selected(int p_which) { + + if (updating) + return; + + _current_animation_updated(); +} +void AnimationPlayerEditor::_current_animation_updated() { + + String current = _get_current_animation(); + + if (current != "") { Ref<Animation> anim = player->get_animation(current); + + player->set_assigned_animation(current); { + if (!anim->is_connected("changed", this, "_current_animation_updated")) + anim->connect("changed", this, "_current_animation_updated"); + track_editor->set_animation(anim); Node *root = player->get_node(player->get_root()); if (root) { @@ -1068,17 +1083,19 @@ void AnimationPlayerEditor::_list_changed() { _update_player(); } -void AnimationPlayerEditor::_animation_key_editor_anim_len_changed(float p_len) { - - frame->set_max(p_len); -} - void AnimationPlayerEditor::_animation_key_editor_anim_step_changed(float p_len) { if (p_len) frame->set_step(p_len); else frame->set_step(0.00001); + + String current = _get_current_animation(); + + if (current != "") { + Ref<Animation> anim = player->get_animation(current); + anim->_change_notify("step"); + } } void AnimationPlayerEditor::_animation_key_editor_seek(float p_pos, bool p_drag) { @@ -1431,6 +1448,7 @@ void AnimationPlayerEditor::_prepare_onion_layers_2() { new_state["show_rulers"] = false; new_state["show_guides"] = false; new_state["show_helpers"] = false; + new_state["show_zoom_control"] = false; // TODO: Save/restore only affected entries CanvasItemEditor::get_singleton()->set_state(new_state); } @@ -1483,7 +1501,7 @@ void AnimationPlayerEditor::_prepare_onion_layers_2() { if (valid) { player->seek(pos, true); get_tree()->flush_transform_notifications(); // Needed for transforms of Spatials - values_backup.update_skeletons(); // Needed for Skeletons + values_backup.update_skeletons(); // Needed for Skeletons (2D & 3D) VS::get_singleton()->viewport_set_active(onion.captures[cidx], true); VS::get_singleton()->viewport_set_parent_viewport(root_vp, onion.captures[cidx]); @@ -1557,6 +1575,7 @@ void AnimationPlayerEditor::_bind_methods() { ClassDB::bind_method(D_METHOD("_autoplay_pressed"), &AnimationPlayerEditor::_autoplay_pressed); ClassDB::bind_method(D_METHOD("_pause_pressed"), &AnimationPlayerEditor::_pause_pressed); ClassDB::bind_method(D_METHOD("_animation_selected"), &AnimationPlayerEditor::_animation_selected); + ClassDB::bind_method(D_METHOD("_current_animation_updated"), &AnimationPlayerEditor::_current_animation_updated); ClassDB::bind_method(D_METHOD("_animation_name_edited"), &AnimationPlayerEditor::_animation_name_edited); ClassDB::bind_method(D_METHOD("_animation_new"), &AnimationPlayerEditor::_animation_new); ClassDB::bind_method(D_METHOD("_animation_rename"), &AnimationPlayerEditor::_animation_rename); @@ -1576,7 +1595,6 @@ void AnimationPlayerEditor::_bind_methods() { //ClassDB::bind_method(D_METHOD("_editor_load_all"),&AnimationPlayerEditor::_editor_load_all); ClassDB::bind_method(D_METHOD("_list_changed"), &AnimationPlayerEditor::_list_changed); ClassDB::bind_method(D_METHOD("_animation_key_editor_seek"), &AnimationPlayerEditor::_animation_key_editor_seek); - ClassDB::bind_method(D_METHOD("_animation_key_editor_anim_len_changed"), &AnimationPlayerEditor::_animation_key_editor_anim_len_changed); ClassDB::bind_method(D_METHOD("_animation_key_editor_anim_step_changed"), &AnimationPlayerEditor::_animation_key_editor_anim_step_changed); ClassDB::bind_method(D_METHOD("_hide_anim_editors"), &AnimationPlayerEditor::_hide_anim_editors); ClassDB::bind_method(D_METHOD("_animation_duplicate"), &AnimationPlayerEditor::_animation_duplicate); @@ -1809,7 +1827,6 @@ AnimationPlayerEditor::AnimationPlayerEditor(EditorNode *p_editor, AnimationPlay add_child(track_editor); track_editor->set_v_size_flags(SIZE_EXPAND_FILL); track_editor->connect("timeline_changed", this, "_animation_key_editor_seek"); - track_editor->connect("animation_len_changed", this, "_animation_key_editor_anim_len_changed"); track_editor->connect("animation_step_changed", this, "_animation_key_editor_anim_step_changed"); _update_player(); diff --git a/editor/plugins/animation_player_editor_plugin.h b/editor/plugins/animation_player_editor_plugin.h index c6ab6c5e30..6162181f8c 100644 --- a/editor/plugins/animation_player_editor_plugin.h +++ b/editor/plugins/animation_player_editor_plugin.h @@ -173,7 +173,9 @@ class AnimationPlayerEditor : public VBoxContainer { void _autoplay_pressed(); void _stop_pressed(); void _pause_pressed(); + String _get_current_animation() const; void _animation_selected(int p_which); + void _current_animation_updated(); void _animation_new(); void _animation_rename(); void _animation_name_edited(); diff --git a/editor/plugins/canvas_item_editor_plugin.cpp b/editor/plugins/canvas_item_editor_plugin.cpp index c0f2410636..92cc12d931 100644 --- a/editor/plugins/canvas_item_editor_plugin.cpp +++ b/editor/plugins/canvas_item_editor_plugin.cpp @@ -1387,7 +1387,7 @@ bool CanvasItemEditor::_gui_input_anchors(const Ref<InputEvent> &p_event) { // Starts anchor dragging if needed if (drag_type == DRAG_NONE) { - if (b.is_valid() && b->get_button_index() == BUTTON_LEFT && b->is_pressed() && tool == TOOL_SELECT && show_helpers) { + if (b.is_valid() && b->get_button_index() == BUTTON_LEFT && b->is_pressed() && tool == TOOL_SELECT) { List<CanvasItem *> selection = _get_edited_canvas_items(); if (selection.size() == 1) { Control *control = Object::cast_to<Control>(selection[0]); @@ -2213,6 +2213,7 @@ bool CanvasItemEditor::_gui_input_hover(const Ref<InputEvent> &p_event) { void CanvasItemEditor::_gui_input_viewport(const Ref<InputEvent> &p_event) { bool accepted = false; + if (EditorSettings::get_singleton()->get("editors/2d/simple_spacebar_panning") || !Input::get_singleton()->is_key_pressed(KEY_SPACE)) { if ((accepted = _gui_input_rulers_and_guides(p_event))) { //printf("Rulers and guides\n"); @@ -2512,20 +2513,50 @@ void CanvasItemEditor::_draw_grid() { } } -void CanvasItemEditor::_draw_control_helpers(Control *control) { +void CanvasItemEditor::_draw_control_anchors(Control *control) { Transform2D xform = transform * control->get_global_transform_with_canvas(); RID ci = viewport->get_canvas_item(); + if (tool == TOOL_SELECT && !Object::cast_to<Container>(control->get_parent())) { + + // Compute the anchors + float anchors_values[4]; + anchors_values[0] = control->get_anchor(MARGIN_LEFT); + anchors_values[1] = control->get_anchor(MARGIN_TOP); + anchors_values[2] = control->get_anchor(MARGIN_RIGHT); + anchors_values[3] = control->get_anchor(MARGIN_BOTTOM); + + Vector2 anchors_pos[4]; + for (int i = 0; i < 4; i++) { + Vector2 value = Vector2((i % 2 == 0) ? anchors_values[i] : anchors_values[(i + 1) % 4], (i % 2 == 1) ? anchors_values[i] : anchors_values[(i + 1) % 4]); + anchors_pos[i] = xform.xform(_anchor_to_position(control, value)); + } + + // Draw the anchors handles + Rect2 anchor_rects[4]; + anchor_rects[0] = Rect2(anchors_pos[0] - anchor_handle->get_size(), anchor_handle->get_size()); + anchor_rects[1] = Rect2(anchors_pos[1] - Vector2(0.0, anchor_handle->get_size().y), Point2(-anchor_handle->get_size().x, anchor_handle->get_size().y)); + anchor_rects[2] = Rect2(anchors_pos[2], -anchor_handle->get_size()); + anchor_rects[3] = Rect2(anchors_pos[3] - Vector2(anchor_handle->get_size().x, 0.0), Point2(anchor_handle->get_size().x, -anchor_handle->get_size().y)); + + for (int i = 0; i < 4; i++) { + anchor_handle->draw_rect(ci, anchor_rects[i]); + } + } +} + +void CanvasItemEditor::_draw_control_helpers(Control *control) { + Transform2D xform = transform * control->get_global_transform_with_canvas(); if (tool == TOOL_SELECT && show_helpers && !Object::cast_to<Container>(control->get_parent())) { // Draw the helpers Color color_base = Color(0.8, 0.8, 0.8, 0.5); + // Compute the anchors float anchors_values[4]; anchors_values[0] = control->get_anchor(MARGIN_LEFT); anchors_values[1] = control->get_anchor(MARGIN_TOP); anchors_values[2] = control->get_anchor(MARGIN_RIGHT); anchors_values[3] = control->get_anchor(MARGIN_BOTTOM); - // Draw the anchors Vector2 anchors[4]; Vector2 anchors_pos[4]; for (int i = 0; i < 4; i++) { @@ -2592,16 +2623,6 @@ void CanvasItemEditor::_draw_control_helpers(Control *control) { _draw_percentage_at_position(percent_val, (line_ends[(dragged_anchor + 1) % 4] + anchors_pos[dragged_anchor]) / 2, (Margin)((dragged_anchor + 1) % 4)); } - Rect2 anchor_rects[4]; - anchor_rects[0] = Rect2(anchors_pos[0] - anchor_handle->get_size(), anchor_handle->get_size()); - anchor_rects[1] = Rect2(anchors_pos[1] - Vector2(0.0, anchor_handle->get_size().y), Point2(-anchor_handle->get_size().x, anchor_handle->get_size().y)); - anchor_rects[2] = Rect2(anchors_pos[2], -anchor_handle->get_size()); - anchor_rects[3] = Rect2(anchors_pos[3] - Vector2(anchor_handle->get_size().x, 0.0), Point2(anchor_handle->get_size().x, -anchor_handle->get_size().y)); - - for (int i = 0; i < 4; i++) { - anchor_handle->draw_rect(ci, anchor_rects[i]); - } - // Draw the margin values and the node width/height when dragging control side float ratio = 0.33; Transform2D parent_transform = xform * control->get_transform().affine_inverse(); @@ -2779,6 +2800,7 @@ void CanvasItemEditor::_draw_selection() { // Draw control-related helpers Control *control = Object::cast_to<Control>(canvas_item); if (control && _is_node_movable(control)) { + _draw_control_anchors(control); _draw_control_helpers(control); } @@ -3311,24 +3333,32 @@ void CanvasItemEditor::_notification(int p_what) { // Activate / Deactivate the pivot tool pivot_button->set_disabled(nb_having_pivot == 0); - // Show / Hide the layout button + // Show / Hide the layout and anchors mode buttons if (nb_control > 0 && nb_control == selection.size()) { presets_menu->set_visible(true); presets_menu->set_tooltip(TTR("Presets for the anchors and margins values of a Control node.")); + anchor_mode_button->set_visible(true); + anchor_mode_button->set_tooltip(TTR("When active, moving Control nodes changes their anchors instead of their margins.")); + + // Set the pressed state of the node + anchor_mode_button->set_pressed(anchors_mode); // Disable if the selected node is child of a container presets_menu->set_disabled(false); + anchor_mode_button->set_disabled(false); for (List<CanvasItem *>::Element *E = selection.front(); E; E = E->next()) { Control *control = Object::cast_to<Control>(E->get()); if (!control || Object::cast_to<Container>(control->get_parent())) { presets_menu->set_disabled(true); presets_menu->set_tooltip(TTR("Children of containers have their anchors and margins values overridden by their parent.")); + anchor_mode_button->set_disabled(true); + anchor_mode_button->set_tooltip(TTR("Children of containers have their anchors and margins values overridden by their parent.")); break; } } - } else { presets_menu->set_visible(false); + anchor_mode_button->set_visible(false); } // Update the viewport if bones changes @@ -3436,9 +3466,10 @@ void CanvasItemEditor::_notification(int p_what) { p->add_icon_item(get_icon("ControlHcenterWide", "EditorIcons"), "HCenter Wide ", ANCHORS_AND_MARGINS_PRESET_HCENTER_WIDE); p->add_separator(); p->add_icon_item(get_icon("ControlAlignWide", "EditorIcons"), "Full Rect", ANCHORS_AND_MARGINS_PRESET_WIDE); + p->add_icon_item(get_icon("Anchor", "EditorIcons"), "Keep Ratio", ANCHORS_AND_MARGINS_PRESET_KEEP_RATIO); p->add_separator(); - p->add_submenu_item(TTR("Anchors Only"), "Anchors"); - p->set_item_icon(20, get_icon("Anchor", "EditorIcons")); + p->add_submenu_item(TTR("Anchors only"), "Anchors"); + p->set_item_icon(21, get_icon("Anchor", "EditorIcons")); anchors_popup->clear(); anchors_popup->add_icon_item(get_icon("ControlAlignTopLeft", "EditorIcons"), "Top Left", ANCHORS_PRESET_TOP_LEFT); @@ -3460,7 +3491,29 @@ void CanvasItemEditor::_notification(int p_what) { anchors_popup->add_icon_item(get_icon("ControlHcenterWide", "EditorIcons"), "HCenter Wide ", ANCHORS_PRESET_HCENTER_WIDE); anchors_popup->add_separator(); anchors_popup->add_icon_item(get_icon("ControlAlignWide", "EditorIcons"), "Full Rect", ANCHORS_PRESET_WIDE); + + anchor_mode_button->set_icon(get_icon("Anchor", "EditorIcons")); + } +} + +void CanvasItemEditor::_selection_changed() { + // Update the anchors_mode + int nbValidControls = 0; + int nbAnchorsMode = 0; + List<Node *> selection = editor_selection->get_selected_node_list(); + for (List<Node *>::Element *E = selection.front(); E; E = E->next()) { + Control *control = Object::cast_to<Control>(E->get()); + if (!control) + continue; + if (Object::cast_to<Container>(control->get_parent())) + continue; + + nbValidControls++; + if (control->has_meta("_edit_use_anchors_") && control->get_meta("_edit_use_anchors_")) { + nbAnchorsMode++; + } } + anchors_mode = (nbValidControls == nbAnchorsMode); } void CanvasItemEditor::edit(CanvasItem *p_canvas_item) { @@ -3680,6 +3733,36 @@ void CanvasItemEditor::_set_anchors_and_margins_preset(Control::LayoutPreset p_p } undo_redo->commit_action(); + + anchors_mode = false; +} + +void CanvasItemEditor::_set_anchors_and_margins_to_keep_ratio() { + List<Node *> selection = editor_selection->get_selected_node_list(); + + undo_redo->create_action(TTR("Change Anchors and Margins")); + + for (List<Node *>::Element *E = selection.front(); E; E = E->next()) { + + Control *control = Object::cast_to<Control>(E->get()); + if (control) { + Point2 top_left_anchor = _position_to_anchor(control, Point2()); + Point2 bottom_right_anchor = _position_to_anchor(control, control->get_size()); + undo_redo->add_do_method(control, "set_anchor", MARGIN_LEFT, top_left_anchor.x, false, true); + undo_redo->add_do_method(control, "set_anchor", MARGIN_RIGHT, bottom_right_anchor.x, false, true); + undo_redo->add_do_method(control, "set_anchor", MARGIN_TOP, top_left_anchor.y, false, true); + undo_redo->add_do_method(control, "set_anchor", MARGIN_BOTTOM, bottom_right_anchor.y, false, true); + undo_redo->add_do_method(control, "set_meta", "_edit_use_anchors_", true); + + bool use_anchors = control->has_meta("_edit_use_anchors_") && control->get_meta("_edit_use_anchors_"); + undo_redo->add_undo_method(control, "_edit_set_state", control->_edit_get_state()); + undo_redo->add_undo_method(control, "set_meta", "_edit_use_anchors_", use_anchors); + + anchors_mode = true; + } + } + + undo_redo->commit_action(); } void CanvasItemEditor::_set_anchors_preset(Control::LayoutPreset p_preset) { @@ -3811,6 +3894,21 @@ void CanvasItemEditor::_insert_animation_keys(bool p_location, bool p_rotation, } } +void CanvasItemEditor::_button_toggle_anchor_mode(bool p_status) { + List<CanvasItem *> selection = _get_edited_canvas_items(false, false); + for (List<CanvasItem *>::Element *E = selection.front(); E; E = E->next()) { + Control *control = Object::cast_to<Control>(E->get()); + if (!control || Object::cast_to<Container>(control->get_parent())) + continue; + + control->set_meta("_edit_use_anchors_", p_status); + } + + anchors_mode = p_status; + + viewport->update(); +} + void CanvasItemEditor::_popup_callback(int p_op) { last_option = MenuOption(p_op); @@ -3911,6 +4009,7 @@ void CanvasItemEditor::_popup_callback(int p_op) { show_rulers = !show_rulers; int idx = view_menu->get_popup()->get_item_index(SHOW_RULERS); view_menu->get_popup()->set_item_checked(idx, show_rulers); + _update_scrollbars(); viewport->update(); } break; case SHOW_GUIDES: { @@ -4047,6 +4146,9 @@ void CanvasItemEditor::_popup_callback(int p_op) { case ANCHORS_AND_MARGINS_PRESET_WIDE: { _set_anchors_and_margins_preset(Control::PRESET_WIDE); } break; + case ANCHORS_AND_MARGINS_PRESET_KEEP_RATIO: { + _set_anchors_and_margins_to_keep_ratio(); + } break; case ANCHORS_PRESET_TOP_LEFT: { _set_anchors_preset(PRESET_TOP_LEFT); @@ -4220,6 +4322,7 @@ void CanvasItemEditor::_popup_callback(int p_op) { Map<Node *, Object *> &selection = editor_selection->get_selection(); + undo_redo->create_action(TTR("Create Custom Bone(s) from Node(s)")); for (Map<Node *, Object *>::Element *E = selection.front(); E; E = E->next()) { Node2D *n2d = Object::cast_to<Node2D>(E->key()); @@ -4229,19 +4332,24 @@ void CanvasItemEditor::_popup_callback(int p_op) { continue; if (!n2d->get_parent_item()) continue; + if (n2d->has_meta("_edit_bone_") && (bool)n2d->get_meta("_edit_bone_") == true) + continue; - n2d->set_meta("_edit_bone_", true); - if (!skeleton_show_bones) - skeleton_menu->get_popup()->activate_item(skeleton_menu->get_popup()->get_item_index(SKELETON_SHOW_BONES)); + undo_redo->add_do_method(n2d, "set_meta", "_edit_bone_", true); + undo_redo->add_undo_method(n2d, "remove_meta", "_edit_bone_"); } - _queue_update_bone_list(); - viewport->update(); + undo_redo->add_do_method(this, "_queue_update_bone_list"); + undo_redo->add_undo_method(this, "_queue_update_bone_list"); + undo_redo->add_do_method(viewport, "update"); + undo_redo->add_undo_method(viewport, "update"); + undo_redo->commit_action(); } break; case SKELETON_CLEAR_BONES: { Map<Node *, Object *> &selection = editor_selection->get_selection(); + undo_redo->create_action(TTR("Clear Bones")); for (Map<Node *, Object *>::Element *E = selection.front(); E; E = E->next()) { Node2D *n2d = Object::cast_to<Node2D>(E->key()); @@ -4249,40 +4357,47 @@ void CanvasItemEditor::_popup_callback(int p_op) { continue; if (!n2d->is_visible_in_tree()) continue; + if (!n2d->has_meta("_edit_bone_")) + continue; - n2d->set_meta("_edit_bone_", Variant()); - if (!skeleton_show_bones) - skeleton_menu->get_popup()->activate_item(skeleton_menu->get_popup()->get_item_index(SKELETON_SHOW_BONES)); + undo_redo->add_do_method(n2d, "remove_meta", "_edit_bone_"); + undo_redo->add_undo_method(n2d, "set_meta", "_edit_bone_", n2d->get_meta("_edit_bone_")); } - _queue_update_bone_list(); - viewport->update(); + undo_redo->add_do_method(this, "_queue_update_bone_list"); + undo_redo->add_undo_method(this, "_queue_update_bone_list"); + undo_redo->add_do_method(viewport, "update"); + undo_redo->add_undo_method(viewport, "update"); + undo_redo->commit_action(); } break; case SKELETON_SET_IK_CHAIN: { List<Node *> selection = editor_selection->get_selected_node_list(); + undo_redo->create_action(TTR("Make IK Chain")); for (List<Node *>::Element *E = selection.front(); E; E = E->next()) { CanvasItem *canvas_item = Object::cast_to<CanvasItem>(E->get()); if (!canvas_item || !canvas_item->is_visible_in_tree()) continue; - if (canvas_item->get_viewport() != EditorNode::get_singleton()->get_scene_root()) continue; + if (canvas_item->has_meta("_edit_ik_") && (bool)canvas_item->get_meta("_edit_ik_") == true) + continue; - canvas_item->set_meta("_edit_ik_", true); - if (!skeleton_show_bones) - skeleton_menu->get_popup()->activate_item(skeleton_menu->get_popup()->get_item_index(SKELETON_SHOW_BONES)); + undo_redo->add_do_method(canvas_item, "set_meta", "_edit_ik_", true); + undo_redo->add_undo_method(canvas_item, "remove_meta", "_edit_ik_"); } - - viewport->update(); + undo_redo->add_do_method(viewport, "update"); + undo_redo->add_undo_method(viewport, "update"); + undo_redo->commit_action(); } break; case SKELETON_CLEAR_IK_CHAIN: { Map<Node *, Object *> &selection = editor_selection->get_selection(); + undo_redo->create_action(TTR("Clear IK Chain")); for (Map<Node *, Object *>::Element *E = selection.front(); E; E = E->next()) { CanvasItem *n2d = Object::cast_to<CanvasItem>(E->key()); @@ -4290,12 +4405,15 @@ void CanvasItemEditor::_popup_callback(int p_op) { continue; if (!n2d->is_visible_in_tree()) continue; + if (!n2d->has_meta("_edit_ik_")) + continue; - n2d->set_meta("_edit_ik_", Variant()); - if (!skeleton_show_bones) - skeleton_menu->get_popup()->activate_item(skeleton_menu->get_popup()->get_item_index(SKELETON_SHOW_BONES)); + undo_redo->add_do_method(n2d, "remove_meta", "_edit_ik_"); + undo_redo->add_undo_method(n2d, "set_meta", "_edit_ik_", n2d->get_meta("_edit_ik_")); } - viewport->update(); + undo_redo->add_do_method(viewport, "update"); + undo_redo->add_undo_method(viewport, "update"); + undo_redo->commit_action(); } break; } @@ -4366,6 +4484,7 @@ void CanvasItemEditor::_bind_methods() { ClassDB::bind_method("_button_zoom_reset", &CanvasItemEditor::_button_zoom_reset); ClassDB::bind_method("_button_zoom_plus", &CanvasItemEditor::_button_zoom_plus); ClassDB::bind_method("_button_toggle_snap", &CanvasItemEditor::_button_toggle_snap); + ClassDB::bind_method("_button_toggle_anchor_mode", &CanvasItemEditor::_button_toggle_anchor_mode); ClassDB::bind_method("_update_scroll", &CanvasItemEditor::_update_scroll); ClassDB::bind_method("_update_scrollbars", &CanvasItemEditor::_update_scrollbars); ClassDB::bind_method("_popup_callback", &CanvasItemEditor::_popup_callback); @@ -4376,8 +4495,10 @@ void CanvasItemEditor::_bind_methods() { ClassDB::bind_method("_draw_viewport", &CanvasItemEditor::_draw_viewport); ClassDB::bind_method("_gui_input_viewport", &CanvasItemEditor::_gui_input_viewport); ClassDB::bind_method("_snap_changed", &CanvasItemEditor::_snap_changed); + ClassDB::bind_method("_queue_update_bone_list", &CanvasItemEditor::_update_bone_list); ClassDB::bind_method("_update_bone_list", &CanvasItemEditor::_update_bone_list); ClassDB::bind_method("_tree_changed", &CanvasItemEditor::_tree_changed); + ClassDB::bind_method("_selection_changed", &CanvasItemEditor::_selection_changed); ClassDB::bind_method("_popup_warning_depop", &CanvasItemEditor::_popup_warning_depop); ClassDB::bind_method(D_METHOD("_selection_result_pressed"), &CanvasItemEditor::_selection_result_pressed); ClassDB::bind_method(D_METHOD("_selection_menu_hide"), &CanvasItemEditor::_selection_menu_hide); @@ -4411,6 +4532,7 @@ Dictionary CanvasItemEditor::get_state() const { state["show_rulers"] = show_rulers; state["show_guides"] = show_guides; state["show_helpers"] = show_helpers; + state["show_zoom_control"] = zoom_hb->is_visible(); state["show_edit_locks"] = show_edit_locks; state["snap_rotation"] = snap_rotation; state["snap_relative"] = snap_relative; @@ -4421,6 +4543,7 @@ Dictionary CanvasItemEditor::get_state() const { void CanvasItemEditor::set_state(const Dictionary &p_state) { + bool update_scrollbars = false; Dictionary state = p_state; if (state.has("zoom")) { zoom = p_state["zoom"]; @@ -4429,7 +4552,7 @@ void CanvasItemEditor::set_state(const Dictionary &p_state) { if (state.has("ofs")) { view_offset = p_state["ofs"]; previous_update_view_offset = view_offset; - _update_scrollbars(); + update_scrollbars = true; } if (state.has("grid_offset")) { @@ -4517,6 +4640,7 @@ void CanvasItemEditor::set_state(const Dictionary &p_state) { show_rulers = state["show_rulers"]; int idx = view_menu->get_popup()->get_item_index(SHOW_RULERS); view_menu->get_popup()->set_item_checked(idx, show_rulers); + update_scrollbars = true; } if (state.has("show_guides")) { @@ -4537,6 +4661,11 @@ void CanvasItemEditor::set_state(const Dictionary &p_state) { view_menu->get_popup()->set_item_checked(idx, show_edit_locks); } + if (state.has("show_zoom_control")) { + // This one is not user-controllable, but instrumentable + zoom_hb->set_visible(state["show_zoom_control"]); + } + if (state.has("snap_rotation")) { snap_rotation = state["snap_rotation"]; int idx = snap_config_menu->get_popup()->get_item_index(SNAP_USE_ROTATION); @@ -4561,6 +4690,9 @@ void CanvasItemEditor::set_state(const Dictionary &p_state) { skeleton_menu->get_popup()->set_item_checked(idx, skeleton_show_bones); } + if (update_scrollbars) { + _update_scrollbars(); + } viewport->update(); } @@ -4636,6 +4768,8 @@ CanvasItemEditor::CanvasItemEditor(EditorNode *p_editor) { snap_relative = false; snap_pixel = false; + anchors_mode = false; + skeleton_show_bones = true; drag_type = DRAG_NONE; @@ -4654,6 +4788,7 @@ CanvasItemEditor::CanvasItemEditor(EditorNode *p_editor) { editor_selection = p_editor->get_editor_selection(); editor_selection->add_editor_plugin(this); editor_selection->connect("selection_changed", this, "update"); + editor_selection->connect("selection_changed", this, "_selection_changed"); hb = memnew(HBoxContainer); add_child(hb); @@ -4913,6 +5048,12 @@ CanvasItemEditor::CanvasItemEditor(EditorNode *p_editor) { anchors_popup->set_name("Anchors"); anchors_popup->connect("id_pressed", this, "_popup_callback"); + anchor_mode_button = memnew(ToolButton); + hb->add_child(anchor_mode_button); + anchor_mode_button->set_toggle_mode(true); + anchor_mode_button->hide(); + anchor_mode_button->connect("toggled", this, "_button_toggle_anchor_mode"); + animation_hb = memnew(HBoxContainer); hb->add_child(animation_hb); animation_hb->add_child(memnew(VSeparator)); diff --git a/editor/plugins/canvas_item_editor_plugin.h b/editor/plugins/canvas_item_editor_plugin.h index 14ea81f302..e098d261c0 100644 --- a/editor/plugins/canvas_item_editor_plugin.h +++ b/editor/plugins/canvas_item_editor_plugin.h @@ -129,6 +129,7 @@ private: ANCHORS_AND_MARGINS_PRESET_VCENTER_WIDE, ANCHORS_AND_MARGINS_PRESET_HCENTER_WIDE, ANCHORS_AND_MARGINS_PRESET_WIDE, + ANCHORS_AND_MARGINS_PRESET_KEEP_RATIO, ANCHORS_PRESET_TOP_LEFT, ANCHORS_PRESET_TOP_RIGHT, ANCHORS_PRESET_BOTTOM_LEFT, @@ -240,6 +241,8 @@ private: Point2 view_offset; Point2 previous_update_view_offset; + bool anchors_mode; + Point2 grid_offset; Point2 grid_step; int grid_step_multiplier; @@ -347,6 +350,8 @@ private: PopupMenu *anchors_and_margins_popup; PopupMenu *anchors_popup; + ToolButton *anchor_mode_button; + Button *key_loc_button; Button *key_rot_button; Button *key_scale_button; @@ -438,6 +443,7 @@ private: void _draw_guides(); void _draw_focus(); void _draw_grid(); + void _draw_control_anchors(Control *control); void _draw_control_helpers(Control *control); void _draw_selection(); void _draw_axis(); @@ -462,6 +468,8 @@ private: void _gui_input_viewport(const Ref<InputEvent> &p_event); + void _selection_changed(); + void _focus_selection(int p_op); void _solve_IK(Node2D *leaf_node, Point2 target_position); @@ -473,6 +481,9 @@ private: void _set_anchors_preset(Control::LayoutPreset p_preset); void _set_margins_preset(Control::LayoutPreset p_preset); void _set_anchors_and_margins_preset(Control::LayoutPreset p_preset); + void _set_anchors_and_margins_to_keep_ratio(); + + void _button_toggle_anchor_mode(bool p_status); HBoxContainer *zoom_hb; void _zoom_on_position(float p_zoom, Point2 p_position = Point2()); @@ -575,6 +586,8 @@ public: void focus_selection(); + bool is_anchors_mode_enabled() { return anchors_mode; }; + CanvasItemEditor(EditorNode *p_editor); }; diff --git a/editor/plugins/editor_preview_plugins.cpp b/editor/plugins/editor_preview_plugins.cpp index 58d7968723..28e57ac48a 100644 --- a/editor/plugins/editor_preview_plugins.cpp +++ b/editor/plugins/editor_preview_plugins.cpp @@ -78,7 +78,7 @@ bool EditorTexturePreviewPlugin::handles(const String &p_type) const { return ClassDB::is_parent_class(p_type, "Texture"); } -bool EditorTexturePreviewPlugin::should_generate_small_preview() const { +bool EditorTexturePreviewPlugin::generate_small_preview_automatically() const { return true; } @@ -186,7 +186,7 @@ Ref<Texture> EditorImagePreviewPlugin::generate(const RES &p_from, const Size2 p EditorImagePreviewPlugin::EditorImagePreviewPlugin() { } -bool EditorImagePreviewPlugin::should_generate_small_preview() const { +bool EditorImagePreviewPlugin::generate_small_preview_automatically() const { return true; } //////////////////////////////////////////////////////////////////////////// @@ -250,7 +250,7 @@ Ref<Texture> EditorBitmapPreviewPlugin::generate(const RES &p_from, const Size2 return ptex; } -bool EditorBitmapPreviewPlugin::should_generate_small_preview() const { +bool EditorBitmapPreviewPlugin::generate_small_preview_automatically() const { return true; } @@ -317,7 +317,7 @@ bool EditorMaterialPreviewPlugin::handles(const String &p_type) const { return ClassDB::is_parent_class(p_type, "Material"); //any material } -bool EditorMaterialPreviewPlugin::should_generate_small_preview() const { +bool EditorMaterialPreviewPlugin::generate_small_preview_automatically() const { return true; } diff --git a/editor/plugins/editor_preview_plugins.h b/editor/plugins/editor_preview_plugins.h index ed2c003a0a..16b1f3082b 100644 --- a/editor/plugins/editor_preview_plugins.h +++ b/editor/plugins/editor_preview_plugins.h @@ -39,7 +39,7 @@ class EditorTexturePreviewPlugin : public EditorResourcePreviewGenerator { GDCLASS(EditorTexturePreviewPlugin, EditorResourcePreviewGenerator) public: virtual bool handles(const String &p_type) const; - virtual bool should_generate_small_preview() const; + virtual bool generate_small_preview_automatically() const; virtual Ref<Texture> generate(const RES &p_from, const Size2 p_size) const; EditorTexturePreviewPlugin(); @@ -49,7 +49,7 @@ class EditorImagePreviewPlugin : public EditorResourcePreviewGenerator { GDCLASS(EditorImagePreviewPlugin, EditorResourcePreviewGenerator) public: virtual bool handles(const String &p_type) const; - virtual bool should_generate_small_preview() const; + virtual bool generate_small_preview_automatically() const; virtual Ref<Texture> generate(const RES &p_from, const Size2 p_size) const; EditorImagePreviewPlugin(); @@ -59,7 +59,7 @@ class EditorBitmapPreviewPlugin : public EditorResourcePreviewGenerator { GDCLASS(EditorBitmapPreviewPlugin, EditorResourcePreviewGenerator) public: virtual bool handles(const String &p_type) const; - virtual bool should_generate_small_preview() const; + virtual bool generate_small_preview_automatically() const; virtual Ref<Texture> generate(const RES &p_from, const Size2 p_size) const; EditorBitmapPreviewPlugin(); @@ -98,7 +98,7 @@ protected: public: virtual bool handles(const String &p_type) const; - virtual bool should_generate_small_preview() const; + virtual bool generate_small_preview_automatically() const; virtual Ref<Texture> generate(const RES &p_from, const Size2 p_size) const; EditorMaterialPreviewPlugin(); diff --git a/editor/plugins/script_editor_plugin.cpp b/editor/plugins/script_editor_plugin.cpp index 92579e5cef..38985a2b2c 100644 --- a/editor/plugins/script_editor_plugin.cpp +++ b/editor/plugins/script_editor_plugin.cpp @@ -1558,7 +1558,15 @@ struct _ScriptEditorItemData { bool operator<(const _ScriptEditorItemData &id) const { - return category == id.category ? sort_key < id.sort_key : category < id.category; + if (category == id.category) { + if (sort_key == id.sort_key) { + return index < id.index; + } else { + return sort_key < id.sort_key; + } + } else { + return category < id.category; + } } }; @@ -3305,9 +3313,7 @@ void ScriptEditorPlugin::edit(Object *p_object) { } else { script_editor->edit(p_script); } - } - - if (Object::cast_to<TextFile>(p_object)) { + } else if (Object::cast_to<TextFile>(p_object)) { script_editor->edit(Object::cast_to<TextFile>(p_object)); } } diff --git a/editor/plugins/script_text_editor.cpp b/editor/plugins/script_text_editor.cpp index eaba48fa05..f66ae0465f 100644 --- a/editor/plugins/script_text_editor.cpp +++ b/editor/plugins/script_text_editor.cpp @@ -213,6 +213,7 @@ void ScriptTextEditor::_load_theme_settings() { Color function_color = EDITOR_GET("text_editor/highlighting/function_color"); Color member_variable_color = EDITOR_GET("text_editor/highlighting/member_variable_color"); Color mark_color = EDITOR_GET("text_editor/highlighting/mark_color"); + Color bookmark_color = EDITOR_GET("text_editor/highlighting/bookmark_color"); Color breakpoint_color = EDITOR_GET("text_editor/highlighting/breakpoint_color"); Color executing_line_color = EDITOR_GET("text_editor/highlighting/executing_line_color"); Color code_folding_color = EDITOR_GET("text_editor/highlighting/code_folding_color"); @@ -245,6 +246,7 @@ void ScriptTextEditor::_load_theme_settings() { text_edit->add_color_override("number_color", number_color); text_edit->add_color_override("function_color", function_color); text_edit->add_color_override("member_variable_color", member_variable_color); + text_edit->add_color_override("bookmark_color", bookmark_color); text_edit->add_color_override("breakpoint_color", breakpoint_color); text_edit->add_color_override("executing_line_color", executing_line_color); text_edit->add_color_override("mark_color", mark_color); @@ -376,7 +378,6 @@ void ScriptTextEditor::reload_text() { int v = te->get_v_scroll(); te->set_text(script->get_source_code()); - te->clear_undo_history(); te->cursor_set_line(row); te->cursor_set_column(column); te->set_h_scroll(h); @@ -1066,6 +1067,22 @@ void ScriptTextEditor::_edit_option(int p_op) { goto_line_dialog->popup_find_line(tx); } break; + case BOOKMARK_TOGGLE: { + + code_editor->toggle_bookmark(); + } break; + case BOOKMARK_GOTO_NEXT: { + + code_editor->goto_next_bookmark(); + } break; + case BOOKMARK_GOTO_PREV: { + + code_editor->goto_prev_bookmark(); + } break; + case BOOKMARK_REMOVE_ALL: { + + code_editor->remove_all_bookmarks(); + } break; case DEBUG_TOGGLE_BREAKPOINT: { int line = tx->cursor_get_line(); @@ -1500,6 +1517,7 @@ void ScriptTextEditor::_make_context_menu(bool p_selection, bool p_color, bool p context_menu->add_shortcut(ED_GET_SHORTCUT("script_text_editor/indent_left"), EDIT_INDENT_LEFT); context_menu->add_shortcut(ED_GET_SHORTCUT("script_text_editor/indent_right"), EDIT_INDENT_RIGHT); context_menu->add_shortcut(ED_GET_SHORTCUT("script_text_editor/toggle_comment"), EDIT_TOGGLE_COMMENT); + context_menu->add_shortcut(ED_GET_SHORTCUT("script_text_editor/toggle_bookmark"), BOOKMARK_TOGGLE); if (p_selection) { context_menu->add_separator(); @@ -1652,6 +1670,16 @@ ScriptTextEditor::ScriptTextEditor() { search_menu->get_popup()->connect("id_pressed", this, "_edit_option"); + PopupMenu *bookmarks = memnew(PopupMenu); + bookmarks->set_name("bookmarks"); + edit_menu->get_popup()->add_child(bookmarks); + edit_menu->get_popup()->add_submenu_item(TTR("Bookmarks"), "bookmarks"); + bookmarks->add_shortcut(ED_GET_SHORTCUT("script_text_editor/toggle_bookmark"), BOOKMARK_TOGGLE); + bookmarks->add_shortcut(ED_GET_SHORTCUT("script_text_editor/remove_all_bookmarks"), BOOKMARK_REMOVE_ALL); + bookmarks->add_shortcut(ED_GET_SHORTCUT("script_text_editor/goto_next_bookmark"), BOOKMARK_GOTO_NEXT); + bookmarks->add_shortcut(ED_GET_SHORTCUT("script_text_editor/goto_previous_bookmark"), BOOKMARK_GOTO_PREV); + bookmarks->connect("id_pressed", this, "_edit_option"); + edit_hb->add_child(edit_menu); quick_open = memnew(ScriptEditorQuickOpen); @@ -1693,6 +1721,10 @@ void ScriptTextEditor::register_editor() { ED_SHORTCUT("script_text_editor/indent_left", TTR("Indent Left"), 0); ED_SHORTCUT("script_text_editor/indent_right", TTR("Indent Right"), 0); ED_SHORTCUT("script_text_editor/toggle_comment", TTR("Toggle Comment"), KEY_MASK_CMD | KEY_K); + ED_SHORTCUT("script_text_editor/toggle_bookmark", TTR("Toggle Bookmark"), KEY_MASK_CMD | KEY_MASK_ALT | KEY_B); + ED_SHORTCUT("script_text_editor/goto_next_bookmark", TTR("Go to Next Bookmark"), KEY_MASK_CMD | KEY_B); + ED_SHORTCUT("script_text_editor/goto_previous_bookmark", TTR("Go to Previous Bookmark"), KEY_MASK_CMD | KEY_MASK_SHIFT | KEY_B); + ED_SHORTCUT("script_text_editor/remove_all_bookmarks", TTR("Remove All Bookmarks"), 0); ED_SHORTCUT("script_text_editor/toggle_fold_line", TTR("Fold/Unfold Line"), KEY_MASK_ALT | KEY_F); ED_SHORTCUT("script_text_editor/fold_all_lines", TTR("Fold All Lines"), 0); ED_SHORTCUT("script_text_editor/unfold_all_lines", TTR("Unfold All Lines"), 0); @@ -1700,7 +1732,7 @@ void ScriptTextEditor::register_editor() { ED_SHORTCUT("script_text_editor/clone_down", TTR("Clone Down"), KEY_MASK_SHIFT | KEY_MASK_CMD | KEY_C); ED_SHORTCUT("script_text_editor/complete_symbol", TTR("Complete Symbol"), KEY_MASK_CTRL | KEY_SPACE); #else - ED_SHORTCUT("script_text_editor/clone_down", TTR("Clone Down"), KEY_MASK_CMD | KEY_B); + ED_SHORTCUT("script_text_editor/clone_down", TTR("Clone Down"), KEY_MASK_CMD | KEY_D); ED_SHORTCUT("script_text_editor/complete_symbol", TTR("Complete Symbol"), KEY_MASK_CMD | KEY_SPACE); #endif ED_SHORTCUT("script_text_editor/trim_trailing_whitespace", TTR("Trim Trailing Whitespace"), KEY_MASK_CMD | KEY_MASK_ALT | KEY_T); @@ -1740,7 +1772,7 @@ void ScriptTextEditor::register_editor() { #ifdef OSX_ENABLED ED_SHORTCUT("script_text_editor/contextual_help", TTR("Contextual Help"), KEY_MASK_ALT | KEY_MASK_SHIFT | KEY_SPACE); #else - ED_SHORTCUT("script_text_editor/contextual_help", TTR("Contextual Help"), KEY_MASK_SHIFT | KEY_F1); + ED_SHORTCUT("script_text_editor/contextual_help", TTR("Contextual Help"), KEY_MASK_ALT | KEY_F1); #endif ScriptEditor::register_create_script_editor_function(create_editor); diff --git a/editor/plugins/script_text_editor.h b/editor/plugins/script_text_editor.h index 0dbc884594..bdfdf18d45 100644 --- a/editor/plugins/script_text_editor.h +++ b/editor/plugins/script_text_editor.h @@ -128,6 +128,10 @@ class ScriptTextEditor : public ScriptEditorBase { SEARCH_LOCATE_FUNCTION, SEARCH_GOTO_LINE, SEARCH_IN_FILES, + BOOKMARK_TOGGLE, + BOOKMARK_GOTO_NEXT, + BOOKMARK_GOTO_PREV, + BOOKMARK_REMOVE_ALL, DEBUG_TOGGLE_BREAKPOINT, DEBUG_REMOVE_ALL_BREAKPOINTS, DEBUG_GOTO_NEXT_BREAKPOINT, diff --git a/editor/plugins/shader_editor_plugin.cpp b/editor/plugins/shader_editor_plugin.cpp index 31660a9e19..a795405dfc 100644 --- a/editor/plugins/shader_editor_plugin.cpp +++ b/editor/plugins/shader_editor_plugin.cpp @@ -84,6 +84,7 @@ void ShaderTextEditor::_load_theme_settings() { Color function_color = EDITOR_GET("text_editor/highlighting/function_color"); Color member_variable_color = EDITOR_GET("text_editor/highlighting/member_variable_color"); Color mark_color = EDITOR_GET("text_editor/highlighting/mark_color"); + Color bookmark_color = EDITOR_GET("text_editor/highlighting/bookmark_color"); Color breakpoint_color = EDITOR_GET("text_editor/highlighting/breakpoint_color"); Color executing_line_color = EDITOR_GET("text_editor/highlighting/executing_line_color"); Color code_folding_color = EDITOR_GET("text_editor/highlighting/code_folding_color"); @@ -113,6 +114,7 @@ void ShaderTextEditor::_load_theme_settings() { get_text_edit()->add_color_override("function_color", function_color); get_text_edit()->add_color_override("member_variable_color", member_variable_color); get_text_edit()->add_color_override("mark_color", mark_color); + get_text_edit()->add_color_override("bookmark_color", bookmark_color); get_text_edit()->add_color_override("breakpoint_color", breakpoint_color); get_text_edit()->add_color_override("executing_line_color", executing_line_color); get_text_edit()->add_color_override("code_folding_color", code_folding_color); @@ -304,6 +306,22 @@ void ShaderEditor::_menu_option(int p_option) { goto_line_dialog->popup_find_line(shader_editor->get_text_edit()); } break; + case BOOKMARK_TOGGLE: { + + shader_editor->toggle_bookmark(); + } break; + case BOOKMARK_GOTO_NEXT: { + + shader_editor->goto_next_bookmark(); + } break; + case BOOKMARK_GOTO_PREV: { + + shader_editor->goto_prev_bookmark(); + } break; + case BOOKMARK_REMOVE_ALL: { + + shader_editor->remove_all_bookmarks(); + } break; } if (p_option != SEARCH_FIND && p_option != SEARCH_REPLACE && p_option != SEARCH_GOTO_LINE) { shader_editor->get_text_edit()->call_deferred("grab_focus"); @@ -535,6 +553,16 @@ ShaderEditor::ShaderEditor(EditorNode *p_node) { search_menu->get_popup()->add_shortcut(ED_GET_SHORTCUT("script_text_editor/goto_line"), SEARCH_GOTO_LINE); search_menu->get_popup()->connect("id_pressed", this, "_menu_option"); + PopupMenu *bookmarks = memnew(PopupMenu); + bookmarks->set_name("bookmarks"); + edit_menu->get_popup()->add_child(bookmarks); + edit_menu->get_popup()->add_submenu_item(TTR("Bookmarks"), "bookmarks"); + bookmarks->add_shortcut(ED_GET_SHORTCUT("script_text_editor/toggle_bookmark"), BOOKMARK_TOGGLE); + bookmarks->add_shortcut(ED_GET_SHORTCUT("script_text_editor/remove_all_bookmarks"), BOOKMARK_REMOVE_ALL); + bookmarks->add_shortcut(ED_GET_SHORTCUT("script_text_editor/goto_next_bookmark"), BOOKMARK_GOTO_NEXT); + bookmarks->add_shortcut(ED_GET_SHORTCUT("script_text_editor/goto_previous_bookmark"), BOOKMARK_GOTO_PREV); + bookmarks->connect("id_pressed", this, "_edit_option"); + add_child(main_container); main_container->add_child(hbc); hbc->add_child(search_menu); diff --git a/editor/plugins/shader_editor_plugin.h b/editor/plugins/shader_editor_plugin.h index 46c78c1d33..28ac9faaa5 100644 --- a/editor/plugins/shader_editor_plugin.h +++ b/editor/plugins/shader_editor_plugin.h @@ -88,6 +88,10 @@ class ShaderEditor : public PanelContainer { SEARCH_FIND_PREV, SEARCH_REPLACE, SEARCH_GOTO_LINE, + BOOKMARK_TOGGLE, + BOOKMARK_GOTO_NEXT, + BOOKMARK_GOTO_PREV, + BOOKMARK_REMOVE_ALL, }; diff --git a/editor/plugins/spatial_editor_plugin.cpp b/editor/plugins/spatial_editor_plugin.cpp index 5a733f6509..95a70f2ae5 100644 --- a/editor/plugins/spatial_editor_plugin.cpp +++ b/editor/plugins/spatial_editor_plugin.cpp @@ -5605,7 +5605,7 @@ SpatialEditor::SpatialEditor(EditorNode *p_editor) { ED_SHORTCUT("spatial_editor/front_view", TTR("Front View"), KEY_KP_1); ED_SHORTCUT("spatial_editor/left_view", TTR("Left View"), KEY_MASK_ALT + KEY_KP_3); ED_SHORTCUT("spatial_editor/right_view", TTR("Right View"), KEY_KP_3); - ED_SHORTCUT("spatial_editor/switch_perspective_orthogonal", TTR("Switch Perspective/Orthogonal view"), KEY_KP_5); + ED_SHORTCUT("spatial_editor/switch_perspective_orthogonal", TTR("Switch Perspective/Orthogonal View"), KEY_KP_5); ED_SHORTCUT("spatial_editor/insert_anim_key", TTR("Insert Animation Key"), KEY_K); ED_SHORTCUT("spatial_editor/focus_origin", TTR("Focus Origin"), KEY_O); ED_SHORTCUT("spatial_editor/focus_selection", TTR("Focus Selection"), KEY_F); @@ -5626,7 +5626,7 @@ SpatialEditor::SpatialEditor(EditorNode *p_editor) { hbc_menu->add_child(transform_menu); p = transform_menu->get_popup(); - p->add_shortcut(ED_SHORTCUT("spatial_editor/snap_to_floor", TTR("Snap object to floor"), KEY_PAGEDOWN), MENU_SNAP_TO_FLOOR); + p->add_shortcut(ED_SHORTCUT("spatial_editor/snap_to_floor", TTR("Snap Object to Floor"), KEY_PAGEDOWN), MENU_SNAP_TO_FLOOR); p->add_shortcut(ED_SHORTCUT("spatial_editor/configure_snap", TTR("Configure Snap...")), MENU_TRANSFORM_CONFIGURE_SNAP); p->add_separator(); p->add_shortcut(ED_SHORTCUT("spatial_editor/transform_dialog", TTR("Transform Dialog...")), MENU_TRANSFORM_DIALOG); diff --git a/editor/plugins/text_editor.cpp b/editor/plugins/text_editor.cpp index becaae3567..a0f3c253d1 100644 --- a/editor/plugins/text_editor.cpp +++ b/editor/plugins/text_editor.cpp @@ -93,6 +93,7 @@ void TextEditor::_load_theme_settings() { Color function_color = EDITOR_GET("text_editor/highlighting/function_color"); Color member_variable_color = EDITOR_GET("text_editor/highlighting/member_variable_color"); Color mark_color = EDITOR_GET("text_editor/highlighting/mark_color"); + Color bookmark_color = EDITOR_GET("text_editor/highlighting/bookmark_color"); Color breakpoint_color = EDITOR_GET("text_editor/highlighting/breakpoint_color"); Color executing_line_color = EDITOR_GET("text_editor/highlighting/executing_line_color"); Color code_folding_color = EDITOR_GET("text_editor/highlighting/code_folding_color"); @@ -127,6 +128,7 @@ void TextEditor::_load_theme_settings() { text_edit->add_color_override("breakpoint_color", breakpoint_color); text_edit->add_color_override("executing_line_color", executing_line_color); text_edit->add_color_override("mark_color", mark_color); + text_edit->add_color_override("bookmark_color", bookmark_color); text_edit->add_color_override("code_folding_color", code_folding_color); text_edit->add_color_override("search_result_color", search_result_color); text_edit->add_color_override("search_result_border_color", search_result_border_color); @@ -202,7 +204,6 @@ void TextEditor::reload_text() { int v = te->get_v_scroll(); te->set_text(text_file->get_text()); - te->clear_undo_history(); te->cursor_set_line(row); te->cursor_set_column(column); te->set_h_scroll(h); @@ -438,6 +439,22 @@ void TextEditor::_edit_option(int p_op) { goto_line_dialog->popup_find_line(tx); } break; + case BOOKMARK_TOGGLE: { + + code_editor->toggle_bookmark(); + } break; + case BOOKMARK_GOTO_NEXT: { + + code_editor->goto_next_bookmark(); + } break; + case BOOKMARK_GOTO_PREV: { + + code_editor->goto_prev_bookmark(); + } break; + case BOOKMARK_REMOVE_ALL: { + + code_editor->remove_all_bookmarks(); + } break; } } @@ -620,5 +637,15 @@ TextEditor::TextEditor() { highlighter_menu->add_radio_check_item(TTR("Standard")); highlighter_menu->connect("id_pressed", this, "_change_syntax_highlighter"); + PopupMenu *bookmarks = memnew(PopupMenu); + bookmarks->set_name("bookmarks"); + edit_menu->get_popup()->add_child(bookmarks); + edit_menu->get_popup()->add_submenu_item(TTR("Bookmarks"), "bookmarks"); + bookmarks->add_shortcut(ED_GET_SHORTCUT("script_text_editor/toggle_bookmark"), BOOKMARK_TOGGLE); + bookmarks->add_shortcut(ED_GET_SHORTCUT("script_text_editor/remove_all_bookmarks"), BOOKMARK_REMOVE_ALL); + bookmarks->add_shortcut(ED_GET_SHORTCUT("script_text_editor/goto_next_bookmark"), BOOKMARK_GOTO_NEXT); + bookmarks->add_shortcut(ED_GET_SHORTCUT("script_text_editor/goto_previous_bookmark"), BOOKMARK_GOTO_PREV); + bookmarks->connect("id_pressed", this, "_edit_option"); + code_editor->get_text_edit()->set_drag_forwarding(this); } diff --git a/editor/plugins/text_editor.h b/editor/plugins/text_editor.h index 767001e2f6..2da7474793 100644 --- a/editor/plugins/text_editor.h +++ b/editor/plugins/text_editor.h @@ -87,6 +87,10 @@ private: SEARCH_FIND_PREV, SEARCH_REPLACE, SEARCH_GOTO_LINE, + BOOKMARK_TOGGLE, + BOOKMARK_GOTO_NEXT, + BOOKMARK_GOTO_PREV, + BOOKMARK_REMOVE_ALL, }; protected: diff --git a/editor/plugins/theme_editor_plugin.cpp b/editor/plugins/theme_editor_plugin.cpp index 85743c96d6..5b67d259ba 100644 --- a/editor/plugins/theme_editor_plugin.cpp +++ b/editor/plugins/theme_editor_plugin.cpp @@ -631,12 +631,14 @@ ThemeEditor::ThemeEditor() { scroll = memnew(ScrollContainer); add_child(scroll); + scroll->set_theme(Theme::get_default()); scroll->set_enable_v_scroll(true); scroll->set_enable_h_scroll(false); scroll->set_v_size_flags(SIZE_EXPAND_FILL); main_container = memnew(MarginContainer); scroll->add_child(main_container); + main_container->set_theme(Theme::get_default()); main_container->set_clip_contents(true); main_container->set_custom_minimum_size(Size2(700, 0) * EDSCALE); main_container->set_v_size_flags(SIZE_EXPAND_FILL); @@ -646,11 +648,9 @@ ThemeEditor::ThemeEditor() { Panel *panel = memnew(Panel); main_container->add_child(panel); - panel->set_theme(Theme::get_default()); MarginContainer *mc = memnew(MarginContainer); main_container->add_child(mc); - mc->set_theme(Theme::get_default()); mc->add_constant_override("margin_right", 4 * EDSCALE); mc->add_constant_override("margin_top", 4 * EDSCALE); mc->add_constant_override("margin_left", 4 * EDSCALE); @@ -879,11 +879,9 @@ ThemeEditor::ThemeEditor() { void ThemeEditorPlugin::edit(Object *p_node) { if (Object::cast_to<Theme>(p_node)) { - theme_editor->show(); theme_editor->edit(Object::cast_to<Theme>(p_node)); } else { theme_editor->edit(Ref<Theme>()); - theme_editor->hide(); } } @@ -898,11 +896,11 @@ void ThemeEditorPlugin::make_visible(bool p_visible) { theme_editor->set_process(true); button->show(); editor->make_bottom_panel_item_visible(theme_editor); - } else { theme_editor->set_process(false); if (theme_editor->is_visible_in_tree()) editor->hide_bottom_panel(); + button->hide(); } } diff --git a/editor/plugins/tile_set_editor_plugin.cpp b/editor/plugins/tile_set_editor_plugin.cpp index 21470d81ed..93c6614841 100644 --- a/editor/plugins/tile_set_editor_plugin.cpp +++ b/editor/plugins/tile_set_editor_plugin.cpp @@ -1654,7 +1654,7 @@ void TileSetEditor::_on_tool_clicked(int p_tool) { edited_collision_shape = _convex; _set_edited_shape_points(_get_collision_shape_points(concave)); } else { - // Shoudn't haphen + // Shouldn't happen } for (int i = 0; i < sd.size(); i++) { if (sd[i].get("shape") == previous_shape) { @@ -1892,7 +1892,7 @@ void TileSetEditor::_update_toggle_shape_button() { tools[SHAPE_TOGGLE_TYPE]->set_icon(get_icon("ConcavePolygonShape2D", "EditorIcons")); tools[SHAPE_TOGGLE_TYPE]->set_text("Make Concave"); } else { - // Shoudn't happen + // Shouldn't happen separator_shape_toggle->hide(); tools[SHAPE_TOGGLE_TYPE]->hide(); } diff --git a/editor/plugins/visual_shader_editor_plugin.cpp b/editor/plugins/visual_shader_editor_plugin.cpp index f3eb5d1483..2c68633a3c 100644 --- a/editor/plugins/visual_shader_editor_plugin.cpp +++ b/editor/plugins/visual_shader_editor_plugin.cpp @@ -358,7 +358,9 @@ void VisualShaderEditor::_update_graph() { for (int i = 0; i < graph->get_child_count(); i++) { if (Object::cast_to<GraphNode>(graph->get_child(i))) { - memdelete(graph->get_child(i)); + Node *node = graph->get_child(i); + graph->remove_child(node); + memdelete(node); i--; } } @@ -377,13 +379,33 @@ void VisualShaderEditor::_update_graph() { Vector<int> nodes = visual_shader->get_node_list(type); + Control *offset; + for (int n_i = 0; n_i < nodes.size(); n_i++) { Vector2 position = visual_shader->get_node_position(type, nodes[n_i]); Ref<VisualShaderNode> vsnode = visual_shader->get_node(type, nodes[n_i]); + Ref<VisualShaderNodeGroupBase> group_node = Object::cast_to<VisualShaderNodeGroupBase>(vsnode.ptr()); + bool is_group = !group_node.is_null(); + Size2 size = Size2(0, 0); + + Ref<VisualShaderNodeExpression> expression_node = Object::cast_to<VisualShaderNodeExpression>(group_node.ptr()); + bool is_expression = !expression_node.is_null(); + String expression = ""; + GraphNode *node = memnew(GraphNode); + if (is_group) { + size = group_node->get_size(); + + node->set_resizable(true); + node->connect("resize_request", this, "_node_resized", varray((int)type, nodes[n_i])); + } + if (is_expression) { + expression = expression_node->get_expression(); + } + /*if (!vsnode->is_connected("changed", this, "_node_changed")) { vsnode->connect("changed", this, "_node_changed", varray(vsnode->get_instance_id()), CONNECT_DEFERRED); }*/ @@ -403,6 +425,10 @@ void VisualShaderEditor::_update_graph() { Control *custom_editor = NULL; int port_offset = 0; + if (is_group) { + port_offset++; + } + Ref<VisualShaderNodeUniform> uniform = vsnode; if (uniform.is_valid()) { graph->add_child(node); @@ -438,6 +464,24 @@ void VisualShaderEditor::_update_graph() { custom_editor = NULL; } + if (is_group) { + HBoxContainer *hb2 = memnew(HBoxContainer); + + Button *add_input_btn = memnew(Button); + add_input_btn->set_text(TTR("Add input +")); + add_input_btn->connect("pressed", this, "_add_input_port", varray(nodes[n_i], group_node->get_free_input_port_id(), VisualShaderNode::PORT_TYPE_VECTOR, "input" + itos(group_node->get_free_input_port_id())), CONNECT_DEFERRED); + hb2->add_child(add_input_btn); + + hb2->add_spacer(); + + Button *add_output_btn = memnew(Button); + add_output_btn->set_text(TTR("Add output +")); + add_output_btn->connect("pressed", this, "_add_output_port", varray(nodes[n_i], group_node->get_free_output_port_id(), VisualShaderNode::PORT_TYPE_VECTOR, "output" + itos(group_node->get_free_output_port_id())), CONNECT_DEFERRED); + hb2->add_child(add_output_btn); + + node->add_child(hb2); + } + for (int i = 0; i < MAX(vsnode->get_input_port_count(), vsnode->get_output_port_count()); i++) { if (vsnode->is_port_separator(i)) { @@ -507,21 +551,75 @@ void VisualShaderEditor::_update_graph() { if (valid_left) { - Label *label = memnew(Label); - label->set_text(name_left); - label->add_style_override("normal", label_style); //more compact - hb->add_child(label); + if (is_group) { + + OptionButton *type_box = memnew(OptionButton); + hb->add_child(type_box); + type_box->add_item(TTR("Scalar")); + type_box->add_item(TTR("Vector")); + type_box->add_item(TTR("Boolean")); + type_box->add_item(TTR("Transform")); + type_box->select(group_node->get_input_port_type(i)); + type_box->set_custom_minimum_size(Size2(100 * EDSCALE, 0)); + type_box->connect("item_selected", this, "_change_input_port_type", varray(nodes[n_i], i), CONNECT_DEFERRED); + + LineEdit *name_box = memnew(LineEdit); + hb->add_child(name_box); + name_box->set_custom_minimum_size(Size2(60 * EDSCALE, 0)); + name_box->set_text(name_left); + name_box->set_expand_to_text_length(true); + name_box->connect("text_entered", this, "_change_input_port_name", varray(name_box, nodes[n_i], i)); + name_box->connect("focus_exited", this, "_port_name_focus_out", varray(name_box, nodes[n_i], i, false)); + + if (is_group) { + Button *remove_btn = memnew(Button); + remove_btn->set_icon(EditorNode::get_singleton()->get_gui_base()->get_icon("Remove", "EditorIcons")); + remove_btn->set_tooltip(TTR("Remove") + " " + name_left); + remove_btn->connect("pressed", this, "_remove_input_port", varray(nodes[n_i], i), CONNECT_DEFERRED); + hb->add_child(remove_btn); + } + } else { + + Label *label = memnew(Label); + label->set_text(name_left); + label->add_style_override("normal", label_style); //more compact + hb->add_child(label); + } } hb->add_spacer(); if (valid_right) { - - Label *label = memnew(Label); - label->set_text(name_right); - label->set_align(Label::ALIGN_RIGHT); - label->add_style_override("normal", label_style); //more compact - hb->add_child(label); + if (is_group) { + Button *remove_btn = memnew(Button); + remove_btn->set_icon(EditorNode::get_singleton()->get_gui_base()->get_icon("Remove", "EditorIcons")); + remove_btn->set_tooltip(TTR("Remove") + " " + name_left); + remove_btn->connect("pressed", this, "_remove_output_port", varray(nodes[n_i], i), CONNECT_DEFERRED); + hb->add_child(remove_btn); + + LineEdit *name_box = memnew(LineEdit); + hb->add_child(name_box); + name_box->set_custom_minimum_size(Size2(60 * EDSCALE, 0)); + name_box->set_text(name_right); + name_box->set_expand_to_text_length(true); + name_box->connect("text_entered", this, "_change_output_port_name", varray(name_box, nodes[n_i], i)); + name_box->connect("focus_exited", this, "_port_name_focus_out", varray(name_box, nodes[n_i], i, true)); + + OptionButton *type_box = memnew(OptionButton); + hb->add_child(type_box); + type_box->add_item(TTR("Scalar")); + type_box->add_item(TTR("Vector")); + type_box->add_item(TTR("Boolean")); + type_box->add_item(TTR("Transform")); + type_box->select(group_node->get_output_port_type(i)); + type_box->set_custom_minimum_size(Size2(100 * EDSCALE, 0)); + type_box->connect("item_selected", this, "_change_output_port_type", varray(nodes[n_i], i), CONNECT_DEFERRED); + } else { + Label *label = memnew(Label); + label->set_text(name_right); + label->add_style_override("normal", label_style); //more compact + hb->add_child(label); + } } } @@ -540,18 +638,33 @@ void VisualShaderEditor::_update_graph() { hb->add_child(preview); } + if (is_group) { + offset = memnew(Control); + offset->set_custom_minimum_size(Size2(0, 5 * EDSCALE)); + node->add_child(offset); + port_offset++; + } + node->add_child(hb); node->set_slot(i + port_offset, valid_left, port_left, type_color[port_left], valid_right, port_right, type_color[port_right]); } if (vsnode->get_output_port_for_preview() >= 0 && vsnode->get_output_port_type(vsnode->get_output_port_for_preview()) != VisualShaderNode::PORT_TYPE_TRANSFORM) { + offset = memnew(Control); + offset->set_custom_minimum_size(Size2(0, 5 * EDSCALE)); + node->add_child(offset); + VisualShaderNodePortPreview *port_preview = memnew(VisualShaderNodePortPreview); port_preview->setup(visual_shader, type, nodes[n_i], vsnode->get_output_port_for_preview()); port_preview->set_h_size_flags(SIZE_SHRINK_CENTER); node->add_child(port_preview); } + offset = memnew(Control); + offset->set_custom_minimum_size(Size2(0, 5 * EDSCALE)); + node->add_child(offset); + String error = vsnode->get_warning(visual_shader->get_mode(), type); if (error != String()) { Label *error_label = memnew(Label); @@ -560,9 +673,42 @@ void VisualShaderEditor::_update_graph() { node->add_child(error_label); } + if (is_expression) { + + TextEdit *expression_box = memnew(TextEdit); + expression_node->set_control(expression_box, 0); + node->add_child(expression_box); + + Color text_color = EDITOR_GET("text_editor/highlighting/text_color"); + Color keyword_color = EDITOR_GET("text_editor/highlighting/keyword_color"); + Color comment_color = EDITOR_GET("text_editor/highlighting/comment_color"); + Color symbol_color = EDITOR_GET("text_editor/highlighting/symbol_color"); + + expression_box->set_syntax_coloring(true); + + for (List<String>::Element *E = keyword_list.front(); E; E = E->next()) { + + expression_box->add_keyword_color(E->get(), keyword_color); + } + + expression_box->add_font_override("font", get_font("expression", "EditorFonts")); + expression_box->add_color_override("font_color", text_color); + expression_box->add_color_override("symbol_color", symbol_color); + expression_box->add_color_region("/*", "*/", comment_color, false); + expression_box->add_color_region("//", "", comment_color, false); + + expression_box->set_text(expression); + expression_box->set_context_menu_enabled(false); + expression_box->set_show_line_numbers(true); + + expression_box->connect("focus_exited", this, "_expression_focus_out", varray(expression_box, nodes[n_i])); + } + if (!uniform.is_valid()) { graph->add_child(node); _update_created_node(node); + if (is_group) + call_deferred("_set_node_size", (int)type, nodes[n_i], size); } } @@ -577,6 +723,285 @@ void VisualShaderEditor::_update_graph() { } } +void VisualShaderEditor::_add_input_port(int p_node, int p_port, int p_port_type, const String &p_name) { + + VisualShader::Type type = VisualShader::Type(edit_type->get_selected()); + Ref<VisualShaderNodeExpression> node = visual_shader->get_node(type, p_node); + if (node.is_null()) { + return; + } + + undo_redo->create_action(TTR("Add input port")); + undo_redo->add_do_method(node.ptr(), "add_input_port", p_port, p_port_type, p_name); + undo_redo->add_undo_method(node.ptr(), "remove_input_port", p_port); + undo_redo->add_do_method(this, "_update_graph"); + undo_redo->add_undo_method(this, "_update_graph"); + undo_redo->add_do_method(this, "_rebuild"); + undo_redo->add_undo_method(this, "_rebuild"); + undo_redo->commit_action(); +} + +void VisualShaderEditor::_add_output_port(int p_node, int p_port, int p_port_type, const String &p_name) { + + VisualShader::Type type = VisualShader::Type(edit_type->get_selected()); + Ref<VisualShaderNodeGroupBase> node = visual_shader->get_node(type, p_node); + if (node.is_null()) { + return; + } + + undo_redo->create_action(TTR("Add output port")); + undo_redo->add_do_method(node.ptr(), "add_output_port", p_port, p_port_type, p_name); + undo_redo->add_undo_method(node.ptr(), "remove_output_port", p_port); + undo_redo->add_do_method(this, "_update_graph"); + undo_redo->add_undo_method(this, "_update_graph"); + undo_redo->add_do_method(this, "_rebuild"); + undo_redo->add_undo_method(this, "_rebuild"); + undo_redo->commit_action(); +} + +void VisualShaderEditor::_change_input_port_type(int p_type, int p_node, int p_port) { + + VisualShader::Type type = VisualShader::Type(edit_type->get_selected()); + Ref<VisualShaderNodeGroupBase> node = visual_shader->get_node(type, p_node); + if (node.is_null()) { + return; + } + + undo_redo->create_action(TTR("Change input port type")); + undo_redo->add_do_method(node.ptr(), "set_input_port_type", p_port, p_type); + undo_redo->add_undo_method(node.ptr(), "set_input_port_type", p_port, node->get_input_port_type(p_port)); + undo_redo->add_do_method(this, "_update_graph"); + undo_redo->add_undo_method(this, "_update_graph"); + undo_redo->add_do_method(this, "_rebuild"); + undo_redo->add_undo_method(this, "_rebuild"); + undo_redo->commit_action(); +} + +void VisualShaderEditor::_change_output_port_type(int p_type, int p_node, int p_port) { + + VisualShader::Type type = VisualShader::Type(edit_type->get_selected()); + Ref<VisualShaderNodeGroupBase> node = visual_shader->get_node(type, p_node); + if (node.is_null()) { + return; + } + + undo_redo->create_action(TTR("Change output port type")); + undo_redo->add_do_method(node.ptr(), "set_output_port_type", p_port, p_type); + undo_redo->add_undo_method(node.ptr(), "set_output_port_type", p_port, node->get_output_port_type(p_port)); + undo_redo->add_do_method(this, "_update_graph"); + undo_redo->add_undo_method(this, "_update_graph"); + undo_redo->add_do_method(this, "_rebuild"); + undo_redo->add_undo_method(this, "_rebuild"); + undo_redo->commit_action(); +} + +void VisualShaderEditor::_change_input_port_name(const String &p_text, Object *line_edit, int p_node_id, int p_port_id) { + + VisualShader::Type type = VisualShader::Type(edit_type->get_selected()); + + Ref<VisualShaderNodeGroupBase> node = visual_shader->get_node(type, p_node_id); + ERR_FAIL_COND(!node.is_valid()); + + undo_redo->create_action(TTR("Change input port name")); + undo_redo->add_do_method(node.ptr(), "set_input_port_name", p_port_id, p_text); + undo_redo->add_undo_method(node.ptr(), "set_input_port_name", p_port_id, node->get_input_port_name(p_port_id)); + undo_redo->add_do_method(this, "_rebuild"); + undo_redo->add_undo_method(this, "_rebuild"); + undo_redo->commit_action(); +} + +void VisualShaderEditor::_change_output_port_name(const String &p_text, Object *line_edit, int p_node_id, int p_port_id) { + + VisualShader::Type type = VisualShader::Type(edit_type->get_selected()); + + Ref<VisualShaderNodeGroupBase> node = visual_shader->get_node(type, p_node_id); + ERR_FAIL_COND(!node.is_valid()); + + undo_redo->create_action(TTR("Change output port name")); + undo_redo->add_do_method(node.ptr(), "set_output_port_name", p_port_id, p_text); + undo_redo->add_undo_method(node.ptr(), "set_output_port_name", p_port_id, node->get_output_port_name(p_port_id)); + undo_redo->add_do_method(this, "_rebuild"); + undo_redo->add_undo_method(this, "_rebuild"); + undo_redo->commit_action(); +} + +void VisualShaderEditor::_remove_input_port(int p_node, int p_port) { + + VisualShader::Type type = VisualShader::Type(edit_type->get_selected()); + Ref<VisualShaderNodeGroupBase> node = visual_shader->get_node(type, p_node); + if (node.is_null()) { + return; + } + + undo_redo->create_action(TTR("Remove input port")); + + List<VisualShader::Connection> conns; + visual_shader->get_node_connections(type, &conns); + for (List<VisualShader::Connection>::Element *E = conns.front(); E; E = E->next()) { + + int from_node = E->get().from_node; + int from_port = E->get().from_port; + int to_node = E->get().to_node; + int to_port = E->get().to_port; + + if (to_node == p_node) { + if (to_port == p_port) { + undo_redo->add_do_method(visual_shader.ptr(), "disconnect_nodes", type, from_node, from_port, to_node, to_port); + undo_redo->add_undo_method(visual_shader.ptr(), "connect_nodes_forced", type, from_node, from_port, to_node, to_port); + } else if (to_port > p_port) { + undo_redo->add_do_method(visual_shader.ptr(), "disconnect_nodes", type, from_node, from_port, to_node, to_port); + undo_redo->add_undo_method(visual_shader.ptr(), "connect_nodes_forced", type, from_node, from_port, to_node, to_port); + + undo_redo->add_do_method(visual_shader.ptr(), "connect_nodes_forced", type, from_node, from_port, to_node, to_port - 1); + undo_redo->add_undo_method(visual_shader.ptr(), "disconnect_nodes", type, from_node, from_port, to_node, to_port - 1); + } + } + } + + undo_redo->add_do_method(node.ptr(), "remove_input_port", p_port); + undo_redo->add_undo_method(node.ptr(), "add_input_port", p_port, (int)node->get_input_port_type(p_port), node->get_input_port_name(p_port)); + + undo_redo->add_do_method(this, "_update_graph"); + undo_redo->add_undo_method(this, "_update_graph"); + + undo_redo->add_do_method(this, "_rebuild"); + undo_redo->add_undo_method(this, "_rebuild"); + + undo_redo->commit_action(); +} + +void VisualShaderEditor::_remove_output_port(int p_node, int p_port) { + + VisualShader::Type type = VisualShader::Type(edit_type->get_selected()); + Ref<VisualShaderNodeGroupBase> node = visual_shader->get_node(type, p_node); + if (node.is_null()) { + return; + } + + undo_redo->create_action(TTR("Remove output port")); + + List<VisualShader::Connection> conns; + visual_shader->get_node_connections(type, &conns); + for (List<VisualShader::Connection>::Element *E = conns.front(); E; E = E->next()) { + + int from_node = E->get().from_node; + int from_port = E->get().from_port; + int to_node = E->get().to_node; + int to_port = E->get().to_port; + + if (from_node == p_node) { + if (from_port == p_port) { + undo_redo->add_do_method(visual_shader.ptr(), "disconnect_nodes", type, from_node, from_port, to_node, to_port); + undo_redo->add_undo_method(visual_shader.ptr(), "connect_nodes_forced", type, from_node, from_port, to_node, to_port); + } else if (from_port > p_port) { + undo_redo->add_do_method(visual_shader.ptr(), "disconnect_nodes", type, from_node, from_port, to_node, to_port); + undo_redo->add_undo_method(visual_shader.ptr(), "connect_nodes_forced", type, from_node, from_port, to_node, to_port); + + undo_redo->add_do_method(visual_shader.ptr(), "connect_nodes_forced", type, from_node, from_port - 1, to_node, to_port); + undo_redo->add_undo_method(visual_shader.ptr(), "disconnect_nodes", type, from_node, from_port - 1, to_node, to_port); + } + } + } + + undo_redo->add_do_method(node.ptr(), "remove_output_port", p_port); + undo_redo->add_undo_method(node.ptr(), "add_output_port", p_port, (int)node->get_output_port_type(p_port), node->get_output_port_name(p_port)); + + undo_redo->add_do_method(this, "_update_graph"); + undo_redo->add_undo_method(this, "_update_graph"); + + undo_redo->add_do_method(this, "_rebuild"); + undo_redo->add_undo_method(this, "_rebuild"); + + undo_redo->commit_action(); +} + +void VisualShaderEditor::_expression_focus_out(Object *text_edit, int p_node) { + + VisualShader::Type type = VisualShader::Type(edit_type->get_selected()); + Ref<VisualShaderNodeExpression> node = visual_shader->get_node(type, p_node); + if (node.is_null()) { + return; + } + + TextEdit *expression_box = Object::cast_to<TextEdit>(text_edit); + + if (node->get_expression() == expression_box->get_text()) + return; + + undo_redo->create_action(TTR("Set expression")); + undo_redo->add_do_method(node.ptr(), "set_expression", expression_box->get_text()); + undo_redo->add_undo_method(node.ptr(), "set_expression", node->get_expression()); + undo_redo->add_do_method(this, "_rebuild"); + undo_redo->add_undo_method(this, "_rebuild"); + undo_redo->commit_action(); +} + +void VisualShaderEditor::_rebuild() { + EditorNode::get_singleton()->get_log()->clear(); + visual_shader->rebuild(); +} + +void VisualShaderEditor::_set_node_size(int p_type, int p_node, const Vector2 &p_size) { + + VisualShader::Type type = VisualShader::Type(p_type); + Ref<VisualShaderNode> node = visual_shader->get_node(type, p_node); + if (node.is_null()) { + return; + } + + Ref<VisualShaderNodeGroupBase> group_node = Object::cast_to<VisualShaderNodeGroupBase>(node.ptr()); + + if (group_node.is_null()) { + return; + } + + Vector2 size = p_size; + + group_node->set_size(size); + + GraphNode *gn = NULL; + if (edit_type->get_selected() == p_type) { // check - otherwise the error will be emitted + Node *node2 = graph->get_node(itos(p_node)); + gn = Object::cast_to<GraphNode>(node2); + if (!gn) + return; + + gn->set_custom_minimum_size(size); + gn->set_size(Size2(1, 1)); + } + + Ref<VisualShaderNodeExpression> expression_node = Object::cast_to<VisualShaderNodeExpression>(node.ptr()); + if (!expression_node.is_null()) { + Control *text_box = expression_node->get_control(0); + Size2 box_size = size; + if (gn != NULL) { + if (box_size.x < 150 * EDSCALE || box_size.y < 0) { + box_size.x = gn->get_size().x; + } + } + box_size.x -= text_box->get_margin(MARGIN_LEFT); + box_size.x -= 28 * EDSCALE; + box_size.y -= text_box->get_margin(MARGIN_TOP); + box_size.y -= 28 * EDSCALE; + text_box->set_custom_minimum_size(Size2(box_size.x, box_size.y)); + text_box->set_size(Size2(1, 1)); + } +} + +void VisualShaderEditor::_node_resized(const Vector2 &p_new_size, int p_type, int p_node) { + + VisualShader::Type type = VisualShader::Type(p_type); + Ref<VisualShaderNodeGroupBase> node = visual_shader->get_node(type, p_node); + if (node.is_null()) { + return; + } + + undo_redo->create_action(TTR("Resize VisualShader node"), UndoRedo::MERGE_ENDS); + undo_redo->add_do_method(this, "_set_node_size", p_type, p_node, p_new_size / EDSCALE); + undo_redo->add_undo_method(this, "_set_node_size", p_type, p_node, node->get_size()); + undo_redo->commit_action(); +} + void VisualShaderEditor::_preview_select_port(int p_node, int p_port) { VisualShader::Type type = VisualShader::Type(edit_type->get_selected()); @@ -623,6 +1048,52 @@ void VisualShaderEditor::_line_edit_focus_out(Object *line_edit, int p_node_id) _line_edit_changed(text, line_edit, p_node_id); } +void VisualShaderEditor::_port_name_focus_out(Object *line_edit, int p_node_id, int p_port_id, bool p_output) { + + VisualShader::Type type = VisualShader::Type(edit_type->get_selected()); + + Ref<VisualShaderNodeGroupBase> node = visual_shader->get_node(type, p_node_id); + ERR_FAIL_COND(!node.is_valid()); + + String text = Object::cast_to<LineEdit>(line_edit)->get_text(); + + if (!p_output) { + if (node->get_input_port_name(p_port_id) == text) + return; + } else { + if (node->get_output_port_name(p_port_id) == text) + return; + } + + List<String> input_names; + List<String> output_names; + + for (int i = 0; i < node->get_input_port_count(); i++) { + if (!p_output && i == p_port_id) continue; + input_names.push_back(node->get_input_port_name(i)); + } + for (int i = 0; i < node->get_output_port_count(); i++) { + if (p_output && i == p_port_id) continue; + output_names.push_back(node->get_output_port_name(i)); + } + + String validated_name = visual_shader->validate_port_name(text, input_names, output_names); + if (validated_name == "") { + if (!p_output) { + Object::cast_to<LineEdit>(line_edit)->set_text(node->get_input_port_name(p_port_id)); + } else { + Object::cast_to<LineEdit>(line_edit)->set_text(node->get_output_port_name(p_port_id)); + } + return; + } + + if (!p_output) { + _change_input_port_name(validated_name, line_edit, p_node_id, p_port_id); + } else { + _change_output_port_name(validated_name, line_edit, p_node_id, p_port_id); + } +} + void VisualShaderEditor::_port_edited() { VisualShader::Type type = VisualShader::Type(edit_type->get_selected()); @@ -757,6 +1228,12 @@ void VisualShaderEditor::_add_node(int p_idx, int p_op_idx) { undo_redo->create_action(TTR("Add Node to Visual Shader")); undo_redo->add_do_method(visual_shader.ptr(), "add_node", type, vsnode, position, id_to_use); undo_redo->add_undo_method(visual_shader.ptr(), "remove_node", type, id_to_use); + + VisualShaderNodeExpression *expr = Object::cast_to<VisualShaderNodeExpression>(vsnode.ptr()); + if (expr) { + undo_redo->add_do_method(expr, "set_size", Size2(250 * EDSCALE, 150 * EDSCALE)); + } + undo_redo->add_do_method(this, "_update_graph"); undo_redo->add_undo_method(this, "_update_graph"); undo_redo->commit_action(); @@ -831,10 +1308,25 @@ void VisualShaderEditor::_connection_to_empty(const String &p_from, int p_from_s void VisualShaderEditor::_delete_request(int which) { VisualShader::Type type = VisualShader::Type(edit_type->get_selected()); + Ref<VisualShaderNode> node = Ref<VisualShaderNode>(visual_shader->get_node(type, which)); undo_redo->create_action(TTR("Delete Node")); undo_redo->add_do_method(visual_shader.ptr(), "remove_node", type, which); - undo_redo->add_undo_method(visual_shader.ptr(), "add_node", type, visual_shader->get_node(type, which), visual_shader->get_node_position(type, which), which); + undo_redo->add_undo_method(visual_shader.ptr(), "add_node", type, node, visual_shader->get_node_position(type, which), which); + + // restore size, inputs and outputs if node is group + VisualShaderNodeGroupBase *group = Object::cast_to<VisualShaderNodeGroupBase>(node.ptr()); + if (group) { + undo_redo->add_undo_method(group, "set_size", group->get_size()); + undo_redo->add_undo_method(group, "set_inputs", group->get_inputs()); + undo_redo->add_undo_method(group, "set_outputs", group->get_outputs()); + } + + // restore expression text if node is expression + VisualShaderNodeExpression *expression = Object::cast_to<VisualShaderNodeExpression>(node.ptr()); + if (expression) { + undo_redo->add_undo_method(expression, "set_expression", expression->get_expression()); + } List<VisualShader::Connection> conns; visual_shader->get_node_connections(type, &conns); @@ -1022,6 +1514,19 @@ void VisualShaderEditor::_duplicate_nodes() { undo_redo->add_do_method(visual_shader.ptr(), "add_node", type, dupli, visual_shader->get_node_position(type, E->get()) + Vector2(10, 10) * EDSCALE, id_from); undo_redo->add_undo_method(visual_shader.ptr(), "remove_node", type, id_from); + // duplicate size, inputs and outputs if node is group + Ref<VisualShaderNodeGroupBase> group = Object::cast_to<VisualShaderNodeGroupBase>(node.ptr()); + if (!group.is_null()) { + undo_redo->add_do_method(dupli.ptr(), "set_size", group->get_size()); + undo_redo->add_do_method(dupli.ptr(), "set_inputs", group->get_inputs()); + undo_redo->add_do_method(dupli.ptr(), "set_outputs", group->get_outputs()); + } + // duplicate expression text if node is expression + Ref<VisualShaderNodeExpression> expression = Object::cast_to<VisualShaderNodeExpression>(node.ptr()); + if (!expression.is_null()) { + undo_redo->add_do_method(dupli.ptr(), "set_expression", expression->get_expression()); + } + id_from++; } @@ -1030,7 +1535,7 @@ void VisualShaderEditor::_duplicate_nodes() { for (List<VisualShader::Connection>::Element *E = conns.front(); E; E = E->next()) { if (connection_remap.has(E->get().from_node) && connection_remap.has(E->get().to_node)) { - undo_redo->add_do_method(visual_shader.ptr(), "connect_nodes", type, connection_remap[E->get().from_node], E->get().from_port, connection_remap[E->get().to_node], E->get().to_port); + undo_redo->add_do_method(visual_shader.ptr(), "connect_nodes_forced", type, connection_remap[E->get().from_node], E->get().from_port, connection_remap[E->get().to_node], E->get().to_port); } } @@ -1073,8 +1578,25 @@ void VisualShaderEditor::_on_nodes_delete() { undo_redo->create_action(TTR("Delete Nodes")); for (List<int>::Element *F = to_erase.front(); F; F = F->next()) { + + Ref<VisualShaderNode> node = visual_shader->get_node(type, F->get()); + undo_redo->add_do_method(visual_shader.ptr(), "remove_node", type, F->get()); - undo_redo->add_undo_method(visual_shader.ptr(), "add_node", type, visual_shader->get_node(type, F->get()), visual_shader->get_node_position(type, F->get()), F->get()); + undo_redo->add_undo_method(visual_shader.ptr(), "add_node", type, node, visual_shader->get_node_position(type, F->get()), F->get()); + + // restore size, inputs and outputs if node is group + VisualShaderNodeGroupBase *group = Object::cast_to<VisualShaderNodeGroupBase>(node.ptr()); + if (group) { + undo_redo->add_undo_method(group, "set_size", group->get_size()); + undo_redo->add_undo_method(group, "set_inputs", group->get_inputs()); + undo_redo->add_undo_method(group, "set_outputs", group->get_outputs()); + } + + // restore expression text if node is expression + VisualShaderNodeExpression *expression = Object::cast_to<VisualShaderNodeExpression>(node.ptr()); + if (expression) { + undo_redo->add_undo_method(expression, "set_expression", expression->get_expression()); + } } List<VisualShader::Connection> conns; @@ -1267,8 +1789,10 @@ void VisualShaderEditor::drop_data_fw(const Point2 &p_point, const Variant &p_da } void VisualShaderEditor::_bind_methods() { + ClassDB::bind_method("_rebuild", &VisualShaderEditor::_rebuild); ClassDB::bind_method("_update_graph", &VisualShaderEditor::_update_graph); ClassDB::bind_method("_update_options_menu", &VisualShaderEditor::_update_options_menu); + ClassDB::bind_method("_expression_focus_out", &VisualShaderEditor::_expression_focus_out); ClassDB::bind_method("_add_node", &VisualShaderEditor::_add_node); ClassDB::bind_method("_node_dragged", &VisualShaderEditor::_node_dragged); ClassDB::bind_method("_connection_request", &VisualShaderEditor::_connection_request); @@ -1283,11 +1807,22 @@ void VisualShaderEditor::_bind_methods() { ClassDB::bind_method("_connection_to_empty", &VisualShaderEditor::_connection_to_empty); ClassDB::bind_method("_line_edit_focus_out", &VisualShaderEditor::_line_edit_focus_out); ClassDB::bind_method("_line_edit_changed", &VisualShaderEditor::_line_edit_changed); + ClassDB::bind_method("_port_name_focus_out", &VisualShaderEditor::_port_name_focus_out); ClassDB::bind_method("_duplicate_nodes", &VisualShaderEditor::_duplicate_nodes); ClassDB::bind_method("_mode_selected", &VisualShaderEditor::_mode_selected); ClassDB::bind_method("_input_select_item", &VisualShaderEditor::_input_select_item); ClassDB::bind_method("_preview_select_port", &VisualShaderEditor::_preview_select_port); ClassDB::bind_method("_graph_gui_input", &VisualShaderEditor::_graph_gui_input); + ClassDB::bind_method("_add_input_port", &VisualShaderEditor::_add_input_port); + ClassDB::bind_method("_change_input_port_type", &VisualShaderEditor::_change_input_port_type); + ClassDB::bind_method("_change_input_port_name", &VisualShaderEditor::_change_input_port_name); + ClassDB::bind_method("_remove_input_port", &VisualShaderEditor::_remove_input_port); + ClassDB::bind_method("_add_output_port", &VisualShaderEditor::_add_output_port); + ClassDB::bind_method("_change_output_port_type", &VisualShaderEditor::_change_output_port_type); + ClassDB::bind_method("_change_output_port_name", &VisualShaderEditor::_change_output_port_name); + ClassDB::bind_method("_remove_output_port", &VisualShaderEditor::_remove_output_port); + ClassDB::bind_method("_node_resized", &VisualShaderEditor::_node_resized); + ClassDB::bind_method("_set_node_size", &VisualShaderEditor::_set_node_size); ClassDB::bind_method(D_METHOD("get_drag_data_fw"), &VisualShaderEditor::get_drag_data_fw); ClassDB::bind_method(D_METHOD("can_drop_data_fw"), &VisualShaderEditor::can_drop_data_fw); @@ -1311,6 +1846,7 @@ VisualShaderEditor::VisualShaderEditor() { updating = false; saved_node_pos_dirty = false; saved_node_pos = Point2(0, 0); + ShaderLanguage::get_keyword_list(&keyword_list); graph = memnew(GraphEdit); add_child(graph); @@ -1588,6 +2124,7 @@ VisualShaderEditor::VisualShaderEditor() { add_options.push_back(AddOption("Min", "Scalar", "Functions", "VisualShaderNodeScalarOp", TTR("Returns the lesser of two values."), VisualShaderNodeScalarOp::OP_MIN, VisualShaderNode::PORT_TYPE_SCALAR)); add_options.push_back(AddOption("Mix", "Scalar", "Functions", "VisualShaderNodeScalarInterp", TTR("Linear interpolation between two scalars."), -1, VisualShaderNode::PORT_TYPE_SCALAR)); add_options.push_back(AddOption("Negate", "Scalar", "Functions", "VisualShaderNodeScalarFunc", TTR("Returns the opposite value of the parameter."), VisualShaderNodeScalarFunc::FUNC_NEGATE, VisualShaderNode::PORT_TYPE_SCALAR)); + add_options.push_back(AddOption("OneMinus", "Scalar", "Functions", "VisualShaderNodeScalarFunc", TTR("1.0 - scalar"), VisualShaderNodeScalarFunc::FUNC_ONEMINUS, VisualShaderNode::PORT_TYPE_SCALAR)); add_options.push_back(AddOption("Pow", "Scalar", "Functions", "VisualShaderNodeScalarOp", TTR("Returns the value of the first parameter raised to the power of the second."), VisualShaderNodeScalarOp::OP_POW, VisualShaderNode::PORT_TYPE_SCALAR)); add_options.push_back(AddOption("Radians", "Scalar", "Functions", "VisualShaderNodeScalarFunc", TTR("Converts a quantity in degrees to radians."), VisualShaderNodeScalarFunc::FUNC_RADIANS, VisualShaderNode::PORT_TYPE_SCALAR)); add_options.push_back(AddOption("Reciprocal", "Scalar", "Functions", "VisualShaderNodeScalarFunc", TTR("1.0 / scalar"), VisualShaderNodeScalarFunc::FUNC_RECIPROCAL, VisualShaderNode::PORT_TYPE_SCALAR)); @@ -1677,6 +2214,7 @@ VisualShaderEditor::VisualShaderEditor() { add_options.push_back(AddOption("Mix", "Vector", "Functions", "VisualShaderNodeVectorInterp", TTR("Linear interpolation between two vectors."), -1, VisualShaderNode::PORT_TYPE_VECTOR)); add_options.push_back(AddOption("Negate", "Vector", "Functions", "VisualShaderNodeVectorFunc", TTR("Returns the opposite value of the parameter."), VisualShaderNodeVectorFunc::FUNC_NEGATE, VisualShaderNode::PORT_TYPE_VECTOR)); add_options.push_back(AddOption("Normalize", "Vector", "Functions", "VisualShaderNodeVectorFunc", TTR("Calculates the normalize product of vector."), VisualShaderNodeVectorFunc::FUNC_NORMALIZE, VisualShaderNode::PORT_TYPE_VECTOR)); + add_options.push_back(AddOption("OneMinus", "Vector", "Functions", "VisualShaderNodeVectorFunc", TTR("1.0 - vector"), VisualShaderNodeVectorFunc::FUNC_ONEMINUS, VisualShaderNode::PORT_TYPE_VECTOR)); add_options.push_back(AddOption("Pow", "Vector", "Functions", "VisualShaderNodeVectorOp", TTR("Returns the value of the first parameter raised to the power of the second."), VisualShaderNodeVectorOp::OP_POW, VisualShaderNode::PORT_TYPE_VECTOR)); add_options.push_back(AddOption("Radians", "Vector", "Functions", "VisualShaderNodeVectorFunc", TTR("Converts a quantity in degrees to radians."), VisualShaderNodeVectorFunc::FUNC_RADIANS, VisualShaderNode::PORT_TYPE_VECTOR)); add_options.push_back(AddOption("Reciprocal", "Vector", "Functions", "VisualShaderNodeVectorFunc", TTR("1.0 / vector"), VisualShaderNodeVectorFunc::FUNC_RECIPROCAL, VisualShaderNode::PORT_TYPE_VECTOR)); @@ -1708,6 +2246,9 @@ VisualShaderEditor::VisualShaderEditor() { // SPECIAL + add_options.push_back(AddOption("Expression", "Special", "", "VisualShaderNodeExpression", TTR("Custom Godot Shader Language expression, with custom amount of input and output ports. This is a direct injection of code into the vertex/fragment/light function, do not use it to write the function declarations inside."))); + add_options.push_back(AddOption("Fresnel", "Special", "", "VisualShaderNodeFresnel", TTR("Returns falloff based on the dot product of surface normal and view direction of camera (pass associated inputs to it)."), -1, VisualShaderNode::PORT_TYPE_SCALAR)); + add_options.push_back(AddOption("ScalarDerivativeFunc", "Special", "Common", "VisualShaderNodeScalarDerivativeFunc", TTR("(GLES3 only) (Fragment/Light mode only) Scalar derivative function."), -1, VisualShaderNode::PORT_TYPE_SCALAR, VisualShader::TYPE_FRAGMENT | VisualShader::TYPE_LIGHT)); add_options.push_back(AddOption("VectorDerivativeFunc", "Special", "Common", "VisualShaderNodeVectorDerivativeFunc", TTR("(GLES3 only) (Fragment/Light mode only) Vector derivative function."), -1, VisualShaderNode::PORT_TYPE_VECTOR, VisualShader::TYPE_FRAGMENT | VisualShader::TYPE_LIGHT)); diff --git a/editor/plugins/visual_shader_editor_plugin.h b/editor/plugins/visual_shader_editor_plugin.h index eb0dee7594..e851030ab4 100644 --- a/editor/plugins/visual_shader_editor_plugin.h +++ b/editor/plugins/visual_shader_editor_plugin.h @@ -128,6 +128,7 @@ class VisualShaderEditor : public VBoxContainer { }; Vector<AddOption> add_options; + List<String> keyword_list; void _draw_color_over_button(Object *obj, Color p_color); @@ -160,14 +161,32 @@ class VisualShaderEditor : public VBoxContainer { void _line_edit_changed(const String &p_text, Object *line_edit, int p_node_id); void _line_edit_focus_out(Object *line_edit, int p_node_id); + void _port_name_focus_out(Object *line_edit, int p_node_id, int p_port_id, bool p_output); + void _duplicate_nodes(); Vector<Ref<VisualShaderNodePlugin> > plugins; void _mode_selected(int p_id); + void _rebuild(); void _input_select_item(Ref<VisualShaderNodeInput> input, String name); + void _add_input_port(int p_node, int p_port, int p_type, const String &p_name); + void _remove_input_port(int p_node, int p_port); + void _change_input_port_type(int p_type, int p_node, int p_port); + void _change_input_port_name(const String &p_text, Object *line_edit, int p_node, int p_port); + + void _add_output_port(int p_node, int p_port, int p_type, const String &p_name); + void _remove_output_port(int p_node, int p_port); + void _change_output_port_type(int p_type, int p_node, int p_port); + void _change_output_port_name(const String &p_text, Object *line_edit, int p_node, int p_port); + + void _expression_focus_out(Object *text_edit, int p_node); + + void _set_node_size(int p_type, int p_node, const Size2 &p_size); + void _node_resized(const Vector2 &p_new_size, int p_type, int p_node); + void _preview_select_port(int p_node, int p_port); void _graph_gui_input(const Ref<InputEvent> p_event); diff --git a/editor/project_export.cpp b/editor/project_export.cpp index e1950c666c..cc110f309c 100644 --- a/editor/project_export.cpp +++ b/editor/project_export.cpp @@ -571,9 +571,8 @@ void ProjectExportDialog::_duplicate_preset() { Ref<EditorExportPreset> preset = current->get_platform()->create_preset(); ERR_FAIL_COND(!preset.is_valid()); - String name = current->get_name() + "" + itos(1); + String name = current->get_name() + " (copy)"; bool make_runnable = true; - int attempt = 2; while (true) { bool valid = true; @@ -592,8 +591,7 @@ void ProjectExportDialog::_duplicate_preset() { if (valid) break; - attempt++; - name = current->get_name() + " " + itos(attempt); + name += " (copy)"; } preset->set_name(name); diff --git a/editor/scene_tree_editor.cpp b/editor/scene_tree_editor.cpp index 62845bfb9b..e3ad740005 100644 --- a/editor/scene_tree_editor.cpp +++ b/editor/scene_tree_editor.cpp @@ -49,7 +49,7 @@ Node *SceneTreeEditor::get_scene_node() { void SceneTreeEditor::_cell_button_pressed(Object *p_item, int p_column, int p_id) { if (connect_to_script_mode) { - return; //dont do anything in this mode + return; //don't do anything in this mode } TreeItem *item = Object::cast_to<TreeItem>(p_item); ERR_FAIL_COND(!item); @@ -471,6 +471,17 @@ void SceneTreeEditor::_node_removed(Node *p_node) { emit_signal("node_selected"); } } + +void SceneTreeEditor::_node_renamed(Node *p_node) { + + emit_signal("node_renamed"); + + if (!tree_dirty) { + MessageQueue::get_singleton()->push_call(this, "_update_tree"); + tree_dirty = true; + } +} + void SceneTreeEditor::_update_tree() { if (!is_inside_tree()) { @@ -594,6 +605,7 @@ void SceneTreeEditor::_notification(int p_what) { get_tree()->connect("tree_changed", this, "_tree_changed"); get_tree()->connect("node_removed", this, "_node_removed"); + get_tree()->connect("node_renamed", this, "_node_renamed"); get_tree()->connect("node_configuration_warning_changed", this, "_warning_changed"); tree->connect("item_collapsed", this, "_cell_collapsed"); @@ -604,6 +616,7 @@ void SceneTreeEditor::_notification(int p_what) { get_tree()->disconnect("tree_changed", this, "_tree_changed"); get_tree()->disconnect("node_removed", this, "_node_removed"); + get_tree()->disconnect("node_renamed", this, "_node_renamed"); tree->disconnect("item_collapsed", this, "_cell_collapsed"); get_tree()->disconnect("node_configuration_warning_changed", this, "_warning_changed"); } break; @@ -685,12 +698,6 @@ void SceneTreeEditor::_rename_node(ObjectID p_node, const String &p_name) { n->set_name(p_name); item->set_metadata(0, n->get_path()); item->set_text(0, p_name); - emit_signal("node_renamed"); - - if (!tree_dirty) { - MessageQueue::get_singleton()->push_call(this, "_update_tree"); - tree_dirty = true; - } } void SceneTreeEditor::_renamed() { @@ -1025,6 +1032,7 @@ void SceneTreeEditor::_bind_methods() { ClassDB::bind_method("_tree_changed", &SceneTreeEditor::_tree_changed); ClassDB::bind_method("_update_tree", &SceneTreeEditor::_update_tree); ClassDB::bind_method("_node_removed", &SceneTreeEditor::_node_removed); + ClassDB::bind_method("_node_renamed", &SceneTreeEditor::_node_renamed); ClassDB::bind_method("_selected_changed", &SceneTreeEditor::_selected_changed); ClassDB::bind_method("_deselect_items", &SceneTreeEditor::_deselect_items); ClassDB::bind_method("_renamed", &SceneTreeEditor::_renamed); diff --git a/editor/scene_tree_editor.h b/editor/scene_tree_editor.h index 9158c4aa48..1c14da0d3a 100644 --- a/editor/scene_tree_editor.h +++ b/editor/scene_tree_editor.h @@ -78,6 +78,7 @@ class SceneTreeEditor : public Control { void _update_tree(); void _tree_changed(); void _node_removed(Node *p_node); + void _node_renamed(Node *p_node); TreeItem *_find(TreeItem *p_node, const NodePath &p_path); void _notification(int p_what); diff --git a/editor/translations/af.po b/editor/translations/af.po index 795044c0cd..5bc804cfcd 100644 --- a/editor/translations/af.po +++ b/editor/translations/af.po @@ -163,16 +163,21 @@ msgstr "" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "Anim Voeg Baan By" +msgid "Animation length (frames)" +msgstr "Animasie lengte (in sekondes)." #: editor/animation_track_editor.cpp #, fuzzy -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "Animasie lengte (in sekondes)." #: editor/animation_track_editor.cpp #, fuzzy +msgid "Add Track" +msgstr "Anim Voeg Baan By" + +#: editor/animation_track_editor.cpp +#, fuzzy msgid "Animation Looping" msgstr "Animasie Zoem." diff --git a/editor/translations/ar.po b/editor/translations/ar.po index 50efabd7f5..1c5fb54fdf 100644 --- a/editor/translations/ar.po +++ b/editor/translations/ar.po @@ -24,12 +24,13 @@ # Mohammad Fares <mhdchehade@gmail.com>, 2018. # NewFriskFan26 <newfriskfan26@gmail.com>, 2019. # spiderx0x <legendofdarks@gmail.com>, 2019. +# Ibraheem Tawfik <tawfikibraheem@gmail.com>, 2019. msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-04-17 10:02+0000\n" -"Last-Translator: Omar Aglan <omar.aglan91@yahoo.com>\n" +"PO-Revision-Date: 2019-04-29 08:48+0000\n" +"Last-Translator: Ibraheem Tawfik <tawfikibraheem@gmail.com>\n" "Language-Team: Arabic <https://hosted.weblate.org/projects/godot-engine/" "godot/ar/>\n" "Language: ar\n" @@ -38,7 +39,7 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=6; plural=n==0 ? 0 : n==1 ? 1 : n==2 ? 2 : n%100>=3 " "&& n%100<=10 ? 3 : n%100>=11 ? 4 : 5;\n" -"X-Generator: Weblate 3.6-dev\n" +"X-Generator: Weblate 3.6.1\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -174,14 +175,20 @@ msgid "Animation Playback Track" msgstr "شريط ضبط الØركة" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "إضاÙØ© مسار" +#, fuzzy +msgid "Animation length (frames)" +msgstr "مدة الØركة (بالثواني)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "مدة الØركة (بالثواني)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "إضاÙØ© مسار" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "تكرار الØركة" @@ -358,8 +365,9 @@ msgstr "" "-الصوت الجاري للأعب ثلاثي الأبعاد" #: editor/animation_track_editor.cpp +#, fuzzy msgid "Animation tracks can only point to AnimationPlayer nodes." -msgstr "" +msgstr "مسارات الØركة يمكنها Ùقط أن تشير إلى عقدة مشغّل الØركة AnimationPlayer" #: editor/animation_track_editor.cpp msgid "An animation player can't animate itself, only other players." @@ -442,11 +450,11 @@ msgstr "قيمة خطوة الØركة." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "ثواني" #: editor/animation_track_editor.cpp msgid "FPS" -msgstr "" +msgstr "إطار خلال ثانية" #: editor/animation_track_editor.cpp editor/editor_properties.cpp #: editor/plugins/polygon_2d_editor_plugin.cpp @@ -1417,7 +1425,7 @@ msgstr "مل٠النموذج غير موجود:" #: platform/iphone/export/export.cpp platform/javascript/export/export.cpp #: platform/osx/export/export.cpp platform/uwp/export/export.cpp msgid "Custom release template not found." -msgstr "" +msgstr "قالب الإصدار المخصص ليس موجود" #: editor/editor_export.cpp platform/javascript/export/export.cpp msgid "Template file not found:" @@ -1531,14 +1539,13 @@ msgid "Move Favorite Down" msgstr "Øرك المÙÙضلة للأسÙÙ„" #: editor/editor_file_dialog.cpp -#, fuzzy msgid "Previous Folder" -msgstr "التبويب السابق" +msgstr "المجلد السابق" #: editor/editor_file_dialog.cpp #, fuzzy msgid "Next Folder" -msgstr "أنشئ مجلد" +msgstr "المجلد اللاØÙ‚" #: editor/editor_file_dialog.cpp msgid "Go to parent folder" @@ -1610,7 +1617,7 @@ msgstr "خصائص" #: editor/editor_help.cpp msgid "Properties:" -msgstr "" +msgstr "خصائص:" #: editor/editor_help.cpp msgid "Methods" @@ -1624,7 +1631,7 @@ msgstr "قائمة الطرق" #: editor/editor_help.cpp #, fuzzy msgid "Theme Properties" -msgstr "خصائص" +msgstr "خصائص النمط" #: editor/editor_help.cpp #, fuzzy @@ -1656,14 +1663,12 @@ msgid "Constants:" msgstr "الثوابت:" #: editor/editor_help.cpp -#, fuzzy msgid "Class Description" -msgstr "الوصÙ" +msgstr "وص٠الصÙ" #: editor/editor_help.cpp -#, fuzzy msgid "Class Description:" -msgstr "الوصÙ:" +msgstr "وص٠الصÙ:" #: editor/editor_help.cpp msgid "Online Tutorials:" @@ -1721,34 +1726,28 @@ msgid "Search Help" msgstr "إبØØ« ÙÙŠ المساعدة" #: editor/editor_help_search.cpp -#, fuzzy msgid "Display All" -msgstr "إستبدال الكل" +msgstr "إظهار الكل" #: editor/editor_help_search.cpp -#, fuzzy msgid "Classes Only" -msgstr "الÙئات" +msgstr "الصÙÙˆÙ Ùقط" #: editor/editor_help_search.cpp -#, fuzzy msgid "Methods Only" -msgstr "قائمة الطرق" +msgstr "الطرق Ùقط" #: editor/editor_help_search.cpp -#, fuzzy msgid "Signals Only" -msgstr "إشارات" +msgstr "إشارات Ùقط" #: editor/editor_help_search.cpp -#, fuzzy msgid "Constants Only" -msgstr "الثوابت" +msgstr "ثوابت Ùقط" #: editor/editor_help_search.cpp -#, fuzzy msgid "Properties Only" -msgstr "خصائص" +msgstr "خصائص Ùقط" #: editor/editor_help_search.cpp #, fuzzy @@ -1756,9 +1755,8 @@ msgid "Theme Properties Only" msgstr "خصائص" #: editor/editor_help_search.cpp -#, fuzzy msgid "Member Type" -msgstr "الأعضاء" +msgstr "نوع العضو" #: editor/editor_help_search.cpp #, fuzzy @@ -1767,11 +1765,11 @@ msgstr "صنÙ:" #: editor/editor_inspector.cpp editor/project_settings_editor.cpp msgid "Property:" -msgstr "" +msgstr "خصيصة:" #: editor/editor_inspector.cpp msgid "Set" -msgstr "" +msgstr "مجموعة" #: editor/editor_inspector.cpp msgid "Set Multiple:" @@ -1806,7 +1804,7 @@ msgstr "" #: editor/editor_node.cpp editor/plugins/script_editor_plugin.cpp #: scene/gui/dialogs.cpp msgid "OK" -msgstr "" +msgstr "Øسنا" #: editor/editor_node.cpp editor/plugins/animation_player_editor_plugin.cpp msgid "Error saving resource!" diff --git a/editor/translations/bg.po b/editor/translations/bg.po index fb81a1793a..e62de9bb28 100644 --- a/editor/translations/bg.po +++ b/editor/translations/bg.po @@ -165,12 +165,18 @@ msgstr "" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "ДобавÑне на нови пътечки." +msgid "Animation length (frames)" +msgstr "Ðово Име на ÐнимациÑ:" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" -msgstr "" +#, fuzzy +msgid "Animation length (seconds)" +msgstr "Промени Името на ÐнимациÑта:" + +#: editor/animation_track_editor.cpp +#, fuzzy +msgid "Add Track" +msgstr "ДобавÑне на нови пътечки." #: editor/animation_track_editor.cpp #, fuzzy diff --git a/editor/translations/bn.po b/editor/translations/bn.po index 4b7dd76be6..3ff5ddaf1c 100644 --- a/editor/translations/bn.po +++ b/editor/translations/bn.po @@ -172,16 +172,21 @@ msgstr "অà§à¦¯à¦¾à¦¨à¦¿à¦®à§‡à¦¶à¦¨à§‡à¦° চালনা বনà§à¦§ কর #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "অà§à¦¯à¦¾à¦¨à¦¿à¦®à§‡à¦¶à¦¨ (Anim) টà§à¦°à§à¦¯à¦¾à¦• যোগ করà§à¦¨" +msgid "Animation length (frames)" +msgstr "অà§à¦¯à¦¾à¦¨à¦¿à¦®à§‡à¦¶à¦¨à§‡à¦° (Animation) দৈরà§à¦˜à§à¦¯ (সময় সেকেনà§à¦¡à§‡)।" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "অà§à¦¯à¦¾à¦¨à¦¿à¦®à§‡à¦¶à¦¨à§‡à¦° (Animation) দৈরà§à¦˜à§à¦¯ (সময় সেকেনà§à¦¡à§‡)।" #: editor/animation_track_editor.cpp #, fuzzy +msgid "Add Track" +msgstr "অà§à¦¯à¦¾à¦¨à¦¿à¦®à§‡à¦¶à¦¨ (Anim) টà§à¦°à§à¦¯à¦¾à¦• যোগ করà§à¦¨" + +#: editor/animation_track_editor.cpp +#, fuzzy msgid "Animation Looping" msgstr "অà§à¦¯à¦¾à¦¨à¦¿à¦®à§‡à¦¶à¦¨ (Animation) জà§à¦® (zoom) করà§à¦¨à¥¤" diff --git a/editor/translations/ca.po b/editor/translations/ca.po index cd87bb8a46..20d9da2ae1 100644 --- a/editor/translations/ca.po +++ b/editor/translations/ca.po @@ -7,11 +7,12 @@ # Roger Blanco Ribera <roger.blancoribera@gmail.com>, 2016-2018. # Rubén Moreno <ruben.moreno.romero@gmail.com>, 2018. # roger <616steam@gmail.com>, 2019. +# Roger BR <drai_kin@hotmail.com>, 2019. msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-04-19 16:33+0000\n" +"PO-Revision-Date: 2019-05-19 07:48+0000\n" "Last-Translator: roger <616steam@gmail.com>\n" "Language-Team: Catalan <https://hosted.weblate.org/projects/godot-engine/" "godot/ca/>\n" @@ -20,7 +21,7 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=n != 1;\n" -"X-Generator: Weblate 3.6-dev\n" +"X-Generator: Weblate 3.7-dev\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -91,9 +92,8 @@ msgid "Add Bezier Point" msgstr "Afegir punt Bezier" #: editor/animation_bezier_editor.cpp -#, fuzzy msgid "Move Bezier Points" -msgstr "Mou el Punt" +msgstr "Moure Punts Bezier" #: editor/animation_bezier_editor.cpp editor/animation_track_editor.cpp msgid "Anim Duplicate Keys" @@ -121,12 +121,11 @@ msgstr "Modifica el valor de la clau" #: editor/animation_track_editor.cpp msgid "Anim Change Call" -msgstr "Modifica la Crida" +msgstr "Canviar crida d'animació" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Change Animation Length" -msgstr "Modifica el bucle d'Animació" +msgstr "Canviar la durada de l'Animació" #: editor/animation_track_editor.cpp #: editor/plugins/sprite_frames_editor_plugin.cpp @@ -158,14 +157,20 @@ msgid "Animation Playback Track" msgstr "Pista de reproducció d'Animacions" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Afegeix una Pista" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Durada de l'Animació (en segons)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Durada de l'Animació (en segons)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Afegeix una Pista" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Bucle de l'Animació" @@ -183,9 +188,8 @@ msgid "Anim Clips:" msgstr "Talls d'Animació:" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Change Track Path" -msgstr "Modifica el Valor de la Taula" +msgstr "Canviar el camà de la pista" #: editor/animation_track_editor.cpp msgid "Toggle this track on/off." @@ -212,9 +216,8 @@ msgid "Time (s): " msgstr "Temps (s): " #: editor/animation_track_editor.cpp -#, fuzzy msgid "Toggle Track Enabled" -msgstr "Activa Doppler" +msgstr "Pista de commutació activada" #: editor/animation_track_editor.cpp msgid "Continuous" @@ -267,19 +270,16 @@ msgid "Delete Key(s)" msgstr "Elimina les Claus" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Change Animation Update Mode" -msgstr "Modifica el Nom de l'Animació:" +msgstr "Canviar el Mode d'Actualització de l'Animació" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Change Animation Interpolation Mode" -msgstr "Mode d'Interpolació" +msgstr "Canviar Mode d'Interpolació de l'Animació" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Change Animation Loop Mode" -msgstr "Modifica el bucle d'Animació" +msgstr "Canviar Mode de bucle d'Animació" #: editor/animation_track_editor.cpp msgid "Remove Anim Track" @@ -364,9 +364,8 @@ msgid "Not possible to add a new track without a root" msgstr "No es pot afegir una nova pista sense cap arrel" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Add Bezier Track" -msgstr "Afegeix una Pista" +msgstr "Afegir Pista Bezier" #: editor/animation_track_editor.cpp msgid "Track path is invalid, so can't add a key." @@ -377,9 +376,8 @@ msgid "Track is not of type Spatial, can't insert key" msgstr "No s'hi pot inserir cap Clau. La pista no és del tipus \"Spatial\"" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Add Transform Track Key" -msgstr "Pista de Transformació 3D" +msgstr "Afegir Clau de Pista de Transformació" #: editor/animation_track_editor.cpp msgid "Add Track Key" @@ -439,7 +437,7 @@ msgstr "Valor del pas d'Animació." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "Segons" #: editor/animation_track_editor.cpp msgid "FPS" @@ -483,14 +481,12 @@ msgid "Delete Selection" msgstr "Elimina la Selecció" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Go to Next Step" -msgstr "Vés al Pas Següent" +msgstr "Anar al Pas Següent" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Go to Previous Step" -msgstr "Vés al Pas Anterior" +msgstr "Anar al Pas Anterior" #: editor/animation_track_editor.cpp msgid "Optimize Animation" @@ -565,17 +561,16 @@ msgid "Copy" msgstr "Copia" #: editor/animation_track_editor_plugins.cpp -#, fuzzy msgid "Add Audio Track Clip" -msgstr "Talls d'Àudio:" +msgstr "Afegir Clip de Pista d'Àudio" #: editor/animation_track_editor_plugins.cpp msgid "Change Audio Track Clip Start Offset" -msgstr "" +msgstr "Canviar Desplaçament d'Inici de Clip de Pista d'Àudio" #: editor/animation_track_editor_plugins.cpp msgid "Change Audio Track Clip End Offset" -msgstr "" +msgstr "Canviar Desplaçament de Fi del Clip de Pista d'Àudio" #: editor/array_property_edit.cpp msgid "Resize Array" @@ -647,7 +642,7 @@ msgstr "Avisos" #: editor/code_editor.cpp msgid "Line and column numbers." -msgstr "" +msgstr "Números de lÃnia i columna." #: editor/connections_dialog.cpp msgid "Method in target Node must be specified!" @@ -752,9 +747,9 @@ msgid "Edit Connection: " msgstr "Edita la Connexió: " #: editor/connections_dialog.cpp -#, fuzzy msgid "Are you sure you want to remove all connections from the \"%s\" signal?" -msgstr "Esteu segur que voleu eliminar totes les connexions d'aquest senyal?" +msgstr "" +"Esteu segurs de que voleu eliminar totes les connexions del senyal \"%s\"?" #: editor/connections_dialog.cpp editor/editor_help.cpp editor/node_dock.cpp msgid "Signals" @@ -908,9 +903,8 @@ msgid "Error loading:" msgstr "Error en carregar:" #: editor/dependency_editor.cpp -#, fuzzy msgid "Load failed due to missing dependencies:" -msgstr "No es pot carregar l'escena. Manquen dependències:" +msgstr "Cà rrega fallida perquè falten les següents dependències:" #: editor/dependency_editor.cpp editor/editor_node.cpp msgid "Open Anyway" @@ -1061,9 +1055,8 @@ msgid "Uncompressing Assets" msgstr "Descomprimint Recursos" #: editor/editor_asset_installer.cpp editor/project_manager.cpp -#, fuzzy msgid "Package installed successfully!" -msgstr "Paquet instal·lat correctament!" +msgstr "Paquet instal·lat amb èxit!" #: editor/editor_asset_installer.cpp #: editor/plugins/asset_library_editor_plugin.cpp @@ -1209,9 +1202,8 @@ msgid "Add Bus" msgstr "Afegeix Bus" #: editor/editor_audio_buses.cpp -#, fuzzy msgid "Add a new Audio Bus to this layout." -msgstr "Anomena i Desa el Disseny del Bus d'Àudio..." +msgstr "Afegir un nou Bus d'Àudio a aquesta configuració." #: editor/editor_audio_buses.cpp editor/editor_properties.cpp #: editor/plugins/animation_player_editor_plugin.cpp editor/property_editor.cpp @@ -1397,12 +1389,16 @@ msgid "" "Target platform requires 'ETC' texture compression for GLES2. Enable 'Import " "Etc' in Project Settings." msgstr "" +"La plataforma de destà requereix compressió de textures 'ETC' per a GLES2. " +"Activa 'Import Etc' en la Configuració del Projecte." #: editor/editor_export.cpp msgid "" "Target platform requires 'ETC2' texture compression for GLES3. Enable " "'Import Etc 2' in Project Settings." msgstr "" +"La plataforma de destà requereix compressió de textures 'ETC' per a GLES2. " +"Activa 'Import Etc 2' en la Configuració del Projecte." #: editor/editor_export.cpp msgid "" @@ -1421,9 +1417,8 @@ msgstr "No s'ha trobat cap plantilla de depuració personalitzada." #: editor/editor_export.cpp platform/android/export/export.cpp #: platform/iphone/export/export.cpp platform/javascript/export/export.cpp #: platform/osx/export/export.cpp platform/uwp/export/export.cpp -#, fuzzy msgid "Custom release template not found." -msgstr "No s'ha trobat cap paquet de llançament personalitzat." +msgstr "No s'ha trobat cap plantilla de publicació personalitzada." #: editor/editor_export.cpp platform/javascript/export/export.cpp msgid "Template file not found:" @@ -1438,24 +1433,21 @@ msgid "File Exists, Overwrite?" msgstr "Fitxer Existent, Voleu sobreescriure'l?" #: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp -#, fuzzy msgid "Select This Folder" -msgstr "Selecciona aquest Directori" +msgstr "Seleccionar aquest Directori" #: editor/editor_file_dialog.cpp editor/filesystem_dock.cpp msgid "Copy Path" msgstr "Copia CamÃ" #: editor/editor_file_dialog.cpp editor/filesystem_dock.cpp -#, fuzzy msgid "Open in File Manager" -msgstr "Mostra en el Gestor de Fitxers" +msgstr "Obrir en el Gestor de Fitxers" #: editor/editor_file_dialog.cpp editor/filesystem_dock.cpp #: editor/project_manager.cpp -#, fuzzy msgid "Show in File Manager" -msgstr "Mostra en el Gestor de Fitxers" +msgstr "Mostrar en el Gestor de Fitxers" #: editor/editor_file_dialog.cpp editor/filesystem_dock.cpp msgid "New Folder..." @@ -1549,9 +1541,8 @@ msgid "Go to parent folder" msgstr "Vés al directori principal" #: editor/editor_file_dialog.cpp -#, fuzzy msgid "(Un)favorite current folder." -msgstr "No s'ha pogut crear el directori." +msgstr "Eliminar carpeta actual de preferits." #: editor/editor_file_dialog.cpp editor/filesystem_dock.cpp msgid "View items as a grid of thumbnails." @@ -1677,14 +1668,12 @@ msgstr "" "$url2]sol·licitant-lo[/url][/color]." #: editor/editor_help.cpp -#, fuzzy msgid "Property Descriptions" -msgstr "Descripció de la Propietat:" +msgstr "Descripcions de la Propietat" #: editor/editor_help.cpp -#, fuzzy msgid "Property Descriptions:" -msgstr "Descripció de la Propietat:" +msgstr "Descripcions de la Propietat:" #: editor/editor_help.cpp msgid "" @@ -1695,14 +1684,12 @@ msgstr "" "$color][url=$url] totaportant-ne una[/url][/color]!" #: editor/editor_help.cpp -#, fuzzy msgid "Method Descriptions" -msgstr "Descripció del mètode:" +msgstr "Descripcions del Mètode" #: editor/editor_help.cpp -#, fuzzy msgid "Method Descriptions:" -msgstr "Descripció del mètode:" +msgstr "Descripcions del Mètode:" #: editor/editor_help.cpp msgid "" @@ -1718,9 +1705,8 @@ msgid "Search Help" msgstr "Cerca Ajuda" #: editor/editor_help_search.cpp -#, fuzzy msgid "Display All" -msgstr "Mostra les Normals" +msgstr "Mostra-ho tot" #: editor/editor_help_search.cpp msgid "Classes Only" @@ -1747,9 +1733,8 @@ msgid "Theme Properties Only" msgstr "Només Propietats del Tema" #: editor/editor_help_search.cpp -#, fuzzy msgid "Member Type" -msgstr "Membres" +msgstr "Tipus de Membre" #: editor/editor_help_search.cpp msgid "Class" @@ -1876,7 +1861,7 @@ msgstr "" #: editor/editor_node.cpp editor/scene_tree_dock.cpp msgid "Can't overwrite scene that is still open!" -msgstr "" +msgstr "No es pot sobreescriure la escena si encara està oberta!" #: editor/editor_node.cpp msgid "Can't load MeshLibrary for merging!" @@ -2205,9 +2190,8 @@ msgstr "Predeterminat" #: editor/editor_node.cpp editor/editor_properties.cpp #: editor/plugins/script_editor_plugin.cpp editor/property_editor.cpp -#, fuzzy msgid "Show in FileSystem" -msgstr "Mostra'l en el Sistema de Fitxers" +msgstr "Mostrar en el Sistema de Fitxers" #: editor/editor_node.cpp msgid "Play This Scene" @@ -2290,9 +2274,8 @@ msgid "Save Scene" msgstr "Desa Escena" #: editor/editor_node.cpp -#, fuzzy msgid "Save All Scenes" -msgstr "Desa Totes les Escenes" +msgstr "Desar Totes les Escenes" #: editor/editor_node.cpp msgid "Close Scene" @@ -2563,9 +2546,8 @@ msgid "Save & Restart" msgstr "Desa i Reinicia" #: editor/editor_node.cpp -#, fuzzy msgid "Spins when the editor window redraws." -msgstr "Gira i Gira mentre l'editor es repinta!" +msgstr "Gira quan la finestra de l'editor es redibuixa." #: editor/editor_node.cpp msgid "Update Always" @@ -2776,9 +2758,8 @@ msgid "Assign..." msgstr "Assigna..." #: editor/editor_properties.cpp -#, fuzzy msgid "Invalid RID" -msgstr "Camà no và lid" +msgstr "RID no và lid" #: editor/editor_properties.cpp msgid "" @@ -3224,12 +3205,10 @@ msgid "New Resource..." msgstr "Recurs Nou..." #: editor/filesystem_dock.cpp editor/script_editor_debugger.cpp -#, fuzzy msgid "Expand All" msgstr "Expandir tot" #: editor/filesystem_dock.cpp editor/script_editor_debugger.cpp -#, fuzzy msgid "Collapse All" msgstr "Col·lapsar tot" @@ -3253,9 +3232,8 @@ msgid "Re-Scan Filesystem" msgstr "ReAnalitza Sistema de Fitxers" #: editor/filesystem_dock.cpp -#, fuzzy msgid "Toggle split mode" -msgstr "Commuta Mode" +msgstr "Commutar mode dividit" #: editor/filesystem_dock.cpp msgid "Search files" @@ -3284,18 +3262,16 @@ msgid "Create Script" msgstr "Crea un Script" #: editor/find_in_files.cpp -#, fuzzy msgid "Find in Files" -msgstr "Cerca en els fitxers" +msgstr "Cercar en els Fitxers" #: editor/find_in_files.cpp -#, fuzzy msgid "Find:" -msgstr "Cerca: " +msgstr "Cercar:" #: editor/find_in_files.cpp msgid "Folder:" -msgstr "Directori: " +msgstr "Directori:" #: editor/find_in_files.cpp msgid "Filters:" @@ -3474,7 +3450,7 @@ msgstr "ReImportar" #: editor/import_dock.cpp msgid "Save scenes, re-import and restart" -msgstr "" +msgstr "Guardar escenes, reimportar i reiniciar" #: editor/import_dock.cpp msgid "Changing the type of an imported file requires editor restart." @@ -3643,14 +3619,12 @@ msgid "Insert Point" msgstr "Insereix un Punt" #: editor/plugins/abstract_polygon_2d_editor.cpp -#, fuzzy msgid "Edit Polygon (Remove Point)" -msgstr "Edita el PolÃgon (Elimina un Punt)" +msgstr "Editar PolÃgon (Eliminar Punt)" #: editor/plugins/abstract_polygon_2d_editor.cpp -#, fuzzy msgid "Remove Polygon And Point" -msgstr "Elimina el PolÃgon i el Punt" +msgstr "Eliminar PolÃgon i Punt" #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp @@ -3664,25 +3638,21 @@ msgstr "Afegeix una Animació" #: editor/plugins/animation_blend_space_2d_editor.cpp #: editor/plugins/animation_blend_tree_editor_plugin.cpp #: editor/plugins/animation_state_machine_editor.cpp -#, fuzzy msgid "Load..." -msgstr "Carrega..." +msgstr "Carregar..." #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp -#, fuzzy msgid "Move Node Point" -msgstr "Mou el Punt" +msgstr "Moure Punt de Node" #: editor/plugins/animation_blend_space_1d_editor.cpp -#, fuzzy msgid "Change BlendSpace1D Limits" -msgstr "Modifica el Temps de Mescla" +msgstr "Canviar LÃmits de BlendSpace1D" #: editor/plugins/animation_blend_space_1d_editor.cpp -#, fuzzy msgid "Change BlendSpace1D Labels" -msgstr "Modifica el Temps de Mescla" +msgstr "Canviar Etiquetes de BlendSpace1D" #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp @@ -3694,24 +3664,21 @@ msgstr "" #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp -#, fuzzy msgid "Add Node Point" -msgstr "Afegeix un Node" +msgstr "Afegir Punt de Node" #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp -#, fuzzy msgid "Add Animation Point" -msgstr "Afegeix una Animació" +msgstr "Afegir Punt d'Animació" #: editor/plugins/animation_blend_space_1d_editor.cpp -#, fuzzy msgid "Remove BlendSpace1D Point" -msgstr "Elimina un Punt del CamÃ" +msgstr "Eliminar Punt BlendSpace1D" #: editor/plugins/animation_blend_space_1d_editor.cpp msgid "Move BlendSpace1D Node Point" -msgstr "" +msgstr "Moure Punt BlendSpace1D" #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp @@ -3760,24 +3727,20 @@ msgid "Add Triangle" msgstr "Afegir Triangle" #: editor/plugins/animation_blend_space_2d_editor.cpp -#, fuzzy msgid "Change BlendSpace2D Limits" -msgstr "Modifica el Temps de Mescla" +msgstr "Canviar LÃmits BlendSpace2D" #: editor/plugins/animation_blend_space_2d_editor.cpp -#, fuzzy msgid "Change BlendSpace2D Labels" -msgstr "Modifica el Temps de Mescla" +msgstr "Canviar Etiquetes BlendSpace2D" #: editor/plugins/animation_blend_space_2d_editor.cpp -#, fuzzy msgid "Remove BlendSpace2D Point" -msgstr "Elimina un Punt del CamÃ" +msgstr "Eliminar Punt BlendSpace2D" #: editor/plugins/animation_blend_space_2d_editor.cpp -#, fuzzy msgid "Remove BlendSpace2D Triangle" -msgstr "Elimina la Variable" +msgstr "Eliminar Triangle BlendSpace2D" #: editor/plugins/animation_blend_space_2d_editor.cpp msgid "BlendSpace2D does not belong to an AnimationTree node." @@ -3839,7 +3802,6 @@ msgstr "No es pot connectar. El port és en ús o la connexió no és và lida." #: editor/plugins/animation_blend_tree_editor_plugin.cpp #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Nodes Connected" msgstr "Nodes Connectats" @@ -3849,9 +3811,8 @@ msgid "Nodes Disconnected" msgstr "Nodes Desconnectats" #: editor/plugins/animation_blend_tree_editor_plugin.cpp -#, fuzzy msgid "Set Animation" -msgstr "Animació" +msgstr "Establir Animació" #: editor/plugins/animation_blend_tree_editor_plugin.cpp #: editor/plugins/visual_shader_editor_plugin.cpp @@ -3897,20 +3858,17 @@ msgstr "Nom del node:" #: editor/plugins/animation_blend_tree_editor_plugin.cpp #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Add Node..." -msgstr "Afegeix un Node" +msgstr "Afegir Node..." #: editor/plugins/animation_blend_tree_editor_plugin.cpp #: editor/plugins/root_motion_editor_plugin.cpp -#, fuzzy msgid "Edit Filtered Tracks:" -msgstr "Edita Filtres" +msgstr "Editar Pistes Filtrades:" #: editor/plugins/animation_blend_tree_editor_plugin.cpp -#, fuzzy msgid "Enable filtering" -msgstr "Fills Editables" +msgstr "Habilitar filtració" #: editor/plugins/animation_player_editor_plugin.cpp msgid "Toggle Autoplay" @@ -3938,14 +3896,12 @@ msgid "Remove Animation" msgstr "Eliminar l'Animació" #: editor/plugins/animation_player_editor_plugin.cpp -#, fuzzy msgid "Invalid animation name!" -msgstr "ERROR: El Nom de l'Animació no és và lid!" +msgstr "El Nom de l'Animació no és và lid!" #: editor/plugins/animation_player_editor_plugin.cpp -#, fuzzy msgid "Animation name already exists!" -msgstr "ERROR: Ja existeix aquest nom d'Animació!" +msgstr "El nom d'animació ja existeix!" #: editor/plugins/animation_player_editor_plugin.cpp #: editor/plugins/sprite_frames_editor_plugin.cpp @@ -3969,14 +3925,12 @@ msgid "Duplicate Animation" msgstr "Duplica l'Animació" #: editor/plugins/animation_player_editor_plugin.cpp -#, fuzzy msgid "No animation to copy!" -msgstr "ERROR: Cap animació per copiar!" +msgstr "No hi ha animacions per copiar!" #: editor/plugins/animation_player_editor_plugin.cpp -#, fuzzy msgid "No animation resource on clipboard!" -msgstr "ERROR: Cap recurs d'animació al porta-retalls!" +msgstr "No hi ha recursos d'animació al porta-retalls!" #: editor/plugins/animation_player_editor_plugin.cpp msgid "Pasted Animation" @@ -3987,9 +3941,8 @@ msgid "Paste Animation" msgstr "Enganxa l'Animació" #: editor/plugins/animation_player_editor_plugin.cpp -#, fuzzy msgid "No animation to edit!" -msgstr "ERROR: Cap animació per editar!" +msgstr "Cap animació per editar!" #: editor/plugins/animation_player_editor_plugin.cpp msgid "Play selected animation backwards from current pos. (A)" @@ -4034,14 +3987,12 @@ msgid "New" msgstr "Nou" #: editor/plugins/animation_player_editor_plugin.cpp -#, fuzzy msgid "Edit Transitions..." -msgstr "Transicions" +msgstr "Editar Transicions..." #: editor/plugins/animation_player_editor_plugin.cpp -#, fuzzy msgid "Open in Inspector" -msgstr "Obre en l'Editor" +msgstr "Obre en l'Inspector" #: editor/plugins/animation_player_editor_plugin.cpp msgid "Display list of animations in player." @@ -4133,14 +4084,12 @@ msgid "Cross-Animation Blend Times" msgstr "Temps de mescla entre Animacions" #: editor/plugins/animation_state_machine_editor.cpp -#, fuzzy msgid "Move Node" -msgstr "Mode de moviment" +msgstr "Moure Node" #: editor/plugins/animation_state_machine_editor.cpp -#, fuzzy msgid "Add Transition" -msgstr "Afegeix una Traducció" +msgstr "Afegir una Transició" #: editor/plugins/animation_state_machine_editor.cpp #: modules/visual_script/visual_script_editor.cpp @@ -4148,9 +4097,8 @@ msgid "Add Node" msgstr "Afegeix un Node" #: editor/plugins/animation_state_machine_editor.cpp -#, fuzzy msgid "End" -msgstr "Final/s" +msgstr "Final" #: editor/plugins/animation_state_machine_editor.cpp msgid "Immediate" @@ -4162,7 +4110,7 @@ msgstr "Sincronitzar" #: editor/plugins/animation_state_machine_editor.cpp msgid "At End" -msgstr "" +msgstr "Al Final" #: editor/plugins/animation_state_machine_editor.cpp msgid "Travel" @@ -4173,45 +4121,44 @@ msgid "Start and end nodes are needed for a sub-transition." msgstr "" #: editor/plugins/animation_state_machine_editor.cpp -#, fuzzy msgid "No playback resource set at path: %s." -msgstr "Fora del camà dels recursos." +msgstr "Cap recurs de reproducció assignat en el camÃ: %s." #: editor/plugins/animation_state_machine_editor.cpp -#, fuzzy msgid "Node Removed" -msgstr "Eliminat:" +msgstr "Node Eliminat" #: editor/plugins/animation_state_machine_editor.cpp -#, fuzzy msgid "Transition Removed" -msgstr "Node de Transició" +msgstr "Transició Eliminada" #: editor/plugins/animation_state_machine_editor.cpp msgid "Set Start Node (Autoplay)" -msgstr "" +msgstr "Establir node d'inici (Reproducció Automà tica)" #: editor/plugins/animation_state_machine_editor.cpp +#, fuzzy msgid "" "Select and move nodes.\n" "RMB to add new nodes.\n" "Shift+LMB to create connections." msgstr "" +"Seleccionar i moure nodes.\n" +"Clic dret per afegir nous nodes.\n" +"Shift + clic esquerra per a crear connexions." #: editor/plugins/animation_state_machine_editor.cpp -#, fuzzy msgid "Create new nodes." -msgstr "Crea Nou %s" +msgstr "Crear nous nodes." #: editor/plugins/animation_state_machine_editor.cpp -#, fuzzy msgid "Connect nodes." -msgstr "Connecta els Nodes" +msgstr "Connectar nodes." #: editor/plugins/animation_state_machine_editor.cpp #, fuzzy msgid "Remove selected node or transition." -msgstr "Treu la pista seleccionada." +msgstr "Eliminar el node o transició seleccionats." #: editor/plugins/animation_state_machine_editor.cpp msgid "Toggle autoplay this animation on start, restart or seek to zero." @@ -4224,7 +4171,7 @@ msgstr "" #: editor/plugins/animation_state_machine_editor.cpp #, fuzzy msgid "Transition: " -msgstr "Transició" +msgstr "Transició: " #: editor/plugins/animation_tree_editor_plugin.cpp #: editor/plugins/animation_tree_player_editor_plugin.cpp @@ -4418,14 +4365,12 @@ msgid "Asset Download Error:" msgstr "Error en la baixada de l'Actiu:" #: editor/plugins/asset_library_editor_plugin.cpp -#, fuzzy msgid "Downloading (%s / %s)..." -msgstr "S'esta descarrengant" +msgstr "Descarregant (%s / %s)..." #: editor/plugins/asset_library_editor_plugin.cpp -#, fuzzy msgid "Downloading..." -msgstr "S'esta descarrengant" +msgstr "Descarregant..." #: editor/plugins/asset_library_editor_plugin.cpp msgid "Resolving..." @@ -4798,9 +4743,8 @@ msgid "Restores the object's children's ability to be selected." msgstr "Permet la selecció de nodes fills." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Skeleton Options" -msgstr "Singleton" +msgstr "Opcions d'esquelet" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Show Bones" @@ -4855,7 +4799,7 @@ msgstr "Mostra el Viewport" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Show Group And Lock Icons" -msgstr "" +msgstr "Mostrar Grup i Bloquejar Icones" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Center Selection" @@ -4871,15 +4815,15 @@ msgstr "Desar Disseny" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Translation mask for inserting keys." -msgstr "" +msgstr "Mascara de translació per a inserir claus." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Rotation mask for inserting keys." -msgstr "" +msgstr "Mascara de rotació per a inserir claus." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Scale mask for inserting keys." -msgstr "" +msgstr "Mascara d'escala per a inserir claus." #: editor/plugins/canvas_item_editor_plugin.cpp #, fuzzy @@ -5100,7 +5044,7 @@ msgstr "Precalcula la Sonda d'IG" #: editor/plugins/gradient_editor_plugin.cpp msgid "Gradient Edited" -msgstr "" +msgstr "Degradat Editat" #: editor/plugins/item_list_editor_plugin.cpp msgid "Item %d" @@ -5451,9 +5395,8 @@ msgid "Add Point to Curve" msgstr "Afegeix un Punt a la Corba" #: editor/plugins/path_2d_editor_plugin.cpp -#, fuzzy msgid "Split Curve" -msgstr "Tanca la Corba" +msgstr "Partir Corba" #: editor/plugins/path_2d_editor_plugin.cpp msgid "Move Point in Curve" @@ -5483,9 +5426,8 @@ msgid "Click: Add Point" msgstr "Clic: Afegeix un Punt" #: editor/plugins/path_2d_editor_plugin.cpp -#, fuzzy msgid "Left Click: Split Segment (in curve)" -msgstr "Parteix el Segment (de la Corba)" +msgstr "Clic Esquerra: Partir Segment (en la Corba)" #: editor/plugins/path_2d_editor_plugin.cpp #: editor/plugins/path_editor_plugin.cpp @@ -5571,7 +5513,7 @@ msgstr "Mou el Punt" #: editor/plugins/polygon_2d_editor_plugin.cpp msgid "" "The skeleton property of the Polygon2D does not point to a Skeleton2D node" -msgstr "" +msgstr "La propietat esquelet del Polygon2D no apunta a un node Skeleton2D" #: editor/plugins/polygon_2d_editor_plugin.cpp #, fuzzy @@ -5579,10 +5521,13 @@ msgid "Sync Bones" msgstr "Mostra els Ossos" #: editor/plugins/polygon_2d_editor_plugin.cpp +#, fuzzy msgid "" "No texture in this polygon.\n" "Set a texture to be able to edit UV." msgstr "" +"No hi ha textura en aquest polÃgon.\n" +"Assigneu una textura per a poder editar el UV." #: editor/plugins/polygon_2d_editor_plugin.cpp msgid "Create UV Map" @@ -5610,13 +5555,13 @@ msgid "Remove Internal Vertex" msgstr "Elimina el Punt In-Control" #: editor/plugins/polygon_2d_editor_plugin.cpp +#, fuzzy msgid "Invalid Polygon (need 3 different vertices)" -msgstr "" +msgstr "PolÃgon no và lid (es necessiten 3 vèrtex diferents)" #: editor/plugins/polygon_2d_editor_plugin.cpp -#, fuzzy msgid "Add Custom Polygon" -msgstr "Edita PolÃgon" +msgstr "Afegir PolÃgon Personalitzat" #: editor/plugins/polygon_2d_editor_plugin.cpp #, fuzzy @@ -5633,8 +5578,9 @@ msgid "Transform Polygon" msgstr "Tipus de Transformació" #: editor/plugins/polygon_2d_editor_plugin.cpp +#, fuzzy msgid "Paint Bone Weights" -msgstr "" +msgstr "Pintar Pes dels Ossos" #: editor/plugins/polygon_2d_editor_plugin.cpp #, fuzzy @@ -5694,22 +5640,30 @@ msgid "Scale Polygon" msgstr "Escala el PolÃgon" #: editor/plugins/polygon_2d_editor_plugin.cpp +#, fuzzy msgid "Create a custom polygon. Enables custom polygon rendering." msgstr "" +"Crear polÃgon personalitzat. Habilita el renderitzat de polÃgons " +"personalitzats." #: editor/plugins/polygon_2d_editor_plugin.cpp +#, fuzzy msgid "" "Remove a custom polygon. If none remain, custom polygon rendering is " "disabled." msgstr "" +"Eliminar un polÃgon personalitzat. Si no en queda cap, el renderitzat de " +"polÃgons personalitzats es deshabilita." #: editor/plugins/polygon_2d_editor_plugin.cpp +#, fuzzy msgid "Paint weights with specified intensity." -msgstr "" +msgstr "Pinta el pes amb la intensitat especificada." #: editor/plugins/polygon_2d_editor_plugin.cpp +#, fuzzy msgid "Unpaint weights with specified intensity." -msgstr "" +msgstr "Despinta el pes amb la intensitat especificada." #: editor/plugins/polygon_2d_editor_plugin.cpp msgid "Radius:" @@ -5728,9 +5682,8 @@ msgid "Clear UV" msgstr "Esborra UVs" #: editor/plugins/polygon_2d_editor_plugin.cpp -#, fuzzy msgid "Grid Settings" -msgstr "Configuració del GridMap" +msgstr "Configuració de la QuadrÃcula" #: editor/plugins/polygon_2d_editor_plugin.cpp #: editor/plugins/spatial_editor_plugin.cpp @@ -5743,7 +5696,7 @@ msgstr "Activa l'Alineament" #: editor/plugins/polygon_2d_editor_plugin.cpp msgid "Grid" -msgstr "Graella" +msgstr "QuadrÃcula" #: editor/plugins/polygon_2d_editor_plugin.cpp #, fuzzy @@ -5948,9 +5901,8 @@ msgid "File" msgstr "Fitxer" #: editor/plugins/script_editor_plugin.cpp -#, fuzzy msgid "Open..." -msgstr "Obre" +msgstr "Obrir..." #: editor/plugins/script_editor_plugin.cpp msgid "Save All" @@ -6091,9 +6043,8 @@ msgid "Debugger" msgstr "Depurador" #: editor/plugins/script_editor_plugin.cpp -#, fuzzy msgid "Search Results" -msgstr "Cerca Ajuda" +msgstr "Resultats de cerca" #: editor/plugins/script_text_editor.cpp msgid "Line" @@ -6142,7 +6093,7 @@ msgstr "Converteix a Majúscules" #: editor/plugins/script_text_editor.cpp editor/plugins/text_editor.cpp msgid "Syntax Highlighter" -msgstr "" +msgstr "Ressaltador de sintaxi" #: editor/plugins/script_text_editor.cpp scene/gui/line_edit.cpp #: scene/gui/text_edit.cpp @@ -6231,9 +6182,8 @@ msgid "Find Previous" msgstr "Cerca l'Anterior" #: editor/plugins/script_text_editor.cpp -#, fuzzy msgid "Find in Files..." -msgstr "Filtrat de Fitxers..." +msgstr "Cercar en Fitxers..." #: editor/plugins/script_text_editor.cpp #, fuzzy @@ -6285,9 +6235,8 @@ msgid "Create physical bones" msgstr "Crea un malla de Navegació" #: editor/plugins/skeleton_editor_plugin.cpp -#, fuzzy msgid "Skeleton" -msgstr "Singleton" +msgstr "Esquelet" #: editor/plugins/skeleton_editor_plugin.cpp #, fuzzy @@ -6438,9 +6387,8 @@ msgid "This operation requires a single selected node." msgstr "Aquesta operació requereix un únic node seleccionat." #: editor/plugins/spatial_editor_plugin.cpp -#, fuzzy msgid "Lock View Rotation" -msgstr "Mostra la Informació" +msgstr "Bloquejar Rotació de la Vista" #: editor/plugins/spatial_editor_plugin.cpp msgid "Display Normal" @@ -6487,9 +6435,8 @@ msgid "Doppler Enable" msgstr "Activa Doppler" #: editor/plugins/spatial_editor_plugin.cpp -#, fuzzy msgid "Cinematic Preview" -msgstr "Creant Previsualitzacions de Malles" +msgstr "Previsualització Cinemà tica" #: editor/plugins/spatial_editor_plugin.cpp msgid "Freelook Left" @@ -6526,9 +6473,8 @@ msgid "" msgstr "" #: editor/plugins/spatial_editor_plugin.cpp -#, fuzzy msgid "View Rotation Locked" -msgstr "Mostra la Informació" +msgstr "Rotació de la Vista Bloquejada" #: editor/plugins/spatial_editor_plugin.cpp msgid "XForm Dialog" @@ -6838,9 +6784,8 @@ msgid "Grow (Pixels): " msgstr "" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Update Preview" -msgstr "Previsualització" +msgstr "Actualitzar Previsualització" #: editor/plugins/sprite_editor_plugin.cpp msgid "Settings:" @@ -6929,9 +6874,8 @@ msgstr "Mode Imant:" #: editor/plugins/texture_region_editor_plugin.cpp #: scene/resources/visual_shader.cpp -#, fuzzy msgid "None" -msgstr "<Cap>" +msgstr "Cap" #: editor/plugins/texture_region_editor_plugin.cpp msgid "Pixel Snap" @@ -7096,9 +7040,8 @@ msgid "Fix Invalid Tiles" msgstr "Nom no và lid." #: editor/plugins/tile_map_editor_plugin.cpp -#, fuzzy msgid "Cut Selection" -msgstr "Centra la Selecció" +msgstr "Tallar Selecció" #: editor/plugins/tile_map_editor_plugin.cpp msgid "Paint TileMap" @@ -7146,9 +7089,8 @@ msgid "Pick Tile" msgstr "Tria un Tessel·la" #: editor/plugins/tile_map_editor_plugin.cpp -#, fuzzy msgid "Copy Selection" -msgstr "Treu la Selecció" +msgstr "Copiar Selecció" #: editor/plugins/tile_map_editor_plugin.cpp #, fuzzy @@ -7192,18 +7134,16 @@ msgid "Merge from Scene" msgstr "Combina-ho a partir de l'Escena" #: editor/plugins/tile_set_editor_plugin.cpp -#, fuzzy msgid "Next Coordinate" -msgstr "Planta Següent" +msgstr "Coordenada Següent" #: editor/plugins/tile_set_editor_plugin.cpp msgid "Select the next shape, subtile, or Tile." msgstr "" #: editor/plugins/tile_set_editor_plugin.cpp -#, fuzzy msgid "Previous Coordinate" -msgstr "Planta Anterior" +msgstr "Coordenada Anterior" #: editor/plugins/tile_set_editor_plugin.cpp msgid "Select the previous shape, subtile, or Tile." @@ -7225,12 +7165,11 @@ msgstr "Elimina un Punt." #: editor/plugins/tile_set_editor_plugin.cpp msgid "Create a new rectangle." -msgstr "Crear un Nou Rectangle." +msgstr "Crear un nou rectangle." #: editor/plugins/tile_set_editor_plugin.cpp -#, fuzzy msgid "Create a new polygon." -msgstr "Crea un nou PolÃgon del no-res." +msgstr "Crear un nou polÃgon." #: editor/plugins/tile_set_editor_plugin.cpp msgid "Keep polygon inside region Rect." @@ -7262,9 +7201,8 @@ msgid "Merge from scene?" msgstr "Combinar-ho a partir de l'escena?" #: editor/plugins/tile_set_editor_plugin.cpp -#, fuzzy msgid "Remove Texture" -msgstr "Elimina la Plantilla" +msgstr "Eliminar Textura" #: editor/plugins/tile_set_editor_plugin.cpp msgid "%s file(s) were not added because was already on the list." @@ -7289,9 +7227,8 @@ msgid "" msgstr "Selecciona la sub-tessel·la en edició." #: editor/plugins/tile_set_editor_plugin.cpp -#, fuzzy msgid "Delete polygon." -msgstr "Elimina els Punts" +msgstr "Eliminar PolÃgon." #: editor/plugins/tile_set_editor_plugin.cpp #, fuzzy @@ -7437,23 +7374,20 @@ msgid "Add Node to Visual Shader" msgstr "Ombreig" #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Duplicate Nodes" -msgstr "Duplica els Nodes" +msgstr "Duplicar Nodes" #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Delete Nodes" -msgstr "Eliminar Node" +msgstr "Eliminar Nodes" #: editor/plugins/visual_shader_editor_plugin.cpp msgid "Visual Shader Input Type Changed" msgstr "" #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Vertex" -msgstr "Vèrtexs" +msgstr "Vèrtex" #: editor/plugins/visual_shader_editor_plugin.cpp #, fuzzy @@ -7461,9 +7395,8 @@ msgid "Fragment" msgstr "Arguments:" #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Light" -msgstr "Dreta" +msgstr "Llum" #: editor/plugins/visual_shader_editor_plugin.cpp #, fuzzy @@ -7471,9 +7404,8 @@ msgid "VisualShader" msgstr "Ombreig" #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Edit Visual Property" -msgstr "Edita Filtres" +msgstr "Editar Propietat Visual" #: editor/plugins/visual_shader_editor_plugin.cpp #, fuzzy @@ -7493,10 +7425,13 @@ msgid "Delete preset '%s'?" msgstr "Esborrar la configuració '%s' ?" #: editor/project_export.cpp +#, fuzzy msgid "" "Failed to export the project for platform '%s'.\n" "Export templates seem to be missing or invalid." msgstr "" +"No s'ha pogut exportar el projecte per la plataforma '%s'.\n" +"Les plantilles d'exportació semblen absents o son invalides." #: editor/project_export.cpp msgid "" @@ -7518,7 +7453,7 @@ msgstr "Exportació per a %s" #: editor/project_export.cpp #, fuzzy msgid "The given export path doesn't exist:" -msgstr "El camà no existeix." +msgstr "El camà triat per la exportació no existeix:" #: editor/project_export.cpp msgid "Export templates for this platform are missing/corrupted:" @@ -7533,9 +7468,8 @@ msgid "Add..." msgstr "Afegeix..." #: editor/project_export.cpp -#, fuzzy msgid "Export Path" -msgstr "Exporta Projecte" +msgstr "Camà d'exportació" #: editor/project_export.cpp msgid "Resources" @@ -7630,14 +7564,12 @@ msgid "Export PCK/Zip" msgstr "Exporta PCK/Zip" #: editor/project_export.cpp -#, fuzzy msgid "Export mode?" -msgstr "Mode d'Exportació:" +msgstr "Mode d'Exportació?" #: editor/project_export.cpp -#, fuzzy msgid "Export All" -msgstr "Exporta" +msgstr "Exportar Tot" #: editor/project_export.cpp msgid "Export templates for this platform are missing:" @@ -7652,10 +7584,8 @@ msgid "The path does not exist." msgstr "El camà no existeix." #: editor/project_manager.cpp -#, fuzzy msgid "Invalid '.zip' project file, does not contain a 'project.godot' file." -msgstr "" -"Seleccioneu un directori que no contingui ja un fitxer 'project.godot'." +msgstr "Fitxer de projecte '.zip' invalid, no conte un fitxer 'project.godot'." #: editor/project_manager.cpp msgid "Please choose an empty folder." @@ -7664,7 +7594,7 @@ msgstr "Selecciona un directori buit." #: editor/project_manager.cpp #, fuzzy msgid "Please choose a 'project.godot' or '.zip' file." -msgstr "Selecciona un fitxer 'projecte.godot'." +msgstr "Si us plau seleccioneu un fitxer 'projecte.godot' o '.zip'." #: editor/project_manager.cpp msgid "Directory already contains a Godot project." @@ -7759,9 +7689,8 @@ msgid "Project Path:" msgstr "Camà del Projecte:" #: editor/project_manager.cpp -#, fuzzy msgid "Project Installation Path:" -msgstr "Camà del Projecte:" +msgstr "Camà d'instal·lació del Projecte:" #: editor/project_manager.cpp msgid "Browse" @@ -7972,9 +7901,8 @@ msgid "Add Input Action Event" msgstr "Afegeix un Incidència d'Acció de Entrada" #: editor/project_settings_editor.cpp -#, fuzzy msgid "All Devices" -msgstr "Dispositiu" +msgstr "Tots els Dispositius" #: editor/project_settings_editor.cpp msgid "Device" @@ -8362,14 +8290,12 @@ msgid "Node's parent name, if available" msgstr "" #: editor/rename_dialog.cpp -#, fuzzy msgid "Node type" -msgstr "Troba el Tipus de Node" +msgstr "Tipus de node" #: editor/rename_dialog.cpp -#, fuzzy msgid "Current scene name" -msgstr "Escena Actual" +msgstr "Nom de l'escena actual" #: editor/rename_dialog.cpp #, fuzzy @@ -8414,9 +8340,8 @@ msgid "" msgstr "" #: editor/rename_dialog.cpp -#, fuzzy msgid "Regular Expressions" -msgstr "Modifica l'Expressió" +msgstr "Expressions Regulars" #: editor/rename_dialog.cpp #, fuzzy @@ -8440,19 +8365,17 @@ msgid "Case" msgstr "" #: editor/rename_dialog.cpp -#, fuzzy msgid "To Lowercase" -msgstr "Minúscula" +msgstr "A Minúscules" #: editor/rename_dialog.cpp -#, fuzzy msgid "To Uppercase" -msgstr "Majúscules" +msgstr "A Majúscules" #: editor/rename_dialog.cpp #, fuzzy msgid "Reset" -msgstr "Reinicia el Zoom" +msgstr "Resetejar" #: editor/rename_dialog.cpp msgid "Error" @@ -8591,24 +8514,20 @@ msgid "Make Local" msgstr "Local" #: editor/scene_tree_dock.cpp -#, fuzzy msgid "New Scene Root" -msgstr "Entesos!" +msgstr "Nova Arrel d'Escena" #: editor/scene_tree_dock.cpp -#, fuzzy msgid "Create Root Node:" -msgstr "Crea un Node" +msgstr "Crear Node Arrel:" #: editor/scene_tree_dock.cpp -#, fuzzy msgid "2D Scene" -msgstr "Escena" +msgstr "Escena 2D" #: editor/scene_tree_dock.cpp -#, fuzzy msgid "3D Scene" -msgstr "Escena" +msgstr "Escena 3D" #: editor/scene_tree_dock.cpp #, fuzzy @@ -8835,18 +8754,16 @@ msgid "N/A" msgstr "No Disponible" #: editor/script_create_dialog.cpp -#, fuzzy msgid "Open Script/Choose Location" -msgstr "Editor d'Scripts" +msgstr "Obrir Script/Escollir Localització" #: editor/script_create_dialog.cpp msgid "Path is empty" msgstr "El camà és Buit" #: editor/script_create_dialog.cpp -#, fuzzy msgid "Filename is empty" -msgstr "El camà per desar és buit!" +msgstr "El nom del fitxer és buit" #: editor/script_create_dialog.cpp msgid "Path is not local" @@ -9034,9 +8951,8 @@ msgid "Set From Tree" msgstr "Estableix des de l'Arbre" #: editor/settings_config_dialog.cpp -#, fuzzy msgid "Erase Shortcut" -msgstr "Sortida Lenta" +msgstr "Eliminar Drecera" #: editor/settings_config_dialog.cpp #, fuzzy @@ -9044,9 +8960,8 @@ msgid "Restore Shortcut" msgstr "Dreceres" #: editor/settings_config_dialog.cpp -#, fuzzy msgid "Change Shortcut" -msgstr "Modifica Ancoratges" +msgstr "Canviar Drecera" #: editor/settings_config_dialog.cpp msgid "Shortcuts" @@ -9347,9 +9262,8 @@ msgid "Clear Selection" msgstr "Esborra la Selecció" #: modules/gridmap/grid_map_editor_plugin.cpp -#, fuzzy msgid "Fill Selection" -msgstr "Tota la Selecció" +msgstr "Omplir la Selecció" #: modules/gridmap/grid_map_editor_plugin.cpp msgid "GridMap Settings" @@ -9571,7 +9485,7 @@ msgstr "Afegeix un Senyal" #: modules/visual_script/visual_script_editor.cpp msgid "Change Expression" -msgstr "Modifica l'Expressió" +msgstr "Canviar Expressió" #: modules/visual_script/visual_script_editor.cpp msgid "Remove VisualScript Nodes" @@ -9856,13 +9770,13 @@ msgid "Invalid public key for APK expansion." msgstr "" #: platform/android/export/export.cpp -#, fuzzy msgid "Invalid package name:" -msgstr "El Nom de Classe no és và lid" +msgstr "El nom del paquet no és và lid:" #: platform/iphone/export/export.cpp +#, fuzzy msgid "Identifier is missing." -msgstr "" +msgstr "Falta l'identificador." #: platform/iphone/export/export.cpp msgid "Identifier segments must be of non-zero length." @@ -9891,9 +9805,8 @@ msgid "App Store Team ID not specified - cannot configure the project." msgstr "" #: platform/iphone/export/export.cpp -#, fuzzy msgid "Invalid Identifier:" -msgstr "El nom no és un identificador và lid:" +msgstr "Identificador no và lid:" #: platform/iphone/export/export.cpp msgid "Required icon is not specified in the preset." @@ -10256,9 +10169,8 @@ msgid "" msgstr "" #: scene/3d/cpu_particles.cpp -#, fuzzy msgid "Nothing is visible because no mesh has been assigned." -msgstr "Res és visible perquè no s'ha assignat cap Malla a cap pas de Dibuix." +msgstr "Res és visible perquè no s'ha assignat cap malla." #: scene/3d/cpu_particles.cpp msgid "" diff --git a/editor/translations/cs.po b/editor/translations/cs.po index 63d5bea503..d8017edec7 100644 --- a/editor/translations/cs.po +++ b/editor/translations/cs.po @@ -164,14 +164,20 @@ msgid "Animation Playback Track" msgstr "Stopa pÅ™ehrávánà animace" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "PÅ™idat stopu" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Délka animace (v sekundách)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Délka animace (v sekundách)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "PÅ™idat stopu" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Opakovánà animace" diff --git a/editor/translations/da.po b/editor/translations/da.po index ee8b415fe3..67c856fed2 100644 --- a/editor/translations/da.po +++ b/editor/translations/da.po @@ -164,14 +164,20 @@ msgid "Animation Playback Track" msgstr "Animation-afspilningsspor" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Tilføj Spor" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Animations længde (i sekunder)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Animations længde (i sekunder)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Tilføj Spor" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Animationsløkke" diff --git a/editor/translations/de.po b/editor/translations/de.po index a9f174e98e..302f96dfa0 100644 --- a/editor/translations/de.po +++ b/editor/translations/de.po @@ -39,11 +39,12 @@ # Martin <martinreininger@gmx.net>, 2019. # Andreas During <anduring@web.de>, 2019. # Arthur S. Muszynski <artism90@gmail.com>, 2019. +# Andreas Binczyk <andreas.binczyk@gmail.com>, 2019. msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-03-30 20:04+0000\n" +"PO-Revision-Date: 2019-04-29 08:48+0000\n" "Last-Translator: So Wieso <sowieso@dukun.de>\n" "Language-Team: German <https://hosted.weblate.org/projects/godot-engine/" "godot/de/>\n" @@ -52,7 +53,7 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=n != 1;\n" -"X-Generator: Weblate 3.6-dev\n" +"X-Generator: Weblate 3.6.1\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -190,14 +191,20 @@ msgid "Animation Playback Track" msgstr "Animationsspielerspur" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Spur hinzufügen" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Animationsdauer (in Sekunden)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Animationsdauer (in Sekunden)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Spur hinzufügen" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Animationswiederholung" @@ -452,9 +459,8 @@ msgid "Group tracks by node or display them as plain list." msgstr "Spuren nach Node gruppieren oder nacheinander anzeigen." #: editor/animation_track_editor.cpp -#, fuzzy msgid "Snap:" -msgstr "Einrasten" +msgstr "Einrasten:" #: editor/animation_track_editor.cpp msgid "Animation step value." @@ -462,7 +468,7 @@ msgstr "Animationsschrittwert." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "Sekunden" #: editor/animation_track_editor.cpp msgid "FPS" @@ -3962,7 +3968,7 @@ msgstr "Animation umbenennen" #: editor/plugins/animation_player_editor_plugin.cpp msgid "Blend Next Changed" -msgstr "Ãœberblende nächste Bearbeitung" +msgstr "Ãœberblende nächste Änderung" #: editor/plugins/animation_player_editor_plugin.cpp msgid "Change Blend Time" @@ -4856,20 +4862,19 @@ msgstr "Layout" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Translation mask for inserting keys." -msgstr "" +msgstr "Verschiebungsmaske für Schlüsselbildeingabe." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Rotation mask for inserting keys." -msgstr "" +msgstr "Rotationsmaske für Schlüsselbildeingabe." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Scale mask for inserting keys." -msgstr "" +msgstr "Skalierungsmaske für Schlüsselbildeingabe." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Insert keys (based on mask)." -msgstr "Schlüsselbilder einfügen (Einfg)" +msgstr "Schlüsselbilder einfügen (basierend auf Maske)." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "" @@ -4878,11 +4883,15 @@ msgid "" "Keys are only added to existing tracks, no new tracks will be created.\n" "Keys must be inserted manually for the first time." msgstr "" +"Füge automatisiert Schlüsselbilder ein wenn Objekte verschoben, rotiert oder " +"skaliert werden (basierend auf Maske).\n" +"Schlüsselbilder werden nur in existierende Spuren eingefügt, es werden keine " +"neuen Spuren angelegt.\n" +"Das erste mal müssen Schlüsselbilder manuell eingefügt werden." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Auto Insert Key" -msgstr "Schlüsselbild einfügen" +msgstr "Schlüsselbild automatisch einfügen" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Insert Key (Existing Tracks)" @@ -5874,9 +5883,8 @@ msgid "Save Theme As..." msgstr "Motiv speichern als..." #: editor/plugins/script_editor_plugin.cpp -#, fuzzy msgid "%s Class Reference" -msgstr " Klassenreferenz" +msgstr "%s Klassenreferenz" #: editor/plugins/script_editor_plugin.cpp msgid "Toggle alphabetical sorting of the method list." @@ -6703,24 +6711,20 @@ msgid "Nameless gizmo" msgstr "Namenloser Anfasser" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Mesh2D" -msgstr "2D-Mesh erzeugen" +msgstr "Mesh2D erzeugen" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Polygon2D" -msgstr "Polygon3D erstellen" +msgstr "Polygon2D erzeugen" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D" -msgstr "Kollisionspolygon erzeugen" +msgstr "CollisionPolygon2D erzeugen" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D" -msgstr "Occluder-Polygon erzeugen" +msgstr "LightOccluder2D erzeugen" #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite is empty!" @@ -6737,43 +6741,36 @@ msgid "Invalid geometry, can't replace by mesh." msgstr "Ungültige Geometrie, Mesh kann nicht ersetzt werden." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create polygon." -msgstr "Ungültige Geometrie, Mesh kann nicht ersetzt werden." +msgstr "Ungültige Geometrie, Polygon kann nicht erzeugt werden." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create collision polygon." -msgstr "Ungültige Geometrie, Mesh kann nicht ersetzt werden." +msgstr "Ungültige Geometrie, Kollisionspolygon kann nicht erzeugt werden." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create light occluder." -msgstr "Ungültige Geometrie, Mesh kann nicht ersetzt werden." +msgstr "Ungültige Geometrie, Light-Occluder kann nicht erzeugt werden." #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite" msgstr "Sprite" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Mesh2D" -msgstr "Zu 2D-Mesh umwandeln" +msgstr "Zu Mesh2D umwandeln" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Polygon2D" -msgstr "Polygon verschieben" +msgstr "Zu Polygon2D umwandeln" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D Sibling" -msgstr "Kollisionspolygon erzeugen" +msgstr "CollisionPolygon2D-Nachbarn erzeugen" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D Sibling" -msgstr "Occluder-Polygon erzeugen" +msgstr "LightOccluder2D erzeugen" #: editor/plugins/sprite_editor_plugin.cpp msgid "Simplification: " @@ -7361,9 +7358,8 @@ msgid "Duplicate Nodes" msgstr "Nodes duplizieren" #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Delete Nodes" -msgstr "Node löschen" +msgstr "Nodes löschen" #: editor/plugins/visual_shader_editor_plugin.cpp msgid "Visual Shader Input Type Changed" diff --git a/editor/translations/de_CH.po b/editor/translations/de_CH.po index cf2e88000d..9be73f30db 100644 --- a/editor/translations/de_CH.po +++ b/editor/translations/de_CH.po @@ -162,11 +162,17 @@ msgid "Animation Playback Track" msgstr "Stoppe Animations-Wiedergabe. (S)" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Animations-Node" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" +msgstr "Animations-Node" + +#: editor/animation_track_editor.cpp +msgid "Add Track" msgstr "" #: editor/animation_track_editor.cpp diff --git a/editor/translations/editor.pot b/editor/translations/editor.pot index f9408cfbbc..d38ce1af81 100644 --- a/editor/translations/editor.pot +++ b/editor/translations/editor.pot @@ -146,11 +146,15 @@ msgid "Animation Playback Track" msgstr "" #: editor/animation_track_editor.cpp -msgid "Add Track" +msgid "Animation length (frames)" msgstr "" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Add Track" msgstr "" #: editor/animation_track_editor.cpp @@ -9860,7 +9864,7 @@ msgstr "" msgid "" "Container by itself serves no purpose unless a script configures it's " "children placement behavior.\n" -"If you dont't intend to add a script, then please use a plain 'Control' node " +"If you don't intend to add a script, then please use a plain 'Control' node " "instead." msgstr "" diff --git a/editor/translations/el.po b/editor/translations/el.po index b6cf0f79dc..0910fbd089 100644 --- a/editor/translations/el.po +++ b/editor/translations/el.po @@ -157,14 +157,20 @@ msgid "Animation Playback Track" msgstr "Κομμάτι αναπαÏαγωγής κίνησης" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Î Ïοσθήκη κομματιοÏ" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Μήκος κίνησης (δευτεÏόλεπτα)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Μήκος κίνησης (δευτεÏόλεπτα)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Î Ïοσθήκη κομματιοÏ" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Επανάληψη κίνησης" diff --git a/editor/translations/eo.po b/editor/translations/eo.po new file mode 100644 index 0000000000..2fe387b131 --- /dev/null +++ b/editor/translations/eo.po @@ -0,0 +1,9952 @@ +# Esperanto translation of the Godot Engine editor +# Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. +# Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) +# This file is distributed under the same license as the Godot source code. +msgid "" +msgstr "" +"Project-Id-Version: Godot Engine editor\n" +"Language-Team: Esperanto <https://hosted.weblate.org/projects/godot-engine/" +"godot/eo/>\n" +"Language: eo\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8-bit\n" + +#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp +#: modules/visual_script/visual_script_builtin_funcs.cpp +msgid "Invalid type argument to convert(), use TYPE_* constants." +msgstr "" + +#: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp +#: modules/mono/glue/gd_glue.cpp +#: modules/visual_script/visual_script_builtin_funcs.cpp +msgid "Not enough bytes for decoding bytes, or invalid format." +msgstr "" + +#: core/math/expression.cpp +msgid "Invalid input %i (not passed) in expression" +msgstr "" + +#: core/math/expression.cpp +msgid "self can't be used because instance is null (not passed)" +msgstr "" + +#: core/math/expression.cpp +msgid "Invalid operands to operator %s, %s and %s." +msgstr "" + +#: core/math/expression.cpp +msgid "Invalid index of type %s for base type %s" +msgstr "" + +#: core/math/expression.cpp +msgid "Invalid named index '%s' for base type %s" +msgstr "" + +#: core/math/expression.cpp +msgid "Invalid arguments to construct '%s'" +msgstr "" + +#: core/math/expression.cpp +msgid "On call to '%s':" +msgstr "" + +#: editor/animation_bezier_editor.cpp +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Free" +msgstr "" + +#: editor/animation_bezier_editor.cpp +msgid "Balanced" +msgstr "" + +#: editor/animation_bezier_editor.cpp +msgid "Mirror" +msgstr "" + +#: editor/animation_bezier_editor.cpp +msgid "Insert Key Here" +msgstr "" + +#: editor/animation_bezier_editor.cpp +msgid "Duplicate Selected Key(s)" +msgstr "" + +#: editor/animation_bezier_editor.cpp +msgid "Delete Selected Key(s)" +msgstr "" + +#: editor/animation_bezier_editor.cpp +msgid "Add Bezier Point" +msgstr "" + +#: editor/animation_bezier_editor.cpp +msgid "Move Bezier Points" +msgstr "" + +#: editor/animation_bezier_editor.cpp editor/animation_track_editor.cpp +msgid "Anim Duplicate Keys" +msgstr "" + +#: editor/animation_bezier_editor.cpp editor/animation_track_editor.cpp +msgid "Anim Delete Keys" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Anim Change Keyframe Time" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Anim Change Transition" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Anim Change Transform" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Anim Change Keyframe Value" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Anim Change Call" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Change Animation Length" +msgstr "" + +#: editor/animation_track_editor.cpp +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Change Animation Loop" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Property Track" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "3D Transform Track" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Call Method Track" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Bezier Curve Track" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Audio Playback Track" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Animation Playback Track" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Animation length (frames)" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Animation length (seconds)" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Animation Looping" +msgstr "" + +#: editor/animation_track_editor.cpp +#: modules/visual_script/visual_script_editor.cpp +msgid "Functions:" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Audio Clips:" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Anim Clips:" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Change Track Path" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Toggle this track on/off." +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Update Mode (How this property is set)" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Interpolation Mode" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Loop Wrap Mode (Interpolate end with beginning on loop)" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Remove this track." +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Time (s): " +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Toggle Track Enabled" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Continuous" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Discrete" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Trigger" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Capture" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Nearest" +msgstr "" + +#: editor/animation_track_editor.cpp editor/plugins/curve_editor_plugin.cpp +#: editor/property_editor.cpp +msgid "Linear" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Cubic" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Clamp Loop Interp" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Wrap Loop Interp" +msgstr "" + +#: editor/animation_track_editor.cpp +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Insert Key" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Duplicate Key(s)" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Delete Key(s)" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Change Animation Update Mode" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Change Animation Interpolation Mode" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Change Animation Loop Mode" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Remove Anim Track" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Create NEW track for %s and insert key?" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Create %d NEW tracks and insert keys?" +msgstr "" + +#: editor/animation_track_editor.cpp editor/create_dialog.cpp +#: editor/editor_audio_buses.cpp editor/editor_plugin_settings.cpp +#: editor/plugin_config_dialog.cpp +#: editor/plugins/abstract_polygon_2d_editor.cpp +#: editor/plugins/mesh_instance_editor_plugin.cpp +#: editor/plugins/particles_editor_plugin.cpp editor/script_create_dialog.cpp +msgid "Create" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Anim Insert" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "AnimationPlayer can't animate itself, only other players." +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Anim Create & Insert" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Anim Insert Track & Key" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Anim Insert Key" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Change Animation Step" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Rearrange Tracks" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Transform tracks only apply to Spatial-based nodes." +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "" +"Audio tracks can only point to nodes of type:\n" +"-AudioStreamPlayer\n" +"-AudioStreamPlayer2D\n" +"-AudioStreamPlayer3D" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Animation tracks can only point to AnimationPlayer nodes." +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "An animation player can't animate itself, only other players." +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Not possible to add a new track without a root" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Add Bezier Track" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Track path is invalid, so can't add a key." +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Track is not of type Spatial, can't insert key" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Add Transform Track Key" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Add Track Key" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Track path is invalid, so can't add a method key." +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Add Method Track Key" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Method not found in object: " +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Anim Move Keys" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Clipboard is empty" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Paste Tracks" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Anim Scale Keys" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "" +"This option does not work for Bezier editing, as it's only a single track." +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Only show tracks from nodes selected in tree." +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Group tracks by node or display them as plain list." +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Snap:" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Animation step value." +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Seconds" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "FPS" +msgstr "" + +#: editor/animation_track_editor.cpp editor/editor_properties.cpp +#: editor/plugins/polygon_2d_editor_plugin.cpp +#: editor/plugins/script_text_editor.cpp +#: editor/plugins/shader_editor_plugin.cpp editor/plugins/text_editor.cpp +#: editor/project_manager.cpp editor/project_settings_editor.cpp +#: editor/property_editor.cpp modules/visual_script/visual_script_editor.cpp +msgid "Edit" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Animation properties." +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Copy Tracks" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Scale Selection" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Scale From Cursor" +msgstr "" + +#: editor/animation_track_editor.cpp modules/gridmap/grid_map_editor_plugin.cpp +msgid "Duplicate Selection" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Duplicate Transposed" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Delete Selection" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Go to Next Step" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Go to Previous Step" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Optimize Animation" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Clean-Up Animation" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Pick the node that will be animated:" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Use Bezier Curves" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Anim. Optimizer" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Max. Linear Error:" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Max. Angular Error:" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Max Optimizable Angle:" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Optimize" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Remove invalid keys" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Remove unresolved and empty tracks" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Clean-up all animations" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Clean-Up Animation(s) (NO UNDO!)" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Clean-Up" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Scale Ratio:" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Select tracks to copy:" +msgstr "" + +#: editor/animation_track_editor.cpp editor/editor_properties.cpp +#: editor/plugins/animation_player_editor_plugin.cpp +#: editor/plugins/script_text_editor.cpp +#: editor/plugins/sprite_frames_editor_plugin.cpp editor/property_editor.cpp +#: scene/gui/line_edit.cpp scene/gui/text_edit.cpp +msgid "Copy" +msgstr "" + +#: editor/animation_track_editor_plugins.cpp +msgid "Add Audio Track Clip" +msgstr "" + +#: editor/animation_track_editor_plugins.cpp +msgid "Change Audio Track Clip Start Offset" +msgstr "" + +#: editor/animation_track_editor_plugins.cpp +msgid "Change Audio Track Clip End Offset" +msgstr "" + +#: editor/array_property_edit.cpp +msgid "Resize Array" +msgstr "" + +#: editor/array_property_edit.cpp +msgid "Change Array Value Type" +msgstr "" + +#: editor/array_property_edit.cpp +msgid "Change Array Value" +msgstr "" + +#: editor/code_editor.cpp +msgid "Go to Line" +msgstr "" + +#: editor/code_editor.cpp +msgid "Line Number:" +msgstr "" + +#: editor/code_editor.cpp editor/editor_help.cpp +msgid "No Matches" +msgstr "" + +#: editor/code_editor.cpp +msgid "Replaced %d occurrence(s)." +msgstr "" + +#: editor/code_editor.cpp editor/find_in_files.cpp +msgid "Match Case" +msgstr "" + +#: editor/code_editor.cpp editor/find_in_files.cpp +msgid "Whole Words" +msgstr "" + +#: editor/code_editor.cpp editor/rename_dialog.cpp +msgid "Replace" +msgstr "" + +#: editor/code_editor.cpp +msgid "Replace All" +msgstr "" + +#: editor/code_editor.cpp +msgid "Selection Only" +msgstr "" + +#: editor/code_editor.cpp editor/plugins/canvas_item_editor_plugin.cpp +#: editor/plugins/texture_region_editor_plugin.cpp +#: editor/plugins/tile_set_editor_plugin.cpp scene/gui/graph_edit.cpp +msgid "Zoom In" +msgstr "" + +#: editor/code_editor.cpp editor/plugins/canvas_item_editor_plugin.cpp +#: editor/plugins/texture_region_editor_plugin.cpp +#: editor/plugins/tile_set_editor_plugin.cpp scene/gui/graph_edit.cpp +msgid "Zoom Out" +msgstr "" + +#: editor/code_editor.cpp +msgid "Reset Zoom" +msgstr "" + +#: editor/code_editor.cpp modules/mono/editor/mono_bottom_panel.cpp +msgid "Warnings" +msgstr "" + +#: editor/code_editor.cpp +msgid "Line and column numbers." +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Method in target Node must be specified!" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "" +"Target method not found! Specify a valid method or attach a script to target " +"Node." +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Connect To Node:" +msgstr "" + +#: editor/connections_dialog.cpp editor/editor_autoload_settings.cpp +#: editor/groups_editor.cpp editor/plugins/item_list_editor_plugin.cpp +#: editor/plugins/theme_editor_plugin.cpp editor/project_settings_editor.cpp +msgid "Add" +msgstr "" + +#: editor/connections_dialog.cpp editor/dependency_editor.cpp +#: editor/groups_editor.cpp editor/plugins/animation_player_editor_plugin.cpp +#: editor/plugins/animation_tree_player_editor_plugin.cpp +#: editor/plugins/resource_preloader_editor_plugin.cpp +#: editor/plugins/theme_editor_plugin.cpp editor/project_manager.cpp +#: editor/project_settings_editor.cpp +msgid "Remove" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Add Extra Call Argument:" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Extra Call Arguments:" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Path to Node:" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Make Function" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Deferred" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Oneshot" +msgstr "" + +#: editor/connections_dialog.cpp editor/dependency_editor.cpp +#: editor/export_template_manager.cpp editor/groups_editor.cpp +#: editor/plugins/animation_player_editor_plugin.cpp +#: editor/plugins/asset_library_editor_plugin.cpp +#: editor/plugins/canvas_item_editor_plugin.cpp +#: editor/plugins/resource_preloader_editor_plugin.cpp +#: editor/plugins/script_editor_plugin.cpp +#: editor/plugins/sprite_frames_editor_plugin.cpp editor/project_export.cpp +#: editor/project_settings_editor.cpp editor/property_editor.cpp +#: editor/run_settings_dialog.cpp editor/settings_config_dialog.cpp +#: modules/visual_script/visual_script_editor.cpp +msgid "Close" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Connect" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Connect '%s' to '%s'" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Disconnect '%s' from '%s'" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Disconnect all from signal: '%s'" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Connect..." +msgstr "" + +#: editor/connections_dialog.cpp +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Disconnect" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Connect Signal: " +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Edit Connection: " +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Are you sure you want to remove all connections from the \"%s\" signal?" +msgstr "" + +#: editor/connections_dialog.cpp editor/editor_help.cpp editor/node_dock.cpp +msgid "Signals" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Are you sure you want to remove all connections from this signal?" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Disconnect All" +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Edit..." +msgstr "" + +#: editor/connections_dialog.cpp +msgid "Go To Method" +msgstr "" + +#: editor/create_dialog.cpp +msgid "Change %s Type" +msgstr "" + +#: editor/create_dialog.cpp editor/project_settings_editor.cpp +#: modules/visual_script/visual_script_editor.cpp +msgid "Change" +msgstr "" + +#: editor/create_dialog.cpp +msgid "Create New %s" +msgstr "" + +#: editor/create_dialog.cpp editor/editor_file_dialog.cpp +#: editor/filesystem_dock.cpp +msgid "Favorites:" +msgstr "" + +#: editor/create_dialog.cpp editor/editor_file_dialog.cpp +msgid "Recent:" +msgstr "" + +#: editor/create_dialog.cpp editor/plugins/asset_library_editor_plugin.cpp +#: editor/plugins/script_editor_plugin.cpp editor/project_manager.cpp +#: editor/property_selector.cpp editor/quick_open.cpp +#: modules/visual_script/visual_script_property_selector.cpp +msgid "Search:" +msgstr "" + +#: editor/create_dialog.cpp editor/plugins/script_editor_plugin.cpp +#: editor/property_selector.cpp editor/quick_open.cpp +#: modules/visual_script/visual_script_property_selector.cpp +msgid "Matches:" +msgstr "" + +#: editor/create_dialog.cpp editor/plugin_config_dialog.cpp +#: editor/plugins/asset_library_editor_plugin.cpp editor/property_selector.cpp +#: modules/visual_script/visual_script_property_selector.cpp +msgid "Description:" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Search Replacement For:" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Dependencies For:" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "" +"Scene '%s' is currently being edited.\n" +"Changes will not take effect unless reloaded." +msgstr "" + +#: editor/dependency_editor.cpp +msgid "" +"Resource '%s' is in use.\n" +"Changes will take effect when reloaded." +msgstr "" + +#: editor/dependency_editor.cpp +#: modules/gdnative/gdnative_library_editor_plugin.cpp +msgid "Dependencies" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Resource" +msgstr "" + +#: editor/dependency_editor.cpp editor/editor_autoload_settings.cpp +#: editor/project_settings_editor.cpp editor/script_create_dialog.cpp +msgid "Path" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Dependencies:" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Fix Broken" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Dependency Editor" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Search Replacement Resource:" +msgstr "" + +#: editor/dependency_editor.cpp editor/editor_file_dialog.cpp +#: editor/editor_help_search.cpp editor/editor_node.cpp +#: editor/filesystem_dock.cpp editor/plugins/script_editor_plugin.cpp +#: editor/property_selector.cpp editor/quick_open.cpp +#: editor/script_create_dialog.cpp +#: modules/visual_script/visual_script_property_selector.cpp +#: scene/gui/file_dialog.cpp +msgid "Open" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Owners Of:" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Remove selected files from the project? (no undo)" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "" +"The files being removed are required by other resources in order for them to " +"work.\n" +"Remove them anyway? (no undo)" +msgstr "" + +#: editor/dependency_editor.cpp editor/export_template_manager.cpp +msgid "Cannot remove:" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Error loading:" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Load failed due to missing dependencies:" +msgstr "" + +#: editor/dependency_editor.cpp editor/editor_node.cpp +msgid "Open Anyway" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Which action should be taken?" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Fix Dependencies" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Errors loading!" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Permanently delete %d item(s)? (No undo!)" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Owns" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Resources Without Explicit Ownership:" +msgstr "" + +#: editor/dependency_editor.cpp editor/editor_node.cpp +msgid "Orphan Resource Explorer" +msgstr "" + +#: editor/dependency_editor.cpp +msgid "Delete selected files?" +msgstr "" + +#: editor/dependency_editor.cpp editor/editor_audio_buses.cpp +#: editor/editor_file_dialog.cpp editor/editor_node.cpp +#: editor/filesystem_dock.cpp editor/plugins/item_list_editor_plugin.cpp +#: editor/plugins/sprite_frames_editor_plugin.cpp editor/project_export.cpp +#: editor/project_settings_editor.cpp editor/scene_tree_dock.cpp +msgid "Delete" +msgstr "" + +#: editor/dictionary_property_edit.cpp +msgid "Change Dictionary Key" +msgstr "" + +#: editor/dictionary_property_edit.cpp +msgid "Change Dictionary Value" +msgstr "" + +#: editor/editor_about.cpp +msgid "Thanks from the Godot community!" +msgstr "" + +#: editor/editor_about.cpp +msgid "Godot Engine contributors" +msgstr "" + +#: editor/editor_about.cpp +msgid "Project Founders" +msgstr "" + +#: editor/editor_about.cpp +msgid "Lead Developer" +msgstr "" + +#: editor/editor_about.cpp +msgid "Project Manager " +msgstr "" + +#: editor/editor_about.cpp +msgid "Developers" +msgstr "" + +#: editor/editor_about.cpp +msgid "Authors" +msgstr "" + +#: editor/editor_about.cpp +msgid "Platinum Sponsors" +msgstr "" + +#: editor/editor_about.cpp +msgid "Gold Sponsors" +msgstr "" + +#: editor/editor_about.cpp +msgid "Mini Sponsors" +msgstr "" + +#: editor/editor_about.cpp +msgid "Gold Donors" +msgstr "" + +#: editor/editor_about.cpp +msgid "Silver Donors" +msgstr "" + +#: editor/editor_about.cpp +msgid "Bronze Donors" +msgstr "" + +#: editor/editor_about.cpp +msgid "Donors" +msgstr "" + +#: editor/editor_about.cpp +msgid "License" +msgstr "" + +#: editor/editor_about.cpp +msgid "Thirdparty License" +msgstr "" + +#: editor/editor_about.cpp +msgid "" +"Godot Engine relies on a number of thirdparty free and open source " +"libraries, all compatible with the terms of its MIT license. The following " +"is an exhaustive list of all such thirdparty components with their " +"respective copyright statements and license terms." +msgstr "" + +#: editor/editor_about.cpp +msgid "All Components" +msgstr "" + +#: editor/editor_about.cpp +msgid "Components" +msgstr "" + +#: editor/editor_about.cpp +msgid "Licenses" +msgstr "" + +#: editor/editor_asset_installer.cpp editor/project_manager.cpp +msgid "Error opening package file, not in zip format." +msgstr "" + +#: editor/editor_asset_installer.cpp +msgid "Uncompressing Assets" +msgstr "" + +#: editor/editor_asset_installer.cpp editor/project_manager.cpp +msgid "Package installed successfully!" +msgstr "" + +#: editor/editor_asset_installer.cpp +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Success!" +msgstr "" + +#: editor/editor_asset_installer.cpp +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Install" +msgstr "" + +#: editor/editor_asset_installer.cpp +msgid "Package Installer" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Speakers" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Add Effect" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Rename Audio Bus" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Change Audio Bus Volume" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Toggle Audio Bus Solo" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Toggle Audio Bus Mute" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Toggle Audio Bus Bypass Effects" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Select Audio Bus Send" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Add Audio Bus Effect" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Move Bus Effect" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Delete Bus Effect" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Audio Bus, Drag and Drop to rearrange." +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Solo" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Mute" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Bypass" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Bus options" +msgstr "" + +#: editor/editor_audio_buses.cpp editor/filesystem_dock.cpp +#: editor/plugins/animation_player_editor_plugin.cpp editor/scene_tree_dock.cpp +msgid "Duplicate" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Reset Volume" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Delete Effect" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Audio" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Add Audio Bus" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Master bus can't be deleted!" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Delete Audio Bus" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Duplicate Audio Bus" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Reset Bus Volume" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Move Audio Bus" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Save Audio Bus Layout As..." +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Location for New Layout..." +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Open Audio Bus Layout" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "There is no 'res://default_bus_layout.tres' file." +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Invalid file, not an audio bus layout." +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Add Bus" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Add a new Audio Bus to this layout." +msgstr "" + +#: editor/editor_audio_buses.cpp editor/editor_properties.cpp +#: editor/plugins/animation_player_editor_plugin.cpp editor/property_editor.cpp +#: editor/script_create_dialog.cpp +msgid "Load" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Load an existing Bus Layout." +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Save As" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Save this Bus Layout to a file." +msgstr "" + +#: editor/editor_audio_buses.cpp editor/import_dock.cpp +msgid "Load Default" +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Load the default Bus Layout." +msgstr "" + +#: editor/editor_audio_buses.cpp +msgid "Create a new Bus Layout." +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Invalid name." +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Valid characters:" +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Invalid name. Must not collide with an existing engine class name." +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Invalid name. Must not collide with an existing buit-in type name." +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Invalid name. Must not collide with an existing global constant name." +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Autoload '%s' already exists!" +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Rename Autoload" +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Toggle AutoLoad Globals" +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Move Autoload" +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Remove Autoload" +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Enable" +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Rearrange Autoloads" +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Invalid Path." +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "File does not exist." +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Not in resource path." +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Add AutoLoad" +msgstr "" + +#: editor/editor_autoload_settings.cpp editor/editor_file_dialog.cpp +#: editor/plugins/animation_tree_editor_plugin.cpp scene/gui/file_dialog.cpp +msgid "Path:" +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Node Name:" +msgstr "" + +#: editor/editor_autoload_settings.cpp editor/editor_help_search.cpp +#: editor/editor_profiler.cpp editor/settings_config_dialog.cpp +msgid "Name" +msgstr "" + +#: editor/editor_autoload_settings.cpp +msgid "Singleton" +msgstr "" + +#: editor/editor_data.cpp +msgid "Updating Scene" +msgstr "" + +#: editor/editor_data.cpp +msgid "Storing local changes..." +msgstr "" + +#: editor/editor_data.cpp +msgid "Updating scene..." +msgstr "" + +#: editor/editor_data.cpp editor/editor_properties.cpp +msgid "[empty]" +msgstr "" + +#: editor/editor_data.cpp +msgid "[unsaved]" +msgstr "" + +#: editor/editor_dir_dialog.cpp +msgid "Please select a base directory first" +msgstr "" + +#: editor/editor_dir_dialog.cpp +msgid "Choose a Directory" +msgstr "" + +#: editor/editor_dir_dialog.cpp editor/editor_file_dialog.cpp +#: editor/filesystem_dock.cpp scene/gui/file_dialog.cpp +msgid "Create Folder" +msgstr "" + +#: editor/editor_dir_dialog.cpp editor/editor_file_dialog.cpp +#: editor/editor_plugin_settings.cpp editor/filesystem_dock.cpp +#: editor/plugins/theme_editor_plugin.cpp editor/project_export.cpp +#: scene/gui/file_dialog.cpp +msgid "Name:" +msgstr "" + +#: editor/editor_dir_dialog.cpp editor/editor_file_dialog.cpp +#: editor/filesystem_dock.cpp scene/gui/file_dialog.cpp +msgid "Could not create folder." +msgstr "" + +#: editor/editor_dir_dialog.cpp +msgid "Choose" +msgstr "" + +#: editor/editor_export.cpp +msgid "Storing File:" +msgstr "" + +#: editor/editor_export.cpp +msgid "No export template found at the expected path:" +msgstr "" + +#: editor/editor_export.cpp +msgid "Packing" +msgstr "" + +#: editor/editor_export.cpp +msgid "" +"Target platform requires 'ETC' texture compression for GLES2. Enable 'Import " +"Etc' in Project Settings." +msgstr "" + +#: editor/editor_export.cpp +msgid "" +"Target platform requires 'ETC2' texture compression for GLES3. Enable " +"'Import Etc 2' in Project Settings." +msgstr "" + +#: editor/editor_export.cpp +msgid "" +"Target platform requires 'ETC' texture compression for the driver fallback " +"to GLES2.\n" +"Enable 'Import Etc' in Project Settings, or disable 'Driver Fallback " +"Enabled'." +msgstr "" + +#: editor/editor_export.cpp platform/android/export/export.cpp +#: platform/iphone/export/export.cpp platform/javascript/export/export.cpp +#: platform/osx/export/export.cpp platform/uwp/export/export.cpp +msgid "Custom debug template not found." +msgstr "" + +#: editor/editor_export.cpp platform/android/export/export.cpp +#: platform/iphone/export/export.cpp platform/javascript/export/export.cpp +#: platform/osx/export/export.cpp platform/uwp/export/export.cpp +msgid "Custom release template not found." +msgstr "" + +#: editor/editor_export.cpp platform/javascript/export/export.cpp +msgid "Template file not found:" +msgstr "" + +#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp +msgid "Select Current Folder" +msgstr "" + +#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp +msgid "File Exists, Overwrite?" +msgstr "" + +#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp +msgid "Select This Folder" +msgstr "" + +#: editor/editor_file_dialog.cpp editor/filesystem_dock.cpp +msgid "Copy Path" +msgstr "" + +#: editor/editor_file_dialog.cpp editor/filesystem_dock.cpp +msgid "Open in File Manager" +msgstr "" + +#: editor/editor_file_dialog.cpp editor/filesystem_dock.cpp +#: editor/project_manager.cpp +msgid "Show in File Manager" +msgstr "" + +#: editor/editor_file_dialog.cpp editor/filesystem_dock.cpp +msgid "New Folder..." +msgstr "" + +#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp +msgid "Refresh" +msgstr "" + +#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp +msgid "All Recognized" +msgstr "" + +#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp +msgid "All Files (*)" +msgstr "" + +#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp +msgid "Open a File" +msgstr "" + +#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp +msgid "Open File(s)" +msgstr "" + +#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp +msgid "Open a Directory" +msgstr "" + +#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp +msgid "Open a File or Directory" +msgstr "" + +#: editor/editor_file_dialog.cpp editor/editor_node.cpp +#: editor/editor_properties.cpp editor/inspector_dock.cpp +#: editor/plugins/animation_player_editor_plugin.cpp +#: editor/plugins/script_editor_plugin.cpp scene/gui/file_dialog.cpp +msgid "Save" +msgstr "" + +#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp +msgid "Save a File" +msgstr "" + +#: editor/editor_file_dialog.cpp +msgid "Go Back" +msgstr "" + +#: editor/editor_file_dialog.cpp +msgid "Go Forward" +msgstr "" + +#: editor/editor_file_dialog.cpp +msgid "Go Up" +msgstr "" + +#: editor/editor_file_dialog.cpp +msgid "Toggle Hidden Files" +msgstr "" + +#: editor/editor_file_dialog.cpp +msgid "Toggle Favorite" +msgstr "" + +#: editor/editor_file_dialog.cpp +msgid "Toggle Mode" +msgstr "" + +#: editor/editor_file_dialog.cpp +msgid "Focus Path" +msgstr "" + +#: editor/editor_file_dialog.cpp +msgid "Move Favorite Up" +msgstr "" + +#: editor/editor_file_dialog.cpp +msgid "Move Favorite Down" +msgstr "" + +#: editor/editor_file_dialog.cpp +msgid "Previous Folder" +msgstr "" + +#: editor/editor_file_dialog.cpp +msgid "Next Folder" +msgstr "" + +#: editor/editor_file_dialog.cpp +msgid "Go to parent folder" +msgstr "" + +#: editor/editor_file_dialog.cpp +msgid "(Un)favorite current folder." +msgstr "" + +#: editor/editor_file_dialog.cpp editor/filesystem_dock.cpp +msgid "View items as a grid of thumbnails." +msgstr "" + +#: editor/editor_file_dialog.cpp editor/filesystem_dock.cpp +msgid "View items as a list." +msgstr "" + +#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp +msgid "Directories & Files:" +msgstr "" + +#: editor/editor_file_dialog.cpp editor/plugins/sprite_editor_plugin.cpp +#: editor/plugins/style_box_editor_plugin.cpp +msgid "Preview:" +msgstr "" + +#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp +msgid "File:" +msgstr "" + +#: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp +msgid "Must use a valid extension." +msgstr "" + +#: editor/editor_file_system.cpp +msgid "ScanSources" +msgstr "" + +#: editor/editor_file_system.cpp +msgid "(Re)Importing Assets" +msgstr "" + +#: editor/editor_help.cpp editor/plugins/spatial_editor_plugin.cpp +msgid "Top" +msgstr "" + +#: editor/editor_help.cpp +msgid "Class:" +msgstr "" + +#: editor/editor_help.cpp editor/scene_tree_editor.cpp +msgid "Inherits:" +msgstr "" + +#: editor/editor_help.cpp +msgid "Inherited by:" +msgstr "" + +#: editor/editor_help.cpp +msgid "Brief Description:" +msgstr "" + +#: editor/editor_help.cpp +msgid "Properties" +msgstr "" + +#: editor/editor_help.cpp +msgid "Properties:" +msgstr "" + +#: editor/editor_help.cpp +msgid "Methods" +msgstr "" + +#: editor/editor_help.cpp +msgid "Methods:" +msgstr "" + +#: editor/editor_help.cpp +msgid "Theme Properties" +msgstr "" + +#: editor/editor_help.cpp +msgid "Theme Properties:" +msgstr "" + +#: editor/editor_help.cpp modules/visual_script/visual_script_editor.cpp +msgid "Signals:" +msgstr "" + +#: editor/editor_help.cpp +msgid "Enumerations" +msgstr "" + +#: editor/editor_help.cpp +msgid "Enumerations:" +msgstr "" + +#: editor/editor_help.cpp +msgid "enum " +msgstr "" + +#: editor/editor_help.cpp +msgid "Constants" +msgstr "" + +#: editor/editor_help.cpp +msgid "Constants:" +msgstr "" + +#: editor/editor_help.cpp +msgid "Class Description" +msgstr "" + +#: editor/editor_help.cpp +msgid "Class Description:" +msgstr "" + +#: editor/editor_help.cpp +msgid "Online Tutorials:" +msgstr "" + +#: editor/editor_help.cpp +msgid "" +"There are currently no tutorials for this class, you can [color=$color][url=" +"$url]contribute one[/url][/color] or [color=$color][url=$url2]request one[/" +"url][/color]." +msgstr "" + +#: editor/editor_help.cpp +msgid "Property Descriptions" +msgstr "" + +#: editor/editor_help.cpp +msgid "Property Descriptions:" +msgstr "" + +#: editor/editor_help.cpp +msgid "" +"There is currently no description for this property. Please help us by " +"[color=$color][url=$url]contributing one[/url][/color]!" +msgstr "" + +#: editor/editor_help.cpp +msgid "Method Descriptions" +msgstr "" + +#: editor/editor_help.cpp +msgid "Method Descriptions:" +msgstr "" + +#: editor/editor_help.cpp +msgid "" +"There is currently no description for this method. Please help us by [color=" +"$color][url=$url]contributing one[/url][/color]!" +msgstr "" + +#: editor/editor_help_search.cpp editor/editor_node.cpp +#: editor/plugins/script_editor_plugin.cpp +msgid "Search Help" +msgstr "" + +#: editor/editor_help_search.cpp +msgid "Display All" +msgstr "" + +#: editor/editor_help_search.cpp +msgid "Classes Only" +msgstr "" + +#: editor/editor_help_search.cpp +msgid "Methods Only" +msgstr "" + +#: editor/editor_help_search.cpp +msgid "Signals Only" +msgstr "" + +#: editor/editor_help_search.cpp +msgid "Constants Only" +msgstr "" + +#: editor/editor_help_search.cpp +msgid "Properties Only" +msgstr "" + +#: editor/editor_help_search.cpp +msgid "Theme Properties Only" +msgstr "" + +#: editor/editor_help_search.cpp +msgid "Member Type" +msgstr "" + +#: editor/editor_help_search.cpp +msgid "Class" +msgstr "" + +#: editor/editor_inspector.cpp editor/project_settings_editor.cpp +msgid "Property:" +msgstr "" + +#: editor/editor_inspector.cpp +msgid "Set" +msgstr "" + +#: editor/editor_inspector.cpp +msgid "Set Multiple:" +msgstr "" + +#: editor/editor_log.cpp +msgid "Output:" +msgstr "" + +#: editor/editor_log.cpp editor/editor_profiler.cpp +#: editor/editor_properties.cpp +#: editor/plugins/animation_tree_player_editor_plugin.cpp +#: editor/property_editor.cpp editor/scene_tree_dock.cpp +#: editor/script_editor_debugger.cpp +#: modules/gdnative/gdnative_library_editor_plugin.cpp scene/gui/line_edit.cpp +#: scene/gui/text_edit.cpp +msgid "Clear" +msgstr "" + +#: editor/editor_log.cpp +msgid "Clear Output" +msgstr "" + +#: editor/editor_node.cpp +msgid "Project export failed with error code %d." +msgstr "" + +#: editor/editor_node.cpp +msgid "Imported resources can't be saved." +msgstr "" + +#: editor/editor_node.cpp editor/plugins/script_editor_plugin.cpp +#: scene/gui/dialogs.cpp +msgid "OK" +msgstr "" + +#: editor/editor_node.cpp editor/plugins/animation_player_editor_plugin.cpp +msgid "Error saving resource!" +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"This resource can't be saved because it does not belong to the edited scene. " +"Make it unique first." +msgstr "" + +#: editor/editor_node.cpp editor/plugins/animation_player_editor_plugin.cpp +msgid "Save Resource As..." +msgstr "" + +#: editor/editor_node.cpp +msgid "Can't open file for writing:" +msgstr "" + +#: editor/editor_node.cpp +msgid "Requested file format unknown:" +msgstr "" + +#: editor/editor_node.cpp +msgid "Error while saving." +msgstr "" + +#: editor/editor_node.cpp editor/plugins/script_editor_plugin.cpp +msgid "Can't open '%s'. The file could have been moved or deleted." +msgstr "" + +#: editor/editor_node.cpp +msgid "Error while parsing '%s'." +msgstr "" + +#: editor/editor_node.cpp +msgid "Unexpected end of file '%s'." +msgstr "" + +#: editor/editor_node.cpp +msgid "Missing '%s' or its dependencies." +msgstr "" + +#: editor/editor_node.cpp +msgid "Error while loading '%s'." +msgstr "" + +#: editor/editor_node.cpp +msgid "Saving Scene" +msgstr "" + +#: editor/editor_node.cpp +msgid "Analyzing" +msgstr "" + +#: editor/editor_node.cpp +msgid "Creating Thumbnail" +msgstr "" + +#: editor/editor_node.cpp +msgid "This operation can't be done without a tree root." +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"This scene can't be saved because there is a cyclic instancing inclusion.\n" +"Please resolve it and then attempt to save again." +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"Couldn't save scene. Likely dependencies (instances or inheritance) couldn't " +"be satisfied." +msgstr "" + +#: editor/editor_node.cpp editor/scene_tree_dock.cpp +msgid "Can't overwrite scene that is still open!" +msgstr "" + +#: editor/editor_node.cpp +msgid "Can't load MeshLibrary for merging!" +msgstr "" + +#: editor/editor_node.cpp +msgid "Error saving MeshLibrary!" +msgstr "" + +#: editor/editor_node.cpp +msgid "Can't load TileSet for merging!" +msgstr "" + +#: editor/editor_node.cpp +msgid "Error saving TileSet!" +msgstr "" + +#: editor/editor_node.cpp +msgid "Error trying to save layout!" +msgstr "" + +#: editor/editor_node.cpp +msgid "Default editor layout overridden." +msgstr "" + +#: editor/editor_node.cpp +msgid "Layout name not found!" +msgstr "" + +#: editor/editor_node.cpp +msgid "Restored default layout to base settings." +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"This resource belongs to a scene that was imported, so it's not editable.\n" +"Please read the documentation relevant to importing scenes to better " +"understand this workflow." +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"This resource belongs to a scene that was instanced or inherited.\n" +"Changes to it will not be kept when saving the current scene." +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"This resource was imported, so it's not editable. Change its settings in the " +"import panel and then re-import." +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"This scene was imported, so changes to it will not be kept.\n" +"Instancing it or inheriting will allow making changes to it.\n" +"Please read the documentation relevant to importing scenes to better " +"understand this workflow." +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"This is a remote object so changes to it will not be kept.\n" +"Please read the documentation relevant to debugging to better understand " +"this workflow." +msgstr "" + +#: editor/editor_node.cpp +msgid "There is no defined scene to run." +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"No main scene has ever been defined, select one?\n" +"You can change it later in \"Project Settings\" under the 'application' " +"category." +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"Selected scene '%s' does not exist, select a valid one?\n" +"You can change it later in \"Project Settings\" under the 'application' " +"category." +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"Selected scene '%s' is not a scene file, select a valid one?\n" +"You can change it later in \"Project Settings\" under the 'application' " +"category." +msgstr "" + +#: editor/editor_node.cpp +msgid "Current scene was never saved, please save it prior to running." +msgstr "" + +#: editor/editor_node.cpp +msgid "Could not start subprocess!" +msgstr "" + +#: editor/editor_node.cpp +msgid "Open Scene" +msgstr "" + +#: editor/editor_node.cpp +msgid "Open Base Scene" +msgstr "" + +#: editor/editor_node.cpp +msgid "Quick Open Scene..." +msgstr "" + +#: editor/editor_node.cpp +msgid "Quick Open Script..." +msgstr "" + +#: editor/editor_node.cpp +msgid "Save & Close" +msgstr "" + +#: editor/editor_node.cpp +msgid "Save changes to '%s' before closing?" +msgstr "" + +#: editor/editor_node.cpp +msgid "Saved %s modified resource(s)." +msgstr "" + +#: editor/editor_node.cpp +msgid "A root node is required to save the scene." +msgstr "" + +#: editor/editor_node.cpp +msgid "Save Scene As..." +msgstr "" + +#: editor/editor_node.cpp +msgid "No" +msgstr "" + +#: editor/editor_node.cpp +msgid "Yes" +msgstr "" + +#: editor/editor_node.cpp +msgid "This scene has never been saved. Save before running?" +msgstr "" + +#: editor/editor_node.cpp editor/scene_tree_dock.cpp +msgid "This operation can't be done without a scene." +msgstr "" + +#: editor/editor_node.cpp +msgid "Export Mesh Library" +msgstr "" + +#: editor/editor_node.cpp +msgid "This operation can't be done without a root node." +msgstr "" + +#: editor/editor_node.cpp +msgid "Export Tile Set" +msgstr "" + +#: editor/editor_node.cpp +msgid "This operation can't be done without a selected node." +msgstr "" + +#: editor/editor_node.cpp +msgid "Current scene not saved. Open anyway?" +msgstr "" + +#: editor/editor_node.cpp +msgid "Can't reload a scene that was never saved." +msgstr "" + +#: editor/editor_node.cpp +msgid "Revert" +msgstr "" + +#: editor/editor_node.cpp +msgid "This action cannot be undone. Revert anyway?" +msgstr "" + +#: editor/editor_node.cpp +msgid "Quick Run Scene..." +msgstr "" + +#: editor/editor_node.cpp +msgid "Quit" +msgstr "" + +#: editor/editor_node.cpp +msgid "Exit the editor?" +msgstr "" + +#: editor/editor_node.cpp +msgid "Open Project Manager?" +msgstr "" + +#: editor/editor_node.cpp +msgid "Save & Quit" +msgstr "" + +#: editor/editor_node.cpp +msgid "Save changes to the following scene(s) before quitting?" +msgstr "" + +#: editor/editor_node.cpp +msgid "Save changes the following scene(s) before opening Project Manager?" +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"This option is deprecated. Situations where refresh must be forced are now " +"considered a bug. Please report." +msgstr "" + +#: editor/editor_node.cpp +msgid "Pick a Main Scene" +msgstr "" + +#: editor/editor_node.cpp +msgid "Unable to enable addon plugin at: '%s' parsing of config failed." +msgstr "" + +#: editor/editor_node.cpp +msgid "Unable to find script field for addon plugin at: 'res://addons/%s'." +msgstr "" + +#: editor/editor_node.cpp +msgid "Unable to load addon script from path: '%s'." +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"Unable to load addon script from path: '%s' There seems to be an error in " +"the code, please check the syntax." +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"Unable to load addon script from path: '%s' Base type is not EditorPlugin." +msgstr "" + +#: editor/editor_node.cpp +msgid "Unable to load addon script from path: '%s' Script is not in tool mode." +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"Scene '%s' was automatically imported, so it can't be modified.\n" +"To make changes to it, a new inherited scene can be created." +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"Error loading scene, it must be inside the project path. Use 'Import' to " +"open the scene, then save it inside the project path." +msgstr "" + +#: editor/editor_node.cpp +msgid "Scene '%s' has broken dependencies:" +msgstr "" + +#: editor/editor_node.cpp +msgid "Clear Recent Scenes" +msgstr "" + +#: editor/editor_node.cpp +msgid "Save Layout" +msgstr "" + +#: editor/editor_node.cpp +msgid "Delete Layout" +msgstr "" + +#: editor/editor_node.cpp editor/import_dock.cpp +#: editor/script_create_dialog.cpp +msgid "Default" +msgstr "" + +#: editor/editor_node.cpp editor/editor_properties.cpp +#: editor/plugins/script_editor_plugin.cpp editor/property_editor.cpp +msgid "Show in FileSystem" +msgstr "" + +#: editor/editor_node.cpp +msgid "Play This Scene" +msgstr "" + +#: editor/editor_node.cpp +msgid "Close Tab" +msgstr "" + +#: editor/editor_node.cpp +msgid "Switch Scene Tab" +msgstr "" + +#: editor/editor_node.cpp +msgid "%d more files or folders" +msgstr "" + +#: editor/editor_node.cpp +msgid "%d more folders" +msgstr "" + +#: editor/editor_node.cpp +msgid "%d more files" +msgstr "" + +#: editor/editor_node.cpp +msgid "Dock Position" +msgstr "" + +#: editor/editor_node.cpp +msgid "Distraction Free Mode" +msgstr "" + +#: editor/editor_node.cpp +msgid "Toggle distraction-free mode." +msgstr "" + +#: editor/editor_node.cpp +msgid "Add a new scene." +msgstr "" + +#: editor/editor_node.cpp +msgid "Scene" +msgstr "" + +#: editor/editor_node.cpp +msgid "Go to previously opened scene." +msgstr "" + +#: editor/editor_node.cpp +msgid "Next tab" +msgstr "" + +#: editor/editor_node.cpp +msgid "Previous tab" +msgstr "" + +#: editor/editor_node.cpp +msgid "Filter Files..." +msgstr "" + +#: editor/editor_node.cpp +msgid "Operations with scene files." +msgstr "" + +#: editor/editor_node.cpp +msgid "New Scene" +msgstr "" + +#: editor/editor_node.cpp +msgid "New Inherited Scene..." +msgstr "" + +#: editor/editor_node.cpp +msgid "Open Scene..." +msgstr "" + +#: editor/editor_node.cpp +msgid "Save Scene" +msgstr "" + +#: editor/editor_node.cpp +msgid "Save All Scenes" +msgstr "" + +#: editor/editor_node.cpp +msgid "Close Scene" +msgstr "" + +#: editor/editor_node.cpp editor/plugins/script_editor_plugin.cpp +msgid "Open Recent" +msgstr "" + +#: editor/editor_node.cpp +msgid "Convert To..." +msgstr "" + +#: editor/editor_node.cpp +msgid "MeshLibrary..." +msgstr "" + +#: editor/editor_node.cpp +msgid "TileSet..." +msgstr "" + +#: editor/editor_node.cpp editor/plugins/script_text_editor.cpp +#: scene/gui/line_edit.cpp scene/gui/text_edit.cpp +msgid "Undo" +msgstr "" + +#: editor/editor_node.cpp editor/plugins/script_text_editor.cpp +#: scene/gui/line_edit.cpp scene/gui/text_edit.cpp +msgid "Redo" +msgstr "" + +#: editor/editor_node.cpp +msgid "Revert Scene" +msgstr "" + +#: editor/editor_node.cpp +msgid "Miscellaneous project or scene-wide tools." +msgstr "" + +#: editor/editor_node.cpp +msgid "Project" +msgstr "" + +#: editor/editor_node.cpp +msgid "Project Settings" +msgstr "" + +#: editor/editor_node.cpp editor/project_export.cpp +msgid "Export" +msgstr "" + +#: editor/editor_node.cpp editor/plugins/tile_set_editor_plugin.cpp +msgid "Tools" +msgstr "" + +#: editor/editor_node.cpp +msgid "Open Project Data Folder" +msgstr "" + +#: editor/editor_node.cpp +msgid "Quit to Project List" +msgstr "" + +#: editor/editor_node.cpp editor/plugins/script_editor_plugin.cpp +#: editor/project_export.cpp +msgid "Debug" +msgstr "" + +#: editor/editor_node.cpp +msgid "Deploy with Remote Debug" +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"When exporting or deploying, the resulting executable will attempt to " +"connect to the IP of this computer in order to be debugged." +msgstr "" + +#: editor/editor_node.cpp +msgid "Small Deploy with Network FS" +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"When this option is enabled, export or deploy will produce a minimal " +"executable.\n" +"The filesystem will be provided from the project by the editor over the " +"network.\n" +"On Android, deploy will use the USB cable for faster performance. This " +"option speeds up testing for games with a large footprint." +msgstr "" + +#: editor/editor_node.cpp +msgid "Visible Collision Shapes" +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"Collision shapes and raycast nodes (for 2D and 3D) will be visible on the " +"running game if this option is turned on." +msgstr "" + +#: editor/editor_node.cpp +msgid "Visible Navigation" +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"Navigation meshes and polygons will be visible on the running game if this " +"option is turned on." +msgstr "" + +#: editor/editor_node.cpp +msgid "Sync Scene Changes" +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"When this option is turned on, any changes made to the scene in the editor " +"will be replicated in the running game.\n" +"When used remotely on a device, this is more efficient with network " +"filesystem." +msgstr "" + +#: editor/editor_node.cpp +msgid "Sync Script Changes" +msgstr "" + +#: editor/editor_node.cpp +msgid "" +"When this option is turned on, any script that is saved will be reloaded on " +"the running game.\n" +"When used remotely on a device, this is more efficient with network " +"filesystem." +msgstr "" + +#: editor/editor_node.cpp +msgid "Editor" +msgstr "" + +#: editor/editor_node.cpp editor/settings_config_dialog.cpp +msgid "Editor Settings" +msgstr "" + +#: editor/editor_node.cpp +msgid "Editor Layout" +msgstr "" + +#: editor/editor_node.cpp +msgid "Toggle Fullscreen" +msgstr "" + +#: editor/editor_node.cpp +msgid "Open Editor Data/Settings Folder" +msgstr "" + +#: editor/editor_node.cpp +msgid "Open Editor Data Folder" +msgstr "" + +#: editor/editor_node.cpp +msgid "Open Editor Settings Folder" +msgstr "" + +#: editor/editor_node.cpp editor/project_export.cpp +msgid "Manage Export Templates" +msgstr "" + +#: editor/editor_node.cpp +msgid "Help" +msgstr "" + +#: editor/editor_node.cpp editor/plugins/asset_library_editor_plugin.cpp +#: editor/plugins/script_editor_plugin.cpp +#: editor/plugins/script_text_editor.cpp +#: editor/plugins/shader_editor_plugin.cpp editor/plugins/text_editor.cpp +#: editor/project_settings_editor.cpp editor/rename_dialog.cpp +msgid "Search" +msgstr "" + +#: editor/editor_node.cpp editor/plugins/script_editor_plugin.cpp +msgid "Online Docs" +msgstr "" + +#: editor/editor_node.cpp +msgid "Q&A" +msgstr "" + +#: editor/editor_node.cpp +msgid "Issue Tracker" +msgstr "" + +#: editor/editor_node.cpp editor/plugins/asset_library_editor_plugin.cpp +msgid "Community" +msgstr "" + +#: editor/editor_node.cpp +msgid "About" +msgstr "" + +#: editor/editor_node.cpp +msgid "Play the project." +msgstr "" + +#: editor/editor_node.cpp +msgid "Play" +msgstr "" + +#: editor/editor_node.cpp +msgid "Pause the scene" +msgstr "" + +#: editor/editor_node.cpp +msgid "Pause Scene" +msgstr "" + +#: editor/editor_node.cpp +msgid "Stop the scene." +msgstr "" + +#: editor/editor_node.cpp editor/editor_profiler.cpp +msgid "Stop" +msgstr "" + +#: editor/editor_node.cpp +msgid "Play the edited scene." +msgstr "" + +#: editor/editor_node.cpp +msgid "Play Scene" +msgstr "" + +#: editor/editor_node.cpp +msgid "Play custom scene" +msgstr "" + +#: editor/editor_node.cpp +msgid "Play Custom Scene" +msgstr "" + +#: editor/editor_node.cpp +msgid "Changing the video driver requires restarting the editor." +msgstr "" + +#: editor/editor_node.cpp editor/project_settings_editor.cpp +#: editor/settings_config_dialog.cpp +msgid "Save & Restart" +msgstr "" + +#: editor/editor_node.cpp +msgid "Spins when the editor window redraws." +msgstr "" + +#: editor/editor_node.cpp +msgid "Update Always" +msgstr "" + +#: editor/editor_node.cpp +msgid "Update Changes" +msgstr "" + +#: editor/editor_node.cpp +msgid "Disable Update Spinner" +msgstr "" + +#: editor/editor_node.cpp editor/plugins/asset_library_editor_plugin.cpp +#: editor/project_manager.cpp +msgid "Import" +msgstr "" + +#: editor/editor_node.cpp +msgid "FileSystem" +msgstr "" + +#: editor/editor_node.cpp +msgid "Inspector" +msgstr "" + +#: editor/editor_node.cpp +msgid "Node" +msgstr "" + +#: editor/editor_node.cpp +msgid "Expand Bottom Panel" +msgstr "" + +#: editor/editor_node.cpp scene/resources/visual_shader.cpp +msgid "Output" +msgstr "" + +#: editor/editor_node.cpp +msgid "Don't Save" +msgstr "" + +#: editor/editor_node.cpp +msgid "Import Templates From ZIP File" +msgstr "" + +#: editor/editor_node.cpp editor/project_export.cpp +msgid "Export Project" +msgstr "" + +#: editor/editor_node.cpp +msgid "Export Library" +msgstr "" + +#: editor/editor_node.cpp +msgid "Merge With Existing" +msgstr "" + +#: editor/editor_node.cpp +msgid "Password:" +msgstr "" + +#: editor/editor_node.cpp +msgid "Open & Run a Script" +msgstr "" + +#: editor/editor_node.cpp +msgid "New Inherited" +msgstr "" + +#: editor/editor_node.cpp +msgid "Load Errors" +msgstr "" + +#: editor/editor_node.cpp editor/plugins/tile_map_editor_plugin.cpp +msgid "Select" +msgstr "" + +#: editor/editor_node.cpp +msgid "Open 2D Editor" +msgstr "" + +#: editor/editor_node.cpp +msgid "Open 3D Editor" +msgstr "" + +#: editor/editor_node.cpp +msgid "Open Script Editor" +msgstr "" + +#: editor/editor_node.cpp editor/project_manager.cpp +msgid "Open Asset Library" +msgstr "" + +#: editor/editor_node.cpp +msgid "Open the next Editor" +msgstr "" + +#: editor/editor_node.cpp +msgid "Open the previous Editor" +msgstr "" + +#: editor/editor_plugin.cpp +msgid "Creating Mesh Previews" +msgstr "" + +#: editor/editor_plugin.cpp +msgid "Thumbnail..." +msgstr "" + +#: editor/editor_plugin_settings.cpp +msgid "Edit Plugin" +msgstr "" + +#: editor/editor_plugin_settings.cpp +msgid "Installed Plugins:" +msgstr "" + +#: editor/editor_plugin_settings.cpp editor/plugin_config_dialog.cpp +msgid "Update" +msgstr "" + +#: editor/editor_plugin_settings.cpp editor/plugin_config_dialog.cpp +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Version:" +msgstr "" + +#: editor/editor_plugin_settings.cpp editor/plugin_config_dialog.cpp +msgid "Author:" +msgstr "" + +#: editor/editor_plugin_settings.cpp +msgid "Status:" +msgstr "" + +#: editor/editor_plugin_settings.cpp +msgid "Edit:" +msgstr "" + +#: editor/editor_profiler.cpp editor/plugins/animation_state_machine_editor.cpp +#: editor/rename_dialog.cpp +msgid "Start" +msgstr "" + +#: editor/editor_profiler.cpp +msgid "Measure:" +msgstr "" + +#: editor/editor_profiler.cpp +msgid "Frame Time (sec)" +msgstr "" + +#: editor/editor_profiler.cpp +msgid "Average Time (sec)" +msgstr "" + +#: editor/editor_profiler.cpp +msgid "Frame %" +msgstr "" + +#: editor/editor_profiler.cpp +msgid "Physics Frame %" +msgstr "" + +#: editor/editor_profiler.cpp +msgid "Time:" +msgstr "" + +#: editor/editor_profiler.cpp +msgid "Inclusive" +msgstr "" + +#: editor/editor_profiler.cpp +msgid "Self" +msgstr "" + +#: editor/editor_profiler.cpp +msgid "Frame #:" +msgstr "" + +#: editor/editor_profiler.cpp +msgid "Time" +msgstr "" + +#: editor/editor_profiler.cpp +msgid "Calls" +msgstr "" + +#: editor/editor_properties.cpp +msgid "On" +msgstr "" + +#: editor/editor_properties.cpp +msgid "Layer" +msgstr "" + +#: editor/editor_properties.cpp +msgid "Bit %d, value %d" +msgstr "" + +#: editor/editor_properties.cpp +msgid "[Empty]" +msgstr "" + +#: editor/editor_properties.cpp editor/plugins/root_motion_editor_plugin.cpp +msgid "Assign..." +msgstr "" + +#: editor/editor_properties.cpp +msgid "Invalid RID" +msgstr "" + +#: editor/editor_properties.cpp +msgid "" +"The selected resource (%s) does not match any type expected for this " +"property (%s)." +msgstr "" + +#: editor/editor_properties.cpp +msgid "" +"Can't create a ViewportTexture on resources saved as a file.\n" +"Resource needs to belong to a scene." +msgstr "" + +#: editor/editor_properties.cpp +msgid "" +"Can't create a ViewportTexture on this resource because it's not set as " +"local to scene.\n" +"Please switch on the 'local to scene' property on it (and all resources " +"containing it up to a node)." +msgstr "" + +#: editor/editor_properties.cpp editor/property_editor.cpp +msgid "Pick a Viewport" +msgstr "" + +#: editor/editor_properties.cpp editor/property_editor.cpp +msgid "New Script" +msgstr "" + +#: editor/editor_properties.cpp editor/property_editor.cpp +msgid "New %s" +msgstr "" + +#: editor/editor_properties.cpp editor/property_editor.cpp +msgid "Make Unique" +msgstr "" + +#: editor/editor_properties.cpp +#: editor/plugins/animation_blend_space_1d_editor.cpp +#: editor/plugins/animation_blend_space_2d_editor.cpp +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +#: editor/plugins/animation_player_editor_plugin.cpp +#: editor/plugins/animation_state_machine_editor.cpp +#: editor/plugins/resource_preloader_editor_plugin.cpp +#: editor/plugins/script_text_editor.cpp +#: editor/plugins/sprite_frames_editor_plugin.cpp +#: editor/plugins/tile_map_editor_plugin.cpp editor/property_editor.cpp +#: scene/gui/line_edit.cpp scene/gui/text_edit.cpp +msgid "Paste" +msgstr "" + +#: editor/editor_properties.cpp editor/property_editor.cpp +msgid "Convert To %s" +msgstr "" + +#: editor/editor_properties.cpp +#: editor/plugins/animation_blend_space_1d_editor.cpp +#: editor/plugins/animation_blend_space_2d_editor.cpp +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +msgid "Open Editor" +msgstr "" + +#: editor/editor_properties.cpp editor/property_editor.cpp +msgid "Selected node is not a Viewport!" +msgstr "" + +#: editor/editor_properties_array_dict.cpp +msgid "Size: " +msgstr "" + +#: editor/editor_properties_array_dict.cpp +msgid "Page: " +msgstr "" + +#: editor/editor_properties_array_dict.cpp +msgid "New Key:" +msgstr "" + +#: editor/editor_properties_array_dict.cpp +msgid "New Value:" +msgstr "" + +#: editor/editor_properties_array_dict.cpp +msgid "Add Key/Value Pair" +msgstr "" + +#: editor/editor_properties_array_dict.cpp +#: editor/plugins/theme_editor_plugin.cpp +msgid "Remove Item" +msgstr "" + +#: editor/editor_run_native.cpp +msgid "Select device from the list" +msgstr "" + +#: editor/editor_run_native.cpp +msgid "" +"No runnable export preset found for this platform.\n" +"Please add a runnable preset in the export menu." +msgstr "" + +#: editor/editor_run_script.cpp +msgid "Write your logic in the _run() method." +msgstr "" + +#: editor/editor_run_script.cpp +msgid "There is an edited scene already." +msgstr "" + +#: editor/editor_run_script.cpp +msgid "Couldn't instance script:" +msgstr "" + +#: editor/editor_run_script.cpp +msgid "Did you forget the 'tool' keyword?" +msgstr "" + +#: editor/editor_run_script.cpp +msgid "Couldn't run script:" +msgstr "" + +#: editor/editor_run_script.cpp +msgid "Did you forget the '_run' method?" +msgstr "" + +#: editor/editor_sub_scene.cpp +msgid "Select Node(s) to Import" +msgstr "" + +#: editor/editor_sub_scene.cpp +msgid "Scene Path:" +msgstr "" + +#: editor/editor_sub_scene.cpp +msgid "Import From Node:" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Re-Download" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Uninstall" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "(Installed)" +msgstr "" + +#: editor/export_template_manager.cpp +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Download" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "(Missing)" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "(Current)" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Retrieving mirrors, please wait..." +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Remove template version '%s'?" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Can't open export templates zip." +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Invalid version.txt format inside templates: %s." +msgstr "" + +#: editor/export_template_manager.cpp +msgid "No version.txt found inside templates." +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Error creating path for templates:" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Extracting Export Templates" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Importing:" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "" +"No download links found for this version. Direct download is only available " +"for official releases." +msgstr "" + +#: editor/export_template_manager.cpp +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Can't resolve." +msgstr "" + +#: editor/export_template_manager.cpp +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Can't connect." +msgstr "" + +#: editor/export_template_manager.cpp +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "No response." +msgstr "" + +#: editor/export_template_manager.cpp +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Request Failed." +msgstr "" + +#: editor/export_template_manager.cpp +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Redirect Loop." +msgstr "" + +#: editor/export_template_manager.cpp +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Failed:" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Download Complete." +msgstr "" + +#: editor/export_template_manager.cpp +msgid "" +"Templates installation failed. The problematic templates archives can be " +"found at '%s'." +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Error requesting url: " +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Connecting to Mirror..." +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Disconnected" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Resolving" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Can't Resolve" +msgstr "" + +#: editor/export_template_manager.cpp +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Connecting..." +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Can't Connect" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Connected" +msgstr "" + +#: editor/export_template_manager.cpp +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Requesting..." +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Downloading" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Connection Error" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "SSL Handshake Error" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Current Version:" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Installed Versions:" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Install From File" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Remove Template" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Select template file" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Export Template Manager" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Download Templates" +msgstr "" + +#: editor/export_template_manager.cpp +msgid "Select mirror from list: (Shift+Click: Open in Browser)" +msgstr "" + +#: editor/file_type_cache.cpp +msgid "Can't open file_type_cache.cch for writing, not saving file type cache!" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Favorites" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Cannot navigate to '%s' as it has not been found in the file system!" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Status: Import of file failed. Please fix file and reimport manually." +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Cannot move/rename resources root." +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Cannot move a folder into itself." +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Error moving:" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Error duplicating:" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Unable to update dependencies:" +msgstr "" + +#: editor/filesystem_dock.cpp editor/scene_tree_editor.cpp +msgid "No name provided." +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Provided name contains invalid characters" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Name contains invalid characters." +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "A file or folder with this name already exists." +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Renaming file:" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Renaming folder:" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Duplicating file:" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Duplicating folder:" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Open Scene(s)" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Instance" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Add to favorites" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Remove from favorites" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Edit Dependencies..." +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "View Owners..." +msgstr "" + +#: editor/filesystem_dock.cpp editor/plugins/animation_player_editor_plugin.cpp +msgid "Rename..." +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Duplicate..." +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Move To..." +msgstr "" + +#: editor/filesystem_dock.cpp editor/plugins/script_editor_plugin.cpp +msgid "New Script..." +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "New Resource..." +msgstr "" + +#: editor/filesystem_dock.cpp editor/script_editor_debugger.cpp +msgid "Expand All" +msgstr "" + +#: editor/filesystem_dock.cpp editor/script_editor_debugger.cpp +msgid "Collapse All" +msgstr "" + +#: editor/filesystem_dock.cpp +#: editor/plugins/animation_tree_player_editor_plugin.cpp +#: editor/project_manager.cpp editor/rename_dialog.cpp +#: editor/scene_tree_dock.cpp +msgid "Rename" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Previous Directory" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Next Directory" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Re-Scan Filesystem" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Toggle split mode" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Search files" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "" +"Scanning Files,\n" +"Please Wait..." +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Move" +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "There is already file or folder with the same name in this location." +msgstr "" + +#: editor/filesystem_dock.cpp +msgid "Overwrite" +msgstr "" + +#: editor/filesystem_dock.cpp editor/plugins/script_editor_plugin.cpp +msgid "Create Script" +msgstr "" + +#: editor/find_in_files.cpp +msgid "Find in Files" +msgstr "" + +#: editor/find_in_files.cpp +msgid "Find:" +msgstr "" + +#: editor/find_in_files.cpp +msgid "Folder:" +msgstr "" + +#: editor/find_in_files.cpp +msgid "Filters:" +msgstr "" + +#: editor/find_in_files.cpp editor/plugins/script_editor_plugin.cpp +#: editor/plugins/script_text_editor.cpp +msgid "Find..." +msgstr "" + +#: editor/find_in_files.cpp editor/plugins/script_text_editor.cpp +msgid "Replace..." +msgstr "" + +#: editor/find_in_files.cpp editor/progress_dialog.cpp scene/gui/dialogs.cpp +msgid "Cancel" +msgstr "" + +#: editor/find_in_files.cpp +msgid "Find: " +msgstr "" + +#: editor/find_in_files.cpp +msgid "Replace: " +msgstr "" + +#: editor/find_in_files.cpp +msgid "Replace all (no undo)" +msgstr "" + +#: editor/find_in_files.cpp +msgid "Searching..." +msgstr "" + +#: editor/find_in_files.cpp +msgid "Search complete" +msgstr "" + +#: editor/groups_editor.cpp +msgid "Group name already exists." +msgstr "" + +#: editor/groups_editor.cpp +msgid "Invalid group name." +msgstr "" + +#: editor/groups_editor.cpp editor/node_dock.cpp +msgid "Groups" +msgstr "" + +#: editor/groups_editor.cpp +msgid "Nodes not in Group" +msgstr "" + +#: editor/groups_editor.cpp editor/scene_tree_dock.cpp +msgid "Filter nodes" +msgstr "" + +#: editor/groups_editor.cpp +msgid "Nodes in Group" +msgstr "" + +#: editor/groups_editor.cpp +msgid "Add to Group" +msgstr "" + +#: editor/groups_editor.cpp +msgid "Remove from Group" +msgstr "" + +#: editor/groups_editor.cpp +msgid "Manage Groups" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Import as Single Scene" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Import with Separate Animations" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Import with Separate Materials" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Import with Separate Objects" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Import with Separate Objects+Materials" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Import with Separate Objects+Animations" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Import with Separate Materials+Animations" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Import with Separate Objects+Materials+Animations" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Import as Multiple Scenes" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Import as Multiple Scenes+Materials" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +#: editor/plugins/mesh_library_editor_plugin.cpp +msgid "Import Scene" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Importing Scene..." +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Generating Lightmaps" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Generating for Mesh: " +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Running Custom Script..." +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Couldn't load post-import script:" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Invalid/broken script for post-import (check console):" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Error running post-import script:" +msgstr "" + +#: editor/import/resource_importer_scene.cpp +msgid "Saving..." +msgstr "" + +#: editor/import_dock.cpp +msgid "Set as Default for '%s'" +msgstr "" + +#: editor/import_dock.cpp +msgid "Clear Default for '%s'" +msgstr "" + +#: editor/import_dock.cpp +msgid " Files" +msgstr "" + +#: editor/import_dock.cpp +msgid "Import As:" +msgstr "" + +#: editor/import_dock.cpp editor/property_editor.cpp +msgid "Preset..." +msgstr "" + +#: editor/import_dock.cpp +msgid "Reimport" +msgstr "" + +#: editor/import_dock.cpp +msgid "Save scenes, re-import and restart" +msgstr "" + +#: editor/import_dock.cpp +msgid "Changing the type of an imported file requires editor restart." +msgstr "" + +#: editor/import_dock.cpp +msgid "" +"WARNING: Assets exist that use this resource, they may stop loading properly." +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Failed to load resource." +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Expand All Properties" +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Collapse All Properties" +msgstr "" + +#: editor/inspector_dock.cpp editor/plugins/animation_player_editor_plugin.cpp +#: editor/plugins/script_editor_plugin.cpp +msgid "Save As..." +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Copy Params" +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Paste Params" +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Edit Resource Clipboard" +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Copy Resource" +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Make Built-In" +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Make Sub-Resources Unique" +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Open in Help" +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Create a new resource in memory and edit it." +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Load an existing resource from disk and edit it." +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Save the currently edited resource." +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Go to the previous edited object in history." +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Go to the next edited object in history." +msgstr "" + +#: editor/inspector_dock.cpp +msgid "History of recently edited objects." +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Object properties." +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Filter properties" +msgstr "" + +#: editor/inspector_dock.cpp +msgid "Changes may be lost!" +msgstr "" + +#: editor/multi_node_edit.cpp +msgid "MultiNode Set" +msgstr "" + +#: editor/node_dock.cpp +msgid "Select a Node to edit Signals and Groups." +msgstr "" + +#: editor/plugin_config_dialog.cpp +msgid "Edit a Plugin" +msgstr "" + +#: editor/plugin_config_dialog.cpp +msgid "Create a Plugin" +msgstr "" + +#: editor/plugin_config_dialog.cpp +msgid "Plugin Name:" +msgstr "" + +#: editor/plugin_config_dialog.cpp +msgid "Subfolder:" +msgstr "" + +#: editor/plugin_config_dialog.cpp +msgid "Language:" +msgstr "" + +#: editor/plugin_config_dialog.cpp +msgid "Script Name:" +msgstr "" + +#: editor/plugin_config_dialog.cpp +msgid "Activate now?" +msgstr "" + +#: editor/plugins/abstract_polygon_2d_editor.cpp +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Create Polygon" +msgstr "" + +#: editor/plugins/abstract_polygon_2d_editor.cpp +#: editor/plugins/animation_blend_space_1d_editor.cpp +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Create points." +msgstr "" + +#: editor/plugins/abstract_polygon_2d_editor.cpp +msgid "" +"Edit points.\n" +"LMB: Move Point\n" +"RMB: Erase Point" +msgstr "" + +#: editor/plugins/abstract_polygon_2d_editor.cpp +#: editor/plugins/animation_blend_space_1d_editor.cpp +msgid "Erase points." +msgstr "" + +#: editor/plugins/abstract_polygon_2d_editor.cpp +msgid "Edit Polygon" +msgstr "" + +#: editor/plugins/abstract_polygon_2d_editor.cpp +msgid "Insert Point" +msgstr "" + +#: editor/plugins/abstract_polygon_2d_editor.cpp +msgid "Edit Polygon (Remove Point)" +msgstr "" + +#: editor/plugins/abstract_polygon_2d_editor.cpp +msgid "Remove Polygon And Point" +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +#: editor/plugins/animation_blend_space_2d_editor.cpp +#: editor/plugins/animation_player_editor_plugin.cpp +#: editor/plugins/animation_state_machine_editor.cpp +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Add Animation" +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +#: editor/plugins/animation_blend_space_2d_editor.cpp +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Load..." +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Move Node Point" +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +msgid "Change BlendSpace1D Limits" +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +msgid "Change BlendSpace1D Labels" +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +#: editor/plugins/animation_blend_space_2d_editor.cpp +#: editor/plugins/animation_state_machine_editor.cpp +msgid "This type of node can't be used. Only root nodes are allowed." +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Add Node Point" +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Add Animation Point" +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +msgid "Remove BlendSpace1D Point" +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +msgid "Move BlendSpace1D Node Point" +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +#: editor/plugins/animation_blend_space_2d_editor.cpp +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +#: editor/plugins/animation_state_machine_editor.cpp +msgid "" +"AnimationTree is inactive.\n" +"Activate to enable playback, check node warnings if activation fails." +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Set the blending position within the space" +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Select and move points, create points with RMB." +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +#: editor/plugins/animation_blend_space_2d_editor.cpp scene/gui/graph_edit.cpp +msgid "Enable snap and show grid." +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Point" +msgstr "" + +#: editor/plugins/animation_blend_space_1d_editor.cpp +#: editor/plugins/animation_blend_space_2d_editor.cpp +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Open Animation Node" +msgstr "" + +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Triangle already exists" +msgstr "" + +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Add Triangle" +msgstr "" + +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Change BlendSpace2D Limits" +msgstr "" + +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Change BlendSpace2D Labels" +msgstr "" + +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Remove BlendSpace2D Point" +msgstr "" + +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Remove BlendSpace2D Triangle" +msgstr "" + +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "BlendSpace2D does not belong to an AnimationTree node." +msgstr "" + +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "No triangles exist, so no blending can take place." +msgstr "" + +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Toggle Auto Triangles" +msgstr "" + +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Create triangles by connecting points." +msgstr "" + +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Erase points and triangles." +msgstr "" + +#: editor/plugins/animation_blend_space_2d_editor.cpp +msgid "Generate blend triangles automatically (instead of manually)" +msgstr "" + +#: editor/plugins/animation_blend_space_2d_editor.cpp +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Blend:" +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +msgid "Parameter Changed" +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Edit Filters" +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +msgid "Output node can't be added to the blend tree." +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +msgid "Add Node to BlendTree" +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Node Moved" +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Unable to connect, port may be in use or connection may be invalid." +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Nodes Connected" +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Nodes Disconnected" +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +msgid "Set Animation" +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Delete Node" +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +#: editor/scene_tree_dock.cpp +msgid "Delete Node(s)" +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +msgid "Toggle Filter On/Off" +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +msgid "Change Filter" +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +msgid "No animation player set, so unable to retrieve track names." +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +msgid "Player path set is invalid, so unable to retrieve track names." +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +#: editor/plugins/root_motion_editor_plugin.cpp +msgid "" +"Animation player has no valid root node path, so unable to retrieve track " +"names." +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Node Renamed" +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Add Node..." +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +#: editor/plugins/root_motion_editor_plugin.cpp +msgid "Edit Filtered Tracks:" +msgstr "" + +#: editor/plugins/animation_blend_tree_editor_plugin.cpp +msgid "Enable filtering" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Toggle Autoplay" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "New Animation Name:" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "New Anim" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Change Animation Name:" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Delete Animation?" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Remove Animation" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Invalid animation name!" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Animation name already exists!" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Rename Animation" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Blend Next Changed" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Change Blend Time" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Load Animation" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Duplicate Animation" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "No animation to copy!" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "No animation resource on clipboard!" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Pasted Animation" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Paste Animation" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "No animation to edit!" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Play selected animation backwards from current pos. (A)" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Play selected animation backwards from end. (Shift+A)" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Stop animation playback. (S)" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Play selected animation from start. (Shift+D)" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Play selected animation from current pos. (D)" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Animation position (in seconds)." +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Scale animation playback globally for the node." +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Animation Tools" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Animation" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "New" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Edit Transitions..." +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Open in Inspector" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Display list of animations in player." +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Autoplay on Load" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Onion Skinning" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Enable Onion Skinning" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Directions" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Past" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Future" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Depth" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "1 step" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "2 steps" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "3 steps" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Differences Only" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Force White Modulate" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Include Gizmos (3D)" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Pin AnimationPlayer" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Create New Animation" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Animation Name:" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +#: editor/plugins/resource_preloader_editor_plugin.cpp +#: editor/plugins/script_editor_plugin.cpp +#: editor/plugins/sprite_frames_editor_plugin.cpp editor/property_editor.cpp +#: editor/script_create_dialog.cpp +msgid "Error!" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Blend Times:" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Next (Auto Queue):" +msgstr "" + +#: editor/plugins/animation_player_editor_plugin.cpp +msgid "Cross-Animation Blend Times" +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Move Node" +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Add Transition" +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +#: modules/visual_script/visual_script_editor.cpp +msgid "Add Node" +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "End" +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Immediate" +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Sync" +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "At End" +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Travel" +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Start and end nodes are needed for a sub-transition." +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "No playback resource set at path: %s." +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Node Removed" +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Transition Removed" +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Set Start Node (Autoplay)" +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "" +"Select and move nodes.\n" +"RMB to add new nodes.\n" +"Shift+LMB to create connections." +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Create new nodes." +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Connect nodes." +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Remove selected node or transition." +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Toggle autoplay this animation on start, restart or seek to zero." +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Set the end animation. This is useful for sub-transitions." +msgstr "" + +#: editor/plugins/animation_state_machine_editor.cpp +msgid "Transition: " +msgstr "" + +#: editor/plugins/animation_tree_editor_plugin.cpp +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "AnimationTree" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "New name:" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Scale:" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Fade In (s):" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Fade Out (s):" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Blend" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Mix" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Auto Restart:" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Restart (s):" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Random Restart (s):" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Start!" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Amount:" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Blend 0:" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Blend 1:" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "X-Fade Time (s):" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Current:" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Add Input" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Clear Auto-Advance" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Set Auto-Advance" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Delete Input" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Animation tree is valid." +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Animation tree is invalid." +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Animation Node" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "OneShot Node" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Mix Node" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Blend2 Node" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Blend3 Node" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Blend4 Node" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "TimeScale Node" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "TimeSeek Node" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Transition Node" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Import Animations..." +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Edit Node Filters" +msgstr "" + +#: editor/plugins/animation_tree_player_editor_plugin.cpp +msgid "Filters..." +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Contents:" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "View Files" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Can't resolve hostname:" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Connection error, please try again." +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Can't connect to host:" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "No response from host:" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Request failed, return code:" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Request failed, too many redirects" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Bad download hash, assuming file has been tampered with." +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Expected:" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Got:" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Failed sha256 hash check" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Asset Download Error:" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Downloading (%s / %s)..." +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Downloading..." +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Resolving..." +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Error making request" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Idle" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Retry" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Download Error" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Download for this asset is already in progress!" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "First" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Previous" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Next" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Last" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +#: modules/gdnative/gdnative_library_editor_plugin.cpp +msgid "All" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +#: editor/project_settings_editor.cpp +msgid "Plugins" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp editor/project_manager.cpp +msgid "Sort:" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Reverse" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +#: editor/project_settings_editor.cpp +msgid "Category:" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Site:" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Support..." +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Official" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Testing" +msgstr "" + +#: editor/plugins/asset_library_editor_plugin.cpp +msgid "Assets ZIP File" +msgstr "" + +#: editor/plugins/baked_lightmap_editor_plugin.cpp +msgid "" +"Can't determine a save path for lightmap images.\n" +"Save your scene (for images to be saved in the same dir), or pick a save " +"path from the BakedLightmap properties." +msgstr "" + +#: editor/plugins/baked_lightmap_editor_plugin.cpp +msgid "" +"No meshes to bake. Make sure they contain an UV2 channel and that the 'Bake " +"Light' flag is on." +msgstr "" + +#: editor/plugins/baked_lightmap_editor_plugin.cpp +msgid "Failed creating lightmap images, make sure path is writable." +msgstr "" + +#: editor/plugins/baked_lightmap_editor_plugin.cpp +msgid "Bake Lightmaps" +msgstr "" + +#: editor/plugins/camera_editor_plugin.cpp +#: editor/plugins/spatial_editor_plugin.cpp editor/rename_dialog.cpp +msgid "Preview" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Configure Snap" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Grid Offset:" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Grid Step:" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Rotation Offset:" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Rotation Step:" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Move vertical guide" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Create new vertical guide" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Remove vertical guide" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Move horizontal guide" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Create new horizontal guide" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Remove horizontal guide" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Create new horizontal and vertical guides" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Move pivot" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Rotate CanvasItem" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Move anchor" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Resize CanvasItem" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Scale CanvasItem" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Move CanvasItem" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Presets for the anchors and margins values of a Control node." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "" +"Children of containers have their anchors and margins values overridden by " +"their parent." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Anchors only" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Change Anchors and Margins" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Change Anchors" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Paste Pose" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "" +"Warning: Children of a container get their position and size determined only " +"by their parent." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +#: editor/plugins/texture_region_editor_plugin.cpp +#: editor/plugins/tile_set_editor_plugin.cpp scene/gui/graph_edit.cpp +msgid "Zoom Reset" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Select Mode" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Drag: Rotate" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Alt+Drag: Move" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Press 'v' to Change Pivot, 'Shift+v' to Drag Pivot (while moving)." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Alt+RMB: Depth list selection" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Move Mode" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Rotate Mode" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Scale Mode" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +#: editor/plugins/spatial_editor_plugin.cpp +msgid "" +"Show a list of all objects at the position clicked\n" +"(same as Alt+RMB in select mode)." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Click to change object's rotation pivot." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Pan Mode" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Toggle snapping." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Use Snap" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Snapping Options" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Snap to grid" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Use Rotation Snap" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Configure Snap..." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Snap Relative" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Use Pixel Snap" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Smart snapping" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Snap to parent" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Snap to node anchor" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Snap to node sides" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Snap to node center" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Snap to other nodes" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Snap to guides" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Lock the selected object in place (can't be moved)." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Unlock the selected object (can be moved)." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Makes sure the object's children are not selectable." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Restores the object's children's ability to be selected." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Skeleton Options" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Show Bones" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Make IK Chain" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Clear IK Chain" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Make Custom Bone(s) from Node(s)" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Clear Custom Bones" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +#: editor/plugins/spatial_editor_plugin.cpp +msgid "View" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Show Grid" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Show Helpers" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Show Rulers" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Show Guides" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Show Origin" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Show Viewport" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Show Group And Lock Icons" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Center Selection" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Frame Selection" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Layout" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Translation mask for inserting keys." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Rotation mask for inserting keys." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Scale mask for inserting keys." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Insert keys (based on mask)." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "" +"Auto insert keys when objects are translated, rotated on scaled (based on " +"mask).\n" +"Keys are only added to existing tracks, no new tracks will be created.\n" +"Keys must be inserted manually for the first time." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Auto Insert Key" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Insert Key (Existing Tracks)" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Copy Pose" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Clear Pose" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Multiply grid step by 2" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Divide grid step by 2" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Add %s" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Adding %s..." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Cannot instantiate multiple nodes without root." +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +#: editor/plugins/spatial_editor_plugin.cpp editor/scene_tree_dock.cpp +msgid "Create Node" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +#: editor/plugins/spatial_editor_plugin.cpp editor/scene_tree_dock.cpp +msgid "Error instancing scene from %s" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "Change default type" +msgstr "" + +#: editor/plugins/canvas_item_editor_plugin.cpp +msgid "" +"Drag & drop + Shift : Add node as sibling\n" +"Drag & drop + Alt : Change node type" +msgstr "" + +#: editor/plugins/collision_polygon_editor_plugin.cpp +msgid "Create Polygon3D" +msgstr "" + +#: editor/plugins/collision_polygon_editor_plugin.cpp +msgid "Edit Poly" +msgstr "" + +#: editor/plugins/collision_polygon_editor_plugin.cpp +msgid "Edit Poly (Remove Point)" +msgstr "" + +#: editor/plugins/collision_shape_2d_editor_plugin.cpp +msgid "Set Handle" +msgstr "" + +#: editor/plugins/cpu_particles_2d_editor_plugin.cpp +#: editor/plugins/particles_2d_editor_plugin.cpp +msgid "Error loading image:" +msgstr "" + +#: editor/plugins/cpu_particles_2d_editor_plugin.cpp +#: editor/plugins/particles_2d_editor_plugin.cpp +msgid "No pixels with transparency > 128 in image..." +msgstr "" + +#: editor/plugins/cpu_particles_2d_editor_plugin.cpp +#: editor/plugins/particles_2d_editor_plugin.cpp +msgid "Load Emission Mask" +msgstr "" + +#: editor/plugins/cpu_particles_2d_editor_plugin.cpp +#: editor/plugins/particles_2d_editor_plugin.cpp +msgid "Clear Emission Mask" +msgstr "" + +#: editor/plugins/cpu_particles_2d_editor_plugin.cpp +#: editor/plugins/particles_2d_editor_plugin.cpp +#: editor/plugins/particles_editor_plugin.cpp +msgid "Particles" +msgstr "" + +#: editor/plugins/cpu_particles_2d_editor_plugin.cpp +#: editor/plugins/particles_2d_editor_plugin.cpp +msgid "Generated Point Count:" +msgstr "" + +#: editor/plugins/cpu_particles_2d_editor_plugin.cpp +#: editor/plugins/particles_2d_editor_plugin.cpp +msgid "Emission Mask" +msgstr "" + +#: editor/plugins/cpu_particles_2d_editor_plugin.cpp +#: editor/plugins/particles_2d_editor_plugin.cpp +msgid "Capture from Pixel" +msgstr "" + +#: editor/plugins/cpu_particles_2d_editor_plugin.cpp +#: editor/plugins/particles_2d_editor_plugin.cpp +msgid "Emission Colors" +msgstr "" + +#: editor/plugins/cpu_particles_editor_plugin.cpp +msgid "CPUParticles" +msgstr "" + +#: editor/plugins/cpu_particles_editor_plugin.cpp +#: editor/plugins/particles_editor_plugin.cpp +msgid "Create Emission Points From Mesh" +msgstr "" + +#: editor/plugins/cpu_particles_editor_plugin.cpp +#: editor/plugins/particles_editor_plugin.cpp +msgid "Create Emission Points From Node" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Flat0" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Flat1" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Ease in" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Ease out" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Smoothstep" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Modify Curve Point" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Modify Curve Tangent" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Load Curve Preset" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Add point" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Remove point" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Left linear" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Right linear" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Load preset" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Remove Curve Point" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Toggle Curve Linear Tangent" +msgstr "" + +#: editor/plugins/curve_editor_plugin.cpp +msgid "Hold Shift to edit tangents individually" +msgstr "" + +#: editor/plugins/gi_probe_editor_plugin.cpp +msgid "Bake GI Probe" +msgstr "" + +#: editor/plugins/gradient_editor_plugin.cpp +msgid "Gradient Edited" +msgstr "" + +#: editor/plugins/item_list_editor_plugin.cpp +msgid "Item %d" +msgstr "" + +#: editor/plugins/item_list_editor_plugin.cpp +msgid "Items" +msgstr "" + +#: editor/plugins/item_list_editor_plugin.cpp +msgid "Item List Editor" +msgstr "" + +#: editor/plugins/light_occluder_2d_editor_plugin.cpp +msgid "Create Occluder Polygon" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Mesh is empty!" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Create Static Trimesh Body" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Create Static Convex Body" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "This doesn't work on scene root!" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Create Trimesh Shape" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Create Convex Shape" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Create Navigation Mesh" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Contained Mesh is not of type ArrayMesh." +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "UV Unwrap failed, mesh may not be manifold?" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "No mesh to debug." +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Model has no UV in this layer" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "MeshInstance lacks a Mesh!" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Mesh has not surface to create outlines from!" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Mesh primitive type is not PRIMITIVE_TRIANGLES!" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Could not create outline!" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Create Outline" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Mesh" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Create Trimesh Static Body" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Create Convex Static Body" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Create Trimesh Collision Sibling" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Create Convex Collision Sibling" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Create Outline Mesh..." +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "View UV1" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "View UV2" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Unwrap UV2 for Lightmap/AO" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Create Outline Mesh" +msgstr "" + +#: editor/plugins/mesh_instance_editor_plugin.cpp +msgid "Outline Size:" +msgstr "" + +#: editor/plugins/mesh_library_editor_plugin.cpp +msgid "Remove item %d?" +msgstr "" + +#: editor/plugins/mesh_library_editor_plugin.cpp +#: editor/plugins/theme_editor_plugin.cpp +msgid "Add Item" +msgstr "" + +#: editor/plugins/mesh_library_editor_plugin.cpp +msgid "Remove Selected Item" +msgstr "" + +#: editor/plugins/mesh_library_editor_plugin.cpp +msgid "Import from Scene" +msgstr "" + +#: editor/plugins/mesh_library_editor_plugin.cpp +msgid "Update from Scene" +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "No mesh source specified (and no MultiMesh set in node)." +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "No mesh source specified (and MultiMesh contains no Mesh)." +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Mesh source is invalid (invalid path)." +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Mesh source is invalid (not a MeshInstance)." +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Mesh source is invalid (contains no Mesh resource)." +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "No surface source specified." +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Surface source is invalid (invalid path)." +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Surface source is invalid (no geometry)." +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Surface source is invalid (no faces)." +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Parent has no solid faces to populate." +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Couldn't map area." +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Select a Source Mesh:" +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Select a Target Surface:" +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Populate Surface" +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Populate MultiMesh" +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Target Surface:" +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Source Mesh:" +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "X-Axis" +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Y-Axis" +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Z-Axis" +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Mesh Up Axis:" +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Random Rotation:" +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Random Tilt:" +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Random Scale:" +msgstr "" + +#: editor/plugins/multimesh_editor_plugin.cpp +msgid "Populate" +msgstr "" + +#: editor/plugins/navigation_polygon_editor_plugin.cpp +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Create Navigation Polygon" +msgstr "" + +#: editor/plugins/particles_2d_editor_plugin.cpp +msgid "Generating Visibility Rect" +msgstr "" + +#: editor/plugins/particles_2d_editor_plugin.cpp +msgid "Generate Visibility Rect" +msgstr "" + +#: editor/plugins/particles_2d_editor_plugin.cpp +msgid "Can only set point into a ParticlesMaterial process material" +msgstr "" + +#: editor/plugins/particles_2d_editor_plugin.cpp +#: editor/plugins/particles_editor_plugin.cpp +msgid "Convert to CPUParticles" +msgstr "" + +#: editor/plugins/particles_2d_editor_plugin.cpp +#: editor/plugins/particles_editor_plugin.cpp +msgid "Generation Time (sec):" +msgstr "" + +#: editor/plugins/particles_editor_plugin.cpp +msgid "Faces contain no area!" +msgstr "" + +#: editor/plugins/particles_editor_plugin.cpp +msgid "No faces!" +msgstr "" + +#: editor/plugins/particles_editor_plugin.cpp +msgid "Node does not contain geometry." +msgstr "" + +#: editor/plugins/particles_editor_plugin.cpp +msgid "Node does not contain geometry (faces)." +msgstr "" + +#: editor/plugins/particles_editor_plugin.cpp +msgid "Create Emitter" +msgstr "" + +#: editor/plugins/particles_editor_plugin.cpp +msgid "Emission Points:" +msgstr "" + +#: editor/plugins/particles_editor_plugin.cpp +msgid "Surface Points" +msgstr "" + +#: editor/plugins/particles_editor_plugin.cpp +msgid "Surface Points+Normal (Directed)" +msgstr "" + +#: editor/plugins/particles_editor_plugin.cpp +msgid "Volume" +msgstr "" + +#: editor/plugins/particles_editor_plugin.cpp +msgid "Emission Source: " +msgstr "" + +#: editor/plugins/particles_editor_plugin.cpp +msgid "A processor material of type 'ParticlesMaterial' is required." +msgstr "" + +#: editor/plugins/particles_editor_plugin.cpp +msgid "Generating AABB" +msgstr "" + +#: editor/plugins/particles_editor_plugin.cpp +msgid "Generate Visibility AABB" +msgstr "" + +#: editor/plugins/particles_editor_plugin.cpp +msgid "Generate AABB" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +msgid "Remove Point from Curve" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +msgid "Remove Out-Control from Curve" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +msgid "Remove In-Control from Curve" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +#: editor/plugins/path_editor_plugin.cpp +msgid "Add Point to Curve" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +msgid "Split Curve" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +msgid "Move Point in Curve" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +msgid "Move In-Control in Curve" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +msgid "Move Out-Control in Curve" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +#: editor/plugins/path_editor_plugin.cpp +msgid "Select Points" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +#: editor/plugins/path_editor_plugin.cpp +msgid "Shift+Drag: Select Control Points" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +#: editor/plugins/path_editor_plugin.cpp +msgid "Click: Add Point" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +msgid "Left Click: Split Segment (in curve)" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +#: editor/plugins/path_editor_plugin.cpp +msgid "Right Click: Delete Point" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +msgid "Select Control Points (Shift+Drag)" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +#: editor/plugins/path_editor_plugin.cpp +msgid "Add Point (in empty space)" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +#: editor/plugins/path_editor_plugin.cpp +msgid "Delete Point" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +#: editor/plugins/path_editor_plugin.cpp +msgid "Close Curve" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +#: editor/plugins/path_editor_plugin.cpp editor/plugins/theme_editor_plugin.cpp +#: editor/project_export.cpp +msgid "Options" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +#: editor/plugins/path_editor_plugin.cpp +msgid "Mirror Handle Angles" +msgstr "" + +#: editor/plugins/path_2d_editor_plugin.cpp +#: editor/plugins/path_editor_plugin.cpp +msgid "Mirror Handle Lengths" +msgstr "" + +#: editor/plugins/path_editor_plugin.cpp +msgid "Curve Point #" +msgstr "" + +#: editor/plugins/path_editor_plugin.cpp +msgid "Set Curve Point Position" +msgstr "" + +#: editor/plugins/path_editor_plugin.cpp +msgid "Set Curve In Position" +msgstr "" + +#: editor/plugins/path_editor_plugin.cpp +msgid "Set Curve Out Position" +msgstr "" + +#: editor/plugins/path_editor_plugin.cpp +msgid "Split Path" +msgstr "" + +#: editor/plugins/path_editor_plugin.cpp +msgid "Remove Path Point" +msgstr "" + +#: editor/plugins/path_editor_plugin.cpp +msgid "Remove Out-Control Point" +msgstr "" + +#: editor/plugins/path_editor_plugin.cpp +msgid "Remove In-Control Point" +msgstr "" + +#: editor/plugins/path_editor_plugin.cpp +msgid "Split Segment (in curve)" +msgstr "" + +#: editor/plugins/physical_bone_plugin.cpp +msgid "Move joint" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "" +"The skeleton property of the Polygon2D does not point to a Skeleton2D node" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Sync Bones" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "" +"No texture in this polygon.\n" +"Set a texture to be able to edit UV." +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Create UV Map" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "" +"Polygon 2D has internal vertices, so it can no longer be edited in the " +"viewport." +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Create Polygon & UV" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Create Internal Vertex" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Remove Internal Vertex" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Invalid Polygon (need 3 different vertices)" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Add Custom Polygon" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Remove Custom Polygon" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Transform UV Map" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Transform Polygon" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Paint Bone Weights" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Open Polygon 2D UV editor." +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Polygon 2D UV Editor" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "UV" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Points" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Polygons" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Bones" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Move Points" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Ctrl: Rotate" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Shift: Move All" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Shift+Ctrl: Scale" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Move Polygon" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Rotate Polygon" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Scale Polygon" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Create a custom polygon. Enables custom polygon rendering." +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "" +"Remove a custom polygon. If none remain, custom polygon rendering is " +"disabled." +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Paint weights with specified intensity." +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Unpaint weights with specified intensity." +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Radius:" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Polygon->UV" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "UV->Polygon" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Clear UV" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Grid Settings" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Snap" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Enable Snap" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Grid" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Configure Grid:" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Grid Offset X:" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Grid Offset Y:" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Grid Step X:" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Grid Step Y:" +msgstr "" + +#: editor/plugins/polygon_2d_editor_plugin.cpp +msgid "Sync Bones to Polygon" +msgstr "" + +#: editor/plugins/resource_preloader_editor_plugin.cpp +msgid "ERROR: Couldn't load resource!" +msgstr "" + +#: editor/plugins/resource_preloader_editor_plugin.cpp +msgid "Add Resource" +msgstr "" + +#: editor/plugins/resource_preloader_editor_plugin.cpp +msgid "Rename Resource" +msgstr "" + +#: editor/plugins/resource_preloader_editor_plugin.cpp +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Delete Resource" +msgstr "" + +#: editor/plugins/resource_preloader_editor_plugin.cpp +msgid "Resource clipboard is empty!" +msgstr "" + +#: editor/plugins/resource_preloader_editor_plugin.cpp +msgid "Paste Resource" +msgstr "" + +#: editor/plugins/resource_preloader_editor_plugin.cpp +#: editor/scene_tree_editor.cpp +msgid "Instance:" +msgstr "" + +#: editor/plugins/resource_preloader_editor_plugin.cpp +#: editor/plugins/theme_editor_plugin.cpp editor/project_settings_editor.cpp +#: editor/scene_tree_editor.cpp +msgid "Type:" +msgstr "" + +#: editor/plugins/resource_preloader_editor_plugin.cpp +#: editor/scene_tree_dock.cpp editor/scene_tree_editor.cpp +msgid "Open in Editor" +msgstr "" + +#: editor/plugins/resource_preloader_editor_plugin.cpp +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Load Resource" +msgstr "" + +#: editor/plugins/resource_preloader_editor_plugin.cpp +msgid "ResourcePreloader" +msgstr "" + +#: editor/plugins/root_motion_editor_plugin.cpp +msgid "AnimationTree has no path set to an AnimationPlayer" +msgstr "" + +#: editor/plugins/root_motion_editor_plugin.cpp +msgid "Path to AnimationPlayer is invalid" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Clear Recent Files" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Close and save changes?" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Error writing TextFile:" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Error: could not load file." +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Error could not load file." +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Error saving file!" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Error while saving theme." +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Error Saving" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Error importing theme." +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Error Importing" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "New TextFile..." +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Open File" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Save File As..." +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Import Theme" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Error while saving theme" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Error saving" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Save Theme As..." +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "%s Class Reference" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Toggle alphabetical sorting of the method list." +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Sort" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +#: editor/plugins/script_text_editor.cpp editor/scene_tree_dock.cpp +#: modules/gdnative/gdnative_library_editor_plugin.cpp +msgid "Move Up" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +#: editor/plugins/script_text_editor.cpp editor/scene_tree_dock.cpp +#: modules/gdnative/gdnative_library_editor_plugin.cpp +msgid "Move Down" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Next script" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Previous script" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "File" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Open..." +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Save All" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Soft Reload Script" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Copy Script Path" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "History Previous" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "History Next" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +#: editor/plugins/theme_editor_plugin.cpp +msgid "Theme" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Import Theme..." +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Reload Theme" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Save Theme" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Close Docs" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Close All" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Close Other Tabs" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp editor/project_manager.cpp +msgid "Run" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Toggle Scripts Panel" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +#: editor/plugins/script_text_editor.cpp +msgid "Find Next" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp editor/script_editor_debugger.cpp +msgid "Step Over" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp editor/script_editor_debugger.cpp +msgid "Step Into" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp editor/script_editor_debugger.cpp +msgid "Break" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp editor/project_manager.cpp +#: editor/script_editor_debugger.cpp +msgid "Continue" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Keep Debugger Open" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Debug with External Editor" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Open Godot online documentation" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Request Docs" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Help improve the Godot documentation by giving feedback" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Search the reference documentation." +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Go to previous edited document." +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Go to next edited document." +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Discard" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "" +"The following files are newer on disk.\n" +"What action should be taken?:" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Reload" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Resave" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp editor/script_editor_debugger.cpp +msgid "Debugger" +msgstr "" + +#: editor/plugins/script_editor_plugin.cpp +msgid "Search Results" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Line" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "(ignore)" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Go to Function" +msgstr "" + +#: editor/plugins/script_text_editor.cpp editor/plugins/text_editor.cpp +msgid "Standard" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Only resources from filesystem can be dropped." +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Lookup Symbol" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Pick Color" +msgstr "" + +#: editor/plugins/script_text_editor.cpp editor/plugins/text_editor.cpp +msgid "Convert Case" +msgstr "" + +#: editor/plugins/script_text_editor.cpp editor/plugins/text_editor.cpp +msgid "Uppercase" +msgstr "" + +#: editor/plugins/script_text_editor.cpp editor/plugins/text_editor.cpp +msgid "Lowercase" +msgstr "" + +#: editor/plugins/script_text_editor.cpp editor/plugins/text_editor.cpp +msgid "Capitalize" +msgstr "" + +#: editor/plugins/script_text_editor.cpp editor/plugins/text_editor.cpp +msgid "Syntax Highlighter" +msgstr "" + +#: editor/plugins/script_text_editor.cpp scene/gui/line_edit.cpp +#: scene/gui/text_edit.cpp +msgid "Cut" +msgstr "" + +#: editor/plugins/script_text_editor.cpp scene/gui/line_edit.cpp +#: scene/gui/text_edit.cpp +msgid "Select All" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Delete Line" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Indent Left" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Indent Right" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Toggle Comment" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Fold/Unfold Line" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Fold All Lines" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Unfold All Lines" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Clone Down" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Complete Symbol" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Trim Trailing Whitespace" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Convert Indent to Spaces" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Convert Indent to Tabs" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Auto Indent" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +#: modules/visual_script/visual_script_editor.cpp +msgid "Toggle Breakpoint" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Remove All Breakpoints" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Go to Next Breakpoint" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Go to Previous Breakpoint" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Find Previous" +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Find in Files..." +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Go to Function..." +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Go to Line..." +msgstr "" + +#: editor/plugins/script_text_editor.cpp +msgid "Contextual Help" +msgstr "" + +#: editor/plugins/shader_editor_plugin.cpp +msgid "Shader" +msgstr "" + +#: editor/plugins/skeleton_2d_editor_plugin.cpp +msgid "This skeleton has no bones, create some children Bone2D nodes." +msgstr "" + +#: editor/plugins/skeleton_2d_editor_plugin.cpp +msgid "Create Rest Pose from Bones" +msgstr "" + +#: editor/plugins/skeleton_2d_editor_plugin.cpp +msgid "Set Rest Pose to Bones" +msgstr "" + +#: editor/plugins/skeleton_2d_editor_plugin.cpp +msgid "Skeleton2D" +msgstr "" + +#: editor/plugins/skeleton_2d_editor_plugin.cpp +msgid "Make Rest Pose (From Bones)" +msgstr "" + +#: editor/plugins/skeleton_2d_editor_plugin.cpp +msgid "Set Bones to Rest Pose" +msgstr "" + +#: editor/plugins/skeleton_editor_plugin.cpp +msgid "Create physical bones" +msgstr "" + +#: editor/plugins/skeleton_editor_plugin.cpp +msgid "Skeleton" +msgstr "" + +#: editor/plugins/skeleton_editor_plugin.cpp +msgid "Create physical skeleton" +msgstr "" + +#: editor/plugins/skeleton_ik_editor_plugin.cpp +msgid "Play IK" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Orthogonal" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Perspective" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Transform Aborted." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "X-Axis Transform." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Y-Axis Transform." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Z-Axis Transform." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "View Plane Transform." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Scaling: " +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Translating: " +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Rotating %s degrees." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Keying is disabled (no key inserted)." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Animation Key Inserted." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Pitch" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Yaw" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Objects Drawn" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Material Changes" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Shader Changes" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Surface Changes" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Draw Calls" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Vertices" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Top View." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Bottom View." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Bottom" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Left View." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Left" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Right View." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Right" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Front View." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Front" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Rear View." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Rear" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Align with View" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp editor/scene_tree_dock.cpp +msgid "No parent to instance a child at." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp editor/scene_tree_dock.cpp +msgid "This operation requires a single selected node." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Lock View Rotation" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Display Normal" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Display Wireframe" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Display Overdraw" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Display Unshaded" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "View Environment" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "View Gizmos" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "View Information" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "View FPS" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Half Resolution" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Audio Listener" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Doppler Enable" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Cinematic Preview" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Freelook Left" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Freelook Right" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Freelook Forward" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Freelook Backwards" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Freelook Up" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Freelook Down" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Freelook Speed Modifier" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "" +"Note: The FPS value displayed is the editor's framerate.\n" +"It cannot be used as a reliable indication of in-game performance." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "View Rotation Locked" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "XForm Dialog" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Snap Nodes To Floor" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Select Mode (Q)" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "" +"Drag: Rotate\n" +"Alt+Drag: Move\n" +"Alt+RMB: Depth list selection" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Move Mode (W)" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Rotate Mode (E)" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Scale Mode (R)" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Local Coords" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Local Space Mode (%s)" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Snap Mode (%s)" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Bottom View" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Top View" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Rear View" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Front View" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Left View" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Right View" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Switch Perspective/Orthogonal view" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Insert Animation Key" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Focus Origin" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Focus Selection" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Align Selection With View" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Tool Select" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Tool Move" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Tool Rotate" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Tool Scale" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Toggle Freelook" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Transform" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Snap object to floor" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Transform Dialog..." +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "1 Viewport" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "2 Viewports" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "2 Viewports (Alt)" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "3 Viewports" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "3 Viewports (Alt)" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "4 Viewports" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Gizmos" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "View Origin" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "View Grid" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Settings" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Snap Settings" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Translate Snap:" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Rotate Snap (deg.):" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Scale Snap (%):" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Viewport Settings" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Perspective FOV (deg.):" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "View Z-Near:" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "View Z-Far:" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Transform Change" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Translate:" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Rotate (deg.):" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Scale (ratio):" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Transform Type" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Pre" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Post" +msgstr "" + +#: editor/plugins/spatial_editor_plugin.cpp +msgid "Nameless gizmo" +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Create Mesh2D" +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Create Polygon2D" +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Create CollisionPolygon2D" +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Create LightOccluder2D" +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Sprite is empty!" +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Can't convert a sprite using animation frames to mesh." +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Invalid geometry, can't replace by mesh." +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Invalid geometry, can't create polygon." +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Invalid geometry, can't create collision polygon." +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Invalid geometry, can't create light occluder." +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Sprite" +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Convert to Mesh2D" +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Convert to Polygon2D" +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Create CollisionPolygon2D Sibling" +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Create LightOccluder2D Sibling" +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Simplification: " +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Grow (Pixels): " +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Update Preview" +msgstr "" + +#: editor/plugins/sprite_editor_plugin.cpp +msgid "Settings:" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "ERROR: Couldn't load frame resource!" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Add Frame" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Resource clipboard is empty or not a texture!" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Paste Frame" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Add Empty" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Change Animation FPS" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "(empty)" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Animations:" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "New Animation" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Speed (FPS):" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Loop" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Animation Frames:" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Insert Empty (Before)" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Insert Empty (After)" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Move (Before)" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "Move (After)" +msgstr "" + +#: editor/plugins/sprite_frames_editor_plugin.cpp +msgid "SpriteFrames" +msgstr "" + +#: editor/plugins/texture_region_editor_plugin.cpp +msgid "Set Region Rect" +msgstr "" + +#: editor/plugins/texture_region_editor_plugin.cpp +msgid "Set Margin" +msgstr "" + +#: editor/plugins/texture_region_editor_plugin.cpp +msgid "Snap Mode:" +msgstr "" + +#: editor/plugins/texture_region_editor_plugin.cpp +#: scene/resources/visual_shader.cpp +msgid "None" +msgstr "" + +#: editor/plugins/texture_region_editor_plugin.cpp +msgid "Pixel Snap" +msgstr "" + +#: editor/plugins/texture_region_editor_plugin.cpp +msgid "Grid Snap" +msgstr "" + +#: editor/plugins/texture_region_editor_plugin.cpp +msgid "Auto Slice" +msgstr "" + +#: editor/plugins/texture_region_editor_plugin.cpp +msgid "Offset:" +msgstr "" + +#: editor/plugins/texture_region_editor_plugin.cpp +msgid "Step:" +msgstr "" + +#: editor/plugins/texture_region_editor_plugin.cpp +msgid "Sep.:" +msgstr "" + +#: editor/plugins/texture_region_editor_plugin.cpp +msgid "TextureRegion" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Can't save theme to file:" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Add All Items" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Add All" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Remove All Items" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Remove All" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Edit theme..." +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Theme editing menu." +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Add Class Items" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Remove Class Items" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Create Empty Template" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Create Empty Editor Template" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Create From Current Editor Theme" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "CheckBox Radio1" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "CheckBox Radio2" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Item" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Check Item" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Checked Item" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Radio Item" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Checked Radio Item" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Has" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Many" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Has,Many,Options" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Tab 1" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Tab 2" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Tab 3" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Data Type:" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Icon" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp editor/rename_dialog.cpp +msgid "Style" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Font" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Color" +msgstr "" + +#: editor/plugins/theme_editor_plugin.cpp +msgid "Constant" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Erase Selection" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Fix Invalid Tiles" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Cut Selection" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Paint TileMap" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Line Draw" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Rectangle Paint" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Bucket Fill" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Erase TileMap" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Find Tile" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Transpose" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Mirror X" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Mirror Y" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Paint Tile" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Pick Tile" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Copy Selection" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Rotate left" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Rotate right" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Flip horizontally" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Flip vertically" +msgstr "" + +#: editor/plugins/tile_map_editor_plugin.cpp +msgid "Clear transform" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Add Texture(s) to TileSet." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Remove selected Texture from TileSet." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Create from Scene" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Merge from Scene" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Next Coordinate" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Select the next shape, subtile, or Tile." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Previous Coordinate" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Select the previous shape, subtile, or Tile." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Copy bitmask." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Paste bitmask." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Erase bitmask." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Create a new rectangle." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Create a new polygon." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Keep polygon inside region Rect." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Enable snap and show grid (configurable via the Inspector)." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Display Tile Names (Hold Alt Key)" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Remove selected texture? This will remove all tiles which use it." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "You haven't selected a texture to remove." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Create from scene? This will overwrite all current tiles." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Merge from scene?" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Remove Texture" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "%s file(s) were not added because was already on the list." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "" +"Drag handles to edit Rect.\n" +"Click on another Tile to edit it." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Delete selected Rect." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "" +"Select current edited sub-tile.\n" +"Click on another Tile to edit it." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Delete polygon." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "" +"LMB: Set bit on.\n" +"RMB: Set bit off.\n" +"Click on another Tile to edit it." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "" +"Select sub-tile to use as icon, this will be also used on invalid autotile " +"bindings.\n" +"Click on another Tile to edit it." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "" +"Select sub-tile to change its priority.\n" +"Click on another Tile to edit it." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "" +"Select sub-tile to change its z index.\n" +"Click on another Tile to edit it." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Set Tile Region" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Create Tile" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Set Tile Icon" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Edit Tile Bitmask" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Edit Collision Polygon" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Edit Occlusion Polygon" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Edit Navigation Polygon" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Paste Tile Bitmask" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Clear Tile Bitmask" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Make Polygon Concave" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Make Polygon Convex" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Remove Tile" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Remove Collision Polygon" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Remove Occlusion Polygon" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Remove Navigation Polygon" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Edit Tile Priority" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Edit Tile Z Index" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Create Collision Polygon" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "Create Occlusion Polygon" +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "This property can't be changed." +msgstr "" + +#: editor/plugins/tile_set_editor_plugin.cpp +msgid "TileSet" +msgstr "" + +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Set Uniform Name" +msgstr "" + +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Set Input Default Port" +msgstr "" + +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Add Node to Visual Shader" +msgstr "" + +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Duplicate Nodes" +msgstr "" + +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Delete Nodes" +msgstr "" + +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Visual Shader Input Type Changed" +msgstr "" + +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Vertex" +msgstr "" + +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Fragment" +msgstr "" + +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Light" +msgstr "" + +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "VisualShader" +msgstr "" + +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Edit Visual Property" +msgstr "" + +#: editor/plugins/visual_shader_editor_plugin.cpp +msgid "Visual Shader Mode Changed" +msgstr "" + +#: editor/project_export.cpp +msgid "Runnable" +msgstr "" + +#: editor/project_export.cpp +msgid "Delete patch '%s' from list?" +msgstr "" + +#: editor/project_export.cpp +msgid "Delete preset '%s'?" +msgstr "" + +#: editor/project_export.cpp +msgid "" +"Failed to export the project for platform '%s'.\n" +"Export templates seem to be missing or invalid." +msgstr "" + +#: editor/project_export.cpp +msgid "" +"Failed to export the project for platform '%s'.\n" +"This might be due to a configuration issue in the export preset or your " +"export settings." +msgstr "" + +#: editor/project_export.cpp +msgid "Release" +msgstr "" + +#: editor/project_export.cpp +msgid "Exporting All" +msgstr "" + +#: editor/project_export.cpp +msgid "The given export path doesn't exist:" +msgstr "" + +#: editor/project_export.cpp +msgid "Export templates for this platform are missing/corrupted:" +msgstr "" + +#: editor/project_export.cpp +msgid "Presets" +msgstr "" + +#: editor/project_export.cpp editor/project_settings_editor.cpp +msgid "Add..." +msgstr "" + +#: editor/project_export.cpp +msgid "Export Path" +msgstr "" + +#: editor/project_export.cpp +msgid "Resources" +msgstr "" + +#: editor/project_export.cpp +msgid "Export all resources in the project" +msgstr "" + +#: editor/project_export.cpp +msgid "Export selected scenes (and dependencies)" +msgstr "" + +#: editor/project_export.cpp +msgid "Export selected resources (and dependencies)" +msgstr "" + +#: editor/project_export.cpp +msgid "Export Mode:" +msgstr "" + +#: editor/project_export.cpp +msgid "Resources to export:" +msgstr "" + +#: editor/project_export.cpp +msgid "" +"Filters to export non-resource files (comma separated, e.g: *.json, *.txt)" +msgstr "" + +#: editor/project_export.cpp +msgid "" +"Filters to exclude files from project (comma separated, e.g: *.json, *.txt)" +msgstr "" + +#: editor/project_export.cpp +msgid "Patches" +msgstr "" + +#: editor/project_export.cpp +msgid "Make Patch" +msgstr "" + +#: editor/project_export.cpp +msgid "Features" +msgstr "" + +#: editor/project_export.cpp +msgid "Custom (comma-separated):" +msgstr "" + +#: editor/project_export.cpp +msgid "Feature List:" +msgstr "" + +#: editor/project_export.cpp +msgid "Script" +msgstr "" + +#: editor/project_export.cpp +msgid "Script Export Mode:" +msgstr "" + +#: editor/project_export.cpp +msgid "Text" +msgstr "" + +#: editor/project_export.cpp +msgid "Compiled" +msgstr "" + +#: editor/project_export.cpp +msgid "Encrypted (Provide Key Below)" +msgstr "" + +#: editor/project_export.cpp +msgid "Invalid Encryption Key (must be 64 characters long)" +msgstr "" + +#: editor/project_export.cpp +msgid "Script Encryption Key (256-bits as hex):" +msgstr "" + +#: editor/project_export.cpp +msgid "Export PCK/Zip" +msgstr "" + +#: editor/project_export.cpp +msgid "Export mode?" +msgstr "" + +#: editor/project_export.cpp +msgid "Export All" +msgstr "" + +#: editor/project_export.cpp +msgid "Export templates for this platform are missing:" +msgstr "" + +#: editor/project_export.cpp +msgid "Export With Debug" +msgstr "" + +#: editor/project_manager.cpp +msgid "The path does not exist." +msgstr "" + +#: editor/project_manager.cpp +msgid "Invalid '.zip' project file, does not contain a 'project.godot' file." +msgstr "" + +#: editor/project_manager.cpp +msgid "Please choose an empty folder." +msgstr "" + +#: editor/project_manager.cpp +msgid "Please choose a 'project.godot' or '.zip' file." +msgstr "" + +#: editor/project_manager.cpp +msgid "Directory already contains a Godot project." +msgstr "" + +#: editor/project_manager.cpp +msgid "Imported Project" +msgstr "" + +#: editor/project_manager.cpp +msgid "Invalid Project Name." +msgstr "" + +#: editor/project_manager.cpp +msgid "Couldn't create folder." +msgstr "" + +#: editor/project_manager.cpp +msgid "There is already a folder in this path with the specified name." +msgstr "" + +#: editor/project_manager.cpp +msgid "It would be a good idea to name your project." +msgstr "" + +#: editor/project_manager.cpp +msgid "Invalid project path (changed anything?)." +msgstr "" + +#: editor/project_manager.cpp +msgid "" +"Couldn't load project.godot in project path (error %d). It may be missing or " +"corrupted." +msgstr "" + +#: editor/project_manager.cpp +msgid "Couldn't edit project.godot in project path." +msgstr "" + +#: editor/project_manager.cpp +msgid "Couldn't create project.godot in project path." +msgstr "" + +#: editor/project_manager.cpp +msgid "The following files failed extraction from package:" +msgstr "" + +#: editor/project_manager.cpp +msgid "Rename Project" +msgstr "" + +#: editor/project_manager.cpp +msgid "New Game Project" +msgstr "" + +#: editor/project_manager.cpp +msgid "Import Existing Project" +msgstr "" + +#: editor/project_manager.cpp +msgid "Import & Edit" +msgstr "" + +#: editor/project_manager.cpp +msgid "Create New Project" +msgstr "" + +#: editor/project_manager.cpp +msgid "Create & Edit" +msgstr "" + +#: editor/project_manager.cpp +msgid "Install Project:" +msgstr "" + +#: editor/project_manager.cpp +msgid "Install & Edit" +msgstr "" + +#: editor/project_manager.cpp +msgid "Project Name:" +msgstr "" + +#: editor/project_manager.cpp +msgid "Create folder" +msgstr "" + +#: editor/project_manager.cpp +msgid "Project Path:" +msgstr "" + +#: editor/project_manager.cpp +msgid "Project Installation Path:" +msgstr "" + +#: editor/project_manager.cpp +msgid "Browse" +msgstr "" + +#: editor/project_manager.cpp +msgid "Renderer:" +msgstr "" + +#: editor/project_manager.cpp +msgid "OpenGL ES 3.0" +msgstr "" + +#: editor/project_manager.cpp +msgid "" +"Higher visual quality\n" +"All features available\n" +"Incompatible with older hardware\n" +"Not recommended for web games" +msgstr "" + +#: editor/project_manager.cpp +msgid "OpenGL ES 2.0" +msgstr "" + +#: editor/project_manager.cpp +msgid "" +"Lower visual quality\n" +"Some features not available\n" +"Works on most hardware\n" +"Recommended for web games" +msgstr "" + +#: editor/project_manager.cpp +msgid "Renderer can be changed later, but scenes may need to be adjusted." +msgstr "" + +#: editor/project_manager.cpp +msgid "Unnamed Project" +msgstr "" + +#: editor/project_manager.cpp +msgid "Can't open project at '%s'." +msgstr "" + +#: editor/project_manager.cpp +msgid "Are you sure to open more than one project?" +msgstr "" + +#: editor/project_manager.cpp +msgid "" +"The following project settings file does not specify the version of Godot " +"through which it was created.\n" +"\n" +"%s\n" +"\n" +"If you proceed with opening it, it will be converted to Godot's current " +"configuration file format.\n" +"Warning: You will not be able to open the project with previous versions of " +"the engine anymore." +msgstr "" + +#: editor/project_manager.cpp +msgid "" +"The following project settings file was generated by an older engine " +"version, and needs to be converted for this version:\n" +"\n" +"%s\n" +"\n" +"Do you want to convert it?\n" +"Warning: You will not be able to open the project with previous versions of " +"the engine anymore." +msgstr "" + +#: editor/project_manager.cpp +msgid "" +"The project settings were created by a newer engine version, whose settings " +"are not compatible with this version." +msgstr "" + +#: editor/project_manager.cpp +msgid "" +"Can't run project: no main scene defined.\n" +"Please edit the project and set the main scene in \"Project Settings\" under " +"the \"Application\" category." +msgstr "" + +#: editor/project_manager.cpp +msgid "" +"Can't run project: Assets need to be imported.\n" +"Please edit the project to trigger the initial import." +msgstr "" + +#: editor/project_manager.cpp +msgid "Are you sure to run more than one project?" +msgstr "" + +#: editor/project_manager.cpp +msgid "Remove project from the list? (Folder contents will not be modified)" +msgstr "" + +#: editor/project_manager.cpp +msgid "" +"Language changed.\n" +"The UI will update next time the editor or project manager starts." +msgstr "" + +#: editor/project_manager.cpp +msgid "" +"You are about the scan %s folders for existing Godot projects. Do you " +"confirm?" +msgstr "" + +#: editor/project_manager.cpp +msgid "Project Manager" +msgstr "" + +#: editor/project_manager.cpp +msgid "Project List" +msgstr "" + +#: editor/project_manager.cpp +msgid "Scan" +msgstr "" + +#: editor/project_manager.cpp +msgid "Select a Folder to Scan" +msgstr "" + +#: editor/project_manager.cpp +msgid "New Project" +msgstr "" + +#: editor/project_manager.cpp +msgid "Templates" +msgstr "" + +#: editor/project_manager.cpp +msgid "Exit" +msgstr "" + +#: editor/project_manager.cpp +msgid "Restart Now" +msgstr "" + +#: editor/project_manager.cpp +msgid "Can't run project" +msgstr "" + +#: editor/project_manager.cpp +msgid "" +"You don't currently have any projects.\n" +"Would you like to explore the official example projects in the Asset Library?" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Key " +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Joy Button" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Joy Axis" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Mouse Button" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "" +"Invalid action name. it cannot be empty nor contain '/', ':', '=', '\\' or " +"'\"'" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Action '%s' already exists!" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Rename Input Action Event" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Change Action deadzone" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Add Input Action Event" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "All Devices" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Device" +msgstr "" + +#: editor/project_settings_editor.cpp editor/settings_config_dialog.cpp +msgid "Shift+" +msgstr "" + +#: editor/project_settings_editor.cpp editor/settings_config_dialog.cpp +msgid "Alt+" +msgstr "" + +#: editor/project_settings_editor.cpp editor/settings_config_dialog.cpp +msgid "Control+" +msgstr "" + +#: editor/project_settings_editor.cpp editor/settings_config_dialog.cpp +msgid "Press a Key..." +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Mouse Button Index:" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Left Button" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Right Button" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Middle Button" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Wheel Up Button" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Wheel Down Button" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Wheel Left Button" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Wheel Right Button" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "X Button 1" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "X Button 2" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Joypad Axis Index:" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Axis" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Joypad Button Index:" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Erase Input Action" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Erase Input Action Event" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Add Event" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Button" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Left Button." +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Right Button." +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Middle Button." +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Wheel Up." +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Wheel Down." +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Add Global Property" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Select a setting item first!" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "No property '%s' exists." +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Setting '%s' is internal, and it can't be deleted." +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Delete Item" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "" +"Invalid action name. It cannot be empty nor contain '/', ':', '=', '\\' or " +"'\"'." +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Already existing" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Add Input Action" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Error saving settings." +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Settings saved OK." +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Override for Feature" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Add Translation" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Remove Translation" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Add Remapped Path" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Resource Remap Add Remap" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Change Resource Remap Language" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Remove Resource Remap" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Remove Resource Remap Option" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Changed Locale Filter" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Changed Locale Filter Mode" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Project Settings (project.godot)" +msgstr "" + +#: editor/project_settings_editor.cpp editor/settings_config_dialog.cpp +msgid "General" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Override For..." +msgstr "" + +#: editor/project_settings_editor.cpp editor/settings_config_dialog.cpp +msgid "Editor must be restarted for changes to take effect" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Input Map" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Action:" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Action" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Deadzone" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Device:" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Index:" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Localization" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Translations" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Translations:" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Remaps" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Resources:" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Remaps by Locale:" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Locale" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Locales Filter" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Show all locales" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Show only selected locales" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Filter mode:" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "Locales:" +msgstr "" + +#: editor/project_settings_editor.cpp +msgid "AutoLoad" +msgstr "" + +#: editor/property_editor.cpp +msgid "Ease In" +msgstr "" + +#: editor/property_editor.cpp +msgid "Ease Out" +msgstr "" + +#: editor/property_editor.cpp +msgid "Zero" +msgstr "" + +#: editor/property_editor.cpp +msgid "Easing In-Out" +msgstr "" + +#: editor/property_editor.cpp +msgid "Easing Out-In" +msgstr "" + +#: editor/property_editor.cpp +msgid "File..." +msgstr "" + +#: editor/property_editor.cpp +msgid "Dir..." +msgstr "" + +#: editor/property_editor.cpp +msgid "Assign" +msgstr "" + +#: editor/property_editor.cpp +msgid "Select Node" +msgstr "" + +#: editor/property_editor.cpp +msgid "Error loading file: Not a resource!" +msgstr "" + +#: editor/property_editor.cpp +msgid "Pick a Node" +msgstr "" + +#: editor/property_editor.cpp +msgid "Bit %d, val %d." +msgstr "" + +#: editor/property_selector.cpp +msgid "Select Property" +msgstr "" + +#: editor/property_selector.cpp +msgid "Select Virtual Method" +msgstr "" + +#: editor/property_selector.cpp +msgid "Select Method" +msgstr "" + +#: editor/pvrtc_compress.cpp +msgid "Could not execute PVRTC tool:" +msgstr "" + +#: editor/pvrtc_compress.cpp +msgid "Can't load back converted image using PVRTC tool:" +msgstr "" + +#: editor/rename_dialog.cpp editor/scene_tree_dock.cpp +msgid "Batch Rename" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Prefix" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Suffix" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Advanced options" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Substitute" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Node name" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Node's parent name, if available" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Node type" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Current scene name" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Root node name" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "" +"Sequential integer counter.\n" +"Compare counter options." +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Per Level counter" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "If set the counter restarts for each group of child nodes" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Initial value for the counter" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Step" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Amount by which counter is incremented for each node" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Padding" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "" +"Minimum number of digits for the counter.\n" +"Missing digits are padded with leading zeros." +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Regular Expressions" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Post-Process" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Keep" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "CamelCase to under_scored" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "under_scored to CamelCase" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Case" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "To Lowercase" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "To Uppercase" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Reset" +msgstr "" + +#: editor/rename_dialog.cpp +msgid "Error" +msgstr "" + +#: editor/reparent_dialog.cpp editor/scene_tree_dock.cpp +msgid "Reparent Node" +msgstr "" + +#: editor/reparent_dialog.cpp +msgid "Reparent Location (Select new Parent):" +msgstr "" + +#: editor/reparent_dialog.cpp +msgid "Keep Global Transform" +msgstr "" + +#: editor/reparent_dialog.cpp editor/scene_tree_dock.cpp +msgid "Reparent" +msgstr "" + +#: editor/run_settings_dialog.cpp +msgid "Run Mode:" +msgstr "" + +#: editor/run_settings_dialog.cpp +msgid "Current Scene" +msgstr "" + +#: editor/run_settings_dialog.cpp +msgid "Main Scene" +msgstr "" + +#: editor/run_settings_dialog.cpp +msgid "Main Scene Arguments:" +msgstr "" + +#: editor/run_settings_dialog.cpp +msgid "Scene Run Settings" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "No parent to instance the scenes at." +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Error loading scene from %s" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "" +"Cannot instance the scene '%s' because the current scene exists within one " +"of its nodes." +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Instance Scene(s)" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Instance Child Scene" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Clear Script" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "This operation can't be done on the tree root." +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Move Node In Parent" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Move Nodes In Parent" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Duplicate Node(s)" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Can't reparent nodes in inherited scenes, order of nodes can't change." +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Node must belong to the edited scene to become root." +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Instantiated scenes can't become root" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Make node as Root" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Delete Node(s)?" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Can not perform with the root node." +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "This operation can't be done on instanced scenes." +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Save New Scene As..." +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "" +"Disabling \"editable_instance\" will cause all properties of the node to be " +"reverted to their default." +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Editable Children" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Load As Placeholder" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Make Local" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "New Scene Root" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Create Root Node:" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "2D Scene" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "3D Scene" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "User Interface" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Custom Node" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Can't operate on nodes from a foreign scene!" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Can't operate on nodes the current scene inherits from!" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Attach Script" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Remove Node(s)" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "" +"Couldn't save new scene. Likely dependencies (instances) couldn't be " +"satisfied." +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Error saving scene." +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Error duplicating scene to save it." +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Sub-Resources" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Clear Inheritance" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Open documentation" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Add Child Node" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Change Type" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Extend Script" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Make Scene Root" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Merge From Scene" +msgstr "" + +#: editor/scene_tree_dock.cpp editor/script_editor_debugger.cpp +msgid "Save Branch as Scene" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Copy Node Path" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Delete (No Confirm)" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Add/Create a New Node" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "" +"Instance a scene file as a Node. Creates an inherited scene if no root node " +"exists." +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Attach a new or existing script for the selected node." +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Clear a script for the selected node." +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Remote" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Local" +msgstr "" + +#: editor/scene_tree_dock.cpp +msgid "Clear Inheritance? (No Undo!)" +msgstr "" + +#: editor/scene_tree_editor.cpp +msgid "Toggle Visible" +msgstr "" + +#: editor/scene_tree_editor.cpp +msgid "Node configuration warning:" +msgstr "" + +#: editor/scene_tree_editor.cpp +msgid "" +"Node has connection(s) and group(s).\n" +"Click to show signals dock." +msgstr "" + +#: editor/scene_tree_editor.cpp +msgid "" +"Node has connections.\n" +"Click to show signals dock." +msgstr "" + +#: editor/scene_tree_editor.cpp +msgid "" +"Node is in group(s).\n" +"Click to show groups dock." +msgstr "" + +#: editor/scene_tree_editor.cpp editor/script_create_dialog.cpp +msgid "Open Script" +msgstr "" + +#: editor/scene_tree_editor.cpp +msgid "" +"Node is locked.\n" +"Click to unlock it." +msgstr "" + +#: editor/scene_tree_editor.cpp +msgid "" +"Children are not selectable.\n" +"Click to make selectable." +msgstr "" + +#: editor/scene_tree_editor.cpp +msgid "Toggle Visibility" +msgstr "" + +#: editor/scene_tree_editor.cpp +msgid "" +"AnimationPlayer is pinned.\n" +"Click to unpin." +msgstr "" + +#: editor/scene_tree_editor.cpp +msgid "Invalid node name, the following characters are not allowed:" +msgstr "" + +#: editor/scene_tree_editor.cpp +msgid "Rename Node" +msgstr "" + +#: editor/scene_tree_editor.cpp +msgid "Scene Tree (Nodes):" +msgstr "" + +#: editor/scene_tree_editor.cpp +msgid "Node Configuration Warning!" +msgstr "" + +#: editor/scene_tree_editor.cpp +msgid "Select a Node" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Error loading template '%s'" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Error - Could not create script in filesystem." +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Error loading script from %s" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "N/A" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Open Script/Choose Location" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Path is empty" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Filename is empty" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Path is not local" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Invalid base path" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Directory of the same name exists" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "File exists, will be reused" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Invalid extension" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Wrong extension chosen" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Invalid Path" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Invalid class name" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Invalid inherited parent name or path" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Script valid" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Allowed: a-z, A-Z, 0-9 and _" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Built-in script (into scene file)" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Create new script file" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Load existing script file" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Language" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Inherits" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Class Name" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Template" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Built-in Script" +msgstr "" + +#: editor/script_create_dialog.cpp +msgid "Attach Node Script" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Remote " +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Bytes:" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Stack Trace" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Pick one or more items from the list to display the graph." +msgstr "" + +#: editor/script_editor_debugger.cpp modules/mono/editor/mono_bottom_panel.cpp +msgid "Errors" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Child Process Connected" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Copy Error" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Inspect Previous Instance" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Inspect Next Instance" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Stack Frames" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Profiler" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Monitor" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Value" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Monitors" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "List of Video Memory Usage by Resource:" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Total:" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Video Mem" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Resource Path" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Type" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Format" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Usage" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Misc" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Clicked Control:" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Clicked Control Type:" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Live Edit Root:" +msgstr "" + +#: editor/script_editor_debugger.cpp +msgid "Set From Tree" +msgstr "" + +#: editor/settings_config_dialog.cpp +msgid "Erase Shortcut" +msgstr "" + +#: editor/settings_config_dialog.cpp +msgid "Restore Shortcut" +msgstr "" + +#: editor/settings_config_dialog.cpp +msgid "Change Shortcut" +msgstr "" + +#: editor/settings_config_dialog.cpp +msgid "Shortcuts" +msgstr "" + +#: editor/settings_config_dialog.cpp +msgid "Binding" +msgstr "" + +#: editor/spatial_editor_gizmos.cpp +msgid "Change Light Radius" +msgstr "" + +#: editor/spatial_editor_gizmos.cpp +msgid "Change AudioStreamPlayer3D Emission Angle" +msgstr "" + +#: editor/spatial_editor_gizmos.cpp +msgid "Change Camera FOV" +msgstr "" + +#: editor/spatial_editor_gizmos.cpp +msgid "Change Camera Size" +msgstr "" + +#: editor/spatial_editor_gizmos.cpp +msgid "Change Notifier AABB" +msgstr "" + +#: editor/spatial_editor_gizmos.cpp +msgid "Change Particles AABB" +msgstr "" + +#: editor/spatial_editor_gizmos.cpp +msgid "Change Probe Extents" +msgstr "" + +#: editor/spatial_editor_gizmos.cpp modules/csg/csg_gizmos.cpp +msgid "Change Sphere Shape Radius" +msgstr "" + +#: editor/spatial_editor_gizmos.cpp modules/csg/csg_gizmos.cpp +msgid "Change Box Shape Extents" +msgstr "" + +#: editor/spatial_editor_gizmos.cpp +msgid "Change Capsule Shape Radius" +msgstr "" + +#: editor/spatial_editor_gizmos.cpp +msgid "Change Capsule Shape Height" +msgstr "" + +#: editor/spatial_editor_gizmos.cpp +msgid "Change Cylinder Shape Radius" +msgstr "" + +#: editor/spatial_editor_gizmos.cpp +msgid "Change Cylinder Shape Height" +msgstr "" + +#: editor/spatial_editor_gizmos.cpp +msgid "Change Ray Shape Length" +msgstr "" + +#: modules/csg/csg_gizmos.cpp +msgid "Change Cylinder Radius" +msgstr "" + +#: modules/csg/csg_gizmos.cpp +msgid "Change Cylinder Height" +msgstr "" + +#: modules/csg/csg_gizmos.cpp +msgid "Change Torus Inner Radius" +msgstr "" + +#: modules/csg/csg_gizmos.cpp +msgid "Change Torus Outer Radius" +msgstr "" + +#: modules/gdnative/gdnative_library_editor_plugin.cpp +msgid "Select the dynamic library for this entry" +msgstr "" + +#: modules/gdnative/gdnative_library_editor_plugin.cpp +msgid "Select dependencies of the library for this entry" +msgstr "" + +#: modules/gdnative/gdnative_library_editor_plugin.cpp +msgid "Remove current entry" +msgstr "" + +#: modules/gdnative/gdnative_library_editor_plugin.cpp +msgid "Double click to create a new entry" +msgstr "" + +#: modules/gdnative/gdnative_library_editor_plugin.cpp +msgid "Platform:" +msgstr "" + +#: modules/gdnative/gdnative_library_editor_plugin.cpp +msgid "Platform" +msgstr "" + +#: modules/gdnative/gdnative_library_editor_plugin.cpp +msgid "Dynamic Library" +msgstr "" + +#: modules/gdnative/gdnative_library_editor_plugin.cpp +msgid "Add an architecture entry" +msgstr "" + +#: modules/gdnative/gdnative_library_editor_plugin.cpp +msgid "GDNativeLibrary" +msgstr "" + +#: modules/gdnative/gdnative_library_singleton_editor.cpp +msgid "Library" +msgstr "" + +#: modules/gdnative/gdnative_library_singleton_editor.cpp +msgid "Status" +msgstr "" + +#: modules/gdnative/gdnative_library_singleton_editor.cpp +msgid "Libraries: " +msgstr "" + +#: modules/gdnative/register_types.cpp +msgid "GDNative" +msgstr "" + +#: modules/gdscript/gdscript_functions.cpp +msgid "Step argument is zero!" +msgstr "" + +#: modules/gdscript/gdscript_functions.cpp +msgid "Not a script with an instance" +msgstr "" + +#: modules/gdscript/gdscript_functions.cpp +msgid "Not based on a script" +msgstr "" + +#: modules/gdscript/gdscript_functions.cpp +msgid "Not based on a resource file" +msgstr "" + +#: modules/gdscript/gdscript_functions.cpp +msgid "Invalid instance dictionary format (missing @path)" +msgstr "" + +#: modules/gdscript/gdscript_functions.cpp +msgid "Invalid instance dictionary format (can't load script at @path)" +msgstr "" + +#: modules/gdscript/gdscript_functions.cpp +msgid "Invalid instance dictionary format (invalid script at @path)" +msgstr "" + +#: modules/gdscript/gdscript_functions.cpp +msgid "Invalid instance dictionary (invalid subclasses)" +msgstr "" + +#: modules/gdscript/gdscript_functions.cpp +msgid "Object can't provide a length." +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Next Plane" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Previous Plane" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Plane:" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Next Floor" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Previous Floor" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Floor:" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "GridMap Delete Selection" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "GridMap Fill Selection" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "GridMap Duplicate Selection" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "GridMap Paint" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Grid Map" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Snap View" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Clip Disabled" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Clip Above" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Clip Below" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Edit X Axis" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Edit Y Axis" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Edit Z Axis" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Cursor Rotate X" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Cursor Rotate Y" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Cursor Rotate Z" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Cursor Back Rotate X" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Cursor Back Rotate Y" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Cursor Back Rotate Z" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Cursor Clear Rotation" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Create Area" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Create Exterior Connector" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Erase Area" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Clear Selection" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Fill Selection" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "GridMap Settings" +msgstr "" + +#: modules/gridmap/grid_map_editor_plugin.cpp +msgid "Pick Distance:" +msgstr "" + +#: modules/mono/csharp_script.cpp +msgid "Class name can't be a reserved keyword" +msgstr "" + +#: modules/mono/editor/godotsharp_editor.cpp +msgid "Generating solution..." +msgstr "" + +#: modules/mono/editor/godotsharp_editor.cpp +msgid "Generating C# project..." +msgstr "" + +#: modules/mono/editor/godotsharp_editor.cpp +msgid "Failed to create solution." +msgstr "" + +#: modules/mono/editor/godotsharp_editor.cpp +msgid "Failed to save solution." +msgstr "" + +#: modules/mono/editor/godotsharp_editor.cpp +msgid "Done" +msgstr "" + +#: modules/mono/editor/godotsharp_editor.cpp +msgid "Failed to create C# project." +msgstr "" + +#: modules/mono/editor/godotsharp_editor.cpp +msgid "Mono" +msgstr "" + +#: modules/mono/editor/godotsharp_editor.cpp +msgid "About C# support" +msgstr "" + +#: modules/mono/editor/godotsharp_editor.cpp +msgid "Create C# solution" +msgstr "" + +#: modules/mono/editor/mono_bottom_panel.cpp +msgid "Builds" +msgstr "" + +#: modules/mono/editor/mono_bottom_panel.cpp +msgid "Build Project" +msgstr "" + +#: modules/mono/editor/mono_bottom_panel.cpp +msgid "View log" +msgstr "" + +#: modules/mono/mono_gd/gd_mono_utils.cpp +msgid "End of inner exception stack trace" +msgstr "" + +#: modules/recast/navigation_mesh_editor_plugin.cpp +msgid "Bake NavMesh" +msgstr "" + +#: modules/recast/navigation_mesh_editor_plugin.cpp +msgid "Clear the navigation mesh." +msgstr "" + +#: modules/recast/navigation_mesh_generator.cpp +msgid "Setting up Configuration..." +msgstr "" + +#: modules/recast/navigation_mesh_generator.cpp +msgid "Calculating grid size..." +msgstr "" + +#: modules/recast/navigation_mesh_generator.cpp +msgid "Creating heightfield..." +msgstr "" + +#: modules/recast/navigation_mesh_generator.cpp +msgid "Marking walkable triangles..." +msgstr "" + +#: modules/recast/navigation_mesh_generator.cpp +msgid "Constructing compact heightfield..." +msgstr "" + +#: modules/recast/navigation_mesh_generator.cpp +msgid "Eroding walkable area..." +msgstr "" + +#: modules/recast/navigation_mesh_generator.cpp +msgid "Partitioning..." +msgstr "" + +#: modules/recast/navigation_mesh_generator.cpp +msgid "Creating contours..." +msgstr "" + +#: modules/recast/navigation_mesh_generator.cpp +msgid "Creating polymesh..." +msgstr "" + +#: modules/recast/navigation_mesh_generator.cpp +msgid "Converting to native navigation mesh..." +msgstr "" + +#: modules/recast/navigation_mesh_generator.cpp +msgid "Navigation Mesh Generator Setup:" +msgstr "" + +#: modules/recast/navigation_mesh_generator.cpp +msgid "Parsing Geometry..." +msgstr "" + +#: modules/recast/navigation_mesh_generator.cpp +msgid "Done!" +msgstr "" + +#: modules/visual_script/visual_script.cpp +msgid "" +"A node yielded without working memory, please read the docs on how to yield " +"properly!" +msgstr "" + +#: modules/visual_script/visual_script.cpp +msgid "" +"Node yielded, but did not return a function state in the first working " +"memory." +msgstr "" + +#: modules/visual_script/visual_script.cpp +msgid "" +"Return value must be assigned to first element of node working memory! Fix " +"your node please." +msgstr "" + +#: modules/visual_script/visual_script.cpp +msgid "Node returned an invalid sequence output: " +msgstr "" + +#: modules/visual_script/visual_script.cpp +msgid "Found sequence bit but not the node in the stack, report bug!" +msgstr "" + +#: modules/visual_script/visual_script.cpp +msgid "Stack overflow with stack depth: " +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Change Signal Arguments" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Change Argument Type" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Change Argument name" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Set Variable Default Value" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Set Variable Type" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Variables:" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Name is not a valid identifier:" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Name already in use by another func/var/signal:" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Rename Function" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Rename Variable" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Rename Signal" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Add Function" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Add Variable" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Add Signal" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Change Expression" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Remove VisualScript Nodes" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Duplicate VisualScript Nodes" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Hold %s to drop a Getter. Hold Shift to drop a generic signature." +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Hold Ctrl to drop a Getter. Hold Shift to drop a generic signature." +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Hold %s to drop a simple reference to the node." +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Hold Ctrl to drop a simple reference to the node." +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Hold %s to drop a Variable Setter." +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Hold Ctrl to drop a Variable Setter." +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Add Preload Node" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Add Node(s) From Tree" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Add Getter Property" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Add Setter Property" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Change Base Type" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Move Node(s)" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Remove VisualScript Node" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Connect Nodes" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Connect Node Data" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Connect Node Sequence" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Script already has function '%s'" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Change Input Value" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Resize Comment" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Can't copy the function node." +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Clipboard is empty!" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Paste VisualScript Nodes" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Remove Function" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Remove Variable" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Editing Variable:" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Remove Signal" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Editing Signal:" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Base Type:" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Members:" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Available Nodes:" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Select or create a function to edit graph" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Edit Signal Arguments:" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Edit Variable:" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Delete Selected" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Find Node Type" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Copy Nodes" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Cut Nodes" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Paste Nodes" +msgstr "" + +#: modules/visual_script/visual_script_editor.cpp +msgid "Edit Member" +msgstr "" + +#: modules/visual_script/visual_script_flow_control.cpp +msgid "Input type not iterable: " +msgstr "" + +#: modules/visual_script/visual_script_flow_control.cpp +msgid "Iterator became invalid" +msgstr "" + +#: modules/visual_script/visual_script_flow_control.cpp +msgid "Iterator became invalid: " +msgstr "" + +#: modules/visual_script/visual_script_func_nodes.cpp +msgid "Invalid index property name." +msgstr "" + +#: modules/visual_script/visual_script_func_nodes.cpp +msgid "Base object is not a Node!" +msgstr "" + +#: modules/visual_script/visual_script_func_nodes.cpp +msgid "Path does not lead Node!" +msgstr "" + +#: modules/visual_script/visual_script_func_nodes.cpp +msgid "Invalid index property name '%s' in node %s." +msgstr "" + +#: modules/visual_script/visual_script_nodes.cpp +msgid ": Invalid argument of type: " +msgstr "" + +#: modules/visual_script/visual_script_nodes.cpp +msgid ": Invalid arguments: " +msgstr "" + +#: modules/visual_script/visual_script_nodes.cpp +msgid "VariableGet not found in script: " +msgstr "" + +#: modules/visual_script/visual_script_nodes.cpp +msgid "VariableSet not found in script: " +msgstr "" + +#: modules/visual_script/visual_script_nodes.cpp +msgid "Custom node has no _step() method, can't process graph." +msgstr "" + +#: modules/visual_script/visual_script_nodes.cpp +msgid "" +"Invalid return value from _step(), must be integer (seq out), or string " +"(error)." +msgstr "" + +#: modules/visual_script/visual_script_property_selector.cpp +msgid "Search VisualScript" +msgstr "" + +#: modules/visual_script/visual_script_property_selector.cpp +msgid "Get %s" +msgstr "" + +#: modules/visual_script/visual_script_property_selector.cpp +msgid "Set %s" +msgstr "" + +#: platform/android/export/export.cpp +msgid "Package name is missing." +msgstr "" + +#: platform/android/export/export.cpp +msgid "Package segments must be of non-zero length." +msgstr "" + +#: platform/android/export/export.cpp +msgid "The character '%s' is not allowed in Android application package names." +msgstr "" + +#: platform/android/export/export.cpp +msgid "A digit cannot be the first character in a package segment." +msgstr "" + +#: platform/android/export/export.cpp +msgid "The character '%s' cannot be the first character in a package segment." +msgstr "" + +#: platform/android/export/export.cpp +msgid "The package must have at least one '.' separator." +msgstr "" + +#: platform/android/export/export.cpp +msgid "ADB executable not configured in the Editor Settings." +msgstr "" + +#: platform/android/export/export.cpp +msgid "OpenJDK jarsigner not configured in the Editor Settings." +msgstr "" + +#: platform/android/export/export.cpp +msgid "Debug keystore not configured in the Editor Settings nor in the preset." +msgstr "" + +#: platform/android/export/export.cpp +msgid "Invalid public key for APK expansion." +msgstr "" + +#: platform/android/export/export.cpp +msgid "Invalid package name:" +msgstr "" + +#: platform/iphone/export/export.cpp +msgid "Identifier is missing." +msgstr "" + +#: platform/iphone/export/export.cpp +msgid "Identifier segments must be of non-zero length." +msgstr "" + +#: platform/iphone/export/export.cpp +msgid "The character '%s' is not allowed in Identifier." +msgstr "" + +#: platform/iphone/export/export.cpp +msgid "A digit cannot be the first character in a Identifier segment." +msgstr "" + +#: platform/iphone/export/export.cpp +msgid "" +"The character '%s' cannot be the first character in a Identifier segment." +msgstr "" + +#: platform/iphone/export/export.cpp +msgid "The Identifier must have at least one '.' separator." +msgstr "" + +#: platform/iphone/export/export.cpp +msgid "App Store Team ID not specified - cannot configure the project." +msgstr "" + +#: platform/iphone/export/export.cpp +msgid "Invalid Identifier:" +msgstr "" + +#: platform/iphone/export/export.cpp +msgid "Required icon is not specified in the preset." +msgstr "" + +#: platform/javascript/export/export.cpp +msgid "Run in Browser" +msgstr "" + +#: platform/javascript/export/export.cpp +msgid "Run exported HTML in the system's default browser." +msgstr "" + +#: platform/javascript/export/export.cpp +msgid "Could not write file:" +msgstr "" + +#: platform/javascript/export/export.cpp +msgid "Could not open template for export:" +msgstr "" + +#: platform/javascript/export/export.cpp +msgid "Invalid export template:" +msgstr "" + +#: platform/javascript/export/export.cpp +msgid "Could not read custom HTML shell:" +msgstr "" + +#: platform/javascript/export/export.cpp +msgid "Could not read boot splash image file:" +msgstr "" + +#: platform/javascript/export/export.cpp +msgid "Using default boot splash image." +msgstr "" + +#: platform/uwp/export/export.cpp +msgid "Invalid package unique name." +msgstr "" + +#: platform/uwp/export/export.cpp +msgid "Invalid product GUID." +msgstr "" + +#: platform/uwp/export/export.cpp +msgid "Invalid publisher GUID." +msgstr "" + +#: platform/uwp/export/export.cpp +msgid "Invalid background color." +msgstr "" + +#: platform/uwp/export/export.cpp +msgid "Invalid Store Logo image dimensions (should be 50x50)." +msgstr "" + +#: platform/uwp/export/export.cpp +msgid "Invalid square 44x44 logo image dimensions (should be 44x44)." +msgstr "" + +#: platform/uwp/export/export.cpp +msgid "Invalid square 71x71 logo image dimensions (should be 71x71)." +msgstr "" + +#: platform/uwp/export/export.cpp +msgid "Invalid square 150x150 logo image dimensions (should be 150x150)." +msgstr "" + +#: platform/uwp/export/export.cpp +msgid "Invalid square 310x310 logo image dimensions (should be 310x310)." +msgstr "" + +#: platform/uwp/export/export.cpp +msgid "Invalid wide 310x150 logo image dimensions (should be 310x150)." +msgstr "" + +#: platform/uwp/export/export.cpp +msgid "Invalid splash screen image dimensions (should be 620x300)." +msgstr "" + +#: scene/2d/animated_sprite.cpp +msgid "" +"A SpriteFrames resource must be created or set in the 'Frames' property in " +"order for AnimatedSprite to display frames." +msgstr "" + +#: scene/2d/canvas_modulate.cpp +msgid "" +"Only one visible CanvasModulate is allowed per scene (or set of instanced " +"scenes). The first created one will work, while the rest will be ignored." +msgstr "" + +#: scene/2d/collision_object_2d.cpp +msgid "" +"This node has no shape, so it can't collide or interact with other objects.\n" +"Consider adding a CollisionShape2D or CollisionPolygon2D as a child to " +"define its shape." +msgstr "" + +#: scene/2d/collision_polygon_2d.cpp +msgid "" +"CollisionPolygon2D only serves to provide a collision shape to a " +"CollisionObject2D derived node. Please only use it as a child of Area2D, " +"StaticBody2D, RigidBody2D, KinematicBody2D, etc. to give them a shape." +msgstr "" + +#: scene/2d/collision_polygon_2d.cpp +msgid "An empty CollisionPolygon2D has no effect on collision." +msgstr "" + +#: scene/2d/collision_shape_2d.cpp +msgid "" +"CollisionShape2D only serves to provide a collision shape to a " +"CollisionObject2D derived node. Please only use it as a child of Area2D, " +"StaticBody2D, RigidBody2D, KinematicBody2D, etc. to give them a shape." +msgstr "" + +#: scene/2d/collision_shape_2d.cpp +msgid "" +"A shape must be provided for CollisionShape2D to function. Please create a " +"shape resource for it!" +msgstr "" + +#: scene/2d/cpu_particles_2d.cpp +msgid "" +"CPUParticles2D animation requires the usage of a CanvasItemMaterial with " +"\"Particles Animation\" enabled." +msgstr "" + +#: scene/2d/light_2d.cpp +msgid "" +"A texture with the shape of the light must be supplied to the 'texture' " +"property." +msgstr "" + +#: scene/2d/light_occluder_2d.cpp +msgid "" +"An occluder polygon must be set (or drawn) for this occluder to take effect." +msgstr "" + +#: scene/2d/light_occluder_2d.cpp +msgid "The occluder polygon for this occluder is empty. Please draw a polygon!" +msgstr "" + +#: scene/2d/navigation_polygon.cpp +msgid "" +"A NavigationPolygon resource must be set or created for this node to work. " +"Please set a property or draw a polygon." +msgstr "" + +#: scene/2d/navigation_polygon.cpp +msgid "" +"NavigationPolygonInstance must be a child or grandchild to a Navigation2D " +"node. It only provides navigation data." +msgstr "" + +#: scene/2d/parallax_layer.cpp +msgid "" +"ParallaxLayer node only works when set as child of a ParallaxBackground node." +msgstr "" + +#: scene/2d/particles_2d.cpp +msgid "" +"GPU-based particles are not supported by the GLES2 video driver.\n" +"Use the CPUParticles2D node instead. You can use the \"Convert to " +"CPUParticles\" option for this purpose." +msgstr "" + +#: scene/2d/particles_2d.cpp scene/3d/particles.cpp +msgid "" +"A material to process the particles is not assigned, so no behavior is " +"imprinted." +msgstr "" + +#: scene/2d/particles_2d.cpp +msgid "" +"Particles2D animation requires the usage of a CanvasItemMaterial with " +"\"Particles Animation\" enabled." +msgstr "" + +#: scene/2d/path_2d.cpp +msgid "PathFollow2D only works when set as a child of a Path2D node." +msgstr "" + +#: scene/2d/physics_body_2d.cpp +msgid "" +"Size changes to RigidBody2D (in character or rigid modes) will be overridden " +"by the physics engine when running.\n" +"Change the size in children collision shapes instead." +msgstr "" + +#: scene/2d/remote_transform_2d.cpp +msgid "Path property must point to a valid Node2D node to work." +msgstr "" + +#: scene/2d/skeleton_2d.cpp +msgid "This Bone2D chain should end at a Skeleton2D node." +msgstr "" + +#: scene/2d/skeleton_2d.cpp +msgid "A Bone2D only works with a Skeleton2D or another Bone2D as parent node." +msgstr "" + +#: scene/2d/skeleton_2d.cpp +msgid "" +"This bone lacks a proper REST pose. Go to the Skeleton2D node and set one." +msgstr "" + +#: scene/2d/visibility_notifier_2d.cpp +msgid "" +"VisibilityEnable2D works best when used with the edited scene root directly " +"as parent." +msgstr "" + +#: scene/3d/arvr_nodes.cpp +msgid "ARVRCamera must have an ARVROrigin node as its parent" +msgstr "" + +#: scene/3d/arvr_nodes.cpp +msgid "ARVRController must have an ARVROrigin node as its parent" +msgstr "" + +#: scene/3d/arvr_nodes.cpp +msgid "" +"The controller id must not be 0 or this controller will not be bound to an " +"actual controller" +msgstr "" + +#: scene/3d/arvr_nodes.cpp +msgid "ARVRAnchor must have an ARVROrigin node as its parent" +msgstr "" + +#: scene/3d/arvr_nodes.cpp +msgid "" +"The anchor id must not be 0 or this anchor will not be bound to an actual " +"anchor" +msgstr "" + +#: scene/3d/arvr_nodes.cpp +msgid "ARVROrigin requires an ARVRCamera child node" +msgstr "" + +#: scene/3d/baked_lightmap.cpp +msgid "%d%%" +msgstr "" + +#: scene/3d/baked_lightmap.cpp +msgid "(Time Left: %d:%02d s)" +msgstr "" + +#: scene/3d/baked_lightmap.cpp +msgid "Plotting Meshes: " +msgstr "" + +#: scene/3d/baked_lightmap.cpp +msgid "Plotting Lights:" +msgstr "" + +#: scene/3d/baked_lightmap.cpp scene/3d/gi_probe.cpp +msgid "Finishing Plot" +msgstr "" + +#: scene/3d/baked_lightmap.cpp +msgid "Lighting Meshes: " +msgstr "" + +#: scene/3d/collision_object.cpp +msgid "" +"This node has no shape, so it can't collide or interact with other objects.\n" +"Consider adding a CollisionShape or CollisionPolygon as a child to define " +"its shape." +msgstr "" + +#: scene/3d/collision_polygon.cpp +msgid "" +"CollisionPolygon only serves to provide a collision shape to a " +"CollisionObject derived node. Please only use it as a child of Area, " +"StaticBody, RigidBody, KinematicBody, etc. to give them a shape." +msgstr "" + +#: scene/3d/collision_polygon.cpp +msgid "An empty CollisionPolygon has no effect on collision." +msgstr "" + +#: scene/3d/collision_shape.cpp +msgid "" +"CollisionShape only serves to provide a collision shape to a CollisionObject " +"derived node. Please only use it as a child of Area, StaticBody, RigidBody, " +"KinematicBody, etc. to give them a shape." +msgstr "" + +#: scene/3d/collision_shape.cpp +msgid "" +"A shape must be provided for CollisionShape to function. Please create a " +"shape resource for it!" +msgstr "" + +#: scene/3d/collision_shape.cpp +msgid "" +"Plane shapes don't work well and will be removed in future versions. Please " +"don't use them." +msgstr "" + +#: scene/3d/cpu_particles.cpp +msgid "Nothing is visible because no mesh has been assigned." +msgstr "" + +#: scene/3d/cpu_particles.cpp +msgid "" +"CPUParticles animation requires the usage of a SpatialMaterial with " +"\"Billboard Particles\" enabled." +msgstr "" + +#: scene/3d/gi_probe.cpp +msgid "Plotting Meshes" +msgstr "" + +#: scene/3d/gi_probe.cpp +msgid "" +"GIProbes are not supported by the GLES2 video driver.\n" +"Use a BakedLightmap instead." +msgstr "" + +#: scene/3d/navigation_mesh.cpp +msgid "A NavigationMesh resource must be set or created for this node to work." +msgstr "" + +#: scene/3d/navigation_mesh.cpp +msgid "" +"NavigationMeshInstance must be a child or grandchild to a Navigation node. " +"It only provides navigation data." +msgstr "" + +#: scene/3d/particles.cpp +msgid "" +"GPU-based particles are not supported by the GLES2 video driver.\n" +"Use the CPUParticles node instead. You can use the \"Convert to CPUParticles" +"\" option for this purpose." +msgstr "" + +#: scene/3d/particles.cpp +msgid "" +"Nothing is visible because meshes have not been assigned to draw passes." +msgstr "" + +#: scene/3d/particles.cpp +msgid "" +"Particles animation requires the usage of a SpatialMaterial with \"Billboard " +"Particles\" enabled." +msgstr "" + +#: scene/3d/path.cpp +msgid "PathFollow only works when set as a child of a Path node." +msgstr "" + +#: scene/3d/path.cpp +msgid "" +"PathFollow ROTATION_ORIENTED requires \"Up Vector\" enabled in its parent " +"Path's Curve resource." +msgstr "" + +#: scene/3d/physics_body.cpp +msgid "" +"Size changes to RigidBody (in character or rigid modes) will be overridden " +"by the physics engine when running.\n" +"Change the size in children collision shapes instead." +msgstr "" + +#: scene/3d/remote_transform.cpp +msgid "Path property must point to a valid Spatial node to work." +msgstr "" + +#: scene/3d/soft_body.cpp +msgid "This body will be ignored until you set a mesh" +msgstr "" + +#: scene/3d/soft_body.cpp +msgid "" +"Size changes to SoftBody will be overridden by the physics engine when " +"running.\n" +"Change the size in children collision shapes instead." +msgstr "" + +#: scene/3d/sprite_3d.cpp +msgid "" +"A SpriteFrames resource must be created or set in the 'Frames' property in " +"order for AnimatedSprite3D to display frames." +msgstr "" + +#: scene/3d/vehicle_body.cpp +msgid "" +"VehicleWheel serves to provide a wheel system to a VehicleBody. Please use " +"it as a child of a VehicleBody." +msgstr "" + +#: scene/3d/world_environment.cpp +msgid "WorldEnvironment needs an Environment resource." +msgstr "" + +#: scene/3d/world_environment.cpp +msgid "" +"Only one WorldEnvironment is allowed per scene (or set of instanced scenes)." +msgstr "" + +#: scene/3d/world_environment.cpp +msgid "" +"This WorldEnvironment is ignored. Either add a Camera (for 3D scenes) or set " +"this environment's Background Mode to Canvas (for 2D scenes)." +msgstr "" + +#: scene/animation/animation_blend_tree.cpp +msgid "On BlendTree node '%s', animation not found: '%s'" +msgstr "" + +#: scene/animation/animation_blend_tree.cpp +msgid "Animation not found: '%s'" +msgstr "" + +#: scene/animation/animation_tree.cpp +msgid "In node '%s', invalid animation: '%s'." +msgstr "" + +#: scene/animation/animation_tree.cpp +msgid "Invalid animation: '%s'." +msgstr "" + +#: scene/animation/animation_tree.cpp +msgid "Nothing connected to input '%s' of node '%s'." +msgstr "" + +#: scene/animation/animation_tree.cpp +msgid "A root AnimationNode for the graph is not set." +msgstr "" + +#: scene/animation/animation_tree.cpp +msgid "Path to an AnimationPlayer node containing animations is not set." +msgstr "" + +#: scene/animation/animation_tree.cpp +msgid "Path set for AnimationPlayer does not lead to an AnimationPlayer node." +msgstr "" + +#: scene/animation/animation_tree.cpp +msgid "AnimationPlayer root is not a valid node." +msgstr "" + +#: scene/animation/animation_tree_player.cpp +msgid "This node has been deprecated. Use AnimationTree instead." +msgstr "" + +#: scene/gui/color_picker.cpp +msgid "Pick a color from the screen." +msgstr "" + +#: scene/gui/color_picker.cpp +msgid "Raw Mode" +msgstr "" + +#: scene/gui/color_picker.cpp +msgid "Switch between hexadecimal and code values." +msgstr "" + +#: scene/gui/color_picker.cpp +msgid "Add current color as a preset." +msgstr "" + +#: scene/gui/container.cpp +msgid "" +"Container by itself serves no purpose unless a script configures it's " +"children placement behavior.\n" +"If you dont't intend to add a script, then please use a plain 'Control' node " +"instead." +msgstr "" + +#: scene/gui/dialogs.cpp +msgid "Alert!" +msgstr "" + +#: scene/gui/dialogs.cpp +msgid "Please Confirm..." +msgstr "" + +#: scene/gui/file_dialog.cpp +msgid "Go to parent folder." +msgstr "" + +#: scene/gui/popup.cpp +msgid "" +"Popups will hide by default unless you call popup() or any of the popup*() " +"functions. Making them visible for editing is fine though, but they will " +"hide upon running." +msgstr "" + +#: scene/gui/range.cpp +msgid "If exp_edit is true min_value must be > 0." +msgstr "" + +#: scene/gui/scroll_container.cpp +msgid "" +"ScrollContainer is intended to work with a single child control.\n" +"Use a container as child (VBox,HBox,etc), or a Control and set the custom " +"minimum size manually." +msgstr "" + +#: scene/gui/tree.cpp +msgid "(Other)" +msgstr "" + +#: scene/main/scene_tree.cpp +msgid "" +"Default Environment as specified in Project Settings (Rendering -> " +"Environment -> Default Environment) could not be loaded." +msgstr "" + +#: scene/main/viewport.cpp +msgid "" +"This viewport is not set as render target. If you intend for it to display " +"its contents directly to the screen, make it a child of a Control so it can " +"obtain a size. Otherwise, make it a RenderTarget and assign its internal " +"texture to some node for display." +msgstr "" + +#: scene/resources/dynamic_font.cpp +msgid "Error initializing FreeType." +msgstr "" + +#: scene/resources/dynamic_font.cpp +msgid "Unknown font format." +msgstr "" + +#: scene/resources/dynamic_font.cpp +msgid "Error loading font." +msgstr "" + +#: scene/resources/dynamic_font.cpp +msgid "Invalid font size." +msgstr "" + +#: scene/resources/visual_shader.cpp +msgid "Input" +msgstr "" + +#: scene/resources/visual_shader_nodes.cpp +msgid "Invalid source for shader." +msgstr "" + +#: servers/visual/shader_language.cpp +msgid "Assignment to function." +msgstr "" + +#: servers/visual/shader_language.cpp +msgid "Assignment to uniform." +msgstr "" + +#: servers/visual/shader_language.cpp +msgid "Varyings can only be assigned in vertex function." +msgstr "" diff --git a/editor/translations/es.po b/editor/translations/es.po index f66b06cccd..783344b9de 100644 --- a/editor/translations/es.po +++ b/editor/translations/es.po @@ -38,12 +38,13 @@ # emma peel <emma.peel@riseup.net>, 2018. # Vicente Juárez <vijuarez@uc.cl>, 2019. # juan david julio <illus.kun@gmail.com>, 2019. +# Patrick Zoch Alves <patrickzochalves@gmail.com>, 2019. msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-04-19 16:33+0000\n" -"Last-Translator: eon-s <emanuel.segretin@gmail.com>\n" +"PO-Revision-Date: 2019-04-30 14:39+0000\n" +"Last-Translator: Javier Ocampos <xavier.ocampos@gmail.com>\n" "Language-Team: Spanish <https://hosted.weblate.org/projects/godot-engine/" "godot/es/>\n" "Language: es\n" @@ -51,7 +52,7 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=n != 1;\n" -"X-Generator: Weblate 3.6-dev\n" +"X-Generator: Weblate 3.6.1\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -189,14 +190,20 @@ msgid "Animation Playback Track" msgstr "Pista de Reproducción de Animación" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Agregar Pista" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Tiempo de Duración de la Animación (segundos)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Tiempo de Duración de la Animación (segundos)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Agregar Pista" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Loop de Animación" @@ -223,7 +230,7 @@ msgstr "Act./Desact. esta pista." #: editor/animation_track_editor.cpp msgid "Update Mode (How this property is set)" -msgstr "Modo de Actualización (Como esta configurada esta propiedad)" +msgstr "Modo de Actualización (Como esta configurada esta propriedad)" #: editor/animation_track_editor.cpp msgid "Interpolation Mode" @@ -453,9 +460,8 @@ msgid "Group tracks by node or display them as plain list." msgstr "Agrupar las pistas por nodo o mostrarlas como una lista plana." #: editor/animation_track_editor.cpp -#, fuzzy msgid "Snap:" -msgstr "Snap" +msgstr "Snap:" #: editor/animation_track_editor.cpp msgid "Animation step value." @@ -463,7 +469,7 @@ msgstr "Valor de step de animación." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "Segundos" #: editor/animation_track_editor.cpp msgid "FPS" @@ -4856,20 +4862,19 @@ msgstr "Disposición" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Translation mask for inserting keys." -msgstr "" +msgstr "Máscara de desplazamiento para insertar claves." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Rotation mask for inserting keys." -msgstr "" +msgstr "Máscara de rotación para insertar claves." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Scale mask for inserting keys." -msgstr "" +msgstr "Máscara de escala para insertar claves." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Insert keys (based on mask)." -msgstr "Insertar Claves (Ins)" +msgstr "Insertar claves (basadas en máscara)." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "" @@ -4878,11 +4883,15 @@ msgid "" "Keys are only added to existing tracks, no new tracks will be created.\n" "Keys must be inserted manually for the first time." msgstr "" +"Inserción automática de claves cuando los objetos son desplazados, rotados " +"en escala (basado en máscara).\n" +"Las claves sólo se añaden a las pistas existentes, no se crearán nuevas " +"pistas.\n" +"Las claves deben insertarse manualmente por primera vez." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Auto Insert Key" -msgstr "Insertar clave de animación" +msgstr "Auto Insertar Clave" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Insert Key (Existing Tracks)" @@ -5877,9 +5886,8 @@ msgid "Save Theme As..." msgstr "Guardar tema como..." #: editor/plugins/script_editor_plugin.cpp -#, fuzzy msgid "%s Class Reference" -msgstr " Referencia de clase" +msgstr "%s Referencia de Clase" #: editor/plugins/script_editor_plugin.cpp msgid "Toggle alphabetical sorting of the method list." @@ -6703,24 +6711,20 @@ msgid "Nameless gizmo" msgstr "Gizmo sin nombre" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Mesh2D" -msgstr "Crear Mesh 2D" +msgstr "Crear Mesh2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Polygon2D" -msgstr "Crear Polygon3D" +msgstr "Crear Polygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D" -msgstr "Crear PolÃgono de Colisión" +msgstr "Crear CollisionPolygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D" -msgstr "Crear polÃgono oclusor" +msgstr "Crear LightOccluder2D" #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite is empty!" @@ -6735,43 +6739,36 @@ msgid "Invalid geometry, can't replace by mesh." msgstr "GeometrÃa inválida, no se puede reemplazar por mesh." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create polygon." -msgstr "GeometrÃa inválida, no se puede reemplazar por mesh." +msgstr "GeometrÃa inválida, no es posible crear un polÃgono." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create collision polygon." -msgstr "GeometrÃa inválida, no se puede reemplazar por mesh." +msgstr "GeometrÃa inválida, no es posible crear un polÃgono de colisión." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create light occluder." -msgstr "GeometrÃa inválida, no se puede reemplazar por mesh." +msgstr "GeometrÃa inválida, no es posible crear un oclusor de luz." #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite" msgstr "Sprite" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Mesh2D" -msgstr "Convertir a Mesh 2D" +msgstr "Convertir a Mesh2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Polygon2D" -msgstr "Mover polÃgono" +msgstr "Convertir a Polygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D Sibling" -msgstr "Crear PolÃgono de Colisión" +msgstr "Crear hermano de CollisionPolygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D Sibling" -msgstr "Crear polÃgono oclusor" +msgstr "Crear hermano de LightOccluder2D" #: editor/plugins/sprite_editor_plugin.cpp msgid "Simplification: " @@ -7357,9 +7354,8 @@ msgid "Duplicate Nodes" msgstr "Duplicar Nodos" #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Delete Nodes" -msgstr "Eliminar Nodo" +msgstr "Eliminar Nodos" #: editor/plugins/visual_shader_editor_plugin.cpp msgid "Visual Shader Input Type Changed" diff --git a/editor/translations/es_AR.po b/editor/translations/es_AR.po index e27603d799..39c41edab3 100644 --- a/editor/translations/es_AR.po +++ b/editor/translations/es_AR.po @@ -10,12 +10,14 @@ # Reynaldo Cruz <rcruz60@gmail.com>, 2018. # Javier Ocampos <xavier.ocampos@gmail.com>, 2018, 2019. # Andrés S <andres.segovia.dev@gmail.com>, 2019. +# Florencia Menéndez <mariaflormz2@gmail.com>, 2019. +# roger <616steam@gmail.com>, 2019. msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-03-30 20:04+0000\n" -"Last-Translator: Lisandro Lorea <lisandrolorea@gmail.com>\n" +"PO-Revision-Date: 2019-05-16 18:49+0000\n" +"Last-Translator: roger <616steam@gmail.com>\n" "Language-Team: Spanish (Argentina) <https://hosted.weblate.org/projects/" "godot-engine/godot/es_AR/>\n" "Language: es_AR\n" @@ -23,7 +25,7 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=n != 1;\n" -"X-Generator: Weblate 3.6-dev\n" +"X-Generator: Weblate 3.7-dev\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -68,7 +70,7 @@ msgstr "En la llamada a '%s':" #: editor/animation_bezier_editor.cpp #: editor/plugins/asset_library_editor_plugin.cpp msgid "Free" -msgstr "Libre" +msgstr "Gratis" #: editor/animation_bezier_editor.cpp msgid "Balanced" @@ -160,14 +162,20 @@ msgid "Animation Playback Track" msgstr "Pista de Reproducción de Animación" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Agregar Pista" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Tiempo de Duración de la Animación (segundos)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Tiempo de Duración de la Animación (segundos)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Agregar Pista" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Loop de Animación" @@ -423,9 +431,8 @@ msgid "Group tracks by node or display them as plain list." msgstr "Agrupar las pistas por nodo o mostrarlas como una lista plana." #: editor/animation_track_editor.cpp -#, fuzzy msgid "Snap:" -msgstr "Esnapear" +msgstr "Snap:" #: editor/animation_track_editor.cpp msgid "Animation step value." @@ -433,7 +440,7 @@ msgstr "Valor de paso de animación." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "Segundos" #: editor/animation_track_editor.cpp msgid "FPS" @@ -4821,20 +4828,20 @@ msgstr "Layout" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Translation mask for inserting keys." -msgstr "" +msgstr "Máscara de traslación para insertar claves." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Rotation mask for inserting keys." -msgstr "" +msgstr "Máscara de rotación para insertar claves." #: editor/plugins/canvas_item_editor_plugin.cpp +#, fuzzy msgid "Scale mask for inserting keys." -msgstr "" +msgstr "Máscara de rotación para insertar claves." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Insert keys (based on mask)." -msgstr "Insertar Claves (Ins)" +msgstr "Insertar claves (basadas en máscara)." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "" @@ -4843,11 +4850,15 @@ msgid "" "Keys are only added to existing tracks, no new tracks will be created.\n" "Keys must be inserted manually for the first time." msgstr "" +"Inserción automática de claves cuando los objetos son trasladados, rotados o " +"escalados (basado en máscara).\n" +"Las claves sólo se añaden a las pistas existentes, no se crearán nuevas " +"pistas.\n" +"Las claves deben insertarse manualmente por primera vez." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Auto Insert Key" -msgstr "Insertar Clave de Animación" +msgstr "Auto Insertar Clave" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Insert Key (Existing Tracks)" @@ -5837,9 +5848,8 @@ msgid "Save Theme As..." msgstr "Guardar Tema Como..." #: editor/plugins/script_editor_plugin.cpp -#, fuzzy msgid "%s Class Reference" -msgstr " Referencia de Clases" +msgstr "%s Referencia de Clase" #: editor/plugins/script_editor_plugin.cpp msgid "Toggle alphabetical sorting of the method list." @@ -6663,24 +6673,20 @@ msgid "Nameless gizmo" msgstr "Gizmo sin nombre" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Mesh2D" -msgstr "Crear Mesh 2D" +msgstr "Crear Mesh2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Polygon2D" -msgstr "Crear Polygon3D" +msgstr "Crear Polygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D" -msgstr "Crear PolÃgono de Colisión" +msgstr "Crear CollisionPolygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D" -msgstr "Crear PolÃgono Oclusor" +msgstr "Crear LightOccluder2D" #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite is empty!" @@ -6695,43 +6701,36 @@ msgid "Invalid geometry, can't replace by mesh." msgstr "GeometrÃa inválida, no se puede reemplazar por mesh." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create polygon." -msgstr "GeometrÃa inválida, no se puede reemplazar por mesh." +msgstr "GeometrÃa inválida, no es posible crear un polÃgono." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create collision polygon." -msgstr "GeometrÃa inválida, no se puede reemplazar por mesh." +msgstr "GeometrÃa inválida, no es posible crear un polÃgono de colisión." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create light occluder." -msgstr "GeometrÃa inválida, no se puede reemplazar por mesh." +msgstr "GeometrÃa inválida, no es posible crear un oclusor de luz." #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite" msgstr "Sprite" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Mesh2D" -msgstr "Convertir A Mesh 2D" +msgstr "Convertir a Mesh2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Polygon2D" -msgstr "Mover PolÃgono" +msgstr "Convertir a Polygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D Sibling" -msgstr "Crear PolÃgono de Colisión" +msgstr "Crear hermano de CollisionPolygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D Sibling" -msgstr "Crear PolÃgono Oclusor" +msgstr "Crear hermano de LightOccluder2D" #: editor/plugins/sprite_editor_plugin.cpp msgid "Simplification: " @@ -7316,9 +7315,8 @@ msgid "Duplicate Nodes" msgstr "Duplicar Nodos" #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Delete Nodes" -msgstr "Eliminar Nodo" +msgstr "Eliminar Nodos" #: editor/plugins/visual_shader_editor_plugin.cpp msgid "Visual Shader Input Type Changed" diff --git a/editor/translations/et.po b/editor/translations/et.po index 455623f6aa..43720cc344 100644 --- a/editor/translations/et.po +++ b/editor/translations/et.po @@ -146,11 +146,15 @@ msgid "Animation Playback Track" msgstr "" #: editor/animation_track_editor.cpp -msgid "Add Track" +msgid "Animation length (frames)" msgstr "" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Add Track" msgstr "" #: editor/animation_track_editor.cpp diff --git a/editor/translations/fa.po b/editor/translations/fa.po index 445b941a96..d3c016bc2d 100644 --- a/editor/translations/fa.po +++ b/editor/translations/fa.po @@ -170,14 +170,20 @@ msgid "Animation Playback Track" msgstr "" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "ترک را اضاÙÙ‡ Ú©Ù†" +#, fuzzy +msgid "Animation length (frames)" +msgstr "طول انیمیشن (به ثانیه)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "طول انیمیشن (به ثانیه)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "ترک را اضاÙÙ‡ Ú©Ù†" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "تکرار انیمیشن" diff --git a/editor/translations/fi.po b/editor/translations/fi.po index 117aaa6561..27df98cab3 100644 --- a/editor/translations/fi.po +++ b/editor/translations/fi.po @@ -13,7 +13,7 @@ msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-04-03 22:06+0000\n" +"PO-Revision-Date: 2019-05-04 13:48+0000\n" "Last-Translator: Tapani Niemi <tapani.niemi@kapsi.fi>\n" "Language-Team: Finnish <https://hosted.weblate.org/projects/godot-engine/" "godot/fi/>\n" @@ -22,7 +22,7 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=n != 1;\n" -"X-Generator: Weblate 3.6-dev\n" +"X-Generator: Weblate 3.7-dev\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -159,14 +159,20 @@ msgid "Animation Playback Track" msgstr "Animaatiotoistoraita" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Lisää raita" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Animaation pituus (sekunteina)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Animaation pituus (sekunteina)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Lisää raita" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Animaation kierto" @@ -416,9 +422,8 @@ msgid "Group tracks by node or display them as plain list." msgstr "Ryhmitä raidat solmujen mukaan tai näytä ne tavallisena luettelona." #: editor/animation_track_editor.cpp -#, fuzzy msgid "Snap:" -msgstr "Tartu" +msgstr "Tartu:" #: editor/animation_track_editor.cpp msgid "Animation step value." @@ -426,7 +431,7 @@ msgstr "Animaation askelluksen arvo." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "Sekunnit" #: editor/animation_track_editor.cpp msgid "FPS" @@ -4792,20 +4797,19 @@ msgstr "Asettelu" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Translation mask for inserting keys." -msgstr "" +msgstr "Siirrosmaski avainruutujen lisäämiseen." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Rotation mask for inserting keys." -msgstr "" +msgstr "Kierrosmaski avainruutujen lisäämiseen." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Scale mask for inserting keys." -msgstr "" +msgstr "Skaalausmaski avainruutujen lisäämiseen." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Insert keys (based on mask)." -msgstr "Lisää avainruutu (olemassa olevat raidat)" +msgstr "Lisää avainruutuja (maskiin perustuen)." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "" @@ -4814,11 +4818,15 @@ msgid "" "Keys are only added to existing tracks, no new tracks will be created.\n" "Keys must be inserted manually for the first time." msgstr "" +"Lisää avainruutuja automaattisesti, kun objekteja siirretään, kierretään tai " +"skaalataan (maskiin perustuen).\n" +"Avainruutuja lisätään vain olemassa oleville raidoille, uusia raitoja ei " +"luoda.\n" +"Avainruudut täytyy lisätä ensimmäisellä kerralla käsin." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Auto Insert Key" -msgstr "Animaatio: Lisää avain" +msgstr "Lisää avainruutuja automaattisesti" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Insert Key (Existing Tracks)" @@ -5808,9 +5816,8 @@ msgid "Save Theme As..." msgstr "Tallenna teema nimellä..." #: editor/plugins/script_editor_plugin.cpp -#, fuzzy msgid "%s Class Reference" -msgstr " Luokan referenssi" +msgstr "%s luokan referenssi" #: editor/plugins/script_editor_plugin.cpp msgid "Toggle alphabetical sorting of the method list." @@ -6634,24 +6641,20 @@ msgid "Nameless gizmo" msgstr "Nimetön muokkain" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Mesh2D" -msgstr "Luo 2D-mesh" +msgstr "Luo Mesh2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Polygon2D" -msgstr "Luo Polygon3D" +msgstr "Luo Polygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D" -msgstr "Luo törmäyspolygoni" +msgstr "Luo CollisionPolygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D" -msgstr "Luo peittopolygoni" +msgstr "Luo LightOccluder2D" #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite is empty!" @@ -6666,43 +6669,36 @@ msgid "Invalid geometry, can't replace by mesh." msgstr "Virheellinen geometria, ei voida korvata meshillä." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create polygon." -msgstr "Virheellinen geometria, ei voida korvata meshillä." +msgstr "Virheellinen geometria, ei voida luoda polygonia." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create collision polygon." -msgstr "Virheellinen geometria, ei voida korvata meshillä." +msgstr "Virheellinen geometria, ei voida luoda törmäyspolygonia." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create light occluder." -msgstr "Virheellinen geometria, ei voida korvata meshillä." +msgstr "Virheellinen geometria, ei voida luoda valopeitettä." #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite" msgstr "Sprite" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Mesh2D" -msgstr "Muunna 2D-meshiksi" +msgstr "Muunna Mesh2D resurssiksi" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Polygon2D" -msgstr "Siirrä polygonia" +msgstr "Muunna Polygon2D solmuksi" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D Sibling" -msgstr "Luo törmäyspolygoni" +msgstr "Luo CollisionPolygon2D solmun sisar" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D Sibling" -msgstr "Luo peittopolygoni" +msgstr "Luo LightOccluder2D solmun sisar" #: editor/plugins/sprite_editor_plugin.cpp msgid "Simplification: " @@ -7287,9 +7283,8 @@ msgid "Duplicate Nodes" msgstr "Kahdenna solmut" #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Delete Nodes" -msgstr "Poista solmu" +msgstr "Poista solmut" #: editor/plugins/visual_shader_editor_plugin.cpp msgid "Visual Shader Input Type Changed" diff --git a/editor/translations/fil.po b/editor/translations/fil.po index aece9febdd..86133e9264 100644 --- a/editor/translations/fil.po +++ b/editor/translations/fil.po @@ -152,11 +152,15 @@ msgid "Animation Playback Track" msgstr "" #: editor/animation_track_editor.cpp -msgid "Add Track" +msgid "Animation length (frames)" msgstr "" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Add Track" msgstr "" #: editor/animation_track_editor.cpp diff --git a/editor/translations/fr.po b/editor/translations/fr.po index 37175d7001..a3a74d7d41 100644 --- a/editor/translations/fr.po +++ b/editor/translations/fr.po @@ -55,11 +55,12 @@ # Caye Pierre <pierrecaye@laposte.net>, 2019. # Peter Kent <0.peter.kent@gmail.com>, 2019. # jef dered <themen098s@vivaldi.net>, 2019. +# Patrick Zoch Alves <patrickzochalves@gmail.com>, 2019. msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-04-05 13:04+0000\n" +"PO-Revision-Date: 2019-05-20 11:49+0000\n" "Last-Translator: Caye Pierre <pierrecaye@laposte.net>\n" "Language-Team: French <https://hosted.weblate.org/projects/godot-engine/" "godot/fr/>\n" @@ -68,7 +69,7 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=n > 1;\n" -"X-Generator: Weblate 3.6-dev\n" +"X-Generator: Weblate 3.7-dev\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -80,15 +81,15 @@ msgstr "" #: modules/mono/glue/gd_glue.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp msgid "Not enough bytes for decoding bytes, or invalid format." -msgstr "Pas assez d'octets pour les octets de décodage, ou format non valide." +msgstr "Pas assez d'octets pour le décodage, ou format non valide." #: core/math/expression.cpp msgid "Invalid input %i (not passed) in expression" -msgstr "Entrée non valide %i (non passée) dans l’expression" +msgstr "Entrée non valide %i (pas passée) dans l’expression" #: core/math/expression.cpp msgid "self can't be used because instance is null (not passed)" -msgstr "self ne peut être utilisé car l'instance est null (non fournie)" +msgstr "self ne peut être utilisé car l'instance est null (pas passée)" #: core/math/expression.cpp msgid "Invalid operands to operator %s, %s and %s." @@ -100,15 +101,15 @@ msgstr "Index de type %s invalide pour le type de base %s" #: core/math/expression.cpp msgid "Invalid named index '%s' for base type %s" -msgstr "Index nommé %s invalide pour le type de base %s" +msgstr "Nom d'index '%s' invalide pour le type de base %s" #: core/math/expression.cpp msgid "Invalid arguments to construct '%s'" -msgstr "Arguments invalides pour construire « %s »" +msgstr "Arguments invalides pour construire '%s'" #: core/math/expression.cpp msgid "On call to '%s':" -msgstr "Sur appel à « %s » :" +msgstr "Sur appel à '%s' :" #: editor/animation_bezier_editor.cpp #: editor/plugins/asset_library_editor_plugin.cpp @@ -129,11 +130,11 @@ msgstr "Insérer la clé ici" #: editor/animation_bezier_editor.cpp msgid "Duplicate Selected Key(s)" -msgstr "Dupliquer les clé(s) sélectionnée(s)" +msgstr "Dupliquer la(les) clé(s) sélectionnée(s)" #: editor/animation_bezier_editor.cpp msgid "Delete Selected Key(s)" -msgstr "Supprimer les clé(s) sélectionnée(s)" +msgstr "Supprimer (la)les clé(s) sélectionnée(s)" #: editor/animation_bezier_editor.cpp msgid "Add Bezier Point" @@ -153,23 +154,23 @@ msgstr "Supprimer les clés d'animation" #: editor/animation_track_editor.cpp msgid "Anim Change Keyframe Time" -msgstr "Modifier le temps d'image-clé" +msgstr "Modifier le temps de l'image-clé" #: editor/animation_track_editor.cpp msgid "Anim Change Transition" -msgstr "Changement de transition de l'animation" +msgstr "Changer la transition de l'animation" #: editor/animation_track_editor.cpp msgid "Anim Change Transform" -msgstr "Anim: Change Transformation" +msgstr "Changer la transformation de l'animation" #: editor/animation_track_editor.cpp msgid "Anim Change Keyframe Value" -msgstr "Anim: Change Valeur de l'Image Clé" +msgstr "Changer la valeur de l'image-clé de l'animation" #: editor/animation_track_editor.cpp msgid "Anim Change Call" -msgstr "Anim: Change l'Appel" +msgstr "Changer l'appel de l'animation" #: editor/animation_track_editor.cpp msgid "Change Animation Length" @@ -205,14 +206,18 @@ msgid "Animation Playback Track" msgstr "Piste de lecture d'animation" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Ajouter une piste" +msgid "Animation length (frames)" +msgstr "Durée de l'animation (en images)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "Durée de l'animation (en secondes)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Ajouter une piste" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Bouclage de l'animation" @@ -247,7 +252,7 @@ msgstr "Mode d'interpolation" #: editor/animation_track_editor.cpp msgid "Loop Wrap Mode (Interpolate end with beginning on loop)" -msgstr "Mode bouclé (fin interpolée avec début en boucle)" +msgstr "Mode bouclé (fin interpolée avec le début dans la boucle)" #: editor/animation_track_editor.cpp msgid "Remove this track." @@ -255,11 +260,11 @@ msgstr "Supprime cette piste." #: editor/animation_track_editor.cpp msgid "Time (s): " -msgstr "Temps (s) : " +msgstr "Temps (s): " #: editor/animation_track_editor.cpp msgid "Toggle Track Enabled" -msgstr "Activer le basculement de piste" +msgstr "Basculement de piste activé" #: editor/animation_track_editor.cpp msgid "Continuous" @@ -473,9 +478,8 @@ msgid "Group tracks by node or display them as plain list." msgstr "Grouper les pistes par nÅ“uds ou les afficher dans une liste simple." #: editor/animation_track_editor.cpp -#, fuzzy msgid "Snap:" -msgstr "Aligner" +msgstr "Aligner :" #: editor/animation_track_editor.cpp msgid "Animation step value." @@ -483,7 +487,7 @@ msgstr "Valeur du pas d'animation." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "Secondes" #: editor/animation_track_editor.cpp msgid "FPS" @@ -4888,20 +4892,19 @@ msgstr "Disposition sur l'écran" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Translation mask for inserting keys." -msgstr "" +msgstr "Masque de translation pour l'insertion des clés." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Rotation mask for inserting keys." -msgstr "" +msgstr "Masque de rotation pour l'insertion des clés." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Scale mask for inserting keys." -msgstr "" +msgstr "Masque de mise à l'échelle pour l'insertion des clés." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Insert keys (based on mask)." -msgstr "Insérer une clé (pistes existantes)" +msgstr "Insérer des clés (en fonction du masque)." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "" @@ -4910,11 +4913,15 @@ msgid "" "Keys are only added to existing tracks, no new tracks will be created.\n" "Keys must be inserted manually for the first time." msgstr "" +"Insertion automatique des clés lors de la translation des objets, rotation à " +"l'échelle (en fonction du masque).\n" +"Les clés ne sont ajoutées qu'aux pistes existantes, aucune nouvelle piste ne " +"sera créée.\n" +"Les clés doivent être insérées manuellement pour la première fois." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Auto Insert Key" -msgstr "Insérer une clé d'animation" +msgstr "Auto insertion de clé" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Insert Key (Existing Tracks)" @@ -5911,9 +5918,8 @@ msgid "Save Theme As..." msgstr "Enregistrer le thème sous…" #: editor/plugins/script_editor_plugin.cpp -#, fuzzy msgid "%s Class Reference" -msgstr " Référence de classe" +msgstr "Référence de classe %s" #: editor/plugins/script_editor_plugin.cpp msgid "Toggle alphabetical sorting of the method list." @@ -6740,24 +6746,20 @@ msgid "Nameless gizmo" msgstr "Gadget sans nom" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Mesh2D" -msgstr "Créer un maillage 2D" +msgstr "Créer un Mesh2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Polygon2D" -msgstr "Créer un Polygon3D" +msgstr "Créer un Polygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D" -msgstr "Créer le polygone de collision" +msgstr "Créer un CollisionPolygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D" -msgstr "Créer un polygone occulteur" +msgstr "Créer un LightOccluder2D" #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite is empty!" @@ -6774,43 +6776,36 @@ msgid "Invalid geometry, can't replace by mesh." msgstr "Géométrie invalide, impossible de remplacer par un maillage." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create polygon." -msgstr "Géométrie invalide, impossible de remplacer par un maillage." +msgstr "Géométrie invalide, impossible de créer le polygone." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create collision polygon." -msgstr "Géométrie invalide, impossible de remplacer par un maillage." +msgstr "Géométrie invalide, impossible de créer le polygone de collision." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create light occluder." -msgstr "Géométrie invalide, impossible de remplacer par un maillage." +msgstr "Géométrie invalide, impossible de créer l'occulteur de lumière." #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite" msgstr "Sprite" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Mesh2D" -msgstr "Convertir en maillage 2D" +msgstr "Convertir en Mesh2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Polygon2D" -msgstr "Déplacer le polygone" +msgstr "Convertir en Polygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D Sibling" -msgstr "Créer le polygone de collision" +msgstr "Créer un CollisionPolygon2D frère" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D Sibling" -msgstr "Créer un polygone occulteur" +msgstr "Créer un LightOccluder2D frère" #: editor/plugins/sprite_editor_plugin.cpp msgid "Simplification: " @@ -6842,7 +6837,7 @@ msgstr "Le presse-papiers des ressources est vide ou n'est pas une texture !" #: editor/plugins/sprite_frames_editor_plugin.cpp msgid "Paste Frame" -msgstr "Coller Frame" +msgstr "Coller une image" #: editor/plugins/sprite_frames_editor_plugin.cpp msgid "Add Empty" @@ -6850,7 +6845,7 @@ msgstr "Ajouter vide" #: editor/plugins/sprite_frames_editor_plugin.cpp msgid "Change Animation FPS" -msgstr "Modifier le taux d'IPS de l'animation" +msgstr "Modifier le nombre d'images par seconde de l'animation" #: editor/plugins/sprite_frames_editor_plugin.cpp msgid "(empty)" @@ -6866,7 +6861,7 @@ msgstr "Nouvelle animation" #: editor/plugins/sprite_frames_editor_plugin.cpp msgid "Speed (FPS):" -msgstr "Vitesse (FPS) :" +msgstr "Vitesse (IPS) :" #: editor/plugins/sprite_frames_editor_plugin.cpp msgid "Loop" @@ -6886,11 +6881,11 @@ msgstr "Insérer vide (après)" #: editor/plugins/sprite_frames_editor_plugin.cpp msgid "Move (Before)" -msgstr "Déplacer (Avant)" +msgstr "Déplacer (avant)" #: editor/plugins/sprite_frames_editor_plugin.cpp msgid "Move (After)" -msgstr "Déplacer (Après)" +msgstr "Déplacer (après)" #: editor/plugins/sprite_frames_editor_plugin.cpp msgid "SpriteFrames" @@ -7397,9 +7392,8 @@ msgid "Duplicate Nodes" msgstr "Dupliquer le(s) nÅ“ud(s)" #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Delete Nodes" -msgstr "Supprimer un nÅ“ud" +msgstr "Supprimer des nÅ“uds" #: editor/plugins/visual_shader_editor_plugin.cpp msgid "Visual Shader Input Type Changed" diff --git a/editor/translations/he.po b/editor/translations/he.po index 8ef45fd8d8..1bde350633 100644 --- a/editor/translations/he.po +++ b/editor/translations/he.po @@ -166,14 +166,20 @@ msgstr "שקופיות ×”×”× ×¤×©×”" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "הוספת רצועות חדשות." +msgid "Animation length (frames)" +msgstr "משך ×”×”× ×¤×©×” (×‘×©× ×™×•×ª)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "משך ×”×”× ×¤×©×” (×‘×©× ×™×•×ª)" #: editor/animation_track_editor.cpp +#, fuzzy +msgid "Add Track" +msgstr "הוספת רצועות חדשות." + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "תקריב ×”× ×¤×©×”" diff --git a/editor/translations/hi.po b/editor/translations/hi.po index f7bf57678d..7bc92cc5b7 100644 --- a/editor/translations/hi.po +++ b/editor/translations/hi.po @@ -5,12 +5,13 @@ # Abhas Kumar Sinha <abhaskumarsinha@gmail.com>, 2017. # Suryansh5545 <suryanshpathak5545@gmail.com>, 2018. # Vikram1323 <vikram1323@gmail.com>, 2018. +# vkubre <v@kubre.in>, 2019. msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2018-12-13 14:40+0100\n" -"Last-Translator: Vikram1323 <vikram1323@gmail.com>\n" +"PO-Revision-Date: 2019-05-04 13:48+0000\n" +"Last-Translator: vkubre <v@kubre.in>\n" "Language-Team: Hindi <https://hosted.weblate.org/projects/godot-engine/godot/" "hi/>\n" "Language: hi\n" @@ -18,7 +19,7 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=n != 1;\n" -"X-Generator: Poedit 2.2\n" +"X-Generator: Weblate 3.7-dev\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -70,7 +71,7 @@ msgstr "संतà¥à¤²à¤¿à¤¤" #: editor/animation_bezier_editor.cpp msgid "Mirror" -msgstr "" +msgstr "पà¥à¤°à¤¤à¤¿à¤®à¤¾" #: editor/animation_bezier_editor.cpp msgid "Insert Key Here" @@ -87,7 +88,7 @@ msgstr "चयनित फ़ाइलें हटाà¤à¤‚?" #: editor/animation_bezier_editor.cpp msgid "Add Bezier Point" -msgstr "" +msgstr "बेज़ियर पॉइंट तैयार करे" #: editor/animation_bezier_editor.cpp msgid "Move Bezier Points" @@ -161,14 +162,20 @@ msgstr "à¤à¤¨à¤¿à¤®à¥‡à¤¶à¤¨ पà¥à¤²à¥‡à¤¬à¥ˆà¤• टà¥à¤°à¥ˆà¤•" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "टà¥à¤°à¥ˆà¤• जोड़ें" +msgid "Animation length (frames)" +msgstr "à¤à¤¨à¤¿à¤®à¥‡à¤¶à¤¨ लंबाई समय (सेकंडà¥à¤¸)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "à¤à¤¨à¤¿à¤®à¥‡à¤¶à¤¨ लंबाई समय (सेकंडà¥à¤¸)" #: editor/animation_track_editor.cpp +#, fuzzy +msgid "Add Track" +msgstr "टà¥à¤°à¥ˆà¤• जोड़ें" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "à¤à¤¨à¤¿à¤®à¥‡à¤¶à¤¨ लूप" diff --git a/editor/translations/hr.po b/editor/translations/hr.po index a7501f9b14..10da7d4fc0 100644 --- a/editor/translations/hr.po +++ b/editor/translations/hr.po @@ -3,11 +3,12 @@ # Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) # This file is distributed under the same license as the Godot source code. # Unlimited Creativity <marinosah1@gmail.com>, 2019. +# Patik <patrikfs5@gmail.com>, 2019. msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" -"PO-Revision-Date: 2019-01-06 15:06+0000\n" -"Last-Translator: Unlimited Creativity <marinosah1@gmail.com>\n" +"PO-Revision-Date: 2019-05-20 11:49+0000\n" +"Last-Translator: Patik <patrikfs5@gmail.com>\n" "Language-Team: Croatian <https://hosted.weblate.org/projects/godot-engine/" "godot/hr/>\n" "Language: hr\n" @@ -15,7 +16,7 @@ msgstr "" "Content-Transfer-Encoding: 8-bit\n" "Plural-Forms: nplurals=3; plural=n%10==1 && n%100!=11 ? 0 : n%10>=2 && n" "%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2;\n" -"X-Generator: Weblate 3.4-dev\n" +"X-Generator: Weblate 3.7-dev\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -26,35 +27,35 @@ msgstr "Neispravni argument za convert(), upotrijebi konstantu TYPE_*" #: modules/mono/glue/gd_glue.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp msgid "Not enough bytes for decoding bytes, or invalid format." -msgstr "" +msgstr "Nedovoljno byte-ova za dekodiranje byte-ova, ili neispravni format." #: core/math/expression.cpp msgid "Invalid input %i (not passed) in expression" -msgstr "" +msgstr "Neispravni ulaz %i (nije proslijeÄ‘en) u izrazu" #: core/math/expression.cpp msgid "self can't be used because instance is null (not passed)" -msgstr "" +msgstr "'self' nije moguće koristiti jer je instanca null (niÅ¡ta)" #: core/math/expression.cpp msgid "Invalid operands to operator %s, %s and %s." -msgstr "" +msgstr "Nevažeći operatori za operator %s, %s i %s." #: core/math/expression.cpp msgid "Invalid index of type %s for base type %s" -msgstr "" +msgstr "Nevažeći indeks za tip %s baznog tipa %s" #: core/math/expression.cpp msgid "Invalid named index '%s' for base type %s" -msgstr "" +msgstr "NevažeÄi imenovani indeks '%s' za bazni tip %s" #: core/math/expression.cpp msgid "Invalid arguments to construct '%s'" -msgstr "" +msgstr "Nevažeći argumenti za konstrukciju '%s'" #: core/math/expression.cpp msgid "On call to '%s':" -msgstr "" +msgstr "Pri pozivu '%s':" #: editor/animation_bezier_editor.cpp #: editor/plugins/asset_library_editor_plugin.cpp @@ -63,7 +64,7 @@ msgstr "" #: editor/animation_bezier_editor.cpp msgid "Balanced" -msgstr "" +msgstr "Balansiran" #: editor/animation_bezier_editor.cpp msgid "Mirror" @@ -71,23 +72,23 @@ msgstr "" #: editor/animation_bezier_editor.cpp msgid "Insert Key Here" -msgstr "" +msgstr "Unesite kljuÄ ovdje" #: editor/animation_bezier_editor.cpp msgid "Duplicate Selected Key(s)" -msgstr "" +msgstr "Duplikati Odabranih KljuÄeva" #: editor/animation_bezier_editor.cpp msgid "Delete Selected Key(s)" -msgstr "" +msgstr "Brisati odabrani kljuÄ/odabrane kljuÄeve" #: editor/animation_bezier_editor.cpp msgid "Add Bezier Point" -msgstr "" +msgstr "Dodaj Bezier ToÄku" #: editor/animation_bezier_editor.cpp msgid "Move Bezier Points" -msgstr "" +msgstr "Pomakni Bezier ToÄke" #: editor/animation_bezier_editor.cpp editor/animation_track_editor.cpp msgid "Anim Duplicate Keys" @@ -151,45 +152,51 @@ msgid "Animation Playback Track" msgstr "" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Trajanje animacije (u sekundama)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" -msgstr "" +#, fuzzy +msgid "Animation length (seconds)" +msgstr "Trajanje animacije (u sekundama)" + +#: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Dodati stazu" #: editor/animation_track_editor.cpp msgid "Animation Looping" -msgstr "" +msgstr "Ponavljanje Animacije" #: editor/animation_track_editor.cpp #: modules/visual_script/visual_script_editor.cpp msgid "Functions:" -msgstr "" +msgstr "Funkcije:" #: editor/animation_track_editor.cpp msgid "Audio Clips:" -msgstr "" +msgstr "Audio Klipovi:" #: editor/animation_track_editor.cpp msgid "Anim Clips:" -msgstr "" +msgstr "Animacijski Klipovi:" #: editor/animation_track_editor.cpp msgid "Change Track Path" -msgstr "" +msgstr "Promijeni Put Staze" #: editor/animation_track_editor.cpp msgid "Toggle this track on/off." -msgstr "" +msgstr "Upali/ugasi ovu stazu." #: editor/animation_track_editor.cpp msgid "Update Mode (How this property is set)" -msgstr "" +msgstr "NaÄin ažuriranja (kako se ovo svojstvo postavlja)" #: editor/animation_track_editor.cpp msgid "Interpolation Mode" -msgstr "" +msgstr "NaÄin Interpolacije" #: editor/animation_track_editor.cpp msgid "Loop Wrap Mode (Interpolate end with beginning on loop)" @@ -197,27 +204,27 @@ msgstr "" #: editor/animation_track_editor.cpp msgid "Remove this track." -msgstr "" +msgstr "Ukloni ovu stazu." #: editor/animation_track_editor.cpp msgid "Time (s): " -msgstr "" +msgstr "Vrijeme/vremena: " #: editor/animation_track_editor.cpp msgid "Toggle Track Enabled" -msgstr "" +msgstr "Upali/Ugasi Stazu" #: editor/animation_track_editor.cpp msgid "Continuous" -msgstr "" +msgstr "Kontinuirano" #: editor/animation_track_editor.cpp msgid "Discrete" -msgstr "" +msgstr "Diskretno" #: editor/animation_track_editor.cpp msgid "Trigger" -msgstr "" +msgstr "OkidaÄ" #: editor/animation_track_editor.cpp msgid "Capture" @@ -225,16 +232,16 @@ msgstr "" #: editor/animation_track_editor.cpp msgid "Nearest" -msgstr "" +msgstr "Najbliži" #: editor/animation_track_editor.cpp editor/plugins/curve_editor_plugin.cpp #: editor/property_editor.cpp msgid "Linear" -msgstr "" +msgstr "Linearno" #: editor/animation_track_editor.cpp msgid "Cubic" -msgstr "" +msgstr "Kubno" #: editor/animation_track_editor.cpp msgid "Clamp Loop Interp" @@ -247,39 +254,39 @@ msgstr "" #: editor/animation_track_editor.cpp #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Insert Key" -msgstr "" +msgstr "Umetni KljuÄ" #: editor/animation_track_editor.cpp msgid "Duplicate Key(s)" -msgstr "" +msgstr "Duplicirani kljuÄ(evi)" #: editor/animation_track_editor.cpp msgid "Delete Key(s)" -msgstr "" +msgstr "ObriÅ¡i kljuÄ(eve)" #: editor/animation_track_editor.cpp msgid "Change Animation Update Mode" -msgstr "" +msgstr "Promijeni NaÄin Ažuriranja Animacije" #: editor/animation_track_editor.cpp msgid "Change Animation Interpolation Mode" -msgstr "" +msgstr "Promijeni NaÄin Interpolacije Animacije" #: editor/animation_track_editor.cpp msgid "Change Animation Loop Mode" -msgstr "" +msgstr "Promijeni NaÄin Ponavljanja Animacije" #: editor/animation_track_editor.cpp msgid "Remove Anim Track" -msgstr "" +msgstr "Ukloni Stazu Animacije" #: editor/animation_track_editor.cpp msgid "Create NEW track for %s and insert key?" -msgstr "" +msgstr "Stvori NOVU stazu za %s i umetni kljuÄ?" #: editor/animation_track_editor.cpp msgid "Create %d NEW tracks and insert keys?" -msgstr "" +msgstr "Napravi %d NOVIH staza i umetni kljuÄeve?" #: editor/animation_track_editor.cpp editor/create_dialog.cpp #: editor/editor_audio_buses.cpp editor/editor_plugin_settings.cpp @@ -288,7 +295,7 @@ msgstr "" #: editor/plugins/mesh_instance_editor_plugin.cpp #: editor/plugins/particles_editor_plugin.cpp editor/script_create_dialog.cpp msgid "Create" -msgstr "" +msgstr "Stvori" #: editor/animation_track_editor.cpp msgid "Anim Insert" @@ -296,27 +303,27 @@ msgstr "" #: editor/animation_track_editor.cpp msgid "AnimationPlayer can't animate itself, only other players." -msgstr "" +msgstr "Animator ne može animirati sebe, samo druge animatore." #: editor/animation_track_editor.cpp msgid "Anim Create & Insert" -msgstr "" +msgstr "Anim Stvori & Umetni" #: editor/animation_track_editor.cpp msgid "Anim Insert Track & Key" -msgstr "" +msgstr "Anim Umetni Stazu & KljuÄ" #: editor/animation_track_editor.cpp msgid "Anim Insert Key" -msgstr "" +msgstr "Anim Umetni KljuÄ" #: editor/animation_track_editor.cpp msgid "Change Animation Step" -msgstr "" +msgstr "Promijeni Korak Animacije" #: editor/animation_track_editor.cpp msgid "Rearrange Tracks" -msgstr "" +msgstr "Preuredi Staze" #: editor/animation_track_editor.cpp msgid "Transform tracks only apply to Spatial-based nodes." @@ -336,23 +343,23 @@ msgstr "" #: editor/animation_track_editor.cpp msgid "An animation player can't animate itself, only other players." -msgstr "" +msgstr "Animator ne može animirati sebe, samo druge objekte." #: editor/animation_track_editor.cpp msgid "Not possible to add a new track without a root" -msgstr "" +msgstr "Nije moguće dodati novu stazu bez korijena" #: editor/animation_track_editor.cpp msgid "Add Bezier Track" -msgstr "" +msgstr "Dodaj Bezier Stazu" #: editor/animation_track_editor.cpp msgid "Track path is invalid, so can't add a key." -msgstr "" +msgstr "Nevažeći put staze, ne mogu dodati kljuÄ." #: editor/animation_track_editor.cpp msgid "Track is not of type Spatial, can't insert key" -msgstr "" +msgstr "Staza nije tipa Prostorna, ne mogu umetnuti kljuÄ" #: editor/animation_track_editor.cpp msgid "Add Transform Track Key" @@ -360,19 +367,19 @@ msgstr "" #: editor/animation_track_editor.cpp msgid "Add Track Key" -msgstr "" +msgstr "Dodaj KljuÄ Staze" #: editor/animation_track_editor.cpp msgid "Track path is invalid, so can't add a method key." -msgstr "" +msgstr "Nevažeći put staze, ne mogu dodati kljuÄ metode." #: editor/animation_track_editor.cpp msgid "Add Method Track Key" -msgstr "" +msgstr "Dodaj KljuÄ Metode Staze" #: editor/animation_track_editor.cpp msgid "Method not found in object: " -msgstr "" +msgstr "Metoda nije naÄ‘ena u objektu: " #: editor/animation_track_editor.cpp msgid "Anim Move Keys" @@ -380,28 +387,29 @@ msgstr "" #: editor/animation_track_editor.cpp msgid "Clipboard is empty" -msgstr "" +msgstr "MeÄ‘uspremnik je prazan" #: editor/animation_track_editor.cpp msgid "Paste Tracks" -msgstr "" +msgstr "Zalijepi Staze" #: editor/animation_track_editor.cpp msgid "Anim Scale Keys" -msgstr "" +msgstr "Anim Skaliraj KljuÄeve" #: editor/animation_track_editor.cpp msgid "" "This option does not work for Bezier editing, as it's only a single track." msgstr "" +"Ova opcija ne radi za editiranje Beziera, zato Å¡to je samo jedna staza." #: editor/animation_track_editor.cpp msgid "Only show tracks from nodes selected in tree." -msgstr "" +msgstr "Pokaži samo staze Ävorova oznaÄenih u stablu." #: editor/animation_track_editor.cpp msgid "Group tracks by node or display them as plain list." -msgstr "" +msgstr "Grupiraj staze po Ävoru ili ih prikaži kao obiÄnu listu." #: editor/animation_track_editor.cpp msgid "Snap:" diff --git a/editor/translations/hu.po b/editor/translations/hu.po index 2f1aa1b660..9ca5955d0d 100644 --- a/editor/translations/hu.po +++ b/editor/translations/hu.po @@ -170,16 +170,21 @@ msgstr "Animáció lejátszásának leállÃtása. (S)" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "Animáció nyomvonal hozzáadás" +msgid "Animation length (frames)" +msgstr "Animáció hossza (másodpercben)." #: editor/animation_track_editor.cpp #, fuzzy -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "Animáció hossza (másodpercben)." #: editor/animation_track_editor.cpp #, fuzzy +msgid "Add Track" +msgstr "Animáció nyomvonal hozzáadás" + +#: editor/animation_track_editor.cpp +#, fuzzy msgid "Animation Looping" msgstr "Animáció nagyÃtás." diff --git a/editor/translations/id.po b/editor/translations/id.po index 876990c0c1..a221eb2276 100644 --- a/editor/translations/id.po +++ b/editor/translations/id.po @@ -170,14 +170,20 @@ msgid "Animation Playback Track" msgstr "Track Pemutar Animasi" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Tambah Track" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Panjang Animasi (detik)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Panjang Animasi (detik)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Tambah Track" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Perulangan Animasi" diff --git a/editor/translations/is.po b/editor/translations/is.po index cc911642be..9b43911998 100644 --- a/editor/translations/is.po +++ b/editor/translations/is.po @@ -159,15 +159,19 @@ msgid "Animation Playback Track" msgstr "" #: editor/animation_track_editor.cpp -#, fuzzy -msgid "Add Track" -msgstr "Anim bæta við lag" +msgid "Animation length (frames)" +msgstr "" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "" #: editor/animation_track_editor.cpp +#, fuzzy +msgid "Add Track" +msgstr "Anim bæta við lag" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "" diff --git a/editor/translations/it.po b/editor/translations/it.po index 3dbfa81714..191e5c8137 100644 --- a/editor/translations/it.po +++ b/editor/translations/it.po @@ -37,8 +37,8 @@ msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-04-14 13:04+0000\n" -"Last-Translator: Marco Galli <mrcgll98@gmail.com>\n" +"PO-Revision-Date: 2019-05-16 18:49+0000\n" +"Last-Translator: MassiminoilTrace <omino.gis@gmail.com>\n" "Language-Team: Italian <https://hosted.weblate.org/projects/godot-engine/" "godot/it/>\n" "Language: it\n" @@ -46,7 +46,7 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=n != 1;\n" -"X-Generator: Weblate 3.6-dev\n" +"X-Generator: Weblate 3.7-dev\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -185,14 +185,20 @@ msgid "Animation Playback Track" msgstr "Traccia di riproduzione animazione" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Aggiungi Traccia" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Durata Animazione (in secondi)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Durata Animazione (in secondi)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Aggiungi Traccia" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Ciclicità Animazione" @@ -1823,7 +1829,7 @@ msgstr "Salva risorsa come..." #: editor/editor_node.cpp msgid "Can't open file for writing:" -msgstr "Impossibile aprire il file per la scrittura:" +msgstr "Impossibile aprire il file in scrittura:" #: editor/editor_node.cpp msgid "Requested file format unknown:" @@ -2033,11 +2039,11 @@ msgstr "Apri scena rapidamente..." #: editor/editor_node.cpp msgid "Quick Open Script..." -msgstr "Apri Script Rapido..." +msgstr "Apri script rapidamente..." #: editor/editor_node.cpp msgid "Save & Close" -msgstr "Salva e Chiudi" +msgstr "Salva e chiudi" #: editor/editor_node.cpp msgid "Save changes to '%s' before closing?" @@ -2053,7 +2059,7 @@ msgstr "È necessario un nodo radice per salvare la scena." #: editor/editor_node.cpp msgid "Save Scene As..." -msgstr "Salva Scena Come..." +msgstr "Salva scena con nome..." #: editor/editor_node.cpp msgid "No" @@ -2061,7 +2067,7 @@ msgstr "No" #: editor/editor_node.cpp msgid "Yes" -msgstr "Si" +msgstr "Sì" #: editor/editor_node.cpp msgid "This scene has never been saved. Save before running?" @@ -2089,7 +2095,7 @@ msgstr "Questa operazione non può essere eseguita senza un nodo selezionato." #: editor/editor_node.cpp msgid "Current scene not saved. Open anyway?" -msgstr "Scena corrente non salvata. Aprire comunque?" +msgstr "Scena attuale non salvata. Aprirla comunque?" #: editor/editor_node.cpp msgid "Can't reload a scene that was never saved." @@ -2105,7 +2111,7 @@ msgstr "Questa azione non può essere annullata. Ripristinare comunque?" #: editor/editor_node.cpp msgid "Quick Run Scene..." -msgstr "Esegui Scena Rapido..." +msgstr "Esegui scena rapidamente..." #: editor/editor_node.cpp msgid "Quit" @@ -2121,7 +2127,7 @@ msgstr "Aprire Gestione Progetti?" #: editor/editor_node.cpp msgid "Save & Quit" -msgstr "Salva e Esci" +msgstr "Salva ed esci" #: editor/editor_node.cpp msgid "Save changes to the following scene(s) before quitting?" @@ -2130,19 +2136,20 @@ msgstr "Salvare le modifiche alle scene seguenti prima di uscire?" #: editor/editor_node.cpp msgid "Save changes the following scene(s) before opening Project Manager?" msgstr "" -"Salvare le modifiche alle scene seguenti prima di aprire il Manager Progetti?" +"Salvare le modifiche alle scene seguenti prima di aprire la Gestione " +"progetti?" #: editor/editor_node.cpp msgid "" "This option is deprecated. Situations where refresh must be forced are now " "considered a bug. Please report." msgstr "" -"Questa opzione é deprecata. Situazioni dove un refresh é obbligatorio sono " -"ora considerate come bug. Si prega di effettuare un report." +"Questa opzione è deprecata. Situazioni dove un refresh è obbligatorio sono " +"ora considerate come bug. Si prega di segnalarlo." #: editor/editor_node.cpp msgid "Pick a Main Scene" -msgstr "Scegli una Scena Principale" +msgstr "Scegli una Scena principale" #: editor/editor_node.cpp msgid "Unable to enable addon plugin at: '%s' parsing of config failed." @@ -2186,9 +2193,9 @@ msgid "" "Scene '%s' was automatically imported, so it can't be modified.\n" "To make changes to it, a new inherited scene can be created." msgstr "" -"La scena '%s' é stata automaticamente importata, pertanto non puo essere " +"La scena '%s' è stata automaticamente importata, pertanto non può essere " "modificata.\n" -"Per effettuare cambiamenti, puo essere creata una nuova scena ereditata." +"Per modificarla, puoi essere creata una nuova scena ereditata." #: editor/editor_node.cpp msgid "" @@ -2205,7 +2212,7 @@ msgstr "La scena '%s' ha rotto le dipendenze:" #: editor/editor_node.cpp msgid "Clear Recent Scenes" -msgstr "Rimuovi Scene Recenti" +msgstr "Rimuovi scene recenti" #: editor/editor_node.cpp msgid "Save Layout" @@ -2223,7 +2230,7 @@ msgstr "Default" #: editor/editor_node.cpp editor/editor_properties.cpp #: editor/plugins/script_editor_plugin.cpp editor/property_editor.cpp msgid "Show in FileSystem" -msgstr "Mostra nel FileSystem" +msgstr "Mostra nel filesystem" #: editor/editor_node.cpp msgid "Play This Scene" @@ -2255,11 +2262,11 @@ msgstr "Posizione dock" #: editor/editor_node.cpp msgid "Distraction Free Mode" -msgstr "Modalità Senza Distrazioni" +msgstr "Modalità senza distrazioni" #: editor/editor_node.cpp msgid "Toggle distraction-free mode." -msgstr "Abilita modalità senza distrazioni." +msgstr "Commuta modalità senza distrazioni." #: editor/editor_node.cpp msgid "Add a new scene." @@ -2283,7 +2290,7 @@ msgstr "Scheda precedente" #: editor/editor_node.cpp msgid "Filter Files..." -msgstr "Filtra Files..." +msgstr "Filtra file..." #: editor/editor_node.cpp msgid "Operations with scene files." @@ -2295,31 +2302,31 @@ msgstr "Nuova scena" #: editor/editor_node.cpp msgid "New Inherited Scene..." -msgstr "Nuova Scena Ereditata..." +msgstr "Nuova scena ereditata..." #: editor/editor_node.cpp msgid "Open Scene..." -msgstr "Apri Scena..." +msgstr "Apri scena..." #: editor/editor_node.cpp msgid "Save Scene" -msgstr "Salva Scena" +msgstr "Salva scena" #: editor/editor_node.cpp msgid "Save All Scenes" -msgstr "Salva tutte le Scene" +msgstr "Salva tutte le scene" #: editor/editor_node.cpp msgid "Close Scene" -msgstr "Chiudi Scena" +msgstr "Chiudi scena" #: editor/editor_node.cpp editor/plugins/script_editor_plugin.cpp msgid "Open Recent" -msgstr "Apri Recente" +msgstr "Apri recente" #: editor/editor_node.cpp msgid "Convert To..." -msgstr "Converti In..." +msgstr "Converti in..." #: editor/editor_node.cpp msgid "MeshLibrary..." @@ -2337,11 +2344,11 @@ msgstr "Annulla" #: editor/editor_node.cpp editor/plugins/script_text_editor.cpp #: scene/gui/line_edit.cpp scene/gui/text_edit.cpp msgid "Redo" -msgstr "Redo" +msgstr "Rifai" #: editor/editor_node.cpp msgid "Revert Scene" -msgstr "Ripristina Scena" +msgstr "Ripristina scena" #: editor/editor_node.cpp msgid "Miscellaneous project or scene-wide tools." @@ -2353,7 +2360,7 @@ msgstr "Progetto" #: editor/editor_node.cpp msgid "Project Settings" -msgstr "Impostazioni Progetto" +msgstr "Impostazioni progetto" #: editor/editor_node.cpp editor/project_export.cpp msgid "Export" @@ -2369,7 +2376,7 @@ msgstr "Apri la cartella del progetto" #: editor/editor_node.cpp msgid "Quit to Project List" -msgstr "Esci alla Lista Progetti" +msgstr "Esci e torna alla lista progetti" #: editor/editor_node.cpp editor/plugins/script_editor_plugin.cpp #: editor/project_export.cpp @@ -2378,7 +2385,7 @@ msgstr "Debug" #: editor/editor_node.cpp msgid "Deploy with Remote Debug" -msgstr "Distribuzione con il Debug Remoto" +msgstr "Distribuzione con Debug remoto" #: editor/editor_node.cpp msgid "" @@ -2409,14 +2416,14 @@ msgstr "" #: editor/editor_node.cpp msgid "Visible Collision Shapes" -msgstr "Forme di Collisione Visibili" +msgstr "Forme di collisione visibili" #: editor/editor_node.cpp msgid "" "Collision shapes and raycast nodes (for 2D and 3D) will be visible on the " "running game if this option is turned on." msgstr "" -"Le forme di collisione e i nodi di raycast (per il 2D e 3D) Saranno visibili " +"Le forme di collisione e i nodi di raycast (per il 2D e 3D) saranno visibili " "nel gioco in esecuzione se l'opzione è attiva." #: editor/editor_node.cpp @@ -2433,7 +2440,7 @@ msgstr "" #: editor/editor_node.cpp msgid "Sync Scene Changes" -msgstr "Sincronizza Cambiamenti Scena" +msgstr "Sincronizza cambiamenti scena" #: editor/editor_node.cpp msgid "" @@ -2444,12 +2451,12 @@ msgid "" msgstr "" "Quando questa opzione è attiva, qualsiasi cambiamento fatto alla scena " "nell'editor sarà replicato nel gioco in esecuzione.\n" -"Quando usata remotamente su un dispositivo, essa è più efficiente con il " +"Quando usata in remoto su un dispositivo, sarà più efficiente con un " "filesystem in rete." #: editor/editor_node.cpp msgid "Sync Script Changes" -msgstr "Sincronizza Cambiamenti Script" +msgstr "Sincronizza cambiamenti script" #: editor/editor_node.cpp msgid "" @@ -2460,7 +2467,7 @@ msgid "" msgstr "" "Quando questa opzione è attiva, qualsiasi script salvato verrà ricaricato " "nel gioco in esecuzione.\n" -"Quando usata remotamente su un dispositivo, essa è più efficiente con il " +"Quando usata in remoto su un dispositivo, sarà più efficiente con un " "filesystem in rete." #: editor/editor_node.cpp @@ -2469,31 +2476,31 @@ msgstr "Editor" #: editor/editor_node.cpp editor/settings_config_dialog.cpp msgid "Editor Settings" -msgstr "Impostazioni Editor" +msgstr "Impostazioni editor" #: editor/editor_node.cpp msgid "Editor Layout" -msgstr "Layout dell'Editor" +msgstr "Layout dell'editor" #: editor/editor_node.cpp msgid "Toggle Fullscreen" -msgstr "Abilita/Disabilita Fullscreen" +msgstr "Abilita/Disabilita modalità a schermo intero" #: editor/editor_node.cpp msgid "Open Editor Data/Settings Folder" -msgstr "Apri Cartella Dati/Impostazioni Editor" +msgstr "Apri cartella dati/impostazioni editor" #: editor/editor_node.cpp msgid "Open Editor Data Folder" -msgstr "Apri la Cartella Dati dell'Editor" +msgstr "Apri la cartella dati dell'editor" #: editor/editor_node.cpp msgid "Open Editor Settings Folder" -msgstr "Apri Cartella Impostazioni Editor" +msgstr "Apri cartella impostazioni editor" #: editor/editor_node.cpp editor/project_export.cpp msgid "Manage Export Templates" -msgstr "Gestisci Template d'Esportazione" +msgstr "Gestisci template d'esportazione" #: editor/editor_node.cpp msgid "Help" @@ -2509,15 +2516,15 @@ msgstr "Cerca" #: editor/editor_node.cpp editor/plugins/script_editor_plugin.cpp msgid "Online Docs" -msgstr "Documentazione Online" +msgstr "Documentazione online" #: editor/editor_node.cpp msgid "Q&A" -msgstr "Domande e Risposte" +msgstr "Domande e risposte" #: editor/editor_node.cpp msgid "Issue Tracker" -msgstr "Tracciatore Segnalazioni" +msgstr "Tracciatore segnalazioni" #: editor/editor_node.cpp editor/plugins/asset_library_editor_plugin.cpp msgid "Community" @@ -2533,7 +2540,7 @@ msgstr "Esegui il progetto." #: editor/editor_node.cpp msgid "Play" -msgstr "Play" +msgstr "Esegui" #: editor/editor_node.cpp msgid "Pause the scene" @@ -2549,7 +2556,7 @@ msgstr "Ferma la scena." #: editor/editor_node.cpp editor/editor_profiler.cpp msgid "Stop" -msgstr "Stop" +msgstr "Ferma" #: editor/editor_node.cpp msgid "Play the edited scene." @@ -2557,7 +2564,7 @@ msgstr "Esegui la scena in modifica." #: editor/editor_node.cpp msgid "Play Scene" -msgstr "Esegui Scena" +msgstr "Esegui scena" #: editor/editor_node.cpp msgid "Play custom scene" @@ -2565,7 +2572,7 @@ msgstr "Esegui scena personalizzata" #: editor/editor_node.cpp msgid "Play Custom Scene" -msgstr "Esegui Scena Personalizzata" +msgstr "Esegui scena personalizzata" #: editor/editor_node.cpp msgid "Changing the video driver requires restarting the editor." @@ -2574,23 +2581,23 @@ msgstr "Il cambiamento dei driver video necessita il riavvio dell'editor." #: editor/editor_node.cpp editor/project_settings_editor.cpp #: editor/settings_config_dialog.cpp msgid "Save & Restart" -msgstr "Salva e Riavvia" +msgstr "Salva e riavvia" #: editor/editor_node.cpp msgid "Spins when the editor window redraws." -msgstr "Gira quando l'editor viene ridisegnato." +msgstr "Gira quando la finestra dell'editor viene ridisegnata." #: editor/editor_node.cpp msgid "Update Always" -msgstr "Aggiorna Sempre" +msgstr "Aggiorna sempre" #: editor/editor_node.cpp msgid "Update Changes" -msgstr "Aggiorna Cambiamenti" +msgstr "Aggiorna cambiamenti" #: editor/editor_node.cpp msgid "Disable Update Spinner" -msgstr "Disabilita lo Spinner di Update" +msgstr "Disabilita l'icona girevole di aggiornamento" #: editor/editor_node.cpp editor/plugins/asset_library_editor_plugin.cpp #: editor/project_manager.cpp @@ -2599,11 +2606,11 @@ msgstr "Importa" #: editor/editor_node.cpp msgid "FileSystem" -msgstr "FileSystem" +msgstr "Filesystem" #: editor/editor_node.cpp msgid "Inspector" -msgstr "Inspector" +msgstr "Ispettore" #: editor/editor_node.cpp msgid "Node" @@ -2611,7 +2618,7 @@ msgstr "Nodo" #: editor/editor_node.cpp msgid "Expand Bottom Panel" -msgstr "Espandi Pannello Inferiore" +msgstr "Espandi pannello inferiore" #: editor/editor_node.cpp scene/resources/visual_shader.cpp msgid "Output" @@ -2623,19 +2630,19 @@ msgstr "Non salvare" #: editor/editor_node.cpp msgid "Import Templates From ZIP File" -msgstr "Importa templates Da File ZIP" +msgstr "Importa template da un file ZIP" #: editor/editor_node.cpp editor/project_export.cpp msgid "Export Project" -msgstr "Esporta Progetto" +msgstr "Esporta progetto" #: editor/editor_node.cpp msgid "Export Library" -msgstr "Esporta Libreria" +msgstr "Esporta libreria" #: editor/editor_node.cpp msgid "Merge With Existing" -msgstr "Unisci Con Esistente" +msgstr "Unisci con esistente" #: editor/editor_node.cpp msgid "Password:" @@ -2643,15 +2650,15 @@ msgstr "Password:" #: editor/editor_node.cpp msgid "Open & Run a Script" -msgstr "Apri e Esegui uno Script" +msgstr "Apri ed esegui uno script" #: editor/editor_node.cpp msgid "New Inherited" -msgstr "Nuova Ereditata" +msgstr "Nuova ereditata" #: editor/editor_node.cpp msgid "Load Errors" -msgstr "Carica Errori" +msgstr "Carica errori" #: editor/editor_node.cpp editor/plugins/tile_map_editor_plugin.cpp msgid "Select" @@ -2659,7 +2666,7 @@ msgstr "Seleziona" #: editor/editor_node.cpp msgid "Open 2D Editor" -msgstr "Apri Editor 2D" +msgstr "Apri editor 2D" #: editor/editor_node.cpp msgid "Open 3D Editor" diff --git a/editor/translations/ja.po b/editor/translations/ja.po index 67a472c64d..74ea163697 100644 --- a/editor/translations/ja.po +++ b/editor/translations/ja.po @@ -26,7 +26,7 @@ msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-04-19 16:33+0000\n" +"PO-Revision-Date: 2019-05-16 18:49+0000\n" "Last-Translator: Wataru Onuki <watonu@magadou.com>\n" "Language-Team: Japanese <https://hosted.weblate.org/projects/godot-engine/" "godot/ja/>\n" @@ -35,7 +35,7 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=1; plural=0;\n" -"X-Generator: Weblate 3.6-dev\n" +"X-Generator: Weblate 3.7-dev\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -171,14 +171,20 @@ msgid "Animation Playback Track" msgstr "アニメーションå†ç”Ÿãƒˆãƒ©ãƒƒã‚¯" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "ãƒˆãƒ©ãƒƒã‚¯ã‚’è¿½åŠ " +#, fuzzy +msgid "Animation length (frames)" +msgstr "アニメーションã®é•·ã• (秒)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "アニメーションã®é•·ã• (秒)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "ãƒˆãƒ©ãƒƒã‚¯ã‚’è¿½åŠ " + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "アニメーションループ" @@ -1395,33 +1401,31 @@ msgid "Packing" msgstr "パックã™ã‚‹" #: editor/editor_export.cpp -#, fuzzy msgid "" "Target platform requires 'ETC' texture compression for GLES2. Enable 'Import " "Etc' in Project Settings." msgstr "" "対象プラットフォームã§ã¯GLES2ã®ãŸã‚ã«'ETC'テクスãƒãƒ£åœ§ç¸®ãŒå¿…è¦ã§ã™ã€‚プãƒã‚¸ã‚§" -"クトè¨å®šã‚ˆã‚Šæœ‰åŠ¹ã«ã—ã¦ãã ã•ã„。" +"クトè¨å®šã‚ˆã‚Š 'Import Etc' をオンã«ã—ã¦ãã ã•ã„。" #: editor/editor_export.cpp -#, fuzzy msgid "" "Target platform requires 'ETC2' texture compression for GLES3. Enable " "'Import Etc 2' in Project Settings." msgstr "" -"対象プラットフォームã§ã¯GLES2ã®ãŸã‚ã«'ETC'テクスãƒãƒ£åœ§ç¸®ãŒå¿…è¦ã§ã™ã€‚プãƒã‚¸ã‚§" -"クトè¨å®šã‚ˆã‚Šæœ‰åŠ¹ã«ã—ã¦ãã ã•ã„。" +"対象プラットフォームã§ã¯GLES3ã®ãŸã‚ã«'ETC2'テクスãƒãƒ£åœ§ç¸®ãŒå¿…è¦ã§ã™ã€‚プãƒã‚¸ã‚§" +"クトè¨å®šã‚ˆã‚Š 'Import Etc 2' をオンã«ã—ã¦ãã ã•ã„。" #: editor/editor_export.cpp -#, fuzzy msgid "" "Target platform requires 'ETC' texture compression for the driver fallback " "to GLES2.\n" "Enable 'Import Etc' in Project Settings, or disable 'Driver Fallback " "Enabled'." msgstr "" -"対象プラットフォームã§ã¯GLES2ã®ãŸã‚ã«'ETC'テクスãƒãƒ£åœ§ç¸®ãŒå¿…è¦ã§ã™ã€‚プãƒã‚¸ã‚§" -"クトè¨å®šã‚ˆã‚Šæœ‰åŠ¹ã«ã—ã¦ãã ã•ã„。" +"対象プラットフォームã§ã¯GLES2ã¸ãƒ•ã‚©ãƒ¼ãƒ«ãƒãƒƒã‚¯ã™ã‚‹ãŸã‚ã«'ETC'テクスãƒãƒ£åœ§ç¸®ãŒ" +"å¿…è¦ã§ã™ã€‚プãƒã‚¸ã‚§ã‚¯ãƒˆè¨å®šã‚ˆã‚Š 'Import Etc' をオンã«ã™ã‚‹ã‹ã€'Fallback To " +"Gles 2' をオフã«ã—ã¦ãã ã•ã„。" #: editor/editor_export.cpp platform/android/export/export.cpp #: platform/iphone/export/export.cpp platform/javascript/export/export.cpp diff --git a/editor/translations/ka.po b/editor/translations/ka.po index 26eabd113b..58114e6cef 100644 --- a/editor/translations/ka.po +++ b/editor/translations/ka.po @@ -162,15 +162,20 @@ msgid "Animation Playback Track" msgstr "" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "áƒáƒœáƒ˜áƒ›áƒáƒªáƒ˜áƒ˜áƒ¡ თრექის დáƒáƒ›áƒáƒ¢áƒ”ბáƒ" +#, fuzzy +msgid "Animation length (frames)" +msgstr "áƒáƒœáƒ˜áƒ›áƒáƒªáƒ˜áƒ˜áƒ¡ ხáƒáƒœáƒ’რძლივáƒáƒ‘რ(წáƒáƒ›áƒ”ბში)." #: editor/animation_track_editor.cpp #, fuzzy -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "áƒáƒœáƒ˜áƒ›áƒáƒªáƒ˜áƒ˜áƒ¡ ხáƒáƒœáƒ’რძლივáƒáƒ‘რ(წáƒáƒ›áƒ”ბში)." #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "áƒáƒœáƒ˜áƒ›áƒáƒªáƒ˜áƒ˜áƒ¡ თრექის დáƒáƒ›áƒáƒ¢áƒ”ბáƒ" + +#: editor/animation_track_editor.cpp #, fuzzy msgid "Animation Looping" msgstr "áƒáƒœáƒ˜áƒ›áƒáƒªáƒ˜áƒ˜áƒ¡ ბრუნვáƒ" diff --git a/editor/translations/ko.po b/editor/translations/ko.po index eb7964f81d..f92a66c981 100644 --- a/editor/translations/ko.po +++ b/editor/translations/ko.po @@ -17,8 +17,8 @@ msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-04-05 13:04+0000\n" -"Last-Translator: moolow <copyhyeon@gmail.com>\n" +"PO-Revision-Date: 2019-05-10 08:15+0000\n" +"Last-Translator: ì†¡íƒœì„ <xotjq237@gmail.com>\n" "Language-Team: Korean <https://hosted.weblate.org/projects/godot-engine/" "godot/ko/>\n" "Language: ko\n" @@ -26,7 +26,7 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=1; plural=0;\n" -"X-Generator: Weblate 3.6-dev\n" +"X-Generator: Weblate 3.7-dev\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -163,14 +163,20 @@ msgid "Animation Playback Track" msgstr "ì• ë‹ˆë©”ì´ì…˜ ìž¬ìƒ íŠ¸ëž™" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "트랙 추가" +#, fuzzy +msgid "Animation length (frames)" +msgstr "ì• ë‹ˆë©”ì´ì…˜ ê¸¸ì´ ì‹œê°„ (ì´ˆ)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "ì• ë‹ˆë©”ì´ì…˜ ê¸¸ì´ ì‹œê°„ (ì´ˆ)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "트랙 추가" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "ì• ë‹ˆë©”ì´ì…˜ 반복" @@ -250,11 +256,11 @@ msgstr "입방형" #: editor/animation_track_editor.cpp msgid "Clamp Loop Interp" -msgstr "í´ëž¨í”„ 루프 ì¸í„°í”„리터" +msgstr "루프 ë³´ê°„ ê³ ì •" #: editor/animation_track_editor.cpp msgid "Wrap Loop Interp" -msgstr "ëž© 루프 ì¸í„°í”„리터" +msgstr "루프 ë³´ê°„ ê°ì¶”기" #: editor/animation_track_editor.cpp #: editor/plugins/canvas_item_editor_plugin.cpp @@ -422,9 +428,8 @@ msgid "Group tracks by node or display them as plain list." msgstr "노드 별로 ê·¸ë£¹ì„ íŠ¸ëž™ 하거나 ì¼ë°˜ 목ë¡ìœ¼ë¡œ 표시합니다." #: editor/animation_track_editor.cpp -#, fuzzy msgid "Snap:" -msgstr "스냅" +msgstr "스냅:" #: editor/animation_track_editor.cpp msgid "Animation step value." @@ -432,7 +437,7 @@ msgstr "ì• ë‹ˆë©”ì´ì…˜ 단계 ê°’." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "ì´ˆ" #: editor/animation_track_editor.cpp msgid "FPS" @@ -4773,20 +4778,19 @@ msgstr "ë ˆì´ì•„웃" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Translation mask for inserting keys." -msgstr "" +msgstr "키를 삽입하기 위한 ì „í™˜ 마스í¬." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Rotation mask for inserting keys." -msgstr "" +msgstr "키를 삽입하기 위한 íšŒì „ 마스í¬." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Scale mask for inserting keys." -msgstr "" +msgstr "키를 삽입하기 위한 규모 마스í¬." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Insert keys (based on mask)." -msgstr "키 삽입 (Ins 키)" +msgstr "키 삽입 (ë§ˆìŠ¤í¬ ê¸°ì¤€)." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "" @@ -4795,11 +4799,13 @@ msgid "" "Keys are only added to existing tracks, no new tracks will be created.\n" "Keys must be inserted manually for the first time." msgstr "" +"물체가 ì „í™˜ë ë•Œ ìžë™ìœ¼ë¡œ 키를 삽입합니다, íšŒì „ ë˜ëŠ” 규모 (ë§ˆìŠ¤í¬ ê¸°ì¤€).\n" +"키는 기존 트랙ì—만 추가ë˜ë©°, 새 íŠ¸ëž™ì´ ë§Œë“¤ì–´ì§€ì§€ 않습니다.\n" +"처ìŒì— 키는 수ë™ìœ¼ë¡œ 삽입하여야 합니다." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Auto Insert Key" -msgstr "ì• ë‹ˆë©”ì´ì…˜ 키 삽입" +msgstr "ìžë™ 키 삽입" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Insert Key (Existing Tracks)" @@ -5785,9 +5791,8 @@ msgid "Save Theme As..." msgstr "테마 다른 ì´ë¦„으로 ì €ìž¥..." #: editor/plugins/script_editor_plugin.cpp -#, fuzzy msgid "%s Class Reference" -msgstr " í´ëž˜ìŠ¤ ë ˆí¼ëŸ°ìŠ¤" +msgstr "%s í´ëž˜ìŠ¤ 참조" #: editor/plugins/script_editor_plugin.cpp msgid "Toggle alphabetical sorting of the method list." @@ -6420,7 +6425,7 @@ msgstr "í¬ê¸° ì¡°ì ˆ 모드 (R)" #: editor/plugins/spatial_editor_plugin.cpp msgid "Local Coords" -msgstr "로컬 좌표" +msgstr "ì§€ì— ì¢Œí‘œ" #: editor/plugins/spatial_editor_plugin.cpp msgid "Local Space Mode (%s)" @@ -6612,24 +6617,20 @@ msgid "Nameless gizmo" msgstr "ì´ë¦„없는 오브ì íŠ¸ì˜ ì¤‘ì‹¬ì " #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Mesh2D" -msgstr "2D 메시 만들기" +msgstr "Mesh2D 만들기" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Polygon2D" -msgstr "í´ë¦¬ê³¤3D 만들기" +msgstr "Polygon2D 만들기" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D" -msgstr "내비게ì´ì…˜ ì¶©ëŒ í´ë¦¬ê³¤ 만들기" +msgstr "CollisionPolygon2D 만들기" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D" -msgstr "Occluder í´ë¦¬ê³¤ 만들기" +msgstr "LightOccluder2D 만들기" #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite is empty!" @@ -6641,46 +6642,39 @@ msgstr "스프ë¼ì´íŠ¸ê°€ ì• ë‹ˆë©”ì´ì…˜ í”„ë ˆìž„ì„ ì‚¬ìš©í•´ì„œ 메시로 ì #: editor/plugins/sprite_editor_plugin.cpp msgid "Invalid geometry, can't replace by mesh." -msgstr "ìœ íš¨í•˜ì§€ ì•Šì€ í˜•ìƒ, 메시로 ëŒ€ì²´í• ìˆ˜ 없습니다." +msgstr "ìž˜ëª»ëœ í˜•íƒœ, 메시로 ëŒ€ì²´í• ìˆ˜ 없습니다." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create polygon." -msgstr "ìœ íš¨í•˜ì§€ ì•Šì€ í˜•ìƒ, 메시로 ëŒ€ì²´í• ìˆ˜ 없습니다." +msgstr "ìž˜ëª»ëœ í˜•íƒœ, í´ë¦¬ê³¤ì„ 만들 수 없습니다." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create collision polygon." -msgstr "ìœ íš¨í•˜ì§€ ì•Šì€ í˜•ìƒ, 메시로 ëŒ€ì²´í• ìˆ˜ 없습니다." +msgstr "ìž˜ëª»ëœ í˜•íƒœ, ì¶©ëŒ í´ë¦¬ê³¤ì„ 만들 수 없습니다." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create light occluder." -msgstr "ìœ íš¨í•˜ì§€ ì•Šì€ í˜•ìƒ, 메시로 ëŒ€ì²´í• ìˆ˜ 없습니다." +msgstr "ìž˜ëª»ëœ í˜•íƒœ, 조명 ì–´í´ë£¨ë”를 만들 수 없습니다." #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite" msgstr "스프ë¼ì´íŠ¸" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Mesh2D" -msgstr "2D 메시로 ì „í™˜" +msgstr "Mesh2Dë¡œ ì „í™˜" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Polygon2D" -msgstr "í´ë¦¬ê³¤ ì´ë™" +msgstr "Polygon2Dë¡œ ì „í™˜" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D Sibling" -msgstr "내비게ì´ì…˜ ì¶©ëŒ í´ë¦¬ê³¤ 만들기" +msgstr "CollisionPolygon2D 노드 만들기" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D Sibling" -msgstr "Occluder í´ë¦¬ê³¤ 만들기" +msgstr "LightOccluder2D 노드 만들기" #: editor/plugins/sprite_editor_plugin.cpp msgid "Simplification: " @@ -7266,7 +7260,6 @@ msgid "Duplicate Nodes" msgstr "노드 ë³µì œ" #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Delete Nodes" msgstr "노드 ì‚ì œ" @@ -8974,7 +8967,7 @@ msgstr "ë¼ì´ë¸ŒëŸ¬ë¦¬ë“¤: " #: modules/gdnative/register_types.cpp msgid "GDNative" -msgstr "GD네ì´í‹°ë¸Œ" +msgstr "GDNative" #: modules/gdscript/gdscript_functions.cpp msgid "Step argument is zero!" diff --git a/editor/translations/lt.po b/editor/translations/lt.po index 22fe1747e6..e21910b69f 100644 --- a/editor/translations/lt.po +++ b/editor/translations/lt.po @@ -158,12 +158,18 @@ msgstr "" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "Animacija: PridÄ—ti Takelį" +msgid "Animation length (frames)" +msgstr "Animacija" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" -msgstr "" +#, fuzzy +msgid "Animation length (seconds)" +msgstr "Animacijos Nodas" + +#: editor/animation_track_editor.cpp +#, fuzzy +msgid "Add Track" +msgstr "Animacija: PridÄ—ti Takelį" #: editor/animation_track_editor.cpp #, fuzzy diff --git a/editor/translations/lv.po b/editor/translations/lv.po index a8acaaf300..d0d40ffcc5 100644 --- a/editor/translations/lv.po +++ b/editor/translations/lv.po @@ -157,14 +157,20 @@ msgid "Animation Playback Track" msgstr "AnimÄcijas atskaņoÅ¡anas celiņs" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Pievienot celiņu" +#, fuzzy +msgid "Animation length (frames)" +msgstr "AnimÄcijas Garums (sekundes)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "AnimÄcijas Garums (sekundes)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Pievienot celiņu" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "AnimÄciju Cilpa" diff --git a/editor/translations/mi.po b/editor/translations/mi.po index 30d76b28d3..4bb8d367f0 100644 --- a/editor/translations/mi.po +++ b/editor/translations/mi.po @@ -144,11 +144,15 @@ msgid "Animation Playback Track" msgstr "" #: editor/animation_track_editor.cpp -msgid "Add Track" +msgid "Animation length (frames)" msgstr "" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Add Track" msgstr "" #: editor/animation_track_editor.cpp diff --git a/editor/translations/ml.po b/editor/translations/ml.po index 215ca3d2cc..2dc5014173 100644 --- a/editor/translations/ml.po +++ b/editor/translations/ml.po @@ -152,11 +152,15 @@ msgid "Animation Playback Track" msgstr "" #: editor/animation_track_editor.cpp -msgid "Add Track" +msgid "Animation length (frames)" msgstr "" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Add Track" msgstr "" #: editor/animation_track_editor.cpp diff --git a/editor/translations/ms.po b/editor/translations/ms.po index f253cca02b..07647f5341 100644 --- a/editor/translations/ms.po +++ b/editor/translations/ms.po @@ -157,15 +157,19 @@ msgid "Animation Playback Track" msgstr "" #: editor/animation_track_editor.cpp -#, fuzzy -msgid "Add Track" -msgstr "Anim Tambah Trek" +msgid "Animation length (frames)" +msgstr "" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "" #: editor/animation_track_editor.cpp +#, fuzzy +msgid "Add Track" +msgstr "Anim Tambah Trek" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "" diff --git a/editor/translations/nb.po b/editor/translations/nb.po index 26bd0cc890..af0f07cf1b 100644 --- a/editor/translations/nb.po +++ b/editor/translations/nb.po @@ -13,11 +13,12 @@ # passeride <lukas@passeride.com>, 2017. # Byzantin <kasper-hoel@hotmail.com>, 2018. # Hans-Marius ØverÃ¥s <hansmariusoveras@gmail.com>, 2019. +# Revolution <revosw@gmail.com>, 2019. msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-04-23 15:48+0000\n" +"PO-Revision-Date: 2019-05-04 13:48+0000\n" "Last-Translator: Allan Nordhøy <epost@anotheragency.no>\n" "Language-Team: Norwegian BokmÃ¥l <https://hosted.weblate.org/projects/godot-" "engine/godot/nb_NO/>\n" @@ -143,7 +144,7 @@ msgstr "Endre Animasjonsnavn:" #: editor/animation_track_editor.cpp #: editor/plugins/sprite_frames_editor_plugin.cpp msgid "Change Animation Loop" -msgstr "" +msgstr "Endre Animasjonssløyfe" #: editor/animation_track_editor.cpp #, fuzzy @@ -177,16 +178,21 @@ msgstr "Stopp avspilling av animasjon. (S)" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "Anim Legg til Spor" +msgid "Animation length (frames)" +msgstr "Animasjon lengde (i sekunder)." #: editor/animation_track_editor.cpp #, fuzzy -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "Animasjon lengde (i sekunder)." #: editor/animation_track_editor.cpp #, fuzzy +msgid "Add Track" +msgstr "Anim Legg til Spor" + +#: editor/animation_track_editor.cpp +#, fuzzy msgid "Animation Looping" msgstr "Animasjons-zoom." @@ -239,7 +245,7 @@ msgstr "X-Fade Tid (s):" #: editor/animation_track_editor.cpp msgid "Toggle Track Enabled" -msgstr "" +msgstr "Veksl Aktivering Av Spor" #: editor/animation_track_editor.cpp msgid "Continuous" @@ -273,11 +279,11 @@ msgstr "Kubisk" #: editor/animation_track_editor.cpp msgid "Clamp Loop Interp" -msgstr "" +msgstr "Klem Sløyfeinterp" #: editor/animation_track_editor.cpp msgid "Wrap Loop Interp" -msgstr "" +msgstr "Pakk Inn Sløyfeinterp" #: editor/animation_track_editor.cpp #: editor/plugins/canvas_item_editor_plugin.cpp @@ -351,14 +357,12 @@ msgid "Anim Insert Key" msgstr "Anim Sett Inn Nøkkel" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Change Animation Step" -msgstr "Endre Animasjonsnavn:" +msgstr "Endre Animasjonstrinn" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Rearrange Tracks" -msgstr "Omorganiser Autoloads" +msgstr "Omorganiser Spor" #: editor/animation_track_editor.cpp #, fuzzy @@ -378,7 +382,6 @@ msgstr "" "-AudioStreamPlayer3D" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Animation tracks can only point to AnimationPlayer nodes." msgstr "Animasjonsspor kan kun peke pÃ¥ AnimationPlayer-noder." @@ -418,9 +421,8 @@ msgid "Add Track Key" msgstr "Anim Legg til Spor" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Track path is invalid, so can't add a method key." -msgstr "Sporsti er ugyldig, sÃ¥ kan ikke legge til metodenøkkel." +msgstr "Sporsti er ugyldig, sÃ¥ kan ikke legge til en metodenøkkel." #: editor/animation_track_editor.cpp #, fuzzy @@ -477,11 +479,11 @@ msgstr "Animasjonstre er gyldig." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "Sekunder" #: editor/animation_track_editor.cpp msgid "FPS" -msgstr "" +msgstr "FPS" #: editor/animation_track_editor.cpp editor/editor_properties.cpp #: editor/plugins/polygon_2d_editor_plugin.cpp @@ -612,11 +614,11 @@ msgstr "Lydklipp:" #: editor/animation_track_editor_plugins.cpp msgid "Change Audio Track Clip Start Offset" -msgstr "" +msgstr "Endre Forskyvning Av Lydklippets Start" #: editor/animation_track_editor_plugins.cpp msgid "Change Audio Track Clip End Offset" -msgstr "" +msgstr "Endre Forskyvning Av Lydklippets Slutt" #: editor/array_property_edit.cpp msgid "Resize Array" @@ -688,7 +690,7 @@ msgstr "Advarsler" #: editor/code_editor.cpp msgid "Line and column numbers." -msgstr "" +msgstr "Linje- og kolonnenummer." #: editor/connections_dialog.cpp msgid "Method in target Node must be specified!" @@ -1445,12 +1447,16 @@ msgid "" "Target platform requires 'ETC' texture compression for GLES2. Enable 'Import " "Etc' in Project Settings." msgstr "" +"MÃ¥lplatform krever 'ETC' teksturkomprimering for GLES2. Aktiver 'Importer " +"Etc' i Prosjektinnstillinger." #: editor/editor_export.cpp msgid "" "Target platform requires 'ETC2' texture compression for GLES3. Enable " "'Import Etc 2' in Project Settings." msgstr "" +"MÃ¥lplatform krever 'ETC' teksturkomprimering for GLES3. Aktiver 'Importer " +"Etc 2' i Prosjektinnstillinger." #: editor/editor_export.cpp msgid "" @@ -1459,6 +1465,10 @@ msgid "" "Enable 'Import Etc' in Project Settings, or disable 'Driver Fallback " "Enabled'." msgstr "" +"MÃ¥lplatform krever 'ETC' teksturkomprimering for drivertilbakefallet til " +"GLES2.\n" +"Aktiver 'Importer Etc' i Prosjektinnstillinger, eller deaktiver " +"'Drivertilbakefall Aktivert'." #: editor/editor_export.cpp platform/android/export/export.cpp #: platform/iphone/export/export.cpp platform/javascript/export/export.cpp @@ -1857,7 +1867,7 @@ msgstr "Eksport av prosjektet mislyktes med feilkode %d." #: editor/editor_node.cpp msgid "Imported resources can't be saved." -msgstr "" +msgstr "Importerte ressurser kan ikke lagres." #: editor/editor_node.cpp editor/plugins/script_editor_plugin.cpp #: scene/gui/dialogs.cpp @@ -1873,6 +1883,8 @@ msgid "" "This resource can't be saved because it does not belong to the edited scene. " "Make it unique first." msgstr "" +"Denne ressursen kan ikke lagres fordi den hører ikke til den redigerte " +"scenen. Gjør den unik først." #: editor/editor_node.cpp editor/plugins/animation_player_editor_plugin.cpp msgid "Save Resource As..." @@ -2102,7 +2114,7 @@ msgstr "Kunne ikke laste ressurs." #: editor/editor_node.cpp msgid "A root node is required to save the scene." -msgstr "" +msgstr "En rotnode kreves for Ã¥ lagre scenen." #: editor/editor_node.cpp msgid "Save Scene As..." @@ -2544,7 +2556,7 @@ msgstr "Redigeringsverktøy-instillinger" #: editor/editor_node.cpp msgid "Open Editor Data Folder" -msgstr "" +msgstr "Ã…pne Redigererdatamappen" #: editor/editor_node.cpp #, fuzzy @@ -2958,12 +2970,12 @@ msgstr "Nytt navn:" #: editor/editor_properties_array_dict.cpp msgid "Add Key/Value Pair" -msgstr "" +msgstr "Legg Til Nøkkel/Verdi Par" #: editor/editor_properties_array_dict.cpp #: editor/plugins/theme_editor_plugin.cpp msgid "Remove Item" -msgstr "" +msgstr "Fjern Gjenstand" #: editor/editor_run_native.cpp msgid "Select device from the list" @@ -3400,7 +3412,7 @@ msgstr "En fil eller mappe med dette navnet eksisterer allerede." #: editor/filesystem_dock.cpp msgid "Overwrite" -msgstr "" +msgstr "Overskriv" #: editor/filesystem_dock.cpp editor/plugins/script_editor_plugin.cpp msgid "Create Script" @@ -3557,7 +3569,7 @@ msgstr "Importerer Scene..." #: editor/import/resource_importer_scene.cpp msgid "Generating Lightmaps" -msgstr "" +msgstr "Genererer Lyskart" #: editor/import/resource_importer_scene.cpp msgid "Generating for Mesh: " @@ -3611,16 +3623,19 @@ msgstr "Reimporter" #: editor/import_dock.cpp msgid "Save scenes, re-import and restart" -msgstr "" +msgstr "Lagre scener, om-importer og start om" #: editor/import_dock.cpp msgid "Changing the type of an imported file requires editor restart." -msgstr "" +msgstr "Ã… endre typen av en importert fil krever omstart av redigereren" #: editor/import_dock.cpp +#, fuzzy msgid "" "WARNING: Assets exist that use this resource, they may stop loading properly." msgstr "" +"ADVARSEL: ___ eksister som bruker denne ressursen, det kan hende de ikke " +"laster inn riktig." #: editor/inspector_dock.cpp msgid "Failed to load resource." @@ -3733,7 +3748,7 @@ msgstr "Plugins" #: editor/plugin_config_dialog.cpp msgid "Subfolder:" -msgstr "" +msgstr "Undermappe:" #: editor/plugin_config_dialog.cpp msgid "Language:" @@ -3834,7 +3849,7 @@ msgstr "Endre Blend-Tid" #: editor/plugins/animation_blend_space_2d_editor.cpp #: editor/plugins/animation_state_machine_editor.cpp msgid "This type of node can't be used. Only root nodes are allowed." -msgstr "" +msgstr "Denne typen node kan ikke bli brukt. Kun rotnoder er tillatt." #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp @@ -3855,7 +3870,7 @@ msgstr "Fjern Stipunkt" #: editor/plugins/animation_blend_space_1d_editor.cpp msgid "Move BlendSpace1D Node Point" -msgstr "" +msgstr "Flytt BlendSpace1D Nodepunkt" #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp @@ -3874,7 +3889,7 @@ msgstr "" #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp msgid "Select and move points, create points with RMB." -msgstr "" +msgstr "Velg og flytt punkt, lag punkt med høyre museklikk." #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp scene/gui/graph_edit.cpp diff --git a/editor/translations/nl.po b/editor/translations/nl.po index 6eb5a47d21..a9d958478a 100644 --- a/editor/translations/nl.po +++ b/editor/translations/nl.po @@ -32,12 +32,14 @@ # jef dered <themen098s@vivaldi.net>, 2019. # Alex H. <sandertjeh13@hotmail.com>, 2019. # edouardgr <edouard.gruyters@gmail.com>, 2019. +# Jimmy De Smet <J773@telenet.be>, 2019. +# Bastiaan van der Plaat <bastiaan.v.d.plaat@gmail.com>, 2019. msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-04-25 11:54+0000\n" -"Last-Translator: edouardgr <edouard.gruyters@gmail.com>\n" +"PO-Revision-Date: 2019-05-19 07:48+0000\n" +"Last-Translator: Alex H. <sandertjeh13@hotmail.com>\n" "Language-Team: Dutch <https://hosted.weblate.org/projects/godot-engine/godot/" "nl/>\n" "Language: nl\n" @@ -182,14 +184,20 @@ msgid "Animation Playback Track" msgstr "Animatie Terugspelen Track" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Track Toevoegen" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Animatielengte (in seconden)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Animatielengte (in seconden)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Track Toevoegen" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Animatie Loopen" @@ -207,13 +215,12 @@ msgid "Anim Clips:" msgstr "Animatieclips:" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Change Track Path" -msgstr "Wijzig Array Waarde" +msgstr "Verander Track pad" #: editor/animation_track_editor.cpp msgid "Toggle this track on/off." -msgstr "Aan-uitschakelaar Track." +msgstr "Schakel deze track aan/uit." #: editor/animation_track_editor.cpp msgid "Update Mode (How this property is set)" @@ -234,12 +241,11 @@ msgstr "Verwijder deze track." #: editor/animation_track_editor.cpp msgid "Time (s): " -msgstr "Tijd (s): " +msgstr "Tijd (en): " #: editor/animation_track_editor.cpp -#, fuzzy msgid "Toggle Track Enabled" -msgstr "Verander de ingeschakelde track" +msgstr "Track schakelaar ingeschakeld" #: editor/animation_track_editor.cpp msgid "Continuous" @@ -285,11 +291,11 @@ msgstr "Voer Sleutel in" #: editor/animation_track_editor.cpp msgid "Duplicate Key(s)" -msgstr "Dupliceer Key(s)" +msgstr "Dupliceer Sleutel(s)" #: editor/animation_track_editor.cpp msgid "Delete Key(s)" -msgstr "Verwijder Key(s)" +msgstr "Verwijder Sleutel(s)" #: editor/animation_track_editor.cpp msgid "Change Animation Update Mode" @@ -349,7 +355,6 @@ msgid "Change Animation Step" msgstr "Verander Animatiestappen" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Rearrange Tracks" msgstr "Herschik Tracks" @@ -396,14 +401,12 @@ msgid "Track is not of type Spatial, can't insert key" msgstr "Track is niet van het type Spatial, kan geen key invoegen" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Add Transform Track Key" -msgstr "3D Transformatie Track" +msgstr "Voeg Transformatie Track Sleutel toe" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Add Track Key" -msgstr "Track Toevoegen" +msgstr "Voeg Track sleutel toe" #: editor/animation_track_editor.cpp msgid "Track path is invalid, so can't add a method key." @@ -412,7 +415,7 @@ msgstr "Track path is niet geldig, dus kan geen methode key toevoegen." #: editor/animation_track_editor.cpp #, fuzzy msgid "Add Method Track Key" -msgstr "Methode Invocatie Track" +msgstr "Voeg Methode Track sleutel toe" #: editor/animation_track_editor.cpp msgid "Method not found in object: " @@ -452,7 +455,7 @@ msgstr "Sporen weergeven op basis van nodes of als lijst." #: editor/animation_track_editor.cpp #, fuzzy msgid "Snap:" -msgstr "Snap" +msgstr "Snap:" #: editor/animation_track_editor.cpp msgid "Animation step value." @@ -460,7 +463,7 @@ msgstr "Animatie stap waarde." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "Seconden" #: editor/animation_track_editor.cpp msgid "FPS" @@ -504,14 +507,12 @@ msgid "Delete Selection" msgstr "Verwijder Selectie" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Go to Next Step" -msgstr "Ga Naar Volgende Stap" +msgstr "Ga naar Volgende Stap" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Go to Previous Step" -msgstr "Ga Naar Vorige Stap" +msgstr "Ga naar Vorige Stap" #: editor/animation_track_editor.cpp msgid "Optimize Animation" @@ -588,15 +589,15 @@ msgstr "Kopiëren" #: editor/animation_track_editor_plugins.cpp #, fuzzy msgid "Add Audio Track Clip" -msgstr "Audioclips:" +msgstr "Voeg audiospoorclip toe" #: editor/animation_track_editor_plugins.cpp msgid "Change Audio Track Clip Start Offset" -msgstr "" +msgstr "Wijzig start afwijking van audiospoorclip" #: editor/animation_track_editor_plugins.cpp msgid "Change Audio Track Clip End Offset" -msgstr "" +msgstr "Wijzig eind afwijking van audiospoorclip" #: editor/array_property_edit.cpp msgid "Resize Array" @@ -752,9 +753,8 @@ msgid "Disconnect '%s' from '%s'" msgstr "Ontkoppel '%s' van '%s'" #: editor/connections_dialog.cpp -#, fuzzy msgid "Disconnect all from signal: '%s'" -msgstr "Ontkoppel '%s' van '%s'" +msgstr "Ontkoppel alles van signaal: '%s'" #: editor/connections_dialog.cpp msgid "Connect..." @@ -788,9 +788,8 @@ msgstr "" "Weet je zeker dat je alle verbindingen naar dit signaal wilt verwijderen?" #: editor/connections_dialog.cpp -#, fuzzy msgid "Disconnect All" -msgstr "Losmaken" +msgstr "Ontkoppel Alles" #: editor/connections_dialog.cpp msgid "Edit..." @@ -934,9 +933,8 @@ msgid "Error loading:" msgstr "Error bij het laden van:" #: editor/dependency_editor.cpp -#, fuzzy msgid "Load failed due to missing dependencies:" -msgstr "Scene faalde om te laden door ontbrekende afhankelijkheden:" +msgstr "Laden mislukt vanwege het ontbrekende van afhankelijkheden:" #: editor/dependency_editor.cpp editor/editor_node.cpp msgid "Open Anyway" @@ -1236,7 +1234,7 @@ msgstr "Bus Toevoegen" #: editor/editor_audio_buses.cpp #, fuzzy msgid "Add a new Audio Bus to this layout." -msgstr "Sla Audio Bus Layout Op Als..." +msgstr "Voeg een nieuwe Audio Bus toe aan deze layout." #: editor/editor_audio_buses.cpp editor/editor_properties.cpp #: editor/plugins/animation_player_editor_plugin.cpp editor/property_editor.cpp @@ -1558,14 +1556,12 @@ msgid "Move Favorite Down" msgstr "Verplaats Favoriet Naar Beneden" #: editor/editor_file_dialog.cpp -#, fuzzy msgid "Previous Folder" -msgstr "Vorig tabblad" +msgstr "Vorige Folder" #: editor/editor_file_dialog.cpp -#, fuzzy msgid "Next Folder" -msgstr "Map Maken" +msgstr "Volgende Folder" #: editor/editor_file_dialog.cpp msgid "Go to parent folder" @@ -1581,9 +1577,8 @@ msgid "View items as a grid of thumbnails." msgstr "Toon items in een miniatuurraster." #: editor/editor_file_dialog.cpp editor/filesystem_dock.cpp -#, fuzzy msgid "View items as a list." -msgstr "Bekijk objecten als een lijst" +msgstr "Bekijk items als een lijst." #: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp msgid "Directories & Files:" @@ -1893,6 +1888,8 @@ msgid "" "This scene can't be saved because there is a cyclic instancing inclusion.\n" "Please resolve it and then attempt to save again." msgstr "" +"Deze scene kan niet opgeslagen worden vanwege een cyclische instantiëring.\n" +"Opslaan is pas mogelijk als dit opgelost wordt." #: editor/editor_node.cpp msgid "" @@ -4254,6 +4251,8 @@ msgstr "De uitgekozen knoop of overgang verwijderen." #: editor/plugins/animation_state_machine_editor.cpp msgid "Toggle autoplay this animation on start, restart or seek to zero." msgstr "" +"Schakel tussen automatisch afspelen van deze animatie bij start, herstart of " +"zoek naar nul." #: editor/plugins/animation_state_machine_editor.cpp msgid "Set the end animation. This is useful for sub-transitions." @@ -4902,16 +4901,19 @@ msgid "Layout" msgstr "Indeling" #: editor/plugins/canvas_item_editor_plugin.cpp +#, fuzzy msgid "Translation mask for inserting keys." -msgstr "" +msgstr "Vertaalmasker voor het invoegen van sleutels." #: editor/plugins/canvas_item_editor_plugin.cpp +#, fuzzy msgid "Rotation mask for inserting keys." -msgstr "" +msgstr "Rotatiemasker voor het invoegen van sleutels." #: editor/plugins/canvas_item_editor_plugin.cpp +#, fuzzy msgid "Scale mask for inserting keys." -msgstr "" +msgstr "Schaalmasker voor het invoegen van sleutels." #: editor/plugins/canvas_item_editor_plugin.cpp #, fuzzy @@ -4919,12 +4921,18 @@ msgid "Insert keys (based on mask)." msgstr "Voeg Sleutel in (Bestaande Banen)" #: editor/plugins/canvas_item_editor_plugin.cpp +#, fuzzy msgid "" "Auto insert keys when objects are translated, rotated on scaled (based on " "mask).\n" "Keys are only added to existing tracks, no new tracks will be created.\n" "Keys must be inserted manually for the first time." msgstr "" +"Automatische invoegtoetsen bij het vertalen van objecten, geroteerd op " +"schaal (op basis van masker).\n" +"Sleutels worden alleen toegevoegd aan bestaande tracks, er worden geen " +"nieuwe tracks aangemaakt.\n" +"Sleutels moeten voor de eerste keer handmatig worden ingevoerd." #: editor/plugins/canvas_item_editor_plugin.cpp #, fuzzy @@ -5568,7 +5576,7 @@ msgstr "" #: editor/plugins/path_2d_editor_plugin.cpp #: editor/plugins/path_editor_plugin.cpp msgid "Mirror Handle Lengths" -msgstr "" +msgstr "Spiegel Lengtehendels" #: editor/plugins/path_editor_plugin.cpp msgid "Curve Point #" @@ -5681,7 +5689,7 @@ msgstr "Transformatie Type" #: editor/plugins/polygon_2d_editor_plugin.cpp msgid "Paint Bone Weights" -msgstr "" +msgstr "Teken Botgewichten" #: editor/plugins/polygon_2d_editor_plugin.cpp #, fuzzy @@ -6101,12 +6109,13 @@ msgid "Open Godot online documentation" msgstr "Open Godot online documentatie" #: editor/plugins/script_editor_plugin.cpp +#, fuzzy msgid "Request Docs" -msgstr "" +msgstr "Verzoek Documenten" #: editor/plugins/script_editor_plugin.cpp msgid "Help improve the Godot documentation by giving feedback" -msgstr "" +msgstr "Help de Godot-documentatie te verbeteren door feedback te geven" #: editor/plugins/script_editor_plugin.cpp msgid "Search the reference documentation." @@ -6311,8 +6320,10 @@ msgid "Shader" msgstr "Shader" #: editor/plugins/skeleton_2d_editor_plugin.cpp +#, fuzzy msgid "This skeleton has no bones, create some children Bone2D nodes." msgstr "" +"Dit skelet heeft geen botten, creëer enkele Bone2D-knooppunten als kinderen." #: editor/plugins/skeleton_2d_editor_plugin.cpp #, fuzzy @@ -6985,8 +6996,9 @@ msgid "SpriteFrames" msgstr "Sprite-Frames" #: editor/plugins/texture_region_editor_plugin.cpp +#, fuzzy msgid "Set Region Rect" -msgstr "" +msgstr "Stel Gebied Vierkant in" #: editor/plugins/texture_region_editor_plugin.cpp msgid "Set Margin" @@ -7336,10 +7348,13 @@ msgid "%s file(s) were not added because was already on the list." msgstr "%s bestand(en) niet toegevoegd omdat deze al op de lijst staan." #: editor/plugins/tile_set_editor_plugin.cpp +#, fuzzy msgid "" "Drag handles to edit Rect.\n" "Click on another Tile to edit it." msgstr "" +"Versleep handles om Vierkant te bewerken.\n" +"Klik op een andere Tegel om deze te bewerken." #: editor/plugins/tile_set_editor_plugin.cpp #, fuzzy @@ -7493,8 +7508,9 @@ msgid "TileSet" msgstr "TileSet..." #: editor/plugins/visual_shader_editor_plugin.cpp +#, fuzzy msgid "Set Uniform Name" -msgstr "" +msgstr "Uniforme naam instellen" #: editor/plugins/visual_shader_editor_plugin.cpp #, fuzzy @@ -7786,7 +7802,7 @@ msgstr "Kan project.godot niet in projectpad maken." #: editor/project_manager.cpp msgid "The following files failed extraction from package:" -msgstr "" +msgstr "De volgende bestanden konden niet worden uitgepakt:" #: editor/project_manager.cpp #, fuzzy @@ -8405,7 +8421,7 @@ msgstr "Bestand..." #: editor/property_editor.cpp msgid "Dir..." -msgstr "" +msgstr "Pad..." #: editor/property_editor.cpp msgid "Assign" @@ -8427,7 +8443,7 @@ msgstr "Plak Nodes" #: editor/property_editor.cpp msgid "Bit %d, val %d." -msgstr "" +msgstr "Bit %d, waarde %d." #: editor/property_selector.cpp msgid "Select Property" @@ -8620,7 +8636,7 @@ msgstr "Scene Uitvoerinstellingen" #: editor/scene_tree_dock.cpp msgid "No parent to instance the scenes at." -msgstr "" +msgstr "Geen ouder om scenes mee te instantiëren." #: editor/scene_tree_dock.cpp msgid "Error loading scene from %s" @@ -8645,16 +8661,19 @@ msgid "Clear Script" msgstr "Script vrijmaken" #: editor/scene_tree_dock.cpp +#, fuzzy msgid "This operation can't be done on the tree root." -msgstr "" +msgstr "Deze bewerking kan niet worden uitgevoerd op de tree root." #: editor/scene_tree_dock.cpp +#, fuzzy msgid "Move Node In Parent" -msgstr "" +msgstr "Verplaats knooppunt naar ouder" #: editor/scene_tree_dock.cpp +#, fuzzy msgid "Move Nodes In Parent" -msgstr "" +msgstr "Verplaats knooppunten naar ouder" #: editor/scene_tree_dock.cpp msgid "Duplicate Node(s)" diff --git a/editor/translations/pl.po b/editor/translations/pl.po index 7923ebe539..0d663d94e4 100644 --- a/editor/translations/pl.po +++ b/editor/translations/pl.po @@ -33,11 +33,12 @@ # Robert <vizz0@onet.pl>, 2019. # MichaÅ‚ Topa <moonchasered@gmail.com>, 2019. # PrzemysÅ‚aw Pierzga <przemyslawpierzga@gmail.com>, 2019. +# Artur MaciÄ…g <arturmaciag@gmail.com>, 2019. msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-04-25 11:54+0000\n" +"PO-Revision-Date: 2019-05-08 11:48+0000\n" "Last-Translator: Tomek <kobewi4e@gmail.com>\n" "Language-Team: Polish <https://hosted.weblate.org/projects/godot-engine/" "godot/pl/>\n" @@ -185,14 +186,20 @@ msgid "Animation Playback Track" msgstr "Åšcieżka animacji" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Dodaj Å›cieżkÄ™" +#, fuzzy +msgid "Animation length (frames)" +msgstr "DÅ‚ugość animacji (sekundy)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "DÅ‚ugość animacji (sekundy)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Dodaj Å›cieżkÄ™" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "ZapÄ™tlenie animacji" @@ -445,9 +452,8 @@ msgid "Group tracks by node or display them as plain list." msgstr "Grupuj Å›cieżki po wÄ™zÅ‚ach lub wyÅ›wietl je jako prostÄ… listÄ™." #: editor/animation_track_editor.cpp -#, fuzzy msgid "Snap:" -msgstr "PrzyciÄ…gaj" +msgstr "PrzyciÄ…ganie:" #: editor/animation_track_editor.cpp msgid "Animation step value." @@ -455,7 +461,7 @@ msgstr "Wartość kroku animacji." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "sekund" #: editor/animation_track_editor.cpp msgid "FPS" @@ -2218,7 +2224,7 @@ msgstr "Zamknij kartÄ™" #: editor/editor_node.cpp msgid "Switch Scene Tab" -msgstr "PrzeÅ‚Ä…cz ZakÅ‚adkÄ™ Sceny" +msgstr "PrzeÅ‚Ä…cz zakÅ‚adkÄ™ sceny" #: editor/editor_node.cpp msgid "%d more files or folders" @@ -4822,20 +4828,19 @@ msgstr "UkÅ‚ad" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Translation mask for inserting keys." -msgstr "" +msgstr "Maska przesuniÄ™cia dla wstawiania kluczy." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Rotation mask for inserting keys." -msgstr "" +msgstr "Maska obrotu dla wstawiania kluczy." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Scale mask for inserting keys." -msgstr "" +msgstr "Maska skali dla wstawiania kluczy." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Insert keys (based on mask)." -msgstr "Wstaw klucz (istniejÄ…ce Å›cieżki)" +msgstr "Wstaw klucze (w oparciu o maskÄ™)." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "" @@ -4844,11 +4849,15 @@ msgid "" "Keys are only added to existing tracks, no new tracks will be created.\n" "Keys must be inserted manually for the first time." msgstr "" +"Automatycznie wstaw klucze, kiedy obiekt jest przesuwany, obracany lub " +"skalowany (w oparciu o maskÄ™).\n" +"Klucze sÄ… dodawane tylko do istniejÄ…cych Å›cieżek, żadne nowe Å›cieżki nie " +"zostanÄ… utworzone.\n" +"Za pierwszym razem klucze muszÄ… być umieszczone rÄ™cznie." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Auto Insert Key" -msgstr "Wstaw klatkÄ™ kluczowÄ…" +msgstr "Automatycznie wstaw klucz" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Insert Key (Existing Tracks)" @@ -5834,9 +5843,8 @@ msgid "Save Theme As..." msgstr "Zapisz motyw jako..." #: editor/plugins/script_editor_plugin.cpp -#, fuzzy msgid "%s Class Reference" -msgstr " - referencja klasy" +msgstr "Referencja klasy %s" #: editor/plugins/script_editor_plugin.cpp msgid "Toggle alphabetical sorting of the method list." @@ -6660,24 +6668,20 @@ msgid "Nameless gizmo" msgstr "Uchwyt bez nazwy" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Mesh2D" -msgstr "Utwórz siatkÄ™ 2D" +msgstr "Utwórz wÄ™zeÅ‚ Mesh2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Polygon2D" -msgstr "Utwórz WielokÄ…t3D" +msgstr "Utwórz wÄ™zeÅ‚ Polygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D" -msgstr "Utwórz wielokÄ…t kolizji" +msgstr "Utwórz wÄ™zeÅ‚ CollisionPolygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D" -msgstr "Stwórz Occluder Polygon" +msgstr "Utwórz wÄ™zeÅ‚ LightOccluder2D" #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite is empty!" @@ -6693,43 +6697,36 @@ msgid "Invalid geometry, can't replace by mesh." msgstr "NieprawidÅ‚owa geometria, nie można zastÄ…pić przez siatkÄ™." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create polygon." -msgstr "NieprawidÅ‚owa geometria, nie można zastÄ…pić przez siatkÄ™." +msgstr "NieprawidÅ‚owa geometria, nie można utworzyć wielokÄ…ta." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create collision polygon." -msgstr "NieprawidÅ‚owa geometria, nie można zastÄ…pić przez siatkÄ™." +msgstr "NieprawidÅ‚owa geometria, nie można utworzyć wielokÄ…ta kolizji." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create light occluder." -msgstr "NieprawidÅ‚owa geometria, nie można zastÄ…pić przez siatkÄ™." +msgstr "NieprawidÅ‚owa geometria, nie można utworzyć przesÅ‚aniacza Å›wiatÅ‚a." #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite" msgstr "Sprite" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Mesh2D" -msgstr "Konwertuj do siatki 2D" +msgstr "ZamieÅ„ na Mesh2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Polygon2D" -msgstr "PrzesuÅ„ WielokÄ…t" +msgstr "ZamieÅ„ na Polygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D Sibling" -msgstr "Utwórz wielokÄ…t kolizji" +msgstr "Utwórz równorzÄ™dny wÄ™zeÅ‚ CollisionPolygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D Sibling" -msgstr "Stwórz Occluder Polygon" +msgstr "Utwórz równorzÄ™dny wÄ™zeÅ‚ LightOccluder2D" #: editor/plugins/sprite_editor_plugin.cpp msgid "Simplification: " @@ -7314,9 +7311,8 @@ msgid "Duplicate Nodes" msgstr "Duplikuj wÄ™zÅ‚y" #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Delete Nodes" -msgstr "UsuÅ„ wÄ™zeÅ‚" +msgstr "UsuÅ„ wÄ™zÅ‚y" #: editor/plugins/visual_shader_editor_plugin.cpp msgid "Visual Shader Input Type Changed" diff --git a/editor/translations/pr.po b/editor/translations/pr.po index 0aa4cbbca8..914145719d 100644 --- a/editor/translations/pr.po +++ b/editor/translations/pr.po @@ -168,11 +168,16 @@ msgid "Animation Playback Track" msgstr "" #: editor/animation_track_editor.cpp -msgid "Add Track" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Yer unique name be evil." + +#: editor/animation_track_editor.cpp +msgid "Animation length (seconds)" msgstr "" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +msgid "Add Track" msgstr "" #: editor/animation_track_editor.cpp diff --git a/editor/translations/pt_BR.po b/editor/translations/pt_BR.po index 9dc52df2be..5412309075 100644 --- a/editor/translations/pt_BR.po +++ b/editor/translations/pt_BR.po @@ -58,12 +58,13 @@ # Hans M. Boron <hansmateusboron@gmail.com>, 2019. # Gustavo Bolanho <jdmapas@gmail.com>, 2019. # Nilton Bendini Junior <almascelulas@bol.com.br>, 2019. +# Ivo Nascimento <iannsp@gmail.com>, 2019. msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: 2016-05-30\n" -"PO-Revision-Date: 2019-04-19 16:33+0000\n" -"Last-Translator: Nilton Bendini Junior <almascelulas@bol.com.br>\n" +"PO-Revision-Date: 2019-04-29 08:48+0000\n" +"Last-Translator: Ivo Nascimento <iannsp@gmail.com>\n" "Language-Team: Portuguese (Brazil) <https://hosted.weblate.org/projects/" "godot-engine/godot/pt_BR/>\n" "Language: pt_BR\n" @@ -71,7 +72,7 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=n > 1;\n" -"X-Generator: Weblate 3.6-dev\n" +"X-Generator: Weblate 3.6.1\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -207,14 +208,20 @@ msgid "Animation Playback Track" msgstr "Faixa de Reprodução de Animação" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Adicionar Trilha" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Duração da Animação (em segundos)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Duração da Animação (em segundos)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Adicionar Trilha" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Loop da Animação" @@ -478,7 +485,7 @@ msgstr "Valor do passo de animação." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "Segundos" #: editor/animation_track_editor.cpp msgid "FPS" diff --git a/editor/translations/pt_PT.po b/editor/translations/pt_PT.po index f9e93885d9..f83c37d2c3 100644 --- a/editor/translations/pt_PT.po +++ b/editor/translations/pt_PT.po @@ -18,7 +18,7 @@ msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-03-30 20:04+0000\n" +"PO-Revision-Date: 2019-04-29 08:48+0000\n" "Last-Translator: João Lopes <linux-man@hotmail.com>\n" "Language-Team: Portuguese (Portugal) <https://hosted.weblate.org/projects/" "godot-engine/godot/pt_PT/>\n" @@ -27,7 +27,7 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=n != 1;\n" -"X-Generator: Weblate 3.6-dev\n" +"X-Generator: Weblate 3.6.1\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -164,14 +164,20 @@ msgid "Animation Playback Track" msgstr "Pista de Reprodução de Animação" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Adicionar Pista" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Duração da Animação (segundos)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Duração da Animação (segundos)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Adicionar Pista" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Loop da Animação" @@ -288,11 +294,11 @@ msgstr "Remover Pista de Animação" #: editor/animation_track_editor.cpp msgid "Create NEW track for %s and insert key?" -msgstr "Criar NOVA Pista para %s e inserir Chave?" +msgstr "Criar NOVA pista para %s e inserir chave?" #: editor/animation_track_editor.cpp msgid "Create %d NEW tracks and insert keys?" -msgstr "Criar %d NOVAS Pistas e inserir Chaves?" +msgstr "Criar %d NOVAS pistas e inserir chaves?" #: editor/animation_track_editor.cpp editor/create_dialog.cpp #: editor/editor_audio_buses.cpp editor/editor_plugin_settings.cpp @@ -373,7 +379,7 @@ msgstr "Caminho da pista é inválido, não se consegue adicionar uma chave." #: editor/animation_track_editor.cpp msgid "Track is not of type Spatial, can't insert key" -msgstr "Pista não do tipo Spatial, não se consegue inserir chave" +msgstr "Pista não do tipo Spatial, impossÃvel inserir chave" #: editor/animation_track_editor.cpp msgid "Add Transform Track Key" @@ -385,8 +391,7 @@ msgstr "Adicionar Chave da Pista" #: editor/animation_track_editor.cpp msgid "Track path is invalid, so can't add a method key." -msgstr "" -"Caminho da pista é inválido, não se consegue adicionar uma chave método." +msgstr "Caminho da pista é inválido, impossÃvel adicionar uma chave método." #: editor/animation_track_editor.cpp msgid "Add Method Track Key" @@ -427,9 +432,8 @@ msgid "Group tracks by node or display them as plain list." msgstr "Agrupar faixas por nó ou exibi-las como lista simples." #: editor/animation_track_editor.cpp -#, fuzzy msgid "Snap:" -msgstr "Ajustar" +msgstr "Ajustar:" #: editor/animation_track_editor.cpp msgid "Animation step value." @@ -437,7 +441,7 @@ msgstr "Valor passo da Animação." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "Segundos" #: editor/animation_track_editor.cpp msgid "FPS" @@ -2846,7 +2850,7 @@ msgstr "Página: " #: editor/editor_properties_array_dict.cpp msgid "New Key:" -msgstr "Novo Chave:" +msgstr "Nova Chave:" #: editor/editor_properties_array_dict.cpp msgid "New Value:" @@ -4804,20 +4808,19 @@ msgstr "Esquema" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Translation mask for inserting keys." -msgstr "" +msgstr "Máscara de translação para inserir chaves." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Rotation mask for inserting keys." -msgstr "" +msgstr "Máscara de rotação para inserir chaves." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Scale mask for inserting keys." -msgstr "" +msgstr "Máscara de escala para inserir chaves." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Insert keys (based on mask)." -msgstr "Inserir Chave (Pistas existentes)" +msgstr "Inserir chaves (baseado na máscara)." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "" @@ -4826,11 +4829,15 @@ msgid "" "Keys are only added to existing tracks, no new tracks will be created.\n" "Keys must be inserted manually for the first time." msgstr "" +"Insere chaves automaticamente quando objetos são movidos, rodados ou " +"redimensionados (baseado na máscara).\n" +"Chaves apenas são adicionadas a pistas existentes, não sendo criadas novas " +"pistas.\n" +"Chaves têm de ser inseridas manualmente na primeira vez." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Auto Insert Key" -msgstr "Anim Inserir Chave" +msgstr "Inserir Chave automaticamente" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Insert Key (Existing Tracks)" @@ -5816,9 +5823,8 @@ msgid "Save Theme As..." msgstr "Guardar tema como..." #: editor/plugins/script_editor_plugin.cpp -#, fuzzy msgid "%s Class Reference" -msgstr " Referência de classe" +msgstr "Referência de classe %s" #: editor/plugins/script_editor_plugin.cpp msgid "Toggle alphabetical sorting of the method list." @@ -6228,7 +6234,7 @@ msgstr "A rodar %s graus." #: editor/plugins/spatial_editor_plugin.cpp msgid "Keying is disabled (no key inserted)." -msgstr "Edição desativada (nenhuma Chave inserida)." +msgstr "Edição desativada (nenhuma chave inserida)." #: editor/plugins/spatial_editor_plugin.cpp msgid "Animation Key Inserted." @@ -6642,24 +6648,20 @@ msgid "Nameless gizmo" msgstr "Bugiganga sem Nome" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Mesh2D" -msgstr "Criar Malha 2D" +msgstr "Criar Mesh2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Polygon2D" -msgstr "Criar Polygon3D" +msgstr "Criar Polygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D" -msgstr "Criar PolÃgono de Colisão" +msgstr "Criar CollisionPolygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D" -msgstr "Criar PolÃgono oclusor" +msgstr "Criar LightOccluder2D" #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite is empty!" @@ -6674,43 +6676,36 @@ msgid "Invalid geometry, can't replace by mesh." msgstr "Geometria inválida, não substituÃvel por malha." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create polygon." -msgstr "Geometria inválida, não substituÃvel por malha." +msgstr "Geometria inválida, impossÃvel criar polÃgono." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create collision polygon." -msgstr "Geometria inválida, não substituÃvel por malha." +msgstr "Geometria inválida, impossÃvel criar polÃgono de colisão." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create light occluder." -msgstr "Geometria inválida, não substituÃvel por malha." +msgstr "Geometria inválida, impossÃvel criar oclusor de luz." #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite" msgstr "Sprite" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Mesh2D" -msgstr "Converter para Malha 2D" +msgstr "Converter para Mesh2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Polygon2D" -msgstr "Mover PolÃgono" +msgstr "Converter para Polygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D Sibling" -msgstr "Criar PolÃgono de Colisão" +msgstr "Criar irmão de CollisionPolygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D Sibling" -msgstr "Criar PolÃgono oclusor" +msgstr "Criar irmão de LightOccluder2D" #: editor/plugins/sprite_editor_plugin.cpp msgid "Simplification: " @@ -7295,9 +7290,8 @@ msgid "Duplicate Nodes" msgstr "Duplicar Nós" #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Delete Nodes" -msgstr "Apagar Nó" +msgstr "Apagar Nós" #: editor/plugins/visual_shader_editor_plugin.cpp msgid "Visual Shader Input Type Changed" diff --git a/editor/translations/ro.po b/editor/translations/ro.po index dbc222bbbf..96565393c6 100644 --- a/editor/translations/ro.po +++ b/editor/translations/ro.po @@ -163,16 +163,21 @@ msgstr "OpreÈ™te rularea animaÈ›iei. (S)" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "Anim AdăugaÈ›i Pistă" +msgid "Animation length (frames)" +msgstr "Lungime AnimaÈ›ie (în secunde)." #: editor/animation_track_editor.cpp #, fuzzy -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "Lungime AnimaÈ›ie (în secunde)." #: editor/animation_track_editor.cpp #, fuzzy +msgid "Add Track" +msgstr "Anim AdăugaÈ›i Pistă" + +#: editor/animation_track_editor.cpp +#, fuzzy msgid "Animation Looping" msgstr "Zoom AnimaÈ›ie." diff --git a/editor/translations/ru.po b/editor/translations/ru.po index b9794177bb..590b9408fd 100644 --- a/editor/translations/ru.po +++ b/editor/translations/ru.po @@ -43,12 +43,16 @@ # ÐÑ€Ñений Солодков <arsen332211@gmail.com>, 2019. # Nikita <yakrobat@protonmail.com>, 2019. # LAT_Rio <AlSenya@yandex.ru>, 2019. +# devnp <dev.necropan@gmail.com>, 2019. +# Виктор <victor8632@bk.ru>, 2019. +# Mickety <xyngraph@gmail.com>, 2019. +# Breadp4ck <iii103@mail.ru>, 2019. msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-04-14 13:04+0000\n" -"Last-Translator: LAT_Rio <AlSenya@yandex.ru>\n" +"PO-Revision-Date: 2019-05-08 11:48+0000\n" +"Last-Translator: Breadp4ck <iii103@mail.ru>\n" "Language-Team: Russian <https://hosted.weblate.org/projects/godot-engine/" "godot/ru/>\n" "Language: ru\n" @@ -57,7 +61,7 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=3; plural=n%10==1 && n%100!=11 ? 0 : n%10>=2 && n" "%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2;\n" -"X-Generator: Weblate 3.6-dev\n" +"X-Generator: Weblate 3.7-dev\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -194,14 +198,20 @@ msgid "Animation Playback Track" msgstr "Трек ВоÑÐ¿Ñ€Ð¾Ð¸Ð·Ð²ÐµÐ´ÐµÐ½Ð¸Ñ Ðнимации" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Добавить новый Трек" +#, fuzzy +msgid "Animation length (frames)" +msgstr "ПродолжительноÑÑ‚ÑŒ анимации (в Ñекундах)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "ПродолжительноÑÑ‚ÑŒ анимации (в Ñекундах)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Добавить новый Трек" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Зацикливание анимации" @@ -464,7 +474,7 @@ msgstr "Значение шага анимации." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "Секунды" #: editor/animation_track_editor.cpp msgid "FPS" @@ -3673,9 +3683,8 @@ msgstr "Загрузка..." #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp -#, fuzzy msgid "Move Node Point" -msgstr "Передвинуть Точку" +msgstr "Передвинуть узел" #: editor/plugins/animation_blend_space_1d_editor.cpp msgid "Change BlendSpace1D Limits" @@ -4830,34 +4839,43 @@ msgid "Layout" msgstr "Макет" #: editor/plugins/canvas_item_editor_plugin.cpp +#, fuzzy msgid "Translation mask for inserting keys." -msgstr "" +msgstr "МаÑка Ð¿ÐµÑ€ÐµÐ¼ÐµÑ‰ÐµÐ½Ð¸Ñ Ð´Ð»Ñ Ð´Ð¾Ð±Ð°Ð²Ð»Ñемых ключей." #: editor/plugins/canvas_item_editor_plugin.cpp +#, fuzzy msgid "Rotation mask for inserting keys." -msgstr "" +msgstr "МаÑка поворота Ð´Ð»Ñ Ð´Ð¾Ð±Ð°Ð²Ð»Ñемых ключей." #: editor/plugins/canvas_item_editor_plugin.cpp +#, fuzzy msgid "Scale mask for inserting keys." -msgstr "" +msgstr "МаÑка маÑштаба Ð´Ð»Ñ Ð´Ð¾Ð±Ð°Ð²Ð»Ñемых ключей." #: editor/plugins/canvas_item_editor_plugin.cpp #, fuzzy msgid "Insert keys (based on mask)." -msgstr "Ð’Ñтавить ключи (Ins)" +msgstr "Ð’Ñтавить ключи (в завиÑимоÑти от маÑки)" #: editor/plugins/canvas_item_editor_plugin.cpp +#, fuzzy msgid "" "Auto insert keys when objects are translated, rotated on scaled (based on " "mask).\n" "Keys are only added to existing tracks, no new tracks will be created.\n" "Keys must be inserted manually for the first time." msgstr "" +"ÐвтоматичеÑки вÑтавлÑÑ‚ÑŒ ключи когда объекты перемещены, повёрнуты или их " +"размер изменён (завиÑит от маÑки).\n" +"Ключи добавлÑÑŽÑ‚ÑÑ Ñ‚Ð¾Ð»ÑŒÐºÐ¾ в ÑущеÑтвующие дорожки, новые дорожки не будут " +"Ñозданы.\n" +"Первые ключи должны быть добавлены вручную." #: editor/plugins/canvas_item_editor_plugin.cpp #, fuzzy msgid "Auto Insert Key" -msgstr "Ð’Ñтавить ключ" +msgstr "ÐвтоматичеÑки вÑтавлÑÑ‚ÑŒ ключ" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Insert Key (Existing Tracks)" @@ -5846,7 +5864,7 @@ msgstr "Сохранить тему как..." #: editor/plugins/script_editor_plugin.cpp #, fuzzy msgid "%s Class Reference" -msgstr " СÑылка на КлаÑÑ" +msgstr "%s Справка по клаÑÑу" #: editor/plugins/script_editor_plugin.cpp msgid "Toggle alphabetical sorting of the method list." @@ -6671,9 +6689,8 @@ msgid "Post" msgstr "ПоÑле" #: editor/plugins/spatial_editor_plugin.cpp -#, fuzzy msgid "Nameless gizmo" -msgstr "БезымÑнный гизмо" +msgstr "БезымÑÐ½Ð½Ð°Ñ ÑˆÑ‚ÑƒÐºÐ¾Ð²Ð¸Ð½Ð°" #: editor/plugins/sprite_editor_plugin.cpp #, fuzzy @@ -6709,14 +6726,13 @@ msgid "Invalid geometry, can't replace by mesh." msgstr "ÐÐµÐºÐ¾Ñ€Ñ€ÐµÐºÑ‚Ð½Ð°Ñ Ð³ÐµÐ¾Ð¼ÐµÑ‚Ñ€Ð¸Ñ, не может быть заменена Ñеткой." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create polygon." -msgstr "ÐÐµÐºÐ¾Ñ€Ñ€ÐµÐºÑ‚Ð½Ð°Ñ Ð³ÐµÐ¾Ð¼ÐµÑ‚Ñ€Ð¸Ñ, не может быть заменена Ñеткой." +msgstr "ÐÐµÐºÐ¾Ñ€Ñ€ÐµÐºÑ‚Ð½Ð°Ñ Ð³ÐµÐ¾Ð¼ÐµÑ‚Ñ€Ð¸Ñ, Ð½ÐµÐ»ÑŒÐ·Ñ Ñоздать полигональную Ñетку." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create collision polygon." -msgstr "ÐÐµÐºÐ¾Ñ€Ñ€ÐµÐºÑ‚Ð½Ð°Ñ Ð³ÐµÐ¾Ð¼ÐµÑ‚Ñ€Ð¸Ñ, не может быть заменена Ñеткой." +msgstr "" +"ÐÐµÐºÐ¾Ñ€Ñ€ÐµÐºÑ‚Ð½Ð°Ñ Ð³ÐµÐ¾Ð¼ÐµÑ‚Ñ€Ð¸Ñ, Ð½ÐµÐ»ÑŒÐ·Ñ Ñоздать полигональную Ñетку Ñтолкновений." #: editor/plugins/sprite_editor_plugin.cpp #, fuzzy @@ -6733,9 +6749,8 @@ msgid "Convert to Mesh2D" msgstr "Преобразовать в 2D Mesh" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Polygon2D" -msgstr "Передвинуть полигон" +msgstr "Преобразовать в Polygon2D" #: editor/plugins/sprite_editor_plugin.cpp #, fuzzy @@ -7331,9 +7346,8 @@ msgid "Duplicate Nodes" msgstr "Дублировать узлы" #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Delete Nodes" -msgstr "Удалить узел" +msgstr "Удалить узлы" #: editor/plugins/visual_shader_editor_plugin.cpp msgid "Visual Shader Input Type Changed" @@ -8885,7 +8899,7 @@ msgstr "Видео памÑÑ‚ÑŒ" #: editor/script_editor_debugger.cpp msgid "Resource Path" -msgstr "Путь реÑурÑа" +msgstr "Путь к реÑурÑу" #: editor/script_editor_debugger.cpp msgid "Type" @@ -9525,9 +9539,8 @@ msgid "Change Input Value" msgstr "Изменить входное значение" #: modules/visual_script/visual_script_editor.cpp -#, fuzzy msgid "Resize Comment" -msgstr "Изменить размер CanvasItem" +msgstr "Изменить размер комментариÑ" #: modules/visual_script/visual_script_editor.cpp msgid "Can't copy the function node." @@ -10341,9 +10354,8 @@ msgid "Please Confirm..." msgstr "Подтверждение..." #: scene/gui/file_dialog.cpp -#, fuzzy msgid "Go to parent folder." -msgstr "Перейти к родительÑкой папке" +msgstr "Перейти к родительÑкой папке." #: scene/gui/popup.cpp msgid "" diff --git a/editor/translations/si.po b/editor/translations/si.po index 581ab36ee0..943dcad6b8 100644 --- a/editor/translations/si.po +++ b/editor/translations/si.po @@ -153,14 +153,20 @@ msgid "Animation Playback Track" msgstr "සජීවීකරණ ධà·à·€à¶±à¶º ලුහුබදින්න" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "ලුහුබදින්නෙක් එක් කරන්න" +#, fuzzy +msgid "Animation length (frames)" +msgstr "සජීවීකරණ කà·à¶½à¶º (à¶à¶´à·Šà¶´à¶»)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "සජීවීකරණ කà·à¶½à¶º (à¶à¶´à·Šà¶´à¶»)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "ලුහුබදින්නෙක් එක් කරන්න" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "සජීවීකරණ පුනරà·à·€à¶»à·Šà¶®à¶±à¶º" diff --git a/editor/translations/sk.po b/editor/translations/sk.po index 862f095dd3..5606781122 100644 --- a/editor/translations/sk.po +++ b/editor/translations/sk.po @@ -158,14 +158,20 @@ msgid "Animation Playback Track" msgstr "" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Dĺžka ÄŒasu Animácie (v sekundách)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Dĺžka ÄŒasu Animácie (v sekundách)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "" diff --git a/editor/translations/sl.po b/editor/translations/sl.po index 23d7e5ebee..c7422f7535 100644 --- a/editor/translations/sl.po +++ b/editor/translations/sl.po @@ -8,12 +8,13 @@ # Simon Å ander <simon.sand3r@gmail.com>, 2017. # Yahara Octanis <yaharao55@gmail.com>, 2018. # Tine Jozelj <tine@tjo.space>, 2018. +# Andrej Poženel <andrej.pozenel@outlook.com>, 2019. msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2018-12-13 14:43+0100\n" -"Last-Translator: Tine Jozelj <tine@tjo.space>\n" +"PO-Revision-Date: 2019-05-16 18:49+0000\n" +"Last-Translator: Andrej Poženel <andrej.pozenel@outlook.com>\n" "Language-Team: Slovenian <https://hosted.weblate.org/projects/godot-engine/" "godot/sl/>\n" "Language: sl\n" @@ -22,26 +23,27 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=4; plural=n%100==1 ? 0 : n%100==2 ? 1 : n%100==3 || n" "%100==4 ? 2 : 3;\n" -"X-Generator: Poedit 2.2\n" +"X-Generator: Weblate 3.7-dev\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp msgid "Invalid type argument to convert(), use TYPE_* constants." -msgstr "Neveljavena vrsta argumenta za convert(), uporabite TYPE_* konstanto." +msgstr "Neveljavna vrsta argumenta za convert(), uporabite TYPE_* konstanto." #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/mono/glue/gd_glue.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp msgid "Not enough bytes for decoding bytes, or invalid format." -msgstr "Ni dovolj pomnilnika za dekodiranje bajtov, ali neveljaven format." +msgstr "" +"Ni dovolj pomnilnika za dekodiranje bajtov, ali pa je neveljaven format." #: core/math/expression.cpp msgid "Invalid input %i (not passed) in expression" -msgstr "" +msgstr "NapaÄen vnos %i(ni podan) v izrazu" #: core/math/expression.cpp msgid "self can't be used because instance is null (not passed)" -msgstr "self nemore biti uporabljen, ker instanca ni null (ni podano)" +msgstr "self ne more biti uporabljen, ker instanca ni null (ni podano)" #: core/math/expression.cpp #, fuzzy @@ -166,16 +168,21 @@ msgstr "Ustavi predvajanje animacije. (S)" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "Animacija Dodaj sled" +msgid "Animation length (frames)" +msgstr "Dolžina animacije (v sekundah)." #: editor/animation_track_editor.cpp #, fuzzy -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "Dolžina animacije (v sekundah)." #: editor/animation_track_editor.cpp #, fuzzy +msgid "Add Track" +msgstr "Animacija Dodaj sled" + +#: editor/animation_track_editor.cpp +#, fuzzy msgid "Animation Looping" msgstr "Približaj animacijo." diff --git a/editor/translations/sq.po b/editor/translations/sq.po index d52ebdcd96..fe29b8779d 100644 --- a/editor/translations/sq.po +++ b/editor/translations/sq.po @@ -154,14 +154,20 @@ msgid "Animation Playback Track" msgstr "Binari i Rishikimit të Animacionit" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Shto Binarë" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Kohëzgjatja e Animacionit (sekonda)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Kohëzgjatja e Animacionit (sekonda)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Shto Binarë" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Përsëritje Animacioni" diff --git a/editor/translations/sr_Cyrl.po b/editor/translations/sr_Cyrl.po index 57e05ca847..f9a7ce452f 100644 --- a/editor/translations/sr_Cyrl.po +++ b/editor/translations/sr_Cyrl.po @@ -165,16 +165,21 @@ msgstr "ЗауÑтави анимацију. (S)" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "Додај нову траку" +msgid "Animation length (frames)" +msgstr "Дужина анимације (у Ñекундама)." #: editor/animation_track_editor.cpp #, fuzzy -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "Дужина анимације (у Ñекундама)." #: editor/animation_track_editor.cpp #, fuzzy +msgid "Add Track" +msgstr "Додај нову траку" + +#: editor/animation_track_editor.cpp +#, fuzzy msgid "Animation Looping" msgstr "Скала анимације." diff --git a/editor/translations/sr_Latn.po b/editor/translations/sr_Latn.po index ac3590e494..3f92101118 100644 --- a/editor/translations/sr_Latn.po +++ b/editor/translations/sr_Latn.po @@ -159,12 +159,18 @@ msgstr "" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "Animacija Dodaj Kanal" +msgid "Animation length (frames)" +msgstr "Optimizuj Animaciju" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" -msgstr "" +#, fuzzy +msgid "Animation length (seconds)" +msgstr "Promijeni Dužinu Animacije" + +#: editor/animation_track_editor.cpp +#, fuzzy +msgid "Add Track" +msgstr "Animacija Dodaj Kanal" #: editor/animation_track_editor.cpp msgid "Animation Looping" diff --git a/editor/translations/sv.po b/editor/translations/sv.po index 63a6d6e6c7..2f08a32697 100644 --- a/editor/translations/sv.po +++ b/editor/translations/sv.po @@ -161,15 +161,20 @@ msgstr "" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "Anim Lägg till spÃ¥r" +msgid "Animation length (frames)" +msgstr "Animation längd (i sekunder)." #: editor/animation_track_editor.cpp #, fuzzy -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "Animation längd (i sekunder)." #: editor/animation_track_editor.cpp +#, fuzzy +msgid "Add Track" +msgstr "Anim Lägg till spÃ¥r" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Animationslooping" diff --git a/editor/translations/ta.po b/editor/translations/ta.po index 17e837d5b1..ee708bff60 100644 --- a/editor/translations/ta.po +++ b/editor/translations/ta.po @@ -157,15 +157,19 @@ msgid "Animation Playback Track" msgstr "" #: editor/animation_track_editor.cpp -#, fuzzy -msgid "Add Track" -msgstr "அசைவூடà¯à®Ÿà¯ பாதை சேரà¯" +msgid "Animation length (frames)" +msgstr "" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "" #: editor/animation_track_editor.cpp +#, fuzzy +msgid "Add Track" +msgstr "அசைவூடà¯à®Ÿà¯ பாதை சேரà¯" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "" diff --git a/editor/translations/te.po b/editor/translations/te.po index b5f7015c88..f43e4c486f 100644 --- a/editor/translations/te.po +++ b/editor/translations/te.po @@ -152,11 +152,15 @@ msgid "Animation Playback Track" msgstr "" #: editor/animation_track_editor.cpp -msgid "Add Track" +msgid "Animation length (frames)" msgstr "" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Add Track" msgstr "" #: editor/animation_track_editor.cpp diff --git a/editor/translations/th.po b/editor/translations/th.po index 5b1470e970..9624447da3 100644 --- a/editor/translations/th.po +++ b/editor/translations/th.po @@ -169,16 +169,21 @@ msgstr "หยุดà¸à¸²à¸£à¹€à¸¥à¹ˆà¸™à¹à¸à¸™à¸´à¹€à¸¡à¸Šà¸±à¸™ (S)" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "เพิ่มà¹à¸—ร็à¸à¹à¸à¸™à¸´à¹€à¸¡à¸Šà¸±à¸™" +msgid "Animation length (frames)" +msgstr "ความยาวà¹à¸à¸™à¸´à¹€à¸¡à¸Šà¸±à¸™ (วินาที)" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "ความยาวà¹à¸à¸™à¸´à¹€à¸¡à¸Šà¸±à¸™ (วินาที)" #: editor/animation_track_editor.cpp #, fuzzy +msgid "Add Track" +msgstr "เพิ่มà¹à¸—ร็à¸à¹à¸à¸™à¸´à¹€à¸¡à¸Šà¸±à¸™" + +#: editor/animation_track_editor.cpp +#, fuzzy msgid "Animation Looping" msgstr "ซูมà¹à¸à¸™à¸´à¹€à¸¡à¸Šà¸±à¸™" diff --git a/editor/translations/tr.po b/editor/translations/tr.po index 30f753d6ab..9622fda90a 100644 --- a/editor/translations/tr.po +++ b/editor/translations/tr.po @@ -25,12 +25,13 @@ # Mertcan Duman <mertcan.dmn16@gmail.com>, 2019. # Furkan Türkal <furkan.turkal@hotmail.com>, 2019. # Aiden Demir <dnm00110011@hotmail.com>, 2019. +# Anton Semchenko <semchenkoanton@protonmail.com>, 2019. msgid "" msgstr "" "Project-Id-Version: Godot Engine editor\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-04-14 13:04+0000\n" -"Last-Translator: Aiden Demir <dnm00110011@hotmail.com>\n" +"PO-Revision-Date: 2019-05-10 08:19+0000\n" +"Last-Translator: Anton Semchenko <semchenkoanton@protonmail.com>\n" "Language-Team: Turkish <https://hosted.weblate.org/projects/godot-engine/" "godot/tr/>\n" "Language: tr\n" @@ -38,23 +39,22 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=n != 1;\n" -"X-Generator: Weblate 3.6-dev\n" +"X-Generator: Weblate 3.7-dev\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp msgid "Invalid type argument to convert(), use TYPE_* constants." -msgstr "" -"convert() için geçersiz türde deÄŸiÅŸtirgen, TYPE_* sabitlerini kullanın." +msgstr "convert() için geçersiz argüman tipi, TYPE_* sabitlerini kullanın." #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/mono/glue/gd_glue.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp msgid "Not enough bytes for decoding bytes, or invalid format." -msgstr "Byte kodu çözmek için yetersiz byte, ya da Geçersiz format." +msgstr "Byte kodu çözmek için yetersiz byte, ya da geçersiz format." #: core/math/expression.cpp msgid "Invalid input %i (not passed) in expression" -msgstr "%i ifadesindeki girdi geçersiz" +msgstr "Ä°fade de geçersiz girdi %i (geçmedi)." #: core/math/expression.cpp msgid "self can't be used because instance is null (not passed)" @@ -67,22 +67,23 @@ msgstr "Geçersiz iÅŸlenen operatörler %s, %s ve %s" #: core/math/expression.cpp msgid "Invalid index of type %s for base type %s" -msgstr "%s temel tipi için, %s tipinde geçersiz index." +msgstr "%s temel tipi için, %s tipinde geçersiz indeks" #: core/math/expression.cpp msgid "Invalid named index '%s' for base type %s" -msgstr "%s temel tipi için, geçersiz isimlendirilmiÅŸ index %s" +msgstr "%s temel tipi için, geçersiz isimlendirilmiÅŸ indeks '%s'" #: core/math/expression.cpp msgid "Invalid arguments to construct '%s'" -msgstr "'%s' oluÅŸturulurken geçersiz argümanlar atandı." +msgstr "'%s' oluÅŸturulurken geçersiz argümanlar atandı" #: core/math/expression.cpp msgid "On call to '%s':" -msgstr "'%s': çaÄŸrıldığında." +msgstr "'%s' çaÄŸrıldığında:" #: editor/animation_bezier_editor.cpp #: editor/plugins/asset_library_editor_plugin.cpp +#, fuzzy msgid "Free" msgstr "Ãœcretsiz" @@ -177,14 +178,20 @@ msgid "Animation Playback Track" msgstr "Animasyon Oynatıcı Ä°zi" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Ä°z Ekle" +#, fuzzy +msgid "Animation length (frames)" +msgstr "Animasyon UzunluÄŸu (saniye)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "Animasyon UzunluÄŸu (saniye)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Ä°z Ekle" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "Animasyon Döngüsü" @@ -276,9 +283,8 @@ msgid "Insert Key" msgstr "Anahtar Gir" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Duplicate Key(s)" -msgstr "Düğüm(leri) ÇoÄŸalt" +msgstr "Anahtar(lar)ı ÇoÄŸalt" #: editor/animation_track_editor.cpp msgid "Delete Key(s)" @@ -439,9 +445,8 @@ msgid "Group tracks by node or display them as plain list." msgstr "Ä°zleri düğüme göre grupla veya onları düz liste olarak göster." #: editor/animation_track_editor.cpp -#, fuzzy msgid "Snap:" -msgstr "Yapış" +msgstr "Yapıştır:" #: editor/animation_track_editor.cpp msgid "Animation step value." @@ -449,7 +454,7 @@ msgstr "Animasyon adım deÄŸeri." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "Saniye" #: editor/animation_track_editor.cpp msgid "FPS" @@ -1214,7 +1219,7 @@ msgstr "Bus ekle" #: editor/editor_audio_buses.cpp msgid "Add a new Audio Bus to this layout." -msgstr "" +msgstr "Bu yerleÅŸim planına yeni ses veri yolu ekle." #: editor/editor_audio_buses.cpp editor/editor_properties.cpp #: editor/plugins/animation_player_editor_plugin.cpp editor/property_editor.cpp @@ -1383,28 +1388,26 @@ msgstr "Dosya Depolama:" #: editor/editor_export.cpp msgid "No export template found at the expected path:" -msgstr "" +msgstr "Beklenen adreste dışa aktarım ÅŸablonu bulunamadı:" #: editor/editor_export.cpp msgid "Packing" msgstr "Çıkınla" #: editor/editor_export.cpp -#, fuzzy msgid "" "Target platform requires 'ETC' texture compression for GLES2. Enable 'Import " "Etc' in Project Settings." msgstr "" -"Hedef platform GLES2 için 'ETC' doku sıkıştırma gerektirir. Proje " +"Hedef platform GLES2 için 'ETC' doku sıkıştırma gerekiyor. Proje " "Ayarları'nda 'Import Etc' etkinleÅŸtirin." #: editor/editor_export.cpp -#, fuzzy msgid "" "Target platform requires 'ETC2' texture compression for GLES3. Enable " "'Import Etc 2' in Project Settings." msgstr "" -"Hedef platform GLES3 için 'ETC2' doku sıkıştırma gerektirir. Proje " +"Hedef platform GLES3 için 'ETC2' doku sıkıştırma gerekiyor. Proje " "Ayarları'nda 'Import Etc 2' etkinleÅŸtirin." #: editor/editor_export.cpp @@ -1418,16 +1421,14 @@ msgstr "" #: editor/editor_export.cpp platform/android/export/export.cpp #: platform/iphone/export/export.cpp platform/javascript/export/export.cpp #: platform/osx/export/export.cpp platform/uwp/export/export.cpp -#, fuzzy msgid "Custom debug template not found." -msgstr "Özel kusur ayıklama çıkını bulunmadı." +msgstr "Özel hata ayıklama ÅŸablonu bulunmadı." #: editor/editor_export.cpp platform/android/export/export.cpp #: platform/iphone/export/export.cpp platform/javascript/export/export.cpp #: platform/osx/export/export.cpp platform/uwp/export/export.cpp -#, fuzzy msgid "Custom release template not found." -msgstr "Özel yayınlama çıkını bulunamadı." +msgstr "Özel yayınlama ÅŸablonu bulunamadı." #: editor/editor_export.cpp platform/javascript/export/export.cpp msgid "Template file not found:" @@ -1541,23 +1542,20 @@ msgid "Move Favorite Down" msgstr "BeÄŸenileni AÅŸağı Taşı" #: editor/editor_file_dialog.cpp -#, fuzzy msgid "Previous Folder" -msgstr "Önceki Zemin" +msgstr "Önceki Klasör" #: editor/editor_file_dialog.cpp -#, fuzzy msgid "Next Folder" -msgstr "Sonraki Zemin" +msgstr "Sonraki Klasör" #: editor/editor_file_dialog.cpp msgid "Go to parent folder" msgstr "Ãœst klasöre git" #: editor/editor_file_dialog.cpp -#, fuzzy msgid "(Un)favorite current folder." -msgstr "Klasör oluÅŸturulamadı." +msgstr "Bu klasörü favorilerden çıkar/favorilere ekle." #: editor/editor_file_dialog.cpp editor/filesystem_dock.cpp #, fuzzy @@ -1565,9 +1563,8 @@ msgid "View items as a grid of thumbnails." msgstr "Öğeleri küçük resim ızgarası ÅŸeklinde göster" #: editor/editor_file_dialog.cpp editor/filesystem_dock.cpp -#, fuzzy msgid "View items as a list." -msgstr "Öğeleri liste olarak göster" +msgstr "Öğeleri liste olarak göster." #: editor/editor_file_dialog.cpp scene/gui/file_dialog.cpp msgid "Directories & Files:" @@ -1627,19 +1624,16 @@ msgid "Methods" msgstr "Metotlar" #: editor/editor_help.cpp -#, fuzzy msgid "Methods:" -msgstr "Metotlar" +msgstr "Metotlar:" #: editor/editor_help.cpp -#, fuzzy msgid "Theme Properties" -msgstr "Özellikler" +msgstr "Tema Özellikleri" #: editor/editor_help.cpp -#, fuzzy msgid "Theme Properties:" -msgstr "Özellikler:" +msgstr "Tema Özellikleri:" #: editor/editor_help.cpp modules/visual_script/visual_script_editor.cpp msgid "Signals:" @@ -1666,14 +1660,12 @@ msgid "Constants:" msgstr "Sabitler:" #: editor/editor_help.cpp -#, fuzzy msgid "Class Description" -msgstr "Açıklama" +msgstr "Sınıf Açıklaması" #: editor/editor_help.cpp -#, fuzzy msgid "Class Description:" -msgstr "Açıklama:" +msgstr "Sınıf Açıklaması:" #: editor/editor_help.cpp msgid "Online Tutorials:" @@ -1690,14 +1682,12 @@ msgstr "" "[color=$color][url=$url2]öneride bulunabilirsiniz[/url][/color]." #: editor/editor_help.cpp -#, fuzzy msgid "Property Descriptions" -msgstr "Özellik Açıklaması:" +msgstr "Özellik Açıklamaları" #: editor/editor_help.cpp -#, fuzzy msgid "Property Descriptions:" -msgstr "Özellik Açıklaması:" +msgstr "Özellik Açıklamaları:" #: editor/editor_help.cpp msgid "" @@ -1708,14 +1698,12 @@ msgstr "" "bulunarak[/url][/color] yardım edebilirsiniz!" #: editor/editor_help.cpp -#, fuzzy msgid "Method Descriptions" -msgstr "Metot Açıklaması:" +msgstr "Metot Açıklamaları" #: editor/editor_help.cpp -#, fuzzy msgid "Method Descriptions:" -msgstr "Metot Açıklaması:" +msgstr "Metot Açıklamaları:" #: editor/editor_help.cpp msgid "" @@ -1731,49 +1719,40 @@ msgid "Search Help" msgstr "Yardım Ara" #: editor/editor_help_search.cpp -#, fuzzy msgid "Display All" -msgstr "OlaÄŸanı Görüntüle" +msgstr "Hepsini Görüntüle" #: editor/editor_help_search.cpp -#, fuzzy msgid "Classes Only" -msgstr "Sınıflar" +msgstr "Sadece Sınıflar" #: editor/editor_help_search.cpp -#, fuzzy msgid "Methods Only" -msgstr "Metotlar" +msgstr "Sadece Metotlar" #: editor/editor_help_search.cpp -#, fuzzy msgid "Signals Only" -msgstr "Sinyaller" +msgstr "Sadece Sinyaller" #: editor/editor_help_search.cpp -#, fuzzy msgid "Constants Only" -msgstr "Sabitler" +msgstr "Sadece Sabitler" #: editor/editor_help_search.cpp -#, fuzzy msgid "Properties Only" -msgstr "Özellikler" +msgstr "Sadece Özellikler" #: editor/editor_help_search.cpp -#, fuzzy msgid "Theme Properties Only" -msgstr "Özellikler" +msgstr "Sadece Tema Özellikleri" #: editor/editor_help_search.cpp -#, fuzzy msgid "Member Type" -msgstr "Ãœyeler" +msgstr "Ãœye Tipi" #: editor/editor_help_search.cpp -#, fuzzy msgid "Class" -msgstr "Sınıf:" +msgstr "Sınıf" #: editor/editor_inspector.cpp editor/project_settings_editor.cpp msgid "Property:" @@ -1785,7 +1764,7 @@ msgstr "Ayarla" #: editor/editor_inspector.cpp msgid "Set Multiple:" -msgstr "" +msgstr "Çoklu Ayarla:" #: editor/editor_log.cpp msgid "Output:" @@ -1811,7 +1790,7 @@ msgstr "Proje dışa aktarımı %d hata koduyla baÅŸarısız." #: editor/editor_node.cpp msgid "Imported resources can't be saved." -msgstr "" +msgstr "İçe aktarılmış kaynaklar kaydedilemez." #: editor/editor_node.cpp editor/plugins/script_editor_plugin.cpp #: scene/gui/dialogs.cpp @@ -1823,10 +1802,13 @@ msgid "Error saving resource!" msgstr "Kaynak kaydedilirken hata!" #: editor/editor_node.cpp +#, fuzzy msgid "" "This resource can't be saved because it does not belong to the edited scene. " "Make it unique first." msgstr "" +"Bu kaynak düzenlenen sahneye ait olmadığı için kaydedilemez. Önce benzersiz " +"hale getir." #: editor/editor_node.cpp editor/plugins/animation_player_editor_plugin.cpp msgid "Save Resource As..." @@ -1846,7 +1828,7 @@ msgstr "Kaydedilirken hata oluÅŸtu." #: editor/editor_node.cpp editor/plugins/script_editor_plugin.cpp msgid "Can't open '%s'. The file could have been moved or deleted." -msgstr "" +msgstr "'%s' açılamıyor. Dosya taşınmış ya da silinmiÅŸ olabilir." #: editor/editor_node.cpp msgid "Error while parsing '%s'." @@ -1885,6 +1867,8 @@ msgid "" "This scene can't be saved because there is a cyclic instancing inclusion.\n" "Please resolve it and then attempt to save again." msgstr "" +"Sahne döngüsel örnekleme bulundurduÄŸu için kaydedilemiyor.\n" +"Lütfen bunu düzeltin ve bir daha kaydetmeyi deneyin." #: editor/editor_node.cpp msgid "" @@ -1896,7 +1880,7 @@ msgstr "" #: editor/editor_node.cpp editor/scene_tree_dock.cpp msgid "Can't overwrite scene that is still open!" -msgstr "" +msgstr "Açık olan sahnenin üzerine yazılamıyor!" #: editor/editor_node.cpp msgid "Can't load MeshLibrary for merging!" @@ -2047,14 +2031,12 @@ msgid "Save changes to '%s' before closing?" msgstr "Kapatmadan önce deÄŸiÅŸklikler buraya '%s' kaydedilsin mi?" #: editor/editor_node.cpp -#, fuzzy msgid "Saved %s modified resource(s)." -msgstr "Kaynak yükleme baÅŸarısız oldu." +msgstr "'%s' deÄŸiÅŸtirilmiÅŸ kaynak kaydedildi." #: editor/editor_node.cpp -#, fuzzy msgid "A root node is required to save the scene." -msgstr "Büyük doku için yalnızca bir dizeç gereklidir." +msgstr "Sahneyi kaydedilmesi için kök düğüm gerekiyor." #: editor/editor_node.cpp msgid "Save Scene As..." @@ -2165,11 +2147,12 @@ msgid "Unable to load addon script from path: '%s'." msgstr "Yoldaki eklenti betiÄŸi yüklenemedi: '%s'." #: editor/editor_node.cpp -#, fuzzy msgid "" "Unable to load addon script from path: '%s' There seems to be an error in " "the code, please check the syntax." -msgstr "Eklenti betiÄŸi '%s' yolundan yüklenemedi. Betik araç modunda deÄŸil." +msgstr "" +"'%s' adresindeki eklenti betik yüklenemiyor. Kodun içinde bir hata var gibi " +"görünüyor, lütfen sözdizimini kontrol edin." #: editor/editor_node.cpp msgid "" @@ -2225,14 +2208,12 @@ msgid "Show in FileSystem" msgstr "Dosya Sisteminde Göster" #: editor/editor_node.cpp -#, fuzzy msgid "Play This Scene" -msgstr "Sahneyi Oynat" +msgstr "Bu Sahneyi Oynat" #: editor/editor_node.cpp -#, fuzzy msgid "Close Tab" -msgstr "DiÄŸer Sekmeleri Kapat" +msgstr "Sekmeyi Kapat" #: editor/editor_node.cpp msgid "Switch Scene Tab" @@ -2307,7 +2288,6 @@ msgid "Save Scene" msgstr "Sahne Kaydet" #: editor/editor_node.cpp -#, fuzzy msgid "Save All Scenes" msgstr "Tüm Sahneleri Kaydet" @@ -2366,9 +2346,8 @@ msgid "Tools" msgstr "Araçlar" #: editor/editor_node.cpp -#, fuzzy msgid "Open Project Data Folder" -msgstr "Proje Yöneticisi Açılsın mı?" +msgstr "Proje Verileri Klasörünü Aç" #: editor/editor_node.cpp msgid "Quit to Project List" @@ -2483,18 +2462,16 @@ msgid "Toggle Fullscreen" msgstr "Tam Ekran Aç / Kapat" #: editor/editor_node.cpp -#, fuzzy msgid "Open Editor Data/Settings Folder" -msgstr "Düzenleyici Ayarları" +msgstr "Düzenleyici Verileri/Ayarları Klasörünü Aç" #: editor/editor_node.cpp msgid "Open Editor Data Folder" -msgstr "" +msgstr "Düzenleyici Verileri Klasörünü Aç" #: editor/editor_node.cpp -#, fuzzy msgid "Open Editor Settings Folder" -msgstr "Düzenleyici Ayarları" +msgstr "Düzenleyici Ayarları Klasörünü Aç" #: editor/editor_node.cpp editor/project_export.cpp msgid "Manage Export Templates" @@ -2575,12 +2552,12 @@ msgstr "Özel Sahneyi Oynat" #: editor/editor_node.cpp msgid "Changing the video driver requires restarting the editor." msgstr "" +"Görüntü sürücüsünü deÄŸiÅŸtirmek için editörün yeniden baÅŸlatılması gerekiyor." #: editor/editor_node.cpp editor/project_settings_editor.cpp #: editor/settings_config_dialog.cpp -#, fuzzy msgid "Save & Restart" -msgstr "Kaydet & Yeniden İçe Aktar" +msgstr "Kaydet ve BaÅŸtan BaÅŸlat" #: editor/editor_node.cpp #, fuzzy @@ -2617,9 +2594,8 @@ msgid "Node" msgstr "Düğüm" #: editor/editor_node.cpp -#, fuzzy msgid "Expand Bottom Panel" -msgstr "Hepsini geniÅŸlet" +msgstr "Alt Panoyu GeniÅŸlet" #: editor/editor_node.cpp scene/resources/visual_shader.cpp msgid "Output" @@ -2698,9 +2674,8 @@ msgid "Thumbnail..." msgstr "Küçük Resim..." #: editor/editor_plugin_settings.cpp -#, fuzzy msgid "Edit Plugin" -msgstr "Çokluyu Düzenleyin" +msgstr "Eklentiyi Düzenle" #: editor/editor_plugin_settings.cpp msgid "Installed Plugins:" @@ -2724,15 +2699,13 @@ msgid "Status:" msgstr "Durum:" #: editor/editor_plugin_settings.cpp -#, fuzzy msgid "Edit:" -msgstr "Düzenle" +msgstr "Düzenle:" #: editor/editor_profiler.cpp editor/plugins/animation_state_machine_editor.cpp #: editor/rename_dialog.cpp -#, fuzzy msgid "Start" -msgstr "BaÅŸlat!" +msgstr "BaÅŸlat" #: editor/editor_profiler.cpp msgid "Measure:" @@ -2784,7 +2757,7 @@ msgstr "Açık" #: editor/editor_properties.cpp msgid "Layer" -msgstr "" +msgstr "Katman" #: editor/editor_properties.cpp #, fuzzy @@ -2810,20 +2783,31 @@ msgid "" "The selected resource (%s) does not match any type expected for this " "property (%s)." msgstr "" +"Seçili kaynak (%s) bu özellik (%s) için beklenen herhangi bir tip ile " +"uyuÅŸmuyor." #: editor/editor_properties.cpp +#, fuzzy msgid "" "Can't create a ViewportTexture on resources saved as a file.\n" "Resource needs to belong to a scene." msgstr "" +"Dosya ÅŸeklinde kaydedilmiÅŸ kaynakların üzerine ViewportTexture " +"oluÅŸturulamıyor.\n" +"Kaynak bir sahneye ait olmalı." #: editor/editor_properties.cpp +#, fuzzy msgid "" "Can't create a ViewportTexture on this resource because it's not set as " "local to scene.\n" "Please switch on the 'local to scene' property on it (and all resources " "containing it up to a node)." msgstr "" +"Bu kaynak üzerine ViewportTexture oluÅŸturulamıyor çünkü bu kaynak 'local to " +"scene' olarak ayarlanmadı.\n" +"Lütfen bu kaynak (ve bir düğüme kadarki bütün kaynakların) üzerindeki 'local " +"to scene' özelliÄŸini açın." #: editor/editor_properties.cpp editor/property_editor.cpp msgid "Pick a Viewport" @@ -2878,7 +2862,7 @@ msgstr "Odacık Boyutu:" #: editor/editor_properties_array_dict.cpp msgid "Page: " -msgstr "" +msgstr "Sayfa: " #: editor/editor_properties_array_dict.cpp #, fuzzy @@ -2892,7 +2876,7 @@ msgstr "Yeni ad:" #: editor/editor_properties_array_dict.cpp msgid "Add Key/Value Pair" -msgstr "" +msgstr "Anahtar/DeÄŸer Ä°kilisini Ekle" #: editor/editor_properties_array_dict.cpp #: editor/plugins/theme_editor_plugin.cpp @@ -3052,6 +3036,8 @@ msgid "" "Templates installation failed. The problematic templates archives can be " "found at '%s'." msgstr "" +"Åžablon yüklemesi baÅŸarısız oldu. Sorunlu ÅŸablon arÅŸivi ÅŸurada bulunabilir: " +"'%s'." #: editor/export_template_manager.cpp msgid "Error requesting url: " @@ -3370,42 +3356,36 @@ msgid "Replace all (no undo)" msgstr "Tümünü DeÄŸiÅŸtir" #: editor/find_in_files.cpp -#, fuzzy msgid "Searching..." -msgstr "Kaydediliyor..." +msgstr "Aranıyor..." #: editor/find_in_files.cpp -#, fuzzy msgid "Search complete" -msgstr "Yazı Ara" +msgstr "Arama tamamlandı" #: editor/groups_editor.cpp -#, fuzzy msgid "Group name already exists." -msgstr "HATA: Bu animasyon adı zaten var!" +msgstr "Grup adı zaten var." #: editor/groups_editor.cpp -#, fuzzy msgid "Invalid group name." -msgstr "Geçersiz ad." +msgstr "Geçersiz grup adı." #: editor/groups_editor.cpp editor/node_dock.cpp msgid "Groups" msgstr "Gruplar" #: editor/groups_editor.cpp -#, fuzzy msgid "Nodes not in Group" -msgstr "ÖbeÄŸe Ekle" +msgstr "Düğümler Grupta DeÄŸil" #: editor/groups_editor.cpp editor/scene_tree_dock.cpp msgid "Filter nodes" msgstr "Düğümleri Süzgeçden Geçir" #: editor/groups_editor.cpp -#, fuzzy msgid "Nodes in Group" -msgstr "Öbekleri Düzenle" +msgstr "Gruptaki Düğümler" #: editor/groups_editor.cpp msgid "Add to Group" @@ -3416,9 +3396,8 @@ msgid "Remove from Group" msgstr "Öbekten Kaldır" #: editor/groups_editor.cpp -#, fuzzy msgid "Manage Groups" -msgstr "Bediz Öbekleri" +msgstr "Grupları Düzenle" #: editor/import/resource_importer_scene.cpp msgid "Import as Single Scene" @@ -3525,30 +3504,31 @@ msgstr "Yeniden İçe Aktar" #: editor/import_dock.cpp msgid "Save scenes, re-import and restart" -msgstr "" +msgstr "Sahneleri kaydet, tekrar içe aktar ve baÅŸtan baÅŸlat" #: editor/import_dock.cpp msgid "Changing the type of an imported file requires editor restart." msgstr "" +"İçe aktarılmış dosyanın tipini deÄŸiÅŸtirmek editörü baÅŸtan baÅŸlatılmasını " +"gerektiriyor." #: editor/import_dock.cpp +#, fuzzy msgid "" "WARNING: Assets exist that use this resource, they may stop loading properly." -msgstr "" +msgstr "UYARI: Bu kaynağı kullanan varlıklar mevcut, doÄŸru yüklenemeyebililer." #: editor/inspector_dock.cpp msgid "Failed to load resource." msgstr "Kaynak yükleme baÅŸarısız oldu." #: editor/inspector_dock.cpp -#, fuzzy msgid "Expand All Properties" -msgstr "Tüm özellikleri geniÅŸlet" +msgstr "Tüm Özellikleri GeniÅŸlet" #: editor/inspector_dock.cpp -#, fuzzy msgid "Collapse All Properties" -msgstr "Tüm özellikleri daralt" +msgstr "Tüm Özellikleri Daralt" #: editor/inspector_dock.cpp editor/plugins/animation_player_editor_plugin.cpp #: editor/plugins/script_editor_plugin.cpp @@ -3564,9 +3544,8 @@ msgid "Paste Params" msgstr "Parametreleri Yapıştır" #: editor/inspector_dock.cpp -#, fuzzy msgid "Edit Resource Clipboard" -msgstr "Kaynak panosu boÅŸ!" +msgstr "Kaynak Panosunu Düzenle" #: editor/inspector_dock.cpp msgid "Copy Resource" @@ -3613,9 +3592,8 @@ msgid "Object properties." msgstr "Nesne özellikleri." #: editor/inspector_dock.cpp -#, fuzzy msgid "Filter properties" -msgstr "Düğümleri Süzgeçden Geçir" +msgstr "Özellikleri süz" #: editor/inspector_dock.cpp msgid "Changes may be lost!" @@ -3630,87 +3608,74 @@ msgid "Select a Node to edit Signals and Groups." msgstr "Sinyalleri ve Grupları düzenlemek için bir Düğüm seçin." #: editor/plugin_config_dialog.cpp -#, fuzzy msgid "Edit a Plugin" -msgstr "Çokluyu Düzenleyin" +msgstr "Eklentiyi Düzenleyin" #: editor/plugin_config_dialog.cpp -#, fuzzy msgid "Create a Plugin" -msgstr "C# Çözümü oluÅŸtur" +msgstr "Eklenti OluÅŸtur" #: editor/plugin_config_dialog.cpp -#, fuzzy msgid "Plugin Name:" -msgstr "Eklentiler" +msgstr "Eklentinin Adı:" #: editor/plugin_config_dialog.cpp msgid "Subfolder:" -msgstr "" +msgstr "Alt Klasör:" #: editor/plugin_config_dialog.cpp -#, fuzzy msgid "Language:" -msgstr "Dil" +msgstr "Dil:" #: editor/plugin_config_dialog.cpp -#, fuzzy msgid "Script Name:" -msgstr "Betik geçerli" +msgstr "Betik Adı:" #: editor/plugin_config_dialog.cpp msgid "Activate now?" -msgstr "" +msgstr "Åžimdi etkinleÅŸtirilsin mi?" #: editor/plugins/abstract_polygon_2d_editor.cpp #: editor/plugins/polygon_2d_editor_plugin.cpp -#, fuzzy msgid "Create Polygon" -msgstr "Çoklu OluÅŸturun" +msgstr "Çokgen OluÅŸtur" #: editor/plugins/abstract_polygon_2d_editor.cpp #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp -#, fuzzy msgid "Create points." -msgstr "Noktaları sil" +msgstr "Noktalar oluÅŸtur." #: editor/plugins/abstract_polygon_2d_editor.cpp -#, fuzzy msgid "" "Edit points.\n" "LMB: Move Point\n" "RMB: Erase Point" msgstr "" -"Varolan çokgeni düzenle:\n" -"FareSolTık: Noktayı Taşı.\n" -"Ctrl+FareSolTık: Parça Ayır.\n" -"FareSaÄŸTık: Noktayı Sil." +"Noktaları düzenle\n" +"Sol Fare Düğmesi: Noktayı Taşı\n" +"SaÄŸ Fare Düğmesi: Noktayı Sil" #: editor/plugins/abstract_polygon_2d_editor.cpp #: editor/plugins/animation_blend_space_1d_editor.cpp -#, fuzzy msgid "Erase points." -msgstr "RMB: Noktayı Sil." +msgstr "Noktaları sil." #: editor/plugins/abstract_polygon_2d_editor.cpp -#, fuzzy msgid "Edit Polygon" -msgstr "Çokluyu Düzenleyin" +msgstr "Çokgeni Düzenle" #: editor/plugins/abstract_polygon_2d_editor.cpp msgid "Insert Point" msgstr "Nokta YerleÅŸtir" #: editor/plugins/abstract_polygon_2d_editor.cpp -#, fuzzy msgid "Edit Polygon (Remove Point)" -msgstr "Çokluyu Düzenleyin (Noktayı Silin)" +msgstr "Çokgeni Düzenle (Noktayı Sil)" #: editor/plugins/abstract_polygon_2d_editor.cpp -#, fuzzy msgid "Remove Polygon And Point" -msgstr "Çokluyu ve Noktayı Kaldır" +msgstr "Çokgeni ve Noktayı Kaldır" #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp @@ -3724,52 +3689,48 @@ msgstr "Animasyon Ekle" #: editor/plugins/animation_blend_space_2d_editor.cpp #: editor/plugins/animation_blend_tree_editor_plugin.cpp #: editor/plugins/animation_state_machine_editor.cpp -#, fuzzy msgid "Load..." -msgstr "Yükle" +msgstr "Yükle..." #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp -#, fuzzy msgid "Move Node Point" -msgstr "Noktayı Taşı" +msgstr "Düğüm Noktasını Taşı" #: editor/plugins/animation_blend_space_1d_editor.cpp #, fuzzy msgid "Change BlendSpace1D Limits" -msgstr "Karışım Süresini DeÄŸiÅŸtir" +msgstr "BlendSpace1D'nin Sınırlarını DeÄŸiÅŸtir" #: editor/plugins/animation_blend_space_1d_editor.cpp #, fuzzy msgid "Change BlendSpace1D Labels" -msgstr "Karışım Süresini DeÄŸiÅŸtir" +msgstr "BlendSpace1D'nin Etiketlerini DeÄŸiÅŸtir" #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp #: editor/plugins/animation_state_machine_editor.cpp msgid "This type of node can't be used. Only root nodes are allowed." -msgstr "" +msgstr "Bu tipte bir düğüm kullanılamaz. Sadece kök düğümlere izin verilir." #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp -#, fuzzy msgid "Add Node Point" -msgstr "Düğüm Ekle" +msgstr "Düğüm Noktası Ekle" #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp -#, fuzzy msgid "Add Animation Point" -msgstr "Animasyon Ekle" +msgstr "Animasyon Noktası Ekle" #: editor/plugins/animation_blend_space_1d_editor.cpp #, fuzzy msgid "Remove BlendSpace1D Point" -msgstr "Yol Noktasını Kaldır" +msgstr "BlendSpace1D Noktasını Kaldır" #: editor/plugins/animation_blend_space_1d_editor.cpp msgid "Move BlendSpace1D Node Point" -msgstr "" +msgstr "BlendSpace1D Düğüm Noktasını Taşı" #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp @@ -3779,73 +3740,75 @@ msgid "" "AnimationTree is inactive.\n" "Activate to enable playback, check node warnings if activation fails." msgstr "" +"AnimationTree etkin deÄŸil.\n" +"Pleybeki aktifleÅŸtirmek için etkin hale getirin. Etkin hale gelmediÄŸi " +"taktirde düğüm uyarılarını kontrol edin." #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp +#, fuzzy msgid "Set the blending position within the space" -msgstr "" +msgstr "Harmanlama konumunu uzay içinde ayarla" #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp msgid "Select and move points, create points with RMB." -msgstr "" +msgstr "Noktaları seç ve taşı. SaÄŸ fare düğmesi ile yeni noktalar oluÅŸtur." #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp scene/gui/graph_edit.cpp msgid "Enable snap and show grid." -msgstr "" +msgstr "Yapıştırmayı etkinleÅŸtir ve ızgarayı göster." #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp -#, fuzzy msgid "Point" -msgstr "Noktayı Taşı" +msgstr "Nokta" #: editor/plugins/animation_blend_space_1d_editor.cpp #: editor/plugins/animation_blend_space_2d_editor.cpp #: editor/plugins/animation_blend_tree_editor_plugin.cpp #: editor/plugins/animation_state_machine_editor.cpp -#, fuzzy msgid "Open Animation Node" -msgstr "Animasyon Düğümü" +msgstr "Animasyon Düğümünü Aç" #: editor/plugins/animation_blend_space_2d_editor.cpp -#, fuzzy msgid "Triangle already exists" -msgstr "Ä°ÅŸlem '%s' zaten var!" +msgstr "Üçgen zaten var" #: editor/plugins/animation_blend_space_2d_editor.cpp -#, fuzzy msgid "Add Triangle" -msgstr "DeÄŸiÅŸken Ekle" +msgstr "Üçgen Ekle" #: editor/plugins/animation_blend_space_2d_editor.cpp #, fuzzy msgid "Change BlendSpace2D Limits" -msgstr "Karışım Süresini DeÄŸiÅŸtir" +msgstr "BlendSpace2D Sınırlarını DeÄŸiÅŸtir" #: editor/plugins/animation_blend_space_2d_editor.cpp #, fuzzy msgid "Change BlendSpace2D Labels" -msgstr "Karışım Süresini DeÄŸiÅŸtir" +msgstr "BlendSpace2D Etiketlerini DeÄŸiÅŸtir" #: editor/plugins/animation_blend_space_2d_editor.cpp #, fuzzy msgid "Remove BlendSpace2D Point" -msgstr "Yol Noktasını Kaldır" +msgstr "BlendSpace2D Noktasını Kaldır" #: editor/plugins/animation_blend_space_2d_editor.cpp #, fuzzy msgid "Remove BlendSpace2D Triangle" -msgstr "DeÄŸiÅŸkeni Kaldır" +msgstr "BlendSpace2D Üçgenini Kaldır" #: editor/plugins/animation_blend_space_2d_editor.cpp +#, fuzzy msgid "BlendSpace2D does not belong to an AnimationTree node." -msgstr "" +msgstr "BlendSpace2D, bir AnimationTree düğümüne ait deÄŸil." #: editor/plugins/animation_blend_space_2d_editor.cpp +#, fuzzy msgid "No triangles exist, so no blending can take place." -msgstr "" +msgstr "Herhangi bir üçgen bulunmuyor, harmanlama iÅŸlemi yapılamaz." #: editor/plugins/animation_blend_space_2d_editor.cpp #, fuzzy diff --git a/editor/translations/uk.po b/editor/translations/uk.po index 637c1ffac4..15d169313b 100644 --- a/editor/translations/uk.po +++ b/editor/translations/uk.po @@ -15,7 +15,7 @@ msgid "" msgstr "" "Project-Id-Version: Ukrainian (Godot Engine)\n" "POT-Creation-Date: \n" -"PO-Revision-Date: 2019-03-30 20:04+0000\n" +"PO-Revision-Date: 2019-04-29 08:48+0000\n" "Last-Translator: Yuri Chornoivan <yurchor@ukr.net>\n" "Language-Team: Ukrainian <https://hosted.weblate.org/projects/godot-engine/" "godot/uk/>\n" @@ -25,7 +25,7 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=3; plural=n%10==1 && n%100!=11 ? 0 : n%10>=2 && n" "%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2;\n" -"X-Generator: Weblate 3.6-dev\n" +"X-Generator: Weblate 3.6.1\n" #: core/math/expression.cpp modules/gdscript/gdscript_functions.cpp #: modules/visual_script/visual_script_builtin_funcs.cpp @@ -163,14 +163,20 @@ msgid "Animation Playback Track" msgstr "Доріжка Ð²Ñ–Ð´Ñ‚Ð²Ð¾Ñ€ÐµÐ½Ð½Ñ Ð°Ð½Ñ–Ð¼Ð°Ñ†Ñ–Ñ—" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "Додати доріжку" +#, fuzzy +msgid "Animation length (frames)" +msgstr "ТриваліÑÑ‚ÑŒ анімації (у Ñекундах)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "ТриваліÑÑ‚ÑŒ анімації (у Ñекундах)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "Додати доріжку" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "ЦиклічніÑÑ‚ÑŒ анімації" @@ -425,9 +431,8 @@ msgstr "" "Групувати доріжки за вузлами або показувати Ñ—Ñ… у форматі проÑтого ÑпиÑку." #: editor/animation_track_editor.cpp -#, fuzzy msgid "Snap:" -msgstr "ПрилипаннÑ" +msgstr "ПрилипаннÑ:" #: editor/animation_track_editor.cpp msgid "Animation step value." @@ -435,7 +440,7 @@ msgstr "Ð—Ð½Ð°Ñ‡ÐµÐ½Ð½Ñ ÐºÑ€Ð¾ÐºÑƒ анімації." #: editor/animation_track_editor.cpp msgid "Seconds" -msgstr "" +msgstr "Секунди" #: editor/animation_track_editor.cpp msgid "FPS" @@ -4811,20 +4816,19 @@ msgstr "Макет" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Translation mask for inserting keys." -msgstr "" +msgstr "МаÑка перенеÑÐµÐ½Ð½Ñ Ð´Ð»Ñ Ð²ÑтавлÑÐ½Ð½Ñ ÐºÐ»ÑŽÑ‡Ð¾Ð²Ð¸Ñ… кадрів." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Rotation mask for inserting keys." -msgstr "" +msgstr "МаÑка Ð¾Ð±ÐµÑ€Ñ‚Ð°Ð½Ð½Ñ Ð´Ð»Ñ Ð²ÑтавлÑÐ½Ð½Ñ ÐºÐ»ÑŽÑ‡Ð¾Ð²Ð¸Ñ… кадрів." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Scale mask for inserting keys." -msgstr "" +msgstr "МаÑка маÑÑˆÑ‚Ð°Ð±ÑƒÐ²Ð°Ð½Ð½Ñ Ð´Ð»Ñ Ð²ÑтавлÑÐ½Ð½Ñ ÐºÐ»ÑŽÑ‡Ð¾Ð²Ð¸Ñ… кадрів." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Insert keys (based on mask)." -msgstr "Ð’Ñтавити ключ (Ñ–Ñнуючі доріжки)" +msgstr "Ð’Ñтавити ключові кадри (на оÑнові маÑки)." #: editor/plugins/canvas_item_editor_plugin.cpp msgid "" @@ -4833,11 +4837,15 @@ msgid "" "Keys are only added to existing tracks, no new tracks will be created.\n" "Keys must be inserted manually for the first time." msgstr "" +"Ðвтоматично вÑтавлÑти ключові кадри при перенеÑенні, обертанні або " +"маÑштабуванні об'єктів (на оÑнові маÑки).\n" +"Ключові кадри додаватимутьÑÑ Ð»Ð¸ÑˆÐµ до наÑвних доріжок, нові доріжки не " +"ÑтворюватимутьÑÑ.\n" +"Спершу ключові кадри Ñлід додати вручну." #: editor/plugins/canvas_item_editor_plugin.cpp -#, fuzzy msgid "Auto Insert Key" -msgstr "Ð’Ñтавити ключ анімації" +msgstr "ÐвтовÑÑ‚Ð°Ð²Ð»ÐµÐ½Ð½Ñ ÐºÐ»ÑŽÑ‡Ð¾Ð²Ð¾Ð³Ð¾ кадру" #: editor/plugins/canvas_item_editor_plugin.cpp msgid "Insert Key (Existing Tracks)" @@ -5826,9 +5834,8 @@ msgid "Save Theme As..." msgstr "Зберегти тему Ñк..." #: editor/plugins/script_editor_plugin.cpp -#, fuzzy msgid "%s Class Reference" -msgstr " ПоÑÐ¸Ð»Ð°Ð½Ð½Ñ Ð½Ð° клаÑ" +msgstr "Довідник з клаÑу %s" #: editor/plugins/script_editor_plugin.cpp msgid "Toggle alphabetical sorting of the method list." @@ -6653,24 +6660,20 @@ msgid "Nameless gizmo" msgstr "Штука без назви" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Mesh2D" -msgstr "Створити плоÑку Ñітку" +msgstr "Створити Mesh2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create Polygon2D" -msgstr "Створити Polygon3D" +msgstr "Створити Polygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D" -msgstr "Створити полігон зіткненнÑ" +msgstr "Створити CollisionPolygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D" -msgstr "Створено затінювальний полігон" +msgstr "Створити LightOccluder2D" #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite is empty!" @@ -6687,43 +6690,36 @@ msgid "Invalid geometry, can't replace by mesh." msgstr "Ðекоректна геометріÑ, неможливо замінити Ñіткою." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create polygon." -msgstr "Ðекоректна геометріÑ, неможливо замінити Ñіткою." +msgstr "Ðекоректна геометріÑ, неможливо Ñтворити багатокутник." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create collision polygon." -msgstr "Ðекоректна геометріÑ, неможливо замінити Ñіткою." +msgstr "Ðекоректна геометріÑ, неможливо Ñтворити багатокутник зіткненнÑ." #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Invalid geometry, can't create light occluder." -msgstr "Ðекоректна геометріÑ, неможливо замінити Ñіткою." +msgstr "Ðекоректна геометріÑ, неможливо Ñтворити перешкоду Ñвітла." #: editor/plugins/sprite_editor_plugin.cpp msgid "Sprite" msgstr "Спрайт" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Mesh2D" -msgstr "Перетворити на плоÑку Ñітку" +msgstr "Перетворити на Mesh2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Convert to Polygon2D" -msgstr "ПереміÑтити полігон" +msgstr "Перетворити на Polygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create CollisionPolygon2D Sibling" -msgstr "Створити полігон зіткненнÑ" +msgstr "Створити близнюк CollisionPolygon2D" #: editor/plugins/sprite_editor_plugin.cpp -#, fuzzy msgid "Create LightOccluder2D Sibling" -msgstr "Створено затінювальний полігон" +msgstr "Створити близнюка LightOccluder2D" #: editor/plugins/sprite_editor_plugin.cpp msgid "Simplification: " @@ -7312,9 +7308,8 @@ msgid "Duplicate Nodes" msgstr "Дублювати вузли" #: editor/plugins/visual_shader_editor_plugin.cpp -#, fuzzy msgid "Delete Nodes" -msgstr "Вилучити вузол" +msgstr "Вилучити вузли" #: editor/plugins/visual_shader_editor_plugin.cpp msgid "Visual Shader Input Type Changed" diff --git a/editor/translations/ur_PK.po b/editor/translations/ur_PK.po index cf4d0fe630..6a737994a5 100644 --- a/editor/translations/ur_PK.po +++ b/editor/translations/ur_PK.po @@ -158,11 +158,15 @@ msgid "Animation Playback Track" msgstr "" #: editor/animation_track_editor.cpp -msgid "Add Track" +msgid "Animation length (frames)" msgstr "" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" +msgstr "" + +#: editor/animation_track_editor.cpp +msgid "Add Track" msgstr "" #: editor/animation_track_editor.cpp diff --git a/editor/translations/vi.po b/editor/translations/vi.po index d18046ad52..49201d2c9f 100644 --- a/editor/translations/vi.po +++ b/editor/translations/vi.po @@ -164,16 +164,21 @@ msgstr "NgÆ°ng chạy animation. (S)" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "Thêm Track Animation" +msgid "Animation length (frames)" +msgstr "Äá»™ dà i Animation (giây)." #: editor/animation_track_editor.cpp #, fuzzy -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "Äá»™ dà i Animation (giây)." #: editor/animation_track_editor.cpp #, fuzzy +msgid "Add Track" +msgstr "Thêm Track Animation" + +#: editor/animation_track_editor.cpp +#, fuzzy msgid "Animation Looping" msgstr "Phóng Animation." diff --git a/editor/translations/zh_CN.po b/editor/translations/zh_CN.po index 3e03b0e8ff..f087c45047 100644 --- a/editor/translations/zh_CN.po +++ b/editor/translations/zh_CN.po @@ -44,12 +44,14 @@ # simano clio <sim2cle@gmail.com>, 2019. # ByonkoGalilei <byonko@qq.com>, 2019. # qjyqjyqjyqjy <qjyqjyqjyqjy@sina.com.cn>, 2019. +# liushuyu011 <liushuyu011@gmail.com>, 2019. +# DS <dseqrasd@126.com>, 2019. msgid "" msgstr "" "Project-Id-Version: Chinese (Simplified) (Godot Engine)\n" "POT-Creation-Date: 2018-01-20 12:15+0200\n" -"PO-Revision-Date: 2019-04-23 15:48+0000\n" -"Last-Translator: qjyqjyqjyqjy <qjyqjyqjyqjy@sina.com.cn>\n" +"PO-Revision-Date: 2019-05-16 18:48+0000\n" +"Last-Translator: DS <dseqrasd@126.com>\n" "Language-Team: Chinese (Simplified) <https://hosted.weblate.org/projects/" "godot-engine/godot/zh_Hans/>\n" "Language: zh_CN\n" @@ -193,14 +195,20 @@ msgid "Animation Playback Track" msgstr "动画回放轨é“" #: editor/animation_track_editor.cpp -msgid "Add Track" -msgstr "æ·»åŠ è½¨é“" +#, fuzzy +msgid "Animation length (frames)" +msgstr "动画时长(秒)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "动画时长(秒)" #: editor/animation_track_editor.cpp +msgid "Add Track" +msgstr "æ·»åŠ è½¨é“" + +#: editor/animation_track_editor.cpp msgid "Animation Looping" msgstr "动画循环" @@ -450,9 +458,8 @@ msgid "Group tracks by node or display them as plain list." msgstr "按节点分组或将它们显示为普通列表。" #: editor/animation_track_editor.cpp -#, fuzzy msgid "Snap:" -msgstr "å¸é™„" +msgstr "å¸é™„:" #: editor/animation_track_editor.cpp msgid "Animation step value." @@ -7953,7 +7960,7 @@ msgstr "编辑器需è¦é‡å¯ä»¥è®©ä¿®æ”¹ç”Ÿæ•ˆ" #: editor/project_settings_editor.cpp msgid "Input Map" -msgstr "事件表" +msgstr "é”®ä½æ˜ å°„" #: editor/project_settings_editor.cpp msgid "Action:" diff --git a/editor/translations/zh_HK.po b/editor/translations/zh_HK.po index 45b43c3ce6..418c8c2987 100644 --- a/editor/translations/zh_HK.po +++ b/editor/translations/zh_HK.po @@ -163,16 +163,21 @@ msgstr "" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "新增動畫軌跡" +msgid "Animation length (frames)" +msgstr "時長(秒)。" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Animation Length Time (seconds)" +msgid "Animation length (seconds)" msgstr "時長(秒)。" #: editor/animation_track_editor.cpp #, fuzzy +msgid "Add Track" +msgstr "新增動畫軌跡" + +#: editor/animation_track_editor.cpp +#, fuzzy msgid "Animation Looping" msgstr "動畫縮放。" diff --git a/editor/translations/zh_TW.po b/editor/translations/zh_TW.po index 6f858474a2..a6bac6efe4 100644 --- a/editor/translations/zh_TW.po +++ b/editor/translations/zh_TW.po @@ -166,15 +166,21 @@ msgstr "動畫回放軌é“" #: editor/animation_track_editor.cpp #, fuzzy -msgid "Add Track" -msgstr "æ·»åŠ å‹•ç•«è»Œ" +msgid "Animation length (frames)" +msgstr "動畫長度(秒)" #: editor/animation_track_editor.cpp -msgid "Animation Length Time (seconds)" +#, fuzzy +msgid "Animation length (seconds)" msgstr "動畫長度(秒)" #: editor/animation_track_editor.cpp #, fuzzy +msgid "Add Track" +msgstr "æ·»åŠ å‹•ç•«è»Œ" + +#: editor/animation_track_editor.cpp +#, fuzzy msgid "Animation Looping" msgstr "動畫空間。" diff --git a/main/main.cpp b/main/main.cpp index bfba795628..fb75b4d78f 100644 --- a/main/main.cpp +++ b/main/main.cpp @@ -1035,7 +1035,7 @@ Error Main::setup(const char *execpath, int argc, char *argv[], bool p_second_ph } OS::get_singleton()->set_low_processor_usage_mode(GLOBAL_DEF("application/run/low_processor_mode", false)); - OS::get_singleton()->set_low_processor_usage_mode_sleep_usec(GLOBAL_DEF("application/run/low_processor_mode_sleep_usec", 8000)); + OS::get_singleton()->set_low_processor_usage_mode_sleep_usec(GLOBAL_DEF("application/run/low_processor_mode_sleep_usec", 6900)); // Roughly 144 FPS ProjectSettings::get_singleton()->set_custom_property_info("application/run/low_processor_mode_sleep_usec", PropertyInfo(Variant::INT, "application/run/low_processor_mode_sleep_usec", PROPERTY_HINT_RANGE, "0,33200,1,or_greater")); // No negative numbers Engine::get_singleton()->set_frame_delay(frame_delay); @@ -1957,7 +1957,7 @@ bool Main::iteration() { return exit; if (OS::get_singleton()->is_in_low_processor_usage_mode() || !OS::get_singleton()->can_draw()) - OS::get_singleton()->delay_usec(OS::get_singleton()->get_low_processor_usage_mode_sleep_usec()); //apply some delay to force idle time (results in about 60 FPS max) + OS::get_singleton()->delay_usec(OS::get_singleton()->get_low_processor_usage_mode_sleep_usec()); //apply some delay to force idle time else { uint32_t frame_delay = Engine::get_singleton()->get_frame_delay(); if (frame_delay) diff --git a/misc/travis/clang-format.sh b/misc/travis/clang-format.sh index ee4d0b2a10..5463a6cedf 100755 --- a/misc/travis/clang-format.sh +++ b/misc/travis/clang-format.sh @@ -1,6 +1,6 @@ #!/bin/sh -CLANG_FORMAT=clang-format-6.0 +CLANG_FORMAT=clang-format-8 if [ "$TRAVIS_PULL_REQUEST" != "false" ]; then # Check the whole commit range against $TRAVIS_BRANCH, the base merge branch diff --git a/modules/assimp/editor_scene_importer_assimp.cpp b/modules/assimp/editor_scene_importer_assimp.cpp index 8d82fb2eeb..8c3c04674b 100644 --- a/modules/assimp/editor_scene_importer_assimp.cpp +++ b/modules/assimp/editor_scene_importer_assimp.cpp @@ -310,8 +310,8 @@ void EditorSceneImporterAssimp::_generate_bone_groups(ImportState &state, const const aiBone *bone = mesh->mBones[j]; String name = _assimp_get_string(bone->mName); ownership[name] = owned_by; - //store the actuall full path for the bone transform - //when skeleton finds it's place in the tree, it will be restored + //store the actual full path for the bone transform + //when skeleton finds its place in the tree, it will be restored bind_xforms[name] = mesh_offset * _assimp_matrix_transform(bone->mOffsetMatrix); } } @@ -855,9 +855,7 @@ Ref<Material> EditorSceneImporterAssimp::_generate_material_from_index(ImportSta Ref<Texture> texture = _load_texture(state, path); if (texture != NULL) { - if (map_mode != NULL) { - _set_texture_mapping_mode(map_mode, texture); - } + _set_texture_mapping_mode(map_mode, texture); mat->set_feature(SpatialMaterial::Feature::FEATURE_NORMAL_MAPPING, true); mat->set_texture(SpatialMaterial::TEXTURE_NORMAL, texture); } @@ -1460,7 +1458,7 @@ void EditorSceneImporterAssimp::_generate_node(ImportState &state, const aiNode int mesh_index = p_assimp_node->mMeshes[i]; surface_indices.push_back(mesh_index); - //take the chane and attempt to find the skeleton from the bones + //take the chance and attempt to find the skeleton from the bones if (!skeleton) { aiMesh *ai_mesh = state.assimp_scene->mMeshes[p_assimp_node->mMeshes[i]]; for (uint32_t j = 0; j < ai_mesh->mNumBones; j++) { @@ -1598,7 +1596,7 @@ void EditorSceneImporterAssimp::_generate_node(ImportState &state, const aiNode skeleton->localize_rests(); node_name = "Skeleton"; //don't use the bone root name - node_transform = Transform(); //dont transform + node_transform = Transform(); //don't transform new_node = skeleton; } else { diff --git a/modules/bullet/space_bullet.cpp b/modules/bullet/space_bullet.cpp index 6bfd98873e..738b415d16 100644 --- a/modules/bullet/space_bullet.cpp +++ b/modules/bullet/space_bullet.cpp @@ -1152,7 +1152,7 @@ public: bool SpaceBullet::recover_from_penetration(RigidBodyBullet *p_body, const btTransform &p_body_position, btScalar p_recover_movement_scale, bool p_infinite_inertia, btVector3 &r_delta_recover_movement, RecoverResult *r_recover_result) { - // Calculate the cummulative AABB of all shapes of the kinematic body + // Calculate the cumulative AABB of all shapes of the kinematic body btVector3 aabb_min, aabb_max; bool shapes_found = false; @@ -1347,7 +1347,7 @@ int SpaceBullet::add_separation_result(PhysicsServer::SeparationResult *r_result int SpaceBullet::recover_from_penetration_ray(RigidBodyBullet *p_body, const btTransform &p_body_position, btScalar p_recover_movement_scale, bool p_infinite_inertia, int p_result_max, btVector3 &r_delta_recover_movement, PhysicsServer::SeparationResult *r_results) { - // Calculate the cummulative AABB of all shapes of the kinematic body + // Calculate the cumulative AABB of all shapes of the kinematic body btVector3 aabb_min, aabb_max; bool shapes_found = false; diff --git a/modules/csg/csg.cpp b/modules/csg/csg.cpp index 7e1cc937cd..3a61afa023 100644 --- a/modules/csg/csg.cpp +++ b/modules/csg/csg.cpp @@ -611,7 +611,7 @@ void CSGBrushOperation::_add_poly_points(const BuildPoly &p_poly, int p_edge, in { EdgeSort es; - es.angle = 0; //wont be checked here + es.angle = 0; //won't be checked here es.edge = p_edge; es.prev_point = p_from_point; es.edge_point = p_to_point; diff --git a/modules/csg/csg_shape.cpp b/modules/csg/csg_shape.cpp index e70773d914..1d27b9b6f4 100644 --- a/modules/csg/csg_shape.cpp +++ b/modules/csg/csg_shape.cpp @@ -2082,6 +2082,9 @@ CSGBrush *CSGPolygon::_build_brush() { for (int i = 0; i <= splits; i++) { float ofs = i * path_interval; + if (ofs > bl) { + ofs = bl; + } if (i == splits && path_joined) { ofs = 0.0; } diff --git a/modules/enet/doc_classes/NetworkedMultiplayerENet.xml b/modules/enet/doc_classes/NetworkedMultiplayerENet.xml index 894c17c684..d3d1e58b7b 100644 --- a/modules/enet/doc_classes/NetworkedMultiplayerENet.xml +++ b/modules/enet/doc_classes/NetworkedMultiplayerENet.xml @@ -110,7 +110,7 @@ Always use [code]TRANSFER_MODE_ORDERED[/code] in place of [code]TRANSFER_MODE_UNRELIABLE[/code]. This is the only way to use ordering with the RPC system. </member> <member name="channel_count" type="int" setter="set_channel_count" getter="get_channel_count"> - The number of channels to be used by ENet. Default: [code]3[/code]. Channels are used to separate different kinds of data. In realiable or ordered mode, for example, the packet delivery order is ensured on a per channel basis. + The number of channels to be used by ENet. Default: [code]3[/code]. Channels are used to separate different kinds of data. In reliable or ordered mode, for example, the packet delivery order is ensured on a per channel basis. </member> <member name="compression_mode" type="int" setter="set_compression_mode" getter="get_compression_mode" enum="NetworkedMultiplayerENet.CompressionMode"> The compression method used for network packets. Default is no compression. These have different tradeoffs of compression speed versus bandwidth, you may need to test which one works best for your use case if you use compression at all. diff --git a/modules/enet/networked_multiplayer_enet.cpp b/modules/enet/networked_multiplayer_enet.cpp index 492b365128..18dfe08e85 100644 --- a/modules/enet/networked_multiplayer_enet.cpp +++ b/modules/enet/networked_multiplayer_enet.cpp @@ -231,7 +231,7 @@ void NetworkedMultiplayerENet::poll() { break; } - // A client joined with an invalid ID (neagtive values, 0, and 1 are reserved). + // A client joined with an invalid ID (negative values, 0, and 1 are reserved). // Probably trying to exploit us. if (server && ((int)event.data < 2 || peer_map.has((int)event.data))) { enet_peer_reset(event.peer); diff --git a/modules/gdnative/config.py b/modules/gdnative/config.py index fde7f1a6e0..7898de5523 100644 --- a/modules/gdnative/config.py +++ b/modules/gdnative/config.py @@ -16,7 +16,8 @@ def get_doc_classes(): "ResourceFormatLoaderVideoStreamGDNative", "StreamPeerGDNative", "VideoStreamGDNative", - "WebRTCPeerGDNative", + "WebRTCPeerConnectionGDNative", + "WebRTCDataChannelGDNative", ] def get_doc_path(): diff --git a/modules/gdnative/doc_classes/WebRTCDataChannelGDNative.xml b/modules/gdnative/doc_classes/WebRTCDataChannelGDNative.xml new file mode 100644 index 0000000000..ac18ec6020 --- /dev/null +++ b/modules/gdnative/doc_classes/WebRTCDataChannelGDNative.xml @@ -0,0 +1,13 @@ +<?xml version="1.0" encoding="UTF-8" ?> +<class name="WebRTCDataChannelGDNative" inherits="WebRTCDataChannel" category="Core" version="3.2"> + <brief_description> + </brief_description> + <description> + </description> + <tutorials> + </tutorials> + <methods> + </methods> + <constants> + </constants> +</class> diff --git a/modules/gdnative/doc_classes/WebRTCPeerConnectionGDNative.xml b/modules/gdnative/doc_classes/WebRTCPeerConnectionGDNative.xml new file mode 100644 index 0000000000..44cb8e5db8 --- /dev/null +++ b/modules/gdnative/doc_classes/WebRTCPeerConnectionGDNative.xml @@ -0,0 +1,13 @@ +<?xml version="1.0" encoding="UTF-8" ?> +<class name="WebRTCPeerConnectionGDNative" inherits="WebRTCPeerConnection" category="Core" version="3.2"> + <brief_description> + </brief_description> + <description> + </description> + <tutorials> + </tutorials> + <methods> + </methods> + <constants> + </constants> +</class> diff --git a/modules/gdnative/gdnative.cpp b/modules/gdnative/gdnative.cpp index c8e17e8dc5..a27935bfe2 100644 --- a/modules/gdnative/gdnative.cpp +++ b/modules/gdnative/gdnative.cpp @@ -404,7 +404,7 @@ bool GDNative::terminate() { } else if (gdnatives->size() == 1) { // we're the last one, terminate! gdnatives->clear(); - // wew this looks scary, but all it does is remove the entry completely + // whew this looks scary, but all it does is remove the entry completely GDNativeLibrary::loaded_libraries->erase(GDNativeLibrary::loaded_libraries->find(library->get_current_library_path())); } } diff --git a/modules/gdnative/gdnative/dictionary.cpp b/modules/gdnative/gdnative/dictionary.cpp index 2c6c9e2de2..fff3fc3625 100644 --- a/modules/gdnative/gdnative/dictionary.cpp +++ b/modules/gdnative/gdnative/dictionary.cpp @@ -55,6 +55,15 @@ void GDAPI godot_dictionary_destroy(godot_dictionary *p_self) { self->~Dictionary(); } +godot_dictionary GDAPI godot_dictionary_duplicate(const godot_dictionary *p_self, const godot_bool p_deep) { + const Dictionary *self = (const Dictionary *)p_self; + godot_dictionary res; + Dictionary *val = (Dictionary *)&res; + memnew_placement(val, Dictionary); + *val = self->duplicate(p_deep); + return res; +} + godot_int GDAPI godot_dictionary_size(const godot_dictionary *p_self) { const Dictionary *self = (const Dictionary *)p_self; return self->size(); diff --git a/modules/gdnative/gdnative/variant.cpp b/modules/gdnative/gdnative/variant.cpp index 8f0d5a2db4..ac4d5a86b2 100644 --- a/modules/gdnative/gdnative/variant.cpp +++ b/modules/gdnative/gdnative/variant.cpp @@ -518,7 +518,7 @@ void GDAPI godot_variant_evaluate(godot_variant_operator p_op, const godot_varia const Variant *a = (const Variant *)p_a; const Variant *b = (const Variant *)p_b; Variant *ret = (Variant *)r_ret; - Variant::evaluate(op, a, b, *ret, *r_valid); + Variant::evaluate(op, *a, *b, *ret, *r_valid); } #ifdef __cplusplus diff --git a/modules/gdnative/gdnative_api.json b/modules/gdnative/gdnative_api.json index 9882a89794..8afe988102 100644 --- a/modules/gdnative/gdnative_api.json +++ b/modules/gdnative/gdnative_api.json @@ -11,7 +11,24 @@ "major": 1, "minor": 1 }, - "next": null, + "next": { + "type": "CORE", + "version": { + "major": 1, + "minor": 2 + }, + "next": null, + "api": [ + { + "name": "godot_dictionary_duplicate", + "return_type": "godot_dictionary", + "arguments": [ + ["const godot_dictionary *", "p_self"], + ["const godot_bool", "p_deep"] + ] + } + ] + }, "api": [ { "name": "godot_color_to_abgr32", @@ -6436,11 +6453,26 @@ "next": null, "api": [ { - "name": "godot_net_bind_webrtc_peer", + "name": "godot_net_set_webrtc_library", + "return_type": "godot_error", + "arguments": [ + ["const godot_net_webrtc_library *", "p_library"] + ] + }, + { + "name": "godot_net_bind_webrtc_peer_connection", + "return_type": "void", + "arguments": [ + ["godot_object *", "p_obj"], + ["const godot_net_webrtc_peer_connection *", "p_interface"] + ] + }, + { + "name": "godot_net_bind_webrtc_data_channel", "return_type": "void", "arguments": [ ["godot_object *", "p_obj"], - ["const godot_net_webrtc_peer *", "p_interface"] + ["const godot_net_webrtc_data_channel *", "p_interface"] ] } ] diff --git a/modules/gdnative/include/gdnative/dictionary.h b/modules/gdnative/include/gdnative/dictionary.h index 14e35b4692..483cd9c4e3 100644 --- a/modules/gdnative/include/gdnative/dictionary.h +++ b/modules/gdnative/include/gdnative/dictionary.h @@ -63,6 +63,8 @@ void GDAPI godot_dictionary_new(godot_dictionary *r_dest); void GDAPI godot_dictionary_new_copy(godot_dictionary *r_dest, const godot_dictionary *p_src); void GDAPI godot_dictionary_destroy(godot_dictionary *p_self); +godot_dictionary GDAPI godot_dictionary_duplicate(const godot_dictionary *p_self, const godot_bool p_deep); + godot_int GDAPI godot_dictionary_size(const godot_dictionary *p_self); godot_bool GDAPI godot_dictionary_empty(const godot_dictionary *p_self); diff --git a/modules/gdnative/include/net/godot_net.h b/modules/gdnative/include/net/godot_net.h index c1bc9daab5..3a411755c1 100644 --- a/modules/gdnative/include/net/godot_net.h +++ b/modules/gdnative/include/net/godot_net.h @@ -111,37 +111,11 @@ typedef struct { /* Binds a MultiplayerPeerGDNative to the provided interface */ void GDAPI godot_net_bind_multiplayer_peer(godot_object *p_obj, const godot_net_multiplayer_peer *); -typedef struct { - godot_gdnative_api_version version; /* version of our API */ - - godot_object *data; /* User reference */ - - /* This is PacketPeer */ - godot_error (*get_packet)(void *, const uint8_t **, int *); - godot_error (*put_packet)(void *, const uint8_t *, int); - godot_int (*get_available_packet_count)(const void *); - godot_int (*get_max_packet_size)(const void *); - - /* This is WebRTCPeer */ - void (*set_write_mode)(void *, godot_int); - godot_int (*get_write_mode)(const void *); - bool (*was_string_packet)(const void *); - godot_int (*get_connection_state)(const void *); - - godot_error (*create_offer)(void *); - godot_error (*set_remote_description)(void *, const char *, const char *); - godot_error (*set_local_description)(void *, const char *, const char *); - godot_error (*add_ice_candidate)(void *, const char *, int, const char *); - godot_error (*poll)(void *); - - void *next; /* For extension? */ -} godot_net_webrtc_peer; - -/* Binds a PacketPeerGDNative to the provided interface */ -void GDAPI godot_net_bind_webrtc_peer(godot_object *p_obj, const godot_net_webrtc_peer *); - #ifdef __cplusplus } #endif +// WebRTC Bindings +#include "net/godot_webrtc.h" + #endif /* GODOT_NATIVENET_H */ diff --git a/modules/gdnative/include/net/godot_webrtc.h b/modules/gdnative/include/net/godot_webrtc.h new file mode 100644 index 0000000000..783f7b727d --- /dev/null +++ b/modules/gdnative/include/net/godot_webrtc.h @@ -0,0 +1,122 @@ +/*************************************************************************/ +/* godot_webrtc.h */ +/*************************************************************************/ +/* This file is part of: */ +/* GODOT ENGINE */ +/* https://godotengine.org */ +/*************************************************************************/ +/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ +/* */ +/* Permission is hereby granted, free of charge, to any person obtaining */ +/* a copy of this software and associated documentation files (the */ +/* "Software"), to deal in the Software without restriction, including */ +/* without limitation the rights to use, copy, modify, merge, publish, */ +/* distribute, sublicense, and/or sell copies of the Software, and to */ +/* permit persons to whom the Software is furnished to do so, subject to */ +/* the following conditions: */ +/* */ +/* The above copyright notice and this permission notice shall be */ +/* included in all copies or substantial portions of the Software. */ +/* */ +/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */ +/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */ +/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/ +/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */ +/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */ +/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */ +/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ +/*************************************************************************/ + +#ifndef GODOT_NATIVEWEBRTC_H +#define GODOT_NATIVEWEBRTC_H + +#include <gdnative/gdnative.h> + +#ifdef __cplusplus +extern "C" { +#endif + +#define GODOT_NET_WEBRTC_API_MAJOR 3 +#define GODOT_NET_WEBRTC_API_MINOR 2 + +/* Library Interface (used to set default GDNative WebRTC implementation */ +typedef struct { + godot_gdnative_api_version version; /* version of our API */ + + /* Called when the library is unset as default interface via godot_net_set_webrtc_library */ + void (*unregistered)(); + + /* Used by WebRTCPeerConnection create when GDNative is the default implementation. */ + /* Takes a pointer to WebRTCPeerConnectionGDNative, should bind and return OK, failure if binding was unsuccessful. */ + godot_error (*create_peer_connection)(godot_object *); + + void *next; /* For extension */ +} godot_net_webrtc_library; + +/* WebRTCPeerConnection interface */ +typedef struct { + godot_gdnative_api_version version; /* version of our API */ + + godot_object *data; /* User reference */ + + /* This is WebRTCPeerConnection */ + godot_int (*get_connection_state)(const void *); + + godot_error (*initialize)(void *, const godot_dictionary *); + godot_object *(*create_data_channel)(void *, const char *p_channel_name, const godot_dictionary *); + godot_error (*create_offer)(void *); + godot_error (*create_answer)(void *); /* unused for now, should be done automatically on set_local_description */ + godot_error (*set_remote_description)(void *, const char *, const char *); + godot_error (*set_local_description)(void *, const char *, const char *); + godot_error (*add_ice_candidate)(void *, const char *, int, const char *); + godot_error (*poll)(void *); + void (*close)(void *); + + void *next; /* For extension? */ +} godot_net_webrtc_peer_connection; + +/* WebRTCDataChannel interface */ +typedef struct { + godot_gdnative_api_version version; /* version of our API */ + + godot_object *data; /* User reference */ + + /* This is PacketPeer */ + godot_error (*get_packet)(void *, const uint8_t **, int *); + godot_error (*put_packet)(void *, const uint8_t *, int); + godot_int (*get_available_packet_count)(const void *); + godot_int (*get_max_packet_size)(const void *); + + /* This is WebRTCDataChannel */ + void (*set_write_mode)(void *, godot_int); + godot_int (*get_write_mode)(const void *); + bool (*was_string_packet)(const void *); + + godot_int (*get_ready_state)(const void *); + const char *(*get_label)(const void *); + bool (*is_ordered)(const void *); + int (*get_id)(const void *); + int (*get_max_packet_life_time)(const void *); + int (*get_max_retransmits)(const void *); + const char *(*get_protocol)(const void *); + bool (*is_negotiated)(const void *); + + godot_error (*poll)(void *); + void (*close)(void *); + + void *next; /* For extension? */ +} godot_net_webrtc_data_channel; + +/* Set the default GDNative library */ +godot_error GDAPI godot_net_set_webrtc_library(const godot_net_webrtc_library *); +/* Binds a WebRTCPeerConnectionGDNative to the provided interface */ +void GDAPI godot_net_bind_webrtc_peer_connection(godot_object *p_obj, const godot_net_webrtc_peer_connection *); +/* Binds a WebRTCDataChannelGDNative to the provided interface */ +void GDAPI godot_net_bind_webrtc_data_channel(godot_object *p_obj, const godot_net_webrtc_data_channel *); + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/modules/gdnative/nativescript/nativescript.cpp b/modules/gdnative/nativescript/nativescript.cpp index 04ba28dc68..f30c9da4c1 100644 --- a/modules/gdnative/nativescript/nativescript.cpp +++ b/modules/gdnative/nativescript/nativescript.cpp @@ -32,6 +32,7 @@ #include "gdnative/gdnative.h" +#include "core/core_string_names.h" #include "core/global_constants.h" #include "core/io/file_access_encrypted.h" #include "core/os/file_access.h" @@ -771,6 +772,27 @@ void NativeScriptInstance::notification(int p_notification) { call_multilevel("_notification", args, 1); } +String NativeScriptInstance::to_string(bool *r_valid) { + if (has_method(CoreStringNames::get_singleton()->_to_string)) { + Variant::CallError ce; + Variant ret = call(CoreStringNames::get_singleton()->_to_string, NULL, 0, ce); + if (ce.error == Variant::CallError::CALL_OK) { + if (ret.get_type() != Variant::STRING) { + if (r_valid) + *r_valid = false; + ERR_EXPLAIN("Wrong type for " + CoreStringNames::get_singleton()->_to_string + ", must be a String."); + ERR_FAIL_V(String()); + } + if (r_valid) + *r_valid = true; + return ret.operator String(); + } + } + if (r_valid) + *r_valid = false; + return String(); +} + void NativeScriptInstance::refcount_incremented() { Variant::CallError err; call("_refcount_incremented", NULL, 0, err); @@ -1345,7 +1367,7 @@ void *NativeScriptLanguage::get_instance_binding_data(int p_idx, Object *p_objec if (!(*binding_data)[p_idx]) { - const void *global_type_tag = global_type_tags[p_idx].get(p_object->get_class_name()); + const void *global_type_tag = get_global_type_tag(p_idx, p_object->get_class_name()); // no binding data yet, soooooo alloc new one \o/ (*binding_data).write[p_idx] = binding_functions[p_idx].second.alloc_instance_binding_data(binding_functions[p_idx].second.data, global_type_tag, (godot_object *)p_object); @@ -1454,6 +1476,9 @@ const void *NativeScriptLanguage::get_global_type_tag(int p_idx, StringName p_cl const HashMap<StringName, const void *> &tags = global_type_tags[p_idx]; + if (!tags.has(p_class_name)) + return NULL; + const void *tag = tags.get(p_class_name); return tag; diff --git a/modules/gdnative/nativescript/nativescript.h b/modules/gdnative/nativescript/nativescript.h index a6865c6243..be1c499714 100644 --- a/modules/gdnative/nativescript/nativescript.h +++ b/modules/gdnative/nativescript/nativescript.h @@ -208,6 +208,7 @@ public: virtual bool has_method(const StringName &p_method) const; virtual Variant call(const StringName &p_method, const Variant **p_args, int p_argcount, Variant::CallError &r_error); virtual void notification(int p_notification); + String to_string(bool *r_valid); virtual Ref<Script> get_script() const; virtual MultiplayerAPI::RPCMode get_rpc_mode(const StringName &p_method) const; virtual MultiplayerAPI::RPCMode get_rset_mode(const StringName &p_variable) const; diff --git a/modules/gdnative/net/webrtc_peer_gdnative.cpp b/modules/gdnative/net/webrtc_gdnative.cpp index 60b1ed4fe4..d77fa057c5 100644 --- a/modules/gdnative/net/webrtc_peer_gdnative.cpp +++ b/modules/gdnative/net/webrtc_gdnative.cpp @@ -1,5 +1,5 @@ /*************************************************************************/ -/* packet_peer_gdnative.cpp */ +/* webrtc_gdnative.cpp */ /*************************************************************************/ /* This file is part of: */ /* GODOT ENGINE */ @@ -32,14 +32,29 @@ #include "modules/gdnative/include/net/godot_net.h" #ifdef WEBRTC_GDNATIVE_ENABLED -#include "modules/webrtc/webrtc_peer_gdnative.h" +#include "modules/webrtc/webrtc_data_channel_gdnative.h" +#include "modules/webrtc/webrtc_peer_connection_gdnative.h" #endif extern "C" { -void GDAPI godot_net_bind_webrtc_peer(godot_object *p_obj, const godot_net_webrtc_peer *p_impl) { +void GDAPI godot_net_bind_webrtc_peer_connection(godot_object *p_obj, const godot_net_webrtc_peer_connection *p_impl) { #ifdef WEBRTC_GDNATIVE_ENABLED - ((WebRTCPeerGDNative *)p_obj)->set_native_webrtc_peer(p_impl); + ((WebRTCPeerConnectionGDNative *)p_obj)->set_native_webrtc_peer_connection(p_impl); +#endif +} + +void GDAPI godot_net_bind_webrtc_data_channel(godot_object *p_obj, const godot_net_webrtc_data_channel *p_impl) { +#ifdef WEBRTC_GDNATIVE_ENABLED + ((WebRTCDataChannelGDNative *)p_obj)->set_native_webrtc_data_channel(p_impl); +#endif +} + +godot_error GDAPI godot_net_set_webrtc_library(const godot_net_webrtc_library *p_lib) { +#ifdef WEBRTC_GDNATIVE_ENABLED + return (godot_error)WebRTCPeerConnectionGDNative::set_default_library(p_lib); +#else + return ERR_UNAVAILABLE; #endif } } diff --git a/modules/gdnative/pluginscript/pluginscript_instance.h b/modules/gdnative/pluginscript/pluginscript_instance.h index b279fdad8b..381c334231 100644 --- a/modules/gdnative/pluginscript/pluginscript_instance.h +++ b/modules/gdnative/pluginscript/pluginscript_instance.h @@ -62,7 +62,7 @@ public: virtual Variant call(const StringName &p_method, const Variant **p_args, int p_argcount, Variant::CallError &r_error); #if 0 // Rely on default implementations provided by ScriptInstance for the moment. - // Note that multilevel call could be removed in 3.0 release, so stay tunned + // Note that multilevel call could be removed in 3.0 release, so stay tuned // (see https://godotengine.org/qa/9244/can-override-the-_ready-and-_process-functions-child-classes) virtual void call_multilevel(const StringName& p_method,const Variant** p_args,int p_argcount); virtual void call_multilevel_reversed(const StringName& p_method,const Variant** p_args,int p_argcount); diff --git a/modules/gdscript/editor/gdscript_highlighter.cpp b/modules/gdscript/editor/gdscript_highlighter.cpp index 4f59b06ae6..060a9d6c91 100644 --- a/modules/gdscript/editor/gdscript_highlighter.cpp +++ b/modules/gdscript/editor/gdscript_highlighter.cpp @@ -330,7 +330,7 @@ Map<int, TextEdit::HighlighterInfo> GDScriptSyntaxHighlighter::_get_line_syntax_ return color_map; } -String GDScriptSyntaxHighlighter::get_name() { +String GDScriptSyntaxHighlighter::get_name() const { return "GDScript"; } diff --git a/modules/gdscript/editor/gdscript_highlighter.h b/modules/gdscript/editor/gdscript_highlighter.h index 9dc10a5d1b..9ba2c80552 100644 --- a/modules/gdscript/editor/gdscript_highlighter.h +++ b/modules/gdscript/editor/gdscript_highlighter.h @@ -65,7 +65,7 @@ public: virtual void _update_cache(); virtual Map<int, TextEdit::HighlighterInfo> _get_line_syntax_highlighting(int p_line); - virtual String get_name(); + virtual String get_name() const; virtual List<String> get_supported_languages(); }; diff --git a/modules/gdscript/gdscript.cpp b/modules/gdscript/gdscript.cpp index 33e99cb82f..3fb9268702 100644 --- a/modules/gdscript/gdscript.cpp +++ b/modules/gdscript/gdscript.cpp @@ -30,6 +30,7 @@ #include "gdscript.h" +#include "core/core_string_names.h" #include "core/engine.h" #include "core/global_constants.h" #include "core/io/file_access_encrypted.h" @@ -1064,7 +1065,7 @@ Variant::Type GDScriptInstance::get_property_type(const StringName &p_name, bool } void GDScriptInstance::get_property_list(List<PropertyInfo> *p_properties) const { - // exported members, not doen yet! + // exported members, not done yet! const GDScript *sptr = script.ptr(); List<PropertyInfo> props; @@ -1234,6 +1235,27 @@ void GDScriptInstance::notification(int p_notification) { } } +String GDScriptInstance::to_string(bool *r_valid) { + if (has_method(CoreStringNames::get_singleton()->_to_string)) { + Variant::CallError ce; + Variant ret = call(CoreStringNames::get_singleton()->_to_string, NULL, 0, ce); + if (ce.error == Variant::CallError::CALL_OK) { + if (ret.get_type() != Variant::STRING) { + if (r_valid) + *r_valid = false; + ERR_EXPLAIN("Wrong type for " + CoreStringNames::get_singleton()->_to_string + ", must be a String."); + ERR_FAIL_V(String()); + } + if (r_valid) + *r_valid = true; + return ret.operator String(); + } + } + if (r_valid) + *r_valid = false; + return String(); +} + Ref<Script> GDScriptInstance::get_script() const { return script; diff --git a/modules/gdscript/gdscript.h b/modules/gdscript/gdscript.h index 38009b878d..716f536e89 100644 --- a/modules/gdscript/gdscript.h +++ b/modules/gdscript/gdscript.h @@ -251,6 +251,7 @@ public: Variant debug_get_member_by_index(int p_idx) const { return members[p_idx]; } virtual void notification(int p_notification); + String to_string(bool *r_valid); virtual Ref<Script> get_script() const; diff --git a/modules/gdscript/gdscript_parser.cpp b/modules/gdscript/gdscript_parser.cpp index 903b3892d1..1c22c4af3c 100644 --- a/modules/gdscript/gdscript_parser.cpp +++ b/modules/gdscript/gdscript_parser.cpp @@ -5248,6 +5248,7 @@ void GDScriptParser::_determine_inheritance(ClassNode *p_class) { if (base_script.is_valid()) { String ident = base; + Ref<GDScript> find_subclass = base_script; for (int i = extend_iter; i < p_class->extends_class.size(); i++) { @@ -5257,7 +5258,7 @@ void GDScriptParser::_determine_inheritance(ClassNode *p_class) { if (base_script->get_subclasses().has(subclass)) { - base_script = base_script->get_subclasses()[subclass]; + find_subclass = base_script->get_subclasses()[subclass]; } else if (base_script->get_constants().has(subclass)) { Ref<GDScript> new_base_class = base_script->get_constants()[subclass]; @@ -5265,7 +5266,7 @@ void GDScriptParser::_determine_inheritance(ClassNode *p_class) { _set_error("Constant is not a class: " + ident, p_class->line); return; } - base_script = new_base_class; + find_subclass = new_base_class; } else { _set_error("Could not find subclass: " + ident, p_class->line); @@ -5273,7 +5274,7 @@ void GDScriptParser::_determine_inheritance(ClassNode *p_class) { } } - script = base_script; + script = find_subclass; } else if (!base_class) { @@ -7473,7 +7474,7 @@ void GDScriptParser::_check_class_level_types(ClassNode *p_class) { return; } - // Replace assignment with implict conversion + // Replace assignment with implicit conversion BuiltInFunctionNode *convert = alloc_node<BuiltInFunctionNode>(); convert->line = v.line; convert->function = GDScriptFunctions::TYPE_CONVERT; @@ -7837,14 +7838,14 @@ void GDScriptParser::_check_block_types(BlockNode *p_block) { if (_is_type_compatible(assign_type, lv->datatype)) { _mark_line_as_unsafe(lv->line); } else { - // Try implict conversion + // Try implicit conversion if (lv->datatype.kind != DataType::BUILTIN || !_is_type_compatible(lv->datatype, assign_type, true)) { _set_error("Assigned value type (" + assign_type.to_string() + ") doesn't match the variable's type (" + lv->datatype.to_string() + ").", lv->line); return; } - // Replace assignment with implict conversion + // Replace assignment with implicit conversion BuiltInFunctionNode *convert = alloc_node<BuiltInFunctionNode>(); convert->line = lv->line; convert->function = GDScriptFunctions::TYPE_CONVERT; @@ -7968,14 +7969,14 @@ void GDScriptParser::_check_block_types(BlockNode *p_block) { if (_is_type_compatible(rh_type, lh_type)) { _mark_line_as_unsafe(op->line); } else { - // Try implict conversion + // Try implicit conversion if (lh_type.kind != DataType::BUILTIN || !_is_type_compatible(lh_type, rh_type, true)) { _set_error("Assigned value type (" + rh_type.to_string() + ") doesn't match the variable's type (" + lh_type.to_string() + ").", op->line); return; } - // Replace assignment with implict conversion + // Replace assignment with implicit conversion BuiltInFunctionNode *convert = alloc_node<BuiltInFunctionNode>(); convert->line = op->line; convert->function = GDScriptFunctions::TYPE_CONVERT; diff --git a/modules/mono/csharp_script.cpp b/modules/mono/csharp_script.cpp index bfbd6ca80e..72199281ff 100644 --- a/modules/mono/csharp_script.cpp +++ b/modules/mono/csharp_script.cpp @@ -1855,6 +1855,34 @@ void CSharpInstance::_call_notification(int p_notification) { } } +String CSharpInstance::to_string(bool *r_valid) { + MonoObject *mono_object = get_mono_object(); + + if (mono_object == NULL) { + if (r_valid) + *r_valid = false; + return String(); + } + + MonoException *exc = NULL; + MonoString *result = GDMonoUtils::object_to_string(mono_object, &exc); + + if (exc) { + GDMonoUtils::set_pending_exception(exc); + if (r_valid) + *r_valid = false; + return String(); + } + + if (result == NULL) { + if (r_valid) + *r_valid = false; + return String(); + } + + return GDMonoMarshal::mono_string_to_godot(result); +} + Ref<Script> CSharpInstance::get_script() const { return script; diff --git a/modules/mono/csharp_script.h b/modules/mono/csharp_script.h index 298d55c4df..e735e0f741 100644 --- a/modules/mono/csharp_script.h +++ b/modules/mono/csharp_script.h @@ -261,6 +261,8 @@ public: virtual void notification(int p_notification); void _call_notification(int p_notification); + virtual String to_string(bool *r_valid); + virtual Ref<Script> get_script() const; virtual ScriptLanguage *get_language(); diff --git a/modules/mono/editor/bindings_generator.cpp b/modules/mono/editor/bindings_generator.cpp index a408716641..cd7774e7a1 100644 --- a/modules/mono/editor/bindings_generator.cpp +++ b/modules/mono/editor/bindings_generator.cpp @@ -2300,9 +2300,14 @@ void BindingsGenerator::_populate_object_type_interfaces() { if (method_info.name.empty()) continue; + String cname = method_info.name; + + if (blacklisted_methods.find(itype.cname) && blacklisted_methods[itype.cname].find(cname)) + continue; + MethodInterface imethod; imethod.name = method_info.name; - imethod.cname = imethod.name; + imethod.cname = cname; if (method_info.flags & METHOD_FLAG_VIRTUAL) imethod.is_virtual = true; @@ -2975,6 +2980,13 @@ void BindingsGenerator::_populate_global_constants() { } } +void BindingsGenerator::_initialize_blacklisted_methods() { + + blacklisted_methods["Object"].push_back("to_string"); // there is already ToString + blacklisted_methods["Object"].push_back("_to_string"); // override ToString instead + blacklisted_methods["Object"].push_back("_init"); // never called in C# (TODO: implement it) +} + void BindingsGenerator::_log(const char *p_format, ...) { if (log_print_enabled) { @@ -2992,6 +3004,8 @@ void BindingsGenerator::_initialize() { enum_types.clear(); + _initialize_blacklisted_methods(); + _populate_object_type_interfaces(); _populate_builtin_type_interfaces(); diff --git a/modules/mono/editor/bindings_generator.h b/modules/mono/editor/bindings_generator.h index bdba28c267..ffc73a7e3e 100644 --- a/modules/mono/editor/bindings_generator.h +++ b/modules/mono/editor/bindings_generator.h @@ -491,6 +491,10 @@ class BindingsGenerator { List<InternalCall> core_custom_icalls; List<InternalCall> editor_custom_icalls; + Map<StringName, List<StringName> > blacklisted_methods; + + void _initialize_blacklisted_methods(); + struct NameCache { StringName type_void; StringName type_Array; diff --git a/modules/mono/glue/Managed/Files/DynamicObject.cs b/modules/mono/glue/Managed/Files/DynamicObject.cs index 9860feafdd..a0f105d55e 100644 --- a/modules/mono/glue/Managed/Files/DynamicObject.cs +++ b/modules/mono/glue/Managed/Files/DynamicObject.cs @@ -202,7 +202,7 @@ namespace Godot //public override bool TryDeleteIndex(DeleteIndexBinder binder, object[] indexes); //public override bool TryDeleteMember(DeleteMemberBinder binder); - // Invokation on the object itself, e.g.: obj(param) + // Invocation on the object itself, e.g.: obj(param) //public override bool TryInvoke(InvokeBinder binder, object[] args, out object result); // No unnary operations to handle diff --git a/modules/mono/glue/Managed/Files/Extensions/NodeExtensions.cs b/modules/mono/glue/Managed/Files/Extensions/NodeExtensions.cs index 366d89b1c2..5023725f17 100644 --- a/modules/mono/glue/Managed/Files/Extensions/NodeExtensions.cs +++ b/modules/mono/glue/Managed/Files/Extensions/NodeExtensions.cs @@ -24,12 +24,12 @@ namespace Godot public T GetOwner<T>() where T : class { - return (T)(object)GetOwner(); + return (T)(object)Owner; } public T GetOwnerOrNull<T>() where T : class { - return GetOwner() as T; + return Owner as T; } public T GetParent<T>() where T : class diff --git a/modules/mono/glue/Managed/Files/MarshalUtils.cs b/modules/mono/glue/Managed/Files/MarshalUtils.cs index 730a1e1585..a1d63a62ef 100644 --- a/modules/mono/glue/Managed/Files/MarshalUtils.cs +++ b/modules/mono/glue/Managed/Files/MarshalUtils.cs @@ -23,7 +23,7 @@ namespace Godot /// <summary> /// Returns <see langword="true"/> if the generic type definition of <paramref name="type"/> - /// is <see cref="Godot.Collections.Dictionary{T}"/>; otherwise returns <see langword="false"/>. + /// is <see cref="Godot.Collections.Dictionary{TKey, TValue}"/>; otherwise returns <see langword="false"/>. /// </summary> /// <exception cref="System.InvalidOperationException"> /// <paramref name="type"/> is not a generic type. That is, IsGenericType returns false. @@ -45,6 +45,44 @@ namespace Godot valueType = genericArgs[1]; } + static bool GenericIEnumerableIsAssignableFromType(Type type) + { + if (type.IsGenericType && type.GetGenericTypeDefinition() == typeof(IEnumerable<>)) + return true; + + foreach (var interfaceType in type.GetInterfaces()) + { + if (interfaceType.IsGenericType && interfaceType.GetGenericTypeDefinition() == typeof(IEnumerable<>)) + return true; + } + + Type baseType = type.BaseType; + + if (baseType == null) + return false; + + return GenericIEnumerableIsAssignableFromType(baseType); + } + + static bool GenericIDictionaryIsAssignableFromType(Type type) + { + if (type.IsGenericType && type.GetGenericTypeDefinition() == typeof(IDictionary<,>)) + return true; + + foreach (var interfaceType in type.GetInterfaces()) + { + if (interfaceType.IsGenericType && interfaceType.GetGenericTypeDefinition() == typeof(IDictionary<,>)) + return true; + } + + Type baseType = type.BaseType; + + if (baseType == null) + return false; + + return GenericIDictionaryIsAssignableFromType(baseType); + } + static bool GenericIEnumerableIsAssignableFromType(Type type, out Type elementType) { if (type.IsGenericType && type.GetGenericTypeDefinition() == typeof(IEnumerable<>)) diff --git a/modules/mono/glue/Managed/IgnoredFiles/Node.cs b/modules/mono/glue/Managed/IgnoredFiles/Node.cs index 99ba0f827a..cff61b1e0b 100644 --- a/modules/mono/glue/Managed/IgnoredFiles/Node.cs +++ b/modules/mono/glue/Managed/IgnoredFiles/Node.cs @@ -15,9 +15,10 @@ namespace Godot throw new NotImplementedException(); } - public Node GetOwner() + public Node Owner { - throw new NotImplementedException(); + get => throw new NotImplementedException(); + set => throw new NotImplementedException(); } public Node GetParent() diff --git a/modules/mono/glue/collections_glue.cpp b/modules/mono/glue/collections_glue.cpp index 4aef5684fd..47239f1260 100644 --- a/modules/mono/glue/collections_glue.cpp +++ b/modules/mono/glue/collections_glue.cpp @@ -162,7 +162,7 @@ MonoObject *godot_icall_Dictionary_GetValue(Dictionary *ptr, MonoObject *key) { #ifdef DEBUG_ENABLED CRASH_COND(!exc); #endif - GDMonoUtils::runtime_object_init(exc); + GDMonoUtils::runtime_object_init(exc, CACHED_CLASS(KeyNotFoundException)); GDMonoUtils::set_pending_exception((MonoException *)exc); return NULL; } @@ -176,7 +176,7 @@ MonoObject *godot_icall_Dictionary_GetValue_Generic(Dictionary *ptr, MonoObject #ifdef DEBUG_ENABLED CRASH_COND(!exc); #endif - GDMonoUtils::runtime_object_init(exc); + GDMonoUtils::runtime_object_init(exc, CACHED_CLASS(KeyNotFoundException)); GDMonoUtils::set_pending_exception((MonoException *)exc); return NULL; } diff --git a/modules/mono/mono_gd/gd_mono_marshal.cpp b/modules/mono/mono_gd/gd_mono_marshal.cpp index 461dcf3ec0..c462b8f71d 100644 --- a/modules/mono/mono_gd/gd_mono_marshal.cpp +++ b/modules/mono/mono_gd/gd_mono_marshal.cpp @@ -161,8 +161,7 @@ Variant::Type managed_to_variant_type(const ManagedType &p_type) { MonoReflectionType *reftype = mono_type_get_object(SCRIPTS_DOMAIN, type_class->get_mono_type()); - MonoReflectionType *key_reftype, *value_reftype; - if (GDMonoUtils::Marshal::generic_idictionary_is_assignable_from(reftype, &key_reftype, &value_reftype)) { + if (GDMonoUtils::Marshal::generic_idictionary_is_assignable_from(reftype)) { return Variant::DICTIONARY; } @@ -170,8 +169,7 @@ Variant::Type managed_to_variant_type(const ManagedType &p_type) { return Variant::DICTIONARY; } - MonoReflectionType *elem_reftype; - if (GDMonoUtils::Marshal::generic_ienumerable_is_assignable_from(reftype, &elem_reftype)) { + if (GDMonoUtils::Marshal::generic_ienumerable_is_assignable_from(reftype)) { return Variant::ARRAY; } @@ -193,16 +191,14 @@ Variant::Type managed_to_variant_type(const ManagedType &p_type) { // The order in which we check the following interfaces is very important (dictionaries and generics first) - MonoReflectionType *key_reftype, *value_reftype; - if (GDMonoUtils::Marshal::generic_idictionary_is_assignable_from(reftype, &key_reftype, &value_reftype)) + if (GDMonoUtils::Marshal::generic_idictionary_is_assignable_from(reftype)) return Variant::DICTIONARY; if (p_type.type_class->implements_interface(CACHED_CLASS(System_Collections_IDictionary))) { return Variant::DICTIONARY; } - MonoReflectionType *elem_reftype; - if (GDMonoUtils::Marshal::generic_ienumerable_is_assignable_from(reftype, &elem_reftype)) + if (GDMonoUtils::Marshal::generic_ienumerable_is_assignable_from(reftype)) return Variant::ARRAY; if (p_type.type_class->implements_interface(CACHED_CLASS(System_Collections_IEnumerable))) { @@ -850,8 +846,7 @@ Variant mono_object_to_variant(MonoObject *p_obj) { MonoReflectionType *reftype = mono_type_get_object(SCRIPTS_DOMAIN, type_class->get_mono_type()); - MonoReflectionType *key_reftype, *value_reftype; - if (GDMonoUtils::Marshal::generic_idictionary_is_assignable_from(reftype, &key_reftype, &value_reftype)) { + if (GDMonoUtils::Marshal::generic_idictionary_is_assignable_from(reftype)) { return GDMonoUtils::Marshal::generic_idictionary_to_dictionary(p_obj); } @@ -859,8 +854,7 @@ Variant mono_object_to_variant(MonoObject *p_obj) { return GDMonoUtils::Marshal::idictionary_to_dictionary(p_obj); } - MonoReflectionType *elem_reftype; - if (GDMonoUtils::Marshal::generic_ienumerable_is_assignable_from(reftype, &elem_reftype)) { + if (GDMonoUtils::Marshal::generic_ienumerable_is_assignable_from(reftype)) { return GDMonoUtils::Marshal::enumerable_to_array(p_obj); } @@ -888,8 +882,7 @@ Variant mono_object_to_variant(MonoObject *p_obj) { // The order in which we check the following interfaces is very important (dictionaries and generics first) - MonoReflectionType *key_reftype, *value_reftype; - if (GDMonoUtils::Marshal::generic_idictionary_is_assignable_from(reftype, &key_reftype, &value_reftype)) { + if (GDMonoUtils::Marshal::generic_idictionary_is_assignable_from(reftype)) { return GDMonoUtils::Marshal::generic_idictionary_to_dictionary(p_obj); } @@ -897,8 +890,7 @@ Variant mono_object_to_variant(MonoObject *p_obj) { return GDMonoUtils::Marshal::idictionary_to_dictionary(p_obj); } - MonoReflectionType *elem_reftype; - if (GDMonoUtils::Marshal::generic_ienumerable_is_assignable_from(reftype, &elem_reftype)) { + if (GDMonoUtils::Marshal::generic_ienumerable_is_assignable_from(reftype)) { return GDMonoUtils::Marshal::enumerable_to_array(p_obj); } diff --git a/modules/mono/mono_gd/gd_mono_utils.cpp b/modules/mono/mono_gd/gd_mono_utils.cpp index 5236e43c90..413c8cba85 100644 --- a/modules/mono/mono_gd/gd_mono_utils.cpp +++ b/modules/mono/mono_gd/gd_mono_utils.cpp @@ -161,6 +161,8 @@ void MonoCache::clear_members() { methodthunk_MarshalUtils_GenericIEnumerableIsAssignableFromType = NULL; methodthunk_MarshalUtils_GenericIDictionaryIsAssignableFromType = NULL; + methodthunk_MarshalUtils_GenericIEnumerableIsAssignableFromType_with_info = NULL; + methodthunk_MarshalUtils_GenericIDictionaryIsAssignableFromType_with_info = NULL; methodthunk_MarshalUtils_MakeGenericArrayType = NULL; methodthunk_MarshalUtils_MakeGenericDictionaryType = NULL; @@ -282,8 +284,10 @@ void update_godot_api_cache() { CACHE_METHOD_THUNK_AND_CHECK(MarshalUtils, ArrayGetElementType, (ArrayGetElementType)GODOT_API_CLASS(MarshalUtils)->get_method_thunk("ArrayGetElementType", 2)); CACHE_METHOD_THUNK_AND_CHECK(MarshalUtils, DictionaryGetKeyValueTypes, (DictionaryGetKeyValueTypes)GODOT_API_CLASS(MarshalUtils)->get_method_thunk("DictionaryGetKeyValueTypes", 3)); - CACHE_METHOD_THUNK_AND_CHECK(MarshalUtils, GenericIEnumerableIsAssignableFromType, (GenericIEnumerableIsAssignableFromType)GODOT_API_CLASS(MarshalUtils)->get_method_thunk("GenericIEnumerableIsAssignableFromType", 2)); - CACHE_METHOD_THUNK_AND_CHECK(MarshalUtils, GenericIDictionaryIsAssignableFromType, (GenericIDictionaryIsAssignableFromType)GODOT_API_CLASS(MarshalUtils)->get_method_thunk("GenericIDictionaryIsAssignableFromType", 3)); + CACHE_METHOD_THUNK_AND_CHECK(MarshalUtils, GenericIEnumerableIsAssignableFromType, (GenericIEnumerableIsAssignableFromType)GODOT_API_CLASS(MarshalUtils)->get_method_thunk("GenericIEnumerableIsAssignableFromType", 1)); + CACHE_METHOD_THUNK_AND_CHECK(MarshalUtils, GenericIDictionaryIsAssignableFromType, (GenericIDictionaryIsAssignableFromType)GODOT_API_CLASS(MarshalUtils)->get_method_thunk("GenericIDictionaryIsAssignableFromType", 1)); + CACHE_METHOD_THUNK_AND_CHECK(MarshalUtils, GenericIEnumerableIsAssignableFromType_with_info, (GenericIEnumerableIsAssignableFromType_with_info)GODOT_API_CLASS(MarshalUtils)->get_method_thunk("GenericIEnumerableIsAssignableFromType", 2)); + CACHE_METHOD_THUNK_AND_CHECK(MarshalUtils, GenericIEnumerableIsAssignableFromType_with_info, (GenericIEnumerableIsAssignableFromType_with_info)GODOT_API_CLASS(MarshalUtils)->get_method_thunk("GenericIDictionaryIsAssignableFromType", 3)); CACHE_METHOD_THUNK_AND_CHECK(MarshalUtils, MakeGenericArrayType, (MakeGenericArrayType)GODOT_API_CLASS(MarshalUtils)->get_method_thunk("MakeGenericArrayType", 1)); CACHE_METHOD_THUNK_AND_CHECK(MarshalUtils, MakeGenericDictionaryType, (MakeGenericDictionaryType)GODOT_API_CLASS(MarshalUtils)->get_method_thunk("MakeGenericDictionaryType", 2)); @@ -300,7 +304,7 @@ void update_godot_api_cache() { // TODO Move to CSharpLanguage::init() and do handle disposal MonoObject *task_scheduler = mono_object_new(SCRIPTS_DOMAIN, GODOT_API_CLASS(GodotTaskScheduler)->get_mono_ptr()); - GDMonoUtils::runtime_object_init(task_scheduler); + GDMonoUtils::runtime_object_init(task_scheduler, GODOT_API_CLASS(GodotTaskScheduler)); mono_cache.task_scheduler_handle = MonoGCHandle::create_strong(task_scheduler); mono_cache.godot_api_cache_updated = true; @@ -401,11 +405,10 @@ MonoThread *get_current_thread() { return mono_thread_current(); } -void runtime_object_init(MonoObject *p_this_obj) { - GD_MONO_BEGIN_RUNTIME_INVOKE; - // FIXME: Do not use mono_runtime_object_init, it aborts if an exception is thrown - mono_runtime_object_init(p_this_obj); - GD_MONO_END_RUNTIME_INVOKE; +void runtime_object_init(MonoObject *p_this_obj, GDMonoClass *p_class, MonoException **r_exc) { + GDMonoMethod *ctor = p_class->get_method(".ctor", 0); + ERR_FAIL_NULL(ctor); + ctor->invoke_raw(p_this_obj, NULL, r_exc); } GDMonoClass *get_object_class(MonoObject *p_object) { @@ -467,7 +470,7 @@ MonoObject *create_managed_for_godot_object(GDMonoClass *p_class, const StringNa CACHED_FIELD(GodotObject, ptr)->set_value_raw(mono_object, p_object); // Construct - GDMonoUtils::runtime_object_init(mono_object); + GDMonoUtils::runtime_object_init(mono_object, p_class); return mono_object; } @@ -477,7 +480,7 @@ MonoObject *create_managed_from(const NodePath &p_from) { ERR_FAIL_NULL_V(mono_object, NULL); // Construct - GDMonoUtils::runtime_object_init(mono_object); + GDMonoUtils::runtime_object_init(mono_object, CACHED_CLASS(NodePath)); CACHED_FIELD(NodePath, ptr)->set_value_raw(mono_object, memnew(NodePath(p_from))); @@ -489,7 +492,7 @@ MonoObject *create_managed_from(const RID &p_from) { ERR_FAIL_NULL_V(mono_object, NULL); // Construct - GDMonoUtils::runtime_object_init(mono_object); + GDMonoUtils::runtime_object_init(mono_object, CACHED_CLASS(RID)); CACHED_FIELD(RID, ptr)->set_value_raw(mono_object, memnew(RID(p_from))); @@ -788,16 +791,32 @@ void dictionary_get_key_value_types(MonoReflectionType *p_dict_reftype, MonoRefl UNLIKELY_UNHANDLED_EXCEPTION(exc); } -MonoBoolean generic_ienumerable_is_assignable_from(MonoReflectionType *p_reftype, MonoReflectionType **r_elem_reftype) { +MonoBoolean generic_ienumerable_is_assignable_from(MonoReflectionType *p_reftype) { GenericIEnumerableIsAssignableFromType thunk = CACHED_METHOD_THUNK(MarshalUtils, GenericIEnumerableIsAssignableFromType); MonoException *exc = NULL; + MonoBoolean res = invoke_method_thunk(thunk, p_reftype, &exc); + UNLIKELY_UNHANDLED_EXCEPTION(exc); + return res; +} + +MonoBoolean generic_idictionary_is_assignable_from(MonoReflectionType *p_reftype) { + GenericIDictionaryIsAssignableFromType thunk = CACHED_METHOD_THUNK(MarshalUtils, GenericIDictionaryIsAssignableFromType); + MonoException *exc = NULL; + MonoBoolean res = invoke_method_thunk(thunk, p_reftype, &exc); + UNLIKELY_UNHANDLED_EXCEPTION(exc); + return res; +} + +MonoBoolean generic_ienumerable_is_assignable_from(MonoReflectionType *p_reftype, MonoReflectionType **r_elem_reftype) { + GenericIEnumerableIsAssignableFromType_with_info thunk = CACHED_METHOD_THUNK(MarshalUtils, GenericIEnumerableIsAssignableFromType_with_info); + MonoException *exc = NULL; MonoBoolean res = invoke_method_thunk(thunk, p_reftype, r_elem_reftype, &exc); UNLIKELY_UNHANDLED_EXCEPTION(exc); return res; } MonoBoolean generic_idictionary_is_assignable_from(MonoReflectionType *p_reftype, MonoReflectionType **r_key_reftype, MonoReflectionType **r_value_reftype) { - GenericIDictionaryIsAssignableFromType thunk = CACHED_METHOD_THUNK(MarshalUtils, GenericIDictionaryIsAssignableFromType); + GenericIDictionaryIsAssignableFromType_with_info thunk = CACHED_METHOD_THUNK(MarshalUtils, GenericIDictionaryIsAssignableFromType_with_info); MonoException *exc = NULL; MonoBoolean res = invoke_method_thunk(thunk, p_reftype, r_key_reftype, r_value_reftype, &exc); UNLIKELY_UNHANDLED_EXCEPTION(exc); diff --git a/modules/mono/mono_gd/gd_mono_utils.h b/modules/mono/mono_gd/gd_mono_utils.h index 081a8a9813..ee239be959 100644 --- a/modules/mono/mono_gd/gd_mono_utils.h +++ b/modules/mono/mono_gd/gd_mono_utils.h @@ -64,8 +64,10 @@ typedef MonoBoolean (*TypeIsGenericDictionary)(MonoReflectionType *, MonoExcepti typedef void (*ArrayGetElementType)(MonoReflectionType *, MonoReflectionType **, MonoException **); typedef void (*DictionaryGetKeyValueTypes)(MonoReflectionType *, MonoReflectionType **, MonoReflectionType **, MonoException **); -typedef MonoBoolean (*GenericIEnumerableIsAssignableFromType)(MonoReflectionType *, MonoReflectionType **, MonoException **); -typedef MonoBoolean (*GenericIDictionaryIsAssignableFromType)(MonoReflectionType *, MonoReflectionType **, MonoReflectionType **, MonoException **); +typedef MonoBoolean (*GenericIEnumerableIsAssignableFromType)(MonoReflectionType *, MonoException **); +typedef MonoBoolean (*GenericIDictionaryIsAssignableFromType)(MonoReflectionType *, MonoException **); +typedef MonoBoolean (*GenericIEnumerableIsAssignableFromType_with_info)(MonoReflectionType *, MonoReflectionType **, MonoException **); +typedef MonoBoolean (*GenericIDictionaryIsAssignableFromType_with_info)(MonoReflectionType *, MonoReflectionType **, MonoReflectionType **, MonoException **); typedef MonoReflectionType *(*MakeGenericArrayType)(MonoReflectionType *, MonoException **); typedef MonoReflectionType *(*MakeGenericDictionaryType)(MonoReflectionType *, MonoReflectionType *, MonoException **); @@ -82,6 +84,8 @@ MonoBoolean type_is_generic_dictionary(MonoReflectionType *p_reftype); void array_get_element_type(MonoReflectionType *p_array_reftype, MonoReflectionType **r_elem_reftype); void dictionary_get_key_value_types(MonoReflectionType *p_dict_reftype, MonoReflectionType **r_key_reftype, MonoReflectionType **r_value_reftype); +MonoBoolean generic_ienumerable_is_assignable_from(MonoReflectionType *p_reftype); +MonoBoolean generic_idictionary_is_assignable_from(MonoReflectionType *p_reftype); MonoBoolean generic_ienumerable_is_assignable_from(MonoReflectionType *p_reftype, MonoReflectionType **r_elem_reftype); MonoBoolean generic_idictionary_is_assignable_from(MonoReflectionType *p_reftype, MonoReflectionType **r_key_reftype, MonoReflectionType **r_value_reftype); @@ -197,6 +201,8 @@ struct MonoCache { GenericIEnumerableIsAssignableFromType methodthunk_MarshalUtils_GenericIEnumerableIsAssignableFromType; GenericIDictionaryIsAssignableFromType methodthunk_MarshalUtils_GenericIDictionaryIsAssignableFromType; + GenericIEnumerableIsAssignableFromType_with_info methodthunk_MarshalUtils_GenericIEnumerableIsAssignableFromType_with_info; + GenericIDictionaryIsAssignableFromType_with_info methodthunk_MarshalUtils_GenericIDictionaryIsAssignableFromType_with_info; MakeGenericArrayType methodthunk_MarshalUtils_MakeGenericArrayType; MakeGenericDictionaryType methodthunk_MarshalUtils_MakeGenericDictionaryType; @@ -249,7 +255,7 @@ _FORCE_INLINE_ bool is_main_thread() { return mono_domain_get() != NULL && mono_thread_get_main() == mono_thread_current(); } -void runtime_object_init(MonoObject *p_this_obj); +void runtime_object_init(MonoObject *p_this_obj, GDMonoClass *p_class, MonoException **r_exc = NULL); GDMonoClass *get_object_class(MonoObject *p_object); GDMonoClass *type_get_proxy_class(const StringName &p_type); diff --git a/modules/visual_script/visual_script.cpp b/modules/visual_script/visual_script.cpp index 581809fec9..8f311d11f4 100644 --- a/modules/visual_script/visual_script.cpp +++ b/modules/visual_script/visual_script.cpp @@ -30,6 +30,7 @@ #include "visual_script.h" +#include "core/core_string_names.h" #include "core/os/os.h" #include "core/project_settings.h" #include "scene/main/node.h" @@ -1976,6 +1977,27 @@ void VisualScriptInstance::notification(int p_notification) { call(VisualScriptLanguage::singleton->notification, &whatp, 1, ce); //do as call } +String VisualScriptInstance::to_string(bool *r_valid) { + if (has_method(CoreStringNames::get_singleton()->_to_string)) { + Variant::CallError ce; + Variant ret = call(CoreStringNames::get_singleton()->_to_string, NULL, 0, ce); + if (ce.error == Variant::CallError::CALL_OK) { + if (ret.get_type() != Variant::STRING) { + if (r_valid) + *r_valid = false; + ERR_EXPLAIN("Wrong type for " + CoreStringNames::get_singleton()->_to_string + ", must be a String."); + ERR_FAIL_V(String()); + } + if (r_valid) + *r_valid = true; + return ret.operator String(); + } + } + if (r_valid) + *r_valid = false; + return String(); +} + Ref<Script> VisualScriptInstance::get_script() const { return script; diff --git a/modules/visual_script/visual_script.h b/modules/visual_script/visual_script.h index 0171b8e6f1..91748d077b 100644 --- a/modules/visual_script/visual_script.h +++ b/modules/visual_script/visual_script.h @@ -405,6 +405,7 @@ public: virtual bool has_method(const StringName &p_method) const; virtual Variant call(const StringName &p_method, const Variant **p_args, int p_argcount, Variant::CallError &r_error); virtual void notification(int p_notification); + String to_string(bool *r_valid); bool set_variable(const StringName &p_variable, const Variant &p_value) { diff --git a/modules/visual_script/visual_script_editor.cpp b/modules/visual_script/visual_script_editor.cpp index 4f6828bf1c..6bbfb1ec5c 100644 --- a/modules/visual_script/visual_script_editor.cpp +++ b/modules/visual_script/visual_script_editor.cpp @@ -2041,7 +2041,7 @@ void VisualScriptEditor::set_edit_state(const Variant &p_state) { Dictionary d = p_state; if (d.has("function")) { - edited_func = p_state; + edited_func = d["function"]; selected = edited_func; } @@ -2218,7 +2218,7 @@ Control *VisualScriptEditor::get_edit_menu() { void VisualScriptEditor::_change_base_type() { - select_base_type->popup_create(true); + select_base_type->popup_create(true, true); } void VisualScriptEditor::clear_edit_menu() { @@ -2726,93 +2726,98 @@ void VisualScriptEditor::_selected_connect_node(const String &p_text, const Stri Ref<VisualScriptFunctionCall> vsfc = vsn; vsfc->set_function(p_text); - VisualScriptNode::TypeGuess tg = _guess_output_type(port_action_node, port_action_output, vn); - if (tg.type == Variant::OBJECT) { - vsfc->set_call_mode(VisualScriptFunctionCall::CALL_MODE_INSTANCE); - vsfc->set_base_type(String("")); - if (tg.gdclass != StringName()) { - vsfc->set_base_type(tg.gdclass); + if (p_connecting) { + VisualScriptNode::TypeGuess tg = _guess_output_type(port_action_node, port_action_output, vn); - } else if (script->get_node(edited_func, port_action_node).is_valid()) { - PropertyHint hint = script->get_node(edited_func, port_action_node)->get_output_value_port_info(port_action_output).hint; - String base_type = script->get_node(edited_func, port_action_node)->get_output_value_port_info(port_action_output).hint_string; + if (tg.type == Variant::OBJECT) { + vsfc->set_call_mode(VisualScriptFunctionCall::CALL_MODE_INSTANCE); + vsfc->set_base_type(String("")); + if (tg.gdclass != StringName()) { + vsfc->set_base_type(tg.gdclass); - if (base_type != String() && hint == PROPERTY_HINT_TYPE_STRING) { - vsfc->set_base_type(base_type); + } else if (script->get_node(edited_func, port_action_node).is_valid()) { + PropertyHint hint = script->get_node(edited_func, port_action_node)->get_output_value_port_info(port_action_output).hint; + String base_type = script->get_node(edited_func, port_action_node)->get_output_value_port_info(port_action_output).hint_string; + + if (base_type != String() && hint == PROPERTY_HINT_TYPE_STRING) { + vsfc->set_base_type(base_type); + } + if (p_text == "call" || p_text == "call_deferred") { + vsfc->set_function(String("")); + } } - if (p_text == "call" || p_text == "call_deferred") { - vsfc->set_function(String("")); + if (tg.script.is_valid()) { + vsfc->set_base_script(tg.script->get_path()); } + } else if (tg.type == Variant::NIL) { + vsfc->set_call_mode(VisualScriptFunctionCall::CALL_MODE_INSTANCE); + vsfc->set_base_type(String("")); + } else { + vsfc->set_call_mode(VisualScriptFunctionCall::CALL_MODE_BASIC_TYPE); + vsfc->set_basic_type(tg.type); } - if (tg.script.is_valid()) { - vsfc->set_base_script(tg.script->get_path()); - } - } else if (tg.type == Variant::NIL) { - vsfc->set_call_mode(VisualScriptFunctionCall::CALL_MODE_INSTANCE); - vsfc->set_base_type(String("")); - } else { - vsfc->set_call_mode(VisualScriptFunctionCall::CALL_MODE_BASIC_TYPE); - vsfc->set_basic_type(tg.type); } } - if (Object::cast_to<VisualScriptPropertySet>(vsn.ptr())) { + // if connecting from another node the call mode shouldn't be self + if (p_connecting) { + if (Object::cast_to<VisualScriptPropertySet>(vsn.ptr())) { + Ref<VisualScriptPropertySet> vsp = vsn; - Ref<VisualScriptPropertySet> vsp = vsn; - - VisualScriptNode::TypeGuess tg = _guess_output_type(port_action_node, port_action_output, vn); - if (tg.type == Variant::OBJECT) { - vsp->set_call_mode(VisualScriptPropertySet::CALL_MODE_INSTANCE); - vsp->set_base_type(String("")); - if (tg.gdclass != StringName()) { - vsp->set_base_type(tg.gdclass); + VisualScriptNode::TypeGuess tg = _guess_output_type(port_action_node, port_action_output, vn); + if (tg.type == Variant::OBJECT) { + vsp->set_call_mode(VisualScriptPropertySet::CALL_MODE_INSTANCE); + vsp->set_base_type(String("")); + if (tg.gdclass != StringName()) { + vsp->set_base_type(tg.gdclass); - } else if (script->get_node(edited_func, port_action_node).is_valid()) { - PropertyHint hint = script->get_node(edited_func, port_action_node)->get_output_value_port_info(port_action_output).hint; - String base_type = script->get_node(edited_func, port_action_node)->get_output_value_port_info(port_action_output).hint_string; + } else if (script->get_node(edited_func, port_action_node).is_valid()) { + PropertyHint hint = script->get_node(edited_func, port_action_node)->get_output_value_port_info(port_action_output).hint; + String base_type = script->get_node(edited_func, port_action_node)->get_output_value_port_info(port_action_output).hint_string; - if (base_type != String() && hint == PROPERTY_HINT_TYPE_STRING) { - vsp->set_base_type(base_type); + if (base_type != String() && hint == PROPERTY_HINT_TYPE_STRING) { + vsp->set_base_type(base_type); + } } + if (tg.script.is_valid()) { + vsp->set_base_script(tg.script->get_path()); + } + } else if (tg.type == Variant::NIL) { + vsp->set_call_mode(VisualScriptPropertySet::CALL_MODE_INSTANCE); + vsp->set_base_type(String("")); + } else { + vsp->set_call_mode(VisualScriptPropertySet::CALL_MODE_BASIC_TYPE); + vsp->set_basic_type(tg.type); } - if (tg.script.is_valid()) { - vsp->set_base_script(tg.script->get_path()); - } - } else if (tg.type == Variant::NIL) { - vsp->set_call_mode(VisualScriptPropertySet::CALL_MODE_INSTANCE); - vsp->set_base_type(String("")); - } else { - vsp->set_call_mode(VisualScriptPropertySet::CALL_MODE_BASIC_TYPE); - vsp->set_basic_type(tg.type); } - } - - if (Object::cast_to<VisualScriptPropertyGet>(vsn.ptr())) { - Ref<VisualScriptPropertyGet> vsp = vsn; - VisualScriptNode::TypeGuess tg = _guess_output_type(port_action_node, port_action_output, vn); - if (tg.type == Variant::OBJECT) { - vsp->set_call_mode(VisualScriptPropertyGet::CALL_MODE_INSTANCE); - vsp->set_base_type(String("")); - if (tg.gdclass != StringName()) { - vsp->set_base_type(tg.gdclass); + if (Object::cast_to<VisualScriptPropertyGet>(vsn.ptr())) { + Ref<VisualScriptPropertyGet> vsp = vsn; - } else if (script->get_node(edited_func, port_action_node).is_valid()) { - PropertyHint hint = script->get_node(edited_func, port_action_node)->get_output_value_port_info(port_action_output).hint; - String base_type = script->get_node(edited_func, port_action_node)->get_output_value_port_info(port_action_output).hint_string; - if (base_type != String() && hint == PROPERTY_HINT_TYPE_STRING) { - vsp->set_base_type(base_type); + VisualScriptNode::TypeGuess tg = _guess_output_type(port_action_node, port_action_output, vn); + if (tg.type == Variant::OBJECT) { + vsp->set_call_mode(VisualScriptPropertyGet::CALL_MODE_INSTANCE); + vsp->set_base_type(String("")); + if (tg.gdclass != StringName()) { + vsp->set_base_type(tg.gdclass); + + } else if (script->get_node(edited_func, port_action_node).is_valid()) { + PropertyHint hint = script->get_node(edited_func, port_action_node)->get_output_value_port_info(port_action_output).hint; + String base_type = script->get_node(edited_func, port_action_node)->get_output_value_port_info(port_action_output).hint_string; + if (base_type != String() && hint == PROPERTY_HINT_TYPE_STRING) { + vsp->set_base_type(base_type); + } } + if (tg.script.is_valid()) { + vsp->set_base_script(tg.script->get_path()); + } + } else if (tg.type == Variant::NIL) { + vsp->set_call_mode(VisualScriptPropertyGet::CALL_MODE_INSTANCE); + vsp->set_base_type(String("")); + } else { + vsp->set_call_mode(VisualScriptPropertyGet::CALL_MODE_BASIC_TYPE); + vsp->set_basic_type(tg.type); } - if (tg.script.is_valid()) { - vsp->set_base_script(tg.script->get_path()); - } - } else if (tg.type == Variant::NIL) { - vsp->set_call_mode(VisualScriptPropertyGet::CALL_MODE_INSTANCE); - vsp->set_base_type(String("")); - } else { - vsp->set_call_mode(VisualScriptPropertyGet::CALL_MODE_BASIC_TYPE); - vsp->set_basic_type(tg.type); } } Ref<VisualScriptNode> vnode_old = script->get_node(edited_func, port_action_node); diff --git a/modules/webrtc/config.py b/modules/webrtc/config.py index 5ed245bad2..2e3a18ad0e 100644 --- a/modules/webrtc/config.py +++ b/modules/webrtc/config.py @@ -6,7 +6,8 @@ def configure(env): def get_doc_classes(): return [ - "WebRTCPeer" + "WebRTCPeerConnection", + "WebRTCDataChannel" ] def get_doc_path(): diff --git a/modules/webrtc/doc_classes/WebRTCDataChannel.xml b/modules/webrtc/doc_classes/WebRTCDataChannel.xml new file mode 100644 index 0000000000..dcc14d4ddb --- /dev/null +++ b/modules/webrtc/doc_classes/WebRTCDataChannel.xml @@ -0,0 +1,95 @@ +<?xml version="1.0" encoding="UTF-8" ?> +<class name="WebRTCDataChannel" inherits="PacketPeer" category="Core" version="3.2"> + <brief_description> + </brief_description> + <description> + </description> + <tutorials> + </tutorials> + <methods> + <method name="close"> + <return type="void"> + </return> + <description> + </description> + </method> + <method name="get_id" qualifiers="const"> + <return type="int"> + </return> + <description> + </description> + </method> + <method name="get_label" qualifiers="const"> + <return type="String"> + </return> + <description> + </description> + </method> + <method name="get_max_packet_life_time" qualifiers="const"> + <return type="int"> + </return> + <description> + </description> + </method> + <method name="get_max_retransmits" qualifiers="const"> + <return type="int"> + </return> + <description> + </description> + </method> + <method name="get_protocol" qualifiers="const"> + <return type="String"> + </return> + <description> + </description> + </method> + <method name="get_ready_state" qualifiers="const"> + <return type="int" enum="WebRTCDataChannel.ChannelState"> + </return> + <description> + </description> + </method> + <method name="is_negotiated" qualifiers="const"> + <return type="bool"> + </return> + <description> + </description> + </method> + <method name="is_ordered" qualifiers="const"> + <return type="bool"> + </return> + <description> + </description> + </method> + <method name="poll"> + <return type="int" enum="Error"> + </return> + <description> + </description> + </method> + <method name="was_string_packet" qualifiers="const"> + <return type="bool"> + </return> + <description> + </description> + </method> + </methods> + <members> + <member name="write_mode" type="int" setter="set_write_mode" getter="get_write_mode" enum="WebRTCDataChannel.WriteMode"> + </member> + </members> + <constants> + <constant name="WRITE_MODE_TEXT" value="0" enum="WriteMode"> + </constant> + <constant name="WRITE_MODE_BINARY" value="1" enum="WriteMode"> + </constant> + <constant name="STATE_CONNECTING" value="0" enum="ChannelState"> + </constant> + <constant name="STATE_OPEN" value="1" enum="ChannelState"> + </constant> + <constant name="STATE_CLOSING" value="2" enum="ChannelState"> + </constant> + <constant name="STATE_CLOSED" value="3" enum="ChannelState"> + </constant> + </constants> +</class> diff --git a/modules/webrtc/doc_classes/WebRTCPeer.xml b/modules/webrtc/doc_classes/WebRTCPeerConnection.xml index 18d1345623..8b14c60deb 100644 --- a/modules/webrtc/doc_classes/WebRTCPeer.xml +++ b/modules/webrtc/doc_classes/WebRTCPeerConnection.xml @@ -1,5 +1,5 @@ <?xml version="1.0" encoding="UTF-8" ?> -<class name="WebRTCPeer" inherits="PacketPeer" category="Core" version="3.2"> +<class name="WebRTCPeerConnection" inherits="Reference" category="Core" version="3.2"> <brief_description> </brief_description> <description> @@ -19,6 +19,24 @@ <description> </description> </method> + <method name="close"> + <return type="void"> + </return> + <description> + </description> + </method> + <method name="create_data_channel"> + <return type="WebRTCDataChannel"> + </return> + <argument index="0" name="label" type="String"> + </argument> + <argument index="1" name="options" type="Dictionary" default="{ + +}"> + </argument> + <description> + </description> + </method> <method name="create_offer"> <return type="int" enum="Error"> </return> @@ -26,8 +44,18 @@ </description> </method> <method name="get_connection_state" qualifiers="const"> - <return type="int" enum="WebRTCPeer.ConnectionState"> + <return type="int" enum="WebRTCPeerConnection.ConnectionState"> + </return> + <description> + </description> + </method> + <method name="initialize"> + <return type="int" enum="Error"> </return> + <argument index="0" name="configuration" type="Dictionary" default="{ + +}"> + </argument> <description> </description> </method> @@ -57,19 +85,15 @@ <description> </description> </method> - <method name="was_string_packet" qualifiers="const"> - <return type="bool"> - </return> - <description> - </description> - </method> </methods> - <members> - <member name="write_mode" type="int" setter="set_write_mode" getter="get_write_mode" enum="WebRTCPeer.WriteMode"> - </member> - </members> <signals> - <signal name="new_ice_candidate"> + <signal name="data_channel_received"> + <argument index="0" name="channel" type="Object"> + </argument> + <description> + </description> + </signal> + <signal name="ice_candidate_created"> <argument index="0" name="media" type="String"> </argument> <argument index="1" name="index" type="int"> @@ -79,7 +103,7 @@ <description> </description> </signal> - <signal name="offer_created"> + <signal name="session_description_created"> <argument index="0" name="type" type="String"> </argument> <argument index="1" name="sdp" type="String"> @@ -89,10 +113,6 @@ </signal> </signals> <constants> - <constant name="WRITE_MODE_TEXT" value="0" enum="WriteMode"> - </constant> - <constant name="WRITE_MODE_BINARY" value="1" enum="WriteMode"> - </constant> <constant name="STATE_NEW" value="0" enum="ConnectionState"> </constant> <constant name="STATE_CONNECTING" value="1" enum="ConnectionState"> diff --git a/modules/webrtc/register_types.cpp b/modules/webrtc/register_types.cpp index ee7a766bd9..44e072cc89 100644 --- a/modules/webrtc/register_types.cpp +++ b/modules/webrtc/register_types.cpp @@ -5,8 +5,8 @@ /* GODOT ENGINE */ /* https://godotengine.org */ /*************************************************************************/ -/* Copyright (c) 2007-2018 Juan Linietsky, Ariel Manzur. */ -/* Copyright (c) 2014-2018 Godot Engine contributors (cf. AUTHORS.md) */ +/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ /* */ /* Permission is hereby granted, free of charge, to any person obtaining */ /* a copy of this software and associated documentation files (the */ @@ -29,27 +29,31 @@ /*************************************************************************/ #include "register_types.h" -#include "webrtc_peer.h" +#include "webrtc_data_channel.h" +#include "webrtc_peer_connection.h" #ifdef JAVASCRIPT_ENABLED #include "emscripten.h" -#include "webrtc_peer_js.h" +#include "webrtc_peer_connection_js.h" #endif #ifdef WEBRTC_GDNATIVE_ENABLED -#include "webrtc_peer_gdnative.h" +#include "webrtc_data_channel_gdnative.h" +#include "webrtc_peer_connection_gdnative.h" #endif void register_webrtc_types() { #ifdef JAVASCRIPT_ENABLED - WebRTCPeerJS::make_default(); + WebRTCPeerConnectionJS::make_default(); #elif defined(WEBRTC_GDNATIVE_ENABLED) - WebRTCPeerGDNative::make_default(); + WebRTCPeerConnectionGDNative::make_default(); #endif - ClassDB::register_custom_instance_class<WebRTCPeer>(); + ClassDB::register_custom_instance_class<WebRTCPeerConnection>(); #ifdef WEBRTC_GDNATIVE_ENABLED - ClassDB::register_class<WebRTCPeerGDNative>(); + ClassDB::register_class<WebRTCPeerConnectionGDNative>(); + ClassDB::register_class<WebRTCDataChannelGDNative>(); #endif + ClassDB::register_virtual_class<WebRTCDataChannel>(); } void unregister_webrtc_types() {} diff --git a/modules/webrtc/register_types.h b/modules/webrtc/register_types.h index 18a5dcc5aa..4923547a95 100644 --- a/modules/webrtc/register_types.h +++ b/modules/webrtc/register_types.h @@ -5,8 +5,8 @@ /* GODOT ENGINE */ /* https://godotengine.org */ /*************************************************************************/ -/* Copyright (c) 2007-2018 Juan Linietsky, Ariel Manzur. */ -/* Copyright (c) 2014-2018 Godot Engine contributors (cf. AUTHORS.md) */ +/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ /* */ /* Permission is hereby granted, free of charge, to any person obtaining */ /* a copy of this software and associated documentation files (the */ diff --git a/modules/webrtc/webrtc_data_channel.cpp b/modules/webrtc/webrtc_data_channel.cpp new file mode 100644 index 0000000000..2bd30e68f5 --- /dev/null +++ b/modules/webrtc/webrtc_data_channel.cpp @@ -0,0 +1,64 @@ +/*************************************************************************/ +/* webrtc_data_channel.cpp */ +/*************************************************************************/ +/* This file is part of: */ +/* GODOT ENGINE */ +/* https://godotengine.org */ +/*************************************************************************/ +/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ +/* */ +/* Permission is hereby granted, free of charge, to any person obtaining */ +/* a copy of this software and associated documentation files (the */ +/* "Software"), to deal in the Software without restriction, including */ +/* without limitation the rights to use, copy, modify, merge, publish, */ +/* distribute, sublicense, and/or sell copies of the Software, and to */ +/* permit persons to whom the Software is furnished to do so, subject to */ +/* the following conditions: */ +/* */ +/* The above copyright notice and this permission notice shall be */ +/* included in all copies or substantial portions of the Software. */ +/* */ +/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */ +/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */ +/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/ +/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */ +/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */ +/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */ +/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ +/*************************************************************************/ + +#include "webrtc_data_channel.h" + +void WebRTCDataChannel::_bind_methods() { + ClassDB::bind_method(D_METHOD("poll"), &WebRTCDataChannel::poll); + ClassDB::bind_method(D_METHOD("close"), &WebRTCDataChannel::close); + + ClassDB::bind_method(D_METHOD("was_string_packet"), &WebRTCDataChannel::was_string_packet); + ClassDB::bind_method(D_METHOD("set_write_mode", "write_mode"), &WebRTCDataChannel::set_write_mode); + ClassDB::bind_method(D_METHOD("get_write_mode"), &WebRTCDataChannel::get_write_mode); + ClassDB::bind_method(D_METHOD("get_ready_state"), &WebRTCDataChannel::get_ready_state); + ClassDB::bind_method(D_METHOD("get_label"), &WebRTCDataChannel::get_label); + ClassDB::bind_method(D_METHOD("is_ordered"), &WebRTCDataChannel::is_ordered); + ClassDB::bind_method(D_METHOD("get_id"), &WebRTCDataChannel::get_id); + ClassDB::bind_method(D_METHOD("get_max_packet_life_time"), &WebRTCDataChannel::get_max_packet_life_time); + ClassDB::bind_method(D_METHOD("get_max_retransmits"), &WebRTCDataChannel::get_max_retransmits); + ClassDB::bind_method(D_METHOD("get_protocol"), &WebRTCDataChannel::get_protocol); + ClassDB::bind_method(D_METHOD("is_negotiated"), &WebRTCDataChannel::is_negotiated); + + ADD_PROPERTY(PropertyInfo(Variant::INT, "write_mode", PROPERTY_HINT_ENUM), "set_write_mode", "get_write_mode"); + + BIND_ENUM_CONSTANT(WRITE_MODE_TEXT); + BIND_ENUM_CONSTANT(WRITE_MODE_BINARY); + + BIND_ENUM_CONSTANT(STATE_CONNECTING); + BIND_ENUM_CONSTANT(STATE_OPEN); + BIND_ENUM_CONSTANT(STATE_CLOSING); + BIND_ENUM_CONSTANT(STATE_CLOSED); +} + +WebRTCDataChannel::WebRTCDataChannel() { +} + +WebRTCDataChannel::~WebRTCDataChannel() { +} diff --git a/modules/webrtc/webrtc_peer.h b/modules/webrtc/webrtc_data_channel.h index e141c14655..0b161da784 100644 --- a/modules/webrtc/webrtc_peer.h +++ b/modules/webrtc/webrtc_data_channel.h @@ -1,12 +1,12 @@ /*************************************************************************/ -/* webrtc_peer.h */ +/* webrtc_data_channel.h */ /*************************************************************************/ /* This file is part of: */ /* GODOT ENGINE */ /* https://godotengine.org */ /*************************************************************************/ -/* Copyright (c) 2007-2018 Juan Linietsky, Ariel Manzur. */ -/* Copyright (c) 2014-2018 Godot Engine contributors (cf. AUTHORS.md) */ +/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ /* */ /* Permission is hereby granted, free of charge, to any person obtaining */ /* a copy of this software and associated documentation files (the */ @@ -28,13 +28,13 @@ /* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /*************************************************************************/ -#ifndef WEBRTC_PEER_H -#define WEBRTC_PEER_H +#ifndef WEBRTC_DATA_CHANNEL_H +#define WEBRTC_DATA_CHANNEL_H #include "core/io/packet_peer.h" -class WebRTCPeer : public PacketPeer { - GDCLASS(WebRTCPeer, PacketPeer); +class WebRTCDataChannel : public PacketPeer { + GDCLASS(WebRTCDataChannel, PacketPeer); public: enum WriteMode { @@ -42,30 +42,32 @@ public: WRITE_MODE_BINARY, }; - enum ConnectionState { - STATE_NEW, + enum ChannelState { STATE_CONNECTING, - STATE_CONNECTED, - STATE_DISCONNECTED, - STATE_FAILED, + STATE_OPEN, + STATE_CLOSING, STATE_CLOSED }; protected: static void _bind_methods(); - static WebRTCPeer *(*_create)(); public: virtual void set_write_mode(WriteMode mode) = 0; virtual WriteMode get_write_mode() const = 0; virtual bool was_string_packet() const = 0; - virtual ConnectionState get_connection_state() const = 0; - virtual Error create_offer() = 0; - virtual Error set_remote_description(String type, String sdp) = 0; - virtual Error set_local_description(String type, String sdp) = 0; - virtual Error add_ice_candidate(String sdpMidName, int sdpMlineIndexName, String sdpName) = 0; + virtual ChannelState get_ready_state() const = 0; + virtual String get_label() const = 0; + virtual bool is_ordered() const = 0; + virtual int get_id() const = 0; + virtual int get_max_packet_life_time() const = 0; + virtual int get_max_retransmits() const = 0; + virtual String get_protocol() const = 0; + virtual bool is_negotiated() const = 0; + virtual Error poll() = 0; + virtual void close() = 0; /** Inherited from PacketPeer: **/ virtual int get_available_packet_count() const = 0; @@ -74,13 +76,10 @@ public: virtual int get_max_packet_size() const = 0; - static Ref<WebRTCPeer> create_ref(); - static WebRTCPeer *create(); - - WebRTCPeer(); - ~WebRTCPeer(); + WebRTCDataChannel(); + ~WebRTCDataChannel(); }; -VARIANT_ENUM_CAST(WebRTCPeer::WriteMode); -VARIANT_ENUM_CAST(WebRTCPeer::ConnectionState); -#endif // WEBRTC_PEER_H +VARIANT_ENUM_CAST(WebRTCDataChannel::WriteMode); +VARIANT_ENUM_CAST(WebRTCDataChannel::ChannelState); +#endif // WEBRTC_DATA_CHANNEL_H diff --git a/modules/webrtc/webrtc_peer_gdnative.cpp b/modules/webrtc/webrtc_data_channel_gdnative.cpp index f782944980..4f33491af2 100644 --- a/modules/webrtc/webrtc_peer_gdnative.cpp +++ b/modules/webrtc/webrtc_data_channel_gdnative.cpp @@ -1,12 +1,12 @@ /*************************************************************************/ -/* webrtc_peer_gdnative.cpp */ +/* webrtc_data_channel_gdnative.cpp */ /*************************************************************************/ /* This file is part of: */ /* GODOT ENGINE */ /* https://godotengine.org */ /*************************************************************************/ -/* Copyright (c) 2007-2018 Juan Linietsky, Ariel Manzur. */ -/* Copyright (c) 2014-2018 Godot Engine contributors (cf. AUTHORS.md) */ +/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ /* */ /* Permission is hereby granted, free of charge, to any person obtaining */ /* a copy of this software and associated documentation files (the */ @@ -30,84 +30,106 @@ #ifdef WEBRTC_GDNATIVE_ENABLED -#include "webrtc_peer_gdnative.h" +#include "webrtc_data_channel_gdnative.h" +#include "core/io/resource_loader.h" +#include "modules/gdnative/nativescript/nativescript.h" -void WebRTCPeerGDNative::_bind_methods() { +void WebRTCDataChannelGDNative::_bind_methods() { } -WebRTCPeerGDNative::WebRTCPeerGDNative() { +WebRTCDataChannelGDNative::WebRTCDataChannelGDNative() { interface = NULL; } -WebRTCPeerGDNative::~WebRTCPeerGDNative() { +WebRTCDataChannelGDNative::~WebRTCDataChannelGDNative() { } -Error WebRTCPeerGDNative::create_offer() { +Error WebRTCDataChannelGDNative::poll() { ERR_FAIL_COND_V(interface == NULL, ERR_UNCONFIGURED); - return (Error)interface->create_offer(interface->data); + return (Error)interface->poll(interface->data); } -Error WebRTCPeerGDNative::set_local_description(String p_type, String p_sdp) { - ERR_FAIL_COND_V(interface == NULL, ERR_UNCONFIGURED); - return (Error)interface->set_local_description(interface->data, p_type.utf8().get_data(), p_sdp.utf8().get_data()); +void WebRTCDataChannelGDNative::close() { + ERR_FAIL_COND(interface == NULL); + interface->close(interface->data); } -Error WebRTCPeerGDNative::set_remote_description(String p_type, String p_sdp) { - ERR_FAIL_COND_V(interface == NULL, ERR_UNCONFIGURED); - return (Error)interface->set_remote_description(interface->data, p_type.utf8().get_data(), p_sdp.utf8().get_data()); +void WebRTCDataChannelGDNative::set_write_mode(WriteMode p_mode) { + ERR_FAIL_COND(interface == NULL); + interface->set_write_mode(interface->data, p_mode); } -Error WebRTCPeerGDNative::add_ice_candidate(String sdpMidName, int sdpMlineIndexName, String sdpName) { - ERR_FAIL_COND_V(interface == NULL, ERR_UNCONFIGURED); - return (Error)interface->add_ice_candidate(interface->data, sdpMidName.utf8().get_data(), sdpMlineIndexName, sdpName.utf8().get_data()); +WebRTCDataChannel::WriteMode WebRTCDataChannelGDNative::get_write_mode() const { + ERR_FAIL_COND_V(interface == NULL, WRITE_MODE_BINARY); + return (WriteMode)interface->get_write_mode(interface->data); } -Error WebRTCPeerGDNative::poll() { - ERR_FAIL_COND_V(interface == NULL, ERR_UNCONFIGURED); - return (Error)interface->poll(interface->data); +bool WebRTCDataChannelGDNative::was_string_packet() const { + ERR_FAIL_COND_V(interface == NULL, false); + return interface->was_string_packet(interface->data); } -void WebRTCPeerGDNative::set_write_mode(WriteMode p_mode) { - ERR_FAIL_COND(interface == NULL); - interface->set_write_mode(interface->data, p_mode); +WebRTCDataChannel::ChannelState WebRTCDataChannelGDNative::get_ready_state() const { + ERR_FAIL_COND_V(interface == NULL, STATE_CLOSED); + return (ChannelState)interface->get_ready_state(interface->data); } -WebRTCPeer::WriteMode WebRTCPeerGDNative::get_write_mode() const { - ERR_FAIL_COND_V(interface == NULL, WRITE_MODE_BINARY); - return (WriteMode)interface->get_write_mode(interface->data); +String WebRTCDataChannelGDNative::get_label() const { + ERR_FAIL_COND_V(interface == NULL, ""); + return String(interface->get_label(interface->data)); } -bool WebRTCPeerGDNative::was_string_packet() const { +bool WebRTCDataChannelGDNative::is_ordered() const { ERR_FAIL_COND_V(interface == NULL, false); - return interface->was_string_packet(interface->data); + return interface->is_ordered(interface->data); } -WebRTCPeer::ConnectionState WebRTCPeerGDNative::get_connection_state() const { - ERR_FAIL_COND_V(interface == NULL, STATE_DISCONNECTED); - return STATE_DISCONNECTED; +int WebRTCDataChannelGDNative::get_id() const { + ERR_FAIL_COND_V(interface == NULL, -1); + return interface->get_id(interface->data); +} + +int WebRTCDataChannelGDNative::get_max_packet_life_time() const { + ERR_FAIL_COND_V(interface == NULL, -1); + return interface->get_max_packet_life_time(interface->data); +} + +int WebRTCDataChannelGDNative::get_max_retransmits() const { + ERR_FAIL_COND_V(interface == NULL, -1); + return interface->get_max_retransmits(interface->data); +} + +String WebRTCDataChannelGDNative::get_protocol() const { + ERR_FAIL_COND_V(interface == NULL, ""); + return String(interface->get_protocol(interface->data)); +} + +bool WebRTCDataChannelGDNative::is_negotiated() const { + ERR_FAIL_COND_V(interface == NULL, false); + return interface->is_negotiated(interface->data); } -Error WebRTCPeerGDNative::get_packet(const uint8_t **r_buffer, int &r_buffer_size) { +Error WebRTCDataChannelGDNative::get_packet(const uint8_t **r_buffer, int &r_buffer_size) { ERR_FAIL_COND_V(interface == NULL, ERR_UNCONFIGURED); return (Error)interface->get_packet(interface->data, r_buffer, &r_buffer_size); } -Error WebRTCPeerGDNative::put_packet(const uint8_t *p_buffer, int p_buffer_size) { +Error WebRTCDataChannelGDNative::put_packet(const uint8_t *p_buffer, int p_buffer_size) { ERR_FAIL_COND_V(interface == NULL, ERR_UNCONFIGURED); return (Error)interface->put_packet(interface->data, p_buffer, p_buffer_size); } -int WebRTCPeerGDNative::get_max_packet_size() const { +int WebRTCDataChannelGDNative::get_max_packet_size() const { ERR_FAIL_COND_V(interface == NULL, 0); return interface->get_max_packet_size(interface->data); } -int WebRTCPeerGDNative::get_available_packet_count() const { +int WebRTCDataChannelGDNative::get_available_packet_count() const { ERR_FAIL_COND_V(interface == NULL, 0); return interface->get_available_packet_count(interface->data); } -void WebRTCPeerGDNative::set_native_webrtc_peer(const godot_net_webrtc_peer *p_impl) { +void WebRTCDataChannelGDNative::set_native_webrtc_data_channel(const godot_net_webrtc_data_channel *p_impl) { interface = p_impl; } diff --git a/modules/webrtc/webrtc_peer_gdnative.h b/modules/webrtc/webrtc_data_channel_gdnative.h index 6786cec8ea..3685f86353 100644 --- a/modules/webrtc/webrtc_peer_gdnative.h +++ b/modules/webrtc/webrtc_data_channel_gdnative.h @@ -1,12 +1,12 @@ /*************************************************************************/ -/* webrtc_peer_gdnative.h */ +/* webrtc_data_channel_gdnative.h */ /*************************************************************************/ /* This file is part of: */ /* GODOT ENGINE */ /* https://godotengine.org */ /*************************************************************************/ -/* Copyright (c) 2007-2018 Juan Linietsky, Ariel Manzur. */ -/* Copyright (c) 2014-2018 Godot Engine contributors (cf. AUTHORS.md) */ +/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ /* */ /* Permission is hereby granted, free of charge, to any person obtaining */ /* a copy of this software and associated documentation files (the */ @@ -30,37 +30,39 @@ #ifdef WEBRTC_GDNATIVE_ENABLED -#ifndef WEBRTC_PEER_GDNATIVE_H -#define WEBRTC_PEER_GDNATIVE_H +#ifndef WEBRTC_DATA_CHANNEL_GDNATIVE_H +#define WEBRTC_DATA_CHANNEL_GDNATIVE_H #include "modules/gdnative/include/net/godot_net.h" -#include "webrtc_peer.h" +#include "webrtc_data_channel.h" -class WebRTCPeerGDNative : public WebRTCPeer { - GDCLASS(WebRTCPeerGDNative, WebRTCPeer); +class WebRTCDataChannelGDNative : public WebRTCDataChannel { + GDCLASS(WebRTCDataChannelGDNative, WebRTCDataChannel); protected: static void _bind_methods(); private: - const godot_net_webrtc_peer *interface; + const godot_net_webrtc_data_channel *interface; public: - static WebRTCPeer *_create() { return memnew(WebRTCPeerGDNative); } - static void make_default() { WebRTCPeer::_create = WebRTCPeerGDNative::_create; } - - void set_native_webrtc_peer(const godot_net_webrtc_peer *p_impl); + void set_native_webrtc_data_channel(const godot_net_webrtc_data_channel *p_impl); virtual void set_write_mode(WriteMode mode); virtual WriteMode get_write_mode() const; virtual bool was_string_packet() const; - virtual ConnectionState get_connection_state() const; - virtual Error create_offer(); - virtual Error set_remote_description(String type, String sdp); - virtual Error set_local_description(String type, String sdp); - virtual Error add_ice_candidate(String sdpMidName, int sdpMlineIndexName, String sdpName); + virtual ChannelState get_ready_state() const; + virtual String get_label() const; + virtual bool is_ordered() const; + virtual int get_id() const; + virtual int get_max_packet_life_time() const; + virtual int get_max_retransmits() const; + virtual String get_protocol() const; + virtual bool is_negotiated() const; + virtual Error poll(); + virtual void close(); /** Inherited from PacketPeer: **/ virtual int get_available_packet_count() const; @@ -69,10 +71,10 @@ public: virtual int get_max_packet_size() const; - WebRTCPeerGDNative(); - ~WebRTCPeerGDNative(); + WebRTCDataChannelGDNative(); + ~WebRTCDataChannelGDNative(); }; -#endif // WEBRTC_PEER_GDNATIVE_H +#endif // WEBRTC_DATA_CHANNEL_GDNATIVE_H #endif // WEBRTC_GDNATIVE_ENABLED diff --git a/modules/webrtc/webrtc_data_channel_js.cpp b/modules/webrtc/webrtc_data_channel_js.cpp new file mode 100644 index 0000000000..2e7c64aa72 --- /dev/null +++ b/modules/webrtc/webrtc_data_channel_js.cpp @@ -0,0 +1,352 @@ +/*************************************************************************/ +/* webrtc_data_channel_js.cpp */ +/*************************************************************************/ +/* This file is part of: */ +/* GODOT ENGINE */ +/* https://godotengine.org */ +/*************************************************************************/ +/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ +/* */ +/* Permission is hereby granted, free of charge, to any person obtaining */ +/* a copy of this software and associated documentation files (the */ +/* "Software"), to deal in the Software without restriction, including */ +/* without limitation the rights to use, copy, modify, merge, publish, */ +/* distribute, sublicense, and/or sell copies of the Software, and to */ +/* permit persons to whom the Software is furnished to do so, subject to */ +/* the following conditions: */ +/* */ +/* The above copyright notice and this permission notice shall be */ +/* included in all copies or substantial portions of the Software. */ +/* */ +/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */ +/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */ +/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/ +/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */ +/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */ +/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */ +/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ +/*************************************************************************/ + +#ifdef JAVASCRIPT_ENABLED + +#include "webrtc_data_channel_js.h" +#include "emscripten.h" + +extern "C" { +EMSCRIPTEN_KEEPALIVE void _emrtc_on_ch_error(void *obj) { + WebRTCDataChannelJS *peer = static_cast<WebRTCDataChannelJS *>(obj); + peer->_on_error(); +} + +EMSCRIPTEN_KEEPALIVE void _emrtc_on_ch_open(void *obj) { + WebRTCDataChannelJS *peer = static_cast<WebRTCDataChannelJS *>(obj); + peer->_on_open(); +} + +EMSCRIPTEN_KEEPALIVE void _emrtc_on_ch_close(void *obj) { + WebRTCDataChannelJS *peer = static_cast<WebRTCDataChannelJS *>(obj); + peer->_on_close(); +} + +EMSCRIPTEN_KEEPALIVE void _emrtc_on_ch_message(void *obj, uint8_t *p_data, uint32_t p_size, bool p_is_string) { + WebRTCDataChannelJS *peer = static_cast<WebRTCDataChannelJS *>(obj); + peer->_on_message(p_data, p_size, p_is_string); +} +} + +void WebRTCDataChannelJS::_on_open() { + in_buffer.resize(16); +} + +void WebRTCDataChannelJS::_on_close() { + close(); +} + +void WebRTCDataChannelJS::_on_error() { + close(); +} + +void WebRTCDataChannelJS::_on_message(uint8_t *p_data, uint32_t p_size, bool p_is_string) { + if (in_buffer.space_left() < p_size + 5) { + ERR_EXPLAIN("Buffer full! Dropping data"); + ERR_FAIL(); + } + + uint8_t is_string = p_is_string ? 1 : 0; + in_buffer.write((uint8_t *)&p_size, 4); + in_buffer.write((uint8_t *)&is_string, 1); + in_buffer.write(p_data, p_size); + queue_count++; +} + +void WebRTCDataChannelJS::close() { + in_buffer.resize(0); + queue_count = 0; + _was_string = false; + /* clang-format off */ + EM_ASM({ + var dict = Module.IDHandler.get($0); + if (!dict) return; + var channel = dict["channel"]; + channel.onopen = null; + channel.onclose = null; + channel.onerror = null; + channel.onmessage = null; + channel.close(); + }, _js_id); + /* clang-format on */ +} + +Error WebRTCDataChannelJS::poll() { + return OK; +} + +WebRTCDataChannelJS::ChannelState WebRTCDataChannelJS::get_ready_state() const { + /* clang-format off */ + return (ChannelState) EM_ASM_INT({ + var dict = Module.IDHandler.get($0); + if (!dict) return 3; // CLOSED + var channel = dict["channel"]; + switch(channel.readyState) { + case "connecting": + return 0; + case "open": + return 1; + case "closing": + return 2; + case "closed": + return 3; + } + return 3; // CLOSED + }, _js_id); + /* clang-format on */ +} + +int WebRTCDataChannelJS::get_available_packet_count() const { + return queue_count; +} + +Error WebRTCDataChannelJS::get_packet(const uint8_t **r_buffer, int &r_buffer_size) { + ERR_FAIL_COND_V(get_ready_state() != STATE_OPEN, ERR_UNCONFIGURED); + + if (queue_count == 0) + return ERR_UNAVAILABLE; + + uint32_t to_read = 0; + uint32_t left = 0; + uint8_t is_string = 0; + r_buffer_size = 0; + + in_buffer.read((uint8_t *)&to_read, 4); + --queue_count; + left = in_buffer.data_left(); + + if (left < to_read + 1) { + in_buffer.advance_read(left); + return FAILED; + } + + in_buffer.read(&is_string, 1); + _was_string = is_string == 1; + in_buffer.read(packet_buffer, to_read); + *r_buffer = packet_buffer; + r_buffer_size = to_read; + + return OK; +} + +Error WebRTCDataChannelJS::put_packet(const uint8_t *p_buffer, int p_buffer_size) { + ERR_FAIL_COND_V(get_ready_state() != STATE_OPEN, ERR_UNCONFIGURED); + + int is_bin = _write_mode == WebRTCDataChannel::WRITE_MODE_BINARY ? 1 : 0; + + /* clang-format off */ + EM_ASM({ + var dict = Module.IDHandler.get($0); + var channel = dict["channel"]; + var bytes_array = new Uint8Array($2); + var i = 0; + + for(i=0; i<$2; i++) { + bytes_array[i] = getValue($1+i, 'i8'); + } + + if ($3) { + channel.send(bytes_array.buffer); + } else { + var string = new TextDecoder("utf-8").decode(bytes_array); + channel.send(string); + } + }, _js_id, p_buffer, p_buffer_size, is_bin); + /* clang-format on */ + + return OK; +} + +int WebRTCDataChannelJS::get_max_packet_size() const { + return 1200; +} + +void WebRTCDataChannelJS::set_write_mode(WriteMode p_mode) { + _write_mode = p_mode; +} + +WebRTCDataChannel::WriteMode WebRTCDataChannelJS::get_write_mode() const { + return _write_mode; +} + +bool WebRTCDataChannelJS::was_string_packet() const { + return _was_string; +} + +String WebRTCDataChannelJS::get_label() const { + return _label; +} + +/* clang-format off */ +#define _JS_GET(PROP) \ +EM_ASM_INT({ \ + var dict = Module.IDHandler.get($0); \ + if (!dict || !dict["channel"]) { \ + return 0; \ + }; \ + return dict["channel"].PROP; \ +}, _js_id) +/* clang-format on */ + +bool WebRTCDataChannelJS::is_ordered() const { + return _JS_GET(ordered); +} + +int WebRTCDataChannelJS::get_id() const { + return _JS_GET(id); +} + +int WebRTCDataChannelJS::get_max_packet_life_time() const { + return _JS_GET(maxPacketLifeTime); +} + +int WebRTCDataChannelJS::get_max_retransmits() const { + return _JS_GET(maxRetransmits); +} + +String WebRTCDataChannelJS::get_protocol() const { + return _protocol; +} + +bool WebRTCDataChannelJS::is_negotiated() const { + return _JS_GET(negotiated); +} + +WebRTCDataChannelJS::WebRTCDataChannelJS() { + queue_count = 0; + _was_string = false; + _write_mode = WRITE_MODE_BINARY; + _js_id = 0; +} + +WebRTCDataChannelJS::WebRTCDataChannelJS(int js_id) { + queue_count = 0; + _was_string = false; + _write_mode = WRITE_MODE_BINARY; + _js_id = js_id; + + /* clang-format off */ + EM_ASM({ + var c_ptr = $0; + var dict = Module.IDHandler.get($1); + if (!dict) return; + var channel = dict["channel"]; + dict["ptr"] = c_ptr; + + channel.binaryType = "arraybuffer"; + channel.onopen = function (evt) { + ccall("_emrtc_on_ch_open", + "void", + ["number"], + [c_ptr] + ); + }; + channel.onclose = function (evt) { + ccall("_emrtc_on_ch_close", + "void", + ["number"], + [c_ptr] + ); + }; + channel.onerror = function (evt) { + ccall("_emrtc_on_ch_error", + "void", + ["number"], + [c_ptr] + ); + }; + channel.onmessage = function(event) { + var buffer; + var is_string = 0; + if (event.data instanceof ArrayBuffer) { + buffer = new Uint8Array(event.data); + } else if (event.data instanceof Blob) { + console.error("Blob type not supported"); + return; + } else if (typeof event.data === "string") { + is_string = 1; + var enc = new TextEncoder("utf-8"); + buffer = new Uint8Array(enc.encode(event.data)); + } else { + console.error("Unknown message type"); + return; + } + var len = buffer.length*buffer.BYTES_PER_ELEMENT; + var out = Module._malloc(len); + Module.HEAPU8.set(buffer, out); + ccall("_emrtc_on_ch_message", + "void", + ["number", "number", "number", "number"], + [c_ptr, out, len, is_string] + ); + Module._free(out); + } + + }, this, js_id); + // Parse label + char *str; + str = (char *)EM_ASM_INT({ + var dict = Module.IDHandler.get($0); + if (!dict || !dict["channel"]) return 0; + var str = dict["channel"].label; + var len = lengthBytesUTF8(str)+1; + var ptr = _malloc(str); + stringToUTF8(str, ptr, len+1); + return ptr; + }, js_id); + if(str != NULL) { + _label.parse_utf8(str); + EM_ASM({ _free($0) }, str); + } + str = (char *)EM_ASM_INT({ + var dict = Module.IDHandler.get($0); + if (!dict || !dict["channel"]) return 0; + var str = dict["channel"].protocol; + var len = lengthBytesUTF8(str)+1; + var ptr = _malloc(str); + stringToUTF8(str, ptr, len+1); + return ptr; + }, js_id); + if(str != NULL) { + _protocol.parse_utf8(str); + EM_ASM({ _free($0) }, str); + } + /* clang-format on */ +} + +WebRTCDataChannelJS::~WebRTCDataChannelJS() { + close(); + /* clang-format off */ + EM_ASM({ + Module.IDHandler.remove($0); + }, _js_id); + /* clang-format on */ +}; +#endif diff --git a/modules/webrtc/webrtc_peer_js.h b/modules/webrtc/webrtc_data_channel_js.h index 02f0c9b55d..b87f8e9326 100644 --- a/modules/webrtc/webrtc_peer_js.h +++ b/modules/webrtc/webrtc_data_channel_js.h @@ -1,12 +1,12 @@ /*************************************************************************/ -/* webrtc_peer_js.h */ +/* webrtc_data_channel_js.h */ /*************************************************************************/ /* This file is part of: */ /* GODOT ENGINE */ /* https://godotengine.org */ /*************************************************************************/ -/* Copyright (c) 2007-2018 Juan Linietsky, Ariel Manzur. */ -/* Copyright (c) 2014-2018 Godot Engine contributors (cf. AUTHORS.md) */ +/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ /* */ /* Permission is hereby granted, free of charge, to any person obtaining */ /* a copy of this software and associated documentation files (the */ @@ -28,43 +28,53 @@ /* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /*************************************************************************/ -#ifndef WEBRTC_PEER_JS_H -#define WEBRTC_PEER_JS_H - #ifdef JAVASCRIPT_ENABLED -#include "webrtc_peer.h" +#ifndef WEBRTC_DATA_CHANNEL_JS_H +#define WEBRTC_DATA_CHANNEL_JS_H + +#include "webrtc_data_channel.h" -class WebRTCPeerJS : public WebRTCPeer { +class WebRTCDataChannelJS : public WebRTCDataChannel { + GDCLASS(WebRTCDataChannelJS, WebRTCDataChannel); private: - enum { - PACKET_BUFFER_SIZE = 65536 - 5 // 4 bytes for the size, 1 for for type - }; + String _label; + String _protocol; bool _was_string; WriteMode _write_mode; + enum { + PACKET_BUFFER_SIZE = 65536 - 5 // 4 bytes for the size, 1 for for type + }; + int _js_id; RingBuffer<uint8_t> in_buffer; int queue_count; uint8_t packet_buffer[PACKET_BUFFER_SIZE]; - ConnectionState _conn_state; public: - static WebRTCPeer *_create() { return memnew(WebRTCPeerJS); } - static void make_default() { WebRTCPeer::_create = WebRTCPeerJS::_create; } + void _on_open(); + void _on_close(); + void _on_error(); + void _on_message(uint8_t *p_data, uint32_t p_size, bool p_is_string); virtual void set_write_mode(WriteMode mode); virtual WriteMode get_write_mode() const; virtual bool was_string_packet() const; - virtual ConnectionState get_connection_state() const; - virtual Error create_offer(); - virtual Error set_remote_description(String type, String sdp); - virtual Error set_local_description(String type, String sdp); - virtual Error add_ice_candidate(String sdpMidName, int sdpMlineIndexName, String sdpName); + virtual ChannelState get_ready_state() const; + virtual String get_label() const; + virtual bool is_ordered() const; + virtual int get_id() const; + virtual int get_max_packet_life_time() const; + virtual int get_max_retransmits() const; + virtual String get_protocol() const; + virtual bool is_negotiated() const; + virtual Error poll(); + virtual void close(); /** Inherited from PacketPeer: **/ virtual int get_available_packet_count() const; @@ -73,16 +83,11 @@ public: virtual int get_max_packet_size() const; - void close(); - void _on_open(); - void _on_close(); - void _on_error(); - void _on_message(uint8_t *p_data, uint32_t p_size, bool p_is_string); - - WebRTCPeerJS(); - ~WebRTCPeerJS(); + WebRTCDataChannelJS(); + WebRTCDataChannelJS(int js_id); + ~WebRTCDataChannelJS(); }; -#endif +#endif // WEBRTC_DATA_CHANNEL_JS_H -#endif // WEBRTC_PEER_JS_H +#endif // JAVASCRIPT_ENABLED diff --git a/modules/webrtc/webrtc_peer.cpp b/modules/webrtc/webrtc_peer_connection.cpp index 30c4505df9..69c7a51a40 100644 --- a/modules/webrtc/webrtc_peer.cpp +++ b/modules/webrtc/webrtc_peer_connection.cpp @@ -1,12 +1,12 @@ /*************************************************************************/ -/* webrtc_peer.cpp */ +/* webrtc_peer_connection.cpp */ /*************************************************************************/ /* This file is part of: */ /* GODOT ENGINE */ /* https://godotengine.org */ /*************************************************************************/ -/* Copyright (c) 2007-2018 Juan Linietsky, Ariel Manzur. */ -/* Copyright (c) 2014-2018 Godot Engine contributors (cf. AUTHORS.md) */ +/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ /* */ /* Permission is hereby granted, free of charge, to any person obtaining */ /* a copy of this software and associated documentation files (the */ @@ -28,43 +28,37 @@ /* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /*************************************************************************/ -#include "webrtc_peer.h" +#include "webrtc_peer_connection.h" -WebRTCPeer *(*WebRTCPeer::_create)() = NULL; +WebRTCPeerConnection *(*WebRTCPeerConnection::_create)() = NULL; -Ref<WebRTCPeer> WebRTCPeer::create_ref() { +Ref<WebRTCPeerConnection> WebRTCPeerConnection::create_ref() { - if (!_create) - return Ref<WebRTCPeer>(); - return Ref<WebRTCPeer>(_create()); + return create(); } -WebRTCPeer *WebRTCPeer::create() { +WebRTCPeerConnection *WebRTCPeerConnection::create() { if (!_create) return NULL; return _create(); } -void WebRTCPeer::_bind_methods() { - ClassDB::bind_method(D_METHOD("create_offer"), &WebRTCPeer::create_offer); - ClassDB::bind_method(D_METHOD("set_local_description", "type", "sdp"), &WebRTCPeer::set_local_description); - ClassDB::bind_method(D_METHOD("set_remote_description", "type", "sdp"), &WebRTCPeer::set_remote_description); - ClassDB::bind_method(D_METHOD("poll"), &WebRTCPeer::poll); - ClassDB::bind_method(D_METHOD("add_ice_candidate", "media", "index", "name"), &WebRTCPeer::add_ice_candidate); - - ClassDB::bind_method(D_METHOD("was_string_packet"), &WebRTCPeer::was_string_packet); - ClassDB::bind_method(D_METHOD("set_write_mode", "write_mode"), &WebRTCPeer::set_write_mode); - ClassDB::bind_method(D_METHOD("get_write_mode"), &WebRTCPeer::get_write_mode); - ClassDB::bind_method(D_METHOD("get_connection_state"), &WebRTCPeer::get_connection_state); - - ADD_SIGNAL(MethodInfo("offer_created", PropertyInfo(Variant::STRING, "type"), PropertyInfo(Variant::STRING, "sdp"))); - ADD_SIGNAL(MethodInfo("new_ice_candidate", PropertyInfo(Variant::STRING, "media"), PropertyInfo(Variant::INT, "index"), PropertyInfo(Variant::STRING, "name"))); +void WebRTCPeerConnection::_bind_methods() { + ClassDB::bind_method(D_METHOD("initialize", "configuration"), &WebRTCPeerConnection::initialize, DEFVAL(Dictionary())); + ClassDB::bind_method(D_METHOD("create_data_channel", "label", "options"), &WebRTCPeerConnection::create_data_channel, DEFVAL(Dictionary())); + ClassDB::bind_method(D_METHOD("create_offer"), &WebRTCPeerConnection::create_offer); + ClassDB::bind_method(D_METHOD("set_local_description", "type", "sdp"), &WebRTCPeerConnection::set_local_description); + ClassDB::bind_method(D_METHOD("set_remote_description", "type", "sdp"), &WebRTCPeerConnection::set_remote_description); + ClassDB::bind_method(D_METHOD("add_ice_candidate", "media", "index", "name"), &WebRTCPeerConnection::add_ice_candidate); + ClassDB::bind_method(D_METHOD("poll"), &WebRTCPeerConnection::poll); + ClassDB::bind_method(D_METHOD("close"), &WebRTCPeerConnection::close); - ADD_PROPERTY(PropertyInfo(Variant::INT, "write_mode", PROPERTY_HINT_ENUM), "set_write_mode", "get_write_mode"); + ClassDB::bind_method(D_METHOD("get_connection_state"), &WebRTCPeerConnection::get_connection_state); - BIND_ENUM_CONSTANT(WRITE_MODE_TEXT); - BIND_ENUM_CONSTANT(WRITE_MODE_BINARY); + ADD_SIGNAL(MethodInfo("session_description_created", PropertyInfo(Variant::STRING, "type"), PropertyInfo(Variant::STRING, "sdp"))); + ADD_SIGNAL(MethodInfo("ice_candidate_created", PropertyInfo(Variant::STRING, "media"), PropertyInfo(Variant::INT, "index"), PropertyInfo(Variant::STRING, "name"))); + ADD_SIGNAL(MethodInfo("data_channel_received", PropertyInfo(Variant::OBJECT, "channel"))); BIND_ENUM_CONSTANT(STATE_NEW); BIND_ENUM_CONSTANT(STATE_CONNECTING); @@ -74,8 +68,8 @@ void WebRTCPeer::_bind_methods() { BIND_ENUM_CONSTANT(STATE_CLOSED); } -WebRTCPeer::WebRTCPeer() { +WebRTCPeerConnection::WebRTCPeerConnection() { } -WebRTCPeer::~WebRTCPeer() { +WebRTCPeerConnection::~WebRTCPeerConnection() { } diff --git a/modules/webrtc/webrtc_peer_connection.h b/modules/webrtc/webrtc_peer_connection.h new file mode 100644 index 0000000000..7be1390dab --- /dev/null +++ b/modules/webrtc/webrtc_peer_connection.h @@ -0,0 +1,74 @@ +/*************************************************************************/ +/* webrtc_peer_connection.h */ +/*************************************************************************/ +/* This file is part of: */ +/* GODOT ENGINE */ +/* https://godotengine.org */ +/*************************************************************************/ +/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ +/* */ +/* Permission is hereby granted, free of charge, to any person obtaining */ +/* a copy of this software and associated documentation files (the */ +/* "Software"), to deal in the Software without restriction, including */ +/* without limitation the rights to use, copy, modify, merge, publish, */ +/* distribute, sublicense, and/or sell copies of the Software, and to */ +/* permit persons to whom the Software is furnished to do so, subject to */ +/* the following conditions: */ +/* */ +/* The above copyright notice and this permission notice shall be */ +/* included in all copies or substantial portions of the Software. */ +/* */ +/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */ +/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */ +/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/ +/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */ +/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */ +/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */ +/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ +/*************************************************************************/ + +#ifndef WEBRTC_PEER_CONNECTION_H +#define WEBRTC_PEER_CONNECTION_H + +#include "core/io/packet_peer.h" +#include "modules/webrtc/webrtc_data_channel.h" + +class WebRTCPeerConnection : public Reference { + GDCLASS(WebRTCPeerConnection, Reference); + +public: + enum ConnectionState { + STATE_NEW, + STATE_CONNECTING, + STATE_CONNECTED, + STATE_DISCONNECTED, + STATE_FAILED, + STATE_CLOSED + }; + +protected: + static void _bind_methods(); + static WebRTCPeerConnection *(*_create)(); + +public: + virtual ConnectionState get_connection_state() const = 0; + + virtual Error initialize(Dictionary p_config = Dictionary()) = 0; + virtual Ref<WebRTCDataChannel> create_data_channel(String p_label, Dictionary p_options = Dictionary()) = 0; + virtual Error create_offer() = 0; + virtual Error set_remote_description(String type, String sdp) = 0; + virtual Error set_local_description(String type, String sdp) = 0; + virtual Error add_ice_candidate(String sdpMidName, int sdpMlineIndexName, String sdpName) = 0; + virtual Error poll() = 0; + virtual void close() = 0; + + static Ref<WebRTCPeerConnection> create_ref(); + static WebRTCPeerConnection *create(); + + WebRTCPeerConnection(); + ~WebRTCPeerConnection(); +}; + +VARIANT_ENUM_CAST(WebRTCPeerConnection::ConnectionState); +#endif // WEBRTC_PEER_CONNECTION_H diff --git a/modules/webrtc/webrtc_peer_connection_gdnative.cpp b/modules/webrtc/webrtc_peer_connection_gdnative.cpp new file mode 100644 index 0000000000..af98aa750a --- /dev/null +++ b/modules/webrtc/webrtc_peer_connection_gdnative.cpp @@ -0,0 +1,124 @@ +/*************************************************************************/ +/* webrtc_peer_connection_gdnative.cpp */ +/*************************************************************************/ +/* This file is part of: */ +/* GODOT ENGINE */ +/* https://godotengine.org */ +/*************************************************************************/ +/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ +/* */ +/* Permission is hereby granted, free of charge, to any person obtaining */ +/* a copy of this software and associated documentation files (the */ +/* "Software"), to deal in the Software without restriction, including */ +/* without limitation the rights to use, copy, modify, merge, publish, */ +/* distribute, sublicense, and/or sell copies of the Software, and to */ +/* permit persons to whom the Software is furnished to do so, subject to */ +/* the following conditions: */ +/* */ +/* The above copyright notice and this permission notice shall be */ +/* included in all copies or substantial portions of the Software. */ +/* */ +/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */ +/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */ +/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/ +/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */ +/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */ +/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */ +/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ +/*************************************************************************/ + +#ifdef WEBRTC_GDNATIVE_ENABLED + +#include "webrtc_peer_connection_gdnative.h" + +#include "core/io/resource_loader.h" +#include "modules/gdnative/nativescript/nativescript.h" +#include "webrtc_data_channel_gdnative.h" + +const godot_net_webrtc_library *WebRTCPeerConnectionGDNative::default_library = NULL; + +Error WebRTCPeerConnectionGDNative::set_default_library(const godot_net_webrtc_library *p_lib) { + if (default_library) { + const godot_net_webrtc_library *old = default_library; + default_library = NULL; + old->unregistered(); + } + default_library = p_lib; + return OK; // Maybe add version check and fail accordingly +} + +WebRTCPeerConnection *WebRTCPeerConnectionGDNative::_create() { + + WebRTCPeerConnectionGDNative *obj = memnew(WebRTCPeerConnectionGDNative); + ERR_EXPLAIN("Default GDNative WebRTC implementation not defined."); + ERR_FAIL_COND_V(!default_library, obj); + + // Call GDNative constructor + Error err = (Error)default_library->create_peer_connection(obj); + ERR_EXPLAIN("GDNative default library constructor returned an error"); + ERR_FAIL_COND_V(err != OK, obj); + + return obj; +} + +void WebRTCPeerConnectionGDNative::_bind_methods() { +} + +WebRTCPeerConnectionGDNative::WebRTCPeerConnectionGDNative() { + interface = NULL; +} + +WebRTCPeerConnectionGDNative::~WebRTCPeerConnectionGDNative() { +} + +Error WebRTCPeerConnectionGDNative::initialize(Dictionary p_config) { + ERR_FAIL_COND_V(interface == NULL, ERR_UNCONFIGURED); + return (Error)interface->initialize(interface->data, (const godot_dictionary *)&p_config); +} + +Ref<WebRTCDataChannel> WebRTCPeerConnectionGDNative::create_data_channel(String p_label, Dictionary p_options) { + ERR_FAIL_COND_V(interface == NULL, NULL); + return (WebRTCDataChannel *)interface->create_data_channel(interface->data, p_label.utf8().get_data(), (const godot_dictionary *)&p_options); +} + +Error WebRTCPeerConnectionGDNative::create_offer() { + ERR_FAIL_COND_V(interface == NULL, ERR_UNCONFIGURED); + return (Error)interface->create_offer(interface->data); +} + +Error WebRTCPeerConnectionGDNative::set_local_description(String p_type, String p_sdp) { + ERR_FAIL_COND_V(interface == NULL, ERR_UNCONFIGURED); + return (Error)interface->set_local_description(interface->data, p_type.utf8().get_data(), p_sdp.utf8().get_data()); +} + +Error WebRTCPeerConnectionGDNative::set_remote_description(String p_type, String p_sdp) { + ERR_FAIL_COND_V(interface == NULL, ERR_UNCONFIGURED); + return (Error)interface->set_remote_description(interface->data, p_type.utf8().get_data(), p_sdp.utf8().get_data()); +} + +Error WebRTCPeerConnectionGDNative::add_ice_candidate(String sdpMidName, int sdpMlineIndexName, String sdpName) { + ERR_FAIL_COND_V(interface == NULL, ERR_UNCONFIGURED); + return (Error)interface->add_ice_candidate(interface->data, sdpMidName.utf8().get_data(), sdpMlineIndexName, sdpName.utf8().get_data()); +} + +Error WebRTCPeerConnectionGDNative::poll() { + ERR_FAIL_COND_V(interface == NULL, ERR_UNCONFIGURED); + return (Error)interface->poll(interface->data); +} + +void WebRTCPeerConnectionGDNative::close() { + ERR_FAIL_COND(interface == NULL); + interface->close(interface->data); +} + +WebRTCPeerConnection::ConnectionState WebRTCPeerConnectionGDNative::get_connection_state() const { + ERR_FAIL_COND_V(interface == NULL, STATE_DISCONNECTED); + return (ConnectionState)interface->get_connection_state(interface->data); +} + +void WebRTCPeerConnectionGDNative::set_native_webrtc_peer_connection(const godot_net_webrtc_peer_connection *p_impl) { + interface = p_impl; +} + +#endif // WEBRTC_GDNATIVE_ENABLED diff --git a/modules/webrtc/webrtc_peer_connection_gdnative.h b/modules/webrtc/webrtc_peer_connection_gdnative.h new file mode 100644 index 0000000000..0a281c3d89 --- /dev/null +++ b/modules/webrtc/webrtc_peer_connection_gdnative.h @@ -0,0 +1,73 @@ +/*************************************************************************/ +/* webrtc_peer_connection_gdnative.h */ +/*************************************************************************/ +/* This file is part of: */ +/* GODOT ENGINE */ +/* https://godotengine.org */ +/*************************************************************************/ +/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ +/* */ +/* Permission is hereby granted, free of charge, to any person obtaining */ +/* a copy of this software and associated documentation files (the */ +/* "Software"), to deal in the Software without restriction, including */ +/* without limitation the rights to use, copy, modify, merge, publish, */ +/* distribute, sublicense, and/or sell copies of the Software, and to */ +/* permit persons to whom the Software is furnished to do so, subject to */ +/* the following conditions: */ +/* */ +/* The above copyright notice and this permission notice shall be */ +/* included in all copies or substantial portions of the Software. */ +/* */ +/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */ +/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */ +/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/ +/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */ +/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */ +/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */ +/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ +/*************************************************************************/ + +#ifdef WEBRTC_GDNATIVE_ENABLED + +#ifndef WEBRTC_PEER_CONNECTION_GDNATIVE_H +#define WEBRTC_PEER_CONNECTION_GDNATIVE_H + +#include "modules/gdnative/include/net/godot_net.h" +#include "webrtc_peer_connection.h" + +class WebRTCPeerConnectionGDNative : public WebRTCPeerConnection { + GDCLASS(WebRTCPeerConnectionGDNative, WebRTCPeerConnection); + +protected: + static void _bind_methods(); + static WebRTCPeerConnection *_create(); + +private: + static const godot_net_webrtc_library *default_library; + const godot_net_webrtc_peer_connection *interface; + +public: + static Error set_default_library(const godot_net_webrtc_library *p_library); + static void make_default() { WebRTCPeerConnection::_create = WebRTCPeerConnectionGDNative::_create; } + + void set_native_webrtc_peer_connection(const godot_net_webrtc_peer_connection *p_impl); + + virtual ConnectionState get_connection_state() const; + + virtual Error initialize(Dictionary p_config = Dictionary()); + virtual Ref<WebRTCDataChannel> create_data_channel(String p_label, Dictionary p_options = Dictionary()); + virtual Error create_offer(); + virtual Error set_remote_description(String type, String sdp); + virtual Error set_local_description(String type, String sdp); + virtual Error add_ice_candidate(String sdpMidName, int sdpMlineIndexName, String sdpName); + virtual Error poll(); + virtual void close(); + + WebRTCPeerConnectionGDNative(); + ~WebRTCPeerConnectionGDNative(); +}; + +#endif // WEBRTC_PEER_CONNECTION_GDNATIVE_H + +#endif // WEBRTC_GDNATIVE_ENABLED diff --git a/modules/webrtc/webrtc_peer_connection_js.cpp b/modules/webrtc/webrtc_peer_connection_js.cpp new file mode 100644 index 0000000000..9758ab3644 --- /dev/null +++ b/modules/webrtc/webrtc_peer_connection_js.cpp @@ -0,0 +1,314 @@ +/*************************************************************************/ +/* webrtc_peer_connection_js.cpp */ +/*************************************************************************/ +/* This file is part of: */ +/* GODOT ENGINE */ +/* https://godotengine.org */ +/*************************************************************************/ +/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ +/* */ +/* Permission is hereby granted, free of charge, to any person obtaining */ +/* a copy of this software and associated documentation files (the */ +/* "Software"), to deal in the Software without restriction, including */ +/* without limitation the rights to use, copy, modify, merge, publish, */ +/* distribute, sublicense, and/or sell copies of the Software, and to */ +/* permit persons to whom the Software is furnished to do so, subject to */ +/* the following conditions: */ +/* */ +/* The above copyright notice and this permission notice shall be */ +/* included in all copies or substantial portions of the Software. */ +/* */ +/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */ +/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */ +/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/ +/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */ +/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */ +/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */ +/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ +/*************************************************************************/ + +#ifdef JAVASCRIPT_ENABLED + +#include "webrtc_peer_connection_js.h" + +#include "webrtc_data_channel_js.h" + +#include "core/io/json.h" +#include "emscripten.h" + +extern "C" { +EMSCRIPTEN_KEEPALIVE void _emrtc_on_ice_candidate(void *obj, char *p_MidName, int p_MlineIndexName, char *p_sdpName) { + WebRTCPeerConnectionJS *peer = static_cast<WebRTCPeerConnectionJS *>(obj); + peer->emit_signal("ice_candidate_created", String(p_MidName), p_MlineIndexName, String(p_sdpName)); +} + +EMSCRIPTEN_KEEPALIVE void _emrtc_session_description_created(void *obj, char *p_type, char *p_offer) { + WebRTCPeerConnectionJS *peer = static_cast<WebRTCPeerConnectionJS *>(obj); + peer->emit_signal("session_description_created", String(p_type), String(p_offer)); +} + +EMSCRIPTEN_KEEPALIVE void _emrtc_on_connection_state_changed(void *obj) { + WebRTCPeerConnectionJS *peer = static_cast<WebRTCPeerConnectionJS *>(obj); + peer->_on_connection_state_changed(); +} + +EMSCRIPTEN_KEEPALIVE void _emrtc_on_error() { + ERR_PRINT("RTCPeerConnection error!"); +} + +EMSCRIPTEN_KEEPALIVE void _emrtc_emit_channel(void *obj, int p_id) { + WebRTCPeerConnectionJS *peer = static_cast<WebRTCPeerConnectionJS *>(obj); + peer->emit_signal("data_channel_received", Ref<WebRTCDataChannelJS>(new WebRTCDataChannelJS(p_id))); +} +} + +void _emrtc_create_pc(int p_id, const Dictionary &p_config) { + String config = JSON::print(p_config); + /* clang-format off */ + EM_ASM({ + var dict = Module.IDHandler.get($0); + var c_ptr = dict["ptr"]; + var config = JSON.parse(UTF8ToString($1)); + // Setup local connaction + var conn = null; + try { + conn = new RTCPeerConnection(config); + } catch (e) { + console.log(e); + return; + } + conn.oniceconnectionstatechange = function(event) { + if (!Module.IDHandler.get($0)) return; + ccall("_emrtc_on_connection_state_changed", "void", ["number"], [c_ptr]); + }; + conn.onicecandidate = function(event) { + if (!Module.IDHandler.get($0)) return; + if (!event.candidate) return; + + var c = event.candidate; + // should emit on ice candidate + ccall("_emrtc_on_ice_candidate", + "void", + ["number", "string", "number", "string"], + [c_ptr, c.sdpMid, c.sdpMLineIndex, c.candidate] + ); + }; + conn.ondatachannel = function (evt) { + var dict = Module.IDHandler.get($0); + if (!dict) { + return; + } + var id = Module.IDHandler.add({"channel": evt.channel, "ptr": null}); + ccall("_emrtc_emit_channel", + "void", + ["number", "number"], + [c_ptr, id] + ); + }; + dict["conn"] = conn; + }, p_id, config.utf8().get_data()); + /* clang-format on */ +} + +void WebRTCPeerConnectionJS::_on_connection_state_changed() { + /* clang-format off */ + _conn_state = (ConnectionState)EM_ASM_INT({ + var dict = Module.IDHandler.get($0); + if (!dict) return 5; // CLOSED + var conn = dict["conn"]; + switch(conn.iceConnectionState) { + case "new": + return 0; + case "checking": + return 1; + case "connected": + case "completed": + return 2; + case "disconnected": + return 3; + case "failed": + return 4; + case "closed": + return 5; + } + return 5; // CLOSED + }, _js_id); + /* clang-format on */ +} + +void WebRTCPeerConnectionJS::close() { + /* clang-format off */ + EM_ASM({ + var dict = Module.IDHandler.get($0); + if (!dict) return; + if (dict["conn"]) { + dict["conn"].close(); + } + }, _js_id); + /* clang-format on */ + _conn_state = STATE_CLOSED; +} + +Error WebRTCPeerConnectionJS::create_offer() { + ERR_FAIL_COND_V(_conn_state != STATE_NEW, FAILED); + + _conn_state = STATE_CONNECTING; + /* clang-format off */ + EM_ASM({ + var dict = Module.IDHandler.get($0); + var conn = dict["conn"]; + var c_ptr = dict["ptr"]; + var onError = function(error) { + console.error(error); + ccall("_emrtc_on_error", "void", [], []); + }; + var onCreated = function(offer) { + ccall("_emrtc_session_description_created", + "void", + ["number", "string", "string"], + [c_ptr, offer.type, offer.sdp] + ); + }; + conn.createOffer().then(onCreated).catch(onError); + }, _js_id); + /* clang-format on */ + return OK; +} + +Error WebRTCPeerConnectionJS::set_local_description(String type, String sdp) { + /* clang-format off */ + EM_ASM({ + var dict = Module.IDHandler.get($0); + var conn = dict["conn"]; + var c_ptr = dict["ptr"]; + var type = UTF8ToString($1); + var sdp = UTF8ToString($2); + var onError = function(error) { + console.error(error); + ccall("_emrtc_on_error", "void", [], []); + }; + conn.setLocalDescription({ + "sdp": sdp, + "type": type + }).catch(onError); + }, _js_id, type.utf8().get_data(), sdp.utf8().get_data()); + /* clang-format on */ + return OK; +} + +Error WebRTCPeerConnectionJS::set_remote_description(String type, String sdp) { + if (type == "offer") { + ERR_FAIL_COND_V(_conn_state != STATE_NEW, FAILED); + _conn_state = STATE_CONNECTING; + } + /* clang-format off */ + EM_ASM({ + var dict = Module.IDHandler.get($0); + var conn = dict["conn"]; + var c_ptr = dict["ptr"]; + var type = UTF8ToString($1); + var sdp = UTF8ToString($2); + + var onError = function(error) { + console.error(error); + ccall("_emrtc_on_error", "void", [], []); + }; + var onCreated = function(offer) { + ccall("_emrtc_session_description_created", + "void", + ["number", "string", "string"], + [c_ptr, offer.type, offer.sdp] + ); + }; + var onSet = function() { + if (type != "offer") { + return; + } + conn.createAnswer().then(onCreated); + }; + conn.setRemoteDescription({ + "sdp": sdp, + "type": type + }).then(onSet).catch(onError); + }, _js_id, type.utf8().get_data(), sdp.utf8().get_data()); + /* clang-format on */ + return OK; +} + +Error WebRTCPeerConnectionJS::add_ice_candidate(String sdpMidName, int sdpMlineIndexName, String sdpName) { + /* clang-format off */ + EM_ASM({ + var dict = Module.IDHandler.get($0); + var conn = dict["conn"]; + var c_ptr = dict["ptr"]; + var sdpMidName = UTF8ToString($1); + var sdpMlineIndexName = UTF8ToString($2); + var sdpName = UTF8ToString($3); + conn.addIceCandidate(new RTCIceCandidate({ + "candidate": sdpName, + "sdpMid": sdpMidName, + "sdpMlineIndex": sdpMlineIndexName + })); + }, _js_id, sdpMidName.utf8().get_data(), sdpMlineIndexName, sdpName.utf8().get_data()); + /* clang-format on */ + return OK; +} + +Error WebRTCPeerConnectionJS::initialize(Dictionary p_config) { + _emrtc_create_pc(_js_id, p_config); + return OK; +} + +Ref<WebRTCDataChannel> WebRTCPeerConnectionJS::create_data_channel(String p_channel, Dictionary p_channel_config) { + String config = JSON::print(p_channel_config); + /* clang-format off */ + int id = EM_ASM_INT({ + try { + var dict = Module.IDHandler.get($0); + if (!dict) return 0; + var label = UTF8ToString($1); + var config = JSON.parse(UTF8ToString($2)); + var conn = dict["conn"]; + return Module.IDHandler.add({ + "channel": conn.createDataChannel(label, config), + "ptr": null + }) + } catch (e) { + return 0; + } + }, _js_id, p_channel.utf8().get_data(), config.utf8().get_data()); + /* clang-format on */ + ERR_FAIL_COND_V(id == 0, NULL); + return memnew(WebRTCDataChannelJS(id)); +} + +Error WebRTCPeerConnectionJS::poll() { + return OK; +} + +WebRTCPeerConnection::ConnectionState WebRTCPeerConnectionJS::get_connection_state() const { + return _conn_state; +} + +WebRTCPeerConnectionJS::WebRTCPeerConnectionJS() { + _conn_state = STATE_NEW; + + /* clang-format off */ + _js_id = EM_ASM_INT({ + return Module.IDHandler.add({"conn": null, "ptr": $0}); + }, this); + /* clang-format on */ + Dictionary config; + _emrtc_create_pc(_js_id, config); +} + +WebRTCPeerConnectionJS::~WebRTCPeerConnectionJS() { + close(); + /* clang-format off */ + EM_ASM({ + Module.IDHandler.remove($0); + }, _js_id); + /* clang-format on */ +}; +#endif diff --git a/modules/webrtc/webrtc_peer_connection_js.h b/modules/webrtc/webrtc_peer_connection_js.h new file mode 100644 index 0000000000..43c0e3d6ee --- /dev/null +++ b/modules/webrtc/webrtc_peer_connection_js.h @@ -0,0 +1,66 @@ +/*************************************************************************/ +/* webrtc_peer_connection_js.h */ +/*************************************************************************/ +/* This file is part of: */ +/* GODOT ENGINE */ +/* https://godotengine.org */ +/*************************************************************************/ +/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ +/* */ +/* Permission is hereby granted, free of charge, to any person obtaining */ +/* a copy of this software and associated documentation files (the */ +/* "Software"), to deal in the Software without restriction, including */ +/* without limitation the rights to use, copy, modify, merge, publish, */ +/* distribute, sublicense, and/or sell copies of the Software, and to */ +/* permit persons to whom the Software is furnished to do so, subject to */ +/* the following conditions: */ +/* */ +/* The above copyright notice and this permission notice shall be */ +/* included in all copies or substantial portions of the Software. */ +/* */ +/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */ +/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */ +/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/ +/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */ +/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */ +/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */ +/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ +/*************************************************************************/ + +#ifndef WEBRTC_PEER_CONNECTION_JS_H +#define WEBRTC_PEER_CONNECTION_JS_H + +#ifdef JAVASCRIPT_ENABLED + +#include "webrtc_peer_connection.h" + +class WebRTCPeerConnectionJS : public WebRTCPeerConnection { + +private: + int _js_id; + ConnectionState _conn_state; + +public: + static WebRTCPeerConnection *_create() { return memnew(WebRTCPeerConnectionJS); } + static void make_default() { WebRTCPeerConnection::_create = WebRTCPeerConnectionJS::_create; } + + void _on_connection_state_changed(); + virtual ConnectionState get_connection_state() const; + + virtual Error initialize(Dictionary configuration = Dictionary()); + virtual Ref<WebRTCDataChannel> create_data_channel(String p_channel_name, Dictionary p_channel_config = Dictionary()); + virtual Error create_offer(); + virtual Error set_remote_description(String type, String sdp); + virtual Error set_local_description(String type, String sdp); + virtual Error add_ice_candidate(String sdpMidName, int sdpMlineIndexName, String sdpName); + virtual Error poll(); + virtual void close(); + + WebRTCPeerConnectionJS(); + ~WebRTCPeerConnectionJS(); +}; + +#endif + +#endif // WEBRTC_PEER_CONNECTION_JS_H diff --git a/modules/webrtc/webrtc_peer_js.cpp b/modules/webrtc/webrtc_peer_js.cpp deleted file mode 100644 index 1282e075ab..0000000000 --- a/modules/webrtc/webrtc_peer_js.cpp +++ /dev/null @@ -1,455 +0,0 @@ -/*************************************************************************/ -/* webrtc_peer_js.cpp */ -/*************************************************************************/ -/* This file is part of: */ -/* GODOT ENGINE */ -/* https://godotengine.org */ -/*************************************************************************/ -/* Copyright (c) 2007-2018 Juan Linietsky, Ariel Manzur. */ -/* Copyright (c) 2014-2018 Godot Engine contributors (cf. AUTHORS.md) */ -/* */ -/* Permission is hereby granted, free of charge, to any person obtaining */ -/* a copy of this software and associated documentation files (the */ -/* "Software"), to deal in the Software without restriction, including */ -/* without limitation the rights to use, copy, modify, merge, publish, */ -/* distribute, sublicense, and/or sell copies of the Software, and to */ -/* permit persons to whom the Software is furnished to do so, subject to */ -/* the following conditions: */ -/* */ -/* The above copyright notice and this permission notice shall be */ -/* included in all copies or substantial portions of the Software. */ -/* */ -/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */ -/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */ -/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/ -/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */ -/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */ -/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */ -/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ -/*************************************************************************/ - -#ifdef JAVASCRIPT_ENABLED - -#include "webrtc_peer_js.h" -#include "emscripten.h" - -extern "C" { -EMSCRIPTEN_KEEPALIVE void _emrtc_on_ice_candidate(void *obj, char *p_MidName, int p_MlineIndexName, char *p_sdpName) { - WebRTCPeerJS *peer = static_cast<WebRTCPeerJS *>(obj); - peer->emit_signal("new_ice_candidate", String(p_MidName), p_MlineIndexName, String(p_sdpName)); -} - -EMSCRIPTEN_KEEPALIVE void _emrtc_offer_created(void *obj, char *p_type, char *p_offer) { - WebRTCPeerJS *peer = static_cast<WebRTCPeerJS *>(obj); - peer->emit_signal("offer_created", String(p_type), String(p_offer)); -} - -EMSCRIPTEN_KEEPALIVE void _emrtc_on_error(void *obj) { - WebRTCPeerJS *peer = static_cast<WebRTCPeerJS *>(obj); - peer->_on_error(); -} - -EMSCRIPTEN_KEEPALIVE void _emrtc_on_open(void *obj) { - WebRTCPeerJS *peer = static_cast<WebRTCPeerJS *>(obj); - peer->_on_open(); -} - -EMSCRIPTEN_KEEPALIVE void _emrtc_on_close(void *obj) { - WebRTCPeerJS *peer = static_cast<WebRTCPeerJS *>(obj); - peer->_on_close(); -} - -EMSCRIPTEN_KEEPALIVE void _emrtc_on_message(void *obj, uint8_t *p_data, uint32_t p_size, bool p_is_string) { - WebRTCPeerJS *peer = static_cast<WebRTCPeerJS *>(obj); - peer->_on_message(p_data, p_size, p_is_string); -} - -EMSCRIPTEN_KEEPALIVE void _emrtc_bind_channel(int p_id) { - /* clang-format off */ - EM_ASM({ - if (!Module.IDHandler.has($0)) { - return; // Godot Object is gone! - } - var dict = Module.IDHandler.get($0); - var channel = dict["channel"]; - var c_ptr = dict["ptr"]; - - channel.onopen = function (evt) { - ccall("_emrtc_on_open", - "void", - ["number"], - [c_ptr] - ); - }; - channel.onclose = function (evt) { - ccall("_emrtc_on_close", - "void", - ["number"], - [c_ptr] - ); - }; - channel.onerror = function (evt) { - ccall("_emrtc_on_error", - "void", - ["number"], - [c_ptr] - ); - }; - - channel.binaryType = "arraybuffer"; - channel.onmessage = function(event) { - var buffer; - var is_string = 0; - if (event.data instanceof ArrayBuffer) { - - buffer = new Uint8Array(event.data); - - } else if (event.data instanceof Blob) { - - alert("Blob type not supported"); - return; - - } else if (typeof event.data === "string") { - - is_string = 1; - var enc = new TextEncoder("utf-8"); - buffer = new Uint8Array(enc.encode(event.data)); - - } else { - - alert("Unknown message type"); - return; - - } - var len = buffer.length*buffer.BYTES_PER_ELEMENT; - var out = Module._malloc(len); - Module.HEAPU8.set(buffer, out); - ccall("_emrtc_on_message", - "void", - ["number", "number", "number", "number"], - [c_ptr, out, len, is_string] - ); - Module._free(out); - } - }, p_id); - /* clang-format on */ -} -} - -void _emrtc_create_pc(int p_id) { - /* clang-format off */ - EM_ASM({ - var dict = Module.IDHandler.get($0); - var c_ptr = dict["ptr"]; - // Setup local connaction - var conn = new RTCPeerConnection(); - conn.onicecandidate = function(event) { - if (!Module.IDHandler.get($0)) return; - if (!event.candidate) return; - - var c = event.candidate; - // should emit on ice candidate - ccall("_emrtc_on_ice_candidate", - "void", - ["number", "string", "number", "string"], - [c_ptr, c.sdpMid, c.sdpMLineIndex, c.candidate] - ); - }; - conn.ondatachannel = function (evt) { - var dict = Module.IDHandler.get($0); - if (!dict || dict["channel"]) { - return; - } - var channel = evt.channel; - dict["channel"] = channel; - ccall("_emrtc_bind_channel", - "void", - ["number"], - [$0] - ); - }; - dict["conn"] = conn; - }, p_id); - /* clang-format on */ -} - -void WebRTCPeerJS::_on_open() { - in_buffer.resize(16); - _conn_state = STATE_CONNECTED; -} - -void WebRTCPeerJS::_on_close() { - close(); -} - -void WebRTCPeerJS::_on_error() { - close(); - _conn_state = STATE_FAILED; -} - -void WebRTCPeerJS::_on_message(uint8_t *p_data, uint32_t p_size, bool p_is_string) { - if (in_buffer.space_left() < p_size + 5) { - ERR_EXPLAIN("Buffer full! Dropping data"); - ERR_FAIL(); - } - - uint8_t is_string = p_is_string ? 1 : 0; - in_buffer.write((uint8_t *)&p_size, 4); - in_buffer.write((uint8_t *)&is_string, 1); - in_buffer.write(p_data, p_size); - queue_count++; -} - -void WebRTCPeerJS::close() { - in_buffer.resize(0); - queue_count = 0; - _was_string = false; - /* clang-format off */ - EM_ASM({ - var dict = Module.IDHandler.get($0); - if (!dict) return; - if (dict["channel"]) { - dict["channel"].close(); - dict["channel"] = null; - } - if (dict["conn"]) { - dict["conn"].close(); - } - }, _js_id); - /* clang-format on */ - _conn_state = STATE_CLOSED; -} - -Error WebRTCPeerJS::create_offer() { - ERR_FAIL_COND_V(_conn_state != STATE_NEW, FAILED); - - _conn_state = STATE_CONNECTING; - /* clang-format off */ - EM_ASM({ - var dict = Module.IDHandler.get($0); - var conn = dict["conn"]; - var c_ptr = dict["ptr"]; - var onError = function(error) { - console.log(error); - ccall("_emrtc_on_error", - "void", - ["number"], - [c_ptr] - ); - }; - var onCreated = function(offer) { - ccall("_emrtc_offer_created", - "void", - ["number", "string", "string"], - [c_ptr, offer.type, offer.sdp] - ); - }; - - var channel = conn.createDataChannel("default"); - dict["channel"] = channel; - ccall("_emrtc_bind_channel", - "void", - ["number"], - [$0] - ); - conn.createOffer().then(onCreated).catch(onError); - }, _js_id); - /* clang-format on */ - return OK; -} - -Error WebRTCPeerJS::set_local_description(String type, String sdp) { - /* clang-format off */ - EM_ASM({ - var dict = Module.IDHandler.get($0); - var conn = dict["conn"]; - var c_ptr = dict["ptr"]; - var type = UTF8ToString($1); - var sdp = UTF8ToString($2); - var onError = function(error) { - console.log(error); - ccall("_emrtc_on_error", - "void", - ["number"], - [c_ptr] - ); - }; - conn.setLocalDescription({ - "sdp": sdp, - "type": type - }).catch(onError); - }, _js_id, type.utf8().get_data(), sdp.utf8().get_data()); - /* clang-format on */ - return OK; -} - -Error WebRTCPeerJS::set_remote_description(String type, String sdp) { - if (type == "offer") { - ERR_FAIL_COND_V(_conn_state != STATE_NEW, FAILED); - _conn_state = STATE_CONNECTING; - } - /* clang-format off */ - EM_ASM({ - var dict = Module.IDHandler.get($0); - var conn = dict["conn"]; - var c_ptr = dict["ptr"]; - var type = UTF8ToString($1); - var sdp = UTF8ToString($2); - - var onError = function(error) { - console.log(error); - ccall("_emrtc_on_error", - "void", - ["number"], - [c_ptr] - ); - }; - var onCreated = function(offer) { - ccall("_emrtc_offer_created", - "void", - ["number", "string", "string"], - [c_ptr, offer.type, offer.sdp] - ); - }; - var onSet = function() { - if (type != "offer") { - return; - } - conn.createAnswer().then(onCreated); - }; - conn.setRemoteDescription({ - "sdp": sdp, - "type": type - }).then(onSet).catch(onError); - }, _js_id, type.utf8().get_data(), sdp.utf8().get_data()); - /* clang-format on */ - return OK; -} - -Error WebRTCPeerJS::add_ice_candidate(String sdpMidName, int sdpMlineIndexName, String sdpName) { - /* clang-format off */ - EM_ASM({ - var dict = Module.IDHandler.get($0); - var conn = dict["conn"]; - var c_ptr = dict["ptr"]; - var sdpMidName = UTF8ToString($1); - var sdpMlineIndexName = UTF8ToString($2); - var sdpName = UTF8ToString($3); - conn.addIceCandidate(new RTCIceCandidate({ - "candidate": sdpName, - "sdpMid": sdpMidName, - "sdpMlineIndex": sdpMlineIndexName - })); - }, _js_id, sdpMidName.utf8().get_data(), sdpMlineIndexName, sdpName.utf8().get_data()); - /* clang-format on */ - return OK; -} - -Error WebRTCPeerJS::poll() { - return OK; -} - -WebRTCPeer::ConnectionState WebRTCPeerJS::get_connection_state() const { - return _conn_state; -} - -int WebRTCPeerJS::get_available_packet_count() const { - return queue_count; -} - -Error WebRTCPeerJS::get_packet(const uint8_t **r_buffer, int &r_buffer_size) { - ERR_FAIL_COND_V(_conn_state != STATE_CONNECTED, ERR_UNCONFIGURED); - - if (queue_count == 0) - return ERR_UNAVAILABLE; - - uint32_t to_read = 0; - uint32_t left = 0; - uint8_t is_string = 0; - r_buffer_size = 0; - - in_buffer.read((uint8_t *)&to_read, 4); - --queue_count; - left = in_buffer.data_left(); - - if (left < to_read + 1) { - in_buffer.advance_read(left); - return FAILED; - } - - in_buffer.read(&is_string, 1); - _was_string = is_string == 1; - in_buffer.read(packet_buffer, to_read); - *r_buffer = packet_buffer; - r_buffer_size = to_read; - - return OK; -} - -Error WebRTCPeerJS::put_packet(const uint8_t *p_buffer, int p_buffer_size) { - ERR_FAIL_COND_V(_conn_state != STATE_CONNECTED, ERR_UNCONFIGURED); - - int is_bin = _write_mode == WebRTCPeer::WRITE_MODE_BINARY ? 1 : 0; - - /* clang-format off */ - EM_ASM({ - var dict = Module.IDHandler.get($0); - var channel = dict["channel"]; - var bytes_array = new Uint8Array($2); - var i = 0; - - for(i=0; i<$2; i++) { - bytes_array[i] = getValue($1+i, 'i8'); - } - - if ($3) { - channel.send(bytes_array.buffer); - } else { - var string = new TextDecoder("utf-8").decode(bytes_array); - channel.send(string); - } - }, _js_id, p_buffer, p_buffer_size, is_bin); - /* clang-format on */ - - return OK; -} - -int WebRTCPeerJS::get_max_packet_size() const { - return 1200; -} - -void WebRTCPeerJS::set_write_mode(WriteMode p_mode) { - _write_mode = p_mode; -} - -WebRTCPeer::WriteMode WebRTCPeerJS::get_write_mode() const { - return _write_mode; -} - -bool WebRTCPeerJS::was_string_packet() const { - return _was_string; -} - -WebRTCPeerJS::WebRTCPeerJS() { - queue_count = 0; - _was_string = false; - _write_mode = WRITE_MODE_BINARY; - _conn_state = STATE_NEW; - - /* clang-format off */ - _js_id = EM_ASM_INT({ - return Module.IDHandler.add({"conn": null, "ptr": $0, "channel": null}); - }, this); - /* clang-format on */ - _emrtc_create_pc(_js_id); -} - -WebRTCPeerJS::~WebRTCPeerJS() { - close(); - /* clang-format off */ - EM_ASM({ - Module.IDHandler.remove($0); - }, _js_id); - /* clang-format on */ -}; -#endif diff --git a/platform/android/detect.py b/platform/android/detect.py index ea70fefbc5..b7641172e4 100644 --- a/platform/android/detect.py +++ b/platform/android/detect.py @@ -214,13 +214,14 @@ def configure(env): lib_sysroot = env["ANDROID_NDK_ROOT"] + "/platforms/" + env['ndk_platform'] + "/" + env['ARCH'] ## Compile flags - - if env['android_stl']: + # Disable exceptions and rtti on non-tools (template) builds + if env['tools'] or env['android_stl']: env.Append(CPPFLAGS=["-isystem", env["ANDROID_NDK_ROOT"] + "/sources/cxx-stl/llvm-libc++/include"]) env.Append(CPPFLAGS=["-isystem", env["ANDROID_NDK_ROOT"] + "/sources/cxx-stl/llvm-libc++abi/include"]) env.Append(CXXFLAGS=['-frtti', "-std=gnu++14"]) else: env.Append(CXXFLAGS=['-fno-rtti', '-fno-exceptions']) + # Don't use dynamic_cast, necessary with no-rtti. env.Append(CPPFLAGS=['-DNO_SAFE_CAST']) ndk_version = get_ndk_version(env["ANDROID_NDK_ROOT"]) diff --git a/platform/android/java/AndroidManifest.xml b/platform/android/java/AndroidManifest.xml index 613d24fbd2..9997950137 100644 --- a/platform/android/java/AndroidManifest.xml +++ b/platform/android/java/AndroidManifest.xml @@ -22,7 +22,7 @@ <!--Anything in this line after the icon will be erased when doing custom build. If you want to add tags manually, do before it.--> <application android:label="@string/godot_project_name_string" android:allowBackup="false" tools:ignore="GoogleAppIndexingWarning" android:icon="@drawable/icon"> -<!--The following values are replaced when Godot exports, modifying them here has no effect. Do theses changes in the--> +<!--The following values are replaced when Godot exports, modifying them here has no effect. Do these changes in the--> <!--export preset. Adding new ones is fine.--> <activity android:name="org.godotengine.godot.Godot" diff --git a/platform/android/java_godot_lib_jni.h b/platform/android/java_godot_lib_jni.h index 3a03294b08..f99935bf7c 100644 --- a/platform/android/java_godot_lib_jni.h +++ b/platform/android/java_godot_lib_jni.h @@ -35,7 +35,7 @@ #include <jni.h> // These functions can be called from within JAVA and are the means by which our JAVA implementation calls back into our C++ code. -// See java/src/org/godotengine/godot/GodotLib.java for the JAVA side of this (yes thats why we have the long names) +// See java/src/org/godotengine/godot/GodotLib.java for the JAVA side of this (yes that's why we have the long names) extern "C" { JNIEXPORT void JNICALL Java_org_godotengine_godot_GodotLib_initialize(JNIEnv *env, jobject obj, jobject activity, jobject p_asset_manager, jboolean p_use_apk_expansion); JNIEXPORT void JNICALL Java_org_godotengine_godot_GodotLib_ondestroy(JNIEnv *env); diff --git a/platform/android/os_android.cpp b/platform/android/os_android.cpp index 93d39859f2..ff1632cba8 100644 --- a/platform/android/os_android.cpp +++ b/platform/android/os_android.cpp @@ -277,7 +277,7 @@ Size2 OS_Android::get_window_size() const { return Vector2(default_videomode.width, default_videomode.height); } -String OS_Android::get_name() { +String OS_Android::get_name() const { return "Android"; } diff --git a/platform/android/os_android.h b/platform/android/os_android.h index d2198b0579..4dbc96f4da 100644 --- a/platform/android/os_android.h +++ b/platform/android/os_android.h @@ -139,7 +139,7 @@ public: virtual Size2 get_window_size() const; - virtual String get_name(); + virtual String get_name() const; virtual MainLoop *get_main_loop() const; virtual bool can_draw() const; diff --git a/platform/haiku/os_haiku.cpp b/platform/haiku/os_haiku.cpp index f3fed6669b..438b50053f 100644 --- a/platform/haiku/os_haiku.cpp +++ b/platform/haiku/os_haiku.cpp @@ -69,7 +69,7 @@ void OS_Haiku::run() { main_loop->finish(); } -String OS_Haiku::get_name() { +String OS_Haiku::get_name() const { return "Haiku"; } diff --git a/platform/haiku/os_haiku.h b/platform/haiku/os_haiku.h index 6ab006843a..e1d4cf8d87 100644 --- a/platform/haiku/os_haiku.h +++ b/platform/haiku/os_haiku.h @@ -74,7 +74,7 @@ public: OS_Haiku(); void run(); - virtual String get_name(); + virtual String get_name() const; virtual MainLoop *get_main_loop() const; diff --git a/platform/iphone/detect.py b/platform/iphone/detect.py index 3ed0a4ade7..d9f710e456 100644 --- a/platform/iphone/detect.py +++ b/platform/iphone/detect.py @@ -115,10 +115,12 @@ def configure(env): env.Append(CPPFLAGS=['-DNEED_LONG_INT']) env.Append(CPPFLAGS=['-DLIBYUV_DISABLE_NEON']) - if env['ios_exceptions']: - env.Append(CCFLAGS=['-fexceptions']) - else: - env.Append(CCFLAGS=['-fno-exceptions']) + # Disable exceptions on non-tools (template) builds + if not env['tools']: + if env['ios_exceptions']: + env.Append(CCFLAGS=['-fexceptions']) + else: + env.Append(CCFLAGS=['-fno-exceptions']) ## Link flags diff --git a/platform/iphone/os_iphone.cpp b/platform/iphone/os_iphone.cpp index d8fb5992cc..6a65cadf09 100644 --- a/platform/iphone/os_iphone.cpp +++ b/platform/iphone/os_iphone.cpp @@ -495,7 +495,7 @@ String OSIPhone::get_user_data_dir() const { return data_dir; }; -String OSIPhone::get_name() { +String OSIPhone::get_name() const { return "iOS"; }; diff --git a/platform/iphone/os_iphone.h b/platform/iphone/os_iphone.h index 460dfacd9b..017125209c 100644 --- a/platform/iphone/os_iphone.h +++ b/platform/iphone/os_iphone.h @@ -174,7 +174,7 @@ public: void set_data_dir(String p_dir); - virtual String get_name(); + virtual String get_name() const; Error shell_open(String p_uri); diff --git a/platform/javascript/detect.py b/platform/javascript/detect.py index 145ce8d83d..145ac42863 100644 --- a/platform/javascript/detect.py +++ b/platform/javascript/detect.py @@ -110,10 +110,12 @@ def configure(env): # once feasible also consider memory buffer size issues. env.Append(CPPDEFINES=['NO_THREADS']) - # These flags help keep the file size down. - env.Append(CCFLAGS=['-fno-exceptions', '-fno-rtti']) - # Don't use dynamic_cast, necessary with no-rtti. - env.Append(CPPDEFINES=['NO_SAFE_CAST']) + # Disable exceptions and rtti on non-tools (template) builds + if not env['tools']: + # These flags help keep the file size down. + env.Append(CCFLAGS=['-fno-exceptions', '-fno-rtti']) + # Don't use dynamic_cast, necessary with no-rtti. + env.Append(CPPDEFINES=['NO_SAFE_CAST']) if env['javascript_eval']: env.Append(CPPDEFINES=['JAVASCRIPT_EVAL_ENABLED']) diff --git a/platform/javascript/os_javascript.cpp b/platform/javascript/os_javascript.cpp index 2e3e10e222..c69e6f0cb8 100644 --- a/platform/javascript/os_javascript.cpp +++ b/platform/javascript/os_javascript.cpp @@ -1159,7 +1159,7 @@ Error OS_JavaScript::shell_open(String p_uri) { return OK; } -String OS_JavaScript::get_name() { +String OS_JavaScript::get_name() const { return "HTML5"; } diff --git a/platform/javascript/os_javascript.h b/platform/javascript/os_javascript.h index f7ce28e660..a0c7c31f2d 100644 --- a/platform/javascript/os_javascript.h +++ b/platform/javascript/os_javascript.h @@ -146,7 +146,7 @@ public: virtual void set_icon(const Ref<Image> &p_icon); String get_executable_path() const; virtual Error shell_open(String p_uri); - virtual String get_name(); + virtual String get_name() const; virtual bool can_draw() const; virtual String get_resource_dir() const; diff --git a/platform/osx/crash_handler_osx.mm b/platform/osx/crash_handler_osx.mm index ed8a955ae5..e19fdf1b9f 100644 --- a/platform/osx/crash_handler_osx.mm +++ b/platform/osx/crash_handler_osx.mm @@ -77,7 +77,12 @@ static void handle_crash(int sig) { void *bt_buffer[256]; size_t size = backtrace(bt_buffer, 256); String _execpath = OS::get_singleton()->get_executable_path(); - String msg = GLOBAL_GET("debug/settings/crash_handler/message"); + + String msg; + const ProjectSettings *proj_settings = ProjectSettings::get_singleton(); + if (proj_settings) { + msg = proj_settings->get("debug/settings/crash_handler/message"); + } // Dump the backtrace to stderr with a message to the user fprintf(stderr, "%s: Program crashed with signal %d\n", __FUNCTION__, sig); diff --git a/platform/osx/os_osx.h b/platform/osx/os_osx.h index 125a88ab6d..d2a6f38b01 100644 --- a/platform/osx/os_osx.h +++ b/platform/osx/os_osx.h @@ -165,7 +165,7 @@ public: void wm_minimized(bool p_minimized); - virtual String get_name(); + virtual String get_name() const; virtual void alert(const String &p_alert, const String &p_title = "ALERT!"); diff --git a/platform/osx/os_osx.mm b/platform/osx/os_osx.mm index fec524c04b..fc97bd4a20 100644 --- a/platform/osx/os_osx.mm +++ b/platform/osx/os_osx.mm @@ -1551,7 +1551,7 @@ void OS_OSX::delete_main_loop() { main_loop = NULL; } -String OS_OSX::get_name() { +String OS_OSX::get_name() const { return "OSX"; } diff --git a/platform/server/os_server.cpp b/platform/server/os_server.cpp index 53f2a65c8e..12e53054bc 100644 --- a/platform/server/os_server.cpp +++ b/platform/server/os_server.cpp @@ -190,7 +190,7 @@ bool OS_Server::can_draw() const { return false; //can never draw }; -String OS_Server::get_name() { +String OS_Server::get_name() const { return "Server"; } diff --git a/platform/server/os_server.h b/platform/server/os_server.h index 7441064790..e3488a693d 100644 --- a/platform/server/os_server.h +++ b/platform/server/os_server.h @@ -93,7 +93,7 @@ protected: virtual void set_main_loop(MainLoop *p_main_loop); public: - virtual String get_name(); + virtual String get_name() const; virtual void set_mouse_show(bool p_show); virtual void set_mouse_grab(bool p_grab); diff --git a/platform/uwp/os_uwp.cpp b/platform/uwp/os_uwp.cpp index 1678d351b3..f9d22481dd 100644 --- a/platform/uwp/os_uwp.cpp +++ b/platform/uwp/os_uwp.cpp @@ -530,7 +530,7 @@ OS::VideoMode OS_UWP::get_video_mode(int p_screen) const { void OS_UWP::get_fullscreen_mode_list(List<VideoMode> *p_list, int p_screen) const { } -String OS_UWP::get_name() { +String OS_UWP::get_name() const { return "UWP"; } diff --git a/platform/uwp/os_uwp.h b/platform/uwp/os_uwp.h index 7b00224017..1bb68bc75d 100644 --- a/platform/uwp/os_uwp.h +++ b/platform/uwp/os_uwp.h @@ -195,7 +195,7 @@ public: virtual MainLoop *get_main_loop() const; - virtual String get_name(); + virtual String get_name() const; virtual Date get_date(bool utc) const; virtual Time get_time(bool utc) const; diff --git a/platform/windows/crash_handler_windows.cpp b/platform/windows/crash_handler_windows.cpp index 4006c4c60e..0716ee67f4 100644 --- a/platform/windows/crash_handler_windows.cpp +++ b/platform/windows/crash_handler_windows.cpp @@ -166,11 +166,16 @@ DWORD CrashHandlerException(EXCEPTION_POINTERS *ep) { line.SizeOfStruct = sizeof(line); IMAGE_NT_HEADERS *h = ImageNtHeader(base); DWORD image_type = h->FileHeader.Machine; - int n = 0; - String msg = GLOBAL_GET("debug/settings/crash_handler/message"); + + String msg; + const ProjectSettings *proj_settings = ProjectSettings::get_singleton(); + if (proj_settings) { + msg = proj_settings->get("debug/settings/crash_handler/message"); + } fprintf(stderr, "Dumping the backtrace. %ls\n", msg.c_str()); + int n = 0; do { if (skip_first) { skip_first = false; diff --git a/platform/windows/os_windows.cpp b/platform/windows/os_windows.cpp index 0b61770d87..4c6e4e96b5 100644 --- a/platform/windows/os_windows.cpp +++ b/platform/windows/os_windows.cpp @@ -705,7 +705,7 @@ LRESULT OS_Windows::WndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam) } } } else if (mouse_mode != MOUSE_MODE_CAPTURED) { - // for reasons unknown to mankind, wheel comes in screen cordinates + // for reasons unknown to mankind, wheel comes in screen coordinates POINT coords; coords.x = mb->get_position().x; coords.y = mb->get_position().y; @@ -2119,7 +2119,7 @@ void OS_Windows::request_attention() { FlashWindowEx(&info); } -String OS_Windows::get_name() { +String OS_Windows::get_name() const { return "Windows"; } diff --git a/platform/windows/os_windows.h b/platform/windows/os_windows.h index 0e0b9bf3f6..59aeb01b51 100644 --- a/platform/windows/os_windows.h +++ b/platform/windows/os_windows.h @@ -246,7 +246,7 @@ public: virtual MainLoop *get_main_loop() const; - virtual String get_name(); + virtual String get_name() const; virtual Date get_date(bool utc) const; virtual Time get_time(bool utc) const; diff --git a/platform/x11/crash_handler_x11.cpp b/platform/x11/crash_handler_x11.cpp index 44d3cf1910..ca7251078f 100644 --- a/platform/x11/crash_handler_x11.cpp +++ b/platform/x11/crash_handler_x11.cpp @@ -53,7 +53,12 @@ static void handle_crash(int sig) { void *bt_buffer[256]; size_t size = backtrace(bt_buffer, 256); String _execpath = OS::get_singleton()->get_executable_path(); - String msg = GLOBAL_GET("debug/settings/crash_handler/message"); + + String msg; + const ProjectSettings *proj_settings = ProjectSettings::get_singleton(); + if (proj_settings) { + msg = proj_settings->get("debug/settings/crash_handler/message"); + } // Dump the backtrace to stderr with a message to the user fprintf(stderr, "%s: Program crashed with signal %d\n", __FUNCTION__, sig); diff --git a/platform/x11/os_x11.cpp b/platform/x11/os_x11.cpp index c2e7b561d3..f034b2389b 100644 --- a/platform/x11/os_x11.cpp +++ b/platform/x11/os_x11.cpp @@ -534,22 +534,26 @@ Error OS_X11::initialize(const VideoMode &p_desired, int p_video_driver, int p_a } { - Pixmap cursormask; - XGCValues xgc; - GC gc; - XColor col; - Cursor cursor; + // Creating an empty/transparent cursor + + // Create 1x1 bitmap + Pixmap cursormask = XCreatePixmap(x11_display, + RootWindow(x11_display, DefaultScreen(x11_display)), 1, 1, 1); - cursormask = XCreatePixmap(x11_display, RootWindow(x11_display, DefaultScreen(x11_display)), 1, 1, 1); + // Fill with zero + XGCValues xgc; xgc.function = GXclear; - gc = XCreateGC(x11_display, cursormask, GCFunction, &xgc); + GC gc = XCreateGC(x11_display, cursormask, GCFunction, &xgc); XFillRectangle(x11_display, cursormask, gc, 0, 0, 1, 1); - col.pixel = 0; - col.red = 0; - col.flags = 4; - cursor = XCreatePixmapCursor(x11_display, - cursormask, cursormask, + + // Color value doesn't matter. Mask zero means no foreground or background will be drawn + XColor col = {}; + + Cursor cursor = XCreatePixmapCursor(x11_display, + cursormask, // source (using cursor mask as placeholder, since it'll all be ignored) + cursormask, // mask &col, &col, 0, 0); + XFreePixmap(x11_display, cursormask); XFreeGC(x11_display, gc); @@ -2592,7 +2596,7 @@ String OS_X11::get_clipboard() const { return ret; } -String OS_X11::get_name() { +String OS_X11::get_name() const { return "X11"; } diff --git a/platform/x11/os_x11.h b/platform/x11/os_x11.h index a54851d4e7..ad35cdb4f9 100644 --- a/platform/x11/os_x11.h +++ b/platform/x11/os_x11.h @@ -216,7 +216,7 @@ protected: bool is_window_maximize_allowed(); public: - virtual String get_name(); + virtual String get_name() const; virtual void set_cursor_shape(CursorShape p_shape); virtual CursorShape get_cursor_shape() const; diff --git a/scene/2d/canvas_modulate.cpp b/scene/2d/canvas_modulate.cpp index bd7bb97b03..009d664462 100644 --- a/scene/2d/canvas_modulate.cpp +++ b/scene/2d/canvas_modulate.cpp @@ -70,7 +70,7 @@ void CanvasModulate::_bind_methods() { void CanvasModulate::set_color(const Color &p_color) { color = p_color; - if (is_inside_tree()) { + if (is_visible_in_tree()) { VS::get_singleton()->canvas_set_modulate(get_canvas(), color); } } diff --git a/scene/2d/cpu_particles_2d.cpp b/scene/2d/cpu_particles_2d.cpp index 721b52edaa..ff27e0a29a 100644 --- a/scene/2d/cpu_particles_2d.cpp +++ b/scene/2d/cpu_particles_2d.cpp @@ -978,7 +978,7 @@ void CPUParticles2D::_notification(int p_what) { if (p_what == NOTIFICATION_DRAW) { if (!redraw) - return; // dont add to render list + return; // don't add to render list RID texrid; if (texture.is_valid()) { diff --git a/scene/2d/skeleton_2d.h b/scene/2d/skeleton_2d.h index cf9877e6f8..d24c0a1561 100644 --- a/scene/2d/skeleton_2d.h +++ b/scene/2d/skeleton_2d.h @@ -39,6 +39,9 @@ class Bone2D : public Node2D { GDCLASS(Bone2D, Node2D) friend class Skeleton2D; +#ifdef TOOLS_ENABLED + friend class AnimatedValuesBackup; +#endif Bone2D *parent_bone; Skeleton2D *skeleton; @@ -71,6 +74,9 @@ class Skeleton2D : public Node2D { GDCLASS(Skeleton2D, Node2D); friend class Bone2D; +#ifdef TOOLS_ENABLED + friend class AnimatedValuesBackup; +#endif struct Bone { bool operator<(const Bone &p_bone) const { diff --git a/scene/2d/tile_map.cpp b/scene/2d/tile_map.cpp index b321bcf3ce..3dc0f46676 100644 --- a/scene/2d/tile_map.cpp +++ b/scene/2d/tile_map.cpp @@ -491,7 +491,7 @@ void TileMap::update_dirty_quadrants() { shape_idx++; #ifdef DEBUG_ENABLED } else { - print_error("The TileSet asigned to the TileMap " + get_name() + " has an invalid convex shape."); + print_error("The TileSet assigned to the TileMap " + get_name() + " has an invalid convex shape."); #endif } } diff --git a/scene/3d/skeleton.cpp b/scene/3d/skeleton.cpp index 15c089ec10..e192e040f2 100644 --- a/scene/3d/skeleton.cpp +++ b/scene/3d/skeleton.cpp @@ -162,7 +162,7 @@ void Skeleton::_update_process_order() { //now check process order int pass_count = 0; while (pass_count < len * len) { - //using bubblesort because of simplicity, it wont run every frame though. + //using bubblesort because of simplicity, it won't run every frame though. //bublesort worst case is O(n^2), and this may be an infinite loop if cyclic bool swapped = false; for (int i = 0; i < len; i++) { diff --git a/scene/3d/spatial.cpp b/scene/3d/spatial.cpp index 05fd984f93..efd418e3c7 100644 --- a/scene/3d/spatial.cpp +++ b/scene/3d/spatial.cpp @@ -676,28 +676,29 @@ void Spatial::set_identity() { void Spatial::look_at(const Vector3 &p_target, const Vector3 &p_up) { - Transform lookat(get_global_transform()); - if (lookat.origin == p_target) { + Vector3 origin(get_global_transform().origin); + look_at_from_position(origin, p_target, p_up); +} + +void Spatial::look_at_from_position(const Vector3 &p_pos, const Vector3 &p_target, const Vector3 &p_up) { + + if (p_pos == p_target) { ERR_EXPLAIN("Node origin and target are in the same position, look_at() failed"); ERR_FAIL(); } - if (p_up.cross(p_target - lookat.origin) == Vector3()) { + if (p_up.cross(p_target - p_pos) == Vector3()) { ERR_EXPLAIN("Up vector and direction between node origin and target are aligned, look_at() failed"); ERR_FAIL(); } - Vector3 original_scale(lookat.basis.get_scale()); - lookat = lookat.looking_at(p_target, p_up); - // as basis was normalized, we just need to apply original scale back - lookat.basis.scale(original_scale); - set_global_transform(lookat); -} - -void Spatial::look_at_from_position(const Vector3 &p_pos, const Vector3 &p_target, const Vector3 &p_up) { Transform lookat; lookat.origin = p_pos; + + Vector3 original_scale(get_global_transform().basis.get_scale()); lookat = lookat.looking_at(p_target, p_up); + // as basis was normalized, we just need to apply original scale back + lookat.basis.scale(original_scale); set_global_transform(lookat); } diff --git a/scene/animation/animation_node_state_machine.cpp b/scene/animation/animation_node_state_machine.cpp index 1e3470cd90..60f8806b25 100644 --- a/scene/animation/animation_node_state_machine.cpp +++ b/scene/animation/animation_node_state_machine.cpp @@ -314,8 +314,9 @@ float AnimationNodeStateMachinePlayback::process(AnimationNodeStateMachine *sm, if (start_request_travel) { if (!playing) { + String node_name = start_request; start_request = StringName(); - ERR_EXPLAIN("Can't travel to '" + String(start_request) + "' if state machine is not active."); + ERR_EXPLAIN("Can't travel to '" + node_name + "' if state machine is not playing."); ERR_FAIL_V(0); } diff --git a/scene/animation/animation_player.cpp b/scene/animation/animation_player.cpp index ead3516116..75088c79fe 100644 --- a/scene/animation/animation_player.cpp +++ b/scene/animation/animation_player.cpp @@ -37,12 +37,20 @@ #ifdef TOOLS_ENABLED #include "editor/editor_settings.h" +#include "scene/2d/skeleton_2d.h" void AnimatedValuesBackup::update_skeletons() { for (int i = 0; i < entries.size(); i++) { if (entries[i].bone_idx != -1) { + // 3D bone Object::cast_to<Skeleton>(entries[i].object)->notification(Skeleton::NOTIFICATION_UPDATE_SKELETON); + } else { + Bone2D *bone = Object::cast_to<Bone2D>(entries[i].object); + if (bone && bone->skeleton) { + // 2D bone + bone->skeleton->_update_transform(); + } } } } @@ -1200,7 +1208,7 @@ void AnimationPlayer::play(const StringName &p_name, float p_custom_blend, float // Animation reset BUT played backwards, set position to the end c.current.pos = c.current.from->animation->get_length(); } else if (!p_from_end && c.current.pos == c.current.from->animation->get_length()) { - // Animation resumed but already ended, set position to the beggining + // Animation resumed but already ended, set position to the beginning c.current.pos = 0; } } diff --git a/scene/animation/skeleton_ik.cpp b/scene/animation/skeleton_ik.cpp index 4da3e6ee28..06d6806f03 100644 --- a/scene/animation/skeleton_ik.cpp +++ b/scene/animation/skeleton_ik.cpp @@ -37,20 +37,20 @@ #ifndef _3D_DISABLED FabrikInverseKinematic::ChainItem *FabrikInverseKinematic::ChainItem::find_child(const BoneId p_bone_id) { - for (int i = childs.size() - 1; 0 <= i; --i) { - if (p_bone_id == childs[i].bone) { - return &childs.write[i]; + for (int i = children.size() - 1; 0 <= i; --i) { + if (p_bone_id == children[i].bone) { + return &children.write[i]; } } return NULL; } FabrikInverseKinematic::ChainItem *FabrikInverseKinematic::ChainItem::add_child(const BoneId p_bone_id) { - const int infant_child_id = childs.size(); - childs.resize(infant_child_id + 1); - childs.write[infant_child_id].bone = p_bone_id; - childs.write[infant_child_id].parent_item = this; - return &childs.write[infant_child_id]; + const int infant_child_id = children.size(); + children.resize(infant_child_id + 1); + children.write[infant_child_id].bone = p_bone_id; + children.write[infant_child_id].parent_item = this; + return &children.write[infant_child_id]; } /// Build a chain that starts from the root to tip @@ -144,8 +144,8 @@ void FabrikInverseKinematic::update_chain(const Skeleton *p_sk, ChainItem *p_cha p_chain_item->initial_transform = p_sk->get_bone_global_pose(p_chain_item->bone); p_chain_item->current_pos = p_chain_item->initial_transform.origin; - for (int i = p_chain_item->childs.size() - 1; 0 <= i; --i) { - update_chain(p_sk, &p_chain_item->childs.write[i]); + for (int i = p_chain_item->children.size() - 1; 0 <= i; --i) { + update_chain(p_sk, &p_chain_item->children.write[i]); } } @@ -210,9 +210,9 @@ void FabrikInverseKinematic::solve_simple_forwards(Chain &r_chain, bool p_solve_ while (sub_chain_root) { // Reach the tip sub_chain_root->current_pos = origin; - if (!sub_chain_root->childs.empty()) { + if (!sub_chain_root->children.empty()) { - ChainItem &child(sub_chain_root->childs.write[0]); + ChainItem &child(sub_chain_root->children.write[0]); // Is not tip // So calculate next origin location @@ -302,10 +302,10 @@ void FabrikInverseKinematic::solve(Task *p_task, real_t blending_delta, bool ove Transform new_bone_pose(ci->initial_transform); new_bone_pose.origin = ci->current_pos; - if (!ci->childs.empty()) { + if (!ci->children.empty()) { /// Rotate basis - const Vector3 initial_ori((ci->childs[0].initial_transform.origin - ci->initial_transform.origin).normalized()); + const Vector3 initial_ori((ci->children[0].initial_transform.origin - ci->initial_transform.origin).normalized()); const Vector3 rot_axis(initial_ori.cross(ci->current_ori).normalized()); if (rot_axis[0] != 0 && rot_axis[1] != 0 && rot_axis[2] != 0) { @@ -322,8 +322,8 @@ void FabrikInverseKinematic::solve(Task *p_task, real_t blending_delta, bool ove p_task->skeleton->set_bone_global_pose(ci->bone, new_bone_pose); - if (!ci->childs.empty()) - ci = &ci->childs.write[0]; + if (!ci->children.empty()) + ci = &ci->children.write[0]; else ci = NULL; } diff --git a/scene/animation/skeleton_ik.h b/scene/animation/skeleton_ik.h index 228184a2df..5d48b7be33 100644 --- a/scene/animation/skeleton_ik.h +++ b/scene/animation/skeleton_ik.h @@ -49,7 +49,7 @@ class FabrikInverseKinematic { struct ChainItem { - Vector<ChainItem> childs; + Vector<ChainItem> children; ChainItem *parent_item; // Bone info diff --git a/scene/audio/audio_stream_player.cpp b/scene/audio/audio_stream_player.cpp index 144e58d8b9..2def9fe8fc 100644 --- a/scene/audio/audio_stream_player.cpp +++ b/scene/audio/audio_stream_player.cpp @@ -32,8 +32,7 @@ #include "core/engine.h" - -void AudioStreamPlayer::_mix_to_bus(const AudioFrame *p_frames,int p_amount) { +void AudioStreamPlayer::_mix_to_bus(const AudioFrame *p_frames, int p_amount) { int bus_index = AudioServer::get_singleton()->thread_find_bus_index(bus); @@ -66,10 +65,8 @@ void AudioStreamPlayer::_mix_to_bus(const AudioFrame *p_frames,int p_amount) { } } - void AudioStreamPlayer::_mix_internal(bool p_fadeout) { - //get data AudioFrame *buffer = mix_buffer.ptrw(); int buffer_size = mix_buffer.size(); @@ -94,15 +91,14 @@ void AudioStreamPlayer::_mix_internal(bool p_fadeout) { //set volume for next mix mix_volume_db = target_volume; - _mix_to_bus(buffer,buffer_size); - + _mix_to_bus(buffer, buffer_size); } void AudioStreamPlayer::_mix_audio() { if (use_fadeout) { - _mix_to_bus(fadeout_buffer.ptr(),fadeout_buffer.size()); - use_fadeout=false; + _mix_to_bus(fadeout_buffer.ptr(), fadeout_buffer.size()); + use_fadeout = false; } if (!stream_playback.is_valid() || !active || @@ -121,7 +117,7 @@ void AudioStreamPlayer::_mix_audio() { if (setstop) { _mix_internal(true); stream_playback->stop(); - setstop=false; + setstop = false; } if (setseek >= 0.0 && !stop_has_priority) { @@ -154,7 +150,7 @@ void AudioStreamPlayer::_notification(int p_what) { if (p_what == NOTIFICATION_INTERNAL_PROCESS) { if (!active || (setseek < 0 && !stream_playback->is_playing())) { - active = false; + active = false; set_process_internal(false); emit_signal("finished"); } @@ -200,7 +196,7 @@ void AudioStreamPlayer::set_stream(Ref<AudioStream> p_stream) { vol += vol_inc; } - use_fadeout=true; + use_fadeout = true; } mix_buffer.resize(AudioServer::get_singleton()->thread_get_mix_buffer_size()); @@ -252,7 +248,7 @@ void AudioStreamPlayer::play(float p_from_pos) { if (stream_playback.is_valid()) { //mix_volume_db = volume_db; do not reset volume ramp here, can cause clicks setseek = p_from_pos; - stop_has_priority=false; + stop_has_priority = false; active = true; set_process_internal(true); } @@ -268,8 +264,8 @@ void AudioStreamPlayer::seek(float p_seconds) { void AudioStreamPlayer::stop() { if (stream_playback.is_valid() && active) { - setstop=true; - stop_has_priority=true; + setstop = true; + stop_has_priority = true; } } @@ -357,7 +353,7 @@ void AudioStreamPlayer::_validate_property(PropertyInfo &property) const { if (property.name == "bus") { String options; - for (int i = 0; i <AudioServer::get_singleton()->get_bus_count(); i++) { + for (int i = 0; i < AudioServer::get_singleton()->get_bus_count(); i++) { if (i > 0) options += ","; String name = AudioServer::get_singleton()->get_bus_name(i); @@ -442,8 +438,8 @@ AudioStreamPlayer::AudioStreamPlayer() { stream_paused_fade = false; mix_target = MIX_TARGET_STEREO; fadeout_buffer.resize(512); - setstop=false; - use_fadeout=false; + setstop = false; + use_fadeout = false; AudioServer::get_singleton()->connect("bus_layout_changed", this, "_bus_layout_changed"); } diff --git a/scene/audio/audio_stream_player.h b/scene/audio/audio_stream_player.h index 0b782b67e7..7987bd7e7d 100644 --- a/scene/audio/audio_stream_player.h +++ b/scene/audio/audio_stream_player.h @@ -112,7 +112,6 @@ public: Ref<AudioStreamPlayback> get_stream_playback(); - AudioStreamPlayer(); ~AudioStreamPlayer(); }; diff --git a/scene/gui/base_button.cpp b/scene/gui/base_button.cpp index e95781c181..5669743ec1 100644 --- a/scene/gui/base_button.cpp +++ b/scene/gui/base_button.cpp @@ -56,185 +56,53 @@ void BaseButton::_gui_input(Ref<InputEvent> p_event) { if (status.disabled) // no interaction with disabled button return; - Ref<InputEventMouseButton> b = p_event; + Ref<InputEventMouseButton> mouse_button = p_event; + bool ui_accept = p_event->is_action("ui_accept") && !p_event->is_echo(); - if (b.is_valid()) { - if (((1 << (b->get_button_index() - 1)) & button_mask) == 0) - return; - - if (status.pressing_button) - return; - - if (action_mode == ACTION_MODE_BUTTON_PRESS) { - - if (b->is_pressed()) { - - emit_signal("button_down"); - - if (!toggle_mode) { //mouse press attempt - - status.press_attempt = true; - status.pressing_inside = true; + bool button_masked = mouse_button.is_valid() && ((1 << (mouse_button->get_button_index() - 1)) & button_mask) > 0; + if (button_masked || ui_accept) { + if (p_event->is_pressed()) { + status.press_attempt = true; + status.pressing_inside = true; + emit_signal("button_down"); + } - pressed(); - if (get_script_instance()) { - Variant::CallError ce; - get_script_instance()->call(SceneStringNames::get_singleton()->_pressed, NULL, 0, ce); + if (status.press_attempt && status.pressing_inside) { + if (toggle_mode) { + if ((p_event->is_pressed() && action_mode == ACTION_MODE_BUTTON_PRESS) || (!p_event->is_pressed() && action_mode == ACTION_MODE_BUTTON_RELEASE)) { + if (action_mode == ACTION_MODE_BUTTON_PRESS) { + status.press_attempt = false; + status.pressing_inside = false; } - - _unpress_group(); - emit_signal("pressed"); - - } else { - status.pressed = !status.pressed; - pressed(); - _unpress_group(); - emit_signal("pressed"); - toggled(status.pressed); - if (get_script_instance()) { - get_script_instance()->call(SceneStringNames::get_singleton()->_toggled, status.pressed); - } - emit_signal("toggled", status.pressed); + pressed(); } - } else { - - emit_signal("button_up"); - - /* this is pointless if (status.press_attempt && status.pressing_inside) { - //released(); - emit_signal("released"); + if (!p_event->is_pressed()) { + pressed(); } -*/ - status.press_attempt = false; } - update(); - return; } - if (b->is_pressed()) { - - status.press_attempt = true; - status.pressing_inside = true; - emit_signal("button_down"); - - } else { - + if (!p_event->is_pressed()) { // pressed state should be correct with button_up signal emit_signal("button_up"); - - if (status.press_attempt && status.pressing_inside) { - - if (!toggle_mode) { //mouse press attempt - - pressed(); - if (get_script_instance()) { - Variant::CallError ce; - get_script_instance()->call(SceneStringNames::get_singleton()->_pressed, NULL, 0, ce); - } - - _unpress_group(); - emit_signal("pressed"); - - } else { - - status.pressed = !status.pressed; - - pressed(); - _unpress_group(); - emit_signal("pressed"); - - toggled(status.pressed); - if (get_script_instance()) { - get_script_instance()->call(SceneStringNames::get_singleton()->_toggled, status.pressed); - } - emit_signal("toggled", status.pressed); - } - } - status.press_attempt = false; } update(); + return; } - Ref<InputEventMouseMotion> mm = p_event; - - if (mm.is_valid()) { - if (status.press_attempt && status.pressing_button == 0) { + Ref<InputEventMouseMotion> mouse_motion = p_event; + if (mouse_motion.is_valid()) { + if (status.press_attempt) { bool last_press_inside = status.pressing_inside; - status.pressing_inside = has_point(mm->get_position()); - if (last_press_inside != status.pressing_inside) + status.pressing_inside = has_point(mouse_motion->get_position()); + if (last_press_inside != status.pressing_inside) { update(); - } - } - - if (!mm.is_valid() && !b.is_valid()) { - - if (p_event->is_echo()) { - return; - } - - if (status.disabled) { - return; - } - - if (status.press_attempt && status.pressing_button == 0) { - return; - } - - if (p_event->is_action("ui_accept")) { - - if (p_event->is_pressed()) { - - status.pressing_button++; - status.press_attempt = true; - status.pressing_inside = true; - emit_signal("button_down"); - - } else if (status.press_attempt) { - - if (status.pressing_button) - status.pressing_button--; - - if (status.pressing_button) - return; - - status.press_attempt = false; - status.pressing_inside = false; - - emit_signal("button_up"); - - if (!toggle_mode) { //mouse press attempt - - pressed(); - if (get_script_instance()) { - Variant::CallError ce; - get_script_instance()->call(SceneStringNames::get_singleton()->_pressed, NULL, 0, ce); - } - - _unpress_group(); - emit_signal("pressed"); - } else { - - status.pressed = !status.pressed; - - pressed(); - _unpress_group(); - emit_signal("pressed"); - - toggled(status.pressed); - if (get_script_instance()) { - get_script_instance()->call(SceneStringNames::get_singleton()->_toggled, status.pressed); - } - emit_signal("toggled", status.pressed); - } } - - accept_event(); - update(); } } } @@ -255,7 +123,6 @@ void BaseButton::_notification(int p_what) { if (status.press_attempt) { status.press_attempt = false; - status.pressing_button = 0; update(); } } @@ -268,9 +135,8 @@ void BaseButton::_notification(int p_what) { if (p_what == NOTIFICATION_FOCUS_EXIT) { - if (status.pressing_button && status.press_attempt) { + if (status.press_attempt) { status.press_attempt = false; - status.pressing_button = 0; status.hovering = false; update(); } else if (status.hovering) { @@ -290,21 +156,23 @@ void BaseButton::_notification(int p_what) { status.hovering = false; status.press_attempt = false; status.pressing_inside = false; - status.pressing_button = 0; } } void BaseButton::pressed() { - if (get_script_instance()) - get_script_instance()->call("pressed"); + if (get_script_instance()) { + get_script_instance()->call(SceneStringNames::get_singleton()->_pressed); + } + emit_signal("pressed"); } void BaseButton::toggled(bool p_pressed) { if (get_script_instance()) { - get_script_instance()->call("toggled", p_pressed); + get_script_instance()->call(SceneStringNames::get_singleton()->_toggled, p_pressed); } + emit_signal("toggled", p_pressed); } void BaseButton::set_disabled(bool p_disabled) { @@ -318,7 +186,6 @@ void BaseButton::set_disabled(bool p_disabled) { } status.press_attempt = false; status.pressing_inside = false; - status.pressing_button = 0; } update(); _change_notify("disabled"); @@ -341,6 +208,10 @@ void BaseButton::set_pressed(bool p_pressed) { if (p_pressed) { _unpress_group(); } + if (toggle_mode) { + toggled(status.pressed); + } + update(); } @@ -585,7 +456,6 @@ BaseButton::BaseButton() { status.hovering = false; status.pressing_inside = false; status.disabled = false; - status.pressing_button = 0; set_focus_mode(FOCUS_ALL); enabled_focus_mode = FOCUS_ALL; action_mode = ACTION_MODE_BUTTON_RELEASE; diff --git a/scene/gui/base_button.h b/scene/gui/base_button.h index 22a8f6d8fe..4762c27b28 100644 --- a/scene/gui/base_button.h +++ b/scene/gui/base_button.h @@ -65,7 +65,6 @@ private: bool pressing_inside; bool disabled; - int pressing_button; } status; diff --git a/scene/gui/container.cpp b/scene/gui/container.cpp index 7f1ca58d58..1f9bfb9936 100644 --- a/scene/gui/container.cpp +++ b/scene/gui/container.cpp @@ -177,7 +177,7 @@ String Container::get_configuration_warning() const { if (warning != String()) { warning += "\n"; } - warning += TTR("Container by itself serves no purpose unless a script configures it's children placement behavior.\nIf you dont't intend to add a script, then please use a plain 'Control' node instead."); + warning += TTR("Container by itself serves no purpose unless a script configures it's children placement behavior.\nIf you don't intend to add a script, then please use a plain 'Control' node instead."); } return warning; } diff --git a/scene/gui/control.cpp b/scene/gui/control.cpp index a38f97a90c..76275c2420 100644 --- a/scene/gui/control.cpp +++ b/scene/gui/control.cpp @@ -43,6 +43,7 @@ #include "scene/scene_string_names.h" #ifdef TOOLS_ENABLED #include "editor/editor_settings.h" +#include "editor/plugins/canvas_item_editor_plugin.h" #endif #include <stdio.h> @@ -66,6 +67,7 @@ Dictionary Control::_edit_get_state() const { s["margins"] = margins; return s; } + void Control::_edit_set_state(const Dictionary &p_state) { Dictionary state = p_state; @@ -87,7 +89,12 @@ void Control::_edit_set_state(const Dictionary &p_state) { } void Control::_edit_set_position(const Point2 &p_position) { +#ifdef TOOLS_ENABLED + set_position(p_position, CanvasItemEditor::get_singleton()->is_anchors_mode_enabled()); +#else + // Unlikely to happen. TODO: enclose all _edit_ functions into TOOLS_ENABLED set_position(p_position); +#endif }; Point2 Control::_edit_get_position() const { @@ -103,8 +110,14 @@ Size2 Control::_edit_get_scale() const { } void Control::_edit_set_rect(const Rect2 &p_edit_rect) { +#ifdef TOOLS_ENABLED + set_position((get_position() + get_transform().basis_xform(p_edit_rect.position)).snapped(Vector2(1, 1)), CanvasItemEditor::get_singleton()->is_anchors_mode_enabled()); + set_size(p_edit_rect.size.snapped(Vector2(1, 1)), CanvasItemEditor::get_singleton()->is_anchors_mode_enabled()); +#else + // Unlikely to happen. TODO: enclose all _edit_ functions into TOOLS_ENABLED set_position((get_position() + get_transform().basis_xform(p_edit_rect.position)).snapped(Vector2(1, 1))); set_size(p_edit_rect.size.snapped(Vector2(1, 1))); +#endif } Rect2 Control::_edit_get_rect() const { @@ -276,7 +289,7 @@ void Control::_update_minimum_size() { Size2 minsize = get_combined_minimum_size(); if (minsize.x > data.size_cache.x || minsize.y > data.size_cache.y) { - _size_changed(); + set_size(data.size_cache); } data.updating_last_minimum_size = false; @@ -1366,7 +1379,7 @@ void Control::set_anchor(Margin p_margin, float p_anchor, bool p_keep_margin, bo float previous_margin_pos = data.margin[p_margin] + data.anchor[p_margin] * parent_range; float previous_opposite_margin_pos = data.margin[(p_margin + 2) % 4] + data.anchor[(p_margin + 2) % 4] * parent_range; - data.anchor[p_margin] = CLAMP(p_anchor, 0.0, 1.0); + data.anchor[p_margin] = p_anchor; if (((p_margin == MARGIN_LEFT || p_margin == MARGIN_TOP) && data.anchor[p_margin] > data.anchor[(p_margin + 2) % 4]) || ((p_margin == MARGIN_RIGHT || p_margin == MARGIN_BOTTOM) && data.anchor[p_margin] < data.anchor[(p_margin + 2) % 4])) { @@ -1395,15 +1408,7 @@ void Control::set_anchor(Margin p_margin, float p_anchor, bool p_keep_margin, bo } void Control::_set_anchor(Margin p_margin, float p_anchor) { -#ifdef TOOLS_ENABLED - if (is_inside_tree() && Engine::get_singleton()->is_editor_hint()) { - set_anchor(p_margin, p_anchor, EDITOR_DEF("editors/2d/keep_margins_when_changing_anchors", false)); - } else { - set_anchor(p_margin, p_anchor, false); - } -#else - set_anchor(p_margin, p_anchor, false); -#endif + set_anchor(p_margin, p_anchor); } void Control::set_anchor_and_margin(Margin p_margin, float p_anchor, float p_pos, bool p_push_opposite_anchor) { @@ -1412,7 +1417,7 @@ void Control::set_anchor_and_margin(Margin p_margin, float p_anchor, float p_pos set_margin(p_margin, p_pos); } -void Control::set_anchors_preset(LayoutPreset p_preset, bool p_keep_margin) { +void Control::set_anchors_preset(LayoutPreset p_preset, bool p_keep_margins) { //Left switch (p_preset) { case PRESET_TOP_LEFT: @@ -1423,21 +1428,21 @@ void Control::set_anchors_preset(LayoutPreset p_preset, bool p_keep_margin) { case PRESET_LEFT_WIDE: case PRESET_HCENTER_WIDE: case PRESET_WIDE: - set_anchor(MARGIN_LEFT, ANCHOR_BEGIN, p_keep_margin); + set_anchor(MARGIN_LEFT, ANCHOR_BEGIN, p_keep_margins); break; case PRESET_CENTER_TOP: case PRESET_CENTER_BOTTOM: case PRESET_CENTER: case PRESET_VCENTER_WIDE: - set_anchor(MARGIN_LEFT, 0.5, p_keep_margin); + set_anchor(MARGIN_LEFT, 0.5, p_keep_margins); break; case PRESET_TOP_RIGHT: case PRESET_BOTTOM_RIGHT: case PRESET_CENTER_RIGHT: case PRESET_RIGHT_WIDE: - set_anchor(MARGIN_LEFT, ANCHOR_END, p_keep_margin); + set_anchor(MARGIN_LEFT, ANCHOR_END, p_keep_margins); break; } @@ -1451,21 +1456,21 @@ void Control::set_anchors_preset(LayoutPreset p_preset, bool p_keep_margin) { case PRESET_TOP_WIDE: case PRESET_VCENTER_WIDE: case PRESET_WIDE: - set_anchor(MARGIN_TOP, ANCHOR_BEGIN, p_keep_margin); + set_anchor(MARGIN_TOP, ANCHOR_BEGIN, p_keep_margins); break; case PRESET_CENTER_LEFT: case PRESET_CENTER_RIGHT: case PRESET_CENTER: case PRESET_HCENTER_WIDE: - set_anchor(MARGIN_TOP, 0.5, p_keep_margin); + set_anchor(MARGIN_TOP, 0.5, p_keep_margins); break; case PRESET_BOTTOM_LEFT: case PRESET_BOTTOM_RIGHT: case PRESET_CENTER_BOTTOM: case PRESET_BOTTOM_WIDE: - set_anchor(MARGIN_TOP, ANCHOR_END, p_keep_margin); + set_anchor(MARGIN_TOP, ANCHOR_END, p_keep_margins); break; } @@ -1475,14 +1480,14 @@ void Control::set_anchors_preset(LayoutPreset p_preset, bool p_keep_margin) { case PRESET_BOTTOM_LEFT: case PRESET_CENTER_LEFT: case PRESET_LEFT_WIDE: - set_anchor(MARGIN_RIGHT, ANCHOR_BEGIN, p_keep_margin); + set_anchor(MARGIN_RIGHT, ANCHOR_BEGIN, p_keep_margins); break; case PRESET_CENTER_TOP: case PRESET_CENTER_BOTTOM: case PRESET_CENTER: case PRESET_VCENTER_WIDE: - set_anchor(MARGIN_RIGHT, 0.5, p_keep_margin); + set_anchor(MARGIN_RIGHT, 0.5, p_keep_margins); break; case PRESET_TOP_RIGHT: @@ -1493,7 +1498,7 @@ void Control::set_anchors_preset(LayoutPreset p_preset, bool p_keep_margin) { case PRESET_BOTTOM_WIDE: case PRESET_HCENTER_WIDE: case PRESET_WIDE: - set_anchor(MARGIN_RIGHT, ANCHOR_END, p_keep_margin); + set_anchor(MARGIN_RIGHT, ANCHOR_END, p_keep_margins); break; } @@ -1503,14 +1508,14 @@ void Control::set_anchors_preset(LayoutPreset p_preset, bool p_keep_margin) { case PRESET_TOP_RIGHT: case PRESET_CENTER_TOP: case PRESET_TOP_WIDE: - set_anchor(MARGIN_BOTTOM, ANCHOR_BEGIN, p_keep_margin); + set_anchor(MARGIN_BOTTOM, ANCHOR_BEGIN, p_keep_margins); break; case PRESET_CENTER_LEFT: case PRESET_CENTER_RIGHT: case PRESET_CENTER: case PRESET_HCENTER_WIDE: - set_anchor(MARGIN_BOTTOM, 0.5, p_keep_margin); + set_anchor(MARGIN_BOTTOM, 0.5, p_keep_margins); break; case PRESET_BOTTOM_LEFT: @@ -1521,7 +1526,7 @@ void Control::set_anchors_preset(LayoutPreset p_preset, bool p_keep_margin) { case PRESET_BOTTOM_WIDE: case PRESET_VCENTER_WIDE: case PRESET_WIDE: - set_anchor(MARGIN_BOTTOM, ANCHOR_END, p_keep_margin); + set_anchor(MARGIN_BOTTOM, ANCHOR_END, p_keep_margins); break; } } @@ -1714,7 +1719,11 @@ Point2 Control::get_global_position() const { return get_global_transform().get_origin(); } -void Control::set_global_position(const Point2 &p_point) { +void Control::_set_global_position(const Point2 &p_point) { + set_global_position(p_point); +} + +void Control::set_global_position(const Point2 &p_point, bool p_keep_margins) { Transform2D inv; @@ -1723,7 +1732,7 @@ void Control::set_global_position(const Point2 &p_point) { inv = data.parent_canvas_item->get_global_transform().affine_inverse(); } - set_position(inv.xform(p_point)); + set_position(inv.xform(p_point), p_keep_margins); } Rect2 Control::_compute_child_rect(const float p_anchors[4], const float p_margins[4]) const { @@ -1737,6 +1746,15 @@ Rect2 Control::_compute_child_rect(const float p_anchors[4], const float p_margi return result; } +void Control::_compute_anchors(Rect2 p_rect, const float p_margins[4], float (&r_anchors)[4]) { + + Size2 parent_rect_size = get_parent_anchorable_rect().size; + r_anchors[0] = (p_rect.position.x - p_margins[0]) / parent_rect_size.x; + r_anchors[1] = (p_rect.position.y - p_margins[1]) / parent_rect_size.y; + r_anchors[2] = (p_rect.position.x + p_rect.size.x - p_margins[2]) / parent_rect_size.x; + r_anchors[3] = (p_rect.position.y + p_rect.size.y - p_margins[3]) / parent_rect_size.y; +} + void Control::_compute_margins(Rect2 p_rect, const float p_anchors[4], float (&r_margins)[4]) { Size2 parent_rect_size = get_parent_anchorable_rect().size; @@ -1746,13 +1764,28 @@ void Control::_compute_margins(Rect2 p_rect, const float p_anchors[4], float (&r r_margins[3] = p_rect.position.y + p_rect.size.y - (p_anchors[3] * parent_rect_size.y); } -void Control::set_position(const Size2 &p_point) { +void Control::_set_position(const Size2 &p_point) { + set_position(p_point); +} - _compute_margins(Rect2(p_point, data.size_cache), data.anchor, data.margin); +void Control::set_position(const Size2 &p_point, bool p_keep_margins) { + if (p_keep_margins) { + _compute_anchors(Rect2(p_point, data.size_cache), data.margin, data.anchor); + _change_notify("anchor_left"); + _change_notify("anchor_right"); + _change_notify("anchor_top"); + _change_notify("anchor_bottom"); + } else { + _compute_margins(Rect2(p_point, data.size_cache), data.anchor, data.margin); + } _size_changed(); } -void Control::set_size(const Size2 &p_size) { +void Control::_set_size(const Size2 &p_size) { + set_size(p_size); +} + +void Control::set_size(const Size2 &p_size, bool p_keep_margins) { Size2 new_size = p_size; Size2 min = get_combined_minimum_size(); @@ -1761,7 +1794,15 @@ void Control::set_size(const Size2 &p_size) { if (new_size.y < min.y) new_size.y = min.y; - _compute_margins(Rect2(data.pos_cache, new_size), data.anchor, data.margin); + if (p_keep_margins) { + _compute_anchors(Rect2(data.pos_cache, new_size), data.margin, data.anchor); + _change_notify("anchor_left"); + _change_notify("anchor_right"); + _change_notify("anchor_top"); + _change_notify("anchor_bottom"); + } else { + _compute_margins(Rect2(data.pos_cache, new_size), data.anchor, data.margin); + } _size_changed(); } @@ -1799,53 +1840,72 @@ Rect2 Control::get_anchorable_rect() const { void Control::add_icon_override(const StringName &p_name, const Ref<Texture> &p_icon) { - ERR_FAIL_COND(p_icon.is_null()); if (data.icon_override.has(p_name)) { data.icon_override[p_name]->disconnect("changed", this, "_override_changed"); } - data.icon_override[p_name] = p_icon; - if (data.icon_override[p_name].is_valid()) { - data.icon_override[p_name]->connect("changed", this, "_override_changed", Vector<Variant>(), CONNECT_REFERENCE_COUNTED); + + // clear if "null" is passed instead of a icon + if (p_icon.is_null()) { + data.icon_override.erase(p_name); + } else { + data.icon_override[p_name] = p_icon; + if (data.icon_override[p_name].is_valid()) { + data.icon_override[p_name]->connect("changed", this, "_override_changed", Vector<Variant>(), CONNECT_REFERENCE_COUNTED); + } } notification(NOTIFICATION_THEME_CHANGED); } void Control::add_shader_override(const StringName &p_name, const Ref<Shader> &p_shader) { - ERR_FAIL_COND(p_shader.is_null()); + if (data.shader_override.has(p_name)) { data.shader_override[p_name]->disconnect("changed", this, "_override_changed"); } - data.shader_override[p_name] = p_shader; - if (data.shader_override[p_name].is_valid()) { - data.shader_override[p_name]->connect("changed", this, "_override_changed", Vector<Variant>(), CONNECT_REFERENCE_COUNTED); + + // clear if "null" is passed instead of a shader + if (p_shader.is_null()) { + data.shader_override.erase(p_name); + } else { + data.shader_override[p_name] = p_shader; + if (data.shader_override[p_name].is_valid()) { + data.shader_override[p_name]->connect("changed", this, "_override_changed", Vector<Variant>(), CONNECT_REFERENCE_COUNTED); + } } notification(NOTIFICATION_THEME_CHANGED); } void Control::add_style_override(const StringName &p_name, const Ref<StyleBox> &p_style) { - ERR_FAIL_COND(p_style.is_null()); if (data.style_override.has(p_name)) { data.style_override[p_name]->disconnect("changed", this, "_override_changed"); } - data.style_override[p_name] = p_style; - if (data.style_override[p_name].is_valid()) { - data.style_override[p_name]->connect("changed", this, "_override_changed", Vector<Variant>(), CONNECT_REFERENCE_COUNTED); - } + // clear if "null" is passed instead of a style + if (p_style.is_null()) { + data.style_override.erase(p_name); + } else { + data.style_override[p_name] = p_style; + if (data.style_override[p_name].is_valid()) { + data.style_override[p_name]->connect("changed", this, "_override_changed", Vector<Variant>(), CONNECT_REFERENCE_COUNTED); + } + } notification(NOTIFICATION_THEME_CHANGED); } void Control::add_font_override(const StringName &p_name, const Ref<Font> &p_font) { - ERR_FAIL_COND(p_font.is_null()); if (data.font_override.has(p_name)) { data.font_override[p_name]->disconnect("changed", this, "_override_changed"); } - data.font_override[p_name] = p_font; - if (data.font_override[p_name].is_valid()) { - data.font_override[p_name]->connect("changed", this, "_override_changed", Vector<Variant>(), CONNECT_REFERENCE_COUNTED); - } + // clear if "null" is passed instead of a font + if (p_font.is_null()) { + data.font_override.erase(p_name); + } else { + data.font_override[p_name] = p_font; + if (data.font_override[p_name].is_valid()) { + data.font_override[p_name]->connect("changed", this, "_override_changed", Vector<Variant>(), CONNECT_REFERENCE_COUNTED); + } + } notification(NOTIFICATION_THEME_CHANGED); } void Control::add_color_override(const StringName &p_name, const Color &p_color) { @@ -2702,20 +2762,23 @@ void Control::_bind_methods() { ClassDB::bind_method(D_METHOD("accept_event"), &Control::accept_event); ClassDB::bind_method(D_METHOD("get_minimum_size"), &Control::get_minimum_size); ClassDB::bind_method(D_METHOD("get_combined_minimum_size"), &Control::get_combined_minimum_size); - ClassDB::bind_method(D_METHOD("set_anchors_preset", "preset", "keep_margin"), &Control::set_anchors_preset, DEFVAL(false)); + ClassDB::bind_method(D_METHOD("set_anchors_preset", "preset", "keep_margins"), &Control::set_anchors_preset, DEFVAL(false)); ClassDB::bind_method(D_METHOD("set_margins_preset", "preset", "resize_mode", "margin"), &Control::set_margins_preset, DEFVAL(PRESET_MODE_MINSIZE), DEFVAL(0)); ClassDB::bind_method(D_METHOD("set_anchors_and_margins_preset", "preset", "resize_mode", "margin"), &Control::set_anchors_and_margins_preset, DEFVAL(PRESET_MODE_MINSIZE), DEFVAL(0)); - ClassDB::bind_method(D_METHOD("set_anchor", "margin", "anchor", "keep_margin", "push_opposite_anchor"), &Control::set_anchor, DEFVAL(false), DEFVAL(true)); ClassDB::bind_method(D_METHOD("_set_anchor", "margin", "anchor"), &Control::_set_anchor); + ClassDB::bind_method(D_METHOD("set_anchor", "margin", "anchor", "keep_margin", "push_opposite_anchor"), &Control::set_anchor, DEFVAL(false), DEFVAL(true)); ClassDB::bind_method(D_METHOD("get_anchor", "margin"), &Control::get_anchor); ClassDB::bind_method(D_METHOD("set_margin", "margin", "offset"), &Control::set_margin); ClassDB::bind_method(D_METHOD("set_anchor_and_margin", "margin", "anchor", "offset", "push_opposite_anchor"), &Control::set_anchor_and_margin, DEFVAL(false)); ClassDB::bind_method(D_METHOD("set_begin", "position"), &Control::set_begin); ClassDB::bind_method(D_METHOD("set_end", "position"), &Control::set_end); - ClassDB::bind_method(D_METHOD("set_position", "position"), &Control::set_position); - ClassDB::bind_method(D_METHOD("set_size", "size"), &Control::set_size); + ClassDB::bind_method(D_METHOD("set_position", "position", "keep_margins"), &Control::set_position, DEFVAL(false)); + ClassDB::bind_method(D_METHOD("_set_position", "margin"), &Control::_set_position); + ClassDB::bind_method(D_METHOD("set_size", "size", "keep_margins"), &Control::set_size, DEFVAL(false)); + ClassDB::bind_method(D_METHOD("_set_size", "size"), &Control::_set_size); ClassDB::bind_method(D_METHOD("set_custom_minimum_size", "size"), &Control::set_custom_minimum_size); - ClassDB::bind_method(D_METHOD("set_global_position", "position"), &Control::set_global_position); + ClassDB::bind_method(D_METHOD("set_global_position", "position", "keep_margins"), &Control::set_global_position, DEFVAL(false)); + ClassDB::bind_method(D_METHOD("_set_global_position", "position"), &Control::_set_global_position); ClassDB::bind_method(D_METHOD("set_rotation", "radians"), &Control::set_rotation); ClassDB::bind_method(D_METHOD("set_rotation_degrees", "degrees"), &Control::set_rotation_degrees); ClassDB::bind_method(D_METHOD("set_scale", "scale"), &Control::set_scale); @@ -2835,10 +2898,10 @@ void Control::_bind_methods() { BIND_VMETHOD(MethodInfo(Variant::BOOL, "_clips_input")); ADD_GROUP("Anchor", "anchor_"); - ADD_PROPERTYI(PropertyInfo(Variant::REAL, "anchor_left", PROPERTY_HINT_RANGE, "0,1,0.01"), "_set_anchor", "get_anchor", MARGIN_LEFT); - ADD_PROPERTYI(PropertyInfo(Variant::REAL, "anchor_top", PROPERTY_HINT_RANGE, "0,1,0.01"), "_set_anchor", "get_anchor", MARGIN_TOP); - ADD_PROPERTYI(PropertyInfo(Variant::REAL, "anchor_right", PROPERTY_HINT_RANGE, "0,1,0.01"), "_set_anchor", "get_anchor", MARGIN_RIGHT); - ADD_PROPERTYI(PropertyInfo(Variant::REAL, "anchor_bottom", PROPERTY_HINT_RANGE, "0,1,0.01"), "_set_anchor", "get_anchor", MARGIN_BOTTOM); + ADD_PROPERTYI(PropertyInfo(Variant::REAL, "anchor_left", PROPERTY_HINT_RANGE, "0,1,0.01,or_lesser,or_greater"), "_set_anchor", "get_anchor", MARGIN_LEFT); + ADD_PROPERTYI(PropertyInfo(Variant::REAL, "anchor_top", PROPERTY_HINT_RANGE, "0,1,0.01,or_lesser,or_greater"), "_set_anchor", "get_anchor", MARGIN_TOP); + ADD_PROPERTYI(PropertyInfo(Variant::REAL, "anchor_right", PROPERTY_HINT_RANGE, "0,1,0.01,or_lesser,or_greater"), "_set_anchor", "get_anchor", MARGIN_RIGHT); + ADD_PROPERTYI(PropertyInfo(Variant::REAL, "anchor_bottom", PROPERTY_HINT_RANGE, "0,1,0.01,or_lesser,or_greater"), "_set_anchor", "get_anchor", MARGIN_BOTTOM); ADD_GROUP("Margin", "margin_"); ADD_PROPERTYI(PropertyInfo(Variant::INT, "margin_left", PROPERTY_HINT_RANGE, "-4096,4096"), "set_margin", "get_margin", MARGIN_LEFT); @@ -2851,9 +2914,9 @@ void Control::_bind_methods() { ADD_PROPERTY(PropertyInfo(Variant::INT, "grow_vertical", PROPERTY_HINT_ENUM, "Begin,End,Both"), "set_v_grow_direction", "get_v_grow_direction"); ADD_GROUP("Rect", "rect_"); - ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "rect_position", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR), "set_position", "get_position"); - ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "rect_global_position", PROPERTY_HINT_NONE, "", 0), "set_global_position", "get_global_position"); - ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "rect_size", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR), "set_size", "get_size"); + ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "rect_position", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR), "_set_position", "get_position"); + ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "rect_global_position", PROPERTY_HINT_NONE, "", 0), "_set_global_position", "get_global_position"); + ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "rect_size", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR), "_set_size", "get_size"); ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "rect_min_size"), "set_custom_minimum_size", "get_custom_minimum_size"); ADD_PROPERTY(PropertyInfo(Variant::REAL, "rect_rotation", PROPERTY_HINT_RANGE, "-1080,1080,0.01"), "set_rotation_degrees", "get_rotation_degrees"); ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "rect_scale"), "set_scale", "get_scale"); diff --git a/scene/gui/control.h b/scene/gui/control.h index 5e33f6ba43..a6f9a442ae 100644 --- a/scene/gui/control.h +++ b/scene/gui/control.h @@ -217,6 +217,9 @@ private: Control *_get_focus_neighbour(Margin p_margin, int p_count = 0); void _set_anchor(Margin p_margin, float p_anchor); + void _set_position(const Point2 &p_point); + void _set_global_position(const Point2 &p_point); + void _set_size(const Size2 &p_size); void _propagate_theme_changed(CanvasItem *p_at, Control *p_owner, bool p_assign = true); void _theme_changed(); @@ -229,6 +232,7 @@ private: Rect2 _compute_child_rect(const float p_anchors[4], const float p_margins[4]) const; void _compute_margins(Rect2 p_rect, const float p_anchors[4], float (&r_margins)[4]); + void _compute_anchors(Rect2 p_rect, const float p_margins[4], float (&r_anchors)[4]); void _size_changed(); String _get_tooltip() const; @@ -325,7 +329,7 @@ public: /* POSITIONING */ - void set_anchors_preset(LayoutPreset p_preset, bool p_keep_margin = true); + void set_anchors_preset(LayoutPreset p_preset, bool p_keep_margins = true); void set_margins_preset(LayoutPreset p_preset, LayoutPresetMode p_resize_mode = PRESET_MODE_MINSIZE, int p_margin = 0); void set_anchors_and_margins_preset(LayoutPreset p_preset, LayoutPresetMode p_resize_mode = PRESET_MODE_MINSIZE, int p_margin = 0); @@ -343,12 +347,12 @@ public: Point2 get_begin() const; Point2 get_end() const; - void set_position(const Point2 &p_point); - void set_global_position(const Point2 &p_point); + void set_position(const Point2 &p_point, bool p_keep_margins = false); + void set_global_position(const Point2 &p_point, bool p_keep_margins = false); Point2 get_position() const; Point2 get_global_position() const; - void set_size(const Size2 &p_size); + void set_size(const Size2 &p_size, bool p_keep_margins = false); Size2 get_size() const; Rect2 get_rect() const; diff --git a/scene/gui/item_list.cpp b/scene/gui/item_list.cpp index 026374ded1..406c8e4f48 100644 --- a/scene/gui/item_list.cpp +++ b/scene/gui/item_list.cpp @@ -470,6 +470,8 @@ Size2 ItemList::Item::get_icon_size() const { void ItemList::_gui_input(const Ref<InputEvent> &p_event) { + double prev_scroll = scroll_bar->get_value(); + Ref<InputEventMouseMotion> mm = p_event; if (defer_select_single >= 0 && mm.is_valid()) { defer_select_single = -1; @@ -767,6 +769,9 @@ void ItemList::_gui_input(const Ref<InputEvent> &p_event) { scroll_bar->set_value(scroll_bar->get_value() + scroll_bar->get_page() * pan_gesture->get_delta().y / 8); } + + if (scroll_bar->get_value() != prev_scroll) + accept_event(); //accept event if scroll changed } void ItemList::ensure_current_is_visible() { diff --git a/scene/gui/line_edit.cpp b/scene/gui/line_edit.cpp index 2d18a80833..fa1a63f5e2 100644 --- a/scene/gui/line_edit.cpp +++ b/scene/gui/line_edit.cpp @@ -68,6 +68,7 @@ void LineEdit::_gui_input(Ref<InputEvent> p_event) { _reset_caret_blink_timer(); if (b->is_pressed()) { + accept_event(); //don't pass event further when clicked on text field if (!text.empty() && is_editable() && _is_over_clear_button(b->get_position())) { clear_button_status.press_attempt = true; clear_button_status.pressing_inside = true; @@ -1656,6 +1657,7 @@ LineEdit::LineEdit() { context_menu_enabled = true; menu = memnew(PopupMenu); add_child(menu); + editable = false; // initialise to opposite first, so we get past the early-out in set_editable set_editable(true); menu->connect("id_pressed", this, "menu_option"); expand_to_text_length = false; diff --git a/scene/gui/scroll_bar.cpp b/scene/gui/scroll_bar.cpp index 2938654ed9..686d1c96cc 100644 --- a/scene/gui/scroll_bar.cpp +++ b/scene/gui/scroll_bar.cpp @@ -53,29 +53,19 @@ void ScrollBar::_gui_input(Ref<InputEvent> p_event) { if (b.is_valid()) { accept_event(); - if (b->get_button_index() == 5 && b->is_pressed()) { + if (b->get_button_index() == BUTTON_WHEEL_DOWN && b->is_pressed()) { - /* - if (orientation==VERTICAL) - set_val( get_val() + get_page() / 4.0 ); - else - */ set_value(get_value() + get_page() / 4.0); accept_event(); } - if (b->get_button_index() == 4 && b->is_pressed()) { + if (b->get_button_index() == BUTTON_WHEEL_UP && b->is_pressed()) { - /* - if (orientation==HORIZONTAL) - set_val( get_val() - get_page() / 4.0 ); - else - */ set_value(get_value() - get_page() / 4.0); accept_event(); } - if (b->get_button_index() != 1) + if (b->get_button_index() != BUTTON_LEFT) return; if (b->is_pressed()) { diff --git a/scene/gui/scroll_container.cpp b/scene/gui/scroll_container.cpp index e50a71b0ff..a1034937b5 100644 --- a/scene/gui/scroll_container.cpp +++ b/scene/gui/scroll_container.cpp @@ -88,13 +88,16 @@ void ScrollContainer::_cancel_drag() { void ScrollContainer::_gui_input(const Ref<InputEvent> &p_gui_input) { + double prev_v_scroll = v_scroll->get_value(); + double prev_h_scroll = h_scroll->get_value(); + Ref<InputEventMouseButton> mb = p_gui_input; if (mb.is_valid()) { if (mb->get_button_index() == BUTTON_WHEEL_UP && mb->is_pressed()) { // only horizontal is enabled, scroll horizontally - if (h_scroll->is_visible() && !v_scroll->is_visible()) { + if (h_scroll->is_visible() && (!v_scroll->is_visible() || mb->get_shift())) { h_scroll->set_value(h_scroll->get_value() - h_scroll->get_page() / 8 * mb->get_factor()); } else if (v_scroll->is_visible_in_tree()) { v_scroll->set_value(v_scroll->get_value() - v_scroll->get_page() / 8 * mb->get_factor()); @@ -103,7 +106,7 @@ void ScrollContainer::_gui_input(const Ref<InputEvent> &p_gui_input) { if (mb->get_button_index() == BUTTON_WHEEL_DOWN && mb->is_pressed()) { // only horizontal is enabled, scroll horizontally - if (h_scroll->is_visible() && !v_scroll->is_visible()) { + if (h_scroll->is_visible() && (!v_scroll->is_visible() || mb->get_shift())) { h_scroll->set_value(h_scroll->get_value() + h_scroll->get_page() / 8 * mb->get_factor()); } else if (v_scroll->is_visible()) { v_scroll->set_value(v_scroll->get_value() + v_scroll->get_page() / 8 * mb->get_factor()); @@ -122,6 +125,9 @@ void ScrollContainer::_gui_input(const Ref<InputEvent> &p_gui_input) { } } + if (v_scroll->get_value() != prev_v_scroll || h_scroll->get_value() != prev_h_scroll) + accept_event(); //accept event if scroll changed + if (!OS::get_singleton()->has_touchscreen_ui_hint()) return; @@ -204,6 +210,9 @@ void ScrollContainer::_gui_input(const Ref<InputEvent> &p_gui_input) { v_scroll->set_value(v_scroll->get_value() + v_scroll->get_page() * pan_gesture->get_delta().y / 8); } } + + if (v_scroll->get_value() != prev_v_scroll || h_scroll->get_value() != prev_h_scroll) + accept_event(); //accept event if scroll changed } void ScrollContainer::_update_scrollbar_position() { diff --git a/scene/gui/spin_box.cpp b/scene/gui/spin_box.cpp index d21143739c..e778af3ceb 100644 --- a/scene/gui/spin_box.cpp +++ b/scene/gui/spin_box.cpp @@ -277,6 +277,7 @@ SpinBox::SpinBox() { add_child(line_edit); line_edit->set_anchors_and_margins_preset(Control::PRESET_WIDE); + line_edit->set_mouse_filter(MOUSE_FILTER_PASS); //connect("value_changed",this,"_value_changed"); line_edit->connect("text_entered", this, "_text_entered", Vector<Variant>(), CONNECT_DEFERRED); line_edit->connect("focus_exited", this, "_line_edit_focus_exit", Vector<Variant>(), CONNECT_DEFERRED); diff --git a/scene/gui/text_edit.cpp b/scene/gui/text_edit.cpp index 71e84e974f..acd2950b4c 100644 --- a/scene/gui/text_edit.cpp +++ b/scene/gui/text_edit.cpp @@ -104,6 +104,13 @@ static CharType _get_right_pair_symbol(CharType c) { return 0; } +static int _find_first_non_whitespace_column_of_line(const String &line) { + int left = 0; + while (left < line.length() && _is_whitespace(line[left])) + left++; + return left; +} + void TextEdit::Text::set_font(const Ref<Font> &p_font) { font = p_font; @@ -292,6 +299,7 @@ void TextEdit::Text::insert(int p_at, const String &p_text) { line.marked = false; line.safe = false; line.breakpoint = false; + line.bookmark = false; line.hidden = false; line.width_cache = -1; line.wrap_amount_cache = -1; @@ -346,7 +354,7 @@ void TextEdit::_update_scrollbars() { if (line_numbers) total_width += cache.line_number_w; - if (draw_breakpoint_gutter) { + if (draw_breakpoint_gutter || draw_bookmark_gutter) { total_width += cache.breakpoint_gutter_width; } @@ -605,7 +613,7 @@ void TextEdit::_notification(int p_what) { draw_caret = false; } - if (draw_breakpoint_gutter) { + if (draw_breakpoint_gutter || draw_bookmark_gutter) { breakpoint_gutter_width = (get_row_height() * 55) / 100; cache.breakpoint_gutter_width = breakpoint_gutter_width; } else { @@ -954,6 +962,16 @@ void TextEdit::_notification(int p_what) { #endif } + // draw bookmark marker + if (text.is_bookmark(line)) { + if (draw_bookmark_gutter) { + int vertical_gap = (get_row_height() * 40) / 100; + int horizontal_gap = (cache.breakpoint_gutter_width * 30) / 100; + int marker_radius = get_row_height() - (vertical_gap * 2); + VisualServer::get_singleton()->canvas_item_add_circle(ci, Point2(cache.style_normal->get_margin(MARGIN_LEFT) + horizontal_gap - 2 + marker_radius / 2, ofs_y + vertical_gap + marker_radius / 2), marker_radius, Color(cache.bookmark_color.r, cache.bookmark_color.g, cache.bookmark_color.b)); + } + } + // draw breakpoint marker if (text.is_breakpoint(line)) { if (draw_breakpoint_gutter) { @@ -1095,7 +1113,7 @@ void TextEdit::_notification(int p_what) { if (line == cursor.line && cursor_wrap_index == line_wrap_index && highlight_current_line) { // draw the wrap indent offset highlight if (line_wrap_index != 0 && j == 0) { - VisualServer::get_singleton()->canvas_item_add_rect(ci, Rect2(char_ofs + char_margin - indent_px, ofs_y, (char_ofs + char_margin), get_row_height()), cache.current_line_color); + VisualServer::get_singleton()->canvas_item_add_rect(ci, Rect2(char_ofs + char_margin - indent_px, ofs_y, indent_px, get_row_height()), cache.current_line_color); } // if its the last char draw to end of the line if (j == str.length() - 1) { @@ -1634,31 +1652,25 @@ void TextEdit::backspace_at_cursor() { _consume_backspace_for_pair_symbol(prev_line, prev_column); } else { // handle space indentation - if (cursor.column - indent_size >= 0 && indent_using_spaces) { - - // if there is enough spaces to count as a tab + if (cursor.column != 0 && indent_using_spaces) { + // check if there are no other chars before cursor, just indentation bool unindent = true; - for (int i = 1; i <= indent_size; i++) { - if (text[cursor.line][cursor.column - i] != ' ') { - unindent = false; - break; - } - } - - // and it is before the first character int i = 0; while (i < cursor.column && i < text[cursor.line].length()) { - if (text[cursor.line][i] != ' ' && text[cursor.line][i] != '\t') { + if (!_is_whitespace(text[cursor.line][i])) { unindent = false; break; } i++; } - // then we can remove it as a single character. + // then we can remove all spaces as a single character. if (unindent) { - _remove_text(cursor.line, cursor.column - indent_size, cursor.line, cursor.column); - prev_column = cursor.column - indent_size; + // we want to remove spaces up to closest indent + // or whole indent if cursor is pointing at it + int spaces_to_delete = _calculate_spaces_till_next_left_indent(cursor.column); + prev_column = cursor.column - spaces_to_delete; + _remove_text(cursor.line, prev_column, cursor.line, cursor.column); } else { _remove_text(prev_line, prev_column, cursor.line, cursor.column); } @@ -1675,6 +1687,10 @@ void TextEdit::indent_right() { int start_line; int end_line; + + // this value informs us by how much we changed selection position by indenting right + // default is 1 for tab indentation + int selection_offset = 1; begin_complex_operation(); if (is_selection_active()) { @@ -1693,18 +1709,24 @@ void TextEdit::indent_right() { for (int i = start_line; i <= end_line; i++) { String line_text = get_line(i); if (indent_using_spaces) { - line_text = space_indent + line_text; + // we don't really care where selection is - we just need to know indentation level at the beginning of the line + int left = _find_first_non_whitespace_column_of_line(line_text); + int spaces_to_add = _calculate_spaces_till_next_right_indent(left); + // since we will add this much spaces we want move whole selection and cursor by this much + selection_offset = spaces_to_add; + for (int j = 0; j < spaces_to_add; j++) + line_text = ' ' + line_text; } else { line_text = '\t' + line_text; } set_line(i, line_text); } - // fix selection and cursor being off by one on the last line + // fix selection and cursor being off after shifting selection right if (is_selection_active()) { - select(selection.from_line, selection.from_column + 1, selection.to_line, selection.to_column + 1); + select(selection.from_line, selection.from_column + selection_offset, selection.to_line, selection.to_column + selection_offset); } - cursor_set_column(cursor.column + 1, false); + cursor_set_column(cursor.column + selection_offset, false); end_complex_operation(); update(); } @@ -1713,6 +1735,15 @@ void TextEdit::indent_left() { int start_line; int end_line; + + // moving cursor and selection after unindenting can get tricky + // because changing content of line can move cursor and selection on it's own (if new line ends before previous position of either) + // therefore we just remember initial values + // and at the end of the operation offset them by number of removed characters + int removed_characters = 0; + int initial_selection_end_column = selection.to_column; + int initial_cursor_column = cursor.column; + begin_complex_operation(); if (is_selection_active()) { @@ -1735,21 +1766,43 @@ void TextEdit::indent_left() { if (line_text.begins_with("\t")) { line_text = line_text.substr(1, line_text.length()); set_line(i, line_text); - } else if (line_text.begins_with(space_indent)) { - line_text = line_text.substr(indent_size, line_text.length()); + removed_characters = 1; + } else if (line_text.begins_with(" ")) { + // when unindenting we aim to remove spaces before line that has selection no matter what is selected + // so we start of by finding first non whitespace character of line + int left = _find_first_non_whitespace_column_of_line(line_text); + + // here we remove only enough spaces to align text to nearest full multiple of indentation_size + // in case where selection begins at the start of indentation_size multiple we remove whole indentation level + int spaces_to_remove = _calculate_spaces_till_next_left_indent(left); + + line_text = line_text.substr(spaces_to_remove, line_text.length()); set_line(i, line_text); + removed_characters = spaces_to_remove; } } // fix selection and cursor being off by one on the last line if (is_selection_active() && last_line_text != get_line(end_line)) { - select(selection.from_line, selection.from_column - 1, selection.to_line, selection.to_column - 1); + select(selection.from_line, selection.from_column - removed_characters, + selection.to_line, initial_selection_end_column - removed_characters); } - cursor_set_column(cursor.column - 1, false); + cursor_set_column(initial_cursor_column - removed_characters, false); end_complex_operation(); update(); } +int TextEdit::_calculate_spaces_till_next_left_indent(int column) { + int spaces_till_indent = column % indent_size; + if (spaces_till_indent == 0) + spaces_till_indent = indent_size; + return spaces_till_indent; +} + +int TextEdit::_calculate_spaces_till_next_right_indent(int column) { + return indent_size - column % indent_size; +} + void TextEdit::_get_mouse_pos(const Point2i &p_mouse, int &r_row, int &r_col) const { float rows = p_mouse.y; @@ -1801,6 +1854,9 @@ void TextEdit::_get_mouse_pos(const Point2i &p_mouse, int &r_row, int &r_col) co void TextEdit::_gui_input(const Ref<InputEvent> &p_gui_input) { + double prev_v_scroll = v_scroll->get_value(); + double prev_h_scroll = h_scroll->get_value(); + Ref<InputEventMouseButton> mb = p_gui_input; if (mb.is_valid()) { @@ -2055,6 +2111,9 @@ void TextEdit::_gui_input(const Ref<InputEvent> &p_gui_input) { _scroll_down(delta); } h_scroll->set_value(h_scroll->get_value() + pan_gesture->get_delta().x * 100); + if (v_scroll->get_value() != prev_v_scroll || h_scroll->get_value() != prev_h_scroll) + accept_event(); //accept event if scroll changed + return; } @@ -2098,6 +2157,9 @@ void TextEdit::_gui_input(const Ref<InputEvent> &p_gui_input) { } } + if (v_scroll->get_value() != prev_v_scroll || h_scroll->get_value() != prev_h_scroll) + accept_event(); //accept event if scroll changed + Ref<InputEventKey> k = p_gui_input; if (k.is_valid()) { @@ -2506,15 +2568,11 @@ void TextEdit::_gui_input(const Ref<InputEvent> &p_gui_input) { } else { if (k->get_shift()) { - //simple unindent + // simple unindent int cc = cursor.column; - - const int len = text[cursor.line].length(); const String &line = text[cursor.line]; - int left = 0; // number of whitespace chars at beginning of line - while (left < len && (line[left] == '\t' || line[left] == ' ')) - left++; + int left = _find_first_non_whitespace_column_of_line(line); cc = MIN(cc, left); while (cc < indent_size && cc < left && line[cc] == ' ') @@ -2522,24 +2580,18 @@ void TextEdit::_gui_input(const Ref<InputEvent> &p_gui_input) { if (cc > 0 && cc <= text[cursor.line].length()) { if (text[cursor.line][cc - 1] == '\t') { + // tabs unindentation _remove_text(cursor.line, cc - 1, cursor.line, cc); if (cursor.column >= left) cursor_set_column(MAX(0, cursor.column - 1)); update(); } else { - int n = 0; - - for (int i = 1; i <= MIN(cc, indent_size); i++) { - if (line[cc - i] != ' ') { - break; - } - n++; - } - - if (n > 0) { - _remove_text(cursor.line, cc - n, cursor.line, cc); - if (cursor.column > left - n) // inside text? - cursor_set_column(MAX(0, cursor.column - n)); + // spaces unindentation + int spaces_to_remove = _calculate_spaces_till_next_left_indent(cc); + if (spaces_to_remove > 0) { + _remove_text(cursor.line, cc - spaces_to_remove, cursor.line, cc); + if (cursor.column > left - spaces_to_remove) // inside text? + cursor_set_column(MAX(0, cursor.column - spaces_to_remove)); update(); } } @@ -2548,9 +2600,14 @@ void TextEdit::_gui_input(const Ref<InputEvent> &p_gui_input) { update(); } } else { - //simple indent + // simple indent if (indent_using_spaces) { - _insert_text_at_cursor(space_indent); + // insert only as much spaces as needed till next indentation level + int spaces_to_add = _calculate_spaces_till_next_right_indent(cursor.column); + String indent_to_insert = String(); + for (int i = 0; i < spaces_to_add; i++) + indent_to_insert = ' ' + indent_to_insert; + _insert_text_at_cursor(indent_to_insert); } else { _insert_text_at_cursor("\t"); } @@ -3603,7 +3660,7 @@ void TextEdit::_insert_text(int p_line, int p_char, const String &p_text, int *r op.chain_forward = false; op.chain_backward = false; - //see if it shold just be set as current op + //see if it should just be set as current op if (current_op.type != op.type) { op.prev_version = get_version(); _push_current_op(); @@ -3654,7 +3711,7 @@ void TextEdit::_remove_text(int p_from_line, int p_from_column, int p_to_line, i op.chain_forward = false; op.chain_backward = false; - //see if it shold just be set as current op + //see if it should just be set as current op if (current_op.type != op.type) { op.prev_version = get_version(); _push_current_op(); @@ -4303,17 +4360,22 @@ Control::CursorShape TextEdit::get_cursor_shape(const Point2 &p_pos) const { void TextEdit::set_text(String p_text) { setting_text = true; - _clear(); - _insert_text_at_cursor(p_text); - clear_undo_history(); - cursor.column = 0; - cursor.line = 0; - cursor.x_ofs = 0; - cursor.line_ofs = 0; - cursor.wrap_ofs = 0; - cursor.last_fit_x = 0; - cursor_set_line(0); - cursor_set_column(0); + if (!undo_enabled) { + _clear(); + _insert_text_at_cursor(p_text); + } + + if (undo_enabled) { + cursor_set_line(0); + cursor_set_column(0); + + begin_complex_operation(); + _remove_text(0, 0, MAX(0, get_line_count() - 1), MAX(get_line(MAX(get_line_count() - 1, 0)).size() - 1, 0)); + _insert_text_at_cursor(p_text); + end_complex_operation(); + selection.active = false; + } + update(); setting_text = false; @@ -4499,6 +4561,7 @@ void TextEdit::_update_caches() { cache.mark_color = get_color("mark_color"); cache.current_line_color = get_color("current_line_color"); cache.line_length_guideline_color = get_color("line_length_guideline_color"); + cache.bookmark_color = get_color("bookmark_color"); cache.breakpoint_color = get_color("breakpoint_color"); cache.executing_line_color = get_color("executing_line_color"); cache.code_folding_color = get_color("code_folding_color"); @@ -5096,6 +5159,37 @@ void TextEdit::clear_executing_line() { update(); } +bool TextEdit::is_line_set_as_bookmark(int p_line) const { + + ERR_FAIL_INDEX_V(p_line, text.size(), false); + return text.is_bookmark(p_line); +} + +void TextEdit::set_line_as_bookmark(int p_line, bool p_bookmark) { + + ERR_FAIL_INDEX(p_line, text.size()); + text.set_bookmark(p_line, p_bookmark); + update(); +} + +void TextEdit::get_bookmarks(List<int> *p_bookmarks) const { + + for (int i = 0; i < text.size(); i++) { + if (text.is_bookmark(i)) + p_bookmarks->push_back(i); + } +} + +Array TextEdit::get_bookmarks_array() const { + + Array arr; + for (int i = 0; i < text.size(); i++) { + if (text.is_bookmark(i)) + arr.append(i); + } + return arr; +} + bool TextEdit::is_line_set_as_breakpoint(int p_line) const { ERR_FAIL_INDEX_V(p_line, text.size(), false); @@ -6183,6 +6277,15 @@ void TextEdit::set_line_length_guideline_column(int p_column) { update(); } +void TextEdit::set_bookmark_gutter_enabled(bool p_draw) { + draw_bookmark_gutter = p_draw; + update(); +} + +bool TextEdit::is_bookmark_gutter_enabled() const { + return draw_bookmark_gutter; +} + void TextEdit::set_breakpoint_gutter_enabled(bool p_draw) { draw_breakpoint_gutter = p_draw; update(); @@ -6579,6 +6682,7 @@ TextEdit::TextEdit() { line_numbers_zero_padded = false; line_length_guideline = false; line_length_guideline_col = 80; + draw_bookmark_gutter = false; draw_breakpoint_gutter = false; draw_fold_gutter = false; draw_info_gutter = false; @@ -6603,6 +6707,7 @@ TextEdit::TextEdit() { context_menu_enabled = true; menu = memnew(PopupMenu); add_child(menu); + readonly = true; // initialise to opposite first, so we get past the early-out in set_readonly set_readonly(false); menu->connect("id_pressed", this, "menu_option"); first_draw = true; diff --git a/scene/gui/text_edit.h b/scene/gui/text_edit.h index eb9fb2cf57..68e590f1e6 100644 --- a/scene/gui/text_edit.h +++ b/scene/gui/text_edit.h @@ -75,6 +75,7 @@ public: int width_cache : 24; bool marked : 1; bool breakpoint : 1; + bool bookmark : 1; bool hidden : 1; bool safe : 1; int wrap_amount_cache : 24; @@ -105,6 +106,8 @@ public: void set(int p_line, const String &p_text); void set_marked(int p_line, bool p_marked) { text.write[p_line].marked = p_marked; } bool is_marked(int p_line) const { return text[p_line].marked; } + void set_bookmark(int p_line, bool p_bookmark) { text.write[p_line].bookmark = p_bookmark; } + bool is_bookmark(int p_line) const { return text[p_line].bookmark; } void set_breakpoint(int p_line, bool p_breakpoint) { text.write[p_line].breakpoint = p_breakpoint; } bool is_breakpoint(int p_line) const { return text[p_line].breakpoint; } void set_hidden(int p_line, bool p_hidden) { text.write[p_line].hidden = p_hidden; } @@ -188,6 +191,7 @@ private: Color member_variable_color; Color selection_color; Color mark_color; + Color bookmark_color; Color breakpoint_color; Color executing_line_color; Color code_folding_color; @@ -300,6 +304,7 @@ private: bool line_numbers_zero_padded; bool line_length_guideline; int line_length_guideline_col; + bool draw_bookmark_gutter; bool draw_breakpoint_gutter; int breakpoint_gutter_width; bool draw_fold_gutter; @@ -432,6 +437,9 @@ private: void _confirm_completion(); void _update_completion_candidates(); + int _calculate_spaces_till_next_left_indent(int column); + int _calculate_spaces_till_next_right_indent(int column); + protected: virtual String get_tooltip(const Point2 &p_pos) const; @@ -490,6 +498,10 @@ public: void insert_at(const String &p_text, int at); int get_line_count() const; void set_line_as_marked(int p_line, bool p_marked); + void set_line_as_bookmark(int p_line, bool p_bookmark); + bool is_line_set_as_bookmark(int p_line) const; + void get_bookmarks(List<int> *p_bookmarks) const; + Array get_bookmarks_array() const; void set_line_as_breakpoint(int p_line, bool p_breakpoint); bool is_line_set_as_breakpoint(int p_line) const; void set_executing_line(int p_line); @@ -664,6 +676,9 @@ public: void set_show_line_length_guideline(bool p_show); void set_line_length_guideline_column(int p_column); + void set_bookmark_gutter_enabled(bool p_draw); + bool is_bookmark_gutter_enabled() const; + void set_breakpoint_gutter_enabled(bool p_draw); bool is_breakpoint_gutter_enabled() const; @@ -720,7 +735,7 @@ public: virtual void _update_cache() = 0; virtual Map<int, TextEdit::HighlighterInfo> _get_line_syntax_highlighting(int p_line) = 0; - virtual String get_name() = 0; + virtual String get_name() const = 0; virtual List<String> get_supported_languages() = 0; void set_text_editor(TextEdit *p_text_editor); diff --git a/scene/gui/tree.cpp b/scene/gui/tree.cpp index f22fe5b6a5..049cae9dd9 100644 --- a/scene/gui/tree.cpp +++ b/scene/gui/tree.cpp @@ -2266,7 +2266,7 @@ void Tree::_gui_input(Ref<InputEvent> p_event) { next = _n; } else { - return; + break; } } if (next == selected_item) @@ -2304,7 +2304,7 @@ void Tree::_gui_input(Ref<InputEvent> p_event) { prev = _n; } else { - return; + break; } } if (prev == selected_item) diff --git a/scene/main/node.cpp b/scene/main/node.cpp index e80de68e3b..368dea7649 100644 --- a/scene/main/node.cpp +++ b/scene/main/node.cpp @@ -949,6 +949,7 @@ void Node::set_name(const String &p_name) { if (is_inside_tree()) { emit_signal("renamed"); + get_tree()->node_renamed(this); get_tree()->tree_changed(); } } diff --git a/scene/main/scene_tree.cpp b/scene/main/scene_tree.cpp index b81364e2f0..65cda73a23 100644 --- a/scene/main/scene_tree.cpp +++ b/scene/main/scene_tree.cpp @@ -105,6 +105,11 @@ void SceneTree::node_removed(Node *p_node) { call_skip.insert(p_node); } +void SceneTree::node_renamed(Node *p_node) { + + emit_signal(node_renamed_name, p_node); +} + SceneTree::Group *SceneTree::add_to_group(const StringName &p_group, Node *p_node) { Map<StringName, Group>::Element *E = group_map.find(p_group); @@ -1895,6 +1900,7 @@ void SceneTree::_bind_methods() { ADD_SIGNAL(MethodInfo("tree_changed")); ADD_SIGNAL(MethodInfo("node_added", PropertyInfo(Variant::OBJECT, "node", PROPERTY_HINT_RESOURCE_TYPE, "Node"))); ADD_SIGNAL(MethodInfo("node_removed", PropertyInfo(Variant::OBJECT, "node", PROPERTY_HINT_RESOURCE_TYPE, "Node"))); + ADD_SIGNAL(MethodInfo("node_renamed", PropertyInfo(Variant::OBJECT, "node", PROPERTY_HINT_RESOURCE_TYPE, "Node"))); ADD_SIGNAL(MethodInfo("screen_resized")); ADD_SIGNAL(MethodInfo("node_configuration_warning_changed", PropertyInfo(Variant::OBJECT, "node", PROPERTY_HINT_RESOURCE_TYPE, "Node"))); @@ -1983,6 +1989,7 @@ SceneTree::SceneTree() { tree_changed_name = "tree_changed"; node_added_name = "node_added"; node_removed_name = "node_removed"; + node_renamed_name = "node_renamed"; ugc_locked = false; call_lock = 0; root_lock = 0; diff --git a/scene/main/scene_tree.h b/scene/main/scene_tree.h index e098b3d53c..0bcb724929 100644 --- a/scene/main/scene_tree.h +++ b/scene/main/scene_tree.h @@ -126,6 +126,7 @@ private: StringName tree_changed_name; StringName node_added_name; StringName node_removed_name; + StringName node_renamed_name; bool use_font_oversampling; int64_t current_frame; @@ -201,6 +202,7 @@ private: void tree_changed(); void node_added(Node *p_node); void node_removed(Node *p_node); + void node_renamed(Node *p_node); Group *add_to_group(const StringName &p_group, Node *p_node); void remove_from_group(const StringName &p_group, Node *p_node); diff --git a/scene/main/viewport.cpp b/scene/main/viewport.cpp index ae2c571201..b5e5022e63 100644 --- a/scene/main/viewport.cpp +++ b/scene/main/viewport.cpp @@ -2765,6 +2765,19 @@ Rect2 Viewport::get_attach_to_screen_rect() const { return to_screen_rect; } +void Viewport::set_use_render_direct_to_screen(bool p_render_direct_to_screen) { + + if (p_render_direct_to_screen == render_direct_to_screen) + return; + + render_direct_to_screen = p_render_direct_to_screen; + VS::get_singleton()->viewport_set_render_direct_to_screen(viewport, p_render_direct_to_screen); +} + +bool Viewport::is_using_render_direct_to_screen() const { + return render_direct_to_screen; +} + void Viewport::set_physics_object_picking(bool p_enable) { physics_object_picking = p_enable; @@ -3030,6 +3043,8 @@ void Viewport::_bind_methods() { ClassDB::bind_method(D_METHOD("set_as_audio_listener_2d", "enable"), &Viewport::set_as_audio_listener_2d); ClassDB::bind_method(D_METHOD("is_audio_listener_2d"), &Viewport::is_audio_listener_2d); ClassDB::bind_method(D_METHOD("set_attach_to_screen_rect", "rect"), &Viewport::set_attach_to_screen_rect); + ClassDB::bind_method(D_METHOD("set_use_render_direct_to_screen", "enable"), &Viewport::set_use_render_direct_to_screen); + ClassDB::bind_method(D_METHOD("is_using_render_direct_to_screen"), &Viewport::is_using_render_direct_to_screen); ClassDB::bind_method(D_METHOD("get_mouse_position"), &Viewport::get_mouse_position); ClassDB::bind_method(D_METHOD("warp_mouse", "to_position"), &Viewport::warp_mouse); @@ -3084,6 +3099,7 @@ void Viewport::_bind_methods() { ADD_PROPERTY(PropertyInfo(Variant::BOOL, "disable_3d"), "set_disable_3d", "is_3d_disabled"); ADD_PROPERTY(PropertyInfo(Variant::BOOL, "keep_3d_linear"), "set_keep_3d_linear", "get_keep_3d_linear"); ADD_PROPERTY(PropertyInfo(Variant::INT, "usage", PROPERTY_HINT_ENUM, "2D,2D No-Sampling,3D,3D No-Effects"), "set_usage", "get_usage"); + ADD_PROPERTY(PropertyInfo(Variant::BOOL, "render_direct_to_screen"), "set_use_render_direct_to_screen", "is_using_render_direct_to_screen"); ADD_PROPERTY(PropertyInfo(Variant::INT, "debug_draw", PROPERTY_HINT_ENUM, "Disabled,Unshaded,Overdraw,Wireframe"), "set_debug_draw", "get_debug_draw"); ADD_GROUP("Render Target", "render_target_"); ADD_PROPERTY(PropertyInfo(Variant::BOOL, "render_target_v_flip"), "set_vflip", "get_vflip"); @@ -3166,6 +3182,8 @@ Viewport::Viewport() { texture_rid = VisualServer::get_singleton()->viewport_get_texture(viewport); texture_flags = 0; + render_direct_to_screen = false; + default_texture.instance(); default_texture->vp = const_cast<Viewport *>(this); viewport_textures.insert(default_texture.ptr()); diff --git a/scene/main/viewport.h b/scene/main/viewport.h index d67b4ac348..b7160d5139 100644 --- a/scene/main/viewport.h +++ b/scene/main/viewport.h @@ -182,6 +182,7 @@ private: Size2 size; Rect2 to_screen_rect; + bool render_direct_to_screen; RID contact_2d_debug; RID contact_3d_debug_multimesh; @@ -481,6 +482,9 @@ public: void set_attach_to_screen_rect(const Rect2 &p_rect); Rect2 get_attach_to_screen_rect() const; + void set_use_render_direct_to_screen(bool p_render_direct_to_screen); + bool is_using_render_direct_to_screen() const; + Vector2 get_mouse_position() const; void warp_mouse(const Vector2 &p_pos); diff --git a/scene/register_scene_types.cpp b/scene/register_scene_types.cpp index 47f5b152f0..5440c88fa8 100644 --- a/scene/register_scene_types.cpp +++ b/scene/register_scene_types.cpp @@ -476,6 +476,7 @@ void register_scene_types() { ClassDB::register_virtual_class<VisualShaderNode>(); ClassDB::register_class<VisualShaderNodeInput>(); ClassDB::register_virtual_class<VisualShaderNodeOutput>(); + ClassDB::register_class<VisualShaderNodeGroupBase>(); ClassDB::register_class<VisualShaderNodeScalarConstant>(); ClassDB::register_class<VisualShaderNodeBooleanConstant>(); ClassDB::register_class<VisualShaderNodeColorConstant>(); @@ -523,6 +524,8 @@ void register_scene_types() { ClassDB::register_class<VisualShaderNodeCubeMapUniform>(); ClassDB::register_class<VisualShaderNodeIf>(); ClassDB::register_class<VisualShaderNodeSwitch>(); + ClassDB::register_class<VisualShaderNodeFresnel>(); + ClassDB::register_class<VisualShaderNodeExpression>(); ClassDB::register_class<ShaderMaterial>(); ClassDB::register_virtual_class<CanvasItem>(); diff --git a/scene/resources/bit_map.cpp b/scene/resources/bit_map.cpp index a9d85be0dc..e4a64a1de1 100644 --- a/scene/resources/bit_map.cpp +++ b/scene/resources/bit_map.cpp @@ -595,16 +595,16 @@ Array BitMap::_opaque_to_polygons_bind(const Rect2 &p_rect, float p_epsilon) con return result_array; } -void BitMap::resize(const Size2& p_new_size) { +void BitMap::resize(const Size2 &p_new_size) { Ref<BitMap> new_bitmap; new_bitmap.instance(); new_bitmap->create(p_new_size); - int lw = MIN(width,p_new_size.width); - int lh = MIN(height,p_new_size.height); - for(int x=0;x<lw;x++) { - for(int y=0;y<lh;y++) { - new_bitmap->set_bit(Vector2(x,y),get_bit(Vector2(x,y))); + int lw = MIN(width, p_new_size.width); + int lh = MIN(height, p_new_size.height); + for (int x = 0; x < lw; x++) { + for (int y = 0; y < lh; y++) { + new_bitmap->set_bit(Vector2(x, y), get_bit(Vector2(x, y))); } } @@ -617,11 +617,11 @@ Ref<Image> BitMap::convert_to_image() const { Ref<Image> image; image.instance(); - image->create(width,height,false,Image::FORMAT_L8); + image->create(width, height, false, Image::FORMAT_L8); image->lock(); - for(int i=0;i<width;i++) { - for(int j=0;j<height;j++) { - image->set_pixel( i,j,get_bit(Point2(i,j)) ? Color(1,1,1) : Color(0,0,0)); + for (int i = 0; i < width; i++) { + for (int j = 0; j < height; j++) { + image->set_pixel(i, j, get_bit(Point2(i, j)) ? Color(1, 1, 1) : Color(0, 0, 0)); } } @@ -629,30 +629,28 @@ Ref<Image> BitMap::convert_to_image() const { return image; } -void BitMap::blit(const Vector2& p_pos,const Ref<BitMap>& p_bitmap) { +void BitMap::blit(const Vector2 &p_pos, const Ref<BitMap> &p_bitmap) { int x = p_pos.x; int y = p_pos.y; int w = p_bitmap->get_size().width; int h = p_bitmap->get_size().height; - for(int i=0;i<w;i++) { - for (int j=0;j<h;j++) { - int px = x+i; - int py = y+j; - if (px<0 || px>=width) + for (int i = 0; i < w; i++) { + for (int j = 0; j < h; j++) { + int px = x + i; + int py = y + j; + if (px < 0 || px >= width) continue; - if (py<0 || py>=height) + if (py < 0 || py >= height) continue; - if (p_bitmap->get_bit(Vector2(i,j))) { - set_bit(Vector2(x,y),true); + if (p_bitmap->get_bit(Vector2(i, j))) { + set_bit(Vector2(x, y), true); } } } - } - void BitMap::_bind_methods() { ClassDB::bind_method(D_METHOD("create", "size"), &BitMap::create); diff --git a/scene/resources/bit_map.h b/scene/resources/bit_map.h index 6e1171b8a9..daf24affb1 100644 --- a/scene/resources/bit_map.h +++ b/scene/resources/bit_map.h @@ -64,11 +64,11 @@ public: int get_true_bit_count() const; Size2 get_size() const; - void resize(const Size2& p_new_size); + void resize(const Size2 &p_new_size); void grow_mask(int p_pixels, const Rect2 &p_rect); - void blit(const Vector2& p_pos,const Ref<BitMap>& p_bitmap); + void blit(const Vector2 &p_pos, const Ref<BitMap> &p_bitmap); Ref<Image> convert_to_image() const; Vector<Vector<Vector2> > clip_opaque_to_polygons(const Rect2 &p_rect, float p_epsilon = 2.0) const; diff --git a/scene/resources/default_theme/default_theme.cpp b/scene/resources/default_theme/default_theme.cpp index 0b88763300..bdb6c78782 100644 --- a/scene/resources/default_theme/default_theme.cpp +++ b/scene/resources/default_theme/default_theme.cpp @@ -441,6 +441,7 @@ void fill_default_theme(Ref<Theme> &theme, const Ref<Font> &default_font, const theme->set_color("font_color_selected", "TextEdit", Color(0, 0, 0)); theme->set_color("selection_color", "TextEdit", font_color_selection); theme->set_color("mark_color", "TextEdit", Color(1.0, 0.4, 0.4, 0.4)); + theme->set_color("bookmark_color", "TextEdit", Color(0.08, 0.49, 0.98)); theme->set_color("breakpoint_color", "TextEdit", Color(0.8, 0.8, 0.4, 0.2)); theme->set_color("executing_line_color", "TextEdit", Color(0.2, 0.8, 0.2, 0.4)); theme->set_color("code_folding_color", "TextEdit", Color(0.8, 0.8, 0.8, 0.8)); diff --git a/scene/resources/material.cpp b/scene/resources/material.cpp index 766c7bbd9f..2e035bbd1f 100644 --- a/scene/resources/material.cpp +++ b/scene/resources/material.cpp @@ -468,6 +468,9 @@ void SpatialMaterial::_update_shader() { if (flags[FLAG_ENSURE_CORRECT_NORMALS]) { code += ",ensure_correct_normals"; } + if (flags[FLAG_USE_SHADOW_TO_OPACITY]) { + code += ",shadow_to_opacity"; + } code += ";\n"; code += "uniform vec4 albedo : hint_color;\n"; @@ -849,7 +852,7 @@ void SpatialMaterial::_update_shader() { code += "\tALBEDO *= 1.0 - ref_amount;\n"; code += "\tALPHA = 1.0;\n"; - } else if (features[FEATURE_TRANSPARENT] || flags[FLAG_USE_ALPHA_SCISSOR] || (distance_fade == DISTANCE_FADE_PIXEL_ALPHA) || proximity_fade_enabled) { + } else if (features[FEATURE_TRANSPARENT] || flags[FLAG_USE_ALPHA_SCISSOR] || flags[FLAG_USE_SHADOW_TO_OPACITY] || (distance_fade == DISTANCE_FADE_PIXEL_ALPHA) || proximity_fade_enabled) { code += "\tALPHA = albedo.a * albedo_tex.a;\n"; } @@ -1349,7 +1352,7 @@ void SpatialMaterial::set_flag(Flags p_flag, bool p_enabled) { return; flags[p_flag] = p_enabled; - if (p_flag == FLAG_USE_ALPHA_SCISSOR || p_flag == FLAG_UNSHADED) { + if ((p_flag == FLAG_USE_ALPHA_SCISSOR) || (p_flag == FLAG_UNSHADED) || (p_flag == FLAG_USE_SHADOW_TO_OPACITY)) { _change_notify(); } _queue_shader_change(); @@ -2060,6 +2063,7 @@ void SpatialMaterial::_bind_methods() { ADD_GROUP("Flags", "flags_"); ADD_PROPERTYI(PropertyInfo(Variant::BOOL, "flags_transparent"), "set_feature", "get_feature", FEATURE_TRANSPARENT); + ADD_PROPERTYI(PropertyInfo(Variant::BOOL, "flags_use_shadow_to_opacity"), "set_flag", "get_flag", FLAG_USE_SHADOW_TO_OPACITY); ADD_PROPERTYI(PropertyInfo(Variant::BOOL, "flags_unshaded"), "set_flag", "get_flag", FLAG_UNSHADED); ADD_PROPERTYI(PropertyInfo(Variant::BOOL, "flags_vertex_lighting"), "set_flag", "get_flag", FLAG_USE_VERTEX_LIGHTING); ADD_PROPERTYI(PropertyInfo(Variant::BOOL, "flags_no_depth_test"), "set_flag", "get_flag", FLAG_DISABLE_DEPTH_TEST); @@ -2266,6 +2270,7 @@ void SpatialMaterial::_bind_methods() { BIND_ENUM_CONSTANT(FLAG_DONT_RECEIVE_SHADOWS); BIND_ENUM_CONSTANT(FLAG_DISABLE_AMBIENT_LIGHT); BIND_ENUM_CONSTANT(FLAG_ENSURE_CORRECT_NORMALS); + BIND_ENUM_CONSTANT(FLAG_USE_SHADOW_TO_OPACITY); BIND_ENUM_CONSTANT(FLAG_MAX); BIND_ENUM_CONSTANT(DIFFUSE_BURLEY); diff --git a/scene/resources/material.h b/scene/resources/material.h index 1f7fc267af..29b45f769b 100644 --- a/scene/resources/material.h +++ b/scene/resources/material.h @@ -196,6 +196,7 @@ public: FLAG_DONT_RECEIVE_SHADOWS, FLAG_ENSURE_CORRECT_NORMALS, FLAG_DISABLE_AMBIENT_LIGHT, + FLAG_USE_SHADOW_TO_OPACITY, FLAG_MAX }; diff --git a/scene/resources/resource_format_text.cpp b/scene/resources/resource_format_text.cpp index e9f90fc85f..6e7bb27e74 100644 --- a/scene/resources/resource_format_text.cpp +++ b/scene/resources/resource_format_text.cpp @@ -447,9 +447,8 @@ Error ResourceInteractiveLoaderText::poll() { resource_cache.push_back(res); #ifdef TOOLS_ENABLED //remember ID for saving - res->set_id_for_path(local_path,index); + res->set_id_for_path(local_path, index); #endif - } ExtResource er; @@ -1545,9 +1544,6 @@ Error ResourceFormatSaverTextInstance::save(const String &p_path, const RES &p_r } { - - - } #ifdef TOOLS_ENABLED @@ -1569,7 +1565,7 @@ Error ResourceFormatSaverTextInstance::save(const String &p_path, const RES &p_r } int attempt = 1; //start from one, more readable format - while(cached_ids_found.has(attempt)) { + while (cached_ids_found.has(attempt)) { attempt++; } @@ -1577,7 +1573,7 @@ Error ResourceFormatSaverTextInstance::save(const String &p_path, const RES &p_r E->get() = attempt; //update also in resource Ref<Resource> res = E->key(); - res->set_id_for_path(local_path,attempt); + res->set_id_for_path(local_path, attempt); } #else //make sure to start from one, as it makes format more readable @@ -1598,7 +1594,6 @@ Error ResourceFormatSaverTextInstance::save(const String &p_path, const RES &p_r sorted_er.sort(); - for (int i = 0; i < sorted_er.size(); i++) { String p = sorted_er[i].resource->get_path(); diff --git a/scene/resources/resource_format_text.h b/scene/resources/resource_format_text.h index ab6f94986c..06c841229b 100644 --- a/scene/resources/resource_format_text.h +++ b/scene/resources/resource_format_text.h @@ -172,10 +172,9 @@ class ResourceFormatSaverTextInstance { struct ResourceSort { RES resource; int index; - bool operator<(const ResourceSort& p_right) const { + bool operator<(const ResourceSort &p_right) const { return index < p_right.index; } - }; void _find_resources(const Variant &p_variant, bool p_main = false); diff --git a/scene/resources/surface_tool.cpp b/scene/resources/surface_tool.cpp index 3ba43006a3..8c0497e91a 100644 --- a/scene/resources/surface_tool.cpp +++ b/scene/resources/surface_tool.cpp @@ -115,7 +115,7 @@ void SurfaceTool::add_vertex(const Vector3 &p_vertex) { //ensure vertices are the expected amount ERR_FAIL_COND(vtx.weights.size() != vtx.bones.size()); if (vtx.weights.size() < expected_vertices) { - //less than requred, fill + //less than required, fill for (int i = vtx.weights.size(); i < expected_vertices; i++) { vtx.weights.push_back(0); vtx.bones.push_back(0); diff --git a/scene/resources/visual_shader.cpp b/scene/resources/visual_shader.cpp index b8f21948c3..1781777fcd 100644 --- a/scene/resources/visual_shader.cpp +++ b/scene/resources/visual_shader.cpp @@ -159,6 +159,7 @@ Vector2 VisualShader::get_node_position(Type p_type, int p_id) const { ERR_FAIL_COND_V(!g->nodes.has(p_id), Vector2()); return g->nodes[p_id].position; } + Ref<VisualShaderNode> VisualShader::get_node(Type p_type, int p_id) const { ERR_FAIL_INDEX_V(p_type, TYPE_MAX, Ref<VisualShaderNode>()); const Graph *g = &graph[p_type]; @@ -269,6 +270,18 @@ bool VisualShader::can_connect_nodes(Type p_type, int p_from_node, int p_from_po return true; } +void VisualShader::connect_nodes_forced(Type p_type, int p_from_node, int p_from_port, int p_to_node, int p_to_port) { + ERR_FAIL_INDEX(p_type, TYPE_MAX); + Graph *g = &graph[p_type]; + Connection c; + c.from_node = p_from_node; + c.from_port = p_from_port; + c.to_node = p_to_node; + c.to_port = p_to_port; + g->connections.push_back(c); + _queue_update(); +} + Error VisualShader::connect_nodes(Type p_type, int p_from_node, int p_from_port, int p_to_node, int p_to_port) { ERR_FAIL_INDEX_V(p_type, TYPE_MAX, ERR_CANT_CONNECT); Graph *g = &graph[p_type]; @@ -304,6 +317,7 @@ Error VisualShader::connect_nodes(Type p_type, int p_from_node, int p_from_port, _queue_update(); return OK; } + void VisualShader::disconnect_nodes(Type p_type, int p_from_node, int p_from_port, int p_to_node, int p_to_port) { ERR_FAIL_INDEX(p_type, TYPE_MAX); Graph *g = &graph[p_type]; @@ -334,6 +348,7 @@ Array VisualShader::_get_node_connections(Type p_type) const { return ret; } + void VisualShader::get_node_connections(Type p_type, List<Connection> *r_connections) const { ERR_FAIL_INDEX(p_type, TYPE_MAX); const Graph *g = &graph[p_type]; @@ -477,6 +492,54 @@ String VisualShader::generate_preview_shader(Type p_type, int p_node, int p_port #define IS_SYMBOL_CHAR(m_d) (((m_d) >= 'a' && (m_d) <= 'z') || ((m_d) >= 'A' && (m_d) <= 'Z') || ((m_d) >= '0' && (m_d) <= '9') || (m_d) == '_') +String VisualShader::validate_port_name(const String &p_name, const List<String> &p_input_ports, const List<String> &p_output_ports) const { + String name = p_name; + + while (name.length() && !IS_INITIAL_CHAR(name[0])) { + name = name.substr(1, name.length() - 1); + } + + if (name != String()) { + + String valid_name; + + for (int i = 0; i < name.length(); i++) { + if (IS_SYMBOL_CHAR(name[i])) { + valid_name += String::chr(name[i]); + } else if (name[i] == ' ') { + valid_name += "_"; + } + } + + name = valid_name; + } + + String valid_name = name; + bool is_equal = false; + + for (int i = 0; i < p_input_ports.size(); i++) { + if (name == p_input_ports[i]) { + is_equal = true; + break; + } + } + + if (!is_equal) { + for (int i = 0; i < p_output_ports.size(); i++) { + if (name == p_output_ports[i]) { + is_equal = true; + break; + } + } + } + + if (is_equal) { + name = ""; + } + + return name; +} + String VisualShader::validate_uniform_name(const String &p_name, const Ref<VisualShaderNodeUniform> &p_uniform) const { String name = p_name; //validate name first @@ -596,7 +659,7 @@ bool VisualShader::_set(const StringName &p_name, const Variant &p_value) { Vector<int> conns = p_value; if (conns.size() % 4 == 0) { for (int i = 0; i < conns.size(); i += 4) { - connect_nodes(type, conns[i + 0], conns[i + 1], conns[i + 2], conns[i + 3]); + connect_nodes_forced(type, conns[i + 0], conns[i + 1], conns[i + 2], conns[i + 3]); } } return true; @@ -611,6 +674,18 @@ bool VisualShader::_set(const StringName &p_name, const Variant &p_value) { } else if (what == "position") { set_node_position(type, id, p_value); return true; + } else if (what == "size") { + ((VisualShaderNodeGroupBase *)get_node(type, id).ptr())->set_size(p_value); + return true; + } else if (what == "input_ports") { + ((VisualShaderNodeGroupBase *)get_node(type, id).ptr())->set_inputs(p_value); + return true; + } else if (what == "output_ports") { + ((VisualShaderNodeGroupBase *)get_node(type, id).ptr())->set_outputs(p_value); + return true; + } else if (what == "expression") { + ((VisualShaderNodeExpression *)get_node(type, id).ptr())->set_expression(p_value); + return true; } } return false; @@ -668,6 +743,18 @@ bool VisualShader::_get(const StringName &p_name, Variant &r_ret) const { } else if (what == "position") { r_ret = get_node_position(type, id); return true; + } else if (what == "size") { + r_ret = ((VisualShaderNodeGroupBase *)get_node(type, id).ptr())->get_size(); + return true; + } else if (what == "input_ports") { + r_ret = ((VisualShaderNodeGroupBase *)get_node(type, id).ptr())->get_inputs(); + return true; + } else if (what == "output_ports") { + r_ret = ((VisualShaderNodeGroupBase *)get_node(type, id).ptr())->get_outputs(); + return true; + } else if (what == "expression") { + r_ret = ((VisualShaderNodeExpression *)get_node(type, id).ptr())->get_expression(); + return true; } } return false; @@ -727,6 +814,15 @@ void VisualShader::_get_property_list(List<PropertyInfo> *p_list) const { p_list->push_back(PropertyInfo(Variant::OBJECT, prop_name + "/node", PROPERTY_HINT_RESOURCE_TYPE, "VisualShaderNode", PROPERTY_USAGE_NOEDITOR | PROPERTY_USAGE_DO_NOT_SHARE_ON_DUPLICATE)); } p_list->push_back(PropertyInfo(Variant::VECTOR2, prop_name + "/position", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NOEDITOR)); + + if (Object::cast_to<VisualShaderNodeGroupBase>(E->get().node.ptr()) != NULL) { + p_list->push_back(PropertyInfo(Variant::VECTOR2, prop_name + "/size", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NOEDITOR)); + p_list->push_back(PropertyInfo(Variant::STRING, prop_name + "/input_ports", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NOEDITOR)); + p_list->push_back(PropertyInfo(Variant::STRING, prop_name + "/output_ports", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NOEDITOR)); + } + if (Object::cast_to<VisualShaderNodeExpression>(E->get().node.ptr()) != NULL) { + p_list->push_back(PropertyInfo(Variant::STRING, prop_name + "/expression", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NOEDITOR)); + } } p_list->push_back(PropertyInfo(Variant::POOL_INT_ARRAY, "nodes/" + String(type_string[i]) + "/connections", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NOEDITOR)); } @@ -993,26 +1089,33 @@ void VisualShader::_input_type_changed(Type p_type, int p_id) { } } +void VisualShader::rebuild() { + dirty = true; + _update_shader(); +} + void VisualShader::_bind_methods() { ClassDB::bind_method(D_METHOD("set_mode", "mode"), &VisualShader::set_mode); ClassDB::bind_method(D_METHOD("add_node", "type", "node", "position", "id"), &VisualShader::add_node); - ClassDB::bind_method(D_METHOD("set_node_position", "type", "id", "position"), &VisualShader::set_node_position); - ClassDB::bind_method(D_METHOD("get_node", "type", "id"), &VisualShader::get_node); + + ClassDB::bind_method(D_METHOD("set_node_position", "type", "id", "position"), &VisualShader::set_node_position); ClassDB::bind_method(D_METHOD("get_node_position", "type", "id"), &VisualShader::get_node_position); ClassDB::bind_method(D_METHOD("get_node_list", "type"), &VisualShader::get_node_list); ClassDB::bind_method(D_METHOD("get_valid_node_id", "type"), &VisualShader::get_valid_node_id); ClassDB::bind_method(D_METHOD("remove_node", "type", "id"), &VisualShader::remove_node); + ClassDB::bind_method(D_METHOD("rebuild"), &VisualShader::rebuild); ClassDB::bind_method(D_METHOD("is_node_connection", "type", "from_node", "from_port", "to_node", "to_port"), &VisualShader::is_node_connection); ClassDB::bind_method(D_METHOD("can_connect_nodes", "type", "from_node", "from_port", "to_node", "to_port"), &VisualShader::is_node_connection); ClassDB::bind_method(D_METHOD("connect_nodes", "type", "from_node", "from_port", "to_node", "to_port"), &VisualShader::connect_nodes); ClassDB::bind_method(D_METHOD("disconnect_nodes", "type", "from_node", "from_port", "to_node", "to_port"), &VisualShader::disconnect_nodes); + ClassDB::bind_method(D_METHOD("connect_nodes_forced", "type", "from_node", "from_port", "to_node", "to_port"), &VisualShader::connect_nodes_forced); ClassDB::bind_method(D_METHOD("get_node_connections", "type"), &VisualShader::_get_node_connections); @@ -1627,3 +1730,555 @@ void VisualShaderNodeUniform::_bind_methods() { VisualShaderNodeUniform::VisualShaderNodeUniform() { } + +////////////// GroupBase + +String VisualShaderNodeGroupBase::get_caption() const { + return "Group"; +} + +void VisualShaderNodeGroupBase::set_size(const Vector2 &p_size) { + size = p_size; +} + +Vector2 VisualShaderNodeGroupBase::get_size() const { + return size; +} + +void VisualShaderNodeGroupBase::set_inputs(const String &p_inputs) { + + if (inputs == p_inputs) + return; + + clear_input_ports(); + + inputs = p_inputs; + + Vector<String> input_strings = inputs.split(";", false); + + int input_port_count = input_strings.size(); + + for (int i = 0; i < input_port_count; i++) { + + Vector<String> arr = input_strings[i].split(","); + + int port_idx = arr[0].to_int(); + int port_type = arr[1].to_int(); + String port_name = arr[2]; + + Port port; + port.type = (PortType)port_type; + port.name = port_name; + input_ports[port_idx] = port; + } +} + +String VisualShaderNodeGroupBase::get_inputs() const { + return inputs; +} + +void VisualShaderNodeGroupBase::set_outputs(const String &p_outputs) { + + if (outputs == p_outputs) + return; + + clear_output_ports(); + + outputs = p_outputs; + + Vector<String> output_strings = outputs.split(";", false); + + int output_port_count = output_strings.size(); + + for (int i = 0; i < output_port_count; i++) { + + Vector<String> arr = output_strings[i].split(","); + + int port_idx = arr[0].to_int(); + int port_type = arr[1].to_int(); + String port_name = arr[2]; + + Port port; + port.type = (PortType)port_type; + port.name = port_name; + output_ports[port_idx] = port; + } +} + +String VisualShaderNodeGroupBase::get_outputs() const { + return outputs; +} + +void VisualShaderNodeGroupBase::add_input_port(int p_id, int p_type, const String &p_name) { + + String str = itos(p_id) + "," + itos(p_type) + "," + p_name + ";"; + Vector<String> inputs_strings = inputs.split(";", false); + int index = 0; + if (p_id < inputs_strings.size()) { + for (int i = 0; i < inputs_strings.size(); i++) { + if (i == p_id) { + inputs = inputs.insert(index, str); + break; + } + index += inputs_strings[i].size(); + } + } else { + inputs += str; + } + + inputs_strings = inputs.split(";", false); + index = 0; + + for (int i = 0; i < inputs_strings.size(); i++) { + int count = 0; + for (int j = 0; j < inputs_strings[i].size(); j++) { + if (inputs_strings[i][j] == ',') { + break; + } + count++; + } + + inputs.erase(index, count); + inputs = inputs.insert(index, itos(i)); + index += inputs_strings[i].size(); + } + + _apply_port_changes(); +} + +void VisualShaderNodeGroupBase::remove_input_port(int p_id) { + + Vector<String> inputs_strings = inputs.split(";", false); + int count = 0; + int index = 0; + for (int i = 0; i < inputs_strings.size(); i++) { + Vector<String> arr = inputs_strings[i].split(","); + if (arr[0].to_int() == p_id) { + count = inputs_strings[i].size(); + break; + } + index += inputs_strings[i].size(); + } + inputs.erase(index, count); + + inputs_strings = inputs.split(";", false); + for (int i = p_id; i < inputs_strings.size(); i++) { + inputs = inputs.replace_first(inputs_strings[i].split(",")[0], itos(i)); + } + + _apply_port_changes(); +} + +int VisualShaderNodeGroupBase::get_input_port_count() const { + return input_ports.size(); +} + +bool VisualShaderNodeGroupBase::has_input_port(int p_id) const { + return input_ports.has(p_id); +} + +void VisualShaderNodeGroupBase::add_output_port(int p_id, int p_type, const String &p_name) { + + String str = itos(p_id) + "," + itos(p_type) + "," + p_name + ";"; + Vector<String> outputs_strings = outputs.split(";", false); + int index = 0; + if (p_id < outputs_strings.size()) { + for (int i = 0; i < outputs_strings.size(); i++) { + if (i == p_id) { + outputs = outputs.insert(index, str); + break; + } + index += outputs_strings[i].size(); + } + } else { + outputs += str; + } + + outputs_strings = outputs.split(";", false); + index = 0; + + for (int i = 0; i < outputs_strings.size(); i++) { + int count = 0; + for (int j = 0; j < outputs_strings[i].size(); j++) { + if (outputs_strings[i][j] == ',') { + break; + } + count++; + } + + outputs.erase(index, count); + outputs = outputs.insert(index, itos(i)); + index += outputs_strings[i].size(); + } + + _apply_port_changes(); +} + +void VisualShaderNodeGroupBase::remove_output_port(int p_id) { + + Vector<String> outputs_strings = outputs.split(";", false); + int count = 0; + int index = 0; + for (int i = 0; i < outputs_strings.size(); i++) { + Vector<String> arr = outputs_strings[i].split(","); + if (arr[0].to_int() == p_id) { + count = outputs_strings[i].size(); + break; + } + index += outputs_strings[i].size(); + } + outputs.erase(index, count); + + outputs_strings = outputs.split(";", false); + for (int i = p_id; i < outputs_strings.size(); i++) { + outputs = outputs.replace_first(outputs_strings[i].split(",")[0], itos(i)); + } + + _apply_port_changes(); +} + +int VisualShaderNodeGroupBase::get_output_port_count() const { + return output_ports.size(); +} + +bool VisualShaderNodeGroupBase::has_output_port(int p_id) const { + return output_ports.has(p_id); +} + +void VisualShaderNodeGroupBase::clear_input_ports() { + input_ports.clear(); +} + +void VisualShaderNodeGroupBase::clear_output_ports() { + output_ports.clear(); +} + +void VisualShaderNodeGroupBase::set_input_port_type(int p_id, int p_type) { + + if (input_ports[p_id].type == p_type) + return; + + Vector<String> inputs_strings = inputs.split(";", false); + int count = 0; + int index = 0; + for (int i = 0; i < inputs_strings.size(); i++) { + Vector<String> arr = inputs_strings[i].split(","); + if (arr[0].to_int() == p_id) { + index += arr[0].size(); + count = arr[1].size() - 1; + break; + } + index += inputs_strings[i].size(); + } + + inputs.erase(index, count); + + inputs = inputs.insert(index, itos(p_type)); + + _apply_port_changes(); +} + +VisualShaderNodeGroupBase::PortType VisualShaderNodeGroupBase::get_input_port_type(int p_id) const { + ERR_FAIL_COND_V(!input_ports.has(p_id), (PortType)0); + return input_ports[p_id].type; +} + +void VisualShaderNodeGroupBase::set_input_port_name(int p_id, const String &p_name) { + + if (input_ports[p_id].name == p_name) + return; + + Vector<String> inputs_strings = inputs.split(";", false); + int count = 0; + int index = 0; + for (int i = 0; i < inputs_strings.size(); i++) { + Vector<String> arr = inputs_strings[i].split(","); + if (arr[0].to_int() == p_id) { + index += arr[0].size() + arr[1].size(); + count = arr[2].size() - 1; + break; + } + index += inputs_strings[i].size(); + } + + inputs.erase(index, count); + + inputs = inputs.insert(index, p_name); + + _apply_port_changes(); +} + +String VisualShaderNodeGroupBase::get_input_port_name(int p_id) const { + ERR_FAIL_COND_V(!input_ports.has(p_id), ""); + return input_ports[p_id].name; +} + +void VisualShaderNodeGroupBase::set_output_port_type(int p_id, int p_type) { + + if (output_ports[p_id].type == p_type) + return; + + Vector<String> output_strings = outputs.split(";", false); + int count = 0; + int index = 0; + for (int i = 0; i < output_strings.size(); i++) { + Vector<String> arr = output_strings[i].split(","); + if (arr[0].to_int() == p_id) { + index += arr[0].size(); + count = arr[1].size() - 1; + break; + } + index += output_strings[i].size(); + } + + outputs.erase(index, count); + + outputs = outputs.insert(index, itos(p_type)); + + _apply_port_changes(); +} + +VisualShaderNodeGroupBase::PortType VisualShaderNodeGroupBase::get_output_port_type(int p_id) const { + ERR_FAIL_COND_V(!output_ports.has(p_id), (PortType)0); + return output_ports[p_id].type; +} + +void VisualShaderNodeGroupBase::set_output_port_name(int p_id, const String &p_name) { + if (output_ports[p_id].name == p_name) + return; + + Vector<String> output_strings = outputs.split(";", false); + int count = 0; + int index = 0; + for (int i = 0; i < output_strings.size(); i++) { + Vector<String> arr = output_strings[i].split(","); + if (arr[0].to_int() == p_id) { + index += arr[0].size() + arr[1].size(); + count = arr[2].size() - 1; + break; + } + index += output_strings[i].size(); + } + + outputs.erase(index, count); + + outputs = outputs.insert(index, p_name); + + _apply_port_changes(); +} + +String VisualShaderNodeGroupBase::get_output_port_name(int p_id) const { + ERR_FAIL_COND_V(!output_ports.has(p_id), ""); + return output_ports[p_id].name; +} + +int VisualShaderNodeGroupBase::get_free_input_port_id() const { + return input_ports.size(); +} + +int VisualShaderNodeGroupBase::get_free_output_port_id() const { + return output_ports.size(); +} + +void VisualShaderNodeGroupBase::set_control(Control *p_control, int p_index) { + controls[p_index] = p_control; +} + +Control *VisualShaderNodeGroupBase::get_control(int p_index) { + ERR_FAIL_COND_V(!controls.has(p_index), NULL); + return controls[p_index]; +} + +void VisualShaderNodeGroupBase::_apply_port_changes() { + + Vector<String> inputs_strings = inputs.split(";", false); + Vector<String> outputs_strings = outputs.split(";", false); + + clear_input_ports(); + clear_output_ports(); + + for (int i = 0; i < inputs_strings.size(); i++) { + Vector<String> arr = inputs_strings[i].split(","); + Port port; + port.type = (PortType)arr[1].to_int(); + port.name = arr[2]; + input_ports[i] = port; + } + for (int i = 0; i < outputs_strings.size(); i++) { + Vector<String> arr = outputs_strings[i].split(","); + Port port; + port.type = (PortType)arr[1].to_int(); + port.name = arr[2]; + output_ports[i] = port; + } +} + +void VisualShaderNodeGroupBase::_bind_methods() { + + ClassDB::bind_method(D_METHOD("set_size", "size"), &VisualShaderNodeGroupBase::set_size); + ClassDB::bind_method(D_METHOD("get_size"), &VisualShaderNodeGroupBase::get_size); + + ClassDB::bind_method(D_METHOD("set_inputs", "inputs"), &VisualShaderNodeGroupBase::set_inputs); + ClassDB::bind_method(D_METHOD("get_inputs"), &VisualShaderNodeGroupBase::get_inputs); + + ClassDB::bind_method(D_METHOD("set_outputs", "outputs"), &VisualShaderNodeGroupBase::set_outputs); + ClassDB::bind_method(D_METHOD("get_outputs"), &VisualShaderNodeGroupBase::get_outputs); + + ClassDB::bind_method(D_METHOD("add_input_port", "id", "type", "name"), &VisualShaderNodeGroupBase::add_input_port); + ClassDB::bind_method(D_METHOD("remove_input_port", "id"), &VisualShaderNodeGroupBase::remove_input_port); + ClassDB::bind_method(D_METHOD("get_input_port_count"), &VisualShaderNodeGroupBase::get_input_port_count); + ClassDB::bind_method(D_METHOD("has_input_port", "id"), &VisualShaderNodeGroupBase::has_input_port); + ClassDB::bind_method(D_METHOD("clear_input_ports"), &VisualShaderNodeGroupBase::clear_input_ports); + + ClassDB::bind_method(D_METHOD("add_output_port", "id", "type", "name"), &VisualShaderNodeGroupBase::add_output_port); + ClassDB::bind_method(D_METHOD("remove_output_port", "id"), &VisualShaderNodeGroupBase::remove_output_port); + ClassDB::bind_method(D_METHOD("get_output_port_count"), &VisualShaderNodeGroupBase::get_output_port_count); + ClassDB::bind_method(D_METHOD("has_output_port", "id"), &VisualShaderNodeGroupBase::has_output_port); + ClassDB::bind_method(D_METHOD("clear_output_ports"), &VisualShaderNodeGroupBase::clear_output_ports); + + ClassDB::bind_method(D_METHOD("set_input_port_name"), &VisualShaderNodeGroupBase::set_input_port_name); + ClassDB::bind_method(D_METHOD("set_input_port_type"), &VisualShaderNodeGroupBase::set_input_port_type); + ClassDB::bind_method(D_METHOD("set_output_port_name"), &VisualShaderNodeGroupBase::set_output_port_name); + ClassDB::bind_method(D_METHOD("set_output_port_type"), &VisualShaderNodeGroupBase::set_output_port_type); + + ClassDB::bind_method(D_METHOD("get_free_input_port_id"), &VisualShaderNodeGroupBase::get_free_input_port_id); + ClassDB::bind_method(D_METHOD("get_free_output_port_id"), &VisualShaderNodeGroupBase::get_free_output_port_id); + + ClassDB::bind_method(D_METHOD("set_control", "control", "index"), &VisualShaderNodeGroupBase::set_control); + ClassDB::bind_method(D_METHOD("get_control", "index"), &VisualShaderNodeGroupBase::get_control); +} + +String VisualShaderNodeGroupBase::generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars, bool p_for_preview) const { + return ""; +} + +VisualShaderNodeGroupBase::VisualShaderNodeGroupBase() { + size = Size2(0, 0); + inputs = ""; + outputs = ""; +} + +////////////// Expression + +String VisualShaderNodeExpression::get_caption() const { + return "Expression"; +} + +void VisualShaderNodeExpression::set_expression(const String &p_expression) { + expression = p_expression; +} + +void VisualShaderNodeExpression::build() { + emit_changed(); +} + +String VisualShaderNodeExpression::get_expression() const { + return expression; +} + +String VisualShaderNodeExpression::generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars, bool p_for_preview) const { + + String _expression = expression; + + _expression = _expression.insert(0, "\n"); + _expression = _expression.replace("\n", "\n\t\t"); + + static Vector<String> pre_symbols; + if (pre_symbols.empty()) { + pre_symbols.push_back("\t"); + pre_symbols.push_back("{"); + pre_symbols.push_back("["); + pre_symbols.push_back("("); + pre_symbols.push_back(" "); + pre_symbols.push_back("-"); + pre_symbols.push_back("*"); + pre_symbols.push_back("/"); + pre_symbols.push_back("+"); + pre_symbols.push_back("="); + pre_symbols.push_back("&"); + pre_symbols.push_back("|"); + pre_symbols.push_back("!"); + } + + static Vector<String> post_symbols; + if (post_symbols.empty()) { + post_symbols.push_back("\0"); + post_symbols.push_back("\t"); + post_symbols.push_back("\n"); + post_symbols.push_back(";"); + post_symbols.push_back("}"); + post_symbols.push_back("]"); + post_symbols.push_back(")"); + post_symbols.push_back(" "); + post_symbols.push_back("."); + post_symbols.push_back("-"); + post_symbols.push_back("*"); + post_symbols.push_back("/"); + post_symbols.push_back("+"); + post_symbols.push_back("="); + post_symbols.push_back("&"); + post_symbols.push_back("|"); + post_symbols.push_back("!"); + } + + for (int i = 0; i < get_input_port_count(); i++) { + for (int j = 0; j < pre_symbols.size(); j++) { + for (int k = 0; k < post_symbols.size(); k++) { + _expression = _expression.replace(pre_symbols[j] + get_input_port_name(i) + post_symbols[k], pre_symbols[j] + p_input_vars[i] + post_symbols[k]); + } + } + } + for (int i = 0; i < get_output_port_count(); i++) { + for (int j = 0; j < pre_symbols.size(); j++) { + for (int k = 0; k < post_symbols.size(); k++) { + _expression = _expression.replace(pre_symbols[j] + get_output_port_name(i) + post_symbols[k], pre_symbols[j] + p_output_vars[i] + post_symbols[k]); + } + } + } + + String output_initializer; + + for (int i = 0; i < get_output_port_count(); i++) { + int port_type = get_output_port_type(i); + String tk = ""; + switch (port_type) { + case PORT_TYPE_SCALAR: + tk = "0.0"; + break; + case PORT_TYPE_VECTOR: + tk = "vec3(0.0, 0.0, 0.0)"; + break; + case PORT_TYPE_BOOLEAN: + tk = "false"; + break; + case PORT_TYPE_TRANSFORM: + tk = "mat4(1.0)"; + break; + default: + continue; + } + output_initializer += "\t" + p_output_vars[i] + "=" + tk + ";\n"; + } + + String code; + code += output_initializer; + code += "\t{"; + code += _expression; + code += "\n\t}"; + + return code; +} + +void VisualShaderNodeExpression::_bind_methods() { + + ClassDB::bind_method(D_METHOD("set_expression", "expression"), &VisualShaderNodeExpression::set_expression); + ClassDB::bind_method(D_METHOD("get_expression"), &VisualShaderNodeExpression::get_expression); + + ClassDB::bind_method(D_METHOD("build"), &VisualShaderNodeExpression::build); + + ADD_PROPERTY(PropertyInfo(Variant::STRING, "expression"), "set_expression", "get_expression"); +} + +VisualShaderNodeExpression::VisualShaderNodeExpression() { + expression = ""; +} diff --git a/scene/resources/visual_shader.h b/scene/resources/visual_shader.h index cf10de9bf5..ea39d118e4 100644 --- a/scene/resources/visual_shader.h +++ b/scene/resources/visual_shader.h @@ -135,7 +135,9 @@ public: bool can_connect_nodes(Type p_type, int p_from_node, int p_from_port, int p_to_node, int p_to_port) const; Error connect_nodes(Type p_type, int p_from_node, int p_from_port, int p_to_node, int p_to_port); void disconnect_nodes(Type p_type, int p_from_node, int p_from_port, int p_to_node, int p_to_port); + void connect_nodes_forced(Type p_type, int p_from_node, int p_from_port, int p_to_node, int p_to_port); + void rebuild(); void get_node_connections(Type p_type, List<Connection> *r_connections) const; void set_mode(Mode p_mode); @@ -148,6 +150,7 @@ public: String generate_preview_shader(Type p_type, int p_node, int p_port, Vector<DefaultTextureParam> &r_default_tex_params) const; + String validate_port_name(const String &p_name, const List<String> &p_input_ports, const List<String> &p_output_ports) const; String validate_uniform_name(const String &p_name, const Ref<VisualShaderNodeUniform> &p_uniform) const; VisualShader(); @@ -314,4 +317,93 @@ public: VisualShaderNodeUniform(); }; +class VisualShaderNodeGroupBase : public VisualShaderNode { + GDCLASS(VisualShaderNodeGroupBase, VisualShaderNode) +private: + void _apply_port_changes(); + +protected: + Vector2 size; + String inputs; + String outputs; + + struct Port { + PortType type; + String name; + }; + + Map<int, Port> input_ports; + Map<int, Port> output_ports; + Map<int, Control *> controls; + +protected: + static void _bind_methods(); + +public: + virtual String get_caption() const; + + void set_size(const Vector2 &p_size); + Vector2 get_size() const; + + void set_inputs(const String &p_inputs); + String get_inputs() const; + + void set_outputs(const String &p_outputs); + String get_outputs() const; + + void add_input_port(int p_id, int p_type, const String &p_name); + void remove_input_port(int p_id); + virtual int get_input_port_count() const; + bool has_input_port(int p_id) const; + void clear_input_ports(); + + void add_output_port(int p_id, int p_type, const String &p_name); + void remove_output_port(int p_id); + virtual int get_output_port_count() const; + bool has_output_port(int p_id) const; + void clear_output_ports(); + + void set_input_port_type(int p_id, int p_type); + virtual PortType get_input_port_type(int p_id) const; + void set_input_port_name(int p_id, const String &p_name); + virtual String get_input_port_name(int p_id) const; + + void set_output_port_type(int p_id, int p_type); + virtual PortType get_output_port_type(int p_id) const; + void set_output_port_name(int p_id, const String &p_name); + virtual String get_output_port_name(int p_id) const; + + int get_free_input_port_id() const; + int get_free_output_port_id() const; + + void set_control(Control *p_control, int p_index); + Control *get_control(int p_index); + + virtual String generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars, bool p_for_preview = false) const; + + VisualShaderNodeGroupBase(); +}; + +class VisualShaderNodeExpression : public VisualShaderNodeGroupBase { + GDCLASS(VisualShaderNodeExpression, VisualShaderNodeGroupBase) + +private: + String expression; + +protected: + static void _bind_methods(); + +public: + virtual String get_caption() const; + + void set_expression(const String &p_expression); + String get_expression() const; + + void build(); + + virtual String generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars, bool p_for_preview = false) const; + + VisualShaderNodeExpression(); +}; + #endif // VISUAL_SHADER_H diff --git a/scene/resources/visual_shader_nodes.cpp b/scene/resources/visual_shader_nodes.cpp index 9b8037965b..a44471a365 100644 --- a/scene/resources/visual_shader_nodes.cpp +++ b/scene/resources/visual_shader_nodes.cpp @@ -1192,7 +1192,7 @@ String VisualShaderNodeScalarFunc::get_output_port_name(int p_port) const { String VisualShaderNodeScalarFunc::generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars, bool p_for_preview) const { - static const char *scalar_func_id[FUNC_TRUNC + 1] = { + static const char *scalar_func_id[FUNC_ONEMINUS + 1] = { "sin($)", "cos($)", "tan($)", @@ -1223,7 +1223,8 @@ String VisualShaderNodeScalarFunc::generate_code(Shader::Mode p_mode, VisualShad "radians($)", "1.0/($)", "roundEven($)", - "trunc($)" + "trunc($)", + "1.0-$" }; return "\t" + p_output_vars[0] + " = " + String(scalar_func_id[func]).replace("$", p_input_vars[0]) + ";\n"; @@ -1251,7 +1252,7 @@ void VisualShaderNodeScalarFunc::_bind_methods() { ClassDB::bind_method(D_METHOD("set_function", "func"), &VisualShaderNodeScalarFunc::set_function); ClassDB::bind_method(D_METHOD("get_function"), &VisualShaderNodeScalarFunc::get_function); - ADD_PROPERTY(PropertyInfo(Variant::INT, "function", PROPERTY_HINT_ENUM, "Sin,Cos,Tan,ASin,ACos,ATan,SinH,CosH,TanH,Log,Exp,Sqrt,Abs,Sign,Floor,Round,Ceil,Frac,Saturate,Negate,ACosH,ASinH,ATanH,Degrees,Exp2,InverseSqrt,Log2,Radians,Reciprocal,RoundEven,Trunc"), "set_function", "get_function"); + ADD_PROPERTY(PropertyInfo(Variant::INT, "function", PROPERTY_HINT_ENUM, "Sin,Cos,Tan,ASin,ACos,ATan,SinH,CosH,TanH,Log,Exp,Sqrt,Abs,Sign,Floor,Round,Ceil,Frac,Saturate,Negate,ACosH,ASinH,ATanH,Degrees,Exp2,InverseSqrt,Log2,Radians,Reciprocal,RoundEven,Trunc,OneMinus"), "set_function", "get_function"); BIND_ENUM_CONSTANT(FUNC_SIN); BIND_ENUM_CONSTANT(FUNC_COS); @@ -1284,6 +1285,7 @@ void VisualShaderNodeScalarFunc::_bind_methods() { BIND_ENUM_CONSTANT(FUNC_RECIPROCAL); BIND_ENUM_CONSTANT(FUNC_ROUNDEVEN); BIND_ENUM_CONSTANT(FUNC_TRUNC); + BIND_ENUM_CONSTANT(FUNC_ONEMINUS); } VisualShaderNodeScalarFunc::VisualShaderNodeScalarFunc() { @@ -1319,7 +1321,7 @@ String VisualShaderNodeVectorFunc::get_output_port_name(int p_port) const { String VisualShaderNodeVectorFunc::generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars, bool p_for_preview) const { - static const char *vec_func_id[FUNC_TRUNC + 1] = { + static const char *vec_func_id[FUNC_ONEMINUS + 1] = { "normalize($)", "max(min($,vec3(1.0)),vec3(0.0))", "-($)", @@ -1353,7 +1355,8 @@ String VisualShaderNodeVectorFunc::generate_code(Shader::Mode p_mode, VisualShad "sqrt($)", "tan($)", "tanh($)", - "trunc($)" + "trunc($)", + "vec3(1.0, 1.0, 1.0)-$" }; String code; @@ -1405,7 +1408,7 @@ void VisualShaderNodeVectorFunc::_bind_methods() { ClassDB::bind_method(D_METHOD("set_function", "func"), &VisualShaderNodeVectorFunc::set_function); ClassDB::bind_method(D_METHOD("get_function"), &VisualShaderNodeVectorFunc::get_function); - ADD_PROPERTY(PropertyInfo(Variant::INT, "function", PROPERTY_HINT_ENUM, "Normalize,Saturate,Negate,Reciprocal,RGB2HSV,HSV2RGB,Abs,ACos,ACosH,ASin,ASinH,ATan,ATanH,Ceil,Cos,CosH,Degrees,Exp,Exp2,Floor,Frac,InverseSqrt,Log,Log2,Radians,Round,RoundEven,Sign,Sin,SinH,Sqrt,Tan,TanH,Trunc"), "set_function", "get_function"); + ADD_PROPERTY(PropertyInfo(Variant::INT, "function", PROPERTY_HINT_ENUM, "Normalize,Saturate,Negate,Reciprocal,RGB2HSV,HSV2RGB,Abs,ACos,ACosH,ASin,ASinH,ATan,ATanH,Ceil,Cos,CosH,Degrees,Exp,Exp2,Floor,Frac,InverseSqrt,Log,Log2,Radians,Round,RoundEven,Sign,Sin,SinH,Sqrt,Tan,TanH,Trunc,OneMinus"), "set_function", "get_function"); BIND_ENUM_CONSTANT(FUNC_NORMALIZE); BIND_ENUM_CONSTANT(FUNC_SATURATE); @@ -1441,6 +1444,7 @@ void VisualShaderNodeVectorFunc::_bind_methods() { BIND_ENUM_CONSTANT(FUNC_TAN); BIND_ENUM_CONSTANT(FUNC_TANH); BIND_ENUM_CONSTANT(FUNC_TRUNC); + BIND_ENUM_CONSTANT(FUNC_ONEMINUS); } VisualShaderNodeVectorFunc::VisualShaderNodeVectorFunc() { @@ -3085,3 +3089,66 @@ VisualShaderNodeSwitch::VisualShaderNodeSwitch() { set_input_port_default_value(1, Vector3(0.0, 0.0, 0.0)); set_input_port_default_value(2, Vector3(0.0, 0.0, 0.0)); } + +////////////// Fresnel + +String VisualShaderNodeFresnel::get_caption() const { + return "Fresnel"; +} + +int VisualShaderNodeFresnel::get_input_port_count() const { + return 4; +} + +VisualShaderNodeFresnel::PortType VisualShaderNodeFresnel::get_input_port_type(int p_port) const { + switch (p_port) { + case 0: + return PORT_TYPE_VECTOR; + case 1: + return PORT_TYPE_VECTOR; + case 2: + return PORT_TYPE_BOOLEAN; + case 3: + return PORT_TYPE_SCALAR; + default: + return PORT_TYPE_VECTOR; + } +} + +String VisualShaderNodeFresnel::get_input_port_name(int p_port) const { + switch (p_port) { + case 0: + return "normal"; + case 1: + return "view"; + case 2: + return "invert"; + case 3: + return "power"; + default: + return ""; + } +} + +int VisualShaderNodeFresnel::get_output_port_count() const { + return 1; +} + +VisualShaderNodeFresnel::PortType VisualShaderNodeFresnel::get_output_port_type(int p_port) const { + return PORT_TYPE_SCALAR; +} + +String VisualShaderNodeFresnel::get_output_port_name(int p_port) const { + return "result"; +} + +String VisualShaderNodeFresnel::generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars, bool p_for_preview) const { + return "\t" + p_output_vars[0] + " = " + p_input_vars[2] + " ? (pow(clamp(dot(" + p_input_vars[0] + ", " + p_input_vars[1] + "), 0.0, 1.0), " + p_input_vars[3] + ")) : (pow(1.0 - clamp(dot(" + p_input_vars[0] + ", " + p_input_vars[1] + "), 0.0, 1.0), " + p_input_vars[3] + "));"; +} + +VisualShaderNodeFresnel::VisualShaderNodeFresnel() { + set_input_port_default_value(0, Vector3(0.0, 0.0, 0.0)); + set_input_port_default_value(1, Vector3(0.0, 0.0, 0.0)); + set_input_port_default_value(2, false); + set_input_port_default_value(3, 1.0); +} diff --git a/scene/resources/visual_shader_nodes.h b/scene/resources/visual_shader_nodes.h index 90c479bd48..852248b9b4 100644 --- a/scene/resources/visual_shader_nodes.h +++ b/scene/resources/visual_shader_nodes.h @@ -562,7 +562,8 @@ public: FUNC_RADIANS, FUNC_RECIPROCAL, FUNC_ROUNDEVEN, - FUNC_TRUNC + FUNC_TRUNC, + FUNC_ONEMINUS }; protected: @@ -635,7 +636,8 @@ public: FUNC_SQRT, FUNC_TAN, FUNC_TANH, - FUNC_TRUNC + FUNC_TRUNC, + FUNC_ONEMINUS }; protected: @@ -1484,4 +1486,26 @@ public: VisualShaderNodeSwitch(); }; +/////////////////////////////////////// +/// FRESNEL +/////////////////////////////////////// + +class VisualShaderNodeFresnel : public VisualShaderNode { + GDCLASS(VisualShaderNodeFresnel, VisualShaderNode) +public: + virtual String get_caption() const; + + virtual int get_input_port_count() const; + virtual PortType get_input_port_type(int p_port) const; + virtual String get_input_port_name(int p_port) const; + + virtual int get_output_port_count() const; + virtual PortType get_output_port_type(int p_port) const; + virtual String get_output_port_name(int p_port) const; + + virtual String generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars, bool p_for_preview = false) const; + + VisualShaderNodeFresnel(); +}; + #endif // VISUAL_SHADER_NODES_H diff --git a/servers/audio/effects/audio_effect_spectrum_analyzer.cpp b/servers/audio/effects/audio_effect_spectrum_analyzer.cpp index 46d92336f3..8e15e9288f 100644 --- a/servers/audio/effects/audio_effect_spectrum_analyzer.cpp +++ b/servers/audio/effects/audio_effect_spectrum_analyzer.cpp @@ -112,7 +112,7 @@ void AudioEffectSpectrumAnalyzerInstance::process(const AudioFrame *p_src_frames } //determine time of capture - double remainer_sec = (temporal_fft_pos / mix_rate); //substract remainder from mix time + double remainer_sec = (temporal_fft_pos / mix_rate); //subtract remainder from mix time last_fft_time = time - uint64_t(remainer_sec * 1000000.0); } @@ -170,7 +170,7 @@ Vector2 AudioEffectSpectrumAnalyzerInstance::get_magnitude_for_frequency_range(f for (int i = begin_pos; i <= end_pos; i++) { max.x = MAX(max.x, r[i].l); - max.y = MAX(max.x, r[i].r); + max.y = MAX(max.y, r[i].r); } return max; diff --git a/servers/physics_2d/space_2d_sw.cpp b/servers/physics_2d/space_2d_sw.cpp index f5acadd71c..e2b1bb9da4 100644 --- a/servers/physics_2d/space_2d_sw.cpp +++ b/servers/physics_2d/space_2d_sw.cpp @@ -795,7 +795,7 @@ bool Space2DSW::test_body_motion(Body2DSW *p_body, const Transform2D &p_from, co cbk.valid_dir = col_obj_shape_xform.get_axis(1).normalized(); float owc_margin = col_obj->get_shape_one_way_collision_margin(shape_idx); - cbk.valid_depth = MAX(owc_margin, p_margin); //user specified, but never less than actual margin or it wont work + cbk.valid_depth = MAX(owc_margin, p_margin); //user specified, but never less than actual margin or it won't work cbk.invalid_by_dir = 0; if (col_obj->get_type() == CollisionObject2DSW::TYPE_BODY) { diff --git a/servers/visual/rasterizer.h b/servers/visual/rasterizer.h index a02f52f034..31888261ec 100644 --- a/servers/visual/rasterizer.h +++ b/servers/visual/rasterizer.h @@ -550,10 +550,12 @@ public: RENDER_TARGET_NO_SAMPLING, RENDER_TARGET_HDR, RENDER_TARGET_KEEP_3D_LINEAR, + RENDER_TARGET_DIRECT_TO_SCREEN, RENDER_TARGET_FLAG_MAX }; virtual RID render_target_create() = 0; + virtual void render_target_set_position(RID p_render_target, int p_x, int p_y) = 0; virtual void render_target_set_size(RID p_render_target, int p_width, int p_height) = 0; virtual RID render_target_get_texture(RID p_render_target) const = 0; virtual void render_target_set_external_texture(RID p_render_target, unsigned int p_texture_id) = 0; diff --git a/servers/visual/shader_language.cpp b/servers/visual/shader_language.cpp index 33714a79b2..6efd05593e 100644 --- a/servers/visual/shader_language.cpp +++ b/servers/visual/shader_language.cpp @@ -616,7 +616,7 @@ ShaderLanguage::Token ShaderLanguage::_get_token() { else tk.type = TK_INT_CONSTANT; - tk.constant = str.to_double(); //wont work with hex + tk.constant = str.to_double(); //won't work with hex tk.line = tk_line; return tk; @@ -2968,6 +2968,10 @@ ShaderLanguage::Node *ShaderLanguage::_parse_expression(BlockNode *p_block, cons member_type = DataType(dt - 1); } else if (l == 2) { member_type = dt; + } else if (l == 3) { + member_type = DataType(dt + 1); + } else if (l == 4) { + member_type = DataType(dt + 2); } else { ok = false; break; @@ -3001,6 +3005,8 @@ ShaderLanguage::Node *ShaderLanguage::_parse_expression(BlockNode *p_block, cons member_type = DataType(dt - 1); } else if (l == 3) { member_type = dt; + } else if (l == 4) { + member_type = DataType(dt + 1); } else { ok = false; break; diff --git a/servers/visual/shader_types.cpp b/servers/visual/shader_types.cpp index 8fd5dfc738..bc6010117c 100644 --- a/servers/visual/shader_types.cpp +++ b/servers/visual/shader_types.cpp @@ -147,6 +147,7 @@ ShaderTypes::ShaderTypes() { shader_modes[VS::SHADER_SPATIAL].functions["light"].built_ins["DIFFUSE_LIGHT"] = ShaderLanguage::TYPE_VEC3; shader_modes[VS::SHADER_SPATIAL].functions["light"].built_ins["SPECULAR_LIGHT"] = ShaderLanguage::TYPE_VEC3; shader_modes[VS::SHADER_SPATIAL].functions["light"].built_ins["OUTPUT_IS_SRGB"] = constt(ShaderLanguage::TYPE_BOOL); + shader_modes[VS::SHADER_SPATIAL].functions["light"].built_ins["ALPHA"] = ShaderLanguage::TYPE_FLOAT; shader_modes[VS::SHADER_SPATIAL].functions["light"].can_discard = true; @@ -187,6 +188,7 @@ ShaderTypes::ShaderTypes() { shader_modes[VS::SHADER_SPATIAL].modes.push_back("shadows_disabled"); shader_modes[VS::SHADER_SPATIAL].modes.push_back("ambient_light_disabled"); + shader_modes[VS::SHADER_SPATIAL].modes.push_back("shadow_to_opacity"); shader_modes[VS::SHADER_SPATIAL].modes.push_back("vertex_lighting"); diff --git a/servers/visual/visual_server_raster.h b/servers/visual/visual_server_raster.h index 3ec428d687..921d55556d 100644 --- a/servers/visual/visual_server_raster.h +++ b/servers/visual/visual_server_raster.h @@ -454,6 +454,7 @@ public: BIND2(viewport_set_clear_mode, RID, ViewportClearMode) BIND3(viewport_attach_to_screen, RID, const Rect2 &, int) + BIND2(viewport_set_render_direct_to_screen, RID, bool) BIND1(viewport_detach, RID) BIND2(viewport_set_update_mode, RID, ViewportUpdateMode) diff --git a/servers/visual/visual_server_viewport.cpp b/servers/visual/visual_server_viewport.cpp index e7f60c2c1f..b7c54caffd 100644 --- a/servers/visual/visual_server_viewport.cpp +++ b/servers/visual/visual_server_viewport.cpp @@ -343,7 +343,7 @@ void VisualServerViewport::draw_viewports() { vp->render_info[VS::VIEWPORT_RENDER_INFO_SURFACE_CHANGES_IN_FRAME] = VSG::storage->get_captured_render_info(VS::INFO_SURFACE_CHANGES_IN_FRAME); vp->render_info[VS::VIEWPORT_RENDER_INFO_DRAW_CALLS_IN_FRAME] = VSG::storage->get_captured_render_info(VS::INFO_DRAW_CALLS_IN_FRAME); - if (vp->viewport_to_screen_rect != Rect2()) { + if (vp->viewport_to_screen_rect != Rect2() && (!vp->viewport_render_direct_to_screen || !VSG::rasterizer->is_low_end())) { //copy to screen if set as such VSG::rasterizer->set_current_render_target(RID()); VSG::rasterizer->blit_render_target_to_screen(vp->render_target, vp->viewport_to_screen_rect, vp->viewport_to_screen); @@ -368,6 +368,7 @@ RID VisualServerViewport::viewport_create() { viewport->hide_canvas = false; viewport->render_target = VSG::storage->render_target_create(); viewport->shadow_atlas = VSG::scene_render->shadow_atlas_create(); + viewport->viewport_render_direct_to_screen = false; return rid; } @@ -424,14 +425,55 @@ void VisualServerViewport::viewport_attach_to_screen(RID p_viewport, const Rect2 Viewport *viewport = viewport_owner.getornull(p_viewport); ERR_FAIL_COND(!viewport); + // If using GLES2 we can optimize this operation by rendering directly to system_fbo + // instead of rendering to fbo and copying to system_fbo after + if (VSG::rasterizer->is_low_end() && viewport->viewport_render_direct_to_screen) { + + VSG::storage->render_target_set_size(viewport->render_target, p_rect.size.x, p_rect.size.y); + VSG::storage->render_target_set_position(viewport->render_target, p_rect.position.x, p_rect.position.y); + } + viewport->viewport_to_screen_rect = p_rect; viewport->viewport_to_screen = p_screen; } + +void VisualServerViewport::viewport_set_render_direct_to_screen(RID p_viewport, bool p_enable) { + Viewport *viewport = viewport_owner.getornull(p_viewport); + ERR_FAIL_COND(!viewport); + + if (p_enable == viewport->viewport_render_direct_to_screen) + return; + + // if disabled, reset render_target size and position + if (!p_enable) { + + VSG::storage->render_target_set_position(viewport->render_target, 0, 0); + VSG::storage->render_target_set_size(viewport->render_target, viewport->size.x, viewport->size.y); + } + + VSG::storage->render_target_set_flag(viewport->render_target, RasterizerStorage::RENDER_TARGET_DIRECT_TO_SCREEN, p_enable); + viewport->viewport_render_direct_to_screen = p_enable; + + // if attached to screen already, setup screen size and position, this needs to happen after setting flag to avoid an unneccesary buffer allocation + if (VSG::rasterizer->is_low_end() && viewport->viewport_to_screen_rect != Rect2() && p_enable) { + + VSG::storage->render_target_set_size(viewport->render_target, viewport->viewport_to_screen_rect.size.x, viewport->viewport_to_screen_rect.size.y); + VSG::storage->render_target_set_position(viewport->render_target, viewport->viewport_to_screen_rect.position.x, viewport->viewport_to_screen_rect.position.y); + } +} + void VisualServerViewport::viewport_detach(RID p_viewport) { Viewport *viewport = viewport_owner.getornull(p_viewport); ERR_FAIL_COND(!viewport); + // if render_direct_to_screen was used, reset size and position + if (VSG::rasterizer->is_low_end() && viewport->viewport_render_direct_to_screen) { + + VSG::storage->render_target_set_position(viewport->render_target, 0, 0); + VSG::storage->render_target_set_size(viewport->render_target, viewport->size.x, viewport->size.y); + } + viewport->viewport_to_screen_rect = Rect2(); viewport->viewport_to_screen = 0; } diff --git a/servers/visual/visual_server_viewport.h b/servers/visual/visual_server_viewport.h index 555b40a103..43bbcb66c3 100644 --- a/servers/visual/visual_server_viewport.h +++ b/servers/visual/visual_server_viewport.h @@ -58,6 +58,7 @@ public: int viewport_to_screen; Rect2 viewport_to_screen_rect; + bool viewport_render_direct_to_screen; bool hide_scenario; bool hide_canvas; @@ -158,6 +159,7 @@ public: void viewport_set_size(RID p_viewport, int p_width, int p_height); void viewport_attach_to_screen(RID p_viewport, const Rect2 &p_rect = Rect2(), int p_screen = 0); + void viewport_set_render_direct_to_screen(RID p_viewport, bool p_enable); void viewport_detach(RID p_viewport); void viewport_set_active(RID p_viewport, bool p_active); diff --git a/servers/visual/visual_server_wrap_mt.h b/servers/visual/visual_server_wrap_mt.h index b2753369b8..cd24deb60c 100644 --- a/servers/visual/visual_server_wrap_mt.h +++ b/servers/visual/visual_server_wrap_mt.h @@ -381,6 +381,7 @@ public: FUNC2(viewport_set_clear_mode, RID, ViewportClearMode) FUNC3(viewport_attach_to_screen, RID, const Rect2 &, int) + FUNC2(viewport_set_render_direct_to_screen, RID, bool) FUNC1(viewport_detach, RID) FUNC2(viewport_set_update_mode, RID, ViewportUpdateMode) diff --git a/servers/visual_server.cpp b/servers/visual_server.cpp index b39b400a53..0fe00ad61a 100644 --- a/servers/visual_server.cpp +++ b/servers/visual_server.cpp @@ -1876,6 +1876,7 @@ void VisualServer::_bind_methods() { ClassDB::bind_method(D_METHOD("viewport_set_active", "viewport", "active"), &VisualServer::viewport_set_active); ClassDB::bind_method(D_METHOD("viewport_set_parent_viewport", "viewport", "parent_viewport"), &VisualServer::viewport_set_parent_viewport); ClassDB::bind_method(D_METHOD("viewport_attach_to_screen", "viewport", "rect", "screen"), &VisualServer::viewport_attach_to_screen, DEFVAL(Rect2()), DEFVAL(0)); + ClassDB::bind_method(D_METHOD("viewport_set_render_direct_to_screen", "viewport", "enabled"), &VisualServer::viewport_set_render_direct_to_screen); ClassDB::bind_method(D_METHOD("viewport_detach", "viewport"), &VisualServer::viewport_detach); ClassDB::bind_method(D_METHOD("viewport_set_update_mode", "viewport", "update_mode"), &VisualServer::viewport_set_update_mode); ClassDB::bind_method(D_METHOD("viewport_set_vflip", "viewport", "enabled"), &VisualServer::viewport_set_vflip); diff --git a/servers/visual_server.h b/servers/visual_server.h index 5146ca47f1..01be996bfc 100644 --- a/servers/visual_server.h +++ b/servers/visual_server.h @@ -610,6 +610,7 @@ public: virtual void viewport_set_parent_viewport(RID p_viewport, RID p_parent_viewport) = 0; virtual void viewport_attach_to_screen(RID p_viewport, const Rect2 &p_rect = Rect2(), int p_screen = 0) = 0; + virtual void viewport_set_render_direct_to_screen(RID p_viewport, bool p_enable) = 0; virtual void viewport_detach(RID p_viewport) = 0; enum ViewportUpdateMode { diff --git a/thirdparty/README.md b/thirdparty/README.md index bc820634bb..732c08fdea 100644 --- a/thirdparty/README.md +++ b/thirdparty/README.md @@ -346,7 +346,7 @@ Collection of single-file libraries used in Godot components. * License: Public Domain - `clipper.{cpp,hpp}` * Upstream: https://sourceforge.net/projects/polyclipping - * Version: 6.4.2 + * Version: 6.4.2 + Godot changes (added optional exceptions handling) * License: BSL-1.0 - `fastlz.{c,h}` * Upstream: https://github.com/ariya/FastLZ diff --git a/thirdparty/assimp/code/res/resource.h b/thirdparty/assimp/code/res/resource.h deleted file mode 100644 index 37d39284fe..0000000000 --- a/thirdparty/assimp/code/res/resource.h +++ /dev/null @@ -1,14 +0,0 @@ -//{{NO_DEPENDENCIES}} -// Microsoft Visual C++ generated include file. -// Used by assimp.rc - -// Nächste Standardwerte für neue Objekte -// -#ifdef APSTUDIO_INVOKED -#ifndef APSTUDIO_READONLY_SYMBOLS -#define _APS_NEXT_RESOURCE_VALUE 101 -#define _APS_NEXT_COMMAND_VALUE 40001 -#define _APS_NEXT_CONTROL_VALUE 1001 -#define _APS_NEXT_SYMED_VALUE 101 -#endif -#endif diff --git a/thirdparty/misc/clipper-exceptions.patch b/thirdparty/misc/clipper-exceptions.patch new file mode 100644 index 0000000000..537afd59b3 --- /dev/null +++ b/thirdparty/misc/clipper-exceptions.patch @@ -0,0 +1,154 @@ +diff --git a/thirdparty/misc/clipper.cpp b/thirdparty/misc/clipper.cpp +index 8c3a59c4ca..c67045d113 100644 +--- a/thirdparty/misc/clipper.cpp ++++ b/thirdparty/misc/clipper.cpp +@@ -48,6 +48,38 @@ + #include <ostream> + #include <functional> + ++//Explicitly disables exceptions handling for target platform ++//#define CLIPPER_NOEXCEPTION ++ ++#define CLIPPER_THROW(exception) std::abort() ++#define CLIPPER_TRY if(true) ++#define CLIPPER_CATCH(exception) if(false) ++ ++#if defined(__cpp_exceptions) || defined(__EXCEPTIONS) || defined(_CPPUNWIND) ++ #ifndef CLIPPER_NOEXCEPTION ++ #undef CLIPPER_THROW ++ #define CLIPPER_THROW(exception) throw exception ++ #undef CLIPPER_TRY ++ #define CLIPPER_TRY try ++ #undef CLIPPER_CATCH ++ #define CLIPPER_CATCH(exception) catch(exception) ++ #endif ++#endif ++ ++//Optionally allows to override exception macros ++#if defined(CLIPPER_THROW_USER) ++ #undef CLIPPER_THROW ++ #define CLIPPER_THROW CLIPPER_THROW_USER ++#endif ++#if defined(CLIPPER_TRY_USER) ++ #undef CLIPPER_TRY ++ #define CLIPPER_TRY CLIPPER_TRY_USER ++#endif ++#if defined(CLIPPER_CATCH_USER) ++ #undef CLIPPER_CATCH ++ #define CLIPPER_CATCH CLIPPER_CATCH_USER ++#endif ++ + namespace ClipperLib { + + static double const pi = 3.141592653589793238; +@@ -898,7 +930,7 @@ void RangeTest(const IntPoint& Pt, bool& useFullRange) + if (useFullRange) + { + if (Pt.X > hiRange || Pt.Y > hiRange || -Pt.X > hiRange || -Pt.Y > hiRange) +- throw clipperException("Coordinate outside allowed range"); ++ CLIPPER_THROW(clipperException("Coordinate outside allowed range")); + } + else if (Pt.X > loRange|| Pt.Y > loRange || -Pt.X > loRange || -Pt.Y > loRange) + { +@@ -1046,10 +1078,10 @@ bool ClipperBase::AddPath(const Path &pg, PolyType PolyTyp, bool Closed) + { + #ifdef use_lines + if (!Closed && PolyTyp == ptClip) +- throw clipperException("AddPath: Open paths must be subject."); ++ CLIPPER_THROW(clipperException("AddPath: Open paths must be subject.")); + #else + if (!Closed) +- throw clipperException("AddPath: Open paths have been disabled."); ++ CLIPPER_THROW(clipperException("AddPath: Open paths have been disabled.")); + #endif + + int highI = (int)pg.size() -1; +@@ -1062,7 +1094,7 @@ bool ClipperBase::AddPath(const Path &pg, PolyType PolyTyp, bool Closed) + + bool IsFlat = true; + //1. Basic (first) edge initialization ... +- try ++ CLIPPER_TRY + { + edges[1].Curr = pg[1]; + RangeTest(pg[0], m_UseFullRange); +@@ -1075,10 +1107,10 @@ bool ClipperBase::AddPath(const Path &pg, PolyType PolyTyp, bool Closed) + InitEdge(&edges[i], &edges[i+1], &edges[i-1], pg[i]); + } + } +- catch(...) ++ CLIPPER_CATCH(...) + { + delete [] edges; +- throw; //range test fails ++ CLIPPER_THROW(); //range test fails + } + TEdge *eStart = &edges[0]; + +@@ -1442,7 +1474,7 @@ void ClipperBase::SwapPositionsInAEL(TEdge *Edge1, TEdge *Edge2) + void ClipperBase::UpdateEdgeIntoAEL(TEdge *&e) + { + if (!e->NextInLML) +- throw clipperException("UpdateEdgeIntoAEL: invalid call"); ++ CLIPPER_THROW(clipperException("UpdateEdgeIntoAEL: invalid call")); + + e->NextInLML->OutIdx = e->OutIdx; + TEdge* AelPrev = e->PrevInAEL; +@@ -1510,7 +1542,7 @@ bool Clipper::Execute(ClipType clipType, Paths &solution, + { + if( m_ExecuteLocked ) return false; + if (m_HasOpenPaths) +- throw clipperException("Error: PolyTree struct is needed for open path clipping."); ++ CLIPPER_THROW(clipperException("Error: PolyTree struct is needed for open path clipping.")); + m_ExecuteLocked = true; + solution.resize(0); + m_SubjFillType = subjFillType; +@@ -1560,7 +1592,7 @@ void Clipper::FixHoleLinkage(OutRec &outrec) + bool Clipper::ExecuteInternal() + { + bool succeeded = true; +- try { ++ CLIPPER_TRY { + Reset(); + m_Maxima = MaximaList(); + m_SortedEdges = 0; +@@ -1583,7 +1615,7 @@ bool Clipper::ExecuteInternal() + InsertLocalMinimaIntoAEL(botY); + } + } +- catch(...) ++ CLIPPER_CATCH(...) + { + succeeded = false; + } +@@ -2827,18 +2859,18 @@ void Clipper::ProcessHorizontal(TEdge *horzEdge) + bool Clipper::ProcessIntersections(const cInt topY) + { + if( !m_ActiveEdges ) return true; +- try { ++ CLIPPER_TRY { + BuildIntersectList(topY); + size_t IlSize = m_IntersectList.size(); + if (IlSize == 0) return true; + if (IlSize == 1 || FixupIntersectionOrder()) ProcessIntersectList(); + else return false; + } +- catch(...) ++ CLIPPER_CATCH(...) + { + m_SortedEdges = 0; + DisposeIntersectNodes(); +- throw clipperException("ProcessIntersections error"); ++ CLIPPER_THROW(clipperException("ProcessIntersections error")); + } + m_SortedEdges = 0; + return true; +@@ -3002,7 +3034,7 @@ void Clipper::DoMaxima(TEdge *e) + DeleteFromAEL(eMaxPair); + } + #endif +- else throw clipperException("DoMaxima error"); ++ else CLIPPER_THROW(clipperException("DoMaxima error")); + } + //------------------------------------------------------------------------------ + diff --git a/thirdparty/misc/clipper.cpp b/thirdparty/misc/clipper.cpp index d3143fe5ab..c67045d113 100644 --- a/thirdparty/misc/clipper.cpp +++ b/thirdparty/misc/clipper.cpp @@ -48,6 +48,38 @@ #include <ostream> #include <functional> +//Explicitly disables exceptions handling for target platform +//#define CLIPPER_NOEXCEPTION + +#define CLIPPER_THROW(exception) std::abort() +#define CLIPPER_TRY if(true) +#define CLIPPER_CATCH(exception) if(false) + +#if defined(__cpp_exceptions) || defined(__EXCEPTIONS) || defined(_CPPUNWIND) + #ifndef CLIPPER_NOEXCEPTION + #undef CLIPPER_THROW + #define CLIPPER_THROW(exception) throw exception + #undef CLIPPER_TRY + #define CLIPPER_TRY try + #undef CLIPPER_CATCH + #define CLIPPER_CATCH(exception) catch(exception) + #endif +#endif + +//Optionally allows to override exception macros +#if defined(CLIPPER_THROW_USER) + #undef CLIPPER_THROW + #define CLIPPER_THROW CLIPPER_THROW_USER +#endif +#if defined(CLIPPER_TRY_USER) + #undef CLIPPER_TRY + #define CLIPPER_TRY CLIPPER_TRY_USER +#endif +#if defined(CLIPPER_CATCH_USER) + #undef CLIPPER_CATCH + #define CLIPPER_CATCH CLIPPER_CATCH_USER +#endif + namespace ClipperLib { static double const pi = 3.141592653589793238; @@ -898,7 +930,7 @@ void RangeTest(const IntPoint& Pt, bool& useFullRange) if (useFullRange) { if (Pt.X > hiRange || Pt.Y > hiRange || -Pt.X > hiRange || -Pt.Y > hiRange) - throw clipperException("Coordinate outside allowed range"); + CLIPPER_THROW(clipperException("Coordinate outside allowed range")); } else if (Pt.X > loRange|| Pt.Y > loRange || -Pt.X > loRange || -Pt.Y > loRange) { @@ -1046,10 +1078,10 @@ bool ClipperBase::AddPath(const Path &pg, PolyType PolyTyp, bool Closed) { #ifdef use_lines if (!Closed && PolyTyp == ptClip) - throw clipperException("AddPath: Open paths must be subject."); + CLIPPER_THROW(clipperException("AddPath: Open paths must be subject.")); #else if (!Closed) - throw clipperException("AddPath: Open paths have been disabled."); + CLIPPER_THROW(clipperException("AddPath: Open paths have been disabled.")); #endif int highI = (int)pg.size() -1; @@ -1062,7 +1094,7 @@ bool ClipperBase::AddPath(const Path &pg, PolyType PolyTyp, bool Closed) bool IsFlat = true; //1. Basic (first) edge initialization ... - try + CLIPPER_TRY { edges[1].Curr = pg[1]; RangeTest(pg[0], m_UseFullRange); @@ -1075,10 +1107,10 @@ bool ClipperBase::AddPath(const Path &pg, PolyType PolyTyp, bool Closed) InitEdge(&edges[i], &edges[i+1], &edges[i-1], pg[i]); } } - catch(...) + CLIPPER_CATCH(...) { delete [] edges; - throw; //range test fails + CLIPPER_THROW(); //range test fails } TEdge *eStart = &edges[0]; @@ -1442,7 +1474,7 @@ void ClipperBase::SwapPositionsInAEL(TEdge *Edge1, TEdge *Edge2) void ClipperBase::UpdateEdgeIntoAEL(TEdge *&e) { if (!e->NextInLML) - throw clipperException("UpdateEdgeIntoAEL: invalid call"); + CLIPPER_THROW(clipperException("UpdateEdgeIntoAEL: invalid call")); e->NextInLML->OutIdx = e->OutIdx; TEdge* AelPrev = e->PrevInAEL; @@ -1510,7 +1542,7 @@ bool Clipper::Execute(ClipType clipType, Paths &solution, { if( m_ExecuteLocked ) return false; if (m_HasOpenPaths) - throw clipperException("Error: PolyTree struct is needed for open path clipping."); + CLIPPER_THROW(clipperException("Error: PolyTree struct is needed for open path clipping.")); m_ExecuteLocked = true; solution.resize(0); m_SubjFillType = subjFillType; @@ -1560,7 +1592,7 @@ void Clipper::FixHoleLinkage(OutRec &outrec) bool Clipper::ExecuteInternal() { bool succeeded = true; - try { + CLIPPER_TRY { Reset(); m_Maxima = MaximaList(); m_SortedEdges = 0; @@ -1583,7 +1615,7 @@ bool Clipper::ExecuteInternal() InsertLocalMinimaIntoAEL(botY); } } - catch(...) + CLIPPER_CATCH(...) { succeeded = false; } @@ -2827,18 +2859,18 @@ void Clipper::ProcessHorizontal(TEdge *horzEdge) bool Clipper::ProcessIntersections(const cInt topY) { if( !m_ActiveEdges ) return true; - try { + CLIPPER_TRY { BuildIntersectList(topY); size_t IlSize = m_IntersectList.size(); if (IlSize == 0) return true; if (IlSize == 1 || FixupIntersectionOrder()) ProcessIntersectList(); else return false; } - catch(...) + CLIPPER_CATCH(...) { m_SortedEdges = 0; DisposeIntersectNodes(); - throw clipperException("ProcessIntersections error"); + CLIPPER_THROW(clipperException("ProcessIntersections error")); } m_SortedEdges = 0; return true; @@ -3002,7 +3034,7 @@ void Clipper::DoMaxima(TEdge *e) DeleteFromAEL(eMaxPair); } #endif - else throw clipperException("DoMaxima error"); + else CLIPPER_THROW(clipperException("DoMaxima error")); } //------------------------------------------------------------------------------ @@ -4329,10 +4361,10 @@ double DistanceFromLineSqrd( const IntPoint& pt, const IntPoint& ln1, const IntPoint& ln2) { //The equation of a line in general form (Ax + By + C = 0) - //given 2 points (x¹,y¹) & (x²,y²) is ... - //(y¹ - y²)x + (x² - x¹)y + (y² - y¹)x¹ - (x² - x¹)y¹ = 0 - //A = (y¹ - y²); B = (x² - x¹); C = (y² - y¹)x¹ - (x² - x¹)y¹ - //perpendicular distance of point (x³,y³) = (Ax³ + By³ + C)/Sqrt(A² + B²) + //given 2 points (x¹,y¹) & (x²,y²) is ... + //(y¹ - y²)x + (x² - x¹)y + (y² - y¹)x¹ - (x² - x¹)y¹ = 0 + //A = (y¹ - y²); B = (x² - x¹); C = (y² - y¹)x¹ - (x² - x¹)y¹ + //perpendicular distance of point (x³,y³) = (Ax³ + By³ + C)/Sqrt(A² + B²) //see http://en.wikipedia.org/wiki/Perpendicular_distance double A = double(ln1.Y - ln2.Y); double B = double(ln2.X - ln1.X); diff --git a/thirdparty/xatlas/xatlas.cpp b/thirdparty/xatlas/xatlas.cpp index eb0824a517..2cc2905eee 100644 --- a/thirdparty/xatlas/xatlas.cpp +++ b/thirdparty/xatlas/xatlas.cpp @@ -4388,7 +4388,7 @@ private: class Solver { public: - // Solve the symmetric system: At·A·x = At·b + // Solve the symmetric system: At·A·x = At·b static bool LeastSquaresSolver(const sparse::Matrix &A, const FullVector &b, FullVector &x, float epsilon = 1e-5f) { xaDebugAssert(A.width() == x.dimension()); @@ -4477,22 +4477,22 @@ private: * Gradient method. * * Solving sparse linear systems: - * (1) A·x = b + * (1) A·x = b * * The conjugate gradient algorithm solves (1) only in the case that A is * symmetric and positive definite. It is based on the idea of minimizing the * function * - * (2) f(x) = 1/2·x·A·x - b·x + * (2) f(x) = 1/2·x·A·x - b·x * * This function is minimized when its gradient * - * (3) df = A·x - b + * (3) df = A·x - b * * is zero, which is equivalent to (1). The minimization is carried out by * generating a succession of search directions p.k and improved minimizers x.k. - * At each stage a quantity alfa.k is found that minimizes f(x.k + alfa.k·p.k), - * and x.k+1 is set equal to the new point x.k + alfa.k·p.k. The p.k and x.k are + * At each stage a quantity alfa.k is found that minimizes f(x.k + alfa.k·p.k), + * and x.k+1 is set equal to the new point x.k + alfa.k·p.k. The p.k and x.k are * built up in such a way that x.k+1 is also the minimizer of f over the whole * vector space of directions already taken, {p.1, p.2, . . . , p.k}. After N * iterations you arrive at the minimizer over the entire vector space, i.e., the @@ -4520,7 +4520,7 @@ private: float delta_new; float alpha; float beta; - // r = b - A·x; + // r = b - A·x; sparse::copy(b, r); sparse::sgemv(-1, A, x, 1, r); // p = r; @@ -4529,24 +4529,24 @@ private: delta_0 = delta_new; while (i < i_max && delta_new > epsilon * epsilon * delta_0) { i++; - // q = A·p + // q = A·p mult(A, p, q); - // alpha = delta_new / p·q + // alpha = delta_new / p·q alpha = delta_new / sparse::dot( p, q ); - // x = alfa·p + x + // x = alfa·p + x sparse::saxpy(alpha, p, x); if ((i & 31) == 0) { // recompute r after 32 steps - // r = b - A·x + // r = b - A·x sparse::copy(b, r); sparse::sgemv(-1, A, x, 1, r); } else { - // r = r - alpha·q + // r = r - alpha·q sparse::saxpy(-alpha, q, r); } delta_old = delta_new; delta_new = sparse::dot( r, r ); beta = delta_new / delta_old; - // p = beta·p + r + // p = beta·p + r sparse::scal(beta, p); sparse::saxpy(1, r, p); } @@ -4572,35 +4572,35 @@ private: float delta_new; float alpha; float beta; - // r = b - A·x + // r = b - A·x sparse::copy(b, r); sparse::sgemv(-1, A, x, 1, r); - // p = M^-1 · r + // p = M^-1 · r preconditioner.apply(r, p); delta_new = sparse::dot(r, p); delta_0 = delta_new; while (i < i_max && delta_new > epsilon * epsilon * delta_0) { i++; - // q = A·p + // q = A·p mult(A, p, q); - // alpha = delta_new / p·q + // alpha = delta_new / p·q alpha = delta_new / sparse::dot(p, q); - // x = alfa·p + x + // x = alfa·p + x sparse::saxpy(alpha, p, x); if ((i & 31) == 0) { // recompute r after 32 steps - // r = b - A·x + // r = b - A·x sparse::copy(b, r); sparse::sgemv(-1, A, x, 1, r); } else { - // r = r - alfa·q + // r = r - alfa·q sparse::saxpy(-alpha, q, r); } - // s = M^-1 · r + // s = M^-1 · r preconditioner.apply(r, s); delta_old = delta_new; delta_new = sparse::dot( r, s ); beta = delta_new / delta_old; - // p = s + beta·p + // p = s + beta·p sparse::scal(beta, p); sparse::saxpy(1, s, p); } |