mystiq
Nov 23rd, 1999, 09:37 AM
I read the API tip about getting the current task list, but that lists EVERYTHING. Can i modify the function (below) or use a different one to return only the processes that are actual programs Windows lists on the task bar?
For arguments sake, im attempting to write a replacement for the taskbar.
Function GetTaskList() As String
Dim CurrWnd As Long
Dim Length As Long
Dim TaskName As String
Dim Parent As Long
Dim Ret As String
Dim NumTasks As Byte
Ret = Chr(0)
CurrWnd = GetWindow(frmMain.hwnd, GW_HWNDFIRST)
While CurrWnd <> 0
Parent = GetParent(CurrWnd)
Length = GetWindowTextLength(CurrWnd)
TaskName = Space$(Length + 1)
Length = GetWindowText(CurrWnd, TaskName, Length + 1)
TaskName = Left$(TaskName, Len(TaskName) - 1)
If Length > 0 Then
If TaskName <> frmMain.Caption Then
Ret = Ret & TaskName & Chr(0)
NumTasks = NumTasks + 1
End If
End If
CurrWnd = GetWindow(CurrWnd, GW_HWNDNEXT)
DoEvents
Wend
On Error GoTo 0
Ret = NumTasks & Ret
GetTaskList = Ret
End Function
------------------
-Mystiq
Serge
Nov 23rd, 1999, 06:28 PM
With the code you have, it will shows you all open windows, not programs (Processes) running. Since Windows95/98 and WindowsNT have different approach to get all processes running, I wrote generic function which will get you all processes according to the operating system you're currently running on.
Module Code
Public Declare Function Process32First Lib "kernel32" (ByVal hSnapshot As Long, lppe As PROCESSENTRY32) As Long
Public Declare Function Process32Next Lib "kernel32" (ByVal hSnapshot As Long, lppe As PROCESSENTRY32) As Long
Public Declare Function CloseHandle Lib "Kernel32.dll" (ByVal Handle As Long) As Long
Public Declare Function OpenProcess Lib "Kernel32.dll" (ByVal dwDesiredAccessas As Long, ByVal bInheritHandle As Long, ByVal dwProcId As Long) As Long
Public Declare Function EnumProcesses Lib "psapi.dll" (ByRef lpidProcess As Long, ByVal cb As Long, ByRef cbNeeded As Long) As Long
Public Declare Function GetModuleFileNameExA Lib "psapi.dll" (ByVal hProcess As Long, ByVal hModule As Long, ByVal ModuleName As String, ByVal nSize As Long) As Long
Public Declare Function EnumProcessModules Lib "psapi.dll" (ByVal hProcess As Long, ByRef lphModule As Long, ByVal cb As Long, ByRef cbNeeded As Long) As Long
Public Declare Function CreateToolhelp32Snapshot Lib "kernel32" (ByVal dwFlags As Long, ByVal th32ProcessID As Long) As Long
Public Declare Function GetVersionExA Lib "kernel32" (lpVersionInformation As OSVERSIONINFO) As Long
Public Type PROCESSENTRY32
dwSize As Long
cntUsage As Long
th32ProcessID As Long ' This process
th32DefaultHeapID As Long
th32ModuleID As Long ' Associated exe
cntThreads As Long
th32ParentProcessID As Long ' This process's parent process
pcPriClassBase As Long ' Base priority of process threads
dwFlags As Long
szExeFile As String * 260 ' MAX_PATH
End Type
Public Type OSVERSIONINFO
dwOSVersionInfoSize As Long
dwMajorVersion As Long
dwMinorVersion As Long
dwBuildNumber As Long
dwPlatformId As Long '1 = Windows 95, 2 = Windows NT
szCSDVersion As String * 128
End Type
Public Const PROCESS_QUERY_INFORMATION = 1024
Public Const PROCESS_VM_READ = 16
Public Const MAX_PATH = 260
Public Const STANDARD_RIGHTS_REQUIRED = &HF0000
Public Const SYNCHRONIZE = &H100000
'STANDARD_RIGHTS_REQUIRED Or SYNCHRONIZE Or &HFFF
Public Const PROCESS_ALL_ACCESS = &H1F0FFF
Public Const TH32CS_SNAPPROCESS = &H2&
Public Const hNull = 0
Public Function GetRunningProcesses() As Variant
Dim arrProc()
Dim intIndex As Integer
Dim lRet As Long
Select Case getVersion()
Case 1 'Windows 95/98
Dim strProcess As String
Dim hSnap As Long, udtProc As PROCESSENTRY32
hSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0)
If hSnap = hNull Then Exit Function
udtProc.dwSize = Len(udtProc)
' Iterate through the processes
lRet = Process32First(hSnap, udtProc)
Do While lRet
strProcess = StripNulls(udtProc.szExeFile)
ReDim Preserve arrProc(intIndex)
arrProc(intIndex) = strProcess
intIndex = intIndex + 1
lRet = Process32Next(hSnap, udtProc)
Loop
Case 2 'Windows NT
Dim lcb As Long, lcbNeeded As Long, lNumElements As Long
Dim lProcessIDs() As Long, lcbNeeded2 As Long
Dim lModules(1 To 200) As Long
Dim strModuleName As String
Dim lSize As Long, lhProcess As Long, i As Long
'Get the array containing the process id's for each process object
lcb = 8
lcbNeeded = 96
Do While lcb <= lcbNeeded
lcb = lcb * 2
ReDim lProcessIDs(lcb / 4) As Long
lRet = EnumProcesses(lProcessIDs(1), lcb, lcbNeeded)
Loop
lNumElements = lcbNeeded / 4
For i = 1 To lNumElements
'Get a handle to the Process
lhProcess = OpenProcess(PROCESS_QUERY_INFORMATION _
Or PROCESS_VM_READ, 0, lProcessIDs(i))
'Got a Process handle
If lhProcess <> 0 Then
'Get an array of the module handles for the specified
'process
lRet = EnumProcessModules(lhProcess, lModules(1), 200, _
lcbNeeded2)
'If the Module Array is retrieved, Get the ModuleFileName
If lRet <> 0 Then
strModuleName = Space(MAX_PATH)
lSize = 500
lRet = GetModuleFileNameExA(lhProcess, lModules(1), _
strModuleName, lSize)
ReDim Preserve arrProc(intIndex)
arrProc(intIndex) = Left(strModuleName, lRet)
intIndex = intIndex + 1
End If
End If
'Close the handle to the process
lRet = CloseHandle(lhProcess)
Next
End Select
GetRunningProcesses = arrProc
End Function
Function StripNulls(pstrString As String) As String
StripNulls = Left(pstrString, InStr(pstrString, vbNullChar) - 1)
End Function
Public Function getVersion() As Long
Dim udtOSVersion As OSVERSIONINFO
Dim lRet As Integer
udtOSVersion.dwOSVersionInfoSize = 148
udtOSVersion.szCSDVersion = Space$(128)
lRet = GetVersionExA(udtOSVersion)
getVersion = udtOSVersion.dwPlatformId
End Function
Form Code (Requires Listbox - List1 and Commandb button - Command1)
Private Sub Command1_Click()
Dim i As Integer
Dim arrProc()
List1.Clear
arrProc = GetRunningProcesses
For i = 0 To UBound(arrProc)
List1.AddItem arrProc(i)
Next
End Sub
------------------
Serge
Software Developer
Serge_Dymkov@vertexinc.com
Access8484@aol.com
ICQ#: 51055819 (http://www.icq.com/51055819)
[This message has been edited by Serge (edited 11-24-1999).]
mystiq
Nov 24th, 1999, 02:40 AM
I also need a way of finding out if a task is running. Using the enum tasks would be rather slow, and since im writing a replacement for the taskbar, slow is not an option :)
------------------
-Mystiq
mystiq
Nov 24th, 1999, 02:45 AM
On that code that gets the current tasks, how can i convert the process to not just the name of the proc, but the window name.
------------------
-Mystiq