lcl/(Shell)TreeView: Add "FindOptions" so that FindNodeWithTextPath works in TShellTreeView even with collapsed nodes and in case-insensitive file systems.

This commit is contained in:
wp_xyz 2022-11-08 15:55:17 +01:00
parent 9cce03ac94
commit 3f3e32ce9b
3 changed files with 42 additions and 6 deletions

View File

@ -3528,9 +3528,14 @@ type
function AllowMultiSelectWithShift(AState: TShiftState): Boolean; function AllowMultiSelectWithShift(AState: TShiftState): Boolean;
procedure SetExpandSignSize(const AExpandSignSize: integer); procedure SetExpandSignSize(const AExpandSignSize: integer);
procedure SetExpandSignWidth(const AValue: integer); procedure SetExpandSignWidth(const AValue: integer);
protected
type
TFindOption = (foFindIgnoresCase, foFindExpands);
TFindOptions = set of TFindOption;
protected protected
FChangeTimer: TTimer; FChangeTimer: TTimer;
FEditor: TEdit; FEditor: TEdit;
FFindOptions: TFindOptions;
class procedure WSRegisterClass; override; class procedure WSRegisterClass; override;
class function GetControlClassDefaultSize: TSize; override; class function GetControlClassDefaultSize: TSize; override;
procedure Added(Node: TTreeNode); virtual; procedure Added(Node: TTreeNode); virtual;

View File

@ -1406,8 +1406,15 @@ end;
function TTreeNode.FindNode(const NodeText: string): TTreeNode; function TTreeNode.FindNode(const NodeText: string): TTreeNode;
begin begin
Result:=GetFirstChild; Result:=GetFirstChild;
while (Result<>nil) and (Result.Text<>NodeText) do if (foFindIgnoresCase in FOwner.FOwner.FFindOptions) then
Result:=Result.GetNextSibling; begin
while (Result <> nil) and not SameText(Result.Text, NodeText) do
Result := Result.GetNextSibling;
end else
begin
while (Result<>nil) and (Result.Text<>NodeText) do
Result:=Result.GetNextSibling;
end;
end; end;
function TTreeNode.GetTextPath: string; function TTreeNode.GetTextPath: string;
@ -2642,8 +2649,15 @@ end;
function TTreeNodes.FindTopLvlNode(const NodeText: string): TTreeNode; function TTreeNodes.FindTopLvlNode(const NodeText: string): TTreeNode;
begin begin
Result := GetFirstNode; Result := GetFirstNode;
while Assigned(Result) and (Result.Text <> NodeText) do if (foFindIgnoresCase in FOwner.FFindOptions) then
Result := Result.GetNextSibling; begin
while Assigned(Result) and not SameText(Result.Text, NodeText) do
Result := Result.GetNextSibling;
end else
begin
while Assigned(Result) and (Result.Text <> NodeText) do
Result := Result.GetNextSibling;
end;
end; end;
function TTreeNodes.FindNodeWithText(const NodeText: string): TTreeNode; function TTreeNodes.FindNodeWithText(const NodeText: string): TTreeNode;
@ -2655,10 +2669,21 @@ end;
function TTreeNodes.FindNodeWithTextPath(TextPath: string): TTreeNode; function TTreeNodes.FindNodeWithTextPath(TextPath: string): TTreeNode;
var var
p: SizeInt;
CurText: String; CurText: String;
begin begin
Result:=nil; Result := nil;
for CurText in TextPath.Split(FOwner.FPathDelimiter) do
begin
if Result = nil then
Result := FindTopLvlNode(CurText)
else begin
if (foFindExpands in FOwner.FFindOptions) then
Result.Expanded := true;
Result := Result.FindNode(CurText);
end;
end;
{
repeat repeat
p:=System.Pos(FOwner.FPathDelimiter,TextPath); p:=System.Pos(FOwner.FPathDelimiter,TextPath);
if p>0 then begin if p>0 then begin
@ -2674,6 +2699,7 @@ begin
else else
Result:=Result.FindNode(CurText); Result:=Result.FindNode(CurText);
until (Result=nil) or (TextPath=''); until (Result=nil) or (TextPath='');
}
end; end;
function TTreeNodes.FindNodeWithData(const NodeData: Pointer): TTreeNode; function TTreeNodes.FindNodeWithData(const NodeData: Pointer): TTreeNode;

View File

@ -639,6 +639,11 @@ begin
FInitialRoot := ''; FInitialRoot := '';
FUseBuiltinIcons := true; FUseBuiltinIcons := true;
PathDelimiter := SysUtils.PathDelim; PathDelimiter := SysUtils.PathDelim;
{$IFDEF CaseInsensitiveFilenames}
FFindOptions := [foFindExpands, foFindIgnoresCase];
{$ELSE}
FFindOptions := [foFindExpands];
{$ENDIF}
// Initial property values // Initial property values
FObjectTypes:= [otFolders]; FObjectTypes:= [otFolders];