Microsoft sort of has a built-in GUI for VBScript in the form of HTA “applications.” HTA is, in a nutshell, web pages — HTML and CSS — that don’t launch in Explorer and run VBScripts. The only problem is, for some reason Microsoft decided, in all its wisdom, that HTAs could run all wscript code, except wscript.sleep — perhaps one of the most useful commands, used to slow code down or wait for other processes to finish.
Now, I poked around for a fix to this, figuring someone had come up with a good loophole. To be sure, there are many ways cobbled together to use wscript.sleep in an HTA, but none of them were very tidy. Calls to nonexistant IPs, a web of nested functions, or useless bits of code were hard to implement, and not one of them could be done within a single sub or function. In short, there was no workaround that said, like wscript.sleep, “Hold on for a few seconds… Okay, now you can go.”
Then it hit me: Why not call an external VBScript that does nothing but accept an argument for the number of seconds to wait, then wscript.sleep for that long? This script could then be called from the HTA with a simple shell command, with parameters set to hide the called script and — most important — not continue executing the current script until that shell command has completed.
So here’s my fix. Here’s the easiest way to call wscript.sleep in an HTA without actually using wscript.sleep. Put this in the HTA at the point you need a pause:
objShell.Run(”wscript.exe sleep.vbs 10000″,0,True)
Of course, you have to first create the shell object to run the command, but the parameters of the actual call are thus:
- wscript.exe — the application to run (in our case, Windows script/VBScript)
- sleep.vbs — the file to open with the aforementioned application (more on this in a second)
- 10000 — the amount of time to sleep (in this case, 10 seconds — the time is given in milliseconds)
All of those go in quotes, with the spaces between each element — it’s just like typing the command via the command line.
- The 0 value says, “Don’t show this application running” — i.e., don’t open a new window.
- The True value tells the VBScript in the HTA not to continue until the shell command has completed.
That’s it for the code in the HTA. Now for the sleep.vbs file we’re calling. This is the code, in full:
Option explicit
Dim ArgObj, vSeconds
‘create the object to get the seconds variable
Set ArgObj = WScript.Arguments
vSeconds = ArgObj(0)
set ArgObj = Nothing
‘ call wscript.sleep
wscript.sleep(vSeconds) ‘<– wait the length of time input
‘ that’s all folks!
If you copy-n-paste that into a text editor and name the file “sleep.vbs,” then call it as shown above, your HTA will pause for 10 seconds without spawning new windows or twiddling around with fake IPs and complex functions. Yes, it’s a lot of code just to use wscript.sleep, but it beats anything else I’ve found. Your mileage may vary — please let me know.