I am very new to programming and this is the first time I have done anything in C#. I have the source code of a program I like to use frequently and I would like to modify it to make it better for me to use personally. The program is set up in a way where when the user holds down the left mouse button, the mouse clicks in random intervals. However I want there to be a delay between when the mouse is held down and up again, which is why I implemented this code:
public void PerformLeftClick(int xpos, int ypos)
{
mouse_event(0x02, xpos, ypos, 0, 0); //leftdown
Thread.Sleep(49);
mouse_event(0x04, xpos, ypos, 0, 0); //leftup
leftDown = true;
}
...
private void leftMouseUp(MouseHook.MSLLHOOKSTRUCT mouseStruct)
{
leftDown = false;
}
private void leftMouseDown(MouseHook.MSLLHOOKSTRUCT mouseStruct)
{
if (leftDown == false)
{
timeLeftClicked = DateTime.Now;
}
leftDown = true;
}
Mouse hook (not my code obviously):
#region Copyright
/// <copyright>
/// Copyright (c) 2011 Ramunas Geciauskas, http://geciauskas.com
///
/// Permission is hereby granted, free of charge, to any person obtaining a copy
/// of this software and associated documentation files (the "Software"), to deal
/// in the Software without restriction, including without limitation the rights
/// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
/// copies of the Software, and to permit persons to whom the Software is
/// furnished to do so, subject to the following conditions:
///
/// The above copyright notice and this permission notice shall be included in
/// all copies or substantial portions of the Software.
///
/// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
/// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
/// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
/// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
/// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
/// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
/// THE SOFTWARE.
/// </copyright>
/// <author>Ramunas Geciauskas</author>
/// <summary>Contains a MouseHook class for setting up low level Windows mouse hooks.</summary>
#endregion
using System;
using System.Runtime.InteropServices;
using System.Diagnostics;
namespace RamGecTools
{
/// <summary>
/// Class for intercepting low level Windows mouse hooks.
/// </summary>
class MouseHook
{
/// <summary>
/// Internal callback processing function
/// </summary>
private delegate IntPtr MouseHookHandler(int nCode, IntPtr wParam, IntPtr lParam);
private MouseHookHandler hookHandler;
/// <summary>
/// Function to be called when defined even occurs
/// </summary>
/// <param name="mouseStruct">MSLLHOOKSTRUCT mouse structure</param>
public delegate void MouseHookCallback(MSLLHOOKSTRUCT mouseStruct);
#region Events
public event MouseHookCallback LeftButtonDown;
public event MouseHookCallback LeftButtonUp;
public event MouseHookCallback RightButtonDown;
public event MouseHookCallback RightButtonUp;
public event MouseHookCallback MouseMove;
public event MouseHookCallback MouseWheel;
public event MouseHookCallback DoubleClick;
public event MouseHookCallback MiddleButtonDown;
public event MouseHookCallback MiddleButtonUp;
#endregion
/// <summary>
/// Low level mouse hook's ID
/// </summary>
private IntPtr hookID = IntPtr.Zero;
/// <summary>
/// Install low level mouse hook
/// </summary>
/// <param name="mouseHookCallbackFunc">Callback function</param>
public void Install()
{
hookHandler = HookFunc;
hookID = SetHook(hookHandler);
}
/// <summary>
/// Remove low level mouse hook
/// </summary>
public void Uninstall()
{
if (hookID == IntPtr.Zero)
return;
UnhookWindowsHookEx(hookID);
hookID = IntPtr.Zero;
}
/// <summary>
/// Destructor. Unhook current hook
/// </summary>
~MouseHook()
{
Uninstall();
}
/// <summary>
/// Sets hook and assigns its ID for tracking
/// </summary>
/// <param name="proc">Internal callback function</param>
/// <returns>Hook ID</returns>
private IntPtr SetHook(MouseHookHandler proc)
{
using (ProcessModule module = Process.GetCurrentProcess().MainModule)
return SetWindowsHookEx(WH_MOUSE_LL, proc, GetModuleHandle(module.ModuleName), 0);
}
/// <summary>
/// Callback function
/// </summary>
private IntPtr HookFunc(int nCode, IntPtr wParam, IntPtr lParam)
{
// parse system messages
if (nCode >= 0)
{
if (MouseMessages.WM_LBUTTONDOWN == (MouseMessages)wParam)
if (LeftButtonDown != null)
LeftButtonDown((MSLLHOOKSTRUCT)Marshal.PtrToStructure(lParam, typeof(MSLLHOOKSTRUCT)));
if (MouseMessages.WM_LBUTTONUP == (MouseMessages)wParam)
if (LeftButtonUp != null)
LeftButtonUp((MSLLHOOKSTRUCT)Marshal.PtrToStructure(lParam, typeof(MSLLHOOKSTRUCT)));
if (MouseMessages.WM_RBUTTONDOWN == (MouseMessages)wParam)
if (RightButtonDown != null)
RightButtonDown((MSLLHOOKSTRUCT)Marshal.PtrToStructure(lParam, typeof(MSLLHOOKSTRUCT)));
if (MouseMessages.WM_RBUTTONUP == (MouseMessages)wParam)
if (RightButtonUp != null)
RightButtonUp((MSLLHOOKSTRUCT)Marshal.PtrToStructure(lParam, typeof(MSLLHOOKSTRUCT)));
if (MouseMessages.WM_MOUSEMOVE == (MouseMessages)wParam)
if (MouseMove != null)
MouseMove((MSLLHOOKSTRUCT)Marshal.PtrToStructure(lParam, typeof(MSLLHOOKSTRUCT)));
if (MouseMessages.WM_MOUSEWHEEL == (MouseMessages)wParam)
if (MouseWheel != null)
MouseWheel((MSLLHOOKSTRUCT)Marshal.PtrToStructure(lParam, typeof(MSLLHOOKSTRUCT)));
if (MouseMessages.WM_LBUTTONDBLCLK == (MouseMessages)wParam)
if (DoubleClick != null)
DoubleClick((MSLLHOOKSTRUCT)Marshal.PtrToStructure(lParam, typeof(MSLLHOOKSTRUCT)));
if (MouseMessages.WM_MBUTTONDOWN == (MouseMessages)wParam)
if (MiddleButtonDown != null)
MiddleButtonDown((MSLLHOOKSTRUCT)Marshal.PtrToStructure(lParam, typeof(MSLLHOOKSTRUCT)));
if (MouseMessages.WM_MBUTTONUP == (MouseMessages)wParam)
if (MiddleButtonUp != null)
MiddleButtonUp((MSLLHOOKSTRUCT)Marshal.PtrToStructure(lParam, typeof(MSLLHOOKSTRUCT)));
}
return CallNextHookEx(hookID, nCode, wParam, lParam);
}
#region WinAPI
private const int WH_MOUSE_LL = 14;
private enum MouseMessages
{
WM_LBUTTONDOWN = 0x0201,
WM_LBUTTONUP = 0x0202,
WM_MOUSEMOVE = 0x0200,
WM_MOUSEWHEEL = 0x020A,
WM_RBUTTONDOWN = 0x0204,
WM_RBUTTONUP = 0x0205,
WM_LBUTTONDBLCLK = 0x0203,
WM_MBUTTONDOWN = 0x0207,
WM_MBUTTONUP = 0x0208
}
[StructLayout(LayoutKind.Sequential)]
public struct POINT
{
public int x;
public int y;
}
[StructLayout(LayoutKind.Sequential)]
public struct MSLLHOOKSTRUCT
{
public POINT pt;
public uint mouseData;
public uint flags;
public uint time;
public IntPtr dwExtraInfo;
}
[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern IntPtr SetWindowsHookEx(int idHook,
MouseHookHandler lpfn, IntPtr hMod, uint dwThreadId);
[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
[return: MarshalAs(UnmanagedType.Bool)]
public static extern bool UnhookWindowsHookEx(IntPtr hhk);
[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern IntPtr CallNextHookEx(IntPtr hhk, int nCode, IntPtr wParam, IntPtr lParam);
[DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern IntPtr GetModuleHandle(string lpModuleName);
#endregion
}
}
Then after this code is executed, this follows:
if (leftDown && ((int)DateTime.Now.Subtract(timeLeftClicked).TotalMilliseconds) > numDelayM)
{
Random random = new Random();
PerformLeftClick(mouseX, mouseY);
Thread.Sleep((((int)numClickSpeed.Value) + random.Next(0, (int)numRandomClick.Value) - 49));
}
which holds the mouse button (after a starting delay), lifts it after 49 milliseconds and then sleeps for a user-inputted time (minus 49). However, sometimes when you lift the mouse button the code continues to loop because I set leftDown to true (as otherwise the code would not repeat, annoyingly). I want it so that as soon as the user lifts from the mouse button the code will stop looping.
Is there any way of making it so that I don't need to set leftDown to True and the code will continue to execute while the left mouse button is being held down, and stopped when it is lifted? Would I need to find another method of checking how the left mouse button is held down for this?
Thanks in advance.