I've made a Class to record the mouse actions, for example to record a task with the mouse (move mouse here and click left button there and... that.)
After recording the mouse actions/task, I can reproduce it from the Class with a thread I made.
What I need is to implement the Middle button of the mouse and the Wheel scrolls too, but I don't have idea how to do that, was a little hard for me to use and understand "GetAsyncKeyState" and I can't found information about "GetAsyncKeyState middle button state" or the wheel scroll (to scroll down/up).
#Region " Record Mouse Class "
' [ Record Mouse Functions ]
'
' // By Elektro H@cker
'
' Examples :
' Record_Mouse.Start_Record()
' Record_Mouse.Stop_Record()
' Record_Mouse.Play() : While Not Record_Mouse.Play_Is_Completed : Application.DoEvents() : End While
' Record_Mouse.Mouse_Speed = 50
Public Class Record_Mouse
''' <summary>
''' Sets the speed of recording/playing the mouse actions.
''' Default value is 25.
''' </summary>
Public Shared Mouse_Speed As Int64 = 25
''' <summary>
''' Gets the status pf the current mouse play.
''' False = mouse task is still playing.
''' True = Mouse task play is done.
''' </summary>
Public Shared Play_Is_Completed As Boolean = False
' Where the mouse coordenates will be stored:
Private Shared Coordenates_List As New List(Of Point)
' Where the mouse clicks will be stored:
Private Shared Clicks_Dictionary As New Dictionary(Of Int64, MouseButton)
' Timer to record the mouse:
Private Shared WithEvents Record_Timer As New Timer
' Button click count to rec/play clicks:
Private Shared Click_Count As Int32 = 0
' Thread to reproduce the mouse actions:
Private Shared Thread_MousePlay_Var As System.Threading.Thread = New Threading.Thread(AddressOf Thread_MousePlay)
' API to record the current mouse button state:
Private Declare Function GetAsyncKeyState Lib "user32" (ByVal vKey As Long) As Integer
' API to reproduce a mouse button click:
Private Declare Sub Mouse_Event Lib "User32" Alias "mouse_event" (ByVal dwFlags As MouseButton, ByVal dx As Integer, ByVal dy As Integer, ByVal dwData As Integer, ByVal dwExtraInfo As Integer)
' GetAsyncKeyState buttons status
Private Shared Last_ClickState_Left As Int64 = -1
Private Shared Last_ClickState_Right As Int64 = -1
Enum MouseButton
Left_Down = &H2 ' Left button (hold)
Left_Up = &H4 ' Left button (release)
Right_Down = &H8 ' Right button (hold)
Right_Up = &H10 ' Right button (release)
Middle_Down = &H20 ' Middle button (hold)
Middle_Up = &H40 ' Middle button (release)
Left ' Left button (press)
Right ' Right button (press)
Middle ' Middle button (press)
End Enum
''' <summary>
''' Starts recording the mouse actions over the screen.
''' It records the position of the mouse and left/right button clicks.
''' </summary>
Public Shared Sub Start_Record()
Play_Is_Completed = False
Record_Timer.Interval = Mouse_Speed
Coordenates_List.Clear() : Clicks_Dictionary.Clear() : Click_Count = 0
Record_Timer.Start()
End Sub
''' <summary>
''' Stop recording the mouse actions.
''' </summary>
Public Shared Sub Stop_Record()
Record_Timer.Stop()
End Sub
''' <summary>
''' Reproduce the mouse actions.
''' </summary>
Public Shared Sub Play()
Thread_MousePlay_Var = New Threading.Thread(AddressOf Thread_MousePlay)
Thread_MousePlay_Var.IsBackground = True
Thread_MousePlay_Var.Start()
End Sub
' Procedure used to store the mouse actions
Private Shared Sub Record_Timer_Tick(sender As Object, e As EventArgs) Handles Record_Timer.Tick
Coordenates_List.Add(Control.MousePosition)
If Not Last_ClickState_Left = GetAsyncKeyState(1) Then
Last_ClickState_Left = GetAsyncKeyState(1)
If GetAsyncKeyState(1) = 32768 Then
Click_Count += 1
Coordenates_List.Add(Nothing)
Clicks_Dictionary.Add(Click_Count, MouseButton.Left_Down)
ElseIf GetAsyncKeyState(1) = 0 Then
Click_Count += 1
Coordenates_List.Add(Nothing)
Clicks_Dictionary.Add(Click_Count, MouseButton.Left_Up)
End If
End If
If Not Last_ClickState_Right = GetAsyncKeyState(2) Then
Last_ClickState_Right = GetAsyncKeyState(2)
If GetAsyncKeyState(2) = 32768 Then
Click_Count += 1
Coordenates_List.Add(Nothing)
Clicks_Dictionary.Add(Click_Count, MouseButton.Right_Down)
ElseIf GetAsyncKeyState(2) = 0 Then
Click_Count += 1
Coordenates_List.Add(Nothing)
Clicks_Dictionary.Add(Click_Count, MouseButton.Right_Up)
End If
End If
End Sub
' Procedure to play a mouse button (click)
Private Shared Sub Mouse_Click(ByVal MouseButton As MouseButton)
Select Case MouseButton
Case MouseButton.Left : Mouse_Event(MouseButton.Left_Down, 0, 0, 0, 0) : Mouse_Event(MouseButton.Left_Up, 0, 0, 0, 0)
Case MouseButton.Right : Mouse_Event(MouseButton.Right_Down, 0, 0, 0, 0) : Mouse_Event(MouseButton.Right_Up, 0, 0, 0, 0)
Case MouseButton.Middle : Mouse_Event(MouseButton.Middle_Down, 0, 0, 0, 0) : Mouse_Event(MouseButton.Middle_Up, 0, 0, 0, 0)
Case Else : Mouse_Event(MouseButton, 0, 0, 0, 0)
End Select
End Sub
' Thread used for reproduce the mouse actions
Private Shared Sub Thread_MousePlay()
Click_Count = 0
For Each Coordenate In Coordenates_List
Threading.Thread.Sleep(Mouse_Speed)
If Coordenate = Nothing Then
Click_Count += 1
If Click_Count > 1 Then Mouse_Click(Clicks_Dictionary.Item(Click_Count))
Else
Cursor.Position = Coordenate
End If
Application.DoEvents()
Next
Play_Is_Completed = True
End Sub
End Class
#End Region
You can get the middle-mouse button with GetAsyncKeyState(4). But you'll never get mouse scroll messages with this approach, there isn't any way to ask for the scroll button position. You must rely on the Window message that tells you that the mouse was scrolled, WM_MOUSEWHEEL.
The requirement that a recording is made even if your own window doesn't have the focus requires a fundamentally different approach, you need to use a low-level hook. A hook set by SetWindowsHookEx(), it will call a method in your program when a mouse event occurs.
No point in posting the code for that, there are lots of samples available for that on the Internet. The proper Google query for it is "vb.net setwindowshookex wh_mouse_ll". The first hit is already very good, the Microsoft KB article has almost everything you need. The way it uses SetWindowsHookEx() does however need tweaking, as shown it will only record mouse events for your own program. Instead, use LoadLibrary("user32.dll") and pass the return value as the 3rd argument, 0 for the 4th argument to get it to record every mouse event.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With