search & replace, added btn to select the scope of "find all"

This commit is contained in:
Basile Burg 2016-01-26 10:36:12 +01:00
parent a8681e3f37
commit 3fdbf6b4be
4 changed files with 215 additions and 90 deletions

BIN
icons/file/document_all.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 317 B

View File

@ -1067,6 +1067,20 @@ LazarusResources.Add('document_plus','PNG',[
+#159'8Ej'#12#255'/'#187#148#251#229#151#0#3#0'7'#190#22'@6n'#188'T'#0#0#0#0 +#159'8Ej'#12#255'/'#187#148#251#229#151#0#3#0'7'#190#22'@6n'#188'T'#0#0#0#0
+'IEND'#174'B`'#130 +'IEND'#174'B`'#130
]); ]);
LazarusResources.Add('document_all','PNG',[
#137'PNG'#13#10#26#10#0#0#0#13'IHDR'#0#0#0#16#0#0#0#16#8#4#0#0#0#181#250'7'
+#234#0#0#0#4'gAMA'#0#0#175#200'7'#5#138#233#0#0#0#25'tEXtSoftware'#0'Adobe I'
+'mageReadyq'#201'e<'#0#0#0#207'IDAT('#207'u'#145'M'#10#194'0'#16'FG='#135'R'
+#207'P'#218#30#195'3'#184#243':E'#23#30#193'#'#184'q'#163#208#222#192'C("'
+#180#218#159#180#240'9'#153#180'i'#10#149#15#134#132'y'#188'0'#25#162#21#5#20
+#218'x4'#7#185'!'#10'T'#221'B'#167'A'#137'}LkZ'#140#129#176#229#198#29#23#156
+#145#226#138#221#137'6'#174'G'#128#10'7(L{'#4'P'#12#252#243#8#208' '#193#216
+#163'o'#135'X#'#29#144'b'#240#228'x'#227#193#167#2'G'#141#12'@'#239')'#144
+#225#217'yxp'#23'0'#181#194#151#145#151'X,'#144'X'#192' '#133'<4i0H'#205#200
+#167#3'<.'#17'm{'#143#137'b'#164'4'#0'O:'#227'a"'#215#160#207'JF'#22'@'#254
+#203'zt'#179#143#3#12#30'7uN'#254'x'#181#158#179'x'#29#159#150'?,?X'#234#201
+'.Yw'#0#0#0#0'IEND'#174'B`'#130
]);
LazarusResources.Add('folder','PNG',[ LazarusResources.Add('folder','PNG',[
#137'PNG'#13#10#26#10#0#0#0#13'IHDR'#0#0#0#16#0#0#0#16#8#6#0#0#0#31#243#255'a' #137'PNG'#13#10#26#10#0#0#0#13'IHDR'#0#0#0#16#0#0#0#16#8#6#0#0#0#31#243#255'a'
+#0#0#0#25'tEXtSoftware'#0'Adobe ImageReadyq'#201'e<'#0#0#2#26'IDATx'#218#164 +#0#0#0#25'tEXtSoftware'#0'Adobe ImageReadyq'#201'e<'#0#0#2#26'IDATx'#218#164

View File

@ -1,26 +1,26 @@
inherited CESearchWidget: TCESearchWidget inherited CESearchWidget: TCESearchWidget
Left = 742 Left = 742
Height = 282 Height = 287
Top = 278 Top = 278
Width = 394 Width = 393
Caption = 'Search & replace' Caption = 'Search & replace'
ClientHeight = 282 ClientHeight = 287
ClientWidth = 394 ClientWidth = 393
inherited Back: TPanel inherited Back: TPanel
Height = 282 Height = 287
Width = 394 Width = 393
ClientHeight = 282 ClientHeight = 287
ClientWidth = 394 ClientWidth = 393
inherited Content: TPanel inherited Content: TPanel
Height = 282 Height = 287
Width = 394 Width = 393
ClientHeight = 282 ClientHeight = 287
ClientWidth = 394 ClientWidth = 393
object cbToFind: TComboBox[0] object cbToFind: TComboBox[0]
Left = 4 Left = 4
Height = 23 Height = 23
Top = 4 Top = 4
Width = 386 Width = 385
Align = alTop Align = alTop
AutoSize = False AutoSize = False
BorderSpacing.Around = 4 BorderSpacing.Around = 4
@ -32,8 +32,8 @@ inherited CESearchWidget: TCESearchWidget
object btnFind: TBitBtn[1] object btnFind: TBitBtn[1]
Left = 4 Left = 4
Height = 24 Height = 24
Top = 170 Top = 167
Width = 386 Width = 385
Align = alBottom Align = alBottom
BorderSpacing.Around = 4 BorderSpacing.Around = 4
Caption = 'btnFind' Caption = 'btnFind'
@ -78,8 +78,8 @@ inherited CESearchWidget: TCESearchWidget
object btnReplace: TBitBtn[2] object btnReplace: TBitBtn[2]
Left = 4 Left = 4
Height = 24 Height = 24
Top = 226 Top = 195
Width = 386 Width = 385
Align = alBottom Align = alBottom
BorderSpacing.Around = 4 BorderSpacing.Around = 4
Caption = 'btnReplace' Caption = 'btnReplace'
@ -123,14 +123,14 @@ inherited CESearchWidget: TCESearchWidget
end end
object grpOpts: TGroupBox[3] object grpOpts: TGroupBox[3]
Left = 4 Left = 4
Height = 108 Height = 105
Top = 58 Top = 58
Width = 386 Width = 385
Align = alClient Align = alClient
BorderSpacing.Around = 4 BorderSpacing.Around = 4
Caption = 'Options' Caption = 'Options'
ClientHeight = 78 ClientHeight = 75
ClientWidth = 382 ClientWidth = 381
TabOrder = 4 TabOrder = 4
object chkWWord: TCheckBox object chkWWord: TCheckBox
Left = 8 Left = 8
@ -190,8 +190,8 @@ inherited CESearchWidget: TCESearchWidget
object btnReplaceAll: TBitBtn[4] object btnReplaceAll: TBitBtn[4]
Left = 4 Left = 4
Height = 24 Height = 24
Top = 254 Top = 259
Width = 386 Width = 385
Align = alBottom Align = alBottom
BorderSpacing.Around = 4 BorderSpacing.Around = 4
Caption = 'btnReplaceAll' Caption = 'btnReplaceAll'
@ -237,18 +237,18 @@ inherited CESearchWidget: TCESearchWidget
Left = 4 Left = 4
Height = 23 Height = 23
Top = 31 Top = 31
Width = 386 Width = 385
Align = alTop Align = alTop
BorderSpacing.Around = 4 BorderSpacing.Around = 4
BevelOuter = bvNone BevelOuter = bvNone
ClientHeight = 23 ClientHeight = 23
ClientWidth = 386 ClientWidth = 385
TabOrder = 5 TabOrder = 5
object cbReplaceWth: TComboBox object cbReplaceWth: TComboBox
Left = 108 Left = 108
Height = 23 Height = 23
Top = 0 Top = 0
Width = 278 Width = 277
Align = alClient Align = alClient
Anchors = [akTop, akLeft, akBottom] Anchors = [akTop, akLeft, akBottom]
ItemHeight = 0 ItemHeight = 0
@ -267,12 +267,22 @@ inherited CESearchWidget: TCESearchWidget
TabOrder = 0 TabOrder = 0
end end
end end
object btnFindAll: TBitBtn[6] object Panel2: TPanel[6]
Left = 0
Height = 32
Top = 223
Width = 393
Align = alBottom
BevelOuter = bvNone
ClientHeight = 32
ClientWidth = 393
TabOrder = 6
object btnFindAll: TBitBtn
Left = 4 Left = 4
Height = 24 Height = 24
Top = 198 Top = 4
Width = 386 Width = 352
Align = alBottom Align = alClient
BorderSpacing.Around = 4 BorderSpacing.Around = 4
Caption = 'btnFindAll' Caption = 'btnFindAll'
Glyph.Data = { Glyph.Data = {
@ -311,7 +321,18 @@ inherited CESearchWidget: TCESearchWidget
FF00FFFFFF00FFFFFF00FFFFFF00FFFFFF00FFFFFF00FFFFFF00FFFFFF00FFFF FF00FFFFFF00FFFFFF00FFFFFF00FFFFFF00FFFFFF00FFFFFF00FFFFFF00FFFF
FF00FFFFFF00FFFFFF00FFFFFF00FFFFFF00FFFFFF00FFFFFF00 FF00FFFFFF00FFFFFF00FFFFFF00FFFFFF00FFFFFF00FFFFFF00
} }
TabOrder = 6 TabOrder = 0
end
object btnAllScope: TBitBtn
Left = 360
Height = 24
Top = 4
Width = 29
Align = alRight
BorderSpacing.Around = 4
OnClick = btnAllScopeClick
TabOrder = 1
end
end end
end end
end end

View File

@ -8,7 +8,7 @@ uses
Classes, SysUtils, FileUtil, Forms, Controls, Graphics, Dialogs, ExtCtrls, Classes, SysUtils, FileUtil, Forms, Controls, Graphics, Dialogs, ExtCtrls,
Menus, StdCtrls, actnList, Buttons, SynEdit, SynEditSearch, SynEditTypes, Menus, StdCtrls, actnList, Buttons, SynEdit, SynEditSearch, SynEditTypes,
ce_common, ce_mru, ce_widget, ce_synmemo, ce_interfaces, ce_observer, ce_common, ce_mru, ce_widget, ce_synmemo, ce_interfaces, ce_observer,
ce_writableComponent, ce_dialogs, strutils; ce_writableComponent, ce_dialogs, ce_sharedres;
type type
@ -43,7 +43,8 @@ type
end; end;
{ TCESearchWidget } { TCESearchWidget }
TCESearchWidget = class(TCEWidget, ICEMultiDocObserver) TCESearchWidget = class(TCEWidget, ICEMultiDocObserver, ICEProjectObserver)
btnAllScope: TBitBtn;
btnFind: TBitBtn; btnFind: TBitBtn;
btnFindAll: TBitBtn; btnFindAll: TBitBtn;
btnReplace: TBitBtn; btnReplace: TBitBtn;
@ -60,6 +61,8 @@ type
grpOpts: TGroupBox; grpOpts: TGroupBox;
imgList: TImageList; imgList: TImageList;
Panel1: TPanel; Panel1: TPanel;
Panel2: TPanel;
procedure btnAllScopeClick(Sender: TObject);
procedure cbReplaceWthChange(Sender: TObject); procedure cbReplaceWthChange(Sender: TObject);
procedure cbToFindChange(Sender: TObject); procedure cbToFindChange(Sender: TObject);
procedure chkEnableRepChange(Sender: TObject); procedure chkEnableRepChange(Sender: TObject);
@ -75,21 +78,31 @@ type
fCancelAll: boolean; fCancelAll: boolean;
fHasSearched: boolean; fHasSearched: boolean;
fHasRestarted: boolean; fHasRestarted: boolean;
fProj: ICECommonProject;
fAllInProj: boolean;
function getOptions: TSynSearchOptions; function getOptions: TSynSearchOptions;
procedure actReplaceAllExecute(sender: TObject); procedure actReplaceAllExecute(sender: TObject);
procedure replaceEvent(Sender: TObject; const ASearch, AReplace: procedure replaceEvent(Sender: TObject; const ASearch, AReplace:
string; Line, Column: integer; var ReplaceAction: TSynReplaceAction); string; Line, Column: integer; var ReplaceAction: TSynReplaceAction);
protected //
procedure updateImperative; override; procedure projNew(aProject: ICECommonProject);
public procedure projChanged(aProject: ICECommonProject);
constructor Create(aOwner: TComponent); override; procedure projClosing(aProject: ICECommonProject);
destructor Destroy; override; procedure projFocused(aProject: ICECommonProject);
procedure projCompiling(aProject: ICECommonProject);
// //
procedure docNew(aDoc: TCESynMemo); procedure docNew(aDoc: TCESynMemo);
procedure docClosing(aDoc: TCESynMemo); procedure docClosing(aDoc: TCESynMemo);
procedure docFocused(aDoc: TCESynMemo); procedure docFocused(aDoc: TCESynMemo);
procedure docChanged(aDoc: TCESynMemo); procedure docChanged(aDoc: TCESynMemo);
// //
procedure findAll(const filename: string; lines: TStrings);
protected
procedure updateImperative; override;
public
constructor Create(aOwner: TComponent); override;
destructor Destroy; override;
//
procedure actFindNextExecute(sender: TObject); procedure actFindNextExecute(sender: TObject);
procedure actReplaceNextExecute(sender: TObject); procedure actReplaceNextExecute(sender: TObject);
procedure actFindAllExecute(sender: TObject); procedure actFindAllExecute(sender: TObject);
@ -215,6 +228,7 @@ begin
btnReplace.Action := fActReplaceNext; btnReplace.Action := fActReplaceNext;
btnReplaceAll.Action := fActReplaceAll; btnReplaceAll.Action := fActReplaceAll;
btnFindAll.Action := fActFindAll; btnFindAll.Action := fActFindAll;
AssignPng(btnAllScope, 'document');
updateImperative; updateImperative;
// //
EntitiesConnector.addObserver(self); EntitiesConnector.addObserver(self);
@ -271,6 +285,37 @@ begin
end; end;
procedure TCESearchWidget.actFindAllExecute(sender: TObject); procedure TCESearchWidget.actFindAllExecute(sender: TObject);
var
i: integer;
syn: TSynEdit;
fnm: string;
begin
if fDoc.isNil and not fAllInProj then
exit;
if (fProj = nil) and fAllInProj then
exit;
//
fSearchMru.Insert(0,fToFind);
cbToFind.Items.Assign(fSearchMru);
//
if fAllInProj then
begin
syn := TSynEdit.Create(nil);
try
for i := 0 to fProj.sourcesCount-1 do
begin
fnm := fProj.sourceAbsolute(i);
syn.Lines.LoadFromFile(fnm);
findAll(fnm, syn.Lines);
end;
finally
syn.Free;
end;
end
else findAll(fDoc.fileName, fDoc.Lines);
end;
procedure TCESearchWidget.findAll(const filename: string; lines: TStrings);
var var
search: TSynEditSearch; search: TSynEditSearch;
options: TSynSearchOptions; options: TSynSearchOptions;
@ -282,11 +327,6 @@ var
i: integer; i: integer;
res: array of TPoint = nil; res: array of TPoint = nil;
begin begin
if fDoc.isNil then exit;
//
fSearchMru.Insert(0,fToFind);
cbToFind.Items.Assign(fSearchMru);
//
search := TSynEditSearch.Create; search := TSynEditSearch.Create;
try try
options := getOptions; options := getOptions;
@ -294,10 +334,12 @@ begin
search.Whole := ssoWholeWord in options; search.Whole := ssoWholeWord in options;
search.RegularExpressions:= ssoRegExpr in options; search.RegularExpressions:= ssoRegExpr in options;
search.Pattern:=fToFind; search.Pattern:=fToFind;
search.IdentChars:=fDoc.IdentChars;
// search.IdentChars:= [];
start := Point(1,1); start := Point(1,1);
stop := Point(high(integer), fDoc.Lines.Count); stop := Point(high(integer), lines.Count);
while search.FindNextOne(fDoc.Lines, start, stop, startf, stopf) do while search.FindNextOne(lines, start, stop, startf, stopf) do
begin begin
setLength(res, length(res) + 1); setLength(res, length(res) + 1);
res[high(res)].X := startf.X; res[high(res)].X := startf.X;
@ -307,10 +349,10 @@ begin
msgs := getMessageDisplay; msgs := getMessageDisplay;
msg := format('%d result(s) for the pattern <%s>', [length(res), fToFind]); msg := format('%d result(s) for the pattern <%s>', [length(res), fToFind]);
msgs.message(msg, nil, amcMisc, amkInf); msgs.message(msg, nil, amcMisc, amkInf);
fmt := fDoc.fileName + '(%d,%d): "%s"'; fmt := fileName + '(%d,%d): "%s"';
for i := 0 to high(res) do for i := 0 to high(res) do
begin begin
msg := format(fmt, [res[i].Y, res[i].X, Trim(fDoc.Lines.Strings[res[i].Y-1])]); msg := format(fmt, [res[i].Y, res[i].X, Trim(lines.Strings[res[i].Y-1])]);
msgs.message(msg, nil, amcMisc, amkInf); msgs.message(msg, nil, amcMisc, amkInf);
end; end;
finally finally
@ -413,6 +455,35 @@ begin
end; end;
{$ENDREGION} {$ENDREGION}
{$REGION ICEProjectObserver ----------------------------------------------------}
procedure TCESearchWidget.projNew(aProject: ICECommonProject);
begin
fProj := aProject;
updateImperative;
end;
procedure TCESearchWidget.projChanged(aProject: ICECommonProject);
begin
end;
procedure TCESearchWidget.projClosing(aProject: ICECommonProject);
begin
if fProj = aProject then
fProj := nil;
updateImperative;
end;
procedure TCESearchWidget.projFocused(aProject: ICECommonProject);
begin
fProj := aProject;
updateImperative;
end;
procedure TCESearchWidget.projCompiling(aProject: ICECommonProject);
begin
end;
{$ENDREGION}
{$REGION ICEMultiDocObserver ---------------------------------------------------} {$REGION ICEMultiDocObserver ---------------------------------------------------}
procedure TCESearchWidget.docNew(aDoc: TCESynMemo); procedure TCESearchWidget.docNew(aDoc: TCESynMemo);
begin begin
@ -461,14 +532,33 @@ begin
updateImperative; updateImperative;
end; end;
procedure TCESearchWidget.updateImperative; procedure TCESearchWidget.btnAllScopeClick(Sender: TObject);
begin begin
fAllInProj := not fAllInProj;
if fAllInProj then
begin
AssignPng(btnAllScope, 'document_all');
btnAllScope.Hint := 'all project sources';
end
else
begin
AssignPng(btnAllScope, 'document');
btnAllScope.Hint := 'selected source';
end;
updateImperative;
end;
procedure TCESearchWidget.updateImperative;
var
canAll: boolean;
begin
canAll := (fDoc.isNotNil and not fAllInProj) or (fAllInProj and (fProj <> nil));
btnFind.Enabled := fDoc.isNotNil and fToFind.isNotEmpty; btnFind.Enabled := fDoc.isNotNil and fToFind.isNotEmpty;
btnFindAll.Enabled := fDoc.isNotNil and fToFind.isNotEmpty; btnFindAll.Enabled := canAll;
btnReplace.Enabled := fDoc.isNotNil and chkEnableRep.Checked and fToFind.isNotEmpty; btnReplace.Enabled := fDoc.isNotNil and chkEnableRep.Checked and fToFind.isNotEmpty;
btnReplaceAll.Enabled := btnReplace.Enabled; btnReplaceAll.Enabled := btnReplace.Enabled;
cbReplaceWth.Enabled := fDoc.isNotNil and chkEnableRep.Checked; cbReplaceWth.Enabled := fDoc.isNotNil and chkEnableRep.Checked;
cbToFind.Enabled := fDoc.isNotNil; cbToFind.Enabled := canAll;
end; end;
{$ENDREGION} {$ENDREGION}