From 1a56869ac9e5a33a3a6011c5930b02b8b7853f08 Mon Sep 17 00:00:00 2001 From: nyamatongwe Date: Sat, 10 Dec 2005 10:08:14 +0000 Subject: Jeffrey Ren's patch to allow Asian languages to work on English Windows 9x. Modified to follow coding conventions and minimise duplicated code. --- win32/PlatWin.cxx | 110 ++++++++++++++++++++++++++++++++++-------------------- 1 file changed, 70 insertions(+), 40 deletions(-) (limited to 'win32') diff --git a/win32/PlatWin.cxx b/win32/PlatWin.cxx index a2862efb0..66bbd25f3 100644 --- a/win32/PlatWin.cxx +++ b/win32/PlatWin.cxx @@ -309,6 +309,10 @@ class SurfaceImpl : public Surface { int maxWidthMeasure; int maxLenText; + int codePage; + // If 9x OS and current code page is same as ANSI code page. + bool win9xACPSame; + void BrushColor(ColourAllocated back); void SetFont(Font &font_); @@ -338,6 +342,7 @@ public: void Ellipse(PRectangle rc, ColourAllocated fore, ColourAllocated back); void Copy(PRectangle rc, Point from, Surface &surfaceSource); + void DrawTextCommon(PRectangle rc, Font &font_, int ybase, const char *s, int len, UINT fuOptions); void DrawTextNoClip(PRectangle rc, Font &font_, int ybase, const char *s, int len, ColourAllocated fore, ColourAllocated back); void DrawTextClipped(PRectangle rc, Font &font_, int ybase, const char *s, int len, ColourAllocated fore, ColourAllocated back); void DrawTextTransparent(PRectangle rc, Font &font_, int ybase, const char *s, int len, ColourAllocated fore); @@ -356,7 +361,7 @@ public: void FlushCachedState(); void SetUnicodeMode(bool unicodeMode_); - void SetDBCSMode(int codePage); + void SetDBCSMode(int codePage_); }; SurfaceImpl::SurfaceImpl() : @@ -372,6 +377,9 @@ SurfaceImpl::SurfaceImpl() : // There appears to be a 16 bit string length limit in GDI on NT and a limit of // 8192 characters on Windows 95. maxLenText = IsNT() ? 65535 : 8192; + + codePage = 0; + win9xACPSame = false; } SurfaceImpl::~SurfaceImpl() { @@ -545,40 +553,41 @@ void SurfaceImpl::Copy(PRectangle rc, Point from, Surface &surfaceSource) { static_cast(surfaceSource).hdc, from.x, from.y, SRCCOPY); } -#define MAX_US_LEN 10000 +const int MAX_US_LEN = 10000; -void SurfaceImpl::DrawTextNoClip(PRectangle rc, Font &font_, int ybase, const char *s, int len, - ColourAllocated fore, ColourAllocated back) { +void SurfaceImpl::DrawTextCommon(PRectangle rc, Font &font_, int ybase, const char *s, int len, UINT fuOptions) { SetFont(font_); - ::SetTextColor(hdc, fore.AsLong()); - ::SetBkColor(hdc, back.AsLong()); RECT rcw = RectFromPRectangle(rc); if (unicodeMode) { wchar_t tbuf[MAX_US_LEN]; - int tlen = UCS2FromUTF8(s, len, tbuf, sizeof(tbuf)/sizeof(wchar_t)-1); - tbuf[tlen] = L'\0'; - ::ExtTextOutW(hdc, rc.left, ybase, ETO_OPAQUE, &rcw, tbuf, tlen, NULL); - } else { - ::ExtTextOut(hdc, rc.left, ybase, ETO_OPAQUE, &rcw, s, + int tlen = UCS2FromUTF8(s, len, tbuf, MAX_US_LEN); + ::ExtTextOutW(hdc, rc.left, ybase, fuOptions, &rcw, tbuf, tlen, NULL); + } else if (IsNT() || (codePage==0) || win9xACPSame) { + ::ExtTextOutA(hdc, rc.left, ybase, fuOptions, &rcw, s, Platform::Minimum(len, maxLenText), NULL); + } else { + // Support Asian string display in 9x English + wchar_t tbuf[MAX_US_LEN]; + int tlen = ::MultiByteToWideChar(codePage, 0, s, len, NULL, 0); + if (tlen > MAX_US_LEN) + tlen = MAX_US_LEN; + ::MultiByteToWideChar(codePage, 0, s, len, tbuf, tlen); + ::ExtTextOutW(hdc, rc.left, ybase, fuOptions, &rcw, tbuf, tlen, NULL); } } +void SurfaceImpl::DrawTextNoClip(PRectangle rc, Font &font_, int ybase, const char *s, int len, + ColourAllocated fore, ColourAllocated back) { + ::SetTextColor(hdc, fore.AsLong()); + ::SetBkColor(hdc, back.AsLong()); + DrawTextCommon(rc, font_, ybase, s, len, ETO_OPAQUE); +} + void SurfaceImpl::DrawTextClipped(PRectangle rc, Font &font_, int ybase, const char *s, int len, ColourAllocated fore, ColourAllocated back) { - SetFont(font_); ::SetTextColor(hdc, fore.AsLong()); ::SetBkColor(hdc, back.AsLong()); - RECT rcw = RectFromPRectangle(rc); - if (unicodeMode) { - wchar_t tbuf[MAX_US_LEN]; - int tlen = UCS2FromUTF8(s, len, tbuf, sizeof(tbuf)/sizeof(wchar_t)-1); - tbuf[tlen] = L'\0'; - ::ExtTextOutW(hdc, rc.left, ybase, ETO_OPAQUE | ETO_CLIPPED, &rcw, tbuf, tlen, NULL); - } else { - ::ExtTextOut(hdc, rc.left, ybase, ETO_OPAQUE | ETO_CLIPPED, &rcw, s, - Platform::Minimum(len, maxLenText), NULL); - } + DrawTextCommon(rc, font_, ybase, s, len, ETO_OPAQUE | ETO_CLIPPED); } void SurfaceImpl::DrawTextTransparent(PRectangle rc, Font &font_, int ybase, const char *s, int len, @@ -586,19 +595,9 @@ void SurfaceImpl::DrawTextTransparent(PRectangle rc, Font &font_, int ybase, con // Avoid drawing spaces in transparent mode for (int i=0;i