summaryrefslogtreecommitdiff
path: root/modules/mono
diff options
context:
space:
mode:
Diffstat (limited to 'modules/mono')
-rw-r--r--modules/mono/csharp_script.cpp19
-rw-r--r--modules/mono/glue/GodotSharp/GodotSharp/Core/Callable.cs28
-rw-r--r--modules/mono/glue/callable_glue.cpp79
-rw-r--r--modules/mono/glue/glue_header.h2
-rw-r--r--modules/mono/utils/string_utils.cpp12
5 files changed, 130 insertions, 10 deletions
diff --git a/modules/mono/csharp_script.cpp b/modules/mono/csharp_script.cpp
index b85b65e6d9..6970349414 100644
--- a/modules/mono/csharp_script.cpp
+++ b/modules/mono/csharp_script.cpp
@@ -1813,8 +1813,9 @@ void CSharpInstance::get_event_signals_state_for_reloading(List<Pair<StringName,
}
void CSharpInstance::get_property_list(List<PropertyInfo> *p_properties) const {
+ List<PropertyInfo> props;
for (OrderedHashMap<StringName, PropertyInfo>::ConstElement E = script->member_info.front(); E; E = E.next()) {
- p_properties->push_front(E.value());
+ props.push_front(E.value());
}
// Call _get_property_list
@@ -1837,15 +1838,19 @@ void CSharpInstance::get_property_list(List<PropertyInfo> *p_properties) const {
if (ret) {
Array array = Array(GDMonoMarshal::mono_object_to_variant(ret));
for (int i = 0, size = array.size(); i < size; i++) {
- p_properties->push_back(PropertyInfo::from_dict(array.get(i)));
+ props.push_back(PropertyInfo::from_dict(array.get(i)));
}
}
- return;
+ break;
}
top = top->get_parent_class();
}
+
+ for (const PropertyInfo &prop : props) {
+ p_properties->push_back(prop);
+ }
}
Variant::Type CSharpInstance::get_property_type(const StringName &p_name, bool *r_is_valid) const {
@@ -3499,8 +3504,14 @@ Ref<Script> CSharpScript::get_base_script() const {
}
void CSharpScript::get_script_property_list(List<PropertyInfo> *r_list) const {
+ List<PropertyInfo> props;
+
for (OrderedHashMap<StringName, PropertyInfo>::ConstElement E = member_info.front(); E; E = E.next()) {
- r_list->push_front(E.value());
+ props.push_front(E.value());
+ }
+
+ for (const PropertyInfo &prop : props) {
+ r_list->push_back(prop);
}
}
diff --git a/modules/mono/glue/GodotSharp/GodotSharp/Core/Callable.cs b/modules/mono/glue/GodotSharp/GodotSharp/Core/Callable.cs
index a28a46896b..2722b64e6d 100644
--- a/modules/mono/glue/GodotSharp/GodotSharp/Core/Callable.cs
+++ b/modules/mono/glue/GodotSharp/GodotSharp/Core/Callable.cs
@@ -1,4 +1,5 @@
using System;
+using System.Runtime.CompilerServices;
namespace Godot
{
@@ -71,5 +72,32 @@ namespace Godot
_method = null;
_delegate = @delegate;
}
+
+ /// <summary>
+ /// Calls the method represented by this <see cref="Callable"/>.
+ /// Arguments can be passed and should match the method's signature.
+ /// </summary>
+ /// <param name="args">Arguments that will be passed to the method call.</param>
+ /// <returns>The value returned by the method.</returns>
+ public object Call(params object[] args)
+ {
+ return godot_icall_Callable_Call(ref this, args);
+ }
+
+ /// <summary>
+ /// Calls the method represented by this <see cref="Callable"/> in deferred mode, i.e. during the idle frame.
+ /// Arguments can be passed and should match the method's signature.
+ /// </summary>
+ /// <param name="args">Arguments that will be passed to the method call.</param>
+ public void CallDeferred(params object[] args)
+ {
+ godot_icall_Callable_CallDeferred(ref this, args);
+ }
+
+ [MethodImpl(MethodImplOptions.InternalCall)]
+ internal static extern object godot_icall_Callable_Call(ref Callable callable, object[] args);
+
+ [MethodImpl(MethodImplOptions.InternalCall)]
+ internal static extern void godot_icall_Callable_CallDeferred(ref Callable callable, object[] args);
}
}
diff --git a/modules/mono/glue/callable_glue.cpp b/modules/mono/glue/callable_glue.cpp
new file mode 100644
index 0000000000..54b65fdb94
--- /dev/null
+++ b/modules/mono/glue/callable_glue.cpp
@@ -0,0 +1,79 @@
+/*************************************************************************/
+/* callable_glue.cpp */
+/*************************************************************************/
+/* This file is part of: */
+/* GODOT ENGINE */
+/* https://godotengine.org */
+/*************************************************************************/
+/* Copyright (c) 2007-2021 Juan Linietsky, Ariel Manzur. */
+/* Copyright (c) 2014-2021 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 MONO_GLUE_ENABLED
+
+#include "../mono_gd/gd_mono_marshal.h"
+#include "arguments_vector.h"
+
+MonoObject *godot_icall_Callable_Call(GDMonoMarshal::M_Callable *p_callable, MonoArray *p_args) {
+ Callable callable = GDMonoMarshal::managed_to_callable(*p_callable);
+
+ int argc = mono_array_length(p_args);
+
+ ArgumentsVector<Variant> arg_store(argc);
+ ArgumentsVector<const Variant *> args(argc);
+
+ for (int i = 0; i < argc; i++) {
+ MonoObject *elem = mono_array_get(p_args, MonoObject *, i);
+ arg_store.set(i, GDMonoMarshal::mono_object_to_variant(elem));
+ args.set(i, &arg_store.get(i));
+ }
+
+ Variant result;
+ Callable::CallError error;
+ callable.call(args.ptr(), argc, result, error);
+
+ return GDMonoMarshal::variant_to_mono_object(result);
+}
+
+void godot_icall_Callable_CallDeferred(GDMonoMarshal::M_Callable *p_callable, MonoArray *p_args) {
+ Callable callable = GDMonoMarshal::managed_to_callable(*p_callable);
+
+ int argc = mono_array_length(p_args);
+
+ ArgumentsVector<Variant> arg_store(argc);
+ ArgumentsVector<const Variant *> args(argc);
+
+ for (int i = 0; i < argc; i++) {
+ MonoObject *elem = mono_array_get(p_args, MonoObject *, i);
+ arg_store.set(i, GDMonoMarshal::mono_object_to_variant(elem));
+ args.set(i, &arg_store.get(i));
+ }
+
+ callable.call_deferred(args.ptr(), argc);
+}
+
+void godot_register_callable_icalls() {
+ GDMonoUtils::add_internal_call("Godot.Callable::godot_icall_Callable_Call", godot_icall_Callable_Call);
+ GDMonoUtils::add_internal_call("Godot.Callable::godot_icall_Callable_CallDeferred", godot_icall_Callable_CallDeferred);
+}
+
+#endif // MONO_GLUE_ENABLED
diff --git a/modules/mono/glue/glue_header.h b/modules/mono/glue/glue_header.h
index eed3bd2167..074220bb9b 100644
--- a/modules/mono/glue/glue_header.h
+++ b/modules/mono/glue/glue_header.h
@@ -36,6 +36,7 @@ void godot_register_collections_icalls();
void godot_register_gd_icalls();
void godot_register_string_name_icalls();
void godot_register_nodepath_icalls();
+void godot_register_callable_icalls();
void godot_register_object_icalls();
void godot_register_rid_icalls();
void godot_register_string_icalls();
@@ -50,6 +51,7 @@ void godot_register_glue_header_icalls() {
godot_register_gd_icalls();
godot_register_string_name_icalls();
godot_register_nodepath_icalls();
+ godot_register_callable_icalls();
godot_register_object_icalls();
godot_register_rid_icalls();
godot_register_string_icalls();
diff --git a/modules/mono/utils/string_utils.cpp b/modules/mono/utils/string_utils.cpp
index 6fdb5079ce..74f5e6d18a 100644
--- a/modules/mono/utils/string_utils.cpp
+++ b/modules/mono/utils/string_utils.cpp
@@ -201,11 +201,11 @@ String str_format(const char *p_format, ...) {
}
#if defined(MINGW_ENABLED)
-#define gd_vsnprintf(m_buffer, m_count, m_format, m_args_copy) vsnprintf_s(m_buffer, m_count, _TRUNCATE, m_format, m_args_copy)
-#define gd_vscprintf(m_format, m_args_copy) _vscprintf(m_format, m_args_copy)
+#define RSnprintf(m_buffer, m_count, m_format, m_args_copy) vsnprintf_s(m_buffer, m_count, _TRUNCATE, m_format, m_args_copy)
+#define RScprintf(m_format, m_args_copy) _vscprintf(m_format, m_args_copy)
#else
-#define gd_vsnprintf(m_buffer, m_count, m_format, m_args_copy) vsnprintf(m_buffer, m_count, m_format, m_args_copy)
-#define gd_vscprintf(m_format, m_args_copy) vsnprintf(nullptr, 0, p_format, m_args_copy)
+#define RSnprintf(m_buffer, m_count, m_format, m_args_copy) vsnprintf(m_buffer, m_count, m_format, m_args_copy)
+#define RScprintf(m_format, m_args_copy) vsnprintf(nullptr, 0, p_format, m_args_copy)
#endif
String str_format(const char *p_format, va_list p_list) {
@@ -231,7 +231,7 @@ char *str_format_new(const char *p_format, va_list p_list) {
va_list list;
va_copy(list, p_list);
- int len = gd_vscprintf(p_format, list);
+ int len = RScprintf(p_format, list);
va_end(list);
len += 1; // for the trailing '/0'
@@ -239,7 +239,7 @@ char *str_format_new(const char *p_format, va_list p_list) {
char *buffer(memnew_arr(char, len));
va_copy(list, p_list);
- gd_vsnprintf(buffer, len, p_format, list);
+ RSnprintf(buffer, len, p_format, list);
va_end(list);
return buffer;