MSDN.WhiteKnight - Stack Overflow answers
Ответ на "Как эмулировать нажатие на кнопку в приложении WPF C#"
Answer 824466
Есть еще вот такой способ:
using System; using System.Collections.Generic; using System.Text; using System.Windows; using System.Windows.Controls; using System.Windows.Data; using System.Windows.Input; using System.Windows.Interop; using System.IO; using System.Xml; using System.Runtime.InteropServices; using System.Threading.Tasks; namespace WpfApplication1 { public partial class MainWindow : Window { public MainWindow() { InitializeComponent(); } /*Вспомогательные методы и константы...*/ public static Point ElementPointToScreenPoint(UIElement element, Point pointOnElement) { return element.PointToScreen(pointOnElement); } [DllImport("user32.dll")] static extern int GetSystemMetrics(int smIndex); [DllImport("user32.dll")] static extern uint SendInput(uint nInputs, [MarshalAs(UnmanagedType.LPArray), In] INPUT[] pInputs, int cbSize); [DllImport("user32.dll")] [return: MarshalAs(UnmanagedType.Bool)] static extern bool GetCursorPos(ref Win32Point pt); const uint MOUSEEVENTF_ABSOLUTE = 0x8000; const uint MOUSEEVENTF_MOVE = 0x0001; const uint MOUSEEVENTF_LEFTDOWN = 0x0002; const uint MOUSEEVENTF_LEFTUP = 0x0004; const int SM_CXSCREEN = 0; const int SM_CYSCREEN = 1; /* Эмулирует нажатие мышью на элемент управления */ public static async void PerformClick(Control ctrl) { double XSCALEFACTOR = 65535.0 / (GetSystemMetrics(SM_CXSCREEN) - 1); double YSCALEFACTOR = 65535.0 / (GetSystemMetrics(SM_CYSCREEN) - 1); //находим координаты центра элемента double x = ctrl.ActualWidth / 2; double y = ctrl.ActualHeight / 2; Point p = ElementPointToScreenPoint(ctrl, new Point(x, y)); //сохраняем текущие координаты мыши Win32Point mouse = new Win32Point(); GetCursorPos(ref mouse); //эмулируем нажатие INPUT[] arr = new INPUT[1]; arr[0].Type = INPUT_TYPE.INPUT_MOUSE; arr[0].Data.Mouse.ExtraInfo = IntPtr.Zero; arr[0].Data.Mouse.X = (int)Math.Round(p.X * XSCALEFACTOR); arr[0].Data.Mouse.Y = (int)Math.Round(p.Y * YSCALEFACTOR); arr[0].Data.Mouse.Flags = MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_MOVE | MOUSEEVENTF_LEFTDOWN | MOUSEEVENTF_LEFTUP; var res =SendInput(1, arr, Marshal.SizeOf(typeof(INPUT))); if(!Window.GetWindow(ctrl).IsMouseOver) await Task.Delay(1); //если мышь за пределами окна, WPF понадобится некоторое время для обработки события //возвращаем предыдущее положение мыши arr[0].Type = INPUT_TYPE.INPUT_MOUSE; arr[0].Data.Mouse.X = (int)Math.Round(mouse.X * XSCALEFACTOR); arr[0].Data.Mouse.Y = (int)Math.Round(mouse.Y * YSCALEFACTOR); arr[0].Data.Mouse.Flags = MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_MOVE ; res = SendInput(1, arr, Marshal.SizeOf(typeof(INPUT))); } private async void Window_Loaded(object sender, RoutedEventArgs e) { //пример использования await Task.Delay(1000); PerformClick(button1); await Task.Delay(3000); PerformClick(button2); } } //WINAPI types... enum INPUT_TYPE : uint { INPUT_MOUSE = 0, INPUT_KEYBOARD = 1, INPUT_HARDWARE = 2 } [StructLayout(LayoutKind.Sequential)] struct INPUT { public INPUT_TYPE Type; public MOUSEKEYBDHARDWAREINPUT Data; } [StructLayout(LayoutKind.Explicit)] struct MOUSEKEYBDHARDWAREINPUT { [FieldOffset(0)] public HARDWAREINPUT Hardware; [FieldOffset(0)] public KEYBDINPUT Keyboard; [FieldOffset(0)] public MOUSEINPUT Mouse; } [StructLayout(LayoutKind.Sequential)] struct HARDWAREINPUT { public uint Msg; public ushort ParamL; public ushort ParamH; } [StructLayout(LayoutKind.Sequential)] struct KEYBDINPUT { public ushort Vk; public ushort Scan; public uint Flags; public uint Time; public IntPtr ExtraInfo; } [StructLayout(LayoutKind.Sequential)] struct MOUSEINPUT { public int X; public int Y; public uint MouseData; public uint Flags; public uint Time; public IntPtr ExtraInfo; } [StructLayout(LayoutKind.Sequential)] struct Win32Point { public Int32 X; public Int32 Y; }; }
Content is retrieved from StackExchange API.
Auto-generated by ruso-archive tools.