有没有一种方法可以用VBScript计算所有打开的窗口?

时间:2019-11-29 22:00:24

标签: vbscript

我想知道是否可以用vbscript计算给定时间打开的窗口数量。我已经熟悉shell.application对象,并且可以计算Windows资源管理器实例,但是无论它是什么,我都希望对每个窗口(最小化或最大化)进行计数。 我还考虑过要计算所有正在运行的任务,但是我需要以某种方式区分后台任务和前台任务才能使之正常工作。

function fnShellWindowsCountVB()
        dim objShell
        dim objShellWindows

        set objShell = CreateObject("shell.application")
        set objShellWindows = objshell.Windows

        if (not objShellWindows is nothing) then
            dim nCount
            nCount = objShellWindows.Count

            msgBox nCount
        end if

        set objShellWindows = nothing
        set objShell = nothing
end function
fnShellWindowsCountVB()

'only counts explorer.exe windows

任何见识都会受到赞赏。

1 个答案:

答案 0 :(得分:2)

不,您不能使用VBScript。

您必须进行API调用才能使用窗口执行任何操作。

VB.Net可以进行API调用,并且像VBScript一样内置在Windows中。

这是来自https://winsourcecode.blogspot.com/2019/05/winlistexe-list-open-windows-and-their.html

它列出了所有打开的窗口,您将拥有几百个。可能您只对顶级窗口感兴趣。

EG记事本是5个窗口。 1个顶层,1个“编辑”控制窗口,1个状态栏窗口以及两个标准窗口,所有程序都可以自动获取这些窗口以处理输入中文文本等。

WinList.exe列出打开的窗口及其子窗口的窗口标题,窗口类和EXE文件

请注意,您必须以管理员身份运行才能访问有关高架窗口的信息。

REM WinList.bat
 REM This file compiles WinList.vb to WinList.exe
 REM WinList.exe list the open windows and their child windows' Window Title, Window Class, and the EXE file that created the window. 
 REM To use type WinList in a command prompt
 C:\Windows\Microsoft.NET\Framework\v4.0.30319\vbc "%~dp0\WinList.vb" /out:"%~dp0\WinList.exe" /target:exe
 Pause




 ---------------------------------------------------------------------------------






'WinList.vb
 imports System.Runtime.InteropServices 
 Public Module WinList  

 Public Declare Function GetTopWindow Lib "user32" (ByVal hwnd As IntPtr) As IntPtr
 Public Declare Function GetWindow Lib "user32" (ByVal hwnd As IntPtr, ByVal wCmd As Integer) As IntPtr
 Public Declare UNICODE Function GetWindowModuleFileNameW Lib "user32" (ByVal hwnd As IntPtr, ByVal WinModule As String, StringLength As Integer) As Integer
 Public Declare UNICODE Function GetWindowTextW Lib "user32" (ByVal hwnd As IntPtr, ByVal lpString As String, ByVal cch As Integer) As Integer
 Public Declare Function GetWindowThreadProcessId Lib "user32" (ByVal hwnd As IntPtr, ByRef lpdwProcessId As IntPtr) As IntPtr
 Public Declare UNICODE Function GetClassNameW Lib "user32" (ByVal hwnd As IntPtr, ByVal lpClassName As String, ByVal nMaxCount As Integer) As Integer
 Public Declare Function IsWindowUnicode Lib "user32" (ByVal hwnd As IntPtr) As Boolean
 Public Const GW_CHILD = 5
 Public Const GW_HWNDNEXT = 2

 Public Sub Main ()
        Dim WindowChain as Integer
            WindowChain = 0        
        Dim hwnd As IntPtr
        hwnd = GetTopWindow(0)
        If hwnd <> 0 Then
                            AddChildWindows(hwnd, 0)
                End If
 End Sub


 Private Sub AddChildWindows(ByVal hwndParent As IntPtr, ByVal Level As Integer) 
        Dim objWMIService As Object
        Dim colItems As Object
        Dim TempStr As String        
        Dim WT As String, CN As String, Length As Integer, hwnd As IntPtr, TID As IntPtr, PID As IntPtr, MN As String, Parenthwnd As IntPtr
        Static Order As Integer
        Static FirstTime As Integer
        Parenthwnd = hwndParent
        If Level = 0 Then
                        hwnd = hwndParent
        Else
            hwnd = GetWindow(hwndParent, GW_CHILD)
        End If
        Do While hwnd <> 0
                 WT = Space(512)
                  Length = GetWindowTextW(hwnd, WT, 508)
                  WT = Left$(WT, Length)
                  If WT = "" Then WT = Chr(171) & "No Window Text" & Chr(187)
                  CN = Space(512)
                  Length = GetClassNameW(hwnd, CN, 508)
                  CN = Left$(CN, Length)
                  If CN = "" Then CN = "Error=" & Err.LastDllError
                  MN = ""

                  TID = GetWindowThreadProcessId(hwnd, PID)

        objWMIService = GetObject("winmgmts:\\.\root\cimv2")
        colItems = objWMIService.ExecQuery("Select * From Win32_Process where ProcessID=" & CStr(PID))
        For Each objItem in colItems        
                MN = objItem.name 
        Next                           
                Dim Unicode  as Boolean
        Unicode = IsWindowUnicode(hwnd)

                  Order = Order + 1
                If FirstTime = 0 Then
                    Console.writeline("Window Text                   " & "Class Name               " & vbTab & "Unicode" & vbtab & "HWnd" & vbTab & "ParentHWnd" & vbTab & "ProcessID" & vbTab & "ThreadID" & vbTab & "Process Name" )
                    FirstTime = 1
                End If
        TempStr = vbCrLf & Space(Level * 3) & WT 
        If 30 - len(TempStr) > -1 then
                TempStr = TempStr & space(30 - len(TempStr))
        End If
        TempStr = TempStr & " " & CN 
        If 55 - len(TempStr) > -1 then
                TempStr = TempStr & space(55 - len(TempStr))
        End If
                Console.write(TempStr  & vbtab & Unicode & vbTab & CStr(hwnd) & vbTab & CStr(Parenthwnd) & vbTab & CStr(PID) & vbTab & CStr(TID) & vbTab & MN )

                  AddChildWindows(hwnd, Level + 1)
                  hwnd = GetWindow(hwnd, GW_HWNDNEXT)
        Loop
      End Sub

 End Module