How to select all root or all child nodes in VirtualStringTree?

delphi, delphi-7, tvirtualstringtree, virtualtreeview

Solution

1. Select all root nodes:

To select all root nodes, you can use the following procedure:

procedure SelectRootNodes(AVirtualTree: TBaseVirtualTree);
var
  Node: PVirtualNode;
begin
  AVirtualTree.BeginUpdate;
  try
    Node := AVirtualTree.GetFirst;
    while Assigned(Node) do
    begin
      AVirtualTree.Selected[Node] := True;
      Node := AVirtualTree.GetNextSibling(Node);
    end;
  finally
    AVirtualTree.EndUpdate;
  end;
end;

2. Select all child nodes:

To select all child nodes, level independent, you need to use recursive function like this:

procedure SelectChildNodes(AVirtualTree: TBaseVirtualTree);
var
  Node: PVirtualNode;

  procedure SelectSubNodes(ANode: PVirtualNode);
  var
    SubNode: PVirtualNode;
  begin
    SubNode := AVirtualTree.GetFirstChild(ANode);
    while Assigned(SubNode) do
    begin
      SelectSubNodes(SubNode);
      AVirtualTree.Selected[SubNode] := True;
      SubNode := AVirtualTree.GetNextSibling(SubNode);
    end;
  end;

begin
  AVirtualTree.BeginUpdate;
  try
    Node := AVirtualTree.GetFirst;
    while Assigned(Node) do
    begin
      SelectSubNodes(Node);
      Node := AVirtualTree.GetNextSibling(Node);
    end;
  finally
    AVirtualTree.EndUpdate;
  end;
end;

Problem

I would like to select either all root nodes or all child nodes (not all nodes in a VirtualTreeView). I've tried to use this code to select all root nodes: ``` procedure SelectAllRoots; var Node: PVirtualNode; begin Form1.VirtualStringTree1.BeginUpdate; Node := Form1.VirtualStringTree1.GetFirst; while True do begin if Node = nil then Break; if not (vsSelected in Node.States) then Node.States := Node.States + [vsSelected]; Node := Form1.VirtualStringTree1.GetNext(Node); end; Form1.VirtualStringTree1.EndUpdate; end; ``` I can tell there's a small glitch. The selection is either incomplete or gets stuck. What am I doing wrong ? Edit: I use MultiSelection.

Original source