Question

I am writing an AutoIt script which attempts to open an application (Vision). When this application is open, the script intends to access an option from the menu which in turn causes another window within the same application to be opened. After configuring and saving some settings, the control is again returned back to the main window in the application (Vision). I intend to automate this whole thing using AutoIt. However, WinActivate() behaves weirdly. How do I resolve this?

The following is my code:

Dim $num, $file_name, $opening_file
$num = 1
$file_name = "Hello"
$opening_file = "Vision - [" & $file_name & "]"
Opt("WinTitleMatchMode", 2);
AutoItSetOption ("TrayIconDebug", 1);0-off
Local $pid_handle = ProcessExists("Vision.exe")

If $pid_handle Then
    ProcessClose($pid_handle)
Endif

Run("C:\Program Files\Vision.exe")
WinWait("Vision - [Start Page]")
WinWaitActive("Vision")
SendKeepActive("Vision")
sleep(3000)
Send("!f")
Send("n")
WinWait("Capture Options - ")
WinWaitActive("Capture Options - ")
SendKeepActive("Capture Options")
ControlClick("Capture Options", "", 32494)
sleep(1000)
ControlSetText("Capture Options", "", 1487, $file_name, "")
Send("{DOWN}")
Send("{Tab}")
WinActivate("Capture Options - ")
ControlClick("Capture Options", "", 32494)
sleep(1000)
Send("{DOWN}{Tab}")
ControlCommand("Capture Options", "", 1471, "ShowDropDown", "")

If $num = 1 Then
    ControlCommand("Capture Options", "", 1471, "SelectString", "1 - here u go")
Elseif $num = 2 Then
    ControlCommand("Capture Options", "", 1471, "SelectString", "2 - blah blah..")
EndIf

sleep(2000)
Send("{ENTER}")
ControlClick("Capture Options", "", 1)

sleep(1000)
WinActivate("Vision")
WinWaitActive("Vision")
SendKeepActive("Vision")
sleep(2000)
Send("^!y")

The problems that I face are as follows:

a) Though the Vision.exe gets opened using the Run() command, if I happen to click on some other window [GUI/Desktop/Browser], the Vision GUI loses focus and the AutoIt script gets stuck up at WinWaitActive() line forever and never returns. Isn't AutoIt supposed to bring the focus onto the Vision GUI by itself?

This way, I see the whole of my automation script fail, if I happen to meddle with the system when it just about happened to open the Vision GUI. How do I fix this?

b) As I said earlier, the flow that needs to happen is: Vision GUI gets opened. Using Alt + F or similar commands, I happen to open another dialog box in the GUI. This causes some configuration settings to be applied. I save, and I return back to the vision GUI main window. Now the problem that I face here is that sometimes the Vision GUI's main window is never activated by AutoIt and here too I end up waiting on the WinWaitActive line. Isn't it supposed to have activated Vision main window before reaching the second line?

WinActivate("Vision")
WinWaitActive("Vision")
SendKeepActive("Vision")
sleep(2000)
Send("^!y")
Was it helpful?

Solution

Two main problems... First for your point a) you should just use WinWait instead and then you can use WinActivate to set it as the active one. After WinActivate you don't need to use WinWaitActive - you can check its return code instead.

Second for point b) you need to behave kind of the same way. You can (with absolute care) use BlockInput(True) before you start activating your Window and then sending some keystrokes, etc to prevent the user from "stealing" the Window Focus. And after you are finished, you should immediately use BlockInput(False). However, it might still occur, that some other application pops up and becomes the active window... For this, you might check for your active window always before perfoming something with it... But it's much better for such cases to try to use the Control... functions because they don't depend on the window to be the active one...

And finally, you should just once determine your windows handle ($handle = WinExists("Vision")) at the topmost possibility and then just use its handle for further usage of Win... functions like WinGetTitle($handle). Because especially when you open popup windows within your application, they might have the same word in its title. So it might not be sure that your commands are being executed with the window you suppose them to be. After getting the PID of your newly run window you might consider using it to receive its windows handle - there are functions in the AutoIt forums to receive a handle from a PID. So you can be sure to use the exact window you are supposing to use.

Oh - and the usage of control IDs is really bad. Who can assure you, they won't change? Use some control names instead... see the section about "extended control title definition" or so in the documentation for these possibilities...

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top