vdfsplat / AppSrc / cSplatCodeMax.pkg @ 67
History | View | Annotate | Download (18.2 KB)
1 |
//TH-Header |
---|---|
2 |
//***************************************************************************************** |
3 |
// Copyright (c) 2013 Antwise Solutions |
4 |
// All rights reserved. |
5 |
// |
6 |
// $FileName : cSplatCodemax.pkg |
7 |
// $ProjectName : Vdf Debugger |
8 |
// $Authors : Wil van Antwerpen |
9 |
// $Created : 12.14.2013 23:50 |
10 |
// $Type : GPLv2 |
11 |
// |
12 |
// Contents: |
13 |
// |
14 |
//***************************************************************************************** |
15 |
//TH-RevisionStart |
16 |
//TH-RevisionEnd |
17 |
|
18 |
|
19 |
Use cComCodeMax.pkg |
20 |
Use cImageList32.pkg |
21 |
Use RGB.pkg |
22 |
Use cOSVersionInfo.pkg |
23 |
//Use cComCDACTreeListCtl.pkg |
24 |
|
25 |
Define CS_LNG_VDF for "Visual DataFlex" |
26 |
Define CS_DAW_KEY for "Data Access Worldwide" |
27 |
Define CS_DAW_VDF for "Visual DataFlex" |
28 |
Define CS_DAW_DF for "DataFlex" |
29 |
Define CS_TAB for (Character(9)) |
30 |
|
31 |
|
32 |
Define ICO_Brkp_obj for $CI01 // breakpoint object icon |
33 |
Define ICO_Inst_ptr for $CI02 // instruction pointer icon |
34 |
Define ICO_Inst_ptr_top for $CI04 // instruction pointer top icon |
35 |
|
36 |
Class cCodeMaxImageList is a cImageList32 |
37 |
|
38 |
Procedure Construct_Object |
39 |
Forward Send Construct_Object |
40 |
|
41 |
Set piMaxImages To 5 |
42 |
Set piImageHeight To 16 |
43 |
Set piImageWidth To 16 |
44 |
End_Procedure // Construct_Object |
45 |
|
46 |
Procedure OnCreate |
47 |
Integer iVoid |
48 |
|
49 |
Get AddImage "brkp_obj.ico" To iVoid // bit 1 // seems the first image is ignored as a margin image |
50 |
Get AddImage "inst_ptr_top.ico" To iVoid // bit 2 |
51 |
Get AddImage "brkp_obj.ico" To iVoid // bit 3 |
52 |
Get AddImage "inst_ptr.ico" To iVoid // bit 4 |
53 |
End_Procedure |
54 |
End_Class |
55 |
|
56 |
|
57 |
Class cSplatCodeMax is a cComCodeMax |
58 |
Procedure Construct_Object |
59 |
Forward Send Construct_Object |
60 |
Property String psFileName "" |
61 |
Property Integer piCurrentLine 0 |
62 |
|
63 |
Object oCodeMaxImages is a cCodeMaxImageList |
64 |
End_Object |
65 |
End_Procedure |
66 |
|
67 |
Function HostOSis64Bits Returns Boolean |
68 |
Handle hoVersionInfo |
69 |
Boolean bIs64Bits |
70 |
|
71 |
Move false to bIs64Bits |
72 |
Get Create U_cOSVersionInfo To hoVersionInfo |
73 |
If (hoVersionInfo) Begin |
74 |
Get pbX64 Of hoVersionInfo To bIs64Bits |
75 |
End |
76 |
|
77 |
Function_Return bIs64Bits |
78 |
End_Function // HostOSis64Bits |
79 |
|
80 |
// Returns compiled runtime version as DataFlex version * 10 |
81 |
Function CompiledRuntimeVersion Returns Integer |
82 |
String sVersion |
83 |
Integer iVersion |
84 |
Move (Replace(".",gsRuntimeVersion,"")) To sVersion |
85 |
Move (Cast(sVersion,integer)) To iVersion |
86 |
Function_Return iVersion |
87 |
End_Function |
88 |
|
89 |
// |
90 |
// Runtime folder that is used for compiling the current version of Splat. |
91 |
// This helps us in getting the required parameters |
92 |
// |
93 |
Function CurrentRuntimeFolder Returns String |
94 |
Boolean bOpened |
95 |
Boolean bExists |
96 |
Handle hoRegistry |
97 |
String sKey |
98 |
String sPath |
99 |
Integer iVersion |
100 |
|
101 |
Move "" To sPath |
102 |
Get Create U_cRegistry to hoRegistry |
103 |
|
104 |
If (hoRegistry) Begin |
105 |
Set phRootKey of hoRegistry to HKEY_LOCAL_MACHINE |
106 |
Set pfAccessRights of hoRegistry to Key_Read |
107 |
|
108 |
// check if this is a 64 bit machine |
109 |
// if so, the Wow6432Node key will exist <- unreliable test as it turns out |
110 |
//Get KeyExists of hoRegistry "SOFTWARE\Wow6432Node" to bExists |
111 |
Get HostOSis64Bits To bExists |
112 |
If bExists Begin |
113 |
Move (Append("SOFTWARE\Wow6432Node\", CS_DAW_KEY)) to sKey |
114 |
End |
115 |
Else Begin |
116 |
Move (Append("SOFTWARE\", CS_DAW_KEY)) to sKey |
117 |
End |
118 |
|
119 |
Get KeyExists of hoRegistry sKey to bExists |
120 |
If bExists Begin |
121 |
Get CompiledRuntimeVersion To iVersion |
122 |
If (iVersion<180) Begin |
123 |
Move (sKey+"\"+CS_DAW_VDF+"\"+gsRuntimeVersion+"\Defaults\") To sKey |
124 |
End |
125 |
Else Begin |
126 |
Move (sKey+"\"+ CS_DAW_DF+"\"+gsRuntimeVersion+"\Defaults\") To sKey |
127 |
End |
128 |
Get OpenKey of hoRegistry sKey to bOpened |
129 |
If bOpened Begin |
130 |
Get ReadString of hoRegistry "VDFRootDir" To sPath |
131 |
|
132 |
Send CloseKey of hoRegistry |
133 |
End |
134 |
End |
135 |
|
136 |
Send Destroy of hoRegistry |
137 |
End |
138 |
|
139 |
|
140 |
Function_Return sPath |
141 |
End_Function // CurrentRuntimeFolder |
142 |
|
143 |
Procedure LoadVDFLanguageDefinition |
144 |
Boolean bCreated |
145 |
Boolean bExists |
146 |
String sRootDir |
147 |
String sLibDir |
148 |
String sLanguageFile |
149 |
Integer iVersion |
150 |
Handle hoLanguage |
151 |
Variant vLanguage |
152 |
|
153 |
Get Create U_cComlanguage To hoLanguage |
154 |
If (hoLanguage) Begin |
155 |
Send CreateComObject of hoLanguage |
156 |
Get IsComObjectCreated Of hoLanguage To bCreated |
157 |
If (bCreated) Begin |
158 |
Get CurrentRuntimeFolder to sRootDir |
159 |
If (sRootDir<>"") Begin |
160 |
Get vFolderFormat sRootDir To sRootDir |
161 |
Move (sRootDir+"Lib\") To sLibDir |
162 |
|
163 |
Get CompiledRuntimeVersion to iVersion |
164 |
If (iVersion<180) Begin |
165 |
Move (sLibDir+"VisualDataFlex.lng") To sLanguageFile |
166 |
End |
167 |
Else Begin |
168 |
Move (sLibDir+"DataFlex.lng") To sLanguageFile |
169 |
End |
170 |
Get vFilePathExists sLanguageFile to bExists |
171 |
If (bExists) Begin |
172 |
Send ComLoadXmlDefinition of hoLanguage sLanguageFile |
173 |
Set ComName of hoLanguage To CS_LNG_VDF |
174 |
Send ComRegister of hoLanguage |
175 |
|
176 |
Get pvComObject of hoLanguage To vLanguage |
177 |
Set ComLanguage To vLanguage |
178 |
|
179 |
Send Destroy of hoLanguage |
180 |
End |
181 |
Else Begin |
182 |
Send Info_Box ("Can't load language for runtime"*gsRuntimeVersion*"Couldn't find language file\n"*sLanguageFile) |
183 |
End |
184 |
End |
185 |
Else Begin |
186 |
Send Info_Box ("Can't load language as unable to determine runtime folder for VDF"*gsRuntimeVersion) |
187 |
End |
188 |
End |
189 |
End |
190 |
End_Procedure // LoadVDFLanguageDefinition |
191 |
|
192 |
// |
193 |
// Returns line numbers starting from line 0 (not line 1) |
194 |
// Columns numbers are also zero based |
195 |
// |
196 |
Function CurrentPosition Variant vPos Integer Byref iLine Integer Byref iColumn Returns Boolean |
197 |
Boolean bOK |
198 |
Handle hoPos |
199 |
|
200 |
Move false To bOK |
201 |
Get Create (RefClass(cComPosition)) To hoPos |
202 |
If (hoPos) Begin |
203 |
Set pvComObject of hoPos to vPos |
204 |
Get ComLineNo of hoPos To iLine |
205 |
Get ComColNo of hoPos To iColumn |
206 |
Send Destroy of hoPos |
207 |
Move True To bOk |
208 |
End |
209 |
Function_Return bOK |
210 |
End_Function |
211 |
|
212 |
Function CurrentLine Returns Integer |
213 |
Boolean bOK |
214 |
Integer iOffset |
215 |
Integer llLine |
216 |
Integer llColumn |
217 |
Integer iLine |
218 |
Variant vPos |
219 |
|
220 |
Move 0 To iLine |
221 |
Get ComSelStart to iOffset |
222 |
//Get ComSelEnd to llColumn |
223 |
Get ComOffsetToPos iOffset to vPos |
224 |
//Get ComGetSel False to vSel |
225 |
Get CurrentPosition vPos (&llLine) (&llColumn) To bOK |
226 |
If (bOK) Begin |
227 |
Move (llLine+1) To iLine // +1 because line number returned is zero based. |
228 |
End |
229 |
If (llLine=0 and piCurrentLine(Self)<>0) Begin |
230 |
// .. not great .. |
231 |
// if file was opened via stack and this window does not yet have the focus by clicking |
232 |
// into the file, it will return line 0, as a result setting a breakpoint isn't reliable |
233 |
// so... we use this ugly workaround. |
234 |
Get piCurrentLine To iLine |
235 |
End |
236 |
Function_Return iLine |
237 |
End_Function |
238 |
|
239 |
Function WordAtPositionDoesNotWork Integer iLine Integer iColumn Returns String |
240 |
String sWord |
241 |
String sLeadingChar |
242 |
String sTrailingChar |
243 |
Handle hoPos |
244 |
Variant vPos |
245 |
|
246 |
Get Create (RefClass(cComPosition)) to hoPos |
247 |
If (hoPos) Begin |
248 |
Send CreateComObject to hoPos |
249 |
Set ComLineNo of hoPos to iLine |
250 |
Set ComColNo of hoPos to iColumn |
251 |
Get pvComObject of hoPos to vPos |
252 |
Move " (=+-*" to sLeadingChar |
253 |
Move " ()=+-*" to sTrailingChar |
254 |
// Won't work ComGetWordEx does not stop on any of the above characters |
255 |
Get ComGetWordEx vPos sLeadingChar sTrailingChar to sWord |
256 |
Send Destroy of hoPos |
257 |
End |
258 |
Function_Return sWord |
259 |
End_Function |
260 |
|
261 |
Function WordAtLinePosition String sLine Integer iColumn Returns String |
262 |
String sWord |
263 |
String sLeadingChar |
264 |
String sTrailingChar |
265 |
String sChar |
266 |
Integer iChar |
267 |
Integer iStart |
268 |
Integer iEnd |
269 |
Integer iLength |
270 |
Boolean bStop |
271 |
|
272 |
Move (CS_TAB+" (=+-*") To sLeadingChar |
273 |
Move (CS_TAB+" ()=+-*") to sTrailingChar |
274 |
|
275 |
Move False to bStop |
276 |
Move iColumn to iChar |
277 |
if (iColumn>0) begin |
278 |
While not bStop |
279 |
Move (Mid(sLine,1,iChar)) To sChar |
280 |
If (iChar<=0 or sLeadingChar contains sChar) begin |
281 |
Move True To bStop |
282 |
Move (iChar+1) To iStart |
283 |
End |
284 |
Decrement iChar |
285 |
Loop |
286 |
End |
287 |
Move (length(sLine)) To iLength |
288 |
For iChar from iColumn To iLength |
289 |
Move (Mid(sLine,1,iChar)) To sChar |
290 |
If (sTrailingChar contains sChar) begin |
291 |
Move (iChar-1) to iEnd |
292 |
Move iLength To iChar |
293 |
End |
294 |
Loop |
295 |
If (iEnd=0) Move iLength To iEnd |
296 |
Move (Mid(sLine,iEnd-iStart+1,iStart)) To sWord |
297 |
Function_Return sWord |
298 |
End_Function |
299 |
|
300 |
// Returns the word under the specified location. |
301 |
// iLine and iColumn are zero based |
302 |
// |
303 |
Function WordAtPosition Integer iLine Integer iColumn Returns String |
304 |
String sWord |
305 |
String sComment |
306 |
String sLeadingChar |
307 |
String sTrailingChar |
308 |
String sChar |
309 |
String sLine |
310 |
Integer iCommentPos |
311 |
Integer iChar |
312 |
Boolean bBeforeLine |
313 |
|
314 |
Get ComGetLine iLine To sLine |
315 |
Move "//" to sComment |
316 |
Move (Pos(sComment,sLine)) To iCommentPos |
317 |
If (iCommentPos>0 and iCommentPos<iColumn and iColumn>0) Begin |
318 |
Function_Return "" // caret is in a comment block |
319 |
End |
320 |
Move " (=+-*" to sLeadingChar |
321 |
Move " ()=+-*" to sTrailingChar |
322 |
Move True to bBeforeLine // test if caret is before any words on the line |
323 |
For iChar from 1 to iColumn |
324 |
Move (Mid(sLine,1,iChar)) to sChar |
325 |
If not ( (sLeadingChar+sTrailingChar) contains sChar ) Begin |
326 |
Move False to bBeforeLine |
327 |
Move iColumn to iChar |
328 |
End |
329 |
Loop |
330 |
If (bBeforeLine) Begin |
331 |
Function_Return "" // before any words |
332 |
End |
333 |
Get WordAtLinePosition sLine iColumn To sWord |
334 |
Function_Return sWord |
335 |
End_Function |
336 |
|
337 |
// |
338 |
// A bunch of parsing problems happen because we don't know how many |
339 |
// white space characters exist. This replaces multiple WS characters to just |
340 |
// one space character. |
341 |
// |
342 |
Function SingleWhiteSpaceLine String sLine Returns String |
343 |
Integer iLength |
344 |
Integer iChar |
345 |
Boolean bPrevWSChar |
346 |
String sChar |
347 |
String sSWSLine |
348 |
String sWSChars |
349 |
|
350 |
Move "" To sSWSLine |
351 |
Move (CS_TAB+" ") To sWSChars |
352 |
Move (length(sLine)) To iLength |
353 |
Move False To bPrevWSChar |
354 |
For iChar From 1 To iLength |
355 |
Move (Mid(sLine,1,iChar)) to sChar |
356 |
If (sWSChars contains sChar) begin |
357 |
If (bPrevWSChar=false) Begin |
358 |
Move True To bPrevWSChar |
359 |
Move (sSWSLine+" ") To sSWSLine |
360 |
End |
361 |
End |
362 |
Else Begin |
363 |
Move False To bPrevWSChar |
364 |
Move (sSWSLine+sChar) To sSWSLine |
365 |
End |
366 |
Loop |
367 |
Function_Return sSWSLine |
368 |
End_Function |
369 |
|
370 |
// |
371 |
// Tries to locate the object (or variable) in a notation like |
372 |
// Get Property Of oObject To |
373 |
// which should return oObject |
374 |
// |
375 |
Function IsPropertyOf String sProperty Integer iline Integer iColumn Returns String |
376 |
Integer iPos |
377 |
Integer iLength |
378 |
Integer iObj |
379 |
String sObject |
380 |
String sLine |
381 |
String sXLine |
382 |
String slLine |
383 |
|
384 |
Move "" To sObject |
385 |
Get ComGetLine iLine To sLine |
386 |
If (sLine<>"") Begin |
387 |
Get SingleWhiteSpaceLine sLine To sXLine |
388 |
Move (lowercase(sXLine)) To slLine |
389 |
Move (Pos(lowercase(sProperty)+" of ",slLine)) To iPos |
390 |
If (iPos) Begin |
391 |
Move (Length(sProperty+" of ")) To iLength |
392 |
Move (iPos+iLength+1) To iObj |
393 |
Get WordAtLinePosition sXline iObj To sObject |
394 |
End |
395 |
|
396 |
End |
397 |
Function_Return sObject |
398 |
End_Function |
399 |
|
400 |
// |
401 |
// Properties that are queried which are not local to the focused object will need to |
402 |
// be referenced in order to get the correct data back. |
403 |
// This code will try to parse out the object. |
404 |
// |
405 |
Function ObjectForProperty String sProperty Integer iLine Integer iColumn Returns String |
406 |
String sObject |
407 |
String sOfObject |
408 |
String sLine |
409 |
|
410 |
Move "Self" To sObject // the default target object is self |
411 |
Get IsPropertyOf sProperty iLine iColumn To sOfObject |
412 |
If (sOfObject<>"") Begin |
413 |
Move sOfObject To sObject |
414 |
End |
415 |
Function_Return sObject |
416 |
End_Function |
417 |
|
418 |
Procedure OnComQuickInfo Integer llLine Integer llColumn String ByRef llTipText |
419 |
Handle hoDebugger |
420 |
String sWord |
421 |
String sResult |
422 |
String sObjectID |
423 |
String sObjectName |
424 |
String sType |
425 |
String sTargetObject |
426 |
Boolean bIsProperty |
427 |
Boolean bIsProcedure |
428 |
Boolean bIsObject |
429 |
Boolean bIsKeyword |
430 |
Boolean bPaused |
431 |
Boolean bOK |
432 |
|
433 |
// Does not always return what we need |
434 |
//Get ComCurrentWord To sWord // gets word under cursor |
435 |
Move False To bOk |
436 |
Get WordAtPosition llLine llColumn To sWord |
437 |
If (sWord<>"") Begin |
438 |
Get phoDebugger To hoDebugger |
439 |
If (hoDebugger) Begin |
440 |
Move "" To sResult |
441 |
Move "" To sType |
442 |
Move False To bIsObject |
443 |
Get pbProgramPaused Of hoDebugger To bPaused |
444 |
If (bPaused) Begin |
445 |
Get IsLanguageKeyword of hoDebugger sWord To bIsKeyword // |
446 |
If (bIsKeyword=false) Begin |
447 |
Get IsVariableProperty of hoDebugger sWord To bIsProperty |
448 |
If (bIsProperty) Begin |
449 |
Get ObjectForProperty sWord llLine llColumn to sTargetObject |
450 |
Move (sWord+"("+sTargetObject+")") To sWord |
451 |
Move "Property " To sType |
452 |
End |
453 |
Else Begin |
454 |
Get IsVariableProcedure Of hoDebugger sWord To bIsProcedure |
455 |
If (bIsProcedure) Begin |
456 |
Move "Procedure " To sType |
457 |
End |
458 |
Else Begin |
459 |
If (lowercase(sWord)="self") Begin |
460 |
Move "Object " To sType |
461 |
Move True To bIsObject |
462 |
End |
463 |
End |
464 |
End |
465 |
Move ("Evaluating "+sType+"'"+sWord+"' results in"+character(10)) To llTipText |
466 |
If (bIsProcedure) Begin |
467 |
Move "Not evaluating methods." To sResult |
468 |
End |
469 |
Else Begin |
470 |
Get ComEval of hoDebugger sWord (&sResult) to bOK |
471 |
End |
472 |
If (bOK) Begin |
473 |
If (bIsObject) Begin |
474 |
Move sResult To sObjectID |
475 |
Move "" To sObjectName |
476 |
Get ComEval of hoDebugger ("name("+sObjectID+")") (&sObjectName) to bOK |
477 |
If (bOK) Begin |
478 |
Move (sResult+" ("+sObjectName+") ") To sResult |
479 |
End |
480 |
End |
481 |
Move (sResult+character(10)+character(10)+"Eval OK") To sResult |
482 |
End |
483 |
Else Begin |
484 |
Move (sResult+character(10)+character(10)+"Eval Failed") To sResult |
485 |
End |
486 |
End |
487 |
Else Begin |
488 |
Move ("Keyword "+sWord) To sResult |
489 |
End |
490 |
End |
491 |
Else Begin |
492 |
Move sWord To sResult |
493 |
End |
494 |
Move (sResult+", line="+trim(llLine+1)*", column="+Trim(llColumn+1)) To sResult |
495 |
End |
496 |
Else Begin |
497 |
Move "Unable to attach to debugger core" To sResult |
498 |
End |
499 |
End |
500 |
Move (llTipText+sResult) To llTipText |
501 |
End_Procedure |
502 |
|
503 |
|
504 |
Procedure OnCreate |
505 |
Handle hWnd |
506 |
Handle hWndImg |
507 |
Handle hoImgList |
508 |
Variant vImageList |
509 |
// Boolean bCreated |
510 |
|
511 |
Forward Send OnCreate |
512 |
|
513 |
// ToDo: Set the ActiveX properties here... |
514 |
// ComImageListRef |
515 |
// ComHImageList // line margin images |
516 |
//Set ComHImageList To (oEditImages(Self))//vImageList |
517 |
|
518 |
Send LoadVDFLanguageDefinition |
519 |
// |
520 |
Set ComDisplayLeftMargin To True |
521 |
Send ComSetColor OLEcmClrLeftMargin clLtGray |
522 |
Set ComBorderStyle To OLEcmBorderClient |
523 |
|
524 |
//Get Window_Handle of oCodeMaxImages To hWnd |
525 |
Get phImageList Of oCodeMaxImages To hWndImg |
526 |
//Move (oCodeMaxImages(Self)) To hoImgList |
527 |
Set ComHImageList To hWndImg //vImageList |
528 |
//Set ComImageListRef To hWndImg |
529 |
End_Procedure |
530 |
|
531 |
Procedure UpdateStatusHelp |
532 |
Integer Fg |
533 |
Move 1 To Fg |
534 |
Send Request_Status_Help Fg |
535 |
End_Procedure |
536 |
|
537 |
// update status bar when cursor is moving |
538 |
Procedure onCaretPosChanged |
539 |
Send UpdateStatusHelp |
540 |
End_Procedure |
541 |
|
542 |
// The caret position changed |
543 |
Procedure OnComSelChange |
544 |
Send onCaretPosChanged |
545 |
Forward Send OnComSelChange |
546 |
End_Procedure |
547 |
|
548 |
|
549 |
|
550 |
Procedure doOpenSourceFile String sFileName |
551 |
String sLanguage |
552 |
Variant vLanguage |
553 |
|
554 |
Send ComOpenFile sFileName |
555 |
|
556 |
Set psFilename To sFileName |
557 |
|
558 |
Set ComReadOnly To True // NO changes allowed |
559 |
Set ComColorSyntax To True |
560 |
|
561 |
// Update view hosting our control |
562 |
//Send doSetCaptionLabel sFileName |
563 |
End_Procedure // doOpenSourceFile |
564 |
|
565 |
Procedure doOpenSourceFileAtLine String sFileName Integer iLine |
566 |
Integer eBkLineColor |
567 |
Integer iTopMostLine |
568 |
Boolean bVisible |
569 |
Boolean bScrollup |
570 |
|
571 |
Move false to bScrollup |
572 |
Send doOpenSourceFile sFileName |
573 |
Set piCurrentLine to iLine |
574 |
Move iLine to iTopMostLine |
575 |
If (iLine>5) Begin |
576 |
Move (iLine-4) to iTopMostLine // scroll up a bit so we can see context |
577 |
Move true to bScrollup |
578 |
End |
579 |
Send ComSetTopIndex 0 iTopMostLine |
580 |
If (iLine>=0) Begin |
581 |
Send ComSetMarginImages (iLine-1) ICO_Inst_ptr //ICO_Brkp_obj// 2 |
582 |
//Set psFilename of oCodeMax To sFileName |
583 |
// Make it visible to the user where we are |
584 |
//Move True to bVisible |
585 |
//Send ComSelectLine of oCodeMax iLine bVisible |
586 |
Move (RGB(223,253,193)) to eBkLineColor |
587 |
Send ComSetLineColor (iLine-1) eBkLineColor //clYellow |
588 |
End |
589 |
|
590 |
Send UpdateStatusHelp |
591 |
|
592 |
// Send ComSetLineColor iLine clRed |
593 |
End_Procedure // doOpenSourceFileAtLine |
594 |
|
595 |
End_Class |