lazarus/ide/findrenameidentifier.pas

708 lines
24 KiB
ObjectPascal

{
***************************************************************************
* *
* This source is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
* This code is distributed in the hope that it will be useful, but *
* WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
* General Public License for more details. *
* *
* A copy of the GNU General Public License is available on the World *
* Wide Web at <http://www.gnu.org/copyleft/gpl.html>. You can also *
* obtain it by writing to the Free Software Foundation, *
* Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
* *
***************************************************************************
Author: Mattias Gaertner
Abstract:
Options dialog and methods for finding and renaming identifier references.
}
unit FindRenameIdentifier;
{$mode objfpc}{$H+}
interface
uses
// RTL + FCL + LCL
Classes, SysUtils, AVL_Tree, LCLProc, Forms, Controls, Dialogs,
StdCtrls, ExtCtrls, ComCtrls, ButtonPanel, LclIntf,
// CodeTools
FileProcs, CTUnitGraph, CodeTree, CodeCache, CodeToolManager, CodeToolsStructs,
// LazUtils
LazFileUtils, LazFileCache, laz2_DOM,
// IDE
LazarusIDEStrConsts, IDEProcs, IDEWindowIntf, MiscOptions, DialogProcs,
LazIDEIntf, IDEDialogs, InputHistory, SearchResultView, CodeHelp;
type
{ TFindRenameIdentifierDialog }
TFindRenameIdentifierDialog = class(TForm)
ButtonPanel1: TButtonPanel;
ShowResultCheckBox: TCheckBox;
CurrentGroupBox: TGroupBox;
CurrentListBox: TListBox;
ExtraFilesEdit: TEdit;
ExtraFilesGroupBox: TGroupBox;
NewEdit: TEdit;
NewGroupBox: TGroupBox;
RenameCheckBox: TCheckBox;
ScopeCommentsCheckBox: TCheckBox;
ScopeGroupBox: TGroupBox;
ScopeRadioGroup: TRadioGroup;
procedure FindOrRenameButtonClick(Sender: TObject);
procedure FindRenameIdentifierDialogClose(Sender: TObject;
var {%H-}CloseAction: TCloseAction);
procedure FindRenameIdentifierDialogCreate(Sender: TObject);
procedure FormShow(Sender: TObject);
procedure HelpButtonClick(Sender: TObject);
procedure RenameCheckBoxChange(Sender: TObject);
private
FAllowRename: boolean;
FIdentifierFilename: string;
FIdentifierPosition: TPoint;
FIsPrivate: boolean;
procedure SetAllowRename(const AValue: boolean);
procedure SetIsPrivate(const AValue: boolean);
procedure UpdateRename;
public
procedure LoadFromConfig;
procedure SaveToConfig;
procedure LoadFromOptions(Options: TFindRenameIdentifierOptions);
procedure SaveToOptions(Options: TFindRenameIdentifierOptions);
procedure SetIdentifier(const NewIdentifierFilename: string;
const NewIdentifierPosition: TPoint);
property IdentifierFilename: string read FIdentifierFilename;
property IdentifierPosition: TPoint read FIdentifierPosition;
property AllowRename: boolean read FAllowRename write SetAllowRename;
property IsPrivate: boolean read FIsPrivate write SetIsPrivate;
end;
procedure CleanUpFileList(Files: TStringList);
function ShowFindRenameIdentifierDialog(const Filename: string;
const Position: TPoint;
AllowRename: boolean; // allow user to disable/enable rename
SetRenameActive: boolean; // check rename
Options: TFindRenameIdentifierOptions): TModalResult;
function GatherIdentifierReferences(Files: TStringList;
DeclarationCode: TCodeBuffer; const DeclarationCaretXY: TPoint;
SearchInComments: boolean;
var TreeOfPCodeXYPosition: TAVLTree): TModalResult;
function GatherUnitReferences(Files: TStringList;
UnitCode: TCodeBuffer; SearchInComments, IgnoreErrors, IgnoreMissingFiles: boolean;
var TreeOfPCodeXYPosition: TAVLTree): TModalResult;
function ShowIdentifierReferences(
DeclarationCode: TCodeBuffer; const DeclarationCaretXY: TPoint;
TreeOfPCodeXYPosition: TAVLTree): TModalResult;
procedure AddReferencesToResultView(DeclarationCode: TCodeBuffer;
const DeclarationCaretXY: TPoint;
TreeOfPCodeXYPosition: TAVLTree; ClearItems: boolean; SearchPageIndex: integer);
function GatherFPDocReferencesForPascalFiles(PascalFiles: TStringList;
DeclarationCode: TCodeBuffer; const DeclarationCaretXY: TPoint;
var ListOfLazFPDocNode: TFPList): TModalResult;
function GatherReferencesInFPDocFile(
const OldPackageName, OldModuleName, OldElementName: string;
const FPDocFilename: string;
var ListOfLazFPDocNode: TFPList): TModalResult;
implementation
{$R *.lfm}
procedure CleanUpFileList(Files: TStringList);
var
i: Integer;
begin
// sort files
Files.Sort;
// remove doubles
i:=0;
while i<=Files.Count-2 do begin
while (i<=Files.Count-2) and (CompareFilenames(Files[i],Files[i+1])=0) do
begin
Files.Delete(i+1);
end;
inc(i);
end;
end;
function ShowFindRenameIdentifierDialog(const Filename: string;
const Position: TPoint; AllowRename: boolean; SetRenameActive: boolean;
Options: TFindRenameIdentifierOptions): TModalResult;
var
FindRenameIdentifierDialog: TFindRenameIdentifierDialog;
begin
FindRenameIdentifierDialog:=TFindRenameIdentifierDialog.Create(nil);
try
FindRenameIdentifierDialog.LoadFromConfig;
FindRenameIdentifierDialog.SetIdentifier(Filename,Position);
FindRenameIdentifierDialog.AllowRename:=AllowRename;
FindRenameIdentifierDialog.RenameCheckBox.Checked:=SetRenameActive and AllowRename;
if Options<>nil then
FindRenameIdentifierDialog.ShowResultCheckBox.Checked:=Options.RenameShowResult and AllowRename;
Result:=FindRenameIdentifierDialog.ShowModal;
if Result=mrOk then
if Options<>nil then
FindRenameIdentifierDialog.SaveToOptions(Options);
finally
FindRenameIdentifierDialog.Free;
end;
end;
function GatherIdentifierReferences(Files: TStringList;
DeclarationCode: TCodeBuffer; const DeclarationCaretXY: TPoint;
SearchInComments: boolean;
var TreeOfPCodeXYPosition: TAVLTree): TModalResult;
var
i: Integer;
LoadResult: TModalResult;
Code: TCodeBuffer;
ListOfPCodeXYPosition: TFPList;
Cache: TFindIdentifierReferenceCache;
begin
Result:=mrCancel;
ListOfPCodeXYPosition:=nil;
TreeOfPCodeXYPosition:=nil;
Cache:=nil;
try
CleanUpFileList(Files);
// search in every file
for i:=0 to Files.Count-1 do begin
//debugln(['GatherIdentifierReferences ',Files[i]]);
LoadResult:=
LoadCodeBuffer(Code,Files[i],[lbfCheckIfText,lbfUpdateFromDisk,lbfIgnoreMissing],true);
if LoadResult=mrAbort then begin
debugln('GatherIdentifierReferences unable to load "',Files[i],'"');
exit;
end;
if LoadResult<>mrOk then continue;
// search references
CodeToolBoss.FreeListOfPCodeXYPosition(ListOfPCodeXYPosition);
if not CodeToolBoss.FindReferences(
DeclarationCode,DeclarationCaretXY.X,DeclarationCaretXY.Y,
Code, not SearchInComments, ListOfPCodeXYPosition, Cache) then
begin
debugln('GatherIdentifierReferences unable to FindReferences in "',Code.Filename,'"');
Result:=mrAbort;
exit;
end;
//debugln('GatherIdentifierReferences FindReferences in "',Code.Filename,'" ',dbgs(ListOfPCodeXYPosition<>nil));
// add to tree
if ListOfPCodeXYPosition<>nil then begin
if TreeOfPCodeXYPosition=nil then
TreeOfPCodeXYPosition:=CodeToolBoss.CreateTreeOfPCodeXYPosition;
CodeToolBoss.AddListToTreeOfPCodeXYPosition(ListOfPCodeXYPosition,
TreeOfPCodeXYPosition,true,false);
end;
end;
Result:=mrOk;
finally
CodeToolBoss.FreeListOfPCodeXYPosition(ListOfPCodeXYPosition);
if Result<>mrOk then
CodeToolBoss.FreeTreeOfPCodeXYPosition(TreeOfPCodeXYPosition);
Cache.Free;
end;
end;
function GatherUnitReferences(Files: TStringList; UnitCode: TCodeBuffer;
SearchInComments, IgnoreErrors, IgnoreMissingFiles: boolean;
var TreeOfPCodeXYPosition: TAVLTree): TModalResult;
var
ListOfPCodeXYPosition: TFPList;
LoadResult: TModalResult;
Code: TCodeBuffer;
i: Integer;
begin
Result:=mrCancel;
ListOfPCodeXYPosition:=nil;
TreeOfPCodeXYPosition:=nil;
try
CleanUpFileList(Files);
Result:=mrOk;
// search in every file
for i:=0 to Files.Count-1 do begin
if CompareFilenames(Files[i],UnitCode.Filename)=0 then continue;
if IgnoreMissingFiles then
begin
if FilenameIsAbsolute(Files[i]) then
begin
if not FileExistsCached(Files[i]) then continue;
end else begin
Code:=CodeToolBoss.LoadFile(Files[i],false,false);
if (Code=nil) then continue;
end;
end;
LoadResult:=
LoadCodeBuffer(Code,Files[i],[lbfCheckIfText,lbfUpdateFromDisk],true);
if LoadResult=mrAbort then begin
debugln('GatherUnitReferences unable to load "',Files[i],'"');
if IgnoreErrors then
continue;
Result:=mrCancel;
exit;
end;
if LoadResult<>mrOk then continue;
// search references
CodeToolBoss.FreeListOfPCodeXYPosition(ListOfPCodeXYPosition);
if not CodeToolBoss.FindUnitReferences(
UnitCode, Code, not SearchInComments, ListOfPCodeXYPosition) then
begin
debugln('GatherUnitReferences unable to FindUnitReferences in "',Code.Filename,'"');
if IgnoreErrors then
continue;
Result:=mrCancel;
exit;
end;
//debugln('GatherUnitReferences FindUnitReferences in "',Code.Filename,'" ',dbgs(ListOfPCodeXYPosition<>nil));
// add to tree
if ListOfPCodeXYPosition<>nil then begin
if TreeOfPCodeXYPosition=nil then
TreeOfPCodeXYPosition:=CodeToolBoss.CreateTreeOfPCodeXYPosition;
CodeToolBoss.AddListToTreeOfPCodeXYPosition(ListOfPCodeXYPosition,
TreeOfPCodeXYPosition,true,false);
end;
end;
finally
CodeToolBoss.FreeListOfPCodeXYPosition(ListOfPCodeXYPosition);
end;
end;
function ShowIdentifierReferences(
DeclarationCode: TCodeBuffer; const DeclarationCaretXY: TPoint;
TreeOfPCodeXYPosition: TAVLTree): TModalResult;
var
Identifier: string;
OldSearchPageIndex: TTabSheet;
SearchPageIndex: TTabSheet;
begin
Result:=mrCancel;
LazarusIDE.DoShowSearchResultsView(iwgfShow);
SearchPageIndex:=nil;
try
// show result
CodeToolBoss.GetIdentifierAt(DeclarationCode,
DeclarationCaretXY.X,DeclarationCaretXY.Y,Identifier);
// create a search result page
//debugln(['ShowIdentifierReferences ',DbgSName(SearchResultsView)]);
SearchPageIndex:=SearchResultsView.AddSearch(
'Ref: '+Identifier,
Identifier,
'',
ExtractFilePath(DeclarationCode.Filename),
'*.pas;*.pp;*.p;*.inc',
[fifWholeWord,fifSearchDirectories]);
if SearchPageIndex = nil then exit;
// list results
SearchResultsView.BeginUpdate(SearchPageIndex.PageIndex);
AddReferencesToResultView(DeclarationCode,DeclarationCaretXY,
TreeOfPCodeXYPosition,true,SearchPageIndex.PageIndex);
OldSearchPageIndex:=SearchPageIndex;
SearchPageIndex:=nil;
SearchResultsView.EndUpdate(OldSearchPageIndex.PageIndex);
IDEWindowCreators.ShowForm(SearchResultsView,true);
finally
if SearchPageIndex <> nil then
SearchResultsView.EndUpdate(SearchPageIndex.PageIndex);
end;
end;
procedure AddReferencesToResultView(DeclarationCode: TCodeBuffer;
const DeclarationCaretXY: TPoint; TreeOfPCodeXYPosition: TAVLTree;
ClearItems: boolean; SearchPageIndex: integer);
var
Identifier: string;
CodePos: PCodeXYPosition;
CurLine: String;
TrimmedLine: String;
TrimCnt: Integer;
ANode: TAVLTreeNode;
begin
CodeToolBoss.GetIdentifierAt(DeclarationCode,
DeclarationCaretXY.X,DeclarationCaretXY.Y,Identifier);
SearchResultsView.BeginUpdate(SearchPageIndex);
if ClearItems then
SearchResultsView.Items[SearchPageIndex].Clear;
if (TreeOfPCodeXYPosition<>nil) then begin
ANode:=TreeOfPCodeXYPosition.FindHighest;
while ANode<>nil do begin
CodePos:=PCodeXYPosition(ANode.Data);
CurLine:=TrimRight(CodePos^.Code.GetLine(CodePos^.Y-1,false));
TrimmedLine:=Trim(CurLine);
TrimCnt:=length(CurLine)-length(TrimmedLine);
//debugln('ShowReferences x=',dbgs(CodePos^.x),' y=',dbgs(CodePos^.y),' ',CurLine);
SearchResultsView.AddMatch(SearchPageIndex,
CodePos^.Code.Filename,
Point(CodePos^.X,CodePos^.Y),
Point(CodePos^.X+length(Identifier),CodePos^.Y),
TrimmedLine,
CodePos^.X-TrimCnt, length(Identifier));
ANode:=TreeOfPCodeXYPosition.FindPrecessor(ANode);
end;
end;
SearchResultsView.EndUpdate(SearchPageIndex);
end;
function GatherFPDocReferencesForPascalFiles(PascalFiles: TStringList;
DeclarationCode: TCodeBuffer; const DeclarationCaretXY: TPoint;
var ListOfLazFPDocNode: TFPList): TModalResult;
var
PascalFilenames, FPDocFilenames: TFilenameToStringTree;
CacheWasUsed: boolean;
Chain: TCodeHelpElementChain;
CHResult: TCodeHelpParseResult;
CHElement: TCodeHelpElement;
FPDocFilename: String;
S2SItem: PStringToStringTreeItem;
begin
Result:=mrCancel;
PascalFilenames:=nil;
FPDocFilenames:=nil;
try
// gather FPDoc files
CleanUpFileList(PascalFiles);
PascalFilenames:=TFilenameToStringTree.Create(false);
PascalFilenames.AddNames(PascalFiles);
CodeHelpBoss.GetFPDocFilenamesForSources(PascalFilenames,true,FPDocFilenames);
if FPDocFilenames=nil then begin
DebugLn(['GatherFPDocReferences no fpdoc files found']);
exit(mrOk);
end;
// get codehelp element
CHResult:=CodeHelpBoss.GetElementChain(DeclarationCode,
DeclarationCaretXY.X,DeclarationCaretXY.Y,true,Chain,CacheWasUsed);
if CHResult<>chprSuccess then begin
DebugLn(['GatherFPDocReferences CodeHelpBoss.GetElementChain failed']);
exit;
end;
CHElement:=Chain[0];
DebugLn(['GatherFPDocReferences OwnerName=',CHElement.ElementOwnerName,' FPDocPkg=',CHElement.ElementFPDocPackageName,' Name=',CHElement.ElementName]);
// search FPDoc files
for S2SItem in FPDocFilenames do begin
FPDocFilename:=S2SItem^.Name;
Result:=GatherReferencesInFPDocFile(
CHElement.ElementFPDocPackageName,CHElement.ElementUnitName,
CHElement.ElementName,
FPDocFilename,ListOfLazFPDocNode);
if Result<>mrOk then exit;
end;
Result:=mrOk;
finally
PascalFilenames.Free;
FPDocFilenames.Free;
if Result<>mrOk then begin
FreeListObjects(ListOfLazFPDocNode,true);
ListOfLazFPDocNode:=nil;
end;
end;
end;
function GatherReferencesInFPDocFile(
const OldPackageName, OldModuleName, OldElementName: string;
const FPDocFilename: string;
var ListOfLazFPDocNode: TFPList
): TModalResult;
var
DocFile: TLazFPDocFile;
IsSamePackage: Boolean;
IsSameModule: Boolean;// = same unit
procedure CheckLink(Node: TDOMNode; Link: string);
var
p: LongInt;
PackageName: String;
begin
if Link='' then exit;
if Link[1]='#' then begin
p:=System.Pos('.',Link);
if p<1 then exit;
PackageName:=copy(Link,2,p-2);
if SysUtils.CompareText(PackageName,OldPackageName)<>0 then exit;
Link:=copy(Link,p+1,length(Link));
end;
if (SysUtils.CompareText(Link,OldElementName)=0)
or (SysUtils.CompareText(Link,OldModuleName+'.'+OldElementName)=0) then
begin
DebugLn(['CheckLink Found: ',Link]);
if ListOfLazFPDocNode=nil then
ListOfLazFPDocNode:=TFPList.Create;
ListOfLazFPDocNode.Add(TLazFPDocNode.Create(DocFile,Node));
end;
end;
procedure SearchLinksInChildNodes(Node: TDomNode);
// search recursively for links
begin
Node:=Node.FirstChild;
while Node<>nil do begin
if (Node.NodeName='link')
and (Node is TDomElement) then begin
CheckLink(Node,TDomElement(Node).GetAttribute('id'));
end;
SearchLinksInChildNodes(Node);
Node:=Node.NextSibling;
end;
end;
var
CHResult: TCodeHelpParseResult;
CacheWasUsed: boolean;
Node: TDOMNode;
begin
Result:=mrCancel;
DebugLn(['GatherFPDocReferences ',
' OldPackageName=',OldPackageName,
' OldModuleName=',OldModuleName,' OldElementName=',OldElementName,
' FPDocFilename=',FPDocFilename]);
CHResult:=CodeHelpBoss.LoadFPDocFile(FPDocFilename,[chofUpdateFromDisk],
DocFile,CacheWasUsed);
if CHResult<>chprSuccess then begin
DebugLn(['GatherReferencesInFPDocFile CodeHelpBoss.LoadFPDocFile failed File=',FPDocFilename]);
exit(mrCancel);
end;
// search in Doc nodes
IsSamePackage:=SysUtils.CompareText(DocFile.GetPackageName,OldPackageName)=0;
IsSameModule:=SysUtils.CompareText(DocFile.GetModuleName,OldModuleName)=0;
DebugLn(['GatherReferencesInFPDocFile ',DocFile.GetPackageName,'=',OldPackageName,' ',DocFile.GetModuleName,'=',OldModuleName]);
Node:=DocFile.GetFirstElement;
while Node<>nil do begin
if Node is TDomElement then begin
if (SysUtils.CompareText(TDomElement(Node).GetAttribute('name'),OldElementName)=0)
and IsSamePackage and IsSameModule
then begin
// this is the element itself
DebugLn(['GatherReferencesInFPDocFile Element itself found: ',Node.NodeName,' ',Node.NodeValue]);
if ListOfLazFPDocNode=nil then
ListOfLazFPDocNode:=TFPList.Create;
ListOfLazFPDocNode.Add(TLazFPDocNode.Create(DocFile,Node));
end;
CheckLink(Node,TDomElement(Node).GetAttribute('link'));
SearchLinksInChildNodes(Node);
end;
Node:=Node.NextSibling;
end;
Result:=mrOk;
end;
{ TFindRenameIdentifierDialog }
procedure TFindRenameIdentifierDialog.FindRenameIdentifierDialogCreate(
Sender: TObject);
begin
IDEDialogLayoutList.ApplyLayout(Self,450,480);
Caption:=lisFRIFindOrRenameIdentifier;
CurrentGroupBox.Caption:=lisCodeToolsOptsIdentifier;
ExtraFilesGroupBox.Caption:=lisFRIAdditionalFilesToSearchEGPathPasPath2Pp;
ButtonPanel1.OKButton.Caption:=lisFRIFindReferences;
ButtonPanel1.OKButton.ModalResult:=mrNone;
ButtonPanel1.CancelButton.Caption:=lisCancel;
NewGroupBox.Caption:=lisFRIRenaming;
RenameCheckBox.Caption:=lisRename;
ShowResultCheckBox.Caption:=lisRenameShowResult;
ScopeCommentsCheckBox.Caption:=lisFRISearchInCommentsToo;
ScopeGroupBox.Caption:=lisFRISearch;
ScopeRadioGroup.Caption:=dlgSearchScope;
ScopeRadioGroup.Items[0]:=lisFRIinCurrentUnit;
ScopeRadioGroup.Items[1]:=lisFRIinMainProject;
ScopeRadioGroup.Items[2]:=lisFRIinProjectPackageOwningCurrentUnit;
ScopeRadioGroup.Items[3]:=lisFRIinAllOpenPackagesAndProjects;
LoadFromConfig;
end;
procedure TFindRenameIdentifierDialog.FormShow(Sender: TObject);
begin
if NewEdit.CanFocus then
begin
NewEdit.SelectAll;
NewEdit.SetFocus;
end;
end;
procedure TFindRenameIdentifierDialog.HelpButtonClick(Sender: TObject);
begin
OpenUrl('http://wiki.freepascal.org/IDE_Window:_Find_or_Rename_identifier');
end;
procedure TFindRenameIdentifierDialog.RenameCheckBoxChange(Sender: TObject);
begin
UpdateRename;
end;
procedure TFindRenameIdentifierDialog.UpdateRename;
begin
RenameCheckBox.Enabled:=AllowRename;
NewEdit.Enabled:=RenameCheckBox.Checked and RenameCheckBox.Enabled;
ShowResultCheckBox.Enabled:=RenameCheckBox.Checked and RenameCheckBox.Enabled;
if NewEdit.Enabled then
ButtonPanel1.OKButton.Caption:=lisFRIRenameAllReferences
else
ButtonPanel1.OKButton.Caption:=lisFRIFindReferences;
end;
procedure TFindRenameIdentifierDialog.SetAllowRename(const AValue: boolean);
begin
if FAllowRename=AValue then exit;
FAllowRename:=AValue;
UpdateRename;
end;
procedure TFindRenameIdentifierDialog.SetIsPrivate(const AValue: boolean);
begin
if FIsPrivate=AValue then exit;
FIsPrivate:=AValue;
ExtraFilesGroupBox.Enabled:=not IsPrivate;
ScopeRadioGroup.Enabled:=not IsPrivate;
ScopeRadioGroup.ItemIndex:=0;
end;
procedure TFindRenameIdentifierDialog.FindOrRenameButtonClick(Sender: TObject);
var
NewIdentifier: String;
begin
NewIdentifier:=NewEdit.Text;
if (NewIdentifier='') or (not IsValidIdent(NewIdentifier)) then begin
IDEMessageDialog(lisFRIInvalidIdentifier,
Format(lisSVUOisNotAValidIdentifier, [NewIdentifier]), mtError, [mbCancel]);
ModalResult:=mrNone;
exit;
end;
ModalResult:=mrOk;
end;
procedure TFindRenameIdentifierDialog.FindRenameIdentifierDialogClose(
Sender: TObject; var CloseAction: TCloseAction);
begin
SaveToConfig;
IDEDialogLayoutList.SaveLayout(Self);
end;
procedure TFindRenameIdentifierDialog.LoadFromConfig;
begin
LoadFromOptions(MiscellaneousOptions.FindRenameIdentifierOptions);
end;
procedure TFindRenameIdentifierDialog.SaveToConfig;
begin
SaveToOptions(MiscellaneousOptions.FindRenameIdentifierOptions);
end;
procedure TFindRenameIdentifierDialog.LoadFromOptions(
Options: TFindRenameIdentifierOptions);
begin
RenameCheckBox.Checked:=Options.Rename;
ExtraFilesEdit.Text:=StringListToText(Options.ExtraFiles,';',true);
NewEdit.Text:=Options.RenameTo;
ShowResultCheckBox.Checked:=Options.RenameShowResult;
ScopeCommentsCheckBox.Checked:=Options.SearchInComments;
case Options.Scope of
frCurrentUnit: ScopeRadioGroup.ItemIndex:=0;
frProject: ScopeRadioGroup.ItemIndex:=1;
frOwnerProjectPackage: ScopeRadioGroup.ItemIndex:=2;
else
ScopeRadioGroup.ItemIndex:=3;
end;
UpdateRename;
end;
procedure TFindRenameIdentifierDialog.SaveToOptions(
Options: TFindRenameIdentifierOptions);
begin
Options.Rename:=RenameCheckBox.Checked;
if ExtraFilesGroupBox.Enabled then
SplitString(ExtraFilesEdit.Text,';',Options.ExtraFiles,true);
Options.RenameTo:=NewEdit.Text;
Options.RenameShowResult := ShowResultCheckBox.Checked;
Options.SearchInComments:=ScopeCommentsCheckBox.Checked;
if ScopeRadioGroup.Enabled then
case ScopeRadioGroup.ItemIndex of
0: Options.Scope:=frCurrentUnit;
1: Options.Scope:=frProject;
2: Options.Scope:=frOwnerProjectPackage;
else Options.Scope:=frAllOpenProjectsAndPackages;
end;
end;
procedure TFindRenameIdentifierDialog.SetIdentifier(
const NewIdentifierFilename: string; const NewIdentifierPosition: TPoint);
var
s: String;
ACodeBuffer: TCodeBuffer;
ListOfCodeBuffer: TFPList;
i: Integer;
CurCode: TCodeBuffer;
NewIdentifier: String;
Tool: TCodeTool;
CodeXY: TCodeXYPosition;
CleanPos: integer;
Node: TCodeTreeNode;
begin
FIdentifierFilename:=NewIdentifierFilename;
FIdentifierPosition:=NewIdentifierPosition;
CurrentListBox.Items.Clear;
s:=IdentifierFilename
+'('+IntToStr(IdentifierPosition.Y)+','+IntToStr(IdentifierPosition.X)+')';
CurrentListBox.Items.Add(s);
LoadCodeBuffer(ACodeBuffer,IdentifierFileName,[lbfCheckIfText],false);
if ACodeBuffer<>nil then begin
CodeToolBoss.GetIncludeCodeChain(ACodeBuffer,true,ListOfCodeBuffer);
if ListOfCodeBuffer<>nil then begin
for i:=0 to ListOfCodeBuffer.Count-1 do begin
CurCode:=TCodeBuffer(ListOfCodeBuffer[i]);
if CurCode=ACodeBuffer then break;
s:=CurCode.Filename;
CurrentListBox.Items.Insert(0,s);
end;
ListOfCodeBuffer.Free;
end;
if CodeToolBoss.GetIdentifierAt(ACodeBuffer,
NewIdentifierPosition.X,NewIdentifierPosition.Y,NewIdentifier) then
begin
CurrentGroupBox.Caption:=Format(lisFRIIdentifier, [NewIdentifier]);
NewEdit.Text:=NewIdentifier;
end;
// check if in implementation or private section
if CodeToolBoss.Explore(ACodeBuffer,Tool,false) then begin
CodeXY:=CodeXYPosition(NewIdentifierPosition.X,NewIdentifierPosition.Y,ACodeBuffer);
if Tool.CaretToCleanPos(CodeXY,CleanPos)=0 then begin
Node:=Tool.BuildSubTreeAndFindDeepestNodeAtPos(CleanPos,false);
if (Node=nil)
or Node.HasParentOfType(ctnImplementation)
or Node.HasParentOfType(ctnClassPrivate) then
IsPrivate:=true;
end;
end;
end;
end;
end.