Home Page

 

IT

 

Developer

 

Virtual Treeview

type declaration * form create * initialize the tree * init node * init children * get text * get image * free node * additional code

For the tree view to work, there needs to be a record structure that will store the data for our nodes. This is, in fact, the node element itself and the Virtual Treeview actually lets us to define whatever node we want. No limits on what properties we want the node to contain.
The node in this case contains only a pointer to an object. This case is useful if there is already an existing hierarchical structure and we want to use the existing elements instead of copying everything to a treeview. I have linked the tree node to an xml node, which ties a treeview to an xml structure.

type
    PMyRec = ^TMyRec;
    TMyRec = record
        my_object :TdomNode;
    end;

The tree view has to be initialized. This is best to put in FormCreate

vst.NodeDataSize := SizeOf(TMyRec);
vst.RootNodeCount := 0;

When you want to initialize the tree, put

vst.addChild(nil);

or

vst.RootNodeCount = 1;

to create the rood node(s). This can be either in FormCreate or after loading the tree or whereever. The next important event is OnInitNode, where the node is initialized. Some interesting attributes that can be used in this procedure are:

Sender.GetNodeLevel(Node)
Include(InitialStates, ivsHasChildren);
Include(InitialStates, ivsExpanded);

OnFreeNode you should dispose of any objects attached to the record. OnGetText is used to retrieve and display the text for your node. The resulting code may look something like the following:

var
    my_node :PMyRec;
begin
    my_node := vst.GetNodeData( Node );
    if assigned(my_node) then
        if my_node.my_object = nil then
            CellText := 'empty node'
        else
            CellText := my_node.my_object.nodeName;
end;

OnImageIndex is used to retrieve the icon index that will be used for the node.

case Kind of
    ikNormal:
        ImageIndex := 0;
    ikSelected:
        imageindex := 1;
    ikState:
        imageindex := 2;
    ikOverlay:
        ImageIndex := 3;
end;
 

OnInitChilden is used to initialize the child nodes for the current node.

var
    Data: PMyRec;

begin
   
Data := Sender.GetNodeData(Node);
    if Data.Level < LevelCount then
        ChildCount := 5;
end;

 


Some additional useful code pieces:

if ParentNode = nil then
    InitialStates := InitialStates + [ivsHasChildren, ivsExpanded];