source: dev/trunk/ab5.0/abdev/abdev/Replace.cpp@ 681

Last change on this file since 681 was 681, checked in by dai_9181, 16 years ago

・TinyXMLをabdevプロジェクトで使えるようにした。
・コードハイライターを汎用的に実装しなおした。syntaxファイルを読み込む仕様とした。

File size: 11.3 KB
Line 
1#include "stdafx.h"
2
3#include "common.h"
4
5void TextEdit_ResetWordColor(int WndNum,CHARRANGE *pCharRange,int DocType){
6 extern HANDLE hHeap;
7 int i,i2,IsStr;
8 char *pBuf,*pTemp;
9 CHARRANGE Range,cr2;
10
11 pBuf=MdiInfo[WndNum]->pMdiTextEdit->buffer;
12
13 //行の先頭位置を取得
14 i=pCharRange->cpMin;
15 for(;i>0;i--){
16 if(pBuf[i-1]=='\r'&&pBuf[i]=='\n'){
17 i++;
18 break;
19 }
20 }
21 Range.cpMin=i;
22
23 //行の末端位置を取得
24 i=pCharRange->cpMax;
25 for(;;i++){
26 if(pBuf[i]=='\0') break;
27 if(pBuf[i]=='\r'&&pBuf[i+1]=='\n') break;
28 }
29 Range.cpMax=i;
30
31 //初期化(すべて黒色に戻す)
32 for(i=Range.cpMin;i<Range.cpMax;i++){
33 MdiInfo[WndNum]->pMdiTextEdit->pColorRef[i]=tci.rgbDefault;
34 }
35
36 if(DocType==WNDTYPE_TEXT) return;
37
38 pTemp=(char *)HeapAlloc(hHeap,0,Range.cpMax-Range.cpMin+1);
39
40 for(i=Range.cpMin,IsStr=0;i<Range.cpMax;i++){
41 if((IsVariableTopChar(pBuf[i])||pBuf[i]=='#')&&IsStr==0){
42 cr2.cpMin=i;
43 for(i2=0;;i++,i2++){
44 if((!IsVariableChar(pBuf[i]))||pBuf[i]=='.'){
45 pTemp[i2]=0;
46 break;
47 }
48 pTemp[i2]=pBuf[i];
49 }
50 cr2.cpMax=i;
51
52 //予約語(青色)
53 bool result = false;
54 if(DocType==WNDTYPE_BASIC)
55 {
56 result = ActiveBasic::IDE::Program::ablang->IsExistKeyword( pTemp );
57 }
58 else if(DocType==WNDTYPE_HTML) result=IsHtmlReservedWord(pTemp);
59
60 if(result){
61 for(i2=cr2.cpMin;i2<cr2.cpMax;i2++){
62 MdiInfo[WndNum]->pMdiTextEdit->pColorRef[i2]=tci.rgbStatement;
63 }
64 }
65 }
66 if(IsStr||ActiveBasic::IDE::Program::ablang->IsQuoteMark( pBuf[i] )&&IsStr==0){
67 //文字列カラー(""で囲まれる範囲)
68 MdiInfo[WndNum]->pMdiTextEdit->pColorRef[i]=tci.rgbString;
69 }
70 if(pBuf[i]=='\0') break;
71 if( ActiveBasic::IDE::Program::ablang->IsQuoteMark( pBuf[i] ) )
72 {
73 IsStr^=1;
74 }
75 if(pBuf[i]=='\r'&&pBuf[i+1]=='\n'){
76 i++;
77 IsStr=0;
78 }
79 }
80
81 HeapDefaultFree(pTemp);
82}
83
84void TextEdit_Replace(int WndNum,char *str,BOOL bRedraw){
85 extern HANDLE hHeap;
86 CHARRANGE Range,DelRange;
87
88 TextEdit_GetSel(WndNum,&DelRange);
89
90 Range.cpMin=DelRange.cpMin;
91 Range.cpMax=DelRange.cpMin+lstrlen(str);
92
93 //バッファ長を取得
94 int length;
95 length=lstrlen(MdiInfo[WndNum]->pMdiTextEdit->buffer);
96
97 int delta;
98 delta=DelRange.cpMin-DelRange.cpMax+(Range.cpMax-Range.cpMin);
99 if(0<delta){
100 ////////////////////
101 // バッファを再確保
102 ////////////////////
103
104 MdiInfo[WndNum]->pMdiTextEdit->buffer=(char *)HeapReAlloc(hHeap,
105 0,
106 MdiInfo[WndNum]->pMdiTextEdit->buffer,
107 length+1+delta);
108
109 MdiInfo[WndNum]->pMdiTextEdit->pColorRef=(COLORREF *)HeapReAlloc(hHeap,
110 0,
111 MdiInfo[WndNum]->pMdiTextEdit->pColorRef,
112 (length+1+delta)*sizeof(COLORREF));
113 }
114
115
116 //ブレークポイントのオフセット分を計算
117 if( projectInfo.IsOpened() ){
118 projectInfo.pobj_DBBreakPoint->replace(
119 MdiInfo[WndNum]->path.c_str(),
120 MdiInfo[WndNum]->pMdiTextEdit->buffer,
121 &DelRange,
122 &Range,
123 str);
124 }
125 else{
126 extern CDBBreakPoint *pobj_DBBreakPoint;
127 pobj_DBBreakPoint->replace(
128 MdiInfo[WndNum]->path.c_str(),
129 MdiInfo[WndNum]->pMdiTextEdit->buffer,
130 &DelRange,
131 &Range,
132 str);
133 }
134
135
136 //文字列バッファをスライドして、挿入
137 SlideString(MdiInfo[WndNum]->pMdiTextEdit->buffer+DelRange.cpMax,
138 delta);
139 memcpy(MdiInfo[WndNum]->pMdiTextEdit->buffer+Range.cpMin,str,lstrlen(str));
140
141 //文字カラーバッファをスライド
142 SlideBuffer(((char *)MdiInfo[WndNum]->pMdiTextEdit->pColorRef)+DelRange.cpMax*sizeof(COLORREF),
143 (length-DelRange.cpMax) * sizeof(COLORREF),
144 delta*sizeof(COLORREF));
145 //色づけ
146 TextEdit_ResetWordColor(WndNum,&Range,MdiInfo[WndNum]->DocType);
147
148 //新しいキャレット位置に変更
149 GetCaretPosFromBufferIndex(MdiInfo[WndNum]->pMdiTextEdit->buffer,
150 Range.cpMax,
151 &MdiInfo[WndNum]->pMdiTextEdit->StartCaretPos);
152 MdiInfo[WndNum]->pMdiTextEdit->EndCaretPos=MdiInfo[WndNum]->pMdiTextEdit->StartCaretPos;
153
154 //コントロールタブスペースの幅と行番号の文字数を更新
155 MdiInfo[WndNum]->pMdiTextEdit->iWidth_ControlTabSpace=
156 GetControlTabSpace(WndNum,&MdiInfo[WndNum]->pMdiTextEdit->iLineNumberTextCount);
157
158 if(bRedraw){
159 ///////////////
160 // 再描画
161 ///////////////
162
163 if(!TextEdit_ScrollCaret(WndNum,0)){
164 UpdateWindow(MdiInfo[WndNum]->pMdiTextEdit->hEdit); //ちらつき防止
165 InvalidateRect(MdiInfo[WndNum]->pMdiTextEdit->hEdit,NULL,0);
166 }
167
168 ResetCaretPos(WndNum,1);
169 }
170
171 //上下キャレット移動時の左右位置保持機能を解除
172 MdiInfo[WndNum]->pMdiTextEdit->Temp_UpDown_CaretXPos=-1;
173
174 //編集メニューをリセット
175 ResetState_EditMenu();
176
177 if( ! MdiInfo[WndNum]->pMdiTextEdit->IsModified() ){
178 //変更フラグをセット
179 MdiInfo[WndNum]->pMdiTextEdit->Modify();
180 }
181
182
183 //if( projectInfo.IsOpened() ){
184 //プロジェクトが開かれているとき
185 if(MdiInfo[WndNum]->DocType==WNDTYPE_BASIC){
186 //クラスツリーを再表示
187 HTREEITEM hFileTreeItem = projectInfo.fileSystem.root.IsExistFile( MdiInfo[WndNum]->path )
188 ? projectInfo.fileSystem.root.FindFile( MdiInfo[WndNum]->path ).GetTreeItemHandle()
189 : (HTREEITEM)-1;
190 ResetClassTree( hFileTreeItem );
191 }
192 //}
193}
194void TextEdit_ReplaceUpdateUndoData(int WndNum,char *str,BOOL bPaste,BOOL bRedraw){
195 extern HANDLE hHeap;
196 int Command;
197 char *KeyStr,*DelStr;
198 char temporary[255];
199 CHARRANGE Range,DelRange;
200
201 if(MdiInfo[WndNum]->IndentStr){
202 //自動インデントを有効にする
203 lstrcpy(temporary,MdiInfo[WndNum]->IndentStr);
204
205 CancelBeforeAutoIndent(WndNum);
206 TextEdit_ReplaceUpdateUndoData(WndNum,temporary,0,1);
207 }
208
209 TextEdit_GetSel(WndNum,&DelRange);
210 if(DelRange.cpMin!=DelRange.cpMax){
211 Command=TEXTEDIT_UNDO_SELKEY;
212 DelStr=(char *)HeapAlloc(hHeap,0,DelRange.cpMax-DelRange.cpMin+1);
213
214 TextEdit_GetSelText(WndNum,&DelRange,DelStr);
215
216 Range.cpMin=DelRange.cpMin;
217 Range.cpMax=DelRange.cpMin;
218 }
219 else{
220 if(bPaste) Command=TEXTEDIT_UNDO_PASTE;
221 else Command=TEXTEDIT_UNDO_KEY;
222 DelStr=0;
223
224 Range=DelRange;
225 }
226 if(str[0]){
227 KeyStr=(char *)HeapAlloc(hHeap,0,lstrlen(str)+1);
228 lstrcpy(KeyStr,str);
229 Range.cpMax+=lstrlen(KeyStr);
230 }
231 else KeyStr=0;
232 TextEdit_NoticeChanging(WndNum,Command,KeyStr,DelStr,&Range,&DelRange);
233
234 TextEdit_Replace(WndNum,str,bRedraw);
235}
236
237
238void TextEdit_Convert(int id){
239 int i,i2;
240
241 int WndNum;
242 WndNum=GetWndNum(GetWindow(hClient,GW_CHILD));
243
244 CHARRANGE CharRange;
245 int length;
246 TextEdit_GetSel(WndNum,&CharRange);
247
248#ifdef THETEXT
249 if(id==IDM_CONV_HASRETURN||id==IDM_CONV_QUOTE){
250#else
251 if(id==IDM_CODEFORMAT){
252#endif
253 char *pBuf;
254 pBuf=MdiInfo[WndNum]->pMdiTextEdit->buffer;
255
256 //行全体を選択(min)
257 for(i=CharRange.cpMin;i>0;i--){
258 if(pBuf[i-1]=='\r'&&pBuf[i]=='\n'){
259 i++;
260 break;
261 }
262 }
263 CharRange.cpMin=i;
264
265 //行全体を選択(max)
266 for(i=CharRange.cpMax;;i++){
267 if(pBuf[i]=='\r'&&pBuf[i+1]=='\n'||pBuf[i]=='\0') break;
268 }
269 CharRange.cpMax=i;
270
271 TextEdit_SetSel(WndNum,CharRange.cpMin,CharRange.cpMax,0);
272 }
273
274 length=CharRange.cpMax-CharRange.cpMin;
275
276 char *buffer,*temporary;
277 buffer=(char *)HeapAlloc(hHeap,0,length*3+1024);
278 temporary=(char *)HeapAlloc(hHeap,0,length*3+1024);
279 memcpy(buffer,MdiInfo[WndNum]->pMdiTextEdit->buffer+CharRange.cpMin,length);
280 buffer[length]=0;
281
282 int x=0;
283 switch(id){
284 case IDM_CONV_ALPHA_SMALL:
285 CharLower(buffer);
286 break;
287 case IDM_CONV_ALPHA_BIG:
288 CharUpper(buffer);
289 break;
290 case IDM_CONV_HALF:
291 LCMapString(GetUserDefaultLCID(),LCMAP_HALFWIDTH,buffer,length+1,temporary,length*2+1);
292 lstrcpy(buffer,temporary);
293 break;
294 case IDM_CONV_MULTI:
295 LCMapString(GetUserDefaultLCID(),LCMAP_FULLWIDTH,buffer,length+1,temporary,length*2+1);
296 lstrcpy(buffer,temporary);
297 break;
298 case IDM_CONV_KATAKANA:
299 LCMapString(GetUserDefaultLCID(),LCMAP_KATAKANA,buffer,length+1,temporary,length*2+1);
300 lstrcpy(buffer,temporary);
301 break;
302 case IDM_CONV_HIRAGANA:
303 LCMapString(GetUserDefaultLCID(),LCMAP_HIRAGANA,buffer,length+1,temporary,length*2+1);
304 lstrcpy(buffer,temporary);
305 break;
306 case IDM_CONV_SPACE:
307 temporary=(char *)HeapReAlloc(hHeap,0,temporary,length*pobj_nv->TabSize+1);
308 buffer=(char *)HeapReAlloc(hHeap,0,buffer,length*pobj_nv->TabSize+1);
309 for(i=0,i2=0;;i++,i2++){
310 if(buffer[i]=='\t'){
311 memset(temporary+i2,' ',pobj_nv->TabSize);
312 i2+=pobj_nv->TabSize-1;
313 continue;
314 }
315 temporary[i2]=buffer[i];
316 if(buffer[i]=='\0') break;
317 }
318
319 lstrcpy(buffer,temporary);
320 break;
321 case IDM_CONV_TAB:
322 char szSpaceTemp[255];
323 memset(szSpaceTemp,' ',pobj_nv->TabSize);
324 szSpaceTemp[pobj_nv->TabSize]=0;
325
326 for(i=0,i2=0;;i++,i2++){
327 if(memcmp(buffer+i,szSpaceTemp,pobj_nv->TabSize)==0){
328 temporary[i2]='\t';
329 i+=pobj_nv->TabSize-1;
330 continue;
331 }
332 temporary[i2]=buffer[i];
333 if(buffer[i]=='\0') break;
334 }
335
336 lstrcpy(buffer,temporary);
337 break;
338
339#ifdef THETEXT
340 case IDM_CONV_HASRETURN:
341 //折り返し改行を挿入
342 int i3;
343 for(i=0,i2=0,x=0;;i++,i2++,x++){
344 if(buffer[i]=='\r'&&buffer[i+1]=='\n'){
345 temporary[i2++]=buffer[i++];
346 temporary[i2]=buffer[i];
347 x=-1;
348 continue;
349 }
350 if(x>pobj_nv->iMaxOneLineTextLength-2){
351 //自動改行(英単語を考慮)
352 int i3=0;
353 while(IsVariableChar(buffer[i-1])){
354 i--;
355 i2--;
356 x--;
357 i3++;
358 if(x==1){
359 i+=i3;
360 i2+=i3;
361 x+=i3;
362 break;
363 }
364 }
365 if(i3==1){
366 i++;
367 i2++;
368 x++;
369 }
370 temporary[i2++]='\r';
371 temporary[i2]='\n';
372 i--;
373 x=-1;
374 continue;
375 }
376
377 if(IsDBCSLeadByte(buffer[i])){
378 temporary[i2++]=buffer[i++];
379 temporary[i2]=buffer[i];
380 x++;
381 }
382 else{
383 temporary[i2]=buffer[i];
384
385 if(buffer[i]=='\t'){
386 //タブ文字
387 int tab;
388 tab=pobj_nv->TabSize;
389
390 if(x%tab==0) i3=tab;
391 else i3=tab-x%tab;
392 x+=i3-1;
393 }
394 }
395
396 if(buffer[i]=='\0') break;
397 }
398
399 lstrcpy(buffer,temporary);
400 break;
401 case IDM_CONV_QUOTE:
402 //引用文に変換
403 for(i=0,i2=0,x=0;;i++,i2++,x++){
404 if(x==0){
405 //"> " を挿入
406 temporary[i2++]='>';
407 temporary[i2++]=' ';
408 }
409 if(buffer[i]=='\r'&&buffer[i+1]=='\n'){
410 temporary[i2++]=buffer[i++];
411 temporary[i2]=buffer[i];
412 x=-1;
413 continue;
414 }
415 if(x>pobj_nv->iMaxOneLineTextLength-4){
416 //自動改行(英単語を考慮)
417 int i3=0;
418 while(IsVariableChar(buffer[i-1])){
419 i--;
420 i2--;
421 x--;
422 i3++;
423 if(x==1){
424 i+=i3;
425 i2+=i3;
426 x+=i3;
427 break;
428 }
429 }
430 if(i3==1){
431 i++;
432 i2++;
433 x++;
434 }
435 temporary[i2++]='\r';
436 temporary[i2]='\n';
437 i--;
438 x=-1;
439 continue;
440 }
441
442 if(IsDBCSLeadByte(buffer[i])){
443 temporary[i2++]=buffer[i++];
444 temporary[i2]=buffer[i];
445 x++;
446 }
447 else{
448 temporary[i2]=buffer[i];
449 if(buffer[i]=='\t'){
450 //タブ文字
451 int tab;
452 tab=pobj_nv->TabSize;
453
454 if(x%tab==0) i3=tab;
455 else i3=tab-x%tab;
456 x+=i3-1;
457 }
458 }
459
460 if(buffer[i]=='\0') break;
461 }
462
463 lstrcpy(buffer,temporary);
464 break;
465
466#else //ProjectEditor
467
468 case IDM_CODEFORMAT:
469 char *temp2;
470 temp2=CodeFormatter(buffer);
471 HeapDefaultFree(buffer);
472 buffer=temp2;
473 break;
474
475#endif
476 }
477
478
479
480 //テキストエディタの文字列をリプレイス
481 TextEdit_ReplaceUpdateUndoData(WndNum,
482 buffer,
483 1,
484 1);
485
486 HeapDefaultFree(buffer);
487 HeapDefaultFree(temporary);
488
489 //キャレット位置までスクロールする
490 TextEdit_ScrollCaret(WndNum,0);
491 ResetCaretPos(WndNum);
492}
Note: See TracBrowser for help on using the repository browser.