diff options
Diffstat (limited to 'modules/mono/utils')
-rw-r--r-- | modules/mono/utils/string_utils.cpp | 49 | ||||
-rw-r--r-- | modules/mono/utils/string_utils.h | 13 |
2 files changed, 62 insertions, 0 deletions
diff --git a/modules/mono/utils/string_utils.cpp b/modules/mono/utils/string_utils.cpp index c390f8b9c2..0ef66577fe 100644 --- a/modules/mono/utils/string_utils.cpp +++ b/modules/mono/utils/string_utils.cpp @@ -32,6 +32,8 @@ #include "core/os/file_access.h" +#include <stdio.h> + namespace { int sfind(const String &p_text, int p_from) { @@ -184,3 +186,50 @@ Error read_all_file_utf8(const String &p_path, String &r_content) { r_content = source; return OK; } + +// TODO: Move to variadic templates once we upgrade to C++11 + +String str_format(const char *p_format, ...) { + va_list list; + + va_start(list, p_format); + String res = str_format(p_format, list); + va_end(list); + + return res; +} +// va_copy was defined in the C99, but not in C++ standards before C++11. +// When you compile C++ without --std=c++<XX> option, compilers still define +// va_copy, otherwise you have to use the internal version (__va_copy). +#if !defined(va_copy) +#if defined(__GNUC__) +#define va_copy(d, s) __va_copy((d), (s)) +#else +#define va_copy(d, s) ((d) = (s)) +#endif +#endif + +#if defined(MINGW_ENABLED) || defined(_MSC_VER) +#define vsnprintf vsnprintf_s +#endif + +String str_format(const char *p_format, va_list p_list) { + va_list list; + + va_copy(list, p_list); + int len = vsnprintf(NULL, 0, p_format, list); + va_end(list); + + len += 1; // for the trailing '/0' + + char *buffer(memnew_arr(char, len)); + + va_copy(list, p_list); + vsnprintf(buffer, len, p_format, list); + va_end(list); + + String res(buffer); + memdelete_arr(buffer); + + return res; +} diff --git a/modules/mono/utils/string_utils.h b/modules/mono/utils/string_utils.h index 61765ccfd8..565b9bb644 100644 --- a/modules/mono/utils/string_utils.h +++ b/modules/mono/utils/string_utils.h @@ -34,6 +34,8 @@ #include "core/ustring.h" #include "core/variant.h" +#include <stdarg.h> + String sformat(const String &p_text, const Variant &p1 = Variant(), const Variant &p2 = Variant(), const Variant &p3 = Variant(), const Variant &p4 = Variant(), const Variant &p5 = Variant()); #ifdef TOOLS_ENABLED @@ -44,4 +46,15 @@ String escape_csharp_keyword(const String &p_name); Error read_all_file_utf8(const String &p_path, String &r_content); +#if defined(__GNUC__) +#define _PRINTF_FORMAT_ATTRIBUTE_1_0 __attribute__((format(printf, 1, 0))) +#define _PRINTF_FORMAT_ATTRIBUTE_1_2 __attribute__((format(printf, 1, 2))) +#else +#define _PRINTF_FORMAT_ATTRIBUTE_1_0 +#define _PRINTF_FORMAT_ATTRIBUTE_1_2 +#endif + +String str_format(const char *p_format, ...) _PRINTF_FORMAT_ATTRIBUTE_1_2; +String str_format(const char *p_format, va_list p_list) _PRINTF_FORMAT_ATTRIBUTE_1_0; + #endif // STRING_FORMAT_H |