]> git.saurik.com Git - wxWidgets.git/blob - src/stc/scintilla/lexlib/StyleContext.h
Make wxOwnerDrawnComboBox::DoGetBestSize() twice as fast.
[wxWidgets.git] / src / stc / scintilla / lexlib / StyleContext.h
1 // Scintilla source code edit control
2 /** @file StyleContext.cxx
3 ** Lexer infrastructure.
4 **/
5 // Copyright 1998-2004 by Neil Hodgson <neilh@scintilla.org>
6 // This file is in the public domain.
7
8 #ifndef STYLECONTEXT_H
9 #define STYLECONTEXT_H
10
11 #ifdef SCI_NAMESPACE
12 namespace Scintilla {
13 #endif
14
15 static inline int MakeLowerCase(int ch) {
16 if (ch < 'A' || ch > 'Z')
17 return ch;
18 else
19 return ch - 'A' + 'a';
20 }
21
22 // All languages handled so far can treat all characters >= 0x80 as one class
23 // which just continues the current token or starts an identifier if in default.
24 // DBCS treated specially as the second character can be < 0x80 and hence
25 // syntactically significant. UTF-8 avoids this as all trail bytes are >= 0x80
26 class StyleContext {
27 LexAccessor &styler;
28 unsigned int endPos;
29 StyleContext &operator=(const StyleContext &);
30 void GetNextChar(unsigned int pos) {
31 chNext = static_cast<unsigned char>(styler.SafeGetCharAt(pos+1));
32 if (styler.IsLeadByte(static_cast<char>(chNext))) {
33 chNext = chNext << 8;
34 chNext |= static_cast<unsigned char>(styler.SafeGetCharAt(pos+2));
35 }
36 // End of line?
37 // Trigger on CR only (Mac style) or either on LF from CR+LF (Dos/Win)
38 // or on LF alone (Unix). Avoid triggering two times on Dos/Win.
39 atLineEnd = (ch == '\r' && chNext != '\n') ||
40 (ch == '\n') ||
41 (currentPos >= endPos);
42 }
43
44 public:
45 unsigned int currentPos;
46 bool atLineStart;
47 bool atLineEnd;
48 int state;
49 int chPrev;
50 int ch;
51 int chNext;
52
53 StyleContext(unsigned int startPos, unsigned int length,
54 int initStyle, LexAccessor &styler_, char chMask=31) :
55 styler(styler_),
56 endPos(startPos + length),
57 currentPos(startPos),
58 atLineEnd(false),
59 state(initStyle & chMask), // Mask off all bits which aren't in the chMask.
60 chPrev(0),
61 ch(0),
62 chNext(0) {
63 styler.StartAt(startPos, chMask);
64 styler.StartSegment(startPos);
65 atLineStart = static_cast<unsigned int>(styler.LineStart(styler.GetLine(startPos))) == startPos;
66 unsigned int pos = currentPos;
67 ch = static_cast<unsigned char>(styler.SafeGetCharAt(pos));
68 if (styler.IsLeadByte(static_cast<char>(ch))) {
69 pos++;
70 ch = ch << 8;
71 ch |= static_cast<unsigned char>(styler.SafeGetCharAt(pos));
72 }
73 GetNextChar(pos);
74 }
75 void Complete() {
76 styler.ColourTo(currentPos - 1, state);
77 styler.Flush();
78 }
79 bool More() const {
80 return currentPos < endPos;
81 }
82 void Forward() {
83 if (currentPos < endPos) {
84 atLineStart = atLineEnd;
85 chPrev = ch;
86 currentPos++;
87 if (ch >= 0x100)
88 currentPos++;
89 ch = chNext;
90 GetNextChar(currentPos + ((ch >= 0x100) ? 1 : 0));
91 } else {
92 atLineStart = false;
93 chPrev = ' ';
94 ch = ' ';
95 chNext = ' ';
96 atLineEnd = true;
97 }
98 }
99 void Forward(int nb) {
100 for (int i = 0; i < nb; i++) {
101 Forward();
102 }
103 }
104 void ChangeState(int state_) {
105 state = state_;
106 }
107 void SetState(int state_) {
108 styler.ColourTo(currentPos - 1, state);
109 state = state_;
110 }
111 void ForwardSetState(int state_) {
112 Forward();
113 styler.ColourTo(currentPos - 1, state);
114 state = state_;
115 }
116 int LengthCurrent() {
117 return currentPos - styler.GetStartSegment();
118 }
119 int GetRelative(int n) {
120 return static_cast<unsigned char>(styler.SafeGetCharAt(currentPos+n));
121 }
122 bool Match(char ch0) const {
123 return ch == static_cast<unsigned char>(ch0);
124 }
125 bool Match(char ch0, char ch1) const {
126 return (ch == static_cast<unsigned char>(ch0)) && (chNext == static_cast<unsigned char>(ch1));
127 }
128 bool Match(const char *s) {
129 if (ch != static_cast<unsigned char>(*s))
130 return false;
131 s++;
132 if (!*s)
133 return true;
134 if (chNext != static_cast<unsigned char>(*s))
135 return false;
136 s++;
137 for (int n=2; *s; n++) {
138 if (*s != styler.SafeGetCharAt(currentPos+n))
139 return false;
140 s++;
141 }
142 return true;
143 }
144 bool MatchIgnoreCase(const char *s) {
145 if (MakeLowerCase(ch) != static_cast<unsigned char>(*s))
146 return false;
147 s++;
148 if (MakeLowerCase(chNext) != static_cast<unsigned char>(*s))
149 return false;
150 s++;
151 for (int n=2; *s; n++) {
152 if (static_cast<unsigned char>(*s) !=
153 MakeLowerCase(static_cast<unsigned char>(styler.SafeGetCharAt(currentPos+n))))
154 return false;
155 s++;
156 }
157 return true;
158 }
159 // Non-inline
160 void GetCurrent(char *s, unsigned int len);
161 void GetCurrentLowered(char *s, unsigned int len);
162 };
163
164 #ifdef SCI_NAMESPACE
165 }
166 #endif
167
168 #endif