From: "Victor \"Zverok\" Shepelev" Date: 2007-03-14T22:01:08+09:00 Subject: Re: Mouse click with win32api ------=_NextPart_000_0001_01C76649.948C31D0 Content-Type: text/plain; charset="US-ASCII" Content-Transfer-Encoding: 7bit From: list-bounce@example.com [mailto:list-bounce@example.com] On Behalf Of Emil Sandin Sent: Wednesday, March 14, 2007 2:46 PM > >Hi, >I would like to write a script like this: > >mouse.move_cursor_to( x, y ) >mouse.click_left_button() > >I have read that I can use AutoIt, but that the program has to have an >ole interface for it to be possible. That autoit doesn't really move the >mouse cursor, but rather tells the program to click a certain >coordinate. > >Is it possible to do this using win32api instead of autoIt, or is there >another neat way of acheive it? There is simple cpp code attached (as well as extconf for it). It is compiled into extension, having module Rwin32::Emulate with methods mouse_down!, mouse_up!, key_down!, key_up! It can be used as is, or as a learning material of "how to do this". Any questions are welcome. If somebody wants to do something more full-featured on this basis, he is welcome too. V. ------=_NextPart_000_0001_01C76649.948C31D0 Content-Type: application/octet-stream; name="extconf.rb" Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename="extconf.rb" require "mkmf" $CFLAGS << ' -w -WL' $CPPFLAGS << ' /Zc:wchar_t /EHsc' create_makefile("rwin32_emulate") ------=_NextPart_000_0001_01C76649.948C31D0 Content-Type: text/plain; name="emulate.cpp" Content-Transfer-Encoding: quoted-printable Content-Disposition: attachment; filename="emulate.cpp" #define _WIN32_WINNT 0x0500 #include #include //some C++ shortcuts to ruby's types and methods typedef VALUE (*method_t)(...); //User input emulation //Assumes it included into object having @hwnd instance variable //Ruby module: Win32--------------------------------------- namespace RWin32 { //Ruby module: RWin32::Emulate----------------------------- namespace Emulate { VALUE rb_mRWin32, rb_mRWin32Emulate; void _prepare_mouse(HWND _hwnd, int _x, int _y, MOUSEINPUT &_out) { _out.time =3D 0; _out.mouseData =3D 0; _out.dwExtraInfo;=20 POINT p; p.x =3D _x; p.y =3D _y; ::ClientToScreen(_hwnd, &p); ::SetCursorPos(p.x, p.y); } void _prepare_key(HWND _hwnd, int _key, KEYBDINPUT &_out) { _out.time =3D 0; _out.dwExtraInfo =3D 0; _out.wScan =3D 0; _out.wVk =3D _key; } void _send(HWND _hwnd, INPUT _param) { ::SendMessage(::GetDesktopWindow(), WM_SYSCOMMAND, (WPARAM) SC_HOTKEY, = (LPARAM) _hwnd); ::SendInput(1, &_param, sizeof(_param)); rb_thread_schedule(); rb_thread_schedule(); } static VALUE mouse_down(VALUE _self, VALUE _x, VALUE _y) { HWND hwnd =3D (HWND)FIX2INT(rb_iv_get(_self, "@hwnd")); INPUT param; =09 param.type =3D INPUT_MOUSE; param.mi.dwFlags =3D MOUSEEVENTF_LEFTDOWN; _prepare_mouse(hwnd, FIX2INT(_x), FIX2INT(_y), param.mi); _send(hwnd, param); =09 return _self; } static VALUE mouse_up(VALUE _self, VALUE _x, VALUE _y) { HWND hwnd =3D (HWND)FIX2INT(rb_iv_get(_self, "@hwnd")); INPUT param; =09 param.type =3D INPUT_MOUSE; param.mi.dwFlags =3D MOUSEEVENTF_LEFTUP; _prepare_mouse(hwnd, FIX2INT(_x), FIX2INT(_y), param.mi); _send(hwnd, param); =09 return _self; } static VALUE key_down(VALUE _self, VALUE _key) { HWND hwnd =3D (HWND)FIX2INT(rb_iv_get(_self, "@hwnd")); INPUT param; =09 param.type =3D INPUT_KEYBOARD; param.ki.dwFlags =3D 0; _prepare_key(hwnd, FIX2INT(_key), param.ki); _send(hwnd, param); =09 return _self; } static VALUE key_up(VALUE _self, VALUE _key) { HWND hwnd =3D (HWND)FIX2INT(rb_iv_get(_self, "@hwnd")); INPUT param; =09 param.type =3D INPUT_KEYBOARD; param.ki.dwFlags =3D KEYEVENTF_KEYUP; _prepare_key(hwnd, FIX2INT(_key), param.ki); _send(hwnd, param); =09 return _self; } void module_init() { rb_mRWin32 =3D rb_define_module("RWin32"); rb_mRWin32Emulate =3D rb_define_module_under(rb_mRWin32, "Emulate"); =09 rb_define_method(rb_mRWin32Emulate, "mouse_down!", = (method_t)&RWin32::Emulate::mouse_down, 2); rb_define_method(rb_mRWin32Emulate, "mouse_up!" , = (method_t)&RWin32::Emulate::mouse_up , 2); rb_define_method(rb_mRWin32Emulate, "key_down!", = (method_t)&RWin32::Emulate::key_down, 1); rb_define_method(rb_mRWin32Emulate, "key_up!" , = (method_t)&RWin32::Emulate::key_up , 1); } }//RWin32::Emulate }//RWin32 void Init_rwin32_emulate()=20 { RWin32::Emulate::module_init(); } ------=_NextPart_000_0001_01C76649.948C31D0--