Board index » delphi » ListView and SubItems...

ListView and SubItems...

Hello,

I am working on a small application to display running processes on my system. This part I have working (on borrowed
code mostly) very well. I even have the process names and paths where I want them (in different columns).

My problem is the rest of the information. With the code I have dug up out of the Win32 help file and some other code
from sources on the internet, I can gather OTHER information about these running processes like PID number, Heap ID, how
many threads, and so on.

How can I take the rest of the information that I can gather and add it to the appropriate column in the ListView?

For instance:

KERNEL32.DLL is running from C:\WINDOWS\SYSTEM\ and has a PID of 20934556 and is running with 13 threads.

I want this information to display like this in the ListView:

Process         Threads         PID             Path
------------            -------------           ------          --------
Kernel32.dll    13              20934556        C:\Windows\System\

It seems that the ONLY thing I can get to work right is the Process Name and the Path. Those are easy, as I just use
ExtractFileName() and ExtractFilePath() to display that information. But, I cannot get the PID, Threads, etc to show up
correctly.

Here is the code I am using, as I said, borrowed from another person.

{=================== Begin Code =============================}
procedure TForm1.updatelabels;          // synch the UI with the internal process list
begin
  if listbox1.itemindex <> -1 then
    if assigned(listbox1.items.objects[listbox1.itemindex]) then
      with procObject(listbox1.items.objects[listbox1.itemindex]) do
        begin
          with TheProc do
            begin
              theflags.caption := inttostr(dwFlags);
              thecount.caption := inttostr(cntUsage);
              theprocid.caption := inttostr(th32ProcessID);
              theheapid.caption := inttostr(th32DefaultHeapID);
              themodid.caption := inttostr(th32DefaultHeapID); //This is the stuff that I need to show correctly
              thethreads.caption := inttostr(cntthreads);
              theparent.caption := inttostr(th32ParentProcessID);
            end;
          with ThePrio do
            case procpriority of
              4: ItemIndex := 0;        // the only possible priority values
              8: ItemIndex := 1;        // are 4, 8, 13, and 24
              13: ItemIndex := 2;
              24: ItemIndex := 3;
            end;
          // only enable process kills if something is selected
          KillEnabled := true;
        end
end;
(********************************************************************************************)

procedure Tform1.LookForExes;
var
  Proc: TProcessEntry32;
  Snap: THandle;
  prochandle: procObject;
  tempname: string;
  oldindex: integer;
begin
  oldindex := listbox1.ItemIndex;       // save old listbox position
  if listbox1.items.count - 1 < oldindex then // check to see if any processes have been killed
    dec(oldindex);                      // and update the index accordingly
  EmptyListbox;                         // clear UI list
  try
    listbox1.items.BeginUpdate;         // disable screen refreshes during update
    listbox1.items.clear;
    try
      // API calls. Picked from someone on the Borland NG's. Sorry ... forgot the name.
      Snap := CreateToolHelp32SnapShot(TH32CS_SNAPALL, 0); // API in ToolHelp.pas (dcu)
      Proc.dwSize := SizeOf(TProcessEntry32);
      Process32First(Snap, Proc);
      repeat
        prochandle := procObject.create(proc);
        if length(string(Proc.szExeFile)) > 0 then // check for processes without a description
          tempname := proc.szExeFile
        else
          tempname := '< Unknown >';
        listbox1.items.addobject(tempname, prochandle); // save the process object to the list
      until (not Process32Next(Snap, Proc));
    except
      showmessage('An error occurred while reading task information');
    end;
  finally
    if listbox1.Items.Count > 0 then    // set listbox position to old position - 1
      begin
        if oldindex > 0 then
          listbox1.ItemIndex := oldindex
        else
          listbox1.ItemIndex := 0;
      end
    else
      KillEnabled := false;
    listbox1.items.endupdate;           // reenable screen updates
  end;
end;
{=================== End Code =============================}

Many thanks, as always, in advance!

Ryan

 

Re:ListView and SubItems...


Set ListView1.ViewStyle to vsReport and use:

var
  Item: TListItem;
begin
  with ListView1.Add do
  begin
    Caption := ProcessName;
    SubItems.Add(IntToStr(ThreadCount));
    SubItems.Add(IntToStr(ProcessID));
    SubItems.Add(ProcessPath);
  end;
end;

ps. For Windows NT you'll have to use the functions from the PSApi unit
(instead of the functions from the TLHelp32 unit). You can find a C++
example of how to do this on
http://support.microsoft.com/support/kb/articles/Q175/0/30.asp.

"Ryan Styles" <ner...@d.cat> schreef in bericht
news:f191dt8odcp7mk6nt32itr4qgn48bddj80@4ax.com...

Quote
> Hello,

> I am working on a small application to display running processes on my

system. This part I have working (on borrowed
Quote
> code mostly) very well. I even have the process names and paths where I

want them (in different columns).
Quote

> My problem is the rest of the information. With the code I have dug up out

of the Win32 help file and some other code
Quote
> from sources on the internet, I can gather OTHER information about these

running processes like PID number, Heap ID, how
Quote
> many threads, and so on.

> How can I take the rest of the information that I can gather and add it to

the appropriate column in the ListView?
Quote

> For instance:

> KERNEL32.DLL is running from C:\WINDOWS\SYSTEM\ and has a PID of 20934556

and is running with 13 threads.
Quote

> I want this information to display like this in the ListView:

> Process Threads PID Path
> ------------ ------------- ------ --------
> Kernel32.dll 13 20934556 C:\Windows\System\

> It seems that the ONLY thing I can get to work right is the Process Name

and the Path. Those are easy, as I just use
Quote
> ExtractFileName() and ExtractFilePath() to display that information. But,

I cannot get the PID, Threads, etc to show up
Quote
> correctly.

> Here is the code I am using, as I said, borrowed from another person.

> {=================== Begin Code =============================}
> procedure TForm1.updatelabels;          // synch the UI with the internal
process list
> begin
>   if listbox1.itemindex <> -1 then
>     if assigned(listbox1.items.objects[listbox1.itemindex]) then
>       with procObject(listbox1.items.objects[listbox1.itemindex]) do
>         begin
>           with TheProc do
>             begin
>               theflags.caption := inttostr(dwFlags);
>               thecount.caption := inttostr(cntUsage);
>               theprocid.caption := inttostr(th32ProcessID);
>               theheapid.caption := inttostr(th32DefaultHeapID);
>               themodid.caption := inttostr(th32DefaultHeapID); //This is

the stuff that I need to show correctly

- Show quoted text -

Quote
>               thethreads.caption := inttostr(cntthreads);
>               theparent.caption := inttostr(th32ParentProcessID);
>             end;
>           with ThePrio do
>             case procpriority of
>               4: ItemIndex := 0;        // the only possible priority
values
>               8: ItemIndex := 1;        // are 4, 8, 13, and 24
>               13: ItemIndex := 2;
>               24: ItemIndex := 3;
>             end;
>           // only enable process kills if something is selected
>           KillEnabled := true;
>         end
> end;

(***************************************************************************
*****************)
Quote

> procedure Tform1.LookForExes;
> var
>   Proc: TProcessEntry32;
>   Snap: THandle;
>   prochandle: procObject;
>   tempname: string;
>   oldindex: integer;
> begin
>   oldindex := listbox1.ItemIndex;       // save old listbox position
>   if listbox1.items.count - 1 < oldindex then // check to see if any

processes have been killed

- Show quoted text -

Quote
>     dec(oldindex);                      // and update the index
accordingly
>   EmptyListbox;                         // clear UI list
>   try
>     listbox1.items.BeginUpdate;         // disable screen refreshes during
update
>     listbox1.items.clear;
>     try
>       // API calls. Picked from someone on the Borland NG's. Sorry ...
forgot the name.
>       Snap := CreateToolHelp32SnapShot(TH32CS_SNAPALL, 0); // API in
ToolHelp.pas (dcu)
>       Proc.dwSize := SizeOf(TProcessEntry32);
>       Process32First(Snap, Proc);
>       repeat
>         prochandle := procObject.create(proc);
>         if length(string(Proc.szExeFile)) > 0 then // check for processes

without a description
Quote
>           tempname := proc.szExeFile
>         else
>           tempname := '< Unknown >';
>         listbox1.items.addobject(tempname, prochandle); // save the

process object to the list

- Show quoted text -

Quote
>       until (not Process32Next(Snap, Proc));
>     except
>       showmessage('An error occurred while reading task information');
>     end;
>   finally
>     if listbox1.Items.Count > 0 then    // set listbox position to old
position - 1
>       begin
>         if oldindex > 0 then
>           listbox1.ItemIndex := oldindex
>         else
>           listbox1.ItemIndex := 0;
>       end
>     else
>       KillEnabled := false;
>     listbox1.items.endupdate;           // reenable screen updates
>   end;
> end;
> {=================== End Code =============================}

> Many thanks, as always, in advance!

> Ryan

Other Threads