From 727bd94560ca9056cdbe40fe2e7923ed008b6eac Mon Sep 17 00:00:00 2001 From: Albrecht Schlosser Date: Mon, 20 Nov 2023 20:12:02 +0100 Subject: Add commandline conversion for Windows (no-op on other platforms) - add Fl::args_to_utf8() to convert commandline arguments to UTF-8 This new function closes the gap that previously only Visual Studio applications converted their commandlines to UTF-8. Tested with MinGW, MSYS2/MinGW-w64, and Visual Studio (2019). --- src/drivers/WinAPI/Fl_WinAPI_System_Driver.H | 4 +++ src/drivers/WinAPI/Fl_WinAPI_System_Driver.cxx | 34 ++++++++++++++++++++++++++ 2 files changed, 38 insertions(+) (limited to 'src/drivers/WinAPI') diff --git a/src/drivers/WinAPI/Fl_WinAPI_System_Driver.H b/src/drivers/WinAPI/Fl_WinAPI_System_Driver.H index aae1017e2..016cad9fa 100644 --- a/src/drivers/WinAPI/Fl_WinAPI_System_Driver.H +++ b/src/drivers/WinAPI/Fl_WinAPI_System_Driver.H @@ -61,11 +61,15 @@ public: int mkdir(const char *fnam, int mode) FL_OVERRIDE; int rmdir(const char *fnam) FL_OVERRIDE; int rename(const char *fnam, const char *newnam) FL_OVERRIDE; + // Windows commandline argument conversion to UTF-8 + int args_to_utf8(int argc, char ** &argv) FL_OVERRIDE; + // Windows specific UTF-8 conversions unsigned utf8towc(const char *src, unsigned srclen, wchar_t* dst, unsigned dstlen) FL_OVERRIDE; unsigned utf8fromwc(char *dst, unsigned dstlen, const wchar_t* src, unsigned srclen) FL_OVERRIDE; int utf8locale() FL_OVERRIDE; unsigned utf8to_mb(const char *src, unsigned srclen, char *dst, unsigned dstlen) FL_OVERRIDE; unsigned utf8from_mb(char *dst, unsigned dstlen, const char *src, unsigned srclen) FL_OVERRIDE; + int clocale_vprintf(FILE *output, const char *format, va_list args) FL_OVERRIDE; int clocale_vsnprintf(char *output, size_t output_size, const char *format, va_list args) FL_OVERRIDE; int clocale_vsscanf(const char *input, const char *format, va_list args) FL_OVERRIDE; diff --git a/src/drivers/WinAPI/Fl_WinAPI_System_Driver.cxx b/src/drivers/WinAPI/Fl_WinAPI_System_Driver.cxx index faf89e979..d7b01465a 100644 --- a/src/drivers/WinAPI/Fl_WinAPI_System_Driver.cxx +++ b/src/drivers/WinAPI/Fl_WinAPI_System_Driver.cxx @@ -299,6 +299,40 @@ int Fl_WinAPI_System_Driver::rename(const char *fnam, const char *newnam) { return _wrename(wbuf, wbuf1); } +// See Fl::args_to_utf8() +int Fl_WinAPI_System_Driver::args_to_utf8(int argc, char ** &argv) { + int i; + char strbuf[2048]; // FIXME: allocate argv and strings dynamically + + // Convert the command line arguments to UTF-8 + LPWSTR *wideArgv = CommandLineToArgvW(GetCommandLineW(), &argc); + argv = (char **)malloc((argc + 1) * sizeof(char *)); + for (i = 0; i < argc; i++) { + int ret = WideCharToMultiByte(CP_UTF8, // CodePage + 0, // dwFlags + wideArgv[i], // lpWideCharStr + -1, // cchWideChar + strbuf, // lpMultiByteStr + sizeof(strbuf), // cbMultiByte + NULL, // lpDefaultChar + NULL); // lpUsedDefaultChar + + if (!ret) + strbuf[0] = '\0'; // return empty string + argv[i] = fl_strdup(strbuf); + } + argv[argc] = NULL; // required NULL pointer at end of list + + // Free the wide character string array + LocalFree(wideArgv); + + // Note: the allocated memory or argv[] will not be free'd by the system + // on exit. This does not constitute a memory leak. + + return argc; +} + + // Two Windows-specific functions fl_utf8_to_locale() and fl_locale_to_utf8() // from file fl_utf8.cxx are put here for API compatibility -- cgit v1.2.3