-
-
Save xiongjia/6749035 to your computer and use it in GitHub Desktop.
#REQUIRES -Version 3.0 | |
# This is a simple sample for access the MS UIAutomation in PowerShell. | |
# In this sample: | |
# 1. Load the MS UIA via System.Reflection.Assembly | |
# 2. Launch the AUT ( calc.exe ) | |
# 3. Find the AutomationElement via the AUT Process Id | |
# 4. Find buttons via 'ClassName' and 'Name' property | |
# 5. Click the '1', '+', '1', '=' buttons. | |
# At last, we will get '2' in the result of calc App. | |
# Load MS UIAutomation assemblies | |
Write-Host "Loading MS UIA assemblies" | |
[void][System.Reflection.Assembly]::LoadWithPartialName("UIAutomationClient") | |
[void][System.Reflection.Assembly]::LoadWithPartialName("UIAutomationTypes") | |
[void][System.Reflection.Assembly]::LoadWithPartialName("UIAutomationProvider") | |
[void][System.Reflection.Assembly]::LoadWithPartialName("UIAutomationClientsideProviders") | |
# Register client side provider | |
Write-Host "Register client-side provider" | |
$client = [System.Reflection.Assembly]::LoadWithPartialName("UIAutomationClientsideProviders") | |
[Windows.Automation.ClientSettings]::RegisterClientSideProviderAssembly($client.GetName()) | |
# Launch the AUT ( calc.exe ) & sleep 10 seconds for wait the process start | |
Write-Host "Launching the AUT" | |
$autProc = Start-Process calc -PassThru | |
Start-Sleep -s 10 | |
# Find the calc Element via the process Id | |
Write-Host "Searching the AUT Root element" | |
$rootElement = [Windows.Automation.AutomationElement]::RootElement | |
$condAUTProc = New-Object Windows.Automation.PropertyCondition([Windows.Automation.AutomationElement]::ProcessIdProperty, $autProc.Id) | |
$autElement = $rootElement.FindFirst([Windows.Automation.TreeScope]::Children, $condAUTProc) | |
# Find the buttons '1', '+', '=' | |
Write-Host "Searching the button elements" | |
$condBtn = New-Object Windows.Automation.PropertyCondition([Windows.Automation.AutomationElement]::ClassNameProperty, "Button") | |
$condName = New-Object Windows.Automation.PropertyCondition([Windows.Automation.AutomationElement]::NameProperty, "1") | |
$condTarget = New-Object Windows.Automation.AndCondition($condBtn, $condName) | |
$btn1Element = $autElement.FindFirst([Windows.Automation.TreeScope]::Descendants, $condTarget) | |
$condName = New-Object Windows.Automation.PropertyCondition([Windows.Automation.AutomationElement]::NameProperty, "+") | |
$condTarget = New-Object Windows.Automation.AndCondition($condBtn, $condName) | |
$btnPlusElement = $autElement.FindFirst([Windows.Automation.TreeScope]::Descendants, $condTarget) | |
$condName = New-Object Windows.Automation.PropertyCondition([Windows.Automation.AutomationElement]::NameProperty, "=") | |
$condTarget = New-Object Windows.Automation.AndCondition($condBtn, $condName) | |
$btnEqualElement = $autElement.FindFirst([Windows.Automation.TreeScope]::Descendants, $condTarget) | |
# Click the buttons | |
Write-Host "Clicking the buttons" | |
$btn1Element.GetCurrentPattern([Windows.Automation.InvokePattern]::Pattern).Invoke() | |
Start-Sleep -s 1 | |
$btnPlusElement.GetCurrentPattern([Windows.Automation.InvokePattern]::Pattern).Invoke() | |
Start-Sleep -s 1 | |
$btn1Element.GetCurrentPattern([Windows.Automation.InvokePattern]::Pattern).Invoke() | |
Start-Sleep -s 1 | |
$btnEqualElement.GetCurrentPattern([Windows.Automation.InvokePattern]::Pattern).Invoke() | |
Start-Sleep -s 1 | |
Write-Host "Finished. Please check the results on the AUT." |
Hi @johndonnelly,
I just came across the same gist. Using UIA Verify http://uiautomationverify.codeplex.com/releases/view/11366 I was able to find out that the button names are "Add" and "Equals" respectively (Windows 7). Changing lines 44.48 to the correct names made it work:
`$condName = New-Object Windows.Automation.PropertyCondition([Windows.Automation.AutomationElement]::NameProperty, "Add")
$condName = New-Object Windows.Automation.PropertyCondition([Windows.Automation.AutomationElement]::NameProperty, "Equals")`
Script is working fine in debug mode. But getting this error when I try to call ps1 from bat script:
Exception calling "RegisterClientSideProviderAssembly" with "1" argument(s):
"Object reference not set to an instance of an object."
At C:\Users\Public\Desktop\Untitled.ps1:6 char:2
+ [Windows.Automation.ClientSettings]::RegisterClientSideProviderAssem ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : NotSpecified: (:) [], MethodInvocationException
+ FullyQualifiedErrorId : NullReferenceException
Can anyone help..
@smartaquarius10 That's very unusual bug, - looks like when calling RegisterClientSideProviderAssembly from powershell.exe, first call fails with exception and all subsequent calls will be successful! Here is a workaround:
try
{
# WORKAROUND: There is a weird bug: first call fails ...
[Windows.Automation.ClientSettings]::RegisterClientSideProviderAssembly([UIAutomationClientsideProviders.UIAutomationClientSideProviders].Assembly.GetName())
}
catch {}
# ... second call succeeds:
[Windows.Automation.ClientSettings]::RegisterClientSideProviderAssembly([UIAutomationClientsideProviders.UIAutomationClientSideProviders].Assembly.GetName())
after this script works fine.
Nice script but I get "You cannot call a method on a null-valued expression." on line 56 and 60. It seems the + and the = button element objects aren't created?