aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authornyamatongwe <unknown>2013-04-05 22:28:25 +1100
committernyamatongwe <unknown>2013-04-05 22:28:25 +1100
commit580fd5354d70de15db73dfb5d152ae01246db413 (patch)
tree0b9e9125b9c21083e9a1914db4b7d617a9725428
parent581cbf27b13df62778b592158bf343c4dbf99276 (diff)
downloadscintilla-mirror-580fd5354d70de15db73dfb5d152ae01246db413.tar.gz
Using character set for DirectWrite text so that Russian and similar
8-bit files display correctly.
-rw-r--r--win32/PlatWin.cxx46
-rw-r--r--win32/ScintillaWin.cxx43
2 files changed, 60 insertions, 29 deletions
diff --git a/win32/PlatWin.cxx b/win32/PlatWin.cxx
index aed9a8e8c..6f11c4ea0 100644
--- a/win32/PlatWin.cxx
+++ b/win32/PlatWin.cxx
@@ -81,6 +81,8 @@ static LONG_PTR GetWindowLongPtr(HWND hWnd, int nIndex) {
}
#endif
+extern UINT CodePageFromCharSet(DWORD characterSet, UINT documentCodePage);
+
// Declarations needed for functions dynamically loaded as not available on all Windows versions.
typedef BOOL (WINAPI *AlphaBlendSig)(HDC, int, int, int, int, HDC, int, int, int, int, BLENDFUNCTION);
typedef HMONITOR (WINAPI *MonitorFromPointSig)(POINT, DWORD);
@@ -164,19 +166,32 @@ struct FormatAndMetrics {
IDWriteTextFormat *pTextFormat;
#endif
int extraFontFlag;
+ int characterSet;
FLOAT yAscent;
FLOAT yDescent;
FLOAT yInternalLeading;
- FormatAndMetrics(HFONT hfont_, int extraFontFlag_) :
- technology(SCWIN_TECH_GDI), hfont(hfont_),
+ FormatAndMetrics(HFONT hfont_, int extraFontFlag_, int characterSet_) :
+ technology(SCWIN_TECH_GDI), hfont(hfont_),
#if defined(USE_D2D)
pTextFormat(0),
#endif
- extraFontFlag(extraFontFlag_), yAscent(2), yDescent(1), yInternalLeading(0) {
+ extraFontFlag(extraFontFlag_), characterSet(characterSet_), yAscent(2), yDescent(1), yInternalLeading(0) {
}
#if defined(USE_D2D)
- FormatAndMetrics(IDWriteTextFormat *pTextFormat_, int extraFontFlag_, FLOAT yAscent_, FLOAT yDescent_, FLOAT yInternalLeading_) :
- technology(SCWIN_TECH_DIRECTWRITE), hfont(0), pTextFormat(pTextFormat_), extraFontFlag(extraFontFlag_), yAscent(yAscent_), yDescent(yDescent_), yInternalLeading(yInternalLeading_) {
+ FormatAndMetrics(IDWriteTextFormat *pTextFormat_,
+ int extraFontFlag_,
+ int characterSet_,
+ FLOAT yAscent_,
+ FLOAT yDescent_,
+ FLOAT yInternalLeading_) :
+ technology(SCWIN_TECH_DIRECTWRITE),
+ hfont(0),
+ pTextFormat(pTextFormat_),
+ extraFontFlag(extraFontFlag_),
+ characterSet(characterSet_),
+ yAscent(yAscent_),
+ yDescent(yDescent_),
+ yInternalLeading(yInternalLeading_) {
}
#endif
~FormatAndMetrics() {
@@ -188,6 +203,7 @@ struct FormatAndMetrics {
pTextFormat = 0;
#endif
extraFontFlag = 0;
+ characterSet = 0;
yAscent = 2;
yDescent = 1;
yInternalLeading = 0;
@@ -315,7 +331,7 @@ FontCached::FontCached(const FontParameters &fp) :
fid = 0;
if (technology == SCWIN_TECH_GDI) {
HFONT hfont = ::CreateFontIndirectA(&lf);
- fid = reinterpret_cast<void *>(new FormatAndMetrics(hfont, fp.extraFontFlag));
+ fid = reinterpret_cast<void *>(new FormatAndMetrics(hfont, fp.extraFontFlag, fp.characterSet));
} else {
#if defined(USE_D2D)
IDWriteTextFormat *pTextFormat;
@@ -354,7 +370,7 @@ FontCached::FontCached(const FontParameters &fp) :
}
pTextLayout->Release();
}
- fid = reinterpret_cast<void *>(new FormatAndMetrics(pTextFormat, fp.extraFontFlag, yAscent, yDescent, yInternalLeading));
+ fid = reinterpret_cast<void *>(new FormatAndMetrics(pTextFormat, fp.extraFontFlag, fp.characterSet, yAscent, yDescent, yInternalLeading));
}
#endif
}
@@ -1140,6 +1156,7 @@ class SurfaceD2D : public Surface {
int x, y;
int codePage;
+ int codePageText;
ID2D1RenderTarget *pRenderTarget;
bool ownRenderTarget;
@@ -1222,6 +1239,7 @@ SurfaceD2D::SurfaceD2D() :
x(0), y(0) {
codePage = 0;
+ codePageText = 0;
pRenderTarget = NULL;
ownRenderTarget = false;
@@ -1335,6 +1353,10 @@ void SurfaceD2D::SetFont(Font &font_) {
yAscent = pfm->yAscent;
yDescent = pfm->yDescent;
yInternalLeading = pfm->yInternalLeading;
+ codePageText = codePage;
+ if (pfm->characterSet) {
+ codePageText = CodePageFromCharSet(pfm->characterSet, codePage);
+ }
if (pRenderTarget) {
pRenderTarget->SetTextAntialiasMode(DWriteMapFontQuality(pfm->extraFontFlag));
}
@@ -1582,7 +1604,7 @@ void SurfaceD2D::DrawTextCommon(PRectangle rc, Font &font_, XYPOSITION ybase, co
SetFont(font_);
// Use Unicode calls
- const TextWide tbuf(s, len, unicodeMode, codePage);
+ const TextWide tbuf(s, len, unicodeMode, codePageText);
if (pRenderTarget && pTextFormat && pBrush) {
if (fuOptions & ETO_CLIPPED) {
D2D1_RECT_F rcClip = {rc.left, rc.top, rc.right, rc.bottom};
@@ -1640,7 +1662,7 @@ void SurfaceD2D::DrawTextTransparent(PRectangle rc, Font &font_, XYPOSITION ybas
XYPOSITION SurfaceD2D::WidthText(Font &font_, const char *s, int len) {
FLOAT width = 1.0;
SetFont(font_);
- const TextWide tbuf(s, len, unicodeMode, codePage);
+ const TextWide tbuf(s, len, unicodeMode, codePageText);
if (pIDWriteFactory && pTextFormat) {
// Create a layout
IDWriteTextLayout *pTextLayout = 0;
@@ -1658,7 +1680,7 @@ XYPOSITION SurfaceD2D::WidthText(Font &font_, const char *s, int len) {
void SurfaceD2D::MeasureWidths(Font &font_, const char *s, int len, XYPOSITION *positions) {
SetFont(font_);
int fit = 0;
- const TextWide tbuf(s, len, unicodeMode, codePage);
+ const TextWide tbuf(s, len, unicodeMode, codePageText);
TextPositions poses(tbuf.tlen);
fit = tbuf.tlen;
const int clusters = 1000;
@@ -1712,7 +1734,7 @@ void SurfaceD2D::MeasureWidths(Font &font_, const char *s, int len, XYPOSITION *
while (i<len) {
positions[i++] = lastPos;
}
- } else if (codePage == 0) {
+ } else if (codePageText == 0) {
// One character per position
PLATFORM_ASSERT(len == tbuf.tlen);
@@ -1725,7 +1747,7 @@ void SurfaceD2D::MeasureWidths(Font &font_, const char *s, int len, XYPOSITION *
// May be more than one byte per position
int ui = 0;
for (int i=0;i<len;) {
- if (::IsDBCSLeadByteEx(codePage, s[i])) {
+ if (::IsDBCSLeadByteEx(codePageText, s[i])) {
positions[i] = poses.buffer[ui];
positions[i+1] = poses.buffer[ui];
i += 2;
diff --git a/win32/ScintillaWin.cxx b/win32/ScintillaWin.cxx
index 4fbeda992..3b5a73d8c 100644
--- a/win32/ScintillaWin.cxx
+++ b/win32/ScintillaWin.cxx
@@ -688,26 +688,35 @@ static unsigned int SciMessageFromEM(unsigned int iMessage) {
return iMessage;
}
-static UINT CodePageFromCharSet(DWORD characterSet, UINT documentCodePage) {
+UINT CodePageFromCharSet(DWORD characterSet, UINT documentCodePage) {
if (documentCodePage == SC_CP_UTF8) {
- // The system calls here are a little slow so avoid if known case.
return SC_CP_UTF8;
}
- CHARSETINFO ci = { 0, 0, { { 0, 0, 0, 0 }, { 0, 0 } } };
- BOOL bci = ::TranslateCharsetInfo(reinterpret_cast<DWORD*>(static_cast<uptr_t>(characterSet)),
- &ci, TCI_SRCCHARSET);
-
- UINT cp;
- if (bci)
- cp = ci.ciACP;
- else
- cp = documentCodePage;
-
- CPINFO cpi;
- if (!IsValidCodePage(cp) && !GetCPInfo(cp, &cpi))
- cp = CP_ACP;
-
- return cp;
+ switch (characterSet) {
+ case SC_CHARSET_ANSI: return 1252;
+ case SC_CHARSET_DEFAULT: return 0;
+ case SC_CHARSET_BALTIC: return 1257;
+ case SC_CHARSET_CHINESEBIG5: return 950;
+ case SC_CHARSET_EASTEUROPE: return 1250;
+ case SC_CHARSET_GB2312: return 936;
+ case SC_CHARSET_GREEK: return 1253;
+ case SC_CHARSET_HANGUL: return 949;
+ case SC_CHARSET_MAC: return 10000;
+ case SC_CHARSET_OEM: return 437;
+ case SC_CHARSET_RUSSIAN: return 1251;
+ case SC_CHARSET_SHIFTJIS: return 932;
+ case SC_CHARSET_TURKISH: return 1254;
+ case SC_CHARSET_JOHAB: return 1361;
+ case SC_CHARSET_HEBREW: return 1255;
+ case SC_CHARSET_ARABIC: return 1256;
+ case SC_CHARSET_VIETNAMESE: return 1258;
+ case SC_CHARSET_THAI: return 874;
+ case SC_CHARSET_8859_15: return 28605;
+ // Not supported
+ case SC_CHARSET_CYRILLIC: return documentCodePage;
+ case SC_CHARSET_SYMBOL: return documentCodePage;
+ }
+ return documentCodePage;
}
UINT ScintillaWin::CodePageOfDocument() {