OSDN Git Service

Commit DialogBox compile Okay
[tortoisegit/TortoiseGitJp.git] / ext / scintilla / src / WindowAccessor.cxx
1 // Scintilla source code edit control\r
2 /** @file WindowAccessor.cxx\r
3  ** Rapid easy access to contents of a Scintilla.\r
4  **/\r
5 // Copyright 1998-2001 by Neil Hodgson <neilh@scintilla.org>\r
6 // The License.txt file describes the conditions under which this software may be distributed.\r
7 \r
8 #include <stdlib.h>\r
9 #include <string.h>\r
10 #include <ctype.h> \r
11 #include <stdio.h>\r
12 \r
13 #include "Platform.h"\r
14 \r
15 #include "PropSet.h"\r
16 #include "Accessor.h"\r
17 #include "WindowAccessor.h"\r
18 #include "Scintilla.h"\r
19 \r
20 #ifdef SCI_NAMESPACE\r
21 using namespace Scintilla;\r
22 #endif\r
23 \r
24 WindowAccessor::~WindowAccessor() {\r
25 }\r
26 \r
27 bool WindowAccessor::InternalIsLeadByte(char ch) {\r
28         if (SC_CP_UTF8 == codePage)\r
29                 // For lexing, all characters >= 0x80 are treated the\r
30                 // same so none is considered a lead byte.\r
31                 return false;   \r
32         else\r
33                 return Platform::IsDBCSLeadByte(codePage, ch);\r
34 }\r
35 \r
36 void WindowAccessor::Fill(int position) {\r
37         if (lenDoc == -1)\r
38                 lenDoc = Platform::SendScintilla(id, SCI_GETTEXTLENGTH, 0, 0);\r
39         startPos = position - slopSize;\r
40         if (startPos + bufferSize > lenDoc)\r
41                 startPos = lenDoc - bufferSize;\r
42         if (startPos < 0)\r
43                 startPos = 0;\r
44         endPos = startPos + bufferSize;\r
45         if (endPos > lenDoc)\r
46                 endPos = lenDoc;\r
47 \r
48         TextRange tr = {{startPos, endPos}, buf};\r
49         Platform::SendScintillaPointer(id, SCI_GETTEXTRANGE, 0, &tr);\r
50 }\r
51 \r
52 bool WindowAccessor::Match(int pos, const char *s) {\r
53         for (int i=0; *s; i++) {\r
54                 if (*s != SafeGetCharAt(pos+i))\r
55                         return false;\r
56                 s++;\r
57         }\r
58         return true;\r
59 }\r
60 \r
61 char WindowAccessor::StyleAt(int position) {\r
62         return static_cast<char>(Platform::SendScintilla(\r
63                 id, SCI_GETSTYLEAT, position, 0));\r
64 }\r
65 \r
66 int WindowAccessor::GetLine(int position) {\r
67         return Platform::SendScintilla(id, SCI_LINEFROMPOSITION, position, 0);\r
68 }\r
69 \r
70 int WindowAccessor::LineStart(int line) {\r
71         return Platform::SendScintilla(id, SCI_POSITIONFROMLINE, line, 0);\r
72 }\r
73 \r
74 int WindowAccessor::LevelAt(int line) {\r
75         return Platform::SendScintilla(id, SCI_GETFOLDLEVEL, line, 0);\r
76 }\r
77 \r
78 int WindowAccessor::Length() { \r
79         if (lenDoc == -1) \r
80                 lenDoc = Platform::SendScintilla(id, SCI_GETTEXTLENGTH, 0, 0);\r
81         return lenDoc; \r
82 }\r
83 \r
84 int WindowAccessor::GetLineState(int line) {\r
85         return Platform::SendScintilla(id, SCI_GETLINESTATE, line);\r
86 }\r
87 \r
88 int WindowAccessor::SetLineState(int line, int state) {\r
89         return Platform::SendScintilla(id, SCI_SETLINESTATE, line, state);\r
90 }\r
91 \r
92 void WindowAccessor::StartAt(unsigned int start, char chMask) {\r
93         Platform::SendScintilla(id, SCI_STARTSTYLING, start, chMask);\r
94 }\r
95 \r
96 void WindowAccessor::StartSegment(unsigned int pos) {\r
97         startSeg = pos;\r
98 }\r
99 \r
100 void WindowAccessor::ColourTo(unsigned int pos, int chAttr) {\r
101         // Only perform styling if non empty range\r
102         if (pos != startSeg - 1) {\r
103                 if (pos < startSeg) {\r
104                         Platform::DebugPrintf("Bad colour positions %d - %d\n", startSeg, pos);\r
105                 }\r
106 \r
107                 if (validLen + (pos - startSeg + 1) >= bufferSize)\r
108                         Flush();\r
109                 if (validLen + (pos - startSeg + 1) >= bufferSize) {\r
110                         // Too big for buffer so send directly\r
111                         Platform::SendScintilla(id, SCI_SETSTYLING, pos - startSeg + 1, chAttr);\r
112                 } else {\r
113                         if (chAttr != chWhile)\r
114                                 chFlags = 0;\r
115                         chAttr |= chFlags;\r
116                         for (unsigned int i = startSeg; i <= pos; i++) {\r
117                                 styleBuf[validLen++] = static_cast<char>(chAttr);\r
118                         }\r
119                 }\r
120         }\r
121         startSeg = pos+1;\r
122 }\r
123 \r
124 void WindowAccessor::SetLevel(int line, int level) {\r
125         Platform::SendScintilla(id, SCI_SETFOLDLEVEL, line, level);\r
126 }\r
127 \r
128 void WindowAccessor::Flush() {\r
129         startPos = extremePosition;\r
130         lenDoc = -1;\r
131         if (validLen > 0) {\r
132                 Platform::SendScintillaPointer(id, SCI_SETSTYLINGEX, validLen, \r
133                         styleBuf);\r
134                 validLen = 0;\r
135         }\r
136 }\r
137 \r
138 int WindowAccessor::IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader) {\r
139         int end = Length();\r
140         int spaceFlags = 0;\r
141         \r
142         // Determines the indentation level of the current line and also checks for consistent \r
143         // indentation compared to the previous line.\r
144         // Indentation is judged consistent when the indentation whitespace of each line lines \r
145         // the same or the indentation of one line is a prefix of the other.\r
146         \r
147         int pos = LineStart(line);\r
148         char ch = (*this)[pos];\r
149         int indent = 0;\r
150         bool inPrevPrefix = line > 0;\r
151         int posPrev = inPrevPrefix ? LineStart(line-1) : 0;\r
152         while ((ch == ' ' || ch == '\t') && (pos < end)) {\r
153                 if (inPrevPrefix) {\r
154                         char chPrev = (*this)[posPrev++];\r
155                         if (chPrev == ' ' || chPrev == '\t') {\r
156                                 if (chPrev != ch)\r
157                                         spaceFlags |= wsInconsistent;\r
158                         } else {\r
159                                 inPrevPrefix = false;\r
160                         }\r
161                 }\r
162                 if (ch == ' ') {\r
163                         spaceFlags |= wsSpace;\r
164                         indent++;\r
165                 } else {        // Tab\r
166                         spaceFlags |= wsTab;\r
167                         if (spaceFlags & wsSpace)\r
168                                 spaceFlags |= wsSpaceTab;\r
169                         indent = (indent / 8 + 1) * 8;\r
170                 }\r
171                 ch = (*this)[++pos];\r
172         }\r
173         \r
174         *flags = spaceFlags;\r
175         indent += SC_FOLDLEVELBASE;\r
176         // if completely empty line or the start of a comment...\r
177         if (isspace(ch) || (pfnIsCommentLeader && (*pfnIsCommentLeader)(*this, pos, end-pos)) )\r
178                 return indent | SC_FOLDLEVELWHITEFLAG;\r
179         else\r
180                 return indent;\r
181 }\r
182 \r
183 void WindowAccessor::IndicatorFill(int start, int end, int indicator, int value) {\r
184         Platform::SendScintilla(id, SCI_SETINDICATORCURRENT, indicator);\r
185         if (value) {\r
186                 Platform::SendScintilla(id, SCI_SETINDICATORVALUE, value);\r
187                 Platform::SendScintilla(id, SCI_INDICATORFILLRANGE, start, end - start);\r
188         } else {\r
189                 Platform::SendScintilla(id, SCI_INDICATORCLEARRANGE, start, end - start);\r
190         }\r
191 }\r