From 445f48d0d974aa23563effc3fa719fcad739c0f0 Mon Sep 17 00:00:00 2001 From: Ladislav Zezula Date: Wed, 4 Dec 2024 10:54:48 +0100 Subject: Full support of printing UTF-8 characters to Windows console --- StormLib_test.vcxproj | 6 ++-- test/StormTest.cpp | 3 ++ test/TLogHelper.cpp | 72 ++++++++++++++++++++++++++++++++++++++++------ test/stormlib-test-001.txt | 13 +++++---- 4 files changed, 77 insertions(+), 17 deletions(-) diff --git a/StormLib_test.vcxproj b/StormLib_test.vcxproj index 71aebf9..e7703c4 100644 --- a/StormLib_test.vcxproj +++ b/StormLib_test.vcxproj @@ -23,7 +23,7 @@ {AA561A7B-26EA-49AF-90E8-C53C1FA2965D} StormLib_test Win32Proj - 10.0.17134.0 + 10.0 @@ -34,7 +34,7 @@ Application - v141_xp + v143 Unicode @@ -45,7 +45,7 @@ Application - v141_xp + v143 Unicode diff --git a/test/StormTest.cpp b/test/StormTest.cpp index 7a4459c..afc4ab8 100755 --- a/test/StormTest.cpp +++ b/test/StormTest.cpp @@ -4350,6 +4350,7 @@ static const LPCSTR Test_CreateMpq_Localized[] = #define TEST_REPLACE_FILE #define TEST_VERIFY_HASHES #define TEST_CREATE_MPQS +#define TEST_MISC_MPQS int _tmain(int argc, TCHAR * argv[]) { @@ -4485,6 +4486,7 @@ int _tmain(int argc, TCHAR * argv[]) } #endif +#ifdef TEST_MISC_MPQS // Test creating of an archive the same way like MPQ Editor does if(dwErrCode == ERROR_SUCCESS) dwErrCode = TestCreateArchive_TestGaps(_T("StormLibTest_GapsTest.mpq")); @@ -4532,6 +4534,7 @@ int _tmain(int argc, TCHAR * argv[]) // Open a MPQ (add custom user data to it) if(dwErrCode == ERROR_SUCCESS) dwErrCode = TestCreateArchive_BigArchive(_T("StormLibTest_BigArchive_v4.mpq")); +#endif // TEST_MISC_MPQS #ifdef _MSC_VER _CrtDumpMemoryLeaks(); diff --git a/test/TLogHelper.cpp b/test/TLogHelper.cpp index baa5327..6eb97f6 100644 --- a/test/TLogHelper.cpp +++ b/test/TLogHelper.cpp @@ -1,4 +1,4 @@ -/*****************************************************************************/ +/*****************************************************************************/ /* TLogHelper.cpp Copyright (c) Ladislav Zezula 2013 */ /*---------------------------------------------------------------------------*/ /* Helper class for reporting StormLib tests */ @@ -187,6 +187,11 @@ class TLogHelper TickCount = GetTickCount(); #endif +#ifdef STORMLIB_WINDOWS + SetConsoleOutputCP(CP_UTF8); // Set the UTF-8 code page to handle national-specific names + SetConsoleCP(CP_UTF8); +#endif + // Remember the startup time SetStartTime(); @@ -208,7 +213,7 @@ class TLogHelper if(nLength < sizeof(szMainTitleT)) szMainTitleT[nLength++] = 0; - printf("%s\n", szMainTitleT); + printf_console("%s\n", szMainTitleT); #endif #ifdef __STORMLIB_SELF__ @@ -218,11 +223,11 @@ class TLogHelper StringCopy(szMainTitleT, _countof(szMainTitleT), szMainTitle); if(szSubTitle1 != NULL && szSubTitle2 != NULL) - nPrevPrinted = _tprintf(_T("\rRunning %s (%s+%s) ..."), szMainTitleT, szSubTitle1, szSubTitle2); + nPrevPrinted = printf_console(_T("\rRunning %s (%s+%s) ..."), szMainTitleT, szSubTitle1, szSubTitle2); else if(szSubTitle1 != NULL) - nPrevPrinted = _tprintf(_T("\rRunning %s (%s) ..."), szMainTitleT, szSubTitle1); + nPrevPrinted = printf_console(_T("\rRunning %s (%s) ..."), szMainTitleT, szSubTitle1); else - nPrevPrinted = _tprintf(_T("\rRunning %s ..."), szMainTitleT); + nPrevPrinted = printf_console(_T("\rRunning %s ..."), szMainTitleT); #endif } } @@ -240,7 +245,7 @@ class TLogHelper #endif #ifdef __CASCLIB_SELF__ - printf("\n"); + printf_console("\n"); #endif } @@ -270,6 +275,57 @@ class TLogHelper // Printing functions // + int printf_console(const char * format, ...) + { + va_list argList; + va_start(argList, format); + int nLength = 0; + +#ifdef STORMLIB_WINDOWS + char * szBuffer; + int ccBuffer = 0x1000; + + if((szBuffer = new char[ccBuffer]) != NULL) + { + // Prepare the string + TestStrPrintfV(szBuffer, ccBuffer, format, argList); + nLength = (int)strlen(szBuffer); + + // Unlike wprintf, WriteConsole supports UTF-8 much better + WriteConsoleA(GetStdHandle(STD_OUTPUT_HANDLE), szBuffer, nLength, NULL, NULL); + delete[] szBuffer; + } +#else + nLength = vprintf(format, argList); +#endif + + return nLength; + } + +#ifdef STORMLIB_WINDOWS + int printf_console(const wchar_t * format, ...) + { + va_list argList; + va_start(argList, format); + int nLength = 0; + + wchar_t * szBuffer; + int ccBuffer = 0x1000; + + if((szBuffer = new wchar_t[ccBuffer]) != NULL) + { + // Prepare the string + TestStrPrintfV(szBuffer, ccBuffer, format, argList); + nLength = (int)wcslen(szBuffer); + + // Unlike wprintf, WriteConsole supports UTF-8 much better + WriteConsoleW(GetStdHandle(STD_OUTPUT_HANDLE), szBuffer, nLength, NULL, NULL); + delete[] szBuffer; + } + return nLength; + } +#endif + template DWORD PrintWithClreol(const XCHAR * szFormat, va_list argList, bool bPrintLastError, bool bPrintEndOfLine) { @@ -341,7 +397,7 @@ class TLogHelper } // Finally print the message - printf("%s", szBuffer); + printf_console("%s", szBuffer); nMessageCounter++; return dwErrCode; } @@ -431,7 +487,7 @@ class TLogHelper else { PrintProgress(" "); - printf("\r"); + printf_console("\r"); } } diff --git a/test/stormlib-test-001.txt b/test/stormlib-test-001.txt index 1225add..a1b2449 100644 --- a/test/stormlib-test-001.txt +++ b/test/stormlib-test-001.txt @@ -102,6 +102,7 @@ TestReadingMpq (MPx_2022_v1_Music.mpk) succeeded. TestReadingMpq (MPx_2022_v1_Scp.mpk) succeeded. TestReadingMpq (MPx_2022_v1_UI.mpk) succeeded. TestReadingMpq (MPQ_1998_v1_StarCraft.mpq) succeeded. +TestReadingMpq (MPQ_2005_v1_texture.MPQ) succeeded. TestReadingMpq (MPQ_2012_v4_OldWorld.MPQ) succeeded. TestReadingMpq (MPQ_2013_v4_world.MPQ) succeeded. TestReadingMpq (MPQ_2013_v4_locale-enGB.MPQ) succeeded. @@ -141,12 +142,12 @@ TestModifyMpq (MPQ_2023_v1_StarcraftMap.scm) succeeded. TestVerifyHash succeeded. CreateNewMpq (StormLibTest_EmptyMpq_v2.mpq) succeeded. CreateNewMpq (StormLibTest_EmptyMpq_v4.mpq) succeeded. -CreateNewMpq (StormLibTest_─îesk├Ż.mpq) succeeded. -CreateNewMpq (StormLibTest_đáĐâĐüĐüđ║đŞđ╣.mpq) succeeded. -CreateNewMpq (StormLibTest_╬Á╬╗╬╗╬Ě╬Ż╬╣╬║╬Č.mpq) succeeded. -CreateNewMpq (StormLibTest_ŠŚąŠťČŔ¬×.mpq) succeeded. -CreateNewMpq (StormLibTest_š«ÇńŻôńŞşŠľç.mpq) succeeded. -CreateNewMpq (StormLibTest_ěž┘äě╣ě╣ě▒ěĘ┘Őěę.mpq) succeeded. +CreateNewMpq (StormLibTest_Český.mpq) succeeded. . +CreateNewMpq (StormLibTest_Русский.mpq) succeeded. ... +CreateNewMpq (StormLibTest_ελληνικά.mpq) succeeded. +CreateNewMpq (StormLibTest_日本語.mpq) succeeded. .. +CreateNewMpq (StormLibTest_简体中文.mpq) succeeded.... +CreateNewMpq (StormLibTest_الععربية.mpq) succeeded.... CreateNewMpq (StormLibTest_NonStdNames.mpq) succeeded. CreateNewMpq (StormLibTest_MpqEditorTest.mpq) succeeded. TestCreateGaps (StormLibTest_GapsTest.mpq) succeeded. -- cgit v1.2.3