2017-02-23 52 views
0

У меня есть приложение, которое часто нужно запускать без активного контроля, но если он обнаруживает ошибку, он всплывает окно сообщения и приостанавливается до тех пор, пока пользователь не закроет его. На данный момент это вызывает множество проблем, так как мы испытываем стресс-тесты и не можем отключить эти сообщения, поэтому кто-то должен постоянно следить за процессом. Я пытался придумать VBScript, который будет проверять всплывающее сообщение и автоматически закрывать его, используя функции AppActivate и SendKeys.AppActivate to Close Window not Looping

Проблема в том, что мне нужно это для работы в графическом интерфейсе, чтобы пользователь мог легко запустить/остановить запуск кода одним нажатием кнопки. В настоящее время у меня есть VBScript, завернутый в приложение HTA с помощью одной кнопки, но по какой-то причине он будет закрывать только первый экземпляр сообщения (несколько одновременно могут быть загружены), а затем останавливается.

Sub Testing 
    Set objShell = CreateObject("WScript.Shell") 
    counter = 1 
    Do While counter < 50 
     ret = objShell.AppActivate("Test Failure") 
     counter = counter + 1 
     If ret = True Then 
      objShell.SendKeys "~" 
     End If 
    Loop 
End Sub 

С кнопкой следующим образом:

<input type="button" value="Run Script" name="run_button" onClick="Testing"><p> 

мне нужно просто постоянно работать в фоновом режиме, только выполнение SendKeys, если окно «Test Failure» выбран/присутствует и быть в состоянии остановите цикл при нажатии второй кнопки.

У меня явно что-то не так (VBScript действительно выполняет сверху вниз, не так ли?), И я никогда раньше не играл с этими функциями, но все кажется, что оно правильно настроено.


Я отметил @Ansgar Wiechers так же правильно, как и решил первопричину моей проблемы. Окончательный код, в котором я оказался, состоял из двух частей. Применение:

<!doctype html> 
<head> 
<hta:application 
    id="AutoCloseFailures" 
    applicationname="AutoCloseFailures" 
    icon="" 
    singleinstance="yes" 
    border="thick" 
    borderstyle="complex" 
    scroll="no" 
    maximizebutton="no" 
    version="0.1" /> 
<title>Auto-Close Failure Messages</title> 
<meta http-equiv="x-ua-compatible" content="ie=8"> 
<meta http-equiv="Content-Type" content="text/html; charset=utf-8"> 
</head> 
<script language="VBScript"> 

    ' Set Global Variables for Subroutines 
    script = "#FOLDERPATH#\AutoCloseDEFXErrorsTimer.vbs" 
    Set sh = CreateObject("WScript.Shell") 
    Set cmdTest = Nothing 
    strVar = "testing2" 

    Sub StartLoop 
    ' Initiate VB Loop to Target Failure Windows & Close Them 
     If cmdTest Is Nothing Then 
      Set cmdTest = sh.Exec("wscript.exe """ & script & """") 
      strVar = "testing" 
     End If 
     document.all.start.style.background="#777d84" 
     document.all.start.style.color="#bfc4c9" 
    End Sub 

    Sub StopLoop 
    ' Terminate VB Loop Process & Reset Application 
     strScriptToKill = "AutoCloseDEFXErrorsTimer.vbs" 
     Set objWMIService = GetObject("winmgmts:{impersonationLevel=impersonate}!\\.\root\cimv2") 
     Set colProcess = objWMIService.ExecQuery (_ 
      "Select * from Win32_Process " & _ 
      "WHERE (Name = 'cscript.exe' OR Name = 'wscript.exe') " & _ 
      "AND Commandline LIKE '%"& strScriptToKill &"%'" _ 
     ) 
     For Each objProcess in colProcess 
      objProcess.Terminate() 
     Next 
     Set cmdTest = Nothing 
     document.all.start.style.background="#587286" 
     document.all.start.style.color="#ffffff" 
    End Sub 

    Sub Window_onLoad 
    ' Force Window Size 
     window.resizeTo 400,190 
     window.moveTo 1530, 0 
    End Sub 
</script> 
<style> 
    body { 
     margin: 0; 
     padding: 0; 
     font-family: "Segoe UI", Geneva, sans-serif; 
     background: #dae3f2; 
    } 
    h1 { 
     font-size: 15pt; 
     text-align: center; 
     margin-bottom: 0; 
     color: #273754; 
    } 
    button { 
     padding:16px 32px; 
     font-family:helvetica; 
     font-size:16px; 
     font-weight:100; 
     color:#fff; 
     background: #587286; 
     border:0; 
    } 
    button:hover { 
     background: #3B5C76; 
    } 
    .container { 
     width: 100%; 
     text-align: center; 
    } 
</style> 
<BODY> 
    <h1>Auto-Close Failure Messages</h1> 
    <br> 
     <div class="container"> 
      <button id="start" onclick="StartLoop">Start</button> 
      <span>&nbsp;&nbsp;&nbsp;</span> 
      <button id="stop" onclick="StopLoop">Stop</button> 
     </div> 
    <br> 
</BODY> 
</HTML> 

И Поддерживаемый файл VBScript:

Set sh = CreateObject("WScript.Shell") 
While True 
    active = sh.AppActivate("#WINDOW TITLE#") 
    If active Then 
     sh.SendKeys "~" 
    End If 
    WScript.Sleep 100 
Wend 

ответ

0

Ваша процедура делает 50 итераций без задержки, так что это, вероятно, уже закончена, прежде чем он смог даже добраться до второй инстанции. Что вы обычно сделать, это запустить AppActivate и SendKeys в бесконечном цикле с небольшой задержкой:

Set sh = CreateObject("WScript.Shell") 
While True 
    active = sh.AppActivate("Test Failure") 
    If active Then 
     sh.SendKeys "~" 
    End If 
    WScript.Sleep 100 
Wend 

Пут, что в сценарии, который запускается асинхронно из вашей HTA:

<html> 
<head> 
<title>sample</title> 
<HTA:APPLICATION 
    ID="sample" 
    APPLICATIONNAME="oHTA" 
    SINGLEINSTANCE="yes"> 

<script language="VBScript"> 
script = "C:\path\to\script.vbs" 
Set sh = CreateObject("WScript.Shell") 
Set cmd = Nothing 

Sub StartLoop 
    If cmd Is Nothing Then 
     Set cmd = sh.Exec("wscript.exe """ & script & """") 
    End If 
End Sub 

Sub StopLoop 
    If Not cmd Is Nothing Then 
     cmd.Terminate 
     Set cmd = Nothing 
    End If 
End Sub 
</script> 
</head> 

<body> 
<p> 
<button id="start" onclick="StartLoop">Start</button> 
<button id="stop" onclick="StopLoop">Stop</button> 
</p> 
</body> 
</html> 

Если требуется, может создать внешний скрипт с ОМТ на лету:

Set fso = CreateObject("Scripting.FileSystemObject") 
... 
Set f = fso.OpenTextFile(script, 2, True) 
f.WriteLine "Set sh = CreateObject(""WScript.Shell"")" 
f.WriteLine "While True" 
f.WriteLine "active = sh.AppActivate(""Test Failure"")" 
... 
f.Close 

и удалить его после того, как после окончания:

If Not cmd Is Nothing Then 
    cmd.Terminate 
    Set cmd = Nothing 
    fso.DeleteFile script, True 
End If 
+0

Спасибо! Я подумал, что, возможно, дело, но проверил его, открыв два экземпляра окна и значительно увеличив значение счета, и он все еще не работал ... думаю, он был недостаточно большим! Я только что попробовал ваше предложение, и он работает намного лучше. Моя единственная проблема в том, что когда я прихожу к «остановке» сценария, я получаю сообщение об ошибке «Invalid Window handle» и указывая на эту строку: «cmd.Terminate». Какие-либо предложения? Я буду продолжать играть и обновляться, если я это сделаю. – GnorthernGnome

+0

@GnorthernGnome 'cmd' должно быть установлено в' Nothing' после завершения внешнего скрипта. См. Обновленный ответ. Если это не поможет, отредактируйте свой вопрос и покажите свой измененный код. –

+0

Приносим извинения за задержку, проект внезапно закрепился на некоторое время. Для чего это стоит, установка «cmd» в «Nothing» не сработала, но мне удалось найти решение. Я обновил свой оригинальный пост с окончательным кодом для всех, кого это интересует. Спасибо за вашу помощь. – GnorthernGnome