I am trying to get the window handler and press the Save button. I found couple of examples on IE8 & 9. But that code doesn't works on IE 11.
const int BM_CLICK = 0x00F5;
[DllImport("user32.dll", SetLastError = true)]
static extern IntPtr FindWindow(string lpClassName, string lpWindowName);
[DllImport("user32.dll")]
[return: MarshalAs(UnmanagedType.Bool)]
static extern bool SetForegroundWindow(IntPtr hWnd);
[DllImport("user32.dll", SetLastError = true)]
static extern IntPtr SetActiveWindow(IntPtr hWnd);
[DllImport("user32.dll", CharSet = CharSet.Auto)]
public static extern IntPtr FindWindowEx(IntPtr parent, IntPtr next, string sClassName, IntPtr sWindowTitle);
[DllImport("user32.dll", SetLastError = true)]
static extern IntPtr FindWindowEx(IntPtr hwndParent, IntPtr hwndChildAfter, string lpszClass, string lpszWindow);
[DllImport("user32.dll", CharSet = CharSet.Auto)]
static extern IntPtr SendMessage(IntPtr hWnd, UInt32 Msg, IntPtr wParam, IntPtr lParam);
[DllImport("user32.dll", ExactSpelling = true, CharSet = CharSet.Auto)]
public static extern uint GetDlgCtrlID(IntPtr hWnd);
[DllImport("user32.dll", CharSet = CharSet.Auto)]
public static extern IntPtr SendMessage(IntPtr hWnd, int msg, int wParam, IntPtr lParam);
//hDialog - handle of dialog window. idBtn - Id of button
public static bool ClickButtonOnDialog(IntPtr hDialog, UInt32 idBtn)
{
IntPtr res = IntPtr.Zero;
uint id;
IntPtr hOkBtn = IntPtr.Zero;
int attempt = 0;
do
{
Thread.Sleep(300);
//searching for button
hOkBtn = FindWindowEx(hDialog, hOkBtn, "Button", IntPtr.Zero);
id = GetDlgCtrlID(hOkBtn);
attempt++;
} while (id != idBtn && attempt < 20);
if (!hOkBtn.Equals(IntPtr.Zero))
{
//click the button
res = SendMessage(hOkBtn, (int)BM_CLICK, 1, IntPtr.Zero);
}
if (res.ToInt32() == 1)
return true;
return false;
}
public static void FindAndSave()
{
IntPtr hOkBtn = IntPtr.Zero;
uint message = 0xf5;
IntPtr hwnd = FindWindow(null, "Internet Explorer");
hOkBtn = FindWindowEx(hwnd, hOkBtn, "Button", "Cancel");
SendMessage(hOkBtn, (int)message, 1, IntPtr.Zero);
I was able to download and close the file download dialog box using the below code
My approach:
Identify the window by the window title using a windows API call.
Loop through the IE window until we find the Element with "Frame Notification Bar or "Notification Bar" as Window Class Name
Find the Button named "Open" or "Save" and perform the click.
Here is the IE 11 code that works. Its a mix of System.Windows.Automation and Win32 API. Could probably get it to work with Win32 unmanaged API's. I used WinID to get the menu's class name and then iterate through its child elements.
IE 11 has this download frame.
We needed to access the Save As from the Save's down arrow.
I had two IE processes running - the above code was always picking up the wrong 32bit IE process. So, I've merged the answers from multiple StackOverflow questions and wrote the below code to get this done (without the dll imports).
Please note that you need to add a reference to UIAutomationClient in the project - in order to use the AutomationElement method.
I have achieved in very simple way. Just by using key strokes.
SendKeys.SendWait("%");
SendKeys.SendWait("%{s}");
Hope this will save your lot of time.