Skocz do zawartości


[Delphi] Dodawanie elementow do TreeView w opdowiedni sposób


5 odpowiedzi w tym temacie

#1 olesio

    Ekspert

  • Super użytkownicy
  • 363 Postów:
  • Gadu-Gadu:478088

Napisano sob, 01 lis 2008 - 21:34

Witam. Piszę również na to forum, bo można zawsze liczyć na Waszą pomoc smile.gif

Nie jestem zbytnio wprawiony w obsłudze TreeView, a chciałem zrobić jedną rzecz.
Aianowicie mam plik a.txt, który wygląda na przykłąd tak jak poniżej:

KOD
arts\artIcons_1\ace.ico
arts\artIcons_1\arabesque.ico
arts\artIcons_2\magichat.ico
arts\artIcons_2\mouse.ico
sport\baseball_caps\al umpire.ico
sport\baseball_caps\texas rangers.ico
sport\f1_helmets\alessandro.ico
sport\f1_helmets\ayrton.ico

To co po ostatnim \ to nazwa ikony, ale ona jest nieważna. Ilość wpisów jest
zawsze różna. Chce uzyskać taki efekt, aby moje drzewo wygladalo nastepująco:

KOD
arts
|- articons_1
|- artIcons_2

sport
|- baseball_caps
|- f1_helmets

Czy ktoś może robił coś podobnego i ma przykładowy kod jak to zrobić, bo ja chcę
żeby program jak spotka po "arts\" nowy wpis (na przykłąd "sports\") to stworzy
nowy głowny item, a to co jest późniiej po \ będzie subitemem czyli tylko raz ma
byc artIcons_1, później artIcons_2 i tak dalej. Kombinowałem z takim kodem jak
ten poniżej ale on tworzy takie drzewo jak poniżej czyli powtarza wpisy, a tego
nie chce. Jakby ktoś miał pomysł jak to zrobić to proszę o podzielnie sie kodem.

Mój kod póki co wygląda tak. Na kóncu następuje rozwinięcie wszystkich gałęzi:
delphi


var
  I, X : integer;
  SL : TStringList;
  TN : TTreeNode;
  OldDir, Dir, Sciezka : string;
begin
  SL := TStringList.Create;
  SL.LoadFromFile('a.txt');
  I := 0;
  repeat
  Sciezka := (SL[I]);
  OldDir := Copy(Sciezka, 1, Pos('', Sciezka) - 1);
    if I [ SL.Count - 1 then
    begin
    X := Pos('', SL[I+1]) + 1;
    Dir := Copy(SL[I+1], X, MaxInt);
    X := Length(Dir);
       while Dir[X] [] '' do
       begin
       Delete(Dir, X, 1);
       X := X - 1;
       end;
     Delete(Dir, Length(Dir), 1);
     end;

  if Dir [] OldDir then
  begin
  TN := TreeView1.Items.Add(nil, OldDir);
  TreeView1.Items.AddChild(TN, Dir);
  end;
Inc(I);
until I = SL.Count;

// Rozszerzenie wszystkich gałęzi
  for I := 0 to TreeView1.Items.Count - 1 do
  begin
  TreeView1.Items[I].Expand(False);
  end;

// Ustawienie zaznaczenia na samą górę
  TreeView1.Items[0].Selected := True;
  TreeView1.Items[0].Expand(False);
end;
 

 

I tworzy taką listę:
Obrazek

#2 Force

    Nowy na forum

  • Super użytkownicy
  • 1138 Postów:

Napisano sob, 01 lis 2008 - 22:13

No tak, jak masz:

if Dir [] OldDir then
begin
TN := TreeView1.Items.Add(nil, OldDir);
TreeView1.Items.AddChild(TN, Dir);
end;
to nie rób od razu:
TN := TreeView1.Items.Add(nil, OldDir);
ale sprawdź czy masz w TreeView1 węzeł główny z OldDir, jak tak to przypisz go do TN-a

#3 olesio

    Ekspert

  • Super użytkownicy
  • 363 Postów:
  • Gadu-Gadu:478088

Napisano sob, 01 lis 2008 - 22:27

Dziękuje za szybką odpowiedź
Pisałem takze na 4p dlatego zamieniałem znaczniki i zamiast [] powinno być <>

Cytat

No tak, jak masz:
to nie rób od razu:
TN := TreeView1.Items.Add(nil, OldDir);
ale sprawdź czy masz w TreeView1 węzeł główny z OldDir, jak tak to przypisz go do TN-a

Mógłbym prosić o przykładowy kod? Bo nie bardzo wiem jak takie sprawdzenie zrobić.

#4 Cubixmeister

    Starszy bywalec

  • Super użytkownicy
  • 125 Postów:
  • Gadu-Gadu:3817607

Napisano sob, 01 lis 2008 - 23:49

Masz gotowca.
Przed chwilą pisane, nie testowałem dokładnie, ale wygląda na to, że jest w porządku... tongue.gif
Masz tutaj obsługę dla nieograniczonej głębokości sub-gałęzi.

delphi

procedure TForm1.Button1Click(Sender: TObject);

  Function GetNode(const Text: String; Owner: TTreeNodes; Parent: TTreeNode): TTreeNode;
  var i: integer;
  begin
    if (Trim(Text) = '') then
        begin
          Result:= Parent;
          Exit;
        end
      else
        Result:= nil;

    for i:=0 to Parent.Count-1 do
      if (Parent[i].Text = Text) then
        begin
          Result:= Parent[i];
          Break;
        end;

    if not Assigned(Result) then
      Result:= Owner.AddChild(Parent, Text);
  end;

var i, offset, p: integer;
    Data: TStrings;
    Node: TTreeNode;
begin
  Data:= Memo1.Lines;
  TreeView1.Items.Clear;
  TreeView1.Items.AddChildFirst(nil, 'root');

  for i:=0 to Data.Count-1 do
    begin
      Node:= TreeView1.Items.GetFirstNode;
      offset:= 1;
      p:= Pos('', Data[i]);
      while (p > 0) do
        begin
          Node:= GetNode( Copy(Data[i], offset, p-offset), TreeView1.Items, Node);
          Offset:= p+1;
          p:= PosEx('', Data[i], offset);
        end;
    end;
end;

 


#5 olesio

    Ekspert

  • Super użytkownicy
  • 363 Postów:
  • Gadu-Gadu:478088

Napisano nie, 02 lis 2008 - 01:11

Serdeczne dzięki Cubixmeister. Super smile.gif Działa idealnie.
Na Was można liczyć, szybka i konkretna odpowiedź.

#6 Henryk555

    Nowy na forum

  • Użytkownicy
  • 6 Postów:

Napisano pon, 01 wrz 2014 - 11:23

A ja mam inne pytanie dotyczące TreeView .... Jesli można, oczywiście :)
Znalazłem kod "Fing node by text" Działa , jest oki ale ... Chciałbym aby programowo można było wyszukać Root by text i ... o ile znajdzie go program, niech rozwinie ew. istniejące gałązki tylko tego root ! Ktoś łaskawie pomoże ? <_<