Hello,
I want to make something like windows explorer. So the easy part first. I added these:

ShellTreeView1: TShellTreeView;
    ShellListView1: TShellListView;
    ShellComboBox1: TShellComboBox;

I connected them and everything is good. I can see files and I can navigate folders, drivers, e.t.c. I changed the ViewStyle attribute of ShellListView1 to vsReport. This is the "Details" Option in windows explorer. With the vsReport attribute you can see these records: "Name" - "Size" - "Type" - "Date Modified" of every file.

Example: http://img371.imageshack.us/img371/9803/ex1ox3.jpg

If the item in ListView is folder, it diplays 'File Folder' under the "Type" column. If it's a file, it diplays the file type. What I want to do is change the "File Folder" to "Super Folder" and change the file type to "Super File". So I changed the 'OnChange' event of the ShellTreeView1 and added the following code:

procedure TForm1.ShellTreeView1Change(Sender: TObject; Node: TTreeNode);
var i:word;
    li : TListItem;
begin

  if ShellListView1.Items.Count > 0 then
  begin

    for i:=0 to ShellListView1.Items.Count-1 do
    Begin
      li:=ShellListView1.Items.Item[i];
      MessageDlg(li.SubItems[1],mtError,[mbOk],0); 
    end;
  end;

end;

With this code I can "read" the Type Column for every file/folder in a folder. But when I add, after the MessageDlg, this code: li.SubItems.Insert(1,'Super Folder: '); It doesn't change the "File Folder"/File Type to "Super Folder: " as it should. Any ideas how I could implement it?

Recommended Answers

All 21 Replies

I dont understand your onchange code for the list view, it goes through and shows a dialog with the sub item yes?

So whatever you select I guess would get an item under the item with index 1, of super folder? Nothing else would change... it would just add a new item under the item with index 1 entry..

I dont understand your onchange code for the list view, it goes through and shows a dialog with the sub item yes?

Yes, it goes through the listbox and shows a dialog with the value in "Type" column for every file/folder. For example, in the picture that I mentioned in my first post, it will display dialogs with values: "File Folder", "MS-DOS Batch File", "Application", e.t.c. (1 dialog for every item under the red arrow). I just added it so that I can know that the application can read the values correctly, cause I want to change these value.

So whatever you select I guess would get an item under the item with index 1, of super folder? Nothing else would change... it would just add a new item under the item with index 1 entry..

When I select a folder from the treeviw (at the left) then this procedure is triggered so that I can change the listbox (at the right). I need it to change the value of "Type" column to "Super Folder" for every file/folder in the listbox.

OK but

li.SubItems.Insert(1,'Super Folder: ');

You would need to trace whats going on, because that inserts, not replaces current data..

Oh, sometimes insert means replace. Try using insert in ms word ^^

Anyway. Here's an example to see that Insert works, or at least it should work. Make a new application and add a listview and a button. Press alt+F12 to view form's source code and change to this:

object Form1: TForm1
  Left = 0
  Top = 0
  Width = 356
  Height = 298
  Caption = 'Form1'
  Color = clBtnFace
  Font.Charset = DEFAULT_CHARSET
  Font.Color = clWindowText
  Font.Height = -11
  Font.Name = 'Tahoma'
  Font.Style = []
  OldCreateOrder = False
  PixelsPerInch = 96
  TextHeight = 13
  object ListView1: TListView
    Left = 8
    Top = 8
    Width = 329
    Height = 185
    Columns = <
      item
        Caption = 'Tets1'
      end
      item
        Caption = 'Test2'
      end
      item
        Caption = 'Test3'
      end>
    TabOrder = 0
    ViewStyle = vsReport
  end
  object Button1: TButton
    Left = 24
    Top = 208
    Width = 297
    Height = 41
    Caption = 'Try Me'
    TabOrder = 1
    OnClick = Button1Click
  end
end

Then add this as button's click function

procedure TForm1.Button1Click(Sender: TObject);
var ListItem:TListItem;
begin
  ListItem:=ListView1.Items.Add;
  ListItem.Caption:='Value1';
  ListItem.SubItems.Add('Value2');
  ListItem.SubItems.Add('Value3');
  ListItem.SubItems.Insert(0,'Value4');
end;

You won't see Value2, but only Value4. This is because it replaces it. The point is that something prevents me from changing the item from ShellListView and I don't know what it is.

its not overwriting

add another column, its still there...

So, which function do you think I should use?

You want to take the first subitem, and change its caption.

Ok then, I replace this: ListItem.SubItems.Insert(0,'Value4'); with this: ListView1.Items.Item[0].SubItems[0]:='Value4'; It works fine, doesn't it?

But it doesn't work with the initial application. In the ShellTreeView1Change procedure I change:

for i:=0 to ShellListView1.Items.Count-1 do
    Begin
      li:=ShellListView1.Items.Item[i];
      MessageDlg(li.SubItems[1],mtError,[mbOk],0); 
    end;

to

for i:=0 to ShellListView1.Items.Count-1 do
    Begin
      li:=ShellListView1.Items.Item[i];
      li.SubItems[1]:='Super Folder';
    end;

And it still doesn't work.

No, I wouldnt expect that to, SubItems[1] is not a string. Its a ListItem.

li (or ShellListView1.Items.Item or ListView1.Items.Item[0]) is a ListItem. (actually TListItem)
li.SubItems is TStrings
li.SubItems[1] is String (if it wasnt then i would be able to compile the program)

Did you try to run the initial application and found a working solution or do you just say things from your knowledge?

If you had read my post you will know I had run your code.. hence I proved its not overwriting it.

However, you seem determind to not follow any debugging or truth.

You mean the 2nd application (post 5) is not overwriting and it's just inserting the item. But if you change ListItem.SubItems.Insert(0,'Value4'); to ListView1.Items.Item[0].SubItems[0]:='Value4'; then it will overwrite it. But this seems not to work for the 1rst one (post1). Right?

But your first post doesnt *DO* what you wanted it to do, firstly it inserts into the 3rd column of your tree, not the second, and also it doesnt overwrite it adds ...

So, given you now have code (that works as your last post would work) why not just "use" the correct code?

I typed in post #9 that i change the code and use this one now:

for i:=0 to ShellListView1.Items.Count-1 do
    Begin
      li:=ShellListView1.Items.Item[i];
      li.SubItems[1]:='Super Folder';
    end;

But it still doesn't work, although it works for the (2nd) example application. Can you try the code in the 1rst post and see if it works for you (after making any change you think it would need)? Cause I don't think you can change the listview's value in my first post's code.

PS: I know that this thread may take a little longer that you'd think it would need, but I hope that you won't stop the efforts as you mention in your signature :P

ok, but one thing important is you're changing *ALL* the values to super folder in that loop, and once again you're changing item 1, not item 0...

I'm changing the values of 1 item for every row.

In this picture: http://img371.imageshack.us/img371/9803/ex1ox3.jpg we have:

subitems[0] -> Size
subitems[1] -> Type
subitems[2] -> Date Modified

Anyway, what I want to do is change at least one element of the listview (i dont really care if i change item 1 or 0). Cause I don't think it will let me change anything in the TShellListView (that's why i made this thread). That's why I'm asking you if you can to run the application in my 1rst post and try to change any value in the TShellListView.

Well. The fact the one you told me to paste in works perfectly well means theres something else wrong in your code.

Do you mean the code in the post #1 or #5 works? Is there something wrong in my code or is it that TShellListView is a custom listview and I need a different way to work with it?

Chances are then its the TShellListView, as you proved the standard one works fine

While reading contetns from listview it is generating an exception after few items have been read,Why so? anybody has solution?

You should create a new topic...and post some code...

I would suspect that you are going past the index of your listview...the listview is 0 based...so you should never access any Item past ListView1.Items.Count -1.

Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.