Ceci est une ancienne révision du document !
Virtual Tree View
Fonctionnement
Les TVirtualTrees contiennent un ensemble de Node (de type PVirtualNode).
Chaque Node contient un membre Data TVirtualNode.Data (Data: record end;
)
Ce Data contient la donnée a gérer pour ce nœud.
En general la donnée est un record qui peut contenir n'importe quoi , par exemple…
TTreeData = record Text: String; URL: string[255]; ImageIndex: integer; end; PTreeData = ^TTreeData;
On déclare aussi un type pointer vers TTreeData (PTreeData
) qui nous sera utile plus tard…
Initialisation
Il faut initialiser le TVirtualTree en lui disant la taille des noeuds grace a NodeDataSize
procedure TForm1.FormCreate(Sender: TObject); begin VSTMain.NodeDataSize := SizeOf(TTreeData); end;
Sinon ça bug dans tous les sens…
Ajout d'un Noeud
Pour ajouter un noeud :
procedure TForm1.FormCreate(Sender: TObject); var pNode: PVirtualNode; pData: PTreeData; begin VSTMain.BeginUpdate; pNode := VSTMain.AddChild(nil); pData := VSTMain.GetNodeData(pNode); pData^.Text := 'root'; VSTMain.EndUpdate; end;
Affichage d'un Noeud
Affichage du texte du noeud
Lors du dessin du composant, le TVirtualTree se sert de l'evenement OnGetText
pour recuperer le texte a afficher.
procedure TForm1.VSTMainGetText(Sender: TBaseVirtualTree; Node: PVirtualNode; Column: TColumnIndex; TextType: TVSTTextType; var CellText: String); var pData: PTreeData; begin pData := VST.GetNodeData(Node); case Column of 0: CellText:= IntToStr(pData^.id); 1: CellText:= IntToStr(pData^.Flags); 2: CellText:= IntToStr(pData^.Current); 3: CellText:= IntToStr(pData^.Worst); end; end;
Affichage des images/icones
On peut mettre deux images avant le texte du noeud.
- L'image “Normale”, dont le
TImageList
sera stocké dans la propertyimages
et la largeur définie dans la propetyimagesWidth
. - L'image “State”, dont le
TImageList
sera stocké dans la propertyStateImages
et la largeur définie dans la propetyStateImagesWidth
.
Lorsque le VST veux récupérer l'index de l'image à afficher, le paramètre Kind
contient l'information du type d'image qu'il souhaite:
ikNormal
: L'image “Normale”ikSelected
: L'image “Normale” quand la ligne est séléctionnéeikState
: L'image “State”ikOverlay
: …..
Le paramètre Column
contient l'index de la colonne pour laquelle il veut l'ImageIndex.
procedure TFrameVSTDisks.VSTGetImageIndex(Sender: TBaseVirtualTree; Node: PVirtualNode; Kind: TVTImageKind; Column: TColumnIndex; var Ghosted: boolean; var ImageIndex: integer); var pData: PTreeData; begin pData := VST.GetNodeData(Node); ImageIndex := -1; case Column of C_COL_DEVICE: case Kind of ikState: ImageIndex := -1; ikNormal,ikSelected: ImageIndex := pData^.Img; end; C_COL_SMART: case Kind of ikState: ImageIndex := -1; ikNormal,ikSelected: ImageIndex := pData^.SmartImg; end; end; end;
Expanded
Un noeud
VSTMain.Expanded[FRootNode]:=true;
Tout
VST.FullExpand; VST.FullCollapse;
Tri
Le tri d'une colonne peut etre déclenché par :
- Click sur l’entête de la colonne. Dans ce cas l'option
Header/Options/hoHeaderClickAutoSort
doit etre àTrue
. - Appel a la procédure Sort :
VST.Sort(Node,Column,Sens);
Pour comparer les nœuds le VST utilise l'event OnCompareNodes
{ Exemple simpliste sans prise en compte de l'index de la column } procedure TFrameVSTDisks.VSTCompareNodes(Sender: TBaseVirtualTree; Node1, Node2: PVirtualNode; Column: TColumnIndex; var Result: Integer); var pD1,pD2: PTreeData; begin pD1:= VST.GetNodeData(Node1); pD2:= VST.GetNodeData(Node2); Result:=0; // Les noeud sont égaux if pD1^.Index>pD2^.Index then Result:=1; // node1>node2 -> Result= 1 if pD1^.Index<pD2^.Index then Result:=-1; // node1<node2 -> Result= -1 end;
Ressources pour le tri :
Selection
GetFirstSelected
function TForm1.GetSelectedMarker: TMarker; var pNode: PVirtualNode; pData: PVSTMarkData; begin pNode:=VSTMark.GetFirstSelected; pData:=VSTMark.GetNodeData(pNode); Result:=pData^.Marker; end;
Modifications
BeginUpdate / EndUpdate
Lorsque l'on met a jour un VST, il est bon pour l'affichage et la rapidité d'entourer ces mises a jour par un BeginUpdate
et un EndUpdate
.
VST.BeginUpdate; try ... finally VST.EndUpdate; end;
Déstruction du VST
OnFreeNode
procedure TForm1.VSTMainFreeNode(Sender: TBaseVirtualTree; Node: PVirtualNode); var Data: PTreeData; begin Data := VSTMain.GetNodeData(Node); Finalize(Data^); end;
On en parle ici :https://www.remkoweijnen.nl/blog/2010/06/09/memory-leaks-when-using-virtual-treeview-component/
Plus d'infos sur Finalize()
: https://www.freepascal.org/docs-html/rtl/system/finalize.html
On voit aussi…
procedure TForm1.VSTMainFreeNode(Sender: TBaseVirtualTree; Node: PVirtualNode); var Data: PTreeData; begin Data := VSTMain.GetNodeData(Node); Data^.Text:=''; Data^.URL:=''; end;