Browse Source

Make string::UTF16toUTF8 and UTF16toUTF8 Windows-only, and use

WideCharToMultiByte/MultiByteToWideChar instead of C++11.
tags/v2.0.0
Andrew Belt 4 years ago
parent
commit
8528dcc1d6
2 changed files with 43 additions and 17 deletions
  1. +8
    -3
      include/string.hpp
  2. +35
    -14
      src/string.cpp

+ 8
- 3
include/string.hpp View File

@@ -12,9 +12,6 @@ namespace rack {
namespace string { namespace string {




/** Performs a Unicode string conversion from UTF-16 to UTF-8. */
std::string UTF16toUTF8(const std::u16string& s);
std::u16string UTF8toUTF16(const std::string& s);
/** Converts a `printf()` format string and optional arguments into a std::string. /** Converts a `printf()` format string and optional arguments into a std::string.
Remember that "%s" must reference a `char *`, so use `.c_str()` for `std::string`s, otherwise you might get binary garbage. Remember that "%s" must reference a `char *`, so use `.c_str()` for `std::string`s, otherwise you might get binary garbage.
*/ */
@@ -89,5 +86,13 @@ struct CaseInsensitiveCompare {
}; };




#if defined ARCH_WIN
/** Performs a Unicode string conversion from UTF-16 to UTF-8.
These are only defined on Windows because the implementation uses Windows' API, and conversion is not needed on other OS's (since everything on Mac and Linux is UTF-8).
*/
std::string UTF16toUTF8(const std::u16string& s);
std::u16string UTF8toUTF16(const std::string& s);
#endif

} // namespace string } // namespace string
} // namespace rack } // namespace rack

+ 35
- 14
src/string.cpp View File

@@ -1,10 +1,12 @@
#include <locale> // for wstring_convert
#include <codecvt> // for codecvt_utf8_utf16
#include <cctype> // for tolower and toupper #include <cctype> // for tolower and toupper
#include <algorithm> // for transform #include <algorithm> // for transform
#include <libgen.h> // for dirname and basename #include <libgen.h> // for dirname and basename
#include <zlib.h> #include <zlib.h>


#if defined ARCH_WIN
#include <windows.h> // for MultiByteToWideChar
#endif

#include <string.hpp> #include <string.hpp>




@@ -12,18 +14,6 @@ namespace rack {
namespace string { namespace string {




std::string UTF16toUTF8(const std::u16string& s) {
std::wstring_convert<std::codecvt_utf8_utf16<char16_t>, char16_t> converter;
return converter.to_bytes(s);
}


std::u16string UTF8toUTF16(const std::string& s) {
std::wstring_convert<std::codecvt_utf8_utf16<char16_t>, char16_t> converter;
return converter.from_bytes(s);
}


std::string f(const char* format, ...) { std::string f(const char* format, ...) {
va_list args; va_list args;
va_start(args, format); va_start(args, format);
@@ -299,5 +289,36 @@ bool CaseInsensitiveCompare::operator()(const std::string& a, const std::string&
} }




#if defined ARCH_WIN
std::string UTF16toUTF8(const std::u16string& sU16) {
if (sU16.empty())
return "";
// Compute length of output buffer
int len = WideCharToMultiByte(CP_UTF8, 0, (wchar_t*) &sU16[0], sU16.size(), NULL, 0, NULL, NULL);
assert(len > 0);
std::string s;
// Allocate enough space for null character
s.resize(len);
len = WideCharToMultiByte(CP_UTF8, 0, (wchar_t*) &sU16[0], sU16.size(), &s[0], len, 0, 0);
assert(len > 0);
return s;
}


std::u16string UTF8toUTF16(const std::string& s) {
if (s.empty())
return u"";
// Compute length of output buffer
int len = MultiByteToWideChar(CP_UTF8, 0, &s[0], s.size(), NULL, 0);
assert(len > 0);
std::u16string sU16;
// Allocate enough space for null character
sU16.resize(len);
len = MultiByteToWideChar(CP_UTF8, 0, &s[0], s.size(), (wchar_t*) &sU16[0], len);
assert(len > 0);
return sU16;
}
#endif

} // namespace string } // namespace string
} // namespace rack } // namespace rack

Loading…
Cancel
Save