diff options
author | nyamatongwe <unknown> | 2000-04-06 08:43:00 +0000 |
---|---|---|
committer | nyamatongwe <unknown> | 2000-04-06 08:43:00 +0000 |
commit | f129e6862882879aed3c8338243dbb43c17721ed (patch) | |
tree | 1352720978356ddc213962ccf1dc248c3b061491 /src | |
parent | dae4eea6225cd2f3ed9f2e4dfe46606cc9a0743f (diff) | |
download | scintilla-mirror-f129e6862882879aed3c8338243dbb43c17721ed.tar.gz |
Initial Unicode support code.
Diffstat (limited to 'src')
-rw-r--r-- | src/Document.cxx | 119 | ||||
-rw-r--r-- | src/Document.h | 2 | ||||
-rw-r--r-- | src/DocumentAccessor.cxx | 7 | ||||
-rw-r--r-- | src/Editor.cxx | 6 | ||||
-rw-r--r-- | src/LexPython.cxx | 2 | ||||
-rw-r--r-- | src/WindowAccessor.cxx | 7 |
6 files changed, 100 insertions, 43 deletions
diff --git a/src/Document.cxx b/src/Document.cxx index 7a30d7fd1..650c0ced2 100644 --- a/src/Document.cxx +++ b/src/Document.cxx @@ -202,18 +202,23 @@ bool Document::IsCrLf(int pos) { bool Document::IsDBCS(int pos) { #if PLAT_WIN if (dbcsCodePage) { - // Anchor DBCS calculations at start of line because start of line can - // not be a DBCS trail byte. - int startLine = pos; - while (startLine > 0 && cb.CharAt(startLine) != '\r' && cb.CharAt(startLine) != '\n') - startLine--; - while (startLine <= pos) { - if (IsDBCSLeadByteEx(dbcsCodePage, cb.CharAt(startLine))) { + if (SC_CP_UTF8 == dbcsCodePage) { + unsigned char ch = static_cast<unsigned char>(cb.CharAt(pos)); + return ch >= 0x80; + } else { + // Anchor DBCS calculations at start of line because start of line can + // not be a DBCS trail byte. + int startLine = pos; + while (startLine > 0 && cb.CharAt(startLine) != '\r' && cb.CharAt(startLine) != '\n') + startLine--; + while (startLine <= pos) { + if (IsDBCSLeadByteEx(dbcsCodePage, cb.CharAt(startLine))) { + startLine++; + if (startLine >= pos) + return true; + } startLine++; - if (startLine >= pos) - return true; } - startLine++; } } return false; @@ -222,6 +227,28 @@ bool Document::IsDBCS(int pos) { #endif } +int Document::LenChar(int pos) { + if (IsCrLf(pos)) { + return 2; + } else if (SC_CP_UTF8 == dbcsCodePage) { + unsigned char ch = static_cast<unsigned char>(cb.CharAt(pos)); + if (ch < 0x80) + return 1; + int len = 2; + if (ch >= (0x80+0x40+0x20)) + len = 3; + int lengthDoc = Length(); + if ((pos + len) > lengthDoc) + return lengthDoc-pos; + else + return len; + } else if (IsDBCS(pos)) { + return 2; + } else { + return 1; + } +} + // Normalise a position so that it is not halfway through a two byte character. // This can occur in two situations - // When lines are terminated with \r\n pairs which should be treated as one character. @@ -253,29 +280,41 @@ int Document::MovePositionOutsideChar(int pos, int moveDir, bool checkLineEnd) { #if PLAT_WIN if (dbcsCodePage) { - // Anchor DBCS calculations at start of line because start of line can - // not be a DBCS trail byte. - int startLine = pos; - while (startLine > 0 && cb.CharAt(startLine) != '\r' && cb.CharAt(startLine) != '\n') - startLine--; - bool atLeadByte = false; - while (startLine < pos) { - if (atLeadByte) - atLeadByte = false; - else if (IsDBCSLeadByteEx(dbcsCodePage, cb.CharAt(startLine))) - atLeadByte = true; - else - atLeadByte = false; - startLine++; - //Platform::DebugPrintf("DBCS %s\n", atlead ? "D" : "-"); - } + if (SC_CP_UTF8 == dbcsCodePage) { + unsigned char ch = static_cast<unsigned char>(cb.CharAt(pos)); + while ((pos > 0) && (pos < Length()) && (ch >= 0x80) && (ch < (0x80 + 0x40))) { + // ch is a trail byte + if (moveDir > 0) + pos++; + else + pos--; + ch = static_cast<unsigned char>(cb.CharAt(pos)); + } + } else { + // Anchor DBCS calculations at start of line because start of line can + // not be a DBCS trail byte. + int startLine = pos; + while (startLine > 0 && cb.CharAt(startLine) != '\r' && cb.CharAt(startLine) != '\n') + startLine--; + bool atLeadByte = false; + while (startLine < pos) { + if (atLeadByte) + atLeadByte = false; + else if (IsDBCSLeadByteEx(dbcsCodePage, cb.CharAt(startLine))) + atLeadByte = true; + else + atLeadByte = false; + startLine++; + //Platform::DebugPrintf("DBCS %s\n", atlead ? "D" : "-"); + } - if (atLeadByte) { - // Position is between a lead byte and a trail byte - if (moveDir > 0) - return pos + 1; - else - return pos - 1; + if (atLeadByte) { + // Position is between a lead byte and a trail byte + if (moveDir > 0) + return pos + 1; + else + return pos - 1; + } } } #endif @@ -440,13 +479,7 @@ void Document::ChangeChar(int pos, char ch) { } void Document::DelChar(int pos) { - if (IsCrLf(pos)) { - DeleteChars(pos, 2); - } else if (IsDBCS(pos)) { - DeleteChars(pos, 2); - } else if (pos < Length()) { - DeleteChars(pos, 1); - } + DeleteChars(pos, LenChar(pos)); } int Document::DelCharBack(int pos) { @@ -455,6 +488,10 @@ int Document::DelCharBack(int pos) { } else if (IsCrLf(pos - 2)) { DeleteChars(pos - 2, 2); return pos - 2; + } else if (SC_CP_UTF8 == dbcsCodePage) { + int startChar = MovePositionOutsideChar(pos-1, -1, false); + DeleteChars(startChar, pos - startChar); + return startChar; } else if (IsDBCS(pos - 1)) { DeleteChars(pos - 2, 2); return pos - 2; @@ -529,6 +566,8 @@ void Document::ConvertLineEnds(int eolModeSet) { } bool Document::IsWordChar(unsigned char ch) { + if ((SC_CP_UTF8 == dbcsCodePage) && (ch >0x80)) + return true; return wordchars[ch]; } @@ -653,7 +692,7 @@ void Document::ChangeCase(Range r, bool makeUpperCase) { for (int pos=r.start; pos<r.end; pos++) { char ch = CharAt(pos); if (dbcsCodePage && IsDBCS(pos)) { - pos++; + pos += LenChar(pos); } else { if (makeUpperCase) { if (islower(ch)) { diff --git a/src/Document.h b/src/Document.h index 7ab187573..ae25d69f4 100644 --- a/src/Document.h +++ b/src/Document.h @@ -87,6 +87,7 @@ public: int stylingBitsMask; int eolMode; + // dbcsCodePage can also be SC_CP_UTF8 to enable UTF-8 mode int dbcsCodePage; int tabInChars; @@ -99,6 +100,7 @@ public: int LineFromPosition(int pos); int ClampPositionIntoDocument(int pos); bool IsCrLf(int pos); + int LenChar(int pos); int MovePositionOutsideChar(int pos, int moveDir, bool checkLineEnd=true); // Gateways to modifying document diff --git a/src/DocumentAccessor.cxx b/src/DocumentAccessor.cxx index dd156fa24..420a359d6 100644 --- a/src/DocumentAccessor.cxx +++ b/src/DocumentAccessor.cxx @@ -22,7 +22,12 @@ bool DocumentAccessor::InternalIsLeadByte(char ch) { // TODO: support DBCS under GTK+ return false; #elif PLAT_WIN - return IsDBCSLeadByteEx(codePage, ch); + if (SC_CP_UTF8 == codePage) + // For lexing, all characters >= 0x80 are treated the + // same so none is considered a lead byte. + return false; + else + return IsDBCSLeadByteEx(codePage, ch); #elif PLAT_WX return false; #endif diff --git a/src/Editor.cxx b/src/Editor.cxx index 1566ffa6e..111142d90 100644 --- a/src/Editor.cxx +++ b/src/Editor.cxx @@ -210,6 +210,7 @@ Point Editor::LocationFromPosition(unsigned int pos) { //Platform::DebugPrintf("line=%d\n", line); Surface surface; surface.Init(); + surface.SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage); Point pt; pt.y = (lineVisible - topLine) * vs.lineHeight; // + half a lineheight? unsigned int posLineStart = pdoc->LineStart(line); @@ -252,6 +253,7 @@ int Editor::PositionFromLocation(Point pt) { //Platform::DebugPrintf("Position of (%d,%d) line = %d top=%d\n", pt.x, pt.y, line, topLine); Surface surface; surface.Init(); + surface.SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage); unsigned int posLineStart = pdoc->LineStart(line); LineLayout ll; @@ -273,6 +275,7 @@ int Editor::PositionFromLineX(int line, int x) { //Platform::DebugPrintf("Position of (%d,%d) line = %d top=%d\n", pt.x, pt.y, line, topLine); Surface surface; surface.Init(); + surface.SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage); unsigned int posLineStart = pdoc->LineStart(line); LineLayout ll; @@ -1024,6 +1027,7 @@ void Editor::Paint(Surface *surfaceWindow, PRectangle rcArea) { } else { surface = surfaceWindow; } + surface->SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage); int visibleLine = topLine + screenLinePaintFirst; int line = cs.DocFromDisplay(visibleLine); @@ -1164,8 +1168,10 @@ long Editor::FormatRange(bool draw, FORMATRANGE *pfr) { Surface *surface = new Surface(); surface->Init(pfr->hdc); + surface->SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage); Surface *surfaceMeasure = new Surface(); surfaceMeasure->Init(pfr->hdcTarget); + surfaceMeasure->SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage); ViewStyle vsPrint(vs); diff --git a/src/LexPython.cxx b/src/LexPython.cxx index 86597e863..1864412a6 100644 --- a/src/LexPython.cxx +++ b/src/LexPython.cxx @@ -71,9 +71,9 @@ static void ColourisePyDoc(unsigned int startPos, int length, int initStyle, for (int i = startPos; i <= lengthDoc; i++) { if (atStartLine) { - char chFlags; char chBad = static_cast<char>(64); char chGood = static_cast<char>(0); + char chFlags = chGood; if (whingeLevel == 1) { chFlags = (spaceFlags & wsInconsistent) ? chBad : chGood; } else if (whingeLevel == 2) { diff --git a/src/WindowAccessor.cxx b/src/WindowAccessor.cxx index d04c0142d..f0ad45914 100644 --- a/src/WindowAccessor.cxx +++ b/src/WindowAccessor.cxx @@ -19,7 +19,12 @@ bool WindowAccessor::InternalIsLeadByte(char ch) { // TODO: support DBCS under GTK+ return false; #elif PLAT_WIN - return IsDBCSLeadByteEx(codePage, ch); + if (SC_CP_UTF8 == codePage) + // For lexing, all characters >= 0x80 are treated the + // same so none is considered a lead byte. + return false; + else + return IsDBCSLeadByteEx(codePage, ch); #elif PLAT_WX return false; #endif |