VBS没有等待.Run命令完成

时间:2014-07-14 15:35:59

标签: vbscript cmd

我有一个代码会自动打开Personalization窗口,将主题更改为Windows 7 Basic,然后关闭窗口。问题是,运行命令完成后窗口没有关闭。我使用的代码是:

Set WshShell = WScript.CreateObject("WScript.Shell")

WshShell.Run "rundll32.exe %SystemRoot%\system32\shell32.dll,Control_RunDLL %SystemRoot%\system32\desk.cpl desk,@Themes /Action:OpenTheme /file:""C:\Windows\Resources\Ease of Access Themes\basic.theme""",1,true

WshShell.AppActivate("Desktop Properties") 
WshShell.Sendkeys "%FC"
WshShell.Sendkeys "{F4}"

现在,使用" true"最后的陈述,它是否应该基本等待这个命令完成,那么它会继续下去吗?因为如果我删除" true"声明以及" 1"最后,而是添加一个计时器,如:

Set WshShell = WScript.CreateObject("WScript.Shell")

WshShell.Run "rundll32.exe %SystemRoot%\system32\shell32.dll,Control_RunDLL %SystemRoot%\system32\desk.cpl desk,@Themes /Action:OpenTheme /file:""C:\Windows\Resources\Ease of Access Themes\basic.theme"""


Wscript.Sleep 5000
WshShell.AppActivate("Desktop Properties") 
WshShell.Sendkeys "%FC"
WshShell.Sendkeys "{F4}"

仅在此处它将等待任务完成,然后关闭窗口。我究竟做错了什么!此外,有人可以准确地解释"%FC"和" {F4}"做?我知道其中一个关闭窗口,但我很难找到他们的意思。提前谢谢!!

1 个答案:

答案 0 :(得分:1)

我希望我知道它的真正原因,但似乎脚本是按设计工作的。 RunDll32.exe必须将处理传递给另一个进程,这就是为什么脚本似乎继续而不等待的原因。我更新了脚本以证明发生了什么

Set WshShell = WScript.CreateObject("WScript.Shell")

msgbox (IsProcessRunning("rundll32.exe"))
WshShell.Run "rundll32.exe %SystemRoot%\system32\shell32.dll,Control_RunDLL %SystemRoot%\system32\desk.cpl desk,@Themes /Action:OpenTheme /file:""C:\Windows\Resources\Ease of Access Themes\basic.theme""",1,true
msgbox (IsProcessRunning("rundll32.exe"))
WshShell.AppActivate("Desktop Properties") 
WshShell.Sendkeys "%FC"
WshShell.Sendkeys "{F4}"

Function IsProcessRunning(pProcessName)
    ' Function will do a WMI query to determine if a the process pProcessName is currently
    ' running on the local computer. Returns True if detected. 
    Dim objWMIService
    Dim strWMIQuery

    strWMIQuery = "Select * From Win32_Process Where name Like '" & pProcessName & "'"
    Set objWMIService = GetObject("winmgmts:{impersonationLevel=impersonate}!\\.\root\cimv2") 

    ' Run The query against the WMI for the local machine
    If (objWMIService.ExecQuery(strWMIQuery).Count > 0) Then
        IsProcessRunning = True
    Else
        IsProcessRunning = False
    End If
End Function

我添加了一个检查进程是否正在运行的函数。一旦你的命令证明它还没有运行。 rundll32.exe调用后也证明它仍然没有运行。虽然这似乎是多余的,但显示第二个False消息框将在主题更改的处理完成之前出现。

旧版MS知识库文章的片段:http://support.microsoft.com/kb/164787

  

Rundll如何运作

     

Rundll执行以下步骤:   1.它解析命令行。   2.它通过LoadLibrary()加载指定的DLL。   3.它通过GetProcAddress()获取函数的地址。   它调用函数,传递命令行尾。   5.当函数返回时,Rundll.exe卸载DLL并退出。

希望有人可以修饰它。