IDE: code explorer: added directives page

git-svn-id: trunk@11815 -
This commit is contained in:
mattias 2007-08-14 17:22:47 +00:00
parent 57286f6635
commit a03409e87a
11 changed files with 942 additions and 302 deletions

View File

@ -1449,15 +1449,15 @@ var
ExprEnd: LongInt;
ResultNodeExt: TCodeTreeNodeExtension;
function CheckExprIdentifier(const Identifier: string): boolean;
function CheckExprIdentifier(Identifier: PChar): boolean;
var
NodeExt: TCodeTreeNodeExtension;
begin
Result:=true;
if CompareIdentifiers('Result',PChar(Identifier))=0 then exit;
if CompareIdentifiers('FuncName',PChar(Identifier))=0 then exit;
if CompareIdentifiers('Result',Identifier)=0 then exit;
if CompareIdentifiers(PChar(FuncName),Identifier)=0 then exit;
// check for const and type definitions
NodeExt:=FindCodeTreeNodeExt(Definitions,Identifier);
NodeExt:=FindCodeTreeNodeExt(Definitions,GetIdentifier(Identifier));
if (NodeExt<>nil) and (NodeExt.Node<>nil) then begin
if NodeExt.Node.Desc in [ctnConstDefinition,ctnTypeDefinition] then
exit;
@ -1471,7 +1471,7 @@ var
begin
if (ProcNode=nil) or (ProcNode.Desc<>ctnProcedure) then exit;
DebugLn(['CheckProcNode START ',ExtractProcHead(ProcNode,[])]);
//DebugLn(['CheckProcNode START ',ExtractProcHead(ProcNode,[])]);
MoveCursorToNodeStart(ProcNode);
// read 'function'
ReadNextAtom;
@ -1518,7 +1518,7 @@ var
end;
if Node.Desc<>ctnBeginBlock then exit;
DebugLn(['CheckProcNode has begin block']);
//DebugLn(['CheckProcNode has begin block']);
// check begin block is only a single assignment
MoveCursorToNodeStart(Node);
@ -1538,14 +1538,15 @@ var
if (CurPos.Flag in [cafSemicolon,cafEnd]) then
break;
// check if all identifiers can be used in a constant expression
if AtomIsIdentifier(false) and not CheckExprIdentifier(GetAtom) then
if AtomIsIdentifier(false)
and not CheckExprIdentifier(@Src[CurPos.StartPos]) then
exit;
ExprEnd:=CurPos.EndPos;
ReadNextAtom;
end;
if ExprStart=ExprEnd then exit;
DebugLn(['CheckProcNode FOUND']);
//DebugLn(['CheckProcNode FOUND']);
// save values
ResultNodeExt:=NodeExtMemManager.NewNode;

View File

@ -51,6 +51,7 @@ uses
type
TCodeToolManager = class;
TCodeTool = TEventsCodeTool;
TDirectivesTool = TCompilerDirectivesTree;
TGetStringProc = procedure(const s: string) of object;
TOnBeforeApplyChanges = procedure(Manager: TCodeToolManager;
@ -79,7 +80,9 @@ type
FCheckFilesOnDisk: boolean;
FCompleteProperties: boolean;
FCurCodeTool: TCodeTool; // current codetool
FCurDirectivesTool: TDirectivesTool;
FCursorBeyondEOL: boolean;
FDirectivesTools: TAVLTree; // tree of TDirectivesTool sorted for Code (TCodeBuffer)
FErrorCode: TCodeBuffer;
FErrorColumn: integer;
FErrorLine: integer;
@ -98,7 +101,7 @@ type
FResourceTool: TResourceCodeTool;
FSetPropertyVariablename: string;
FSourceExtensions: string; // default is '.pp;.pas;.lpr;.dpr;.dpk'
FSourceTools: TAVLTree; // tree of TCustomCodeTool sorted for pointer
FSourceTools: TAVLTree; // tree of TCustomCodeTool sorted TCustomCodeTool(Data).Scanner.MainCode
FTabWidth: integer;
FVisibleEditorLines: integer;
FWriteExceptions: boolean;
@ -183,19 +186,28 @@ type
// initializing single codetools
function FindCodeToolForSource(Code: TCodeBuffer): TCustomCodeTool;
property CurCodeTool: TEventsCodeTool read FCurCodeTool;
property CurCodeTool: TCodeTool read FCurCodeTool;
procedure ClearCurCodeTool;
function InitCurCodeTool(Code: TCodeBuffer): boolean;
function InitResourceTool: boolean;
procedure ClearPositions;
function GetCodeToolForSource(Code: TCodeBuffer;
GoToMainCode, ExceptionOnError: boolean): TCustomCodeTool;
GoToMainCode, ExceptionOnError: boolean): TCustomCodeTool;
// initializing single compilerdirectivestrees
function FindDirectivesToolForSource(Code: TCodeBuffer
): TDirectivesTool;
property CurDirectivesTool: TDirectivesTool read FCurDirectivesTool;
procedure ClearCurDirectivesTool;
function InitCurDirectivesTool(Code: TCodeBuffer): boolean;
function GetDirectivesToolForSource(Code: TCodeBuffer;
ExceptionOnError: boolean): TCompilerDirectivesTree;
// exception handling
procedure ClearError;
function HandleException(AnException: Exception): boolean;
procedure SetError(Code: TCodeBuffer; Line, Column: integer;
const TheMessage: string);
const TheMessage: string);
property CatchExceptions: boolean
read FCatchExceptions write FCatchExceptions;
property WriteExceptions: boolean
@ -286,6 +298,8 @@ type
WithStatements: boolean; OnlyInterface: boolean = false): boolean;
function CheckSyntax(Code: TCodeBuffer; out NewCode: TCodeBuffer;
out NewX, NewY, NewTopLine: integer; out ErrorMsg: string): boolean;
function ExploreDirectives(Code: TCodeBuffer;
out ADirectivesTool: TDirectivesTool): boolean;
// compiler directives
function GuessMisplacedIfdefEndif(Code: TCodeBuffer; X,Y: integer;
@ -640,6 +654,20 @@ begin
Result:=0;
end;
function CompareDirectivesTreeSources(Data1, Data2: Pointer): integer;
var
Src1, Src2: Pointer;
begin
Src1:=TCompilerDirectivesTree(Data1).Code;
Src2:=TCompilerDirectivesTree(Data2).Code;
if Src1<Src2 then
Result:=-1
else if Src1>Src2 then
Result:=+1
else
Result:=0;
end;
function GetOwnerForCodeTreeNode(ANode: TCodeTreeNode): TObject;
begin
Result:=CodeToolBoss.GetOwnerForCodeTreeNode(ANode);
@ -706,6 +734,7 @@ begin
FVisibleEditorLines:=20;
FWriteExceptions:=true;
FSourceTools:=TAVLTree.Create(@CompareCodeToolMainSources);
FDirectivesTools:=TAVLTree.Create(@CompareDirectivesTreeSources);
IdentifierList:=TIdentifierList.Create;
IdentifierHistory:=TIdentifierHistoryList.Create;
IdentifierList.History:=IdentifierHistory;
@ -725,6 +754,8 @@ begin
FreeAndNil(IdentifierList);
FSourceTools.FreeAndClear;
FreeAndNil(FSourceTools);
FDirectivesTools.FreeAndClear;
FreeAndNil(FDirectivesTools);
FreeAndNil(FResourceTool);
{$IFDEF CTDEBUG}
DebugLn('[TCodeToolManager.Destroy] C');
@ -1423,6 +1454,7 @@ end;
function TCodeToolManager.HandleException(AnException: Exception): boolean;
var ErrorSrcTool: TCustomCodeTool;
DirtyPos: Integer;
ErrorDirTool: TCompilerDirectivesTree;
begin
fErrorMsg:=AnException.Message;
fErrorTopLine:=0;
@ -1446,6 +1478,12 @@ begin
fErrorCode:=ErrorSrcTool.ErrorPosition.Code;
fErrorColumn:=ErrorSrcTool.ErrorPosition.X;
fErrorLine:=ErrorSrcTool.ErrorPosition.Y;
end else if (AnException is ECDirectiveParserException) then begin
// Compiler directive parser error
ErrorDirTool:=ECDirectiveParserException(AnException).Sender;
fErrorCode:=ErrorDirTool.Code;
fErrorColumn:=-1;
fErrorLine:=-1;
end else if (AnException is ESourceChangeCacheError) then begin
// SourceChangeCache error
fErrorCode:=nil;
@ -1514,6 +1552,22 @@ begin
ErrorMsg:=ErrorMessage;
end;
function TCodeToolManager.ExploreDirectives(Code: TCodeBuffer; out
ADirectivesTool: TDirectivesTool): boolean;
begin
Result:=false;
ADirectivesTool:=nil;
try
if InitCurDirectivesTool(Code) then begin
ADirectivesTool:=FCurDirectivesTool;
FCurDirectivesTool.Parse;
Result:=true;
end;
except
on e: Exception do Result:=HandleException(e);
end;
end;
function TCodeToolManager.JumpToMethod(Code: TCodeBuffer; X,Y: integer;
var NewCode: TCodeBuffer; var NewX, NewY, NewTopLine: integer;
var RevertableJump: boolean): boolean;
@ -4007,7 +4061,8 @@ end;
function TCodeToolManager.FindCodeToolForSource(Code: TCodeBuffer
): TCustomCodeTool;
var ANode: TAVLTreeNode;
var
ANode: TAVLTreeNode;
CurSrc, SearchedSrc: Pointer;
begin
ANode:=FSourceTools.Root;
@ -4062,6 +4117,14 @@ begin
Result:=TCodeTool.Create;
Result.Scanner:=Code.Scanner;
FSourceTools.Add(Result);
TCodeTool(Result).OnGetCodeToolForBuffer:=@OnGetCodeToolForBuffer;
TCodeTool(Result).OnGetDirectoryCache:=@OnGetDirectoryCache;
TCodeTool(Result).OnFindUsedUnit:=@DoOnFindUsedUnit;
TCodeTool(Result).OnGetSrcPathForCompiledUnit:=@DoOnGetSrcPathForCompiledUnit;
TCodeTool(Result).OnGetMethodName:=@OnInternalGetMethodName;
Result.OnSetGlobalWriteLock:=@OnToolSetWriteLock;
Result.OnGetGlobalWriteLockInfo:=@OnToolGetWriteLockInfo;
TCodeTool(Result).OnParserProgress:=@OnParserProgress;
end;
with TCodeTool(Result) do begin
AdjustTopLineDueToComment:=Self.AdjustTopLineDueToComment;
@ -4073,14 +4136,57 @@ begin
Result.VisibleEditorLines:=FVisibleEditorLines;
Result.JumpCentered:=FJumpCentered;
Result.CursorBeyondEOL:=FCursorBeyondEOL;
TCodeTool(Result).OnGetCodeToolForBuffer:=@OnGetCodeToolForBuffer;
TCodeTool(Result).OnGetDirectoryCache:=@OnGetDirectoryCache;
TCodeTool(Result).OnFindUsedUnit:=@DoOnFindUsedUnit;
TCodeTool(Result).OnGetSrcPathForCompiledUnit:=@DoOnGetSrcPathForCompiledUnit;
TCodeTool(Result).OnGetMethodName:=@OnInternalGetMethodName;
Result.OnSetGlobalWriteLock:=@OnToolSetWriteLock;
Result.OnGetGlobalWriteLockInfo:=@OnToolGetWriteLockInfo;
TCodeTool(Result).OnParserProgress:=@OnParserProgress;
end;
function TCodeToolManager.FindDirectivesToolForSource(Code: TCodeBuffer
): TDirectivesTool;
var
ANode: TAVLTreeNode;
CurSrc, SearchedSrc: Pointer;
begin
ANode:=FDirectivesTools.Root;
SearchedSrc:=Pointer(Code);
while (ANode<>nil) do begin
CurSrc:=Pointer(TDirectivesTool(ANode.Data).Code);
if CurSrc>SearchedSrc then
ANode:=ANode.Left
else if CurSrc<SearchedSrc then
ANode:=ANode.Right
else begin
Result:=TDirectivesTool(ANode.Data);
exit;
end;
end;
Result:=nil;
end;
procedure TCodeToolManager.ClearCurDirectivesTool;
begin
ClearError;
FCurDirectivesTool:=nil;
end;
function TCodeToolManager.InitCurDirectivesTool(Code: TCodeBuffer): boolean;
begin
Result:=false;
ClearCurDirectivesTool;
FCurDirectivesTool:=TDirectivesTool(GetDirectivesToolForSource(Code,true));
{$IFDEF CTDEBUG}
DebugLn('[TCodeToolManager.InitCurDirectivesTool] ',Code.Filename,' ',dbgs(Code.SourceLength));
{$ENDIF}
Result:=true;
end;
function TCodeToolManager.GetDirectivesToolForSource(Code: TCodeBuffer;
ExceptionOnError: boolean): TCompilerDirectivesTree;
begin
Result:=FindDirectivesToolForSource(Code);
if Result=nil then begin
Result:=TDirectivesTool.Create;
Result.Code:=Code;
FDirectivesTools.Add(Result);
end;
Result.NestedComments:=GetNestedCommentsFlagForFile(Code.Filename);
end;
procedure TCodeToolManager.SetAbortable(const AValue: boolean);
@ -4166,19 +4272,34 @@ var
AToolNode: TAVLTreeNode;
CurTool: TCustomCodeTool;
RootCodeTreeNode: TCodeTreeNode;
CurDirTool: TCompilerDirectivesTree;
begin
Result:=nil;
if ANode=nil then exit;
RootCodeTreeNode:=ANode.GetRoot;
// search in codetools
AToolNode:=FSourceTools.FindLowest;
while (AToolNode<>nil) do begin
CurTool:=TCustomCodeTool(AToolNode.Data);
if CurTool.Tree.Root=RootCodeTreeNode then begin
if (CurTool.Tree<>nil) and (CurTool.Tree.Root=RootCodeTreeNode) then begin
Result:=CurTool;
exit;
end;
AToolNode:=FSourceTools.FindSuccessor(AToolNode);
end;
// search in directivestools
AToolNode:=FDirectivesTools.FindLowest;
while (AToolNode<>nil) do begin
CurDirTool:=TCompilerDirectivesTree(AToolNode.Data);
if (CurDirTool.Tree<>nil) and (CurDirTool.Tree.Root=RootCodeTreeNode) then
begin
Result:=CurDirTool;
exit;
end;
AToolNode:=FDirectivesTools.FindSuccessor(AToolNode);
end;
end;
function TCodeToolManager.DirectoryCachePoolGetString(const ADirectory: string;
@ -4248,6 +4369,10 @@ begin
if Result<>0 then begin
dec(Result,70000); exit;
end;
Result:=FDirectivesTools.ConsistencyCheck;
if Result<>0 then begin
dec(Result,80000); exit;
end;
finally
if (Result<>0) and (FCatchExceptions=false) then
raise Exception.CreateFmt(ctsTCodeToolManagerConsistencyCheck, [Result]);

View File

@ -88,12 +88,20 @@ const
H2Pas_Function_Prefix = 'H2PAS_FUNCTION_';
type
CDirectiveParserException = class(Exception)
TCompilerDirectivesTree = class;
{ ECDirectiveParserException }
ECDirectiveParserException = class(Exception)
public
Sender: TCompilerDirectivesTree;
constructor Create(ASender: TCompilerDirectivesTree; const AMessage: string);
end;
{ TCompilerDirectivesTree }
TCompilerDirectivesTree = class
FChangeStep: integer;
private
FDefaultDirectiveFuncList: TKeyWordFunctionList;
FDisableUnusedDefines: boolean;
@ -161,6 +169,7 @@ type
destructor Destroy; override;
procedure Clear;
procedure Parse;
procedure Parse(aCode: TCodeBuffer; aNestedComments: boolean);
function UpdateNeeded: boolean;
procedure ReduceCompilerDirectives(Undefines, Defines: TStrings;
@ -192,6 +201,7 @@ type
function AtomIsIdentifier: boolean;
function GetAtom: string;
procedure Replace(FromPos, ToPos: integer; const NewSrc: string);
procedure IncreaseChangeStep;
procedure ResetMacros;
procedure ClearMacros;
procedure WriteDebugReport;
@ -204,6 +214,7 @@ type
write FRemoveDisabledDirectives;
property UndefH2PasFunctions: boolean read FUndefH2PasFunctions
write FUndefH2PasFunctions;
property ChangeStep: integer read FChangeStep;
end;
TCompilerMacroStatus = (
@ -602,6 +613,7 @@ end;
procedure TCompilerDirectivesTree.InitParser;
begin
ParseChangeStep:=Code.ChangeStep;
IncreaseChangeStep;
InitKeyWordList;
Src:=Code.Source;
SrcLen:=length(Src);
@ -642,7 +654,7 @@ procedure TCompilerDirectivesTree.EndIFNode(const ErrorMsg: string);
procedure RaiseMissingStartNode;
begin
WriteDebugReport;
raise CDirectiveParserException.Create(ErrorMsg);
raise ECDirectiveParserException.Create(Self,ErrorMsg);
end;
begin
@ -1131,7 +1143,7 @@ var
Change: PDefineChange;
begin
if StackPointer=0 then
raise CDirectiveParserException.Create('TCompilerDirectivesTree.DisableUnreachableBlocks.Pop without Push');
raise ECDirectiveParserException.Create(Self,'TCompilerDirectivesTree.DisableUnreachableBlocks.Pop without Push');
// undo all changes
while Stack[StackPointer]<>nil do begin
Change:=Stack[StackPointer];
@ -1320,7 +1332,7 @@ procedure TCompilerDirectivesTree.DisableIfNode(Node: TCodeTreeNode;
procedure RaiseImpossible;
begin
raise CDirectiveParserException.Create('TCompilerDirectivesTree.DisableIfNode');
raise ECDirectiveParserException.Create(Self,'TCompilerDirectivesTree.DisableIfNode');
end;
function GetExpr(ExprNode: TCodeTreeNode; out Negated: boolean): string;
@ -1627,13 +1639,18 @@ begin
end;
end;
procedure TCompilerDirectivesTree.Parse;
begin
Parse(Code,NestedComments)
end;
procedure TCompilerDirectivesTree.Parse(aCode: TCodeBuffer;
aNestedComments: boolean);
procedure RaiseDanglingIFDEF;
begin
WriteDebugReport;
raise CDirectiveParserException.Create('missing EndIf');
raise ECDirectiveParserException.Create(Self,'missing EndIf');
end;
var
@ -1679,7 +1696,7 @@ end;
function TCompilerDirectivesTree.UpdateNeeded: boolean;
begin
Result:=true;
if (Code=nil) then exit;
if (Code=nil) or (Tree=nil) or (Tree.Root=nil) then exit;
if Code.ChangeStep<>ParseChangeStep then exit;
Result:=false;
end;
@ -2441,6 +2458,7 @@ var
DiffPos: Integer;
begin
DebugLn(['TCompilerDirectivesTree.Replace ',FromPos,'-',ToPos,' Old="',copy(Src,FromPos,ToPos-FromPos),'" New="',NewSrc,'"']);
IncreaseChangeStep;
Code.Replace(FromPos,ToPos-FromPos,NewSrc);
Src:=Code.Source;
SrcLen:=length(Src);
@ -2456,6 +2474,14 @@ begin
end;
end;
procedure TCompilerDirectivesTree.IncreaseChangeStep;
begin
if FChangeStep<>$7fffffff then
inc(FChangeStep)
else
FChangeStep:=-$7fffffff;
end;
procedure TCompilerDirectivesTree.ResetMacros;
begin
if Macros<>nil then
@ -2502,5 +2528,14 @@ begin
AdjustPositionAfterInsert(BeginEnd,false,FromPos,ToPos,DiffPos);
end;
{ ECDirectiveParserException }
constructor ECDirectiveParserException.Create(ASender: TCompilerDirectivesTree;
const AMessage: string);
begin
inherited Create(AMessage);
Sender:=ASender;
end;
end.

View File

@ -3210,7 +3210,7 @@ end;
class function TFixH2PasMissingIFDEFsInUnit.ClassDescription: string;
begin
Result:='Adds missing h2pas IFDEFs for function bodies';
Result:='Add missing h2pas IFDEFs for function bodies';
end;
function TFixH2PasMissingIFDEFsInUnit.Execute(aText: TIDETextConverter

View File

@ -1,4 +1,10 @@
object CodeExplorerDlg: TCodeExplorerDlg
Left = 290
Height = 300
Top = 163
Width = 400
HorzScrollBar.Page = 399
VertScrollBar.Page = 299
ActiveControl = UpdatePage
BorderStyle = bsSizeToolWin
Caption = 'CodeExplorerDlg'
@ -6,79 +12,82 @@ object CodeExplorerDlg: TCodeExplorerDlg
ClientWidth = 400
OnCreate = CodeExplorerDlgCreate
OnDestroy = CodeExplorerDlgDestroy
PixelsPerInch = 96
Position = poScreenCenter
HorzScrollBar.Page = 399
VertScrollBar.Page = 299
Left = 290
Height = 300
Top = 163
Width = 400
object OkButton: TButton
AnchorSideRight.Control = CancelButton
Left = 200
Height = 37
Top = 256
Width = 80
Anchors = [akRight, akBottom]
AutoSize = True
BorderSpacing.Around = 6
BorderSpacing.InnerBorder = 4
Caption = 'OkButton'
OnClick = OkButtonClick
TabOrder = 0
AnchorSideRight.Control = CancelButton
Left = 229
Height = 29
Top = 264
Width = 69
end
object CancelButton: TButton
Left = 286
Height = 37
Top = 256
Width = 106
Anchors = [akRight, akBottom]
AutoSize = True
BorderSpacing.Around = 6
BorderSpacing.InnerBorder = 4
Caption = 'CancelButton'
ModalResult = 2
TabOrder = 1
Left = 304
Height = 29
Top = 264
Width = 88
end
object MainNotebook: TNotebook
Height = 248
Width = 400
Align = alTop
Anchors = [akTop, akLeft, akRight, akBottom]
PageIndex = 0
Height = 256
Width = 400
TabOrder = 2
object UpdatePage: TPage
Caption = 'UpdatePage'
ClientWidth = 392
ClientHeight = 230
Height = 230
Width = 392
ClientWidth = 396
ClientHeight = 217
object RefreshRadioGroup: TRadioGroup
Left = 6
Height = 141
Top = 6
Width = 384
Align = alTop
AutoFill = True
BorderSpacing.Around = 6
Caption = 'RefreshRadioGroup'
ChildSizing.LeftRightSpacing = 6
ChildSizing.TopBottomSpacing = 6
ChildSizing.EnlargeHorizontal = crsHomogenousChildResize
ChildSizing.EnlargeVertical = crsHomogenousChildResize
ChildSizing.ShrinkHorizontal = crsScaleChilds
ChildSizing.ShrinkVertical = crsScaleChilds
ChildSizing.Layout = cclLeftToRightThenTopToBottom
ChildSizing.ControlsPerLine = 1
ClientHeight = 122
ClientWidth = 380
Items.Strings = (
'Manual'
'SwitchPage'
'Idle'
)
TabOrder = 0
Left = 6
Height = 105
Top = 6
Width = 380
end
object FollowCursorCheckBox: TCheckBox
Left = 6
Height = 22
Top = 165
Width = 384
Align = alTop
BorderSpacing.Top = 12
BorderSpacing.Around = 6
Caption = 'FollowCursorCheckBox'
TabOrder = 1
Visible = False
Left = 6
Height = 13
Top = 129
Width = 380
end
end
end

View File

@ -1,26 +1,35 @@
{ This is an automatically generated lazarus resource file }
LazarusResources.Add('TCodeExplorerDlg','FORMDATA',[
'TPF0'#16'TCodeExplorerDlg'#15'CodeExplorerDlg'#13'ActiveControl'#7#10'Update'
+'Page'#11'BorderStyle'#7#13'bsSizeToolWin'#7'Caption'#6#15'CodeExplorerDlg'
+#12'ClientHeight'#3','#1#11'ClientWidth'#3#144#1#8'OnCreate'#7#21'CodeExplor'
+'erDlgCreate'#9'OnDestroy'#7#22'CodeExplorerDlgDestroy'#13'PixelsPerInch'#2
+'`'#8'Position'#7#14'poScreenCenter'#18'HorzScrollBar.Page'#3#143#1#18'VertS'
+'crollBar.Page'#3'+'#1#4'Left'#3'"'#1#6'Height'#3','#1#3'Top'#3#163#0#5'Widt'
+'h'#3#144#1#0#7'TButton'#8'OkButton'#7'Anchors'#11#7'akRight'#8'akBottom'#0#8
+'AutoSize'#9#20'BorderSpacing.Around'#2#6#7'Caption'#6#8'OkButton'#7'OnClick'
+#7#13'OkButtonClick'#8'TabOrder'#2#0#23'AnchorSideRight.Control'#7#12'Cancel'
+'Button'#4'Left'#3#229#0#6'Height'#2#29#3'Top'#3#8#1#5'Width'#2'E'#0#0#7'TBu'
+'tton'#12'CancelButton'#7'Anchors'#11#7'akRight'#8'akBottom'#0#8'AutoSize'#9
+#20'BorderSpacing.Around'#2#6#7'Caption'#6#12'CancelButton'#11'ModalResult'#2
+#2#8'TabOrder'#2#1#4'Left'#3'0'#1#6'Height'#2#29#3'Top'#3#8#1#5'Width'#2'X'#0
+#0#9'TNotebook'#12'MainNotebook'#5'Align'#7#5'alTop'#7'Anchors'#11#5'akTop'#6
+'akLeft'#7'akRight'#8'akBottom'#0#9'PageIndex'#2#0#6'Height'#3#0#1#5'Width'#3
+#144#1#0#5'TPage'#10'UpdatePage'#7'Caption'#6#10'UpdatePage'#11'ClientWidth'
+#3#136#1#12'ClientHeight'#3#230#0#6'Height'#3#230#0#5'Width'#3#136#1#0#11'TR'
+'adioGroup'#17'RefreshRadioGroup'#5'Align'#7#5'alTop'#20'BorderSpacing.Aroun'
+'d'#2#6#7'Caption'#6#17'RefreshRadioGroup'#13'Items.Strings'#1#6#6'Manual'#6
+#10'SwitchPage'#6#4'Idle'#0#8'TabOrder'#2#0#4'Left'#2#6#6'Height'#2'i'#3'Top'
+#2#6#5'Width'#3'|'#1#0#0#9'TCheckBox'#20'FollowCursorCheckBox'#5'Align'#7#5
+'alTop'#17'BorderSpacing.Top'#2#12#20'BorderSpacing.Around'#2#6#7'Caption'#6
+#20'FollowCursorCheckBox'#8'TabOrder'#2#1#7'Visible'#8#4'Left'#2#6#6'Height'
+#2#13#3'Top'#3#129#0#5'Width'#3'|'#1#0#0#0#0#0
'TPF0'#16'TCodeExplorerDlg'#15'CodeExplorerDlg'#4'Left'#3'"'#1#6'Height'#3','
+#1#3'Top'#3#163#0#5'Width'#3#144#1#18'HorzScrollBar.Page'#3#143#1#18'VertScr'
+'ollBar.Page'#3'+'#1#13'ActiveControl'#7#10'UpdatePage'#11'BorderStyle'#7#13
+'bsSizeToolWin'#7'Caption'#6#15'CodeExplorerDlg'#12'ClientHeight'#3','#1#11
+'ClientWidth'#3#144#1#8'OnCreate'#7#21'CodeExplorerDlgCreate'#9'OnDestroy'#7
+#22'CodeExplorerDlgDestroy'#8'Position'#7#14'poScreenCenter'#0#7'TButton'#8
+'OkButton'#23'AnchorSideRight.Control'#7#12'CancelButton'#4'Left'#3#200#0#6
+'Height'#2'%'#3'Top'#3#0#1#5'Width'#2'P'#7'Anchors'#11#7'akRight'#8'akBottom'
+#0#8'AutoSize'#9#20'BorderSpacing.Around'#2#6#25'BorderSpacing.InnerBorder'#2
+#4#7'Caption'#6#8'OkButton'#7'OnClick'#7#13'OkButtonClick'#8'TabOrder'#2#0#0
+#0#7'TButton'#12'CancelButton'#4'Left'#3#30#1#6'Height'#2'%'#3'Top'#3#0#1#5
+'Width'#2'j'#7'Anchors'#11#7'akRight'#8'akBottom'#0#8'AutoSize'#9#20'BorderS'
+'pacing.Around'#2#6#25'BorderSpacing.InnerBorder'#2#4#7'Caption'#6#12'Cancel'
+'Button'#11'ModalResult'#2#2#8'TabOrder'#2#1#0#0#9'TNotebook'#12'MainNoteboo'
+'k'#6'Height'#3#248#0#5'Width'#3#144#1#5'Align'#7#5'alTop'#7'Anchors'#11#5'a'
+'kTop'#6'akLeft'#7'akRight'#8'akBottom'#0#9'PageIndex'#2#0#8'TabOrder'#2#2#0
+#5'TPage'#10'UpdatePage'#7'Caption'#6#10'UpdatePage'#11'ClientWidth'#3#140#1
+#12'ClientHeight'#3#217#0#0#11'TRadioGroup'#17'RefreshRadioGroup'#4'Left'#2#6
+#6'Height'#3#141#0#3'Top'#2#6#5'Width'#3#128#1#5'Align'#7#5'alTop'#8'AutoFil'
+'l'#9#20'BorderSpacing.Around'#2#6#7'Caption'#6#17'RefreshRadioGroup'#28'Chi'
+'ldSizing.LeftRightSpacing'#2#6#28'ChildSizing.TopBottomSpacing'#2#6#29'Chil'
+'dSizing.EnlargeHorizontal'#7#24'crsHomogenousChildResize'#27'ChildSizing.En'
+'largeVertical'#7#24'crsHomogenousChildResize'#28'ChildSizing.ShrinkHorizont'
+'al'#7#14'crsScaleChilds'#26'ChildSizing.ShrinkVertical'#7#14'crsScaleChilds'
+#18'ChildSizing.Layout'#7#29'cclLeftToRightThenTopToBottom'#27'ChildSizing.C'
+'ontrolsPerLine'#2#1#12'ClientHeight'#2'z'#11'ClientWidth'#3'|'#1#13'Items.S'
+'trings'#1#6#6'Manual'#6#10'SwitchPage'#6#4'Idle'#0#8'TabOrder'#2#0#0#0#9'TC'
+'heckBox'#20'FollowCursorCheckBox'#4'Left'#2#6#6'Height'#2#22#3'Top'#3#165#0
+#5'Width'#3#128#1#5'Align'#7#5'alTop'#17'BorderSpacing.Top'#2#12#20'BorderSp'
+'acing.Around'#2#6#7'Caption'#6#20'FollowCursorCheckBox'#8'TabOrder'#2#1#7'V'
+'isible'#8#0#0#0#0#0
]);

View File

@ -1,68 +1,126 @@
object CodeExplorerView: TCodeExplorerView
Left = 378
Height = 505
Height = 517
Top = 175
Width = 206
HorzScrollBar.Page = 205
VertScrollBar.Page = 504
Width = 215
HorzScrollBar.Page = 214
VertScrollBar.Page = 516
ActiveControl = RefreshButton
Caption = 'CodeExplorerView'
ClientHeight = 517
ClientWidth = 215
KeyPreview = True
OnClose = CodeExplorerViewCLOSE
OnCreate = CodeExplorerViewCREATE
OnDestroy = CodeExplorerViewDestroy
OnResize = CodeExplorerViewRESIZE
object RefreshButton: TButton
Height = 25
Width = 96
Height = 37
Width = 80
AutoSize = True
BorderSpacing.InnerBorder = 4
Caption = 'Refresh'
OnClick = RefreshButtonCLICK
Constraints.MinWidth = 80
OnClick = RefreshButtonClick
TabOrder = 0
end
object OptionsButton: TButton
Left = 110
Height = 25
Width = 96
AnchorSideLeft.Control = RefreshButton
AnchorSideLeft.Side = asrBottom
Left = 83
Height = 37
Width = 80
AutoSize = True
BorderSpacing.Left = 3
BorderSpacing.InnerBorder = 4
Caption = 'Options'
Constraints.MinWidth = 80
OnClick = OptionsButtonClick
TabOrder = 1
end
object CodeTreeview: TTreeView
AnchorSideTop.Control = FilterEdit
object MainNotebook: TNotebook
AnchorSideTop.Control = OptionsButton
AnchorSideTop.Side = asrBottom
Height = 456
Top = 49
Width = 206
Height = 478
Top = 39
Width = 215
Align = alBottom
Anchors = [akTop, akLeft, akRight, akBottom]
BorderSpacing.Top = 1
DefaultItemHeight = 16
HideSelection = False
Images = Imagelist1
ParentCtl3D = False
PopupMenu = TreePopupmenu
RightClickSelect = True
BorderSpacing.Top = 2
OnPageChanged = MainNotebookPageChanged
PageIndex = 0
TabOrder = 2
OnDblClick = CodeTreeviewDBLCLICK
OnDeletion = CodeTreeviewDELETION
OnKeyUp = CodeTreeviewKeyUp
Options = [tvoAutoItemHeight, tvoKeepCollapsedNodes, tvoRightClickSelect, tvoShowButtons, tvoShowLines, tvoShowRoot, tvoToolTips, tvoNoDoubleClickExpand]
end
object FilterEdit: TEdit
AnchorSideLeft.Control = Owner
AnchorSideTop.Control = RefreshButton
AnchorSideTop.Side = asrBottom
AnchorSideRight.Control = Owner
AnchorSideRight.Side = asrBottom
Height = 23
Top = 25
Width = 206
Anchors = [akTop, akLeft, akRight]
OnChange = FilterEditChange
TabOrder = 3
Text = 'FilterEdit'
object CodePage: TPage
Caption = 'CodePage'
ClientWidth = 211
ClientHeight = 447
object CodeTreeview: TTreeView
AnchorSideTop.Control = CodeFilterEdit
AnchorSideTop.Side = asrBottom
Height = 423
Top = 24
Width = 211
Align = alBottom
Anchors = [akTop, akLeft, akRight, akBottom]
BorderSpacing.Top = 1
DefaultItemHeight = 19
HideSelection = False
Images = Imagelist1
ParentCtl3D = False
PopupMenu = TreePopupmenu
RightClickSelect = True
TabOrder = 0
OnDblClick = CodeTreeviewDblClick
OnDeletion = CodeTreeviewDeletion
OnKeyUp = CodeTreeviewKeyUp
Options = [tvoAutoItemHeight, tvoKeepCollapsedNodes, tvoRightClickSelect, tvoShowButtons, tvoShowLines, tvoShowRoot, tvoToolTips, tvoNoDoubleClickExpand]
end
object CodeFilterEdit: TEdit
AnchorSideLeft.Control = CodePage
AnchorSideTop.Control = CodePage
AnchorSideRight.Control = CodePage
AnchorSideRight.Side = asrBottom
Height = 23
Width = 211
Anchors = [akTop, akLeft, akRight]
OnChange = CodeFilterEditChange
TabOrder = 1
Text = 'CodeFilterEdit'
end
end
object DirectivesPage: TPage
Caption = 'DirectivesPage'
ClientWidth = 211
ClientHeight = 447
object DirectivesFilterEdit: TEdit
AnchorSideLeft.Control = DirectivesPage
AnchorSideTop.Control = DirectivesPage
AnchorSideRight.Control = DirectivesPage
AnchorSideRight.Side = asrBottom
Height = 23
Width = 211
Anchors = [akTop, akLeft, akRight]
OnChange = DirectivesFilterEditChange
TabOrder = 0
Text = 'DirectivesFilterEdit'
end
object DirectivesTreeView: TTreeView
AnchorSideTop.Control = DirectivesFilterEdit
AnchorSideTop.Side = asrBottom
Height = 423
Top = 24
Width = 211
Align = alBottom
Anchors = [akTop, akLeft, akRight, akBottom]
BorderSpacing.Top = 1
DefaultItemHeight = 19
PopupMenu = TreePopupmenu
TabOrder = 1
OnDblClick = DirectivesTreeViewDblClick
OnDeletion = DirectivesTreeViewDeletion
OnKeyUp = DirectivesTreeViewKeyUp
end
end
end
object Imagelist1: TImageList
left = 64
@ -71,5 +129,9 @@ object CodeExplorerView: TCodeExplorerView
object TreePopupmenu: TPopupMenu
left = 64
top = 72
object MenuItem1: TMenuItem
Caption = 'New Item1'
Visible = False
end
end
end

View File

@ -1,32 +1,55 @@
{ Dit is een automatisch aangemaakt lazarus broncode bestand }
LazarusResources.Add('TCodeExplorerView','FORMDATA',[
'TPF0'#17'TCodeExplorerView'#16'CodeExplorerView'#4'Left'#3'z'#1#6'Height'#3
+#249#1#3'Top'#3#175#0#5'Width'#3#206#0#18'HorzScrollBar.Page'#3#205#0#18'Ver'
+'tScrollBar.Page'#3#248#1#13'ActiveControl'#7#13'RefreshButton'#7'Caption'#6
+#16'CodeExplorerView'#10'KeyPreview'#9#7'OnClose'#7#21'CodeExplorerViewCLOSE'
+#8'OnCreate'#7#22'CodeExplorerViewCREATE'#9'OnDestroy'#7#23'CodeExplorerView'
+'Destroy'#8'OnResize'#7#22'CodeExplorerViewRESIZE'#0#7'TButton'#13'RefreshBu'
+'tton'#6'Height'#2#25#5'Width'#2'`'#25'BorderSpacing.InnerBorder'#2#4#7'Capt'
+'ion'#6#7'Refresh'#7'OnClick'#7#18'RefreshButtonCLICK'#8'TabOrder'#2#0#0#0#7
+'TButton'#13'OptionsButton'#4'Left'#2'n'#6'Height'#2#25#5'Width'#2'`'#25'Bor'
+'derSpacing.InnerBorder'#2#4#7'Caption'#6#7'Options'#7'OnClick'#7#18'Options'
+'ButtonClick'#8'TabOrder'#2#1#0#0#9'TTreeView'#12'CodeTreeview'#21'AnchorSid'
+'eTop.Control'#7#10'FilterEdit'#18'AnchorSideTop.Side'#7#9'asrBottom'#6'Heig'
+'ht'#3#200#1#3'Top'#2'1'#5'Width'#3#206#0#5'Align'#7#8'alBottom'#7'Anchors'
+#11#5'akTop'#6'akLeft'#7'akRight'#8'akBottom'#0#17'BorderSpacing.Top'#2#1#17
+'DefaultItemHeight'#2#16#13'HideSelection'#8#6'Images'#7#10'Imagelist1'#11'P'
+'arentCtl3D'#8#9'PopupMenu'#7#13'TreePopupmenu'#16'RightClickSelect'#9#8'Tab'
+'Order'#2#2#10'OnDblClick'#7#20'CodeTreeviewDBLCLICK'#10'OnDeletion'#7#20'Co'
+'deTreeviewDELETION'#7'OnKeyUp'#7#17'CodeTreeviewKeyUp'#7'Options'#11#17'tvo'
+'AutoItemHeight'#21'tvoKeepCollapsedNodes'#19'tvoRightClickSelect'#14'tvoSho'
+'wButtons'#12'tvoShowLines'#11'tvoShowRoot'#11'tvoToolTips'#22'tvoNoDoubleCl'
+'ickExpand'#0#0#0#5'TEdit'#10'FilterEdit'#22'AnchorSideLeft.Control'#7#5'Own'
+'er'#21'AnchorSideTop.Control'#7#13'RefreshButton'#18'AnchorSideTop.Side'#7#9
+'asrBottom'#23'AnchorSideRight.Control'#7#5'Owner'#20'AnchorSideRight.Side'#7
+#9'asrBottom'#6'Height'#2#23#3'Top'#2#25#5'Width'#3#206#0#7'Anchors'#11#5'ak'
+'Top'#6'akLeft'#7'akRight'#0#8'OnChange'#7#16'FilterEditChange'#8'TabOrder'#2
+#3#4'Text'#6#10'FilterEdit'#0#0#10'TImageList'#10'Imagelist1'#4'left'#2'@'#3
+'top'#2' '#0#0#10'TPopupMenu'#13'TreePopupmenu'#4'left'#2'@'#3'top'#2'H'#0#0
+#0
'TPF0'#17'TCodeExplorerView'#16'CodeExplorerView'#4'Left'#3'z'#1#6'Height'#3#5
+#2#3'Top'#3#175#0#5'Width'#3#215#0#18'HorzScrollBar.Page'#3#214#0#18'VertScr'
+'ollBar.Page'#3#4#2#13'ActiveControl'#7#13'RefreshButton'#7'Caption'#6#16'Co'
+'deExplorerView'#12'ClientHeight'#3#5#2#11'ClientWidth'#3#215#0#10'KeyPrevie'
+'w'#9#7'OnClose'#7#21'CodeExplorerViewCLOSE'#8'OnCreate'#7#22'CodeExplorerVi'
+'ewCREATE'#9'OnDestroy'#7#23'CodeExplorerViewDestroy'#8'OnResize'#7#22'CodeE'
+'xplorerViewRESIZE'#0#7'TButton'#13'RefreshButton'#6'Height'#2'%'#5'Width'#2
+'P'#8'AutoSize'#9#25'BorderSpacing.InnerBorder'#2#4#7'Caption'#6#7'Refresh'
+#20'Constraints.MinWidth'#2'P'#7'OnClick'#7#18'RefreshButtonClick'#8'TabOrde'
+'r'#2#0#0#0#7'TButton'#13'OptionsButton'#22'AnchorSideLeft.Control'#7#13'Ref'
+'reshButton'#19'AnchorSideLeft.Side'#7#9'asrBottom'#4'Left'#2'S'#6'Height'#2
+'%'#5'Width'#2'P'#8'AutoSize'#9#18'BorderSpacing.Left'#2#3#25'BorderSpacing.'
+'InnerBorder'#2#4#7'Caption'#6#7'Options'#20'Constraints.MinWidth'#2'P'#7'On'
+'Click'#7#18'OptionsButtonClick'#8'TabOrder'#2#1#0#0#9'TNotebook'#12'MainNot'
+'ebook'#21'AnchorSideTop.Control'#7#13'OptionsButton'#18'AnchorSideTop.Side'
+#7#9'asrBottom'#6'Height'#3#222#1#3'Top'#2''''#5'Width'#3#215#0#5'Align'#7#8
+'alBottom'#7'Anchors'#11#5'akTop'#6'akLeft'#7'akRight'#8'akBottom'#0#17'Bord'
+'erSpacing.Top'#2#2#13'OnPageChanged'#7#23'MainNotebookPageChanged'#9'PageIn'
+'dex'#2#0#8'TabOrder'#2#2#0#5'TPage'#8'CodePage'#7'Caption'#6#8'CodePage'#11
+'ClientWidth'#3#211#0#12'ClientHeight'#3#191#1#0#9'TTreeView'#12'CodeTreevie'
+'w'#21'AnchorSideTop.Control'#7#14'CodeFilterEdit'#18'AnchorSideTop.Side'#7#9
+'asrBottom'#6'Height'#3#167#1#3'Top'#2#24#5'Width'#3#211#0#5'Align'#7#8'alBo'
+'ttom'#7'Anchors'#11#5'akTop'#6'akLeft'#7'akRight'#8'akBottom'#0#17'BorderSp'
+'acing.Top'#2#1#17'DefaultItemHeight'#2#19#13'HideSelection'#8#6'Images'#7#10
+'Imagelist1'#11'ParentCtl3D'#8#9'PopupMenu'#7#13'TreePopupmenu'#16'RightClic'
+'kSelect'#9#8'TabOrder'#2#0#10'OnDblClick'#7#20'CodeTreeviewDblClick'#10'OnD'
+'eletion'#7#20'CodeTreeviewDeletion'#7'OnKeyUp'#7#17'CodeTreeviewKeyUp'#7'Op'
+'tions'#11#17'tvoAutoItemHeight'#21'tvoKeepCollapsedNodes'#19'tvoRightClickS'
+'elect'#14'tvoShowButtons'#12'tvoShowLines'#11'tvoShowRoot'#11'tvoToolTips'
+#22'tvoNoDoubleClickExpand'#0#0#0#5'TEdit'#14'CodeFilterEdit'#22'AnchorSideL'
+'eft.Control'#7#8'CodePage'#21'AnchorSideTop.Control'#7#8'CodePage'#23'Ancho'
+'rSideRight.Control'#7#8'CodePage'#20'AnchorSideRight.Side'#7#9'asrBottom'#6
+'Height'#2#23#5'Width'#3#211#0#7'Anchors'#11#5'akTop'#6'akLeft'#7'akRight'#0
+#8'OnChange'#7#20'CodeFilterEditChange'#8'TabOrder'#2#1#4'Text'#6#14'CodeFil'
+'terEdit'#0#0#0#5'TPage'#14'DirectivesPage'#7'Caption'#6#14'DirectivesPage'
+#11'ClientWidth'#3#211#0#12'ClientHeight'#3#191#1#0#5'TEdit'#20'DirectivesFi'
+'lterEdit'#22'AnchorSideLeft.Control'#7#14'DirectivesPage'#21'AnchorSideTop.'
+'Control'#7#14'DirectivesPage'#23'AnchorSideRight.Control'#7#14'DirectivesPa'
+'ge'#20'AnchorSideRight.Side'#7#9'asrBottom'#6'Height'#2#23#5'Width'#3#211#0
+#7'Anchors'#11#5'akTop'#6'akLeft'#7'akRight'#0#8'OnChange'#7#26'DirectivesFi'
+'lterEditChange'#8'TabOrder'#2#0#4'Text'#6#20'DirectivesFilterEdit'#0#0#9'TT'
+'reeView'#18'DirectivesTreeView'#21'AnchorSideTop.Control'#7#20'DirectivesFi'
+'lterEdit'#18'AnchorSideTop.Side'#7#9'asrBottom'#6'Height'#3#167#1#3'Top'#2
+#24#5'Width'#3#211#0#5'Align'#7#8'alBottom'#7'Anchors'#11#5'akTop'#6'akLeft'
+#7'akRight'#8'akBottom'#0#17'BorderSpacing.Top'#2#1#17'DefaultItemHeight'#2
+#19#9'PopupMenu'#7#13'TreePopupmenu'#8'TabOrder'#2#1#10'OnDblClick'#7#26'Dir'
+'ectivesTreeViewDblClick'#10'OnDeletion'#7#26'DirectivesTreeViewDeletion'#7
+'OnKeyUp'#7#23'DirectivesTreeViewKeyUp'#0#0#0#0#10'TImageList'#10'Imagelist1'
+#4'left'#2'@'#3'top'#2' '#0#0#10'TPopupMenu'#13'TreePopupmenu'#4'left'#2'@'#3
+'top'#2'H'#0#9'TMenuItem'#9'MenuItem1'#7'Caption'#6#9'New Item1'#7'Visible'#8
+#0#0#0#0
]);

View File

@ -24,6 +24,11 @@
* Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
* *
***************************************************************************
Abstract:
Window showing the current source as tree structure.
Normally it shows the codetools nodes of the current unit in the
source editor. If an include file is open, the corresponding unit is shown.
}
unit CodeExplorer;
@ -36,37 +41,53 @@ uses
Classes, SysUtils, LCLProc, LCLType, LResources, Forms, Controls, Graphics,
Dialogs, Buttons, ComCtrls, Menus,
// CodeTools
CodeToolManager, CodeAtom, CodeCache, CodeTree, PascalParserTool,
KeywordFuncLists,
CodeToolManager, CodeAtom, CodeCache, CodeTree, KeywordFuncLists,
DirectivesTree, PascalParserTool,
// IDE Intf
IDECommands, MenuIntf,
// IDE
LazarusIDEStrConsts, EnvironmentOpts, IDEOptionDefs, InputHistory, IDEProcs,
CodeExplOpts, StdCtrls;
CodeExplOpts, StdCtrls, ExtCtrls;
type
TCodeExplorerView = class;
TOnGetCodeTree =
procedure(Sender: TObject; var ACodeTool: TCodeTool) of object;
procedure(Sender: TObject; var ACodeTool: TCodeTool) of object;
TOnGetDirectivesTree =
procedure(Sender: TObject; var ADirectivesTool: TDirectivesTool) of object;
TOnJumpToCode = procedure(Sender: TObject; const Filename: string;
const Caret: TPoint; TopLine: integer) of object;
const Caret: TPoint; TopLine: integer) of object;
TCodeExplorerViewFlag = (
cevRefreshNeeded,
cevRefresing
cevCodeRefreshNeeded,
cevDirectivesRefreshNeeded,
cevRefreshing,
cevCheckOnIdle // check if a refresh is needed on next idle
);
TCodeExplorerViewFlags = set of TCodeExplorerViewFlag;
TCodeExplorerPage = (
cepNone,
cepCode,
cepDirectives
);
{ TCodeExplorerView }
TCodeExplorerView = class(TForm)
FilterEdit: TEdit;
Imagelist1: TImageList;
TreePopupmenu: TPopupMenu;
RefreshButton: TButton;
OptionsButton: TButton;
CodeFilterEdit: TEdit;
CodePage: TPage;
CodeTreeview: TTreeView;
DirectivesFilterEdit: TEdit;
DirectivesPage: TPage;
DirectivesTreeView: TTreeView;
Imagelist1: TImageList;
MainNotebook: TNotebook;
MenuItem1: TMenuItem;
OptionsButton: TButton;
RefreshButton: TButton;
TreePopupmenu: TPopupMenu;
procedure CodeExplorerViewClose(Sender: TObject;
var CloseAction: TCloseAction);
procedure CodeExplorerViewCreate(Sender: TObject);
@ -76,59 +97,97 @@ type
procedure CodeTreeviewDeletion(Sender: TObject; Node: TTreeNode);
procedure CodeTreeviewKeyUp(Sender: TObject; var Key: Word;
Shift: TShiftState);
procedure FilterEditChange(Sender: TObject);
procedure CodeFilterEditChange(Sender: TObject);
procedure DirectivesFilterEditChange(Sender: TObject);
procedure DirectivesTreeViewDblClick(Sender: TObject);
procedure DirectivesTreeViewDeletion(Sender: TObject; Node: TTreeNode);
procedure DirectivesTreeViewKeyUp(Sender: TObject; var Key: Word;
Shift: TShiftState);
procedure JumpToMenuitemClick(Sender: TObject);
procedure MainNotebookPageChanged(Sender: TObject);
procedure OptionsButtonClick(Sender: TObject);
procedure RefreshButtonClick(Sender: TObject);
procedure RefreshMenuitemClick(Sender: TObject);
procedure OnApplicationIdle(Sender: TObject; var Done: Boolean);
private
FMainFilename: string;
FCodeFilename: string;
FDirectivesFilename: string;
FFlags: TCodeExplorerViewFlags;
FLastCodeFilter: string;
FLastCodeChangeStep: integer;
FLastDirectivesFilter: string;
FLastDirectivesChangeStep: integer;
FOnGetCodeTree: TOnGetCodeTree;
FOnGetDirectivesTree: TOnGetDirectivesTree;
FOnJumpToCode: TOnJumpToCode;
FUpdateCount: integer;
ImgIDClass: Integer;
ImgIDConst: Integer;
ImgIDConstSection: Integer;
ImgIDDefault: integer;
ImgIDProgram: Integer;
ImgIDUnit: Integer;
ImgIDInterfaceSection: Integer;
ImgIDFinalization: Integer;
ImgIDImplementation: Integer;
ImgIDInitialization: Integer;
ImgIDFinalization: Integer;
ImgIDTypeSection: Integer;
ImgIDType: Integer;
ImgIDVarSection: Integer;
ImgIDVariable: Integer;
ImgIDConstSection: Integer;
ImgIDConst: Integer;
ImgIDClass: Integer;
ImgIDInterfaceSection: Integer;
ImgIDProc: Integer;
ImgIDProgram: Integer;
ImgIDProperty: Integer;
FLastFilter: string;
function GetFilter: string;
function GetNodeDescription(ACodeTool: TCodeTool;
CodeNode: TCodeTreeNode): string;
function GetNodeImage(CodeNode: TCodeTreeNode): integer;
ImgIDType: Integer;
ImgIDTypeSection: Integer;
ImgIDUnit: Integer;
ImgIDVariable: Integer;
ImgIDVarSection: Integer;
function GetCodeFilter: string;
function GetCurrentPage: TCodeExplorerPage;
function GetDirectivesFilter: string;
function GetCodeNodeDescription(ACodeTool: TCodeTool;
CodeNode: TCodeTreeNode): string;
function GetDirectiveNodeDescription(ADirectivesTool: TDirectivesTool;
Node: TCodeTreeNode): string;
function GetCodeNodeImage(CodeNode: TCodeTreeNode): integer;
function GetDirectiveNodeImage(CodeNode: TCodeTreeNode): integer;
procedure CreateNodes(ACodeTool: TCodeTool; CodeNode: TCodeTreeNode;
ParentViewNode, InFrontViewNode: TTreeNode; CreateSiblings: boolean);
procedure SetFilter(const AValue: string);
ParentViewNode, InFrontViewNode: TTreeNode;
CreateSiblings: boolean);
procedure CreateNodes(ADirectivesTool: TDirectivesTool;
CodeNode: TCodeTreeNode;
ParentViewNode, InFrontViewNode: TTreeNode;
CreateSiblings: boolean);
procedure SetCodeFilter(const AValue: string);
procedure SetCurrentPage(const AValue: TCodeExplorerPage);
procedure SetDirectivesFilter(const AValue: string);
protected
procedure KeyUp(var Key: Word; Shift: TShiftState); override;
procedure ApplyCodeFilter;
procedure ApplyDirectivesFilter;
public
destructor Destroy; override;
procedure BeginUpdate;
procedure EndUpdate;
procedure Refresh;
procedure CheckOnIdle;
procedure Refresh(OnlyVisible: boolean);
procedure RefreshCode(OnlyVisible: boolean);
procedure RefreshDirectives(OnlyVisible: boolean);
procedure JumpToSelection;
procedure CurrentCodeBufferChanged;
procedure FilterChanged;
procedure CodeFilterChanged;
procedure DirectivesFilterChanged;
function FilterNode(ANode: TTreeNode; const TheFilter: string): boolean;
function FilterFits(const NodeText, TheFilter: string): boolean; virtual;
function GetCurrentTreeView: TCustomTreeView;
public
property OnGetCodeTree: TOnGetCodeTree read FOnGetCodeTree
write FOnGetCodeTree;
property OnGetDirectivesTree: TOnGetDirectivesTree read FOnGetDirectivesTree
write FOnGetDirectivesTree;
property OnJumpToCode: TOnJumpToCode read FOnJumpToCode write FOnJumpToCode;
property MainFilename: string read FMainFilename;
property Filter: string read GetFilter write SetFilter;
property CodeFilename: string read FCodeFilename;
property CodeFilter: string read GetCodeFilter write SetCodeFilter;
property DirectivesFilename: string read FDirectivesFilename;
property DirectivesFilter: string read GetDirectivesFilter
write SetDirectivesFilter;
property CurrentPage: TCodeExplorerPage read GetCurrentPage
write SetCurrentPage;
end;
const
@ -161,7 +220,7 @@ type
procedure InitCodeExplorerOptions;
begin
if CodeExplorerOptions=nil then
CodeExplorerOptions:=TCodeExplorerOptions.Create;
CodeExplorerOptions:=TCodeExplorerOptions.Create;
end;
procedure LoadCodeExplorerOptions;
@ -223,8 +282,11 @@ begin
RefreshButton.Caption:=dlgUnitDepRefresh;
OptionsButton.Caption:=dlgFROpts;
FilterEdit.Text:=lisCEFilter;
CodeFilterEdit.Text:=lisCEFilter;
CodePage.Caption:=dlgCodeGeneration;
DirectivesFilterEdit.Text:=lisCEFilter;
DirectivesPage.Caption:=lisDirectives;
AddResImg(Imagelist1,'ce_default',ImgIDDefault);
AddResImg(Imagelist1,'ce_program',ImgIDProgram);
AddResImg(Imagelist1,'ce_unit',ImgIDUnit);
@ -249,6 +311,8 @@ begin
CEJumpToIDEMenuCommand.OnClick:=@JumpToMenuitemCLICK;
CERefreshIDEMenuCommand.OnClick:=@RefreshMenuitemCLICK;
Application.AddOnIdleHandler(@OnApplicationIdle);
end;
procedure TCodeExplorerView.CodeExplorerViewDestroy(Sender: TObject);
@ -258,18 +322,15 @@ end;
procedure TCodeExplorerView.CodeExplorerViewRESIZE(Sender: TObject);
begin
RefreshButton.Width:=ClientWidth div 2;
with OptionsButton do
SetBounds(RefreshButton.Width,Top,
Parent.ClientWidth-RefreshButton.Width,Height);
end;
procedure TCodeExplorerView.CodeTreeviewDBLCLICK(Sender: TObject);
procedure TCodeExplorerView.CodeTreeviewDblClick(Sender: TObject);
begin
JumpToSelection;
end;
procedure TCodeExplorerView.CodeTreeviewDELETION(Sender: TObject;
procedure TCodeExplorerView.CodeTreeviewDeletion(Sender: TObject;
Node: TTreeNode);
begin
if Node.Data<>nil then
@ -283,10 +344,35 @@ begin
JumpToSelection;
end;
procedure TCodeExplorerView.FilterEditChange(Sender: TObject);
procedure TCodeExplorerView.CodeFilterEditChange(Sender: TObject);
begin
if Sender=nil then ;
FilterChanged;
CodeFilterChanged;
end;
procedure TCodeExplorerView.DirectivesFilterEditChange(Sender: TObject);
begin
if Sender=nil then ;
DirectivesFilterChanged;
end;
procedure TCodeExplorerView.DirectivesTreeViewDblClick(Sender: TObject);
begin
JumpToSelection;
end;
procedure TCodeExplorerView.DirectivesTreeViewDeletion(Sender: TObject;
Node: TTreeNode);
begin
if Node.Data<>nil then
TObject(Node.Data).Free;
end;
procedure TCodeExplorerView.DirectivesTreeViewKeyUp(Sender: TObject;
var Key: Word; Shift: TShiftState);
begin
if (Key=VK_RETURN) and (Shift=[]) then
JumpToSelection;
end;
procedure TCodeExplorerView.CodeExplorerViewCLOSE(Sender: TObject;
@ -300,23 +386,35 @@ begin
JumpToSelection;
end;
procedure TCodeExplorerView.MainNotebookPageChanged(Sender: TObject);
begin
Refresh(true);
end;
procedure TCodeExplorerView.OptionsButtonClick(Sender: TObject);
begin
if ShowCodeExplorerOptions=mrOk then
SaveCodeExplorerOptions;
end;
procedure TCodeExplorerView.RefreshButtonCLICK(Sender: TObject);
procedure TCodeExplorerView.RefreshButtonClick(Sender: TObject);
begin
Refresh;
Refresh(true);
end;
procedure TCodeExplorerView.RefreshMenuitemCLICK(Sender: TObject);
begin
Refresh;
Refresh(true);
end;
function TCodeExplorerView.GetNodeDescription(ACodeTool: TCodeTool;
procedure TCodeExplorerView.OnApplicationIdle(Sender: TObject; var Done: Boolean
);
begin
if (cevCheckOnIdle in FFlags) or (CodeExplorerOptions.Refresh=cerOnIdle) then
Refresh(true);
end;
function TCodeExplorerView.GetCodeNodeDescription(ACodeTool: TCodeTool;
CodeNode: TCodeTreeNode): string;
begin
case CodeNode.Desc of
@ -347,50 +445,74 @@ begin
end;
end;
function TCodeExplorerView.GetFilter: string;
function TCodeExplorerView.GetDirectiveNodeDescription(
ADirectivesTool: TDirectivesTool; Node: TCodeTreeNode): string;
begin
Result:=FilterEdit.Text;
Result:=ADirectivesTool.GetDirective(Node);
end;
function TCodeExplorerView.GetCodeFilter: string;
begin
Result:=CodeFilterEdit.Text;
if Result=lisCEFilter then Result:='';
end;
function TCodeExplorerView.GetNodeImage(CodeNode: TCodeTreeNode): integer;
function TCodeExplorerView.GetCurrentPage: TCodeExplorerPage;
begin
if MainNotebook.ActivePageComponent=CodePage then
Result:=cepCode
else if MainNotebook.ActivePageComponent=DirectivesPage then
Result:=cepDirectives
else
Result:=cepNone;
end;
function TCodeExplorerView.GetDirectivesFilter: string;
begin
Result:=DirectivesFilterEdit.Text;
if Result=lisCEFilter then Result:='';
end;
function TCodeExplorerView.GetCodeNodeImage(CodeNode: TCodeTreeNode): integer;
begin
case CodeNode.Desc of
ctnProgram,ctnLibrary,ctnPackage:
Result:=ImgIDProgram;
ctnUnit:
Result:=ImgIDUnit;
ctnInterface:
Result:=ImgIDInterfaceSection;
ctnImplementation:
Result:=ImgIDImplementation;
ctnInitialization:
Result:=ImgIDInitialization;
ctnFinalization:
Result:=ImgIDFinalization;
ctnTypeSection:
Result:=ImgIDTypeSection;
ctnTypeDefinition:
Result:=ImgIDType;
ctnVarSection:
Result:=ImgIDVarSection;
ctnVarDefinition:
Result:=ImgIDVariable;
ctnConstSection,ctnResStrSection:
Result:=ImgIDConstSection;
ctnConstDefinition:
Result:=ImgIDConst;
ctnClass:
Result:=ImgIDClass;
ctnProcedure:
Result:=ImgIDProc;
ctnProperty:
Result:=ImgIDProperty;
ctnProgram,ctnLibrary,ctnPackage: Result:=ImgIDProgram;
ctnUnit: Result:=ImgIDInterfaceSection;
ctnImplementation: Result:=ImgIDImplementation;
ctnInitialization: Result:=ImgIDInitialization;
ctnFinalization: Result:=ImgIDFinalization;
ctnTypeSection: Result:=ImgIDTypeSection;
ctnTypeDefinition: Result:=ImgIDType;
ctnVarSection: Result:=ImgIDVarSection;
ctnVarDefinition: Result:=ImgIDVariable;
ctnConstSection,ctnResStrSection: Result:=ImgIDConstSection;
ctnConstDefinition: Result:=ImgIDConst;
ctnClass: Result:=ImgIDClass;
ctnProcedure: Result:=ImgIDProc;
ctnProperty: Result:=ImgIDProperty;
else
Result:=ImgIDDefault;
end;
end;
function TCodeExplorerView.GetDirectiveNodeImage(CodeNode: TCodeTreeNode
): integer;
begin
case CodeNode.SubDesc of
cdnsInclude: Result:=ImgIDVarSection;
else
case CodeNode.Desc of
cdnIf: Result:=ImgIDTypeSection;
cdnElseIf: Result:=ImgIDTypeSection;
cdnElse: Result:=ImgIDTypeSection;
cdnEnd: Result:=ImgIDTypeSection;
cdnDefine: Result:=ImgIDConst;
else
Result:=ImgIDDefault;
end;
end;
end;
procedure TCodeExplorerView.CreateNodes(ACodeTool: TCodeTool;
CodeNode: TCodeTreeNode;
ParentViewNode, InFrontViewNode: TTreeNode; CreateSiblings: boolean);
@ -443,8 +565,8 @@ begin
ViewNode:=ParentViewNode;
if ShowNode then begin
NodeData:=TViewNodeData.Create(CodeNode);
NodeText:=GetNodeDescription(ACodeTool,CodeNode);
NodeImageIndex:=GetNodeImage(CodeNode);
NodeText:=GetCodeNodeDescription(ACodeTool,CodeNode);
NodeImageIndex:=GetCodeNodeImage(CodeNode);
if InFrontViewNode<>nil then
ViewNode:=CodeTreeview.Items.InsertObjectBehind(
InFrontViewNode,NodeText,NodeData)
@ -464,11 +586,70 @@ begin
end;
end;
procedure TCodeExplorerView.SetFilter(const AValue: string);
procedure TCodeExplorerView.CreateNodes(ADirectivesTool: TDirectivesTool;
CodeNode: TCodeTreeNode; ParentViewNode, InFrontViewNode: TTreeNode;
CreateSiblings: boolean);
var
NodeData: TViewNodeData;
NodeText: String;
ViewNode: TTreeNode;
NodeImageIndex: Integer;
ShowNode: Boolean;
ShowChilds: Boolean;
begin
if Filter=AValue then exit;
FilterEdit.Text:=AValue;
FilterChanged;
while CodeNode<>nil do begin
ShowNode:=true;
ShowChilds:=true;
// do not show root node
if CodeNode.Desc=cdnRoot then begin
ShowNode:=false;
end;
ViewNode:=ParentViewNode;
if ShowNode then begin
NodeData:=TViewNodeData.Create(CodeNode);
NodeText:=GetDirectiveNodeDescription(ADirectivesTool,CodeNode);
NodeImageIndex:=GetDirectiveNodeImage(CodeNode);
if InFrontViewNode<>nil then
ViewNode:=DirectivesTreeView.Items.InsertObjectBehind(
InFrontViewNode,NodeText,NodeData)
else if ParentViewNode<>nil then
ViewNode:=DirectivesTreeView.Items.AddChildObject(
ParentViewNode,NodeText,NodeData)
else
ViewNode:=DirectivesTreeView.Items.AddObject(nil,NodeText,NodeData);
ViewNode.ImageIndex:=NodeImageIndex;
ViewNode.SelectedIndex:=NodeImageIndex;
InFrontViewNode:=ViewNode;
end;
if ShowChilds then
CreateNodes(ADirectivesTool,CodeNode.FirstChild,ViewNode,nil,true);
if not CreateSiblings then break;
CodeNode:=CodeNode.NextBrother;
end;
end;
procedure TCodeExplorerView.SetCodeFilter(const AValue: string);
begin
if CodeFilter=AValue then exit;
CodeFilterEdit.Text:=AValue;
CodeFilterChanged;
end;
procedure TCodeExplorerView.SetCurrentPage(const AValue: TCodeExplorerPage);
begin
case AValue of
cepCode: MainNotebook.ActivePageComponent:=CodePage;
cepDirectives: MainNotebook.ActivePageComponent:=DirectivesPage;
end;
end;
procedure TCodeExplorerView.SetDirectivesFilter(const AValue: string);
begin
if DirectivesFilter=AValue then exit;
DirectivesFilterEdit.Text:=AValue;
DirectivesFilterChanged;
end;
procedure TCodeExplorerView.KeyUp(var Key: Word; Shift: TShiftState);
@ -477,6 +658,40 @@ begin
ExecuteIDEShortCut(Self,Key,Shift,nil);
end;
procedure TCodeExplorerView.ApplyCodeFilter;
var
ANode: TTreeNode;
TheFilter: String;
begin
TheFilter:=CodeFilterEdit.Text;
FLastCodeFilter:=TheFilter;
CodeTreeview.BeginUpdate;
CodeTreeview.Options:=CodeTreeview.Options+[tvoAllowMultiselect];
ANode:=CodeTreeview.Items.GetFirstNode;
while ANode<>nil do begin
FilterNode(ANode,TheFilter);
ANode:=ANode.GetNextSibling;
end;
CodeTreeview.EndUpdate;
end;
procedure TCodeExplorerView.ApplyDirectivesFilter;
var
ANode: TTreeNode;
TheFilter: String;
begin
TheFilter:=DirectivesFilterEdit.Text;
FLastDirectivesFilter:=TheFilter;
DirectivesTreeView.BeginUpdate;
DirectivesTreeView.Options:=DirectivesTreeView.Options+[tvoAllowMultiselect];
ANode:=DirectivesTreeView.Items.GetFirstNode;
while ANode<>nil do begin
FilterNode(ANode,TheFilter);
ANode:=ANode.GetNextSibling;
end;
DirectivesTreeView.EndUpdate;
end;
destructor TCodeExplorerView.Destroy;
begin
inherited Destroy;
@ -490,55 +705,169 @@ begin
end;
procedure TCodeExplorerView.EndUpdate;
var
CurPage: TCodeExplorerPage;
begin
if FUpdateCount<=0 then
RaiseException('TCodeExplorerView.EndUpdate');
dec(FUpdateCount);
if FUpdateCount=0 then begin
if cevRefreshNeeded in FFlags then Refresh;
CurPage:=CurrentPage;
if (CurPage=cepCode) and (cevCodeRefreshNeeded in FFlags) then
RefreshCode(true);
if (CurPage=cepDirectives) and (cevDirectivesRefreshNeeded in FFlags) then
RefreshDirectives(true);
end;
end;
procedure TCodeExplorerView.Refresh;
procedure TCodeExplorerView.CheckOnIdle;
begin
Include(FFlags,cevCheckOnIdle);
end;
procedure TCodeExplorerView.Refresh(OnlyVisible: boolean);
begin
Exclude(FFlags,cevCheckOnIdle);
RefreshCode(OnlyVisible);
RefreshDirectives(OnlyVisible);
end;
procedure TCodeExplorerView.RefreshCode(OnlyVisible: boolean);
var
OldExpanded: TTreeNodeExpandedState;
ACodeTool: TCodeTool;
begin
if FUpdateCount>0 then begin
Include(FFlags,cevRefreshNeeded);
if (FUpdateCount>0)
or (OnlyVisible and ((CurrentPage<>cepCode) or (not IsVisible))) then begin
Include(FFlags,cevCodeRefreshNeeded);
exit;
end;
Exclude(FFlags,cevRefreshNeeded);
Exclude(FFlags,cevCodeRefreshNeeded);
Include(FFlags,cevRefresing);
FilterEdit.Text:=lisCEFilter;
try
Include(FFlags,cevRefreshing);
// get the codetool with the updated codetree
ACodeTool:=nil;
if Assigned(OnGetCodeTree) then
OnGetCodeTree(Self,ACodeTool);
CodeFilterEdit.Text:=lisCEFilter;
// start updating the CodeTreeView
CodeTreeview.BeginUpdate;
OldExpanded:=TTreeNodeExpandedState.Create(CodeTreeView);
// get the codetool with the updated codetree
ACodeTool:=nil;
if Assigned(OnGetCodeTree) then
OnGetCodeTree(Self,ACodeTool);
if (ACodeTool=nil) or (ACodeTool.Tree=nil) or (ACodeTool.Tree.Root=nil) then
begin
CodeTreeview.Items.Clear;
FMainFilename:='';
end else begin
FMainFilename:=ACodeTool.MainFilename;
CodeTreeview.Items.Clear;
CreateNodes(ACodeTool,ACodeTool.Tree.Root,nil,nil,true);
// check for changes in the codetools
if (ACodeTool=nil) then begin
if (FCodeFilename='') then begin
// still no tool
exit;
end;
end else begin
if (ACodeTool.MainFilename=FCodeFilename)
and (ACodeTool.Scanner<>nil)
and (ACodeTool.Scanner.ChangeStep=FLastCodeChangeStep) then begin
// still the same source
exit;
end;
end;
// remember the codetools ChangeStep
if ACodeTool<>nil then begin
FCodeFilename:=ACodeTool.MainFilename;
if ACodeTool.Scanner<>nil then
FLastCodeChangeStep:=ACodeTool.Scanner.ChangeStep;
end else
FCodeFilename:='';
//DebugLn(['TCodeExplorerView.RefreshCode ',FCodeFilename]);
// start updating the CodeTreeView
CodeTreeview.BeginUpdate;
OldExpanded:=TTreeNodeExpandedState.Create(CodeTreeView);
if (ACodeTool=nil) or (ACodeTool.Tree=nil) or (ACodeTool.Tree.Root=nil) then
begin
CodeTreeview.Items.Clear;
end else begin
CodeTreeview.Items.Clear;
CreateNodes(ACodeTool,ACodeTool.Tree.Root,nil,nil,true);
end;
// restore old expanded state
OldExpanded.Apply(CodeTreeView);
OldExpanded.Free;
CodeTreeview.EndUpdate;
finally
Exclude(FFlags,cevRefreshing);
end;
end;
// restore old expanded state
OldExpanded.Apply(CodeTreeView);
OldExpanded.Free;
CodeTreeview.EndUpdate;
Exclude(FFlags,cevRefresing);
procedure TCodeExplorerView.RefreshDirectives(OnlyVisible: boolean);
var
ADirectivesTool: TDirectivesTool;
OldExpanded: TTreeNodeExpandedState;
begin
if (FUpdateCount>0)
or (OnlyVisible and ((CurrentPage<>cepDirectives) or (not IsVisible))) then
begin
Include(FFlags,cevDirectivesRefreshNeeded);
exit;
end;
Exclude(FFlags,cevDirectivesRefreshNeeded);
try
Include(FFlags,cevRefreshing);
DirectivesFilterEdit.Text:=lisCEFilter;
// get the directivestool with the updated tree
ADirectivesTool:=nil;
if Assigned(OnGetDirectivesTree) then
OnGetDirectivesTree(Self,ADirectivesTool);
// check for changes in the codetools
if (ADirectivesTool=nil) then begin
if (FDirectivesFilename='') then begin
// still no tool
exit;
end;
end else begin
if (ADirectivesTool.Code.Filename=FDirectivesFilename)
and (ADirectivesTool.ChangeStep=FLastDirectivesChangeStep) then begin
// still the same source
exit;
end;
end;
// remember the codetools ChangeStep
if ADirectivesTool<>nil then begin
FDirectivesFilename:=ADirectivesTool.Code.Filename;
FLastDirectivesChangeStep:=ADirectivesTool.ChangeStep;
end else
FDirectivesFilename:='';
//DebugLn(['TCodeExplorerView.RefreshDirectives ',FDirectivesFilename]);
// start updating the DirectivesTreeView
DirectivesTreeView.BeginUpdate;
OldExpanded:=TTreeNodeExpandedState.Create(DirectivesTreeView);
if (ADirectivesTool=nil) or (ADirectivesTool.Tree=nil)
or (ADirectivesTool.Tree.Root=nil) then
begin
DirectivesTreeView.Items.Clear;
end else begin
DirectivesTreeView.Items.Clear;
CreateNodes(ADirectivesTool,ADirectivesTool.Tree.Root,nil,nil,true);
end;
// restore old expanded state
OldExpanded.Apply(DirectivesTreeView);
OldExpanded.Free;
DirectivesTreeView.EndUpdate;
finally
Exclude(FFlags,cevRefreshing);
end;
end;
procedure TCodeExplorerView.JumpToSelection;
@ -549,23 +878,42 @@ var
NewTopLine: integer;
CodeBuffer: TCodeBuffer;
ACodeTool: TCodeTool;
CurTreeView: TCustomTreeView;
begin
if tvoAllowMultiselect in CodeTreeview.Options then
CurItem:=CodeTreeView.GetFirstMultiSelected
CurTreeView:=GetCurrentTreeView;
if CurTreeView=nil then exit;
if tvoAllowMultiselect in CurTreeView.Options then
CurItem:=CurTreeView.GetFirstMultiSelected
else
CurItem:=CodeTreeview.Selected;
CurItem:=CurTreeView.Selected;
if CurItem=nil then exit;
CurNode:=TViewNodeData(CurItem.Data);
if CurNode.StartPos<1 then exit;
CodeBuffer:=CodeToolBoss.FindFile(MainFilename);
if CodeBuffer=nil then exit;
ACodeTool:=nil;
CodeToolBoss.Explore(CodeBuffer,ACodeTool,false);
if ACodeTool=nil then exit;
if not ACodeTool.CleanPosToCaretAndTopLine(CurNode.StartPos,Caret,NewTopLine)
then exit;
case CurrentPage of
cepCode:
begin
CodeBuffer:=CodeToolBoss.FindFile(CodeFilename);
if CodeBuffer=nil then exit;
ACodeTool:=nil;
CodeToolBoss.Explore(CodeBuffer,ACodeTool,false);
if ACodeTool=nil then exit;
if not ACodeTool.CleanPosToCaretAndTopLine(CurNode.StartPos,Caret,NewTopLine)
then exit;
end;
cepDirectives:
begin
CodeBuffer:=CodeToolBoss.FindFile(DirectivesFilename);
if CodeBuffer=nil then exit;
CodeBuffer.AbsoluteToLineCol(CurNode.StartPos,Caret.Y,Caret.X);
if Caret.Y<1 then exit;
Caret.Code:=CodeBuffer;
NewTopLine:=Caret.Y-(CodeToolBoss.VisibleEditorLines div 2);
if NewTopLine<1 then NewTopLine:=1;
end;
else
exit;
end;
if Assigned(OnJumpToCode) then
OnJumpToCode(Self,Caret.Code.Filename,Point(Caret.X,Caret.Y),NewTopLine);
end;
@ -573,33 +921,37 @@ end;
procedure TCodeExplorerView.CurrentCodeBufferChanged;
begin
if CodeExplorerOptions.Refresh=cerSwitchEditorPage then
Refresh;
CheckOnIdle;
end;
procedure TCodeExplorerView.FilterChanged;
procedure TCodeExplorerView.CodeFilterChanged;
var
TheFilter: String;
ANode: TTreeNode;
begin
if FUpdateCount>0 then begin
Include(FFlags,cevRefreshNeeded);
TheFilter:=CodeFilterEdit.Text;
if FLastCodeFilter=TheFilter then exit;
if (FUpdateCount>0) or (CurrentPage<>cepCode) then begin
Include(FFlags,cevCodeRefreshNeeded);
exit;
end;
TheFilter:=FilterEdit.Text;
if FLastFilter=TheFilter then exit;
FLastFilter:=TheFilter;
CodeTreeview.BeginUpdate;
CodeTreeview.Options:=CodeTreeview.Options+[tvoAllowMultiselect];
ANode:=CodeTreeview.Items.GetFirstNode;
while ANode<>nil do begin
FilterNode(ANode,TheFilter);
ANode:=ANode.GetNextSibling;
end;
CodeTreeview.EndUpdate;
ApplyCodeFilter;
end;
function TCodeExplorerView.FilterNode(ANode: TTreeNode; const TheFilter: string
): boolean;
procedure TCodeExplorerView.DirectivesFilterChanged;
var
TheFilter: String;
begin
TheFilter:=DirectivesFilterEdit.Text;
if FLastDirectivesFilter=TheFilter then exit;
if (FUpdateCount>0) or (CurrentPage<>cepDirectives) then begin
Include(FFlags,cevDirectivesRefreshNeeded);
exit;
end;
ApplyDirectivesFilter;
end;
function TCodeExplorerView.FilterNode(ANode: TTreeNode;
const TheFilter: string): boolean;
var
ChildNode: TTreeNode;
HasVisibleChilds: Boolean;
@ -648,6 +1000,15 @@ begin
end;
end;
function TCodeExplorerView.GetCurrentTreeView: TCustomTreeView;
begin
case CurrentPage of
cepCode: Result:=CodeTreeview;
cepDirectives: Result:=DirectivesTreeView;
else Result:=nil;
end;
end;
initialization
{$I codeexplorer.lrs}
CodeExplorerView:=nil;

View File

@ -3393,6 +3393,7 @@ resourcestring
lisUIClearIncludedByReference = 'Clear include cache';
lisChangeParent = 'Change parent ...';
lisLazarusIDE = 'Lazarus IDE';
lisDirectives = 'Directives';
implementation
end.

View File

@ -449,6 +449,8 @@ type
// code explorer events
procedure OnCodeExplorerGetCodeTree(Sender: TObject;
var ACodeTool: TCodeTool);
procedure OnCodeExplorerGetDirectivesTree(Sender: TObject;
var ADirectivesTool: TDirectivesTool);
procedure OnCodeExplorerJumpToCode(Sender: TObject; const Filename: string;
const Caret: TPoint; TopLine: integer);
@ -6844,12 +6846,13 @@ begin
if CodeExplorerView=nil then begin
CodeExplorerView:=TCodeExplorerView.Create(OwningComponent);
CodeExplorerView.OnGetCodeTree:=@OnCodeExplorerGetCodeTree;
CodeExplorerView.OnGetDirectivesTree:=@OnCodeExplorerGetDirectivesTree;
CodeExplorerView.OnJumpToCode:=@OnCodeExplorerJumpToCode;
end;
EnvironmentOptions.IDEWindowLayoutList.ItemByEnum(nmiwCodeExplorerName).Apply;
CodeExplorerView.ShowOnTop;
CodeExplorerView.Refresh;
CodeExplorerView.Refresh(true);
end;
procedure TMainIDE.DoShowCodeBrowser;
@ -10330,6 +10333,17 @@ begin
CodeToolBoss.Explore(ActiveUnitInfo.Source,ACodeTool,false);
end;
procedure TMainIDE.OnCodeExplorerGetDirectivesTree(Sender: TObject;
var ADirectivesTool: TDirectivesTool);
var
ActiveUnitInfo: TUnitInfo;
ActiveSrcEdit: TSourceEditor;
begin
ADirectivesTool:=nil;
if not BeginCodeTool(ActiveSrcEdit,ActiveUnitInfo,[]) then exit;
CodeToolBoss.ExploreDirectives(ActiveUnitInfo.Source,ADirectivesTool);
end;
procedure TMainIDE.OnCodeExplorerJumpToCode(Sender: TObject;
const Filename: string; const Caret: TPoint; TopLine: integer);
begin