title: Microsoft UIAutomation can't move Edge browser window
body: <p>I combined learnings from two different sources to detect open windows using UIAutomation and to move the windows:</p>
  <ol>
  <li><a href="https://www.meziantou.net/detect-the-opening-of-a-new-window-in-csharp.htm" rel="nofollow noreferrer">Detect the opening of a new window in C#</a></li>
  <li><a href="https://docs.microsoft.com/en-us/dotnet/framework/ui-automation/move-a-ui-automation-element" rel="nofollow noreferrer">Move a UI Automation Element</a></li>
  </ol>
  <p>I can get practically every app window to move (Win32 apps and UWP apps).  Except for the Microsoft Edge browser window!</p>
  <p><strong>QUESTION: Does anyone know how to use UIAutomation to move the Edge window? Does anyone know what is special about the Edge browser that prevents it from adhering to Microsoft's own UIAutomation library?</strong></p>
  <p>Here's my full console app code (required: Add references to UIAutomationClient and UIAutomationTypes):</p>
  <pre><code>using System;
  using System.Threading;
  using System.Windows.Automation;
  
  namespace UiAutomationTest
  {
      class Program
      {
          static void Main(string[] args)
          {
              Automation.AddAutomationEventHandler(eventId: WindowPattern.WindowOpenedEvent, element: AutomationElement.RootElement, scope: TreeScope.Children, eventHandler: OnWindowOpened);
              Console.ReadLine();
              Automation.RemoveAllEventHandlers();
          }
  
          private static void OnWindowOpened(object sender, AutomationEventArgs e)
          {
              try
              {
                  var element = sender as AutomationElement;
                  if (element != null)
                  {
                      var hWnd = new IntPtr(element.Current.NativeWindowHandle);
                      Console.WriteLine($&quot;Opened: {element.Current.Name} (Pid:{element.Current.ProcessId}),hWnd:{Convert.ToInt32(hWnd.ToString())}&quot;);
                      var _windowPattern = GetControlPattern(element, WindowPattern.Pattern) as WindowPattern;
                      if (_windowPattern == null)
                      {
                          Console.WriteLine(&quot;WindowPattern is null! Aborting.&quot;);
                          return;
                      }
  
                      if (false == _windowPattern.WaitForInputIdle(10000))
                      {
                          Feedback(&quot;Object not responding in a timely manner.&quot;);
                          return;
                      }
                      Console.WriteLine(&quot;Window is ready for input&quot;);
  
                      var _transformPattern = GetControlPattern(element, TransformPattern.Pattern) as TransformPattern;
  
                      if (_transformPattern == null)
                      {
                          Console.WriteLine(&quot;TransformPattern is null! Aborting.&quot;);
                          return;
                      }
  
                      // Is the TransformPattern object moveable?
                      if (_transformPattern.Current.CanMove)
                      {
                          Console.WriteLine(&quot;Waiting 3 seconds before move...&quot;);
  
                          // Wait a bit
                          Thread.Sleep(3000);
  
                          // Move element
                          _transformPattern.Move(250, 500);
                          Console.WriteLine(&quot;Window was moved!&quot;);
                      }
                      else
                      {
                          Feedback(&quot;Window is not moveable.&quot;);
                      }
                  }
              }
              catch (Exception ex)
              {
                  Console.WriteLine($&quot;{ex.GetType()}: {ex.Message}\n{ex.StackTrace}&quot;);
              }
          }
  
          /// &lt;summary&gt;
          /// Gets a specified control pattern.
          /// &lt;/summary&gt;
          /// &lt;param name=&quot;ae&quot;&gt;The automation element we want to obtain the control pattern from.&lt;/param&gt;
          /// &lt;param name=&quot;ap&quot;&gt;The control pattern of interest.&lt;/param&gt;
          /// &lt;returns&gt;A ControlPattern object.&lt;/returns&gt;
          private static object GetControlPattern(AutomationElement ae, AutomationPattern ap)
          {
              if (false == ae.TryGetCurrentPattern(ap, out object oPattern))
              {
                  Feedback(&quot;Object does not support the &quot; + ap.ProgrammaticName + &quot; Pattern&quot;);
                  return null;
              }
  
              Feedback(&quot;Object supports the &quot; + ap.ProgrammaticName + &quot; Pattern.&quot;);
              return oPattern;
          }
  
          private static void Feedback(string message)
          {
              Console.WriteLine(message);
          }
      }
  }
  </code></pre>
  <p>Here's a video showing that I can open Internet Explorer and move it, Chrome and move it, but Edge won't move!</p>
  <p><a href="https://drive.google.com/file/d/1Nc7GG-GdAZMlq9FiEJe6xvMwB2_3b2nd/view?usp=sharing" rel="nofollow noreferrer">CantMoveEdgeWindow.mp4</a></p>
  <p>System Details:</p>
  <ul>
  <li>Windows 10 1809</li>
  <li>Visual Studio 2019 16.7</li>
  <li>.NET Framework 4.7.2 C# Console App</li>
  </ul>
  <p>Lastly, I have even tried using old school Win32 APIs such as EnumWindows, MoveWindow, SetWindowPlacement, and SetWindowPos.  The Edge browser appears to be housed inside of an ApplicationFrameHost.exe process window.  When I try to move the window, I get the same result as using the UIAutomation libraries: It &quot;says&quot; it passed, but the window doesn't actually move!</p>