Merge pull request #45158 from aaronfranke/cs-packedarray

Add C# array features from core PackedArrays
This commit is contained in:
Rémi Verschelde 2021-02-20 09:42:30 +01:00 committed by GitHub
commit ed8333f6bc
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 80 additions and 0 deletions

View File

@ -783,6 +783,72 @@ void BindingsGenerator::_generate_method_icalls(const TypeInterface &p_itype) {
}
}
void BindingsGenerator::_generate_array_extensions(StringBuilder &p_output) {
p_output.append("using System;\n\n");
p_output.append("namespace " BINDINGS_NAMESPACE "\n" OPEN_BLOCK);
// The class where we put the extensions doesn't matter, so just use "GD".
p_output.append(INDENT1 "public static partial class " BINDINGS_GLOBAL_SCOPE_CLASS "\n" INDENT1 "{");
#define ARRAY_IS_EMPTY(m_type) \
p_output.append("\n" INDENT2 "/// <summary>\n"); \
p_output.append(INDENT2 "/// Returns true if this " #m_type " array is empty or doesn't exist.\n"); \
p_output.append(INDENT2 "/// </summary>\n"); \
p_output.append(INDENT2 "/// <param name=\"instance\">The " #m_type " array check.</param>\n"); \
p_output.append(INDENT2 "/// <returns>Whether or not the array is empty.</returns>\n"); \
p_output.append(INDENT2 "public static bool IsEmpty(this " #m_type "[] instance)\n"); \
p_output.append(INDENT2 OPEN_BLOCK); \
p_output.append(INDENT3 "return instance == null || instance.Length == 0;\n"); \
p_output.append(INDENT2 CLOSE_BLOCK);
#define ARRAY_JOIN(m_type) \
p_output.append("\n" INDENT2 "/// <summary>\n"); \
p_output.append(INDENT2 "/// Converts this " #m_type " array to a string delimited by the given string.\n"); \
p_output.append(INDENT2 "/// </summary>\n"); \
p_output.append(INDENT2 "/// <param name=\"instance\">The " #m_type " array to convert.</param>\n"); \
p_output.append(INDENT2 "/// <param name=\"delimiter\">The delimiter to use between items.</param>\n"); \
p_output.append(INDENT2 "/// <returns>A single string with all items.</returns>\n"); \
p_output.append(INDENT2 "public static string Join(this " #m_type "[] instance, string delimiter = \", \")\n"); \
p_output.append(INDENT2 OPEN_BLOCK); \
p_output.append(INDENT3 "return String.Join(delimiter, instance);\n"); \
p_output.append(INDENT2 CLOSE_BLOCK);
#define ARRAY_STRINGIFY(m_type) \
p_output.append("\n" INDENT2 "/// <summary>\n"); \
p_output.append(INDENT2 "/// Converts this " #m_type " array to a string with brackets.\n"); \
p_output.append(INDENT2 "/// </summary>\n"); \
p_output.append(INDENT2 "/// <param name=\"instance\">The " #m_type " array to convert.</param>\n"); \
p_output.append(INDENT2 "/// <returns>A single string with all items.</returns>\n"); \
p_output.append(INDENT2 "public static string Stringify(this " #m_type "[] instance)\n"); \
p_output.append(INDENT2 OPEN_BLOCK); \
p_output.append(INDENT3 "return \"[\" + instance.Join() + \"]\";\n"); \
p_output.append(INDENT2 CLOSE_BLOCK);
#define ARRAY_ALL(m_type) \
ARRAY_IS_EMPTY(m_type) \
ARRAY_JOIN(m_type) \
ARRAY_STRINGIFY(m_type)
ARRAY_ALL(byte);
ARRAY_ALL(int);
ARRAY_ALL(long);
ARRAY_ALL(float);
ARRAY_ALL(double);
ARRAY_ALL(string);
ARRAY_ALL(Color);
ARRAY_ALL(Vector2);
ARRAY_ALL(Vector2i);
ARRAY_ALL(Vector3);
ARRAY_ALL(Vector3i);
#undef ARRAY_ALL
#undef ARRAY_IS_EMPTY
#undef ARRAY_JOIN
#undef ARRAY_STRINGIFY
p_output.append(INDENT1 CLOSE_BLOCK); // End of GD class.
p_output.append(CLOSE_BLOCK); // End of namespace.
}
void BindingsGenerator::_generate_global_constants(StringBuilder &p_output) {
// Constants (in partial GD class)
@ -926,6 +992,19 @@ Error BindingsGenerator::generate_cs_core_project(const String &p_proj_dir) {
compile_items.push_back(output_file);
}
// Generate source file for array extensions
{
StringBuilder extensions_source;
_generate_array_extensions(extensions_source);
String output_file = path::join(base_gen_dir, BINDINGS_GLOBAL_SCOPE_CLASS "_extensions.cs");
Error save_err = _save_file(output_file, extensions_source);
if (save_err != OK) {
return save_err;
}
compile_items.push_back(output_file);
}
for (OrderedHashMap<StringName, TypeInterface>::Element E = obj_types.front(); E; E = E.next()) {
const TypeInterface &itype = E.get();

View File

@ -661,6 +661,7 @@ class BindingsGenerator {
Error _generate_cs_method(const TypeInterface &p_itype, const MethodInterface &p_imethod, int &p_method_bind_count, StringBuilder &p_output);
Error _generate_cs_signal(const BindingsGenerator::TypeInterface &p_itype, const BindingsGenerator::SignalInterface &p_isignal, StringBuilder &p_output);
void _generate_array_extensions(StringBuilder &p_output);
void _generate_global_constants(StringBuilder &p_output);
Error _generate_glue_method(const TypeInterface &p_itype, const MethodInterface &p_imethod, StringBuilder &p_output);