Advertisement
Guest User

sdgsdgsdg

a guest
Jul 29th, 2015
347
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
VB.NET 47.70 KB | None | 0 0
  1. ' ***********************************************************************
  2. ' Author           : Elektro
  3. ' Last Modified On : 16-February-2015
  4. ' ***********************************************************************
  5. ' <copyright file="MouseHook.vb" company="Elektro Studios">
  6. '     Copyright (c) Elektro Studios. All rights reserved.
  7. ' </copyright>
  8. ' ***********************************************************************
  9.  
  10. #Region " Option Statements "
  11.  
  12. Option Strict On
  13. Option Explicit On
  14. Option Infer Off
  15.  
  16. #End Region
  17.  
  18. #Region " Instructions "
  19.  
  20. ' Go to page:
  21. ' Project > Properties > Debug
  22. '
  23. ' Then uncheck the option:
  24. ' "Enable the Visual Studio Hosting Process"
  25.  
  26. #End Region
  27.  
  28. #Region " Usage Examples "
  29.  
  30. ' ''' <summary>
  31. ' ''' A low level mouse hook that intercepts mouse events.
  32. ' ''' </summary>
  33. 'Private WithEvents mouseEvents As New MouseHook(Install:=False) With
  34. '    {
  35. '        .WorkingArea = SystemInformation.VirtualScreen,
  36. '        .SuppressMouseUpEventWhenDoubleClick = False
  37. '    }
  38.  
  39. ' ''' <summary>
  40. ' ''' Handles the Load event of the Form1.
  41. ' ''' </summary>
  42. ' ''' <param name="sender">The source of the event.</param>
  43. ' ''' <param name="e">The <see cref="EventArgs"/> instance containing the event data.</param>
  44. 'Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
  45.  
  46. '    ' Install Mouse Hook on the System.
  47. '    Me.MouseEvents.Install()
  48.  
  49. '    ' Start processing mouse events.
  50. '    Me.MouseEvents.Enable()
  51.  
  52. 'End Sub
  53.  
  54. ' ''' <summary>
  55. ' ''' Handles the FormClosing event of the Form1.
  56. ' ''' </summary>
  57. ' ''' <param name="sender">The source of the event.</param>
  58. ' ''' <param name="e">The <see cref="FormClosingEventArgs"/> instance containing the event data.</param>
  59. 'Private Sub Form1_FormClosing(sender As Object, e As FormClosingEventArgs) _
  60. 'Handles MyBase.FormClosing
  61.  
  62. '    ' Stop processing mouse events.
  63. '    Me.MouseEvents.Disable()
  64.  
  65. '    ' Uninstall the mouse hook from system.
  66. '    Me.MouseEvents.Uninstall()
  67.  
  68. 'End Sub
  69.  
  70. ' ''' <summary>
  71. ' ''' Handles the 'MouseMove' event of the Mouse Hook.
  72. ' ''' </summary>
  73. ' ''' <param name="sender">The source of the event.</param>
  74. ' ''' <param name="MouseLocation">Contains the mouse [X,Y] coordinates where the event fired.</param>
  75. 'Private Sub MouseEvents_MouseMove(ByVal sender As Object, ByVal MouseLocation As Point) _
  76. 'Handles MouseEvents.MouseMove
  77.  
  78. '    Debug.WriteLine(String.Format("Mouse Moved To: x={0}, y={1}",
  79. '                                  CStr(MouseLocation.X), CStr(MouseLocation.Y)))
  80.  
  81. 'End Sub
  82.  
  83. ' ''' <summary>
  84. ' ''' Handles the 'MouseLeftDown' event of the MouseHook.
  85. ' ''' </summary>
  86. ' ''' <param name="sender">The source of the event.</param>
  87. ' ''' <param name="MouseLocation">Contains the mouse [X,Y] coordinates where the event fired.</param>
  88. 'Private Sub MouseEvents_MouseLeftDown(ByVal sender As Object, ByVal MouseLocation As Point) _
  89. 'Handles MouseEvents.MouseLeftDown
  90.  
  91. '    Debug.WriteLine(String.Format("Mouse Left Down At: x={0}, y={1}",
  92. '                                  CStr(MouseLocation.X), CStr(MouseLocation.Y)))
  93.  
  94. 'End Sub
  95.  
  96. ' ''' <summary>
  97. ' ''' Handles the 'MouseLeftUp' event of the Mouse Hook.
  98. ' ''' </summary>
  99. ' ''' <param name="sender">The source of the event.</param>
  100. ' ''' <param name="MouseLocation">Contains the mouse [X,Y] coordinates where the event fired.</param>
  101. 'Private Sub MouseEvents_MouseLeftUp(ByVal sender As Object, ByVal MouseLocation As Point) _
  102. 'Handles MouseEvents.MouseLeftUp
  103.  
  104. '    Debug.WriteLine(String.Format("Mouse Left Up At: x={0}, y={1}",
  105. '                                  CStr(MouseLocation.X), CStr(MouseLocation.Y)))
  106.  
  107. 'End Sub
  108.  
  109. ' ''' <summary>
  110. ' ''' Handles the 'MouseRightDown' event of the MouseHook.
  111. ' ''' </summary>
  112. ' ''' <param name="sender">The source of the event.</param>
  113. ' ''' <param name="MouseLocation">Contains the mouse [X,Y] coordinates where the event fired.</param>
  114. 'Private Sub MouseEvents_MouseRightDown(ByVal sender As Object, ByVal MouseLocation As Point) _
  115. 'Handles MouseEvents.MouseRightDown
  116.  
  117. '    Debug.WriteLine(String.Format("Mouse Right Down At: x={0}, y={1}",
  118. '                                  CStr(MouseLocation.X), CStr(MouseLocation.Y)))
  119.  
  120. 'End Sub
  121.  
  122. ' ''' <summary>
  123. ' ''' Handles the 'MouseRightUp' event of the Mouse Hook.
  124. ' ''' </summary>
  125. ' ''' <param name="sender">The source of the event.</param>
  126. ' ''' <param name="MouseLocation">Contains the mouse [X,Y] coordinates where the event fired.</param>
  127. 'Private Sub MouseEvents_MouseRightUp(ByVal sender As Object, ByVal MouseLocation As Point) _
  128. 'Handles MouseEvents.MouseRightUp
  129.  
  130. '    Debug.WriteLine(String.Format("Mouse Right Up At: x={0}, y={1}",
  131. '                                  CStr(MouseLocation.X), CStr(MouseLocation.Y)))
  132.  
  133. 'End Sub
  134.  
  135. ' ''' <summary>
  136. ' ''' Handles the 'MouseMiddleDown' event of the MouseHook.
  137. ' ''' </summary>
  138. ' ''' <param name="sender">The source of the event.</param>
  139. ' ''' <param name="MouseLocation">Contains the mouse [X,Y] coordinates where the event fired.</param>
  140. 'Private Sub MouseEvents_MouseMiddleDown(ByVal sender As Object, ByVal MouseLocation As Point) _
  141. 'Handles MouseEvents.MouseMiddleDown
  142.  
  143. '    Debug.WriteLine(String.Format("Mouse Middle Down At: x={0}, y={1}",
  144. '                                  CStr(MouseLocation.X), CStr(MouseLocation.Y)))
  145.  
  146. 'End Sub
  147.  
  148. ' ''' <summary>
  149. ' ''' Handles the 'MouseMiddleUp' event of the Mouse Hook.
  150. ' ''' </summary>
  151. ' ''' <param name="sender">The source of the event.</param>
  152. ' ''' <param name="MouseLocation">Contains the mouse [X,Y] coordinates where the event fired.</param>
  153. 'Private Sub MouseEvents_MouseMiddleUp(ByVal sender As Object, ByVal MouseLocation As Point) _
  154. 'Handles MouseEvents.MouseMiddleUp
  155.  
  156. '    Debug.WriteLine(String.Format("Mouse Middle Up At: x={0}, y={1}",
  157. '                                  CStr(MouseLocation.X), CStr(MouseLocation.Y)))
  158.  
  159. 'End Sub
  160.  
  161. ' ''' <summary>
  162. ' ''' Handles the 'MouseLeftDoubleClick' event of the Mouse Hook.
  163. ' ''' </summary>
  164. ' ''' <param name="sender">The source of the event.</param>
  165. ' ''' <param name="MouseLocation">Contains the mouse [X,Y] coordinates where the event fired.</param>
  166. 'Private Sub MouseEvents_MouseLeftDoubleClick(ByVal sender As Object, ByVal MouseLocation As Point) _
  167. 'Handles MouseEvents.MouseLeftDoubleClick
  168.  
  169. '    Debug.WriteLine(String.Format("Mouse Left Double-Click At: x={0}, y={1}",
  170. '                                  CStr(MouseLocation.X), CStr(MouseLocation.Y)))
  171.  
  172. 'End Sub
  173.  
  174. ' ''' <summary>
  175. ' ''' Handles the 'MouseRightDoubleClick' event of the Mouse Hook.
  176. ' ''' </summary>
  177. ' ''' <param name="sender">The source of the event.</param>
  178. ' ''' <param name="MouseLocation">Contains the mouse [X,Y] coordinates where the event fired.</param>
  179. 'Private Sub MouseEvents_MouseRightDoubleClick(ByVal sender As Object, ByVal MouseLocation As Point) _
  180. 'Handles MouseEvents.MouseRightDoubleClick
  181.  
  182. '    Debug.WriteLine(String.Format("Mouse Right Double-Click At: x={0}, y={1}",
  183. '                                  CStr(MouseLocation.X), CStr(MouseLocation.Y)))
  184.  
  185. 'End Sub
  186.  
  187. ' ''' <summary>
  188. ' ''' Handles the 'MouseMiddleDoubleClick' event of the Mouse Hook.
  189. ' ''' </summary>
  190. ' ''' <param name="sender">The source of the event.</param>
  191. ' ''' <param name="MouseLocation">Contains the mouse [X,Y] coordinates where the event fired.</param>
  192. 'Private Sub MouseEvents_MouseMiddleDoubleClick(ByVal sender As Object, ByVal MouseLocation As Point) _
  193. 'Handles MouseEvents.MouseMiddleDoubleClick
  194.  
  195. '    Debug.WriteLine(String.Format("Mouse Middle Double-Click At: x={0}, y={1}",
  196. '                                  CStr(MouseLocation.X), CStr(MouseLocation.Y)))
  197.  
  198. 'End Sub
  199.  
  200. ' ''' <summary>
  201. ' ''' Handles the 'MouseWheel' event of the Mouse Hook.
  202. ' ''' </summary>
  203. ' ''' <param name="sender">The source of the event.</param>
  204. ' ''' <param name="MouseLocation">Contains the mouse [X,Y] coordinates where the event fired.</param>
  205. ' ''' <param name="WheelDirection">Contains the wheel direction (WheelUp or WheelDown).</param>
  206. 'Private Sub MouseEvents_MouseWheel(ByVal sender As Object,
  207. '                                   ByVal MouseLocation As Point,
  208. '                                   ByVal WheelDirection As MouseHook.WheelDirection) _
  209. 'Handles MouseEvents.MouseWheel
  210.  
  211. '    Debug.WriteLine(String.Format("Mouse Whell ({0}) At: x={1}, y={2}",
  212. '                                  WheelDirection.ToString, CStr(MouseLocation.X), CStr(MouseLocation.Y)))
  213.  
  214. 'End Sub
  215.  
  216. #End Region
  217.  
  218. #Region " Imports "
  219.  
  220. Imports System.ComponentModel
  221. Imports System.Reflection
  222. Imports System.Runtime.InteropServices
  223.  
  224. #End Region
  225.  
  226. #Region " MouseHook "
  227.  
  228. ''' <summary>
  229. ''' A low level mouse hook that processes mouse input events.
  230. ''' </summary>
  231. Friend NotInheritable Class MouseHook : Implements IDisposable
  232.  
  233. #Region " P/Invoke "
  234.  
  235.     ''' <summary>
  236.     ''' Platform Invocation methods (P/Invoke), access unmanaged code.
  237.     ''' This class does not suppress stack walks for unmanaged code permission.
  238.     ''' <see cref="System.Security.SuppressUnmanagedCodeSecurityAttribute"/>  must not be applied to this class.
  239.     ''' This class is for methods that can be used anywhere because a stack walk will be performed.
  240.     ''' MSDN Documentation: http://msdn.microsoft.com/en-us/library/ms182161.aspx
  241.     ''' </summary>
  242.     Protected NotInheritable Class NativeMethods
  243.  
  244. #Region " Methods "
  245.  
  246.         ''' <summary>
  247.         ''' Passes the hook information to the next hook procedure in the current hook chain.
  248.         ''' A hook procedure can call this function either before or after processing the hook information.
  249.         ''' For more info see here:
  250.         ''' http://msdn.microsoft.com/en-us/library/windows/desktop/ms644974%28v=vs.85%29.aspx
  251.         ''' </summary>
  252.         ''' <param name="idHook">
  253.         ''' This parameter is ignored.
  254.         ''' </param>
  255.         ''' <param name="nCode">
  256.         ''' The hook code passed to the current hook procedure.
  257.         ''' The next hook procedure uses this code to determine how to process the hook information.
  258.         ''' </param>
  259.         ''' <param name="wParam">
  260.         ''' The wParam value passed to the current hook procedure.
  261.         ''' The meaning of this parameter depends on the type of hook associated with the current hook chain.
  262.         ''' </param>
  263.         ''' <param name="lParam">
  264.         ''' The lParam value passed to the current hook procedure.
  265.         ''' The meaning of this parameter depends on the type of hook associated with the current hook chain.
  266.         ''' </param>
  267.         ''' <returns>
  268.         ''' This value is returned by the next hook procedure in the chain.
  269.         ''' The current hook procedure must also return this value.
  270.         ''' The meaning of the return value depends on the hook type.
  271.         ''' For more information, see the descriptions of the individual hook procedures.
  272.         ''' </returns>
  273.         <DllImport("user32.dll", CallingConvention:=CallingConvention.StdCall, CharSet:=CharSet.Auto)>
  274.         Public Shared Function CallNextHookEx(
  275.                ByVal idHook As IntPtr,
  276.                ByVal nCode As Integer,
  277.                ByVal wParam As IntPtr,
  278.                ByVal lParam As IntPtr
  279.         ) As IntPtr
  280.         End Function
  281.  
  282.         ''' <summary>
  283.         ''' Installs an application-defined hook procedure into a hook chain.
  284.         ''' You would install a hook procedure to monitor the system for certain types of events.
  285.         ''' These events are associated either with a specific thread
  286.         ''' or with all threads in the same desktop as the calling thread.
  287.         ''' For more info see here:
  288.         ''' http://msdn.microsoft.com/en-us/library/windows/desktop/ms644990%28v=vs.85%29.aspx
  289.         ''' </summary>
  290.         ''' <param name="idHook">
  291.         ''' The type of hook procedure to be installed.
  292.         ''' </param>
  293.         ''' <param name="lpfn">
  294.         ''' A pointer to the hook procedure.
  295.         ''' If the dwThreadId parameter is zero or specifies the identifier of a thread created by a different process,
  296.         ''' the lpfn parameter must point to a hook procedure in a DLL.
  297.         ''' Otherwise, lpfn can point to a hook procedure in the code associated with the current process.
  298.         ''' </param>
  299.         ''' <param name="hInstance">
  300.         ''' A handle to the DLL containing the hook procedure pointed to by the lpfn parameter.
  301.         ''' The hMod parameter must be set to NULL if the dwThreadId parameter specifies a thread created by
  302.         ''' the current process and if the hook procedure is within the code associated with the current process.
  303.         ''' </param>
  304.         ''' <param name="threadId">
  305.         ''' The identifier of the thread with which the hook procedure is to be associated.
  306.         ''' For desktop apps, if this parameter is zero, the hook procedure is associated
  307.         ''' with all existing threads running in the same desktop as the calling thread.
  308.         ''' </param>
  309.         ''' <returns>
  310.         ''' If the function succeeds, the return value is the handle to the hook procedure.
  311.         ''' If the function fails, the return value is NULL.
  312.         ''' </returns>
  313.         <DllImport("user32.dll", CallingConvention:=CallingConvention.StdCall, CharSet:=CharSet.Auto)>
  314.         Public Shared Function SetWindowsHookEx(
  315.                ByVal idHook As HookType,
  316.                ByVal lpfn As LowLevelMouseProcDelegate,
  317.                ByVal hInstance As IntPtr,
  318.                ByVal threadId As UInteger
  319.         ) As IntPtr
  320.         End Function
  321.  
  322.         ''' <summary>
  323.         ''' Removes a hook procedure installed in a hook chain by the 'SetWindowsHookEx' function.
  324.         ''' For more info see here:
  325.         ''' http://msdn.microsoft.com/en-us/library/windows/desktop/ms644993%28v=vs.85%29.aspx
  326.         ''' </summary>
  327.         ''' <param name="idHook">
  328.         ''' A handle to the hook to be removed.
  329.         ''' This parameter is a hook handle obtained by a previous call to SetWindowsHookEx.
  330.         ''' </param>
  331.         ''' <returns>
  332.         ''' If the function succeeds, the return value is nonzero.
  333.         ''' If the function fails, the return value is zero.
  334.         ''' </returns>
  335.         <DllImport("user32.dll", CallingConvention:=CallingConvention.StdCall, CharSet:=CharSet.Auto)>
  336.         Public Shared Function UnhookWindowsHookEx(
  337.                ByVal idHook As IntPtr
  338.         ) As Boolean
  339.         End Function
  340.  
  341.         ''' <summary>
  342.         ''' Retrieves the current double-click time for the mouse.
  343.         ''' A double-click is a series of two clicks of the mouse button,
  344.         ''' the second occurring within a specified time after the first.
  345.         ''' The double-click time is the maximum number of milliseconds that may occur
  346.         ''' between the first and second click of a double-click.
  347.         ''' The maximum double-click time is 5000 milliseconds.
  348.         ''' </summary>
  349.         ''' <returns>
  350.         ''' The return value specifies the current double-click time, in milliseconds.
  351.         ''' The maximum return value is 5000 milliseconds.
  352.         ''' </returns>
  353.         <DllImport("user32.dll", CharSet:=CharSet.Auto)>
  354.         Public Shared Function GetDoubleClickTime() As Integer
  355.         End Function
  356.  
  357. #End Region
  358.  
  359. #Region " Enumerations "
  360.  
  361.         ''' <summary>
  362.         ''' Specifies a System-Defined Message.
  363.         ''' MSDN Documentation: http://msdn.microsoft.com/en-us/library/windows/desktop/ms644927%28v=vs.85%29.aspx#system_defined
  364.         ''' </summary>
  365.         Public Enum WindowsMessages As UInteger
  366.  
  367.             ''' <summary>
  368.             ''' Posted to a window when the cursor moves.
  369.             ''' If the mouse is not captured, the message is posted to the window that contains the cursor.
  370.             ''' Otherwise, the message is posted to the window that has captured the mouse
  371.             ''' MSDN Documentation: http://msdn.microsoft.com/en-us/library/windows/desktop/ff468877%28v=vs.85%29.aspx
  372.             ''' </summary>
  373.             WM_MOUSEMOVE = &H200UI
  374.  
  375.             ''' <summary>
  376.             ''' Posted when the user presses the left mouse button while the cursor is in the client area of a window.
  377.             ''' If the mouse is not captured, the message is posted to the window beneath the cursor.
  378.             ''' Otherwise, the message is posted to the window that has captured the mouse
  379.             ''' </summary>
  380.             WM_LBUTTONDOWN = &H201UI
  381.  
  382.             ''' <summary>
  383.             ''' Posted when the user releases the left mouse button while the cursor is in the client area of a window.
  384.             ''' If the mouse is not captured, the message is posted to the window beneath the cursor.
  385.             ''' Otherwise, the message is posted to the window that has captured the mouse
  386.             ''' </summary>
  387.             WM_LBUTTONUP = &H202UI
  388.  
  389.             ''' <summary>
  390.             ''' Posted when the user presses the right mouse button while the cursor is in the client area of a window.
  391.             ''' If the mouse is not captured, the message is posted to the window beneath the cursor.
  392.             ''' Otherwise, the message is posted to the window that has captured the mouse
  393.             ''' </summary>
  394.             WM_RBUTTONDOWN = &H204UI
  395.  
  396.             ''' <summary>
  397.             ''' Posted when the user releases the right mouse button while the cursor is in the client area of a window.
  398.             ''' If the mouse is not captured, the message is posted to the window beneath the cursor.
  399.             ''' Otherwise, the message is posted to the window that has captured the mouse
  400.             ''' </summary>
  401.             WM_RBUTTONUP = &H205UI
  402.  
  403.             ''' <summary>
  404.             ''' Posted when the user presses the middle mouse button while the cursor is in the client area of a window.
  405.             ''' If the mouse is not captured, the message is posted to the window beneath the cursor.
  406.             ''' Otherwise, the message is posted to the window that has captured the mouse
  407.             ''' </summary>
  408.             WM_MBUTTONDOWN = &H207UI
  409.  
  410.             ''' <summary>
  411.             ''' Posted when the user releases the middle mouse button while the cursor is in the client area of a window.
  412.             ''' If the mouse is not captured, the message is posted to the window beneath the cursor.
  413.             ''' Otherwise, the message is posted to the window that has captured the mouse
  414.             ''' </summary>
  415.             WM_MBUTTONUP = &H208UI
  416.  
  417.             ''' <summary>
  418.             ''' Sent to the active window when the mouse's horizontal scroll wheel is tilted or rotated.
  419.             ''' The DefWindowProc function propagates the message to the window's parent.
  420.             ''' There should be no internal forwarding of the message,
  421.             ''' since DefWindowProc propagates it up the parent chain until it finds a window that processes it.
  422.             ''' </summary>
  423.             WM_MOUSEWHEEL = &H20AUI
  424.  
  425.         End Enum
  426.  
  427.         ''' <summary>
  428.         ''' Indicates a type of Hook procedure to be installed.
  429.         ''' MSDN Documentation: http://msdn.microsoft.com/en-us/library/windows/desktop/ms644990%28v=vs.85%29.aspx
  430.         ''' </summary>
  431.         Public Enum HookType As UInteger
  432.  
  433.             ' **************************************
  434.             ' This enumeration is partially defined.
  435.             ' **************************************
  436.  
  437.             ''' <summary>
  438.             ''' Installs a hook procedure that monitors low-level mouse input events.
  439.             ''' For more information, see the LowLevelMouseProc hook procedure.
  440.             ''' </summary>
  441.             WH_MOUSE_LL = 14UI
  442.  
  443.         End Enum
  444.  
  445.         ''' <summary>
  446.         ''' The event-injected flags.
  447.         ''' An application can use the following values to test the flags.
  448.         ''' Testing LLMHF_INJECTED (bit 0) will tell you whether the event was injected.
  449.         ''' If it was, then testing LLMHF_LOWER_IL_INJECTED (bit 1) will tell you
  450.         ''' whether or not the event was injected from a process running at lower integrity level.
  451.         ''' </summary>
  452.         <Flags()>
  453.         Public Enum MsllHookStructFlags As Integer
  454.  
  455.             ''' <summary>
  456.             ''' Test the event-injected (from any process) flag.
  457.             ''' </summary>
  458.             LLMHF_INJECTED = 1I
  459.  
  460.             ''' <summary>
  461.             ''' Test the event-injected (from a process running at lower integrity level) flag.
  462.             ''' </summary>
  463.             LLMHF_LOWER_IL_INJECTED = 2I
  464.  
  465.         End Enum
  466.  
  467. #End Region
  468.  
  469. #Region " Structures "
  470.  
  471.         ''' <summary>
  472.         ''' The POINT structure defines the x- and y- coordinates of a point.
  473.         ''' MSDN Documentation: http://msdn.microsoft.com/en-us/library/windows/desktop/dd162805%28v=vs.85%29.aspx
  474.         ''' </summary>
  475.         <StructLayout(LayoutKind.Sequential)>
  476.         Public Structure Point
  477.  
  478.             ''' <summary>
  479.             ''' The x-coordinate of the point.
  480.             ''' </summary>
  481.             Public X As Integer
  482.  
  483.             ''' <summary>
  484.             ''' The y-coordinate of the point.
  485.             ''' </summary>
  486.             Public Y As Integer
  487.  
  488.         End Structure
  489.  
  490.         ''' <summary>
  491.         ''' Contains information about a low-level mouse input event.
  492.         ''' MSDN Documentation: http://msdn.microsoft.com/en-us/library/windows/desktop/ms644970%28v=vs.85%29.aspx
  493.         ''' </summary>
  494.         Public Structure MsllHookStruct
  495.  
  496.             ''' <summary>
  497.             ''' The ptThe x- and y-coordinates of the cursor, in screen coordinates.
  498.             ''' </summary>
  499.             Public Pt As NativeMethods.Point
  500.  
  501.             ''' <summary>
  502.             ''' If the message is 'WM_MOUSEWHEEL', the high-order word of this member is the wheel delta.
  503.             ''' The low-order word is reserved.
  504.             ''' A positive value indicates that the wheel was rotated forward, away from the user;
  505.             ''' a negative value indicates that the wheel was rotated backward, toward the user.
  506.             ''' One wheel click is defined as 'WHEEL_DELTA', which is '120'.
  507.             ''' </summary>
  508.             Public MouseData As Integer
  509.  
  510.             ''' <summary>
  511.             ''' The event-injected flag.
  512.             ''' </summary>
  513.             Public Flags As MsllHookStructFlags
  514.  
  515.             ''' <summary>
  516.             ''' The time stamp for this message.
  517.             ''' </summary>
  518.             Public Time As UInteger
  519.  
  520.             ''' <summary>
  521.             ''' Additional information associated with the message.
  522.             ''' </summary>
  523.             Public DwExtraInfo As IntPtr
  524.  
  525.         End Structure
  526.  
  527. #End Region
  528.  
  529. #Region " Delegates "
  530.  
  531.         ''' <summary>
  532.         ''' Delegate LowLevelMouseProc
  533.         ''' MSDN Documentation: http://msdn.microsoft.com/en-us/library/windows/desktop/ms644986%28v=vs.85%29.aspx
  534.         ''' </summary>
  535.         ''' <returns>
  536.         ''' If nCode is less than zero, the hook procedure must return the value returned by CallNextHookEx.
  537.         ''' If nCode is greater than or equal to zero, and the hook procedure did not process the message,
  538.         ''' it is highly recommended that you call CallNextHookEx and return the value it returns;
  539.         ''' otherwise, other applications that have installed WH_MOUSE_LL hooks will not receive hook notifications
  540.         ''' and may behave incorrectly as a result.
  541.         ''' If the hook procedure processed the message,
  542.         ''' it may return a nonzero value to prevent the system from passing the message to the rest of the hook chain or the target window procedure.
  543.         ''' </returns>
  544.         Public Delegate Function LowLevelMouseProcDelegate(
  545.                 ByVal nCode As Integer,
  546.                 ByVal wParam As NativeMethods.WindowsMessages,
  547.                 ByVal lParam As IntPtr
  548.         ) As Integer
  549.  
  550. #End Region
  551.  
  552. #Region " Hidden Methods "
  553.  
  554.         ''' <summary>
  555.         ''' Determines whether the specified System.Object instances are considered equal.
  556.         ''' </summary>
  557.         <EditorBrowsable(EditorBrowsableState.Never)>
  558.         Public Shadows Sub Equals()
  559.         End Sub
  560.  
  561.         ''' <summary>
  562.         ''' Determines whether the specified System.Object instances are the same instance.
  563.         ''' </summary>
  564.         <EditorBrowsable(EditorBrowsableState.Never)>
  565.         Private Shadows Sub ReferenceEquals()
  566.         End Sub
  567.  
  568. #End Region
  569.  
  570.     End Class
  571.  
  572. #End Region
  573.  
  574. #Region " Properties "
  575.  
  576.     ''' <summary>
  577.     ''' Handle to the hook procedure.
  578.     ''' </summary>
  579.     Private Property MouseHook As IntPtr
  580.  
  581.     ''' <summary>
  582.     ''' The mouse hook delegate.
  583.     ''' </summary>
  584.     Private Property MouseHookDelegate As NativeMethods.LowLevelMouseProcDelegate
  585.  
  586.     ''' <summary>
  587.     ''' Determines whether the Hook is installed.
  588.     ''' </summary>
  589.     Public Property IsInstalled As Boolean
  590.  
  591.     ''' <summary>
  592.     ''' Determines whether the Hook is enabled.
  593.     ''' </summary>
  594.     Public Property IsEnabled As Boolean = False
  595.  
  596.     ''' <summary>
  597.     ''' ** ONLY FOR TESTING PURPOSES **
  598.     ''' Gets or sets a value indicating whether to suppress the last MouseUp event of
  599.     ''' the specified clicked button when a double-click fires.
  600.     '''
  601.     ''' If this value is set to <c>true</c>, the application will send the events in this order for a Double-Click:
  602.     ''' MouseDown, MouseUp, MouseDown, MouseDoubleClick
  603.     '''
  604.     ''' If this value is set to <c>false</c>, the application will send the events in this order for a Double-Click:
  605.     ''' MouseDown, MouseUp, MouseDown, MouseUp, MouseDoubleClick
  606.     '''
  607.     ''' </summary>
  608.     ''' <value><c>true</c> if MouseUp event is suppressed; otherwise <c>false</c>.</value>
  609.     Public Property SuppressMouseUpEventWhenDoubleClick As Boolean = False
  610.  
  611.     ''' <summary>
  612.     ''' Gets or sets the screen's working area.
  613.     ''' The events fired by this <see cref="MouseHook"/> instance will be restricted to the bounds of the specified rectangle.
  614.     ''' </summary>
  615.     ''' <value>The screen's working area.</value>
  616.     Public Property WorkingArea As Rectangle
  617.         Get
  618.             Return Me.workingarea1
  619.         End Get
  620.         Set(ByVal value As Rectangle)
  621.             Me.workingarea1 = value
  622.         End Set
  623.     End Property
  624.  
  625.     ''' <summary>
  626.     ''' The screen's working area
  627.     ''' </summary>
  628.     Private workingarea1 As Rectangle = SystemInformation.VirtualScreen
  629.  
  630. #End Region
  631.  
  632. #Region " Enumerations "
  633.  
  634.     ''' <summary>
  635.     ''' Indicates the whell direction of the mouse.
  636.     ''' </summary>
  637.     Public Enum WheelDirection As Integer
  638.  
  639.         ''' <summary>
  640.         ''' The wheel is moved up.
  641.         ''' </summary>
  642.         WheelUp = 1I
  643.  
  644.         ''' <summary>
  645.         ''' The wheel is moved down.
  646.         ''' </summary>
  647.         WheelDown = 2I
  648.  
  649.     End Enum
  650.  
  651. #End Region
  652.  
  653. #Region " Events "
  654.  
  655.     ''' <summary>
  656.     ''' Occurs when the mouse moves.
  657.     ''' </summary>
  658.     Public Event MouseMove(ByVal sender As Object,
  659.                            ByVal mouseLocation As Point)
  660.  
  661.     ''' <summary>
  662.     ''' Occurs when the mouse left button is pressed.
  663.     ''' </summary>
  664.     Public Event MouseLeftDown(ByVal sender As Object,
  665.                                ByVal mouseLocation As Point)
  666.  
  667.     ''' <summary>
  668.     ''' Occurs when the mouse left button is released.
  669.     ''' </summary>
  670.     Public Event MouseLeftUp(ByVal sender As Object,
  671.                              ByVal mouseLocation As Point)
  672.  
  673.     ''' <summary>
  674.     ''' Occurs when the mouse left button performs a double-click.
  675.     ''' A double click is considered as: (MouseLeftDown + MouseLeftUp) * 2
  676.     ''' </summary>
  677.     Public Event MouseLeftDoubleClick(ByVal sender As Object,
  678.                                       ByVal mouseLocation As Point)
  679.  
  680.     ''' <summary>
  681.     ''' Occurs when the mouse right button is pressed.
  682.     ''' </summary>
  683.     Public Event MouseRightDown(ByVal sender As Object,
  684.                                 ByVal mouseLocation As Point)
  685.  
  686.     ''' <summary>
  687.     ''' Occurs when the mouse right button is released.
  688.     ''' </summary>
  689.     Public Event MouseRightUp(ByVal sender As Object,
  690.                               ByVal mouseLocation As Point)
  691.  
  692.     ''' <summary>
  693.     ''' Occurs when the mouse right button performs a double-click.
  694.     ''' A double click is considered as: (MouseLeftDown + MouseLeftUp) * 2
  695.     ''' </summary>
  696.     Public Event MouseRightDoubleClick(ByVal sender As Object,
  697.                                        ByVal mouseLocation As Point)
  698.  
  699.     ''' <summary>
  700.     ''' Occurs when the mouse middle button is pressed.
  701.     ''' </summary>
  702.     Public Event MouseMiddleDown(ByVal sender As Object,
  703.                                  ByVal mouseLocation As Point)
  704.  
  705.     ''' <summary>
  706.     ''' Occurs when the mouse middle button is released.
  707.     ''' </summary>
  708.     Public Event MouseMiddleUp(ByVal sender As Object,
  709.                                ByVal mouseLocation As Point)
  710.  
  711.     ''' <summary>
  712.     ''' Occurs when the mouse middle button performs a double-click.
  713.     ''' A double click is considered as: (MouseLeftDown + MouseLeftUp) * 2
  714.     ''' </summary>
  715.     Public Event MouseMiddleDoubleClick(ByVal sender As Object,
  716.                                         ByVal mouseLocation As Point)
  717.  
  718.     ''' <summary>
  719.     ''' Occurs when the mouse wheel is moved up or down.
  720.     ''' </summary>
  721.     Public Event MouseWheel(ByVal sender As Object,
  722.                             ByVal mouseLocation As Point,
  723.                             ByVal wheelDirection As WheelDirection)
  724.  
  725. #End Region
  726.  
  727. #Region " Exceptions "
  728.  
  729.     ''' <summary>
  730.     ''' Exception that is thrown when trying to enable or uninstall a mouse hook that is not installed.
  731.     ''' </summary>
  732.     <Serializable>
  733.     Friend NotInheritable Class MouseHookNotInstalledException : Inherits Exception
  734.  
  735.         ''' <summary>
  736.         ''' Initializes a new instance of the <see cref="MouseHookNotInstalledException"/> class.
  737.         ''' </summary>
  738.         Friend Sub New()
  739.             MyBase.New("MouseHook is not installed.")
  740.         End Sub
  741.  
  742.         ''' <summary>
  743.         ''' Initializes a new instance of the <see cref="MouseHookNotInstalledException" /> class with a specified error message.
  744.         ''' </summary>
  745.         ''' <param name="message">The message that describes the error.</param>
  746.         Friend Sub New(message As String)
  747.             MyBase.New(message)
  748.         End Sub
  749.  
  750.         ''' <summary>
  751.         ''' Initializes a new instance of the <see cref="MouseHookNotInstalledException"/> class.
  752.         ''' </summary>
  753.         ''' <param name="message">The message that describes the error.</param>
  754.         ''' <param name="inner">The inner exception.</param>
  755.         Friend Sub New(message As String, inner As Exception)
  756.             MyBase.New(message, inner)
  757.         End Sub
  758.  
  759.     End Class
  760.  
  761.     ''' <summary>
  762.     ''' Exception that is thrown when trying to disable a mouse hook that is not enabled.
  763.     ''' </summary>
  764.     <Serializable>
  765.     Friend NotInheritable Class MouseHookNotEnabledException : Inherits Exception
  766.  
  767.         ''' <summary>
  768.         ''' Initializes a new instance of the <see cref="MouseHookNotEnabledException"/> class.
  769.         ''' </summary>
  770.         Friend Sub New()
  771.             MyBase.New("MouseHook is not enabled.")
  772.         End Sub
  773.  
  774.         ''' <summary>
  775.         ''' Initializes a new instance of the <see cref="MouseHookNotEnabledException" /> class with a specified error message.
  776.         ''' </summary>
  777.         ''' <param name="message">The message that describes the error.</param>
  778.         Friend Sub New(message As String)
  779.             MyBase.New(message)
  780.         End Sub
  781.  
  782.         ''' <summary>
  783.         ''' Initializes a new instance of the <see cref="MouseHookNotEnabledException"/> class.
  784.         ''' </summary>
  785.         ''' <param name="message">The message that describes the error.</param>
  786.         ''' <param name="inner">The inner exception.</param>
  787.         Friend Sub New(message As String, inner As Exception)
  788.             MyBase.New(message, inner)
  789.         End Sub
  790.  
  791.     End Class
  792.  
  793.     ''' <summary>
  794.     ''' Exception that is thrown when trying to enable a mouse hook that is already enabled.
  795.     ''' </summary>
  796.     <Serializable>
  797.     Friend NotInheritable Class MouseHookEnabledException : Inherits Exception
  798.  
  799.         ''' <summary>
  800.         ''' Initializes a new instance of the <see cref="MouseHookEnabledException"/> class.
  801.         ''' </summary>
  802.         Friend Sub New()
  803.             MyBase.New("MouseHook is already enabled.")
  804.         End Sub
  805.  
  806.         ''' <summary>
  807.         ''' Initializes a new instance of the <see cref="MouseHookEnabledException" /> class with a specified error message.
  808.         ''' </summary>
  809.         ''' <param name="message">The message that describes the error.</param>
  810.         Friend Sub New(message As String)
  811.             MyBase.New(message)
  812.         End Sub
  813.  
  814.         ''' <summary>
  815.         ''' Initializes a new instance of the <see cref="MouseHookEnabledException"/> class.
  816.         ''' </summary>
  817.         ''' <param name="message">The message that describes the error.</param>
  818.         ''' <param name="inner">The inner exception.</param>
  819.         Friend Sub New(message As String, inner As Exception)
  820.             MyBase.New(message, inner)
  821.         End Sub
  822.  
  823.     End Class
  824.  
  825. #End Region
  826.  
  827. #Region " Constructors "
  828.  
  829.     ''' <summary>
  830.     ''' Prevents a default instance of the <see cref="MouseHook"/> class from being created.
  831.     ''' </summary>
  832.     Private Sub New()
  833.     End Sub
  834.  
  835.     ''' <summary>
  836.     ''' Initializes a new instance of the <see cref="MouseHook"/> class.
  837.     ''' </summary>
  838.     ''' <param name="Install">
  839.     ''' If set to <c>true</c>, the Hook starts initialized for this <see cref="MouseHook"/> instance.
  840.     ''' </param>
  841.     Public Sub New(Optional ByVal install As Boolean = False)
  842.  
  843.         If install Then
  844.             Me.Install()
  845.         End If
  846.  
  847.     End Sub
  848.  
  849. #End Region
  850.  
  851. #Region " Public Methods "
  852.  
  853.     ''' <summary>
  854.     ''' Installs the Mouse Hook, then start processing messages to fire events.
  855.     ''' </summary>
  856.     Public Sub Install()
  857.  
  858.         If Me.IsVisualStudioHostingProcessEnabled() Then
  859.             Throw New Exception("Visual Studio Hosting Process should be deactivated.")
  860.             Exit Sub
  861.         End If
  862.  
  863.         Me.MouseHookDelegate = New NativeMethods.LowLevelMouseProcDelegate(AddressOf LowLevelMouseProc)
  864.  
  865.         Try
  866.             Me.MouseHook = NativeMethods.SetWindowsHookEx(NativeMethods.HookType.WH_MOUSE_LL,
  867.                                                           Me.MouseHookDelegate,
  868.                                                           New IntPtr(Marshal.GetHINSTANCE(Assembly.GetExecutingAssembly.GetModules()(0)).ToInt32), 0)
  869.  
  870.             Me.IsInstalled = True
  871.  
  872.         Catch ex As Exception
  873.             Throw
  874.  
  875.         End Try
  876.  
  877.     End Sub
  878.  
  879.     ''' <summary>
  880.     ''' Uninstalls the Mouse Hook and free all resources, then stop processing messages to fire events.
  881.     ''' </summary>
  882.     Public Sub Uninstall()
  883.  
  884.         If Not Me.IsInstalled Then
  885.             Throw New MouseHookNotInstalledException
  886.  
  887.         Else
  888.             Me.IsEnabled = False
  889.             Me.IsInstalled = False
  890.             Me.Finalize()
  891.  
  892.         End If
  893.  
  894.     End Sub
  895.  
  896.     ''' <summary>
  897.     ''' Temporally disables the Mouse Hook events.
  898.     ''' To Re-enable the events, call the <see cref="Enable"/> method.
  899.     ''' </summary>
  900.     Public Sub Disable()
  901.  
  902.         If Not Me.IsInstalled Then
  903.             Throw New MouseHookNotInstalledException
  904.  
  905.         ElseIf Not Me.IsEnabled Then
  906.             Throw New MouseHookNotEnabledException
  907.  
  908.         Else
  909.             Me.IsEnabled = False
  910.  
  911.         End If
  912.  
  913.     End Sub
  914.  
  915.     ''' <summary>
  916.     ''' Re-enables the Mouse Hook events.
  917.     ''' </summary>
  918.     Public Sub Enable()
  919.  
  920.         If Not Me.IsInstalled Then
  921.             Throw New MouseHookNotInstalledException
  922.  
  923.         ElseIf Me.IsEnabled Then
  924.             Throw New MouseHookEnabledException
  925.  
  926.         Else
  927.             Me.IsEnabled = True
  928.  
  929.         End If
  930.  
  931.     End Sub
  932.  
  933. #End Region
  934.  
  935. #Region " Private Methods "
  936.  
  937.     ''' <summary>
  938.     ''' Determines whether the Visual Studio Hosting Process is enabled on the current application.
  939.     ''' </summary>
  940.     ''' <returns><c>true</c> if Visual Studio Hosting Process is enabled; otherwise, <c>false</c>.</returns>
  941.     Private Function IsVisualStudioHostingProcessEnabled() As Boolean
  942.         Return AppDomain.CurrentDomain.FriendlyName.EndsWith("vshost.exe", StringComparison.OrdinalIgnoreCase)
  943.     End Function
  944.  
  945.     ''' <summary>
  946.     ''' Processes the mouse windows messages and raises it's corresponding events.
  947.     ''' MSDN Documentation: http://msdn.microsoft.com/en-us/library/windows/desktop/ms644986%28v=vs.85%29.aspx
  948.     ''' </summary>
  949.     ''' <param name="nCode">
  950.     ''' A code the hook procedure uses to determine how to process the message.
  951.     ''' If nCode is less than zero, the hook procedure must pass the message to the CallNextHookEx function
  952.     ''' without further processing and should return the value returned by CallNextHookEx.
  953.     ''' </param>
  954.     ''' <param name="wParam">The identifier of the mouse message.</param>
  955.     ''' <param name="lParam"> A pointer to an <see cref="NativeMethods.MSLLHOOKSTRUCT"/> structure.</param>
  956.     ''' <returns>
  957.     ''' If nCode is less than zero, the hook procedure must return the value returned by CallNextHookEx.
  958.     ''' If nCode is greater than or equal to zero, and the hook procedure did not process the message,
  959.     ''' it is highly recommended that you call CallNextHookEx and return the value it returns;
  960.     ''' otherwise, other applications that have installed WH_MOUSE_LL hooks will not receive hook notifications
  961.     ''' and may behave incorrectly as a result.
  962.     ''' If the hook procedure processed the message,
  963.     ''' it may return a nonzero value to prevent the system from passing the
  964.     ''' message to the rest of the hook chain or the target window procedure.
  965.     ''' </returns>
  966.     Private Function LowLevelMouseProc(ByVal nCode As Integer,
  967.                                        ByVal wParam As NativeMethods.WindowsMessages,
  968.                                        ByVal lParam As IntPtr) As Integer
  969.  
  970.         If Not Me.IsEnabled Then
  971.             Return CInt(NativeMethods.CallNextHookEx(MouseHook, nCode, New IntPtr(wParam), lParam))
  972.         End If
  973.  
  974.         Static leftClickTime As Integer = 0I ' Determines a left button double-click.
  975.         Static rightClickTime As Integer = 0I ' Determines a right button double-click.
  976.         Static middleClickTime As Integer = 0I ' Determines a middle button double-click.
  977.  
  978.         If nCode = 0I Then
  979.  
  980.             Dim x As Integer
  981.             Dim y As Integer
  982.  
  983.             Dim mouseStruct As NativeMethods.MsllHookStruct
  984.             mouseStruct = CType(Marshal.PtrToStructure(lParam, mouseStruct.GetType()),
  985.                                 NativeMethods.MsllHookStruct)
  986.  
  987.             ' Fix X coordinate.
  988.             Select Case mouseStruct.Pt.X
  989.  
  990.                 Case Is <= 0I
  991.                     If mouseStruct.Pt.X >= Me.WorkingArea.Location.X Then
  992.                         x = mouseStruct.Pt.X
  993.  
  994.                     ElseIf mouseStruct.Pt.X <= Me.WorkingArea.Location.X Then
  995.  
  996.                         If mouseStruct.Pt.X <= (Me.WorkingArea.Location.X - Me.WorkingArea.Width) Then
  997.                             x = (Me.WorkingArea.Location.X - Me.WorkingArea.Width)
  998.                         Else
  999.                             x = mouseStruct.Pt.X
  1000.  
  1001.                         End If
  1002.  
  1003.                     End If
  1004.  
  1005.                 Case Is >= Me.WorkingArea.Width
  1006.                     x = Me.WorkingArea.Width
  1007.  
  1008.                 Case Else
  1009.                     x = mouseStruct.Pt.X
  1010.  
  1011.             End Select
  1012.  
  1013.             ' Fix Y coordinate.
  1014.             Select Case mouseStruct.Pt.Y
  1015.  
  1016.                 Case Is >= Me.WorkingArea.Height
  1017.                     y = Me.WorkingArea.Height
  1018.  
  1019.                 Case Is <= 0I
  1020.                     y = 0I
  1021.  
  1022.                 Case Else
  1023.                     y = mouseStruct.Pt.Y
  1024.  
  1025.             End Select
  1026.  
  1027.             If x <= Me.WorkingArea.Width AndAlso
  1028.                y < Me.WorkingArea.Height AndAlso
  1029.                mouseStruct.Pt.X > Me.WorkingArea.Width Then
  1030.                 Return CInt(NativeMethods.CallNextHookEx(MouseHook, nCode, New IntPtr(wParam), lParam))
  1031.  
  1032.             ElseIf x <= Me.WorkingArea.Width AndAlso
  1033.                    y < Me.WorkingArea.Height AndAlso
  1034.                    mouseStruct.Pt.X < Me.WorkingArea.X Then
  1035.                 Return CInt(NativeMethods.CallNextHookEx(MouseHook, nCode, New IntPtr(wParam), lParam))
  1036.  
  1037.             ElseIf x = Me.WorkingArea.Width AndAlso
  1038.                    y < Me.WorkingArea.Height Then
  1039.  
  1040.                 If Not Me.WorkingArea.Contains(x - 1, y) Then
  1041.                     Return CInt(NativeMethods.CallNextHookEx(MouseHook, nCode, New IntPtr(wParam), lParam))
  1042.                 End If
  1043.  
  1044.             ElseIf x < Me.WorkingArea.Width AndAlso
  1045.                    y = Me.WorkingArea.Height Then
  1046.  
  1047.                 If Not Me.WorkingArea.Contains(x, y - 1) Then
  1048.                     Return CInt(NativeMethods.CallNextHookEx(MouseHook, nCode, New IntPtr(wParam), lParam))
  1049.                 End If
  1050.  
  1051.             End If
  1052.  
  1053.             Select Case wParam
  1054.  
  1055.                 Case NativeMethods.WindowsMessages.WM_MOUSEMOVE
  1056.                     RaiseEvent MouseMove(Me, New Point(x, y))
  1057.  
  1058.                 Case NativeMethods.WindowsMessages.WM_LBUTTONDOWN
  1059.                     RaiseEvent MouseLeftDown(Me, New Point(x, y))
  1060.  
  1061.                 Case NativeMethods.WindowsMessages.WM_LBUTTONUP
  1062.                     If leftClickTime <> 0 Then
  1063.                         leftClickTime = Environment.TickCount() - leftClickTime
  1064.                     End If
  1065.  
  1066.                     If (leftClickTime <> 0I) AndAlso (leftClickTime < NativeMethods.GetDoubleClickTime()) Then
  1067.                         leftClickTime = 0I
  1068.                         If Not Me.SuppressMouseUpEventWhenDoubleClick Then
  1069.                             RaiseEvent MouseLeftUp(Me, New Point(x, y))
  1070.                         End If
  1071.                         RaiseEvent MouseLeftDoubleClick(Me, New Point(x, y))
  1072.  
  1073.                     Else
  1074.                         leftClickTime = Environment.TickCount()
  1075.                         RaiseEvent MouseLeftUp(Me, New Point(x, y))
  1076.  
  1077.                     End If
  1078.  
  1079.                 Case NativeMethods.WindowsMessages.WM_RBUTTONDOWN
  1080.                     RaiseEvent MouseRightDown(Me, New Point(x, y))
  1081.  
  1082.                 Case NativeMethods.WindowsMessages.WM_RBUTTONUP
  1083.                     If rightClickTime <> 0I Then
  1084.                         rightClickTime = Environment.TickCount() - rightClickTime
  1085.                     End If
  1086.  
  1087.                     If (rightClickTime <> 0I) AndAlso (rightClickTime < NativeMethods.GetDoubleClickTime()) Then
  1088.                         rightClickTime = 0I
  1089.                         If Not Me.SuppressMouseUpEventWhenDoubleClick Then
  1090.                             RaiseEvent MouseRightUp(Me, New Point(x, y))
  1091.                         End If
  1092.                         RaiseEvent MouseRightDoubleClick(Me, New Point(x, y))
  1093.  
  1094.                     Else
  1095.                         rightClickTime = Environment.TickCount()
  1096.                         RaiseEvent MouseRightUp(Me, New Point(x, y))
  1097.  
  1098.                     End If
  1099.  
  1100.                 Case NativeMethods.WindowsMessages.WM_MBUTTONDOWN
  1101.                     RaiseEvent MouseMiddleDown(Me, New Point(x, y))
  1102.  
  1103.                 Case NativeMethods.WindowsMessages.WM_MBUTTONUP
  1104.                     If middleClickTime <> 0I Then
  1105.                         middleClickTime = Environment.TickCount() - middleClickTime
  1106.                     End If
  1107.  
  1108.                     If (middleClickTime <> 0I) AndAlso (middleClickTime < NativeMethods.GetDoubleClickTime()) Then
  1109.                         middleClickTime = 0I
  1110.                         If Not Me.SuppressMouseUpEventWhenDoubleClick Then
  1111.                             RaiseEvent MouseMiddleUp(Me, New Point(x, y))
  1112.                         End If
  1113.                         RaiseEvent MouseMiddleDoubleClick(Me, New Point(x, y))
  1114.  
  1115.                     Else
  1116.                         middleClickTime = Environment.TickCount()
  1117.                         RaiseEvent MouseMiddleUp(Me, New Point(x, y))
  1118.  
  1119.                     End If
  1120.  
  1121.                 Case NativeMethods.WindowsMessages.WM_MOUSEWHEEL
  1122.                     RaiseEvent MouseWheel(Me, New Point(x, y), If(mouseStruct.MouseData < 0I,
  1123.                                                                  WheelDirection.WheelDown,
  1124.                                                                  WheelDirection.WheelUp))
  1125.  
  1126.                 Case Else
  1127.                     ' Do Nothing
  1128.                     Exit Select
  1129.  
  1130.             End Select
  1131.  
  1132.             Return CInt(NativeMethods.CallNextHookEx(MouseHook, nCode, New IntPtr(wParam), lParam))
  1133.  
  1134.         ElseIf nCode < 0I Then
  1135.             Return CInt(NativeMethods.CallNextHookEx(MouseHook, nCode, New IntPtr(wParam), lParam))
  1136.  
  1137.         Else ' nCode > 0
  1138.             Return CInt(NativeMethods.CallNextHookEx(MouseHook, nCode, New IntPtr(wParam), lParam))
  1139.  
  1140.         End If
  1141.  
  1142.     End Function
  1143.  
  1144. #End Region
  1145.  
  1146. #Region " Hidden Methods "
  1147.  
  1148.     ''' <summary>
  1149.     ''' Serves as a hash function for a particular type.
  1150.     ''' </summary>
  1151.     <EditorBrowsable(EditorBrowsableState.Never)>
  1152.     Public Shadows Sub GetHashCode()
  1153.     End Sub
  1154.  
  1155.     ''' <summary>
  1156.     ''' Gets the System.Type of the current instance.
  1157.     ''' </summary>
  1158.     ''' <returns>The exact runtime type of the current instance.</returns>
  1159.     <EditorBrowsable(EditorBrowsableState.Never)>
  1160.     Public Shadows Function [GetType]() As Type
  1161.         Return Me.GetType
  1162.     End Function
  1163.  
  1164.     ''' <summary>
  1165.     ''' Determines whether the specified System.Object instances are considered equal.
  1166.     ''' </summary>
  1167.     <EditorBrowsable(EditorBrowsableState.Never)>
  1168.     Public Shadows Sub Equals()
  1169.     End Sub
  1170.  
  1171.     ''' <summary>
  1172.     ''' Determines whether the specified System.Object instances are the same instance.
  1173.     ''' </summary>
  1174.     <EditorBrowsable(EditorBrowsableState.Never)>
  1175.     Private Shadows Sub ReferenceEquals()
  1176.     End Sub
  1177.  
  1178.     ''' <summary>
  1179.     ''' Returns a String that represents the current object.
  1180.     ''' </summary>
  1181.     <EditorBrowsable(EditorBrowsableState.Never)>
  1182.     Public Shadows Sub ToString()
  1183.     End Sub
  1184.  
  1185. #End Region
  1186.  
  1187. #Region "IDisposable Support"
  1188.  
  1189.     ''' <summary>
  1190.     ''' Flag to detect redundant calls at <see cref="Dispose"/> method.
  1191.     ''' </summary>
  1192.     Private disposedValue As Boolean
  1193.  
  1194.     ''' <summary>
  1195.     ''' Releases unmanaged and optionally managed resources.
  1196.     ''' </summary>
  1197.     ''' <param name="disposing">
  1198.     ''' <c>true</c> to release both managed and unmanaged resources;
  1199.     ''' <c>false</c> to release only unmanaged resources.
  1200.     ''' </param>
  1201.     Protected Sub Dispose(ByVal disposing As Boolean)
  1202.  
  1203.         Me.IsEnabled = False
  1204.  
  1205.         If Not Me.disposedValue Then
  1206.  
  1207.             If disposing Then ' Dispose managed state (managed objects).
  1208.  
  1209.             Else ' Free unmanaged resources (unmanaged objects).
  1210.                 NativeMethods.UnhookWindowsHookEx(Me.MouseHook)
  1211.  
  1212.             End If
  1213.  
  1214.         End If
  1215.  
  1216.         Me.disposedValue = True
  1217.  
  1218.     End Sub
  1219.  
  1220.     ''' <summary>
  1221.     ''' Allows an object to try to free resources
  1222.     ''' and perform other cleanup operations before it is reclaimed by garbage collection.
  1223.     ''' </summary>
  1224.     Protected Overrides Sub Finalize()
  1225.  
  1226.         ' Do not change this code. Put cleanup code in method: Dispose(ByVal disposing As Boolean)
  1227.  
  1228.         Me.Dispose(disposing:=False)
  1229.         MyBase.Finalize()
  1230.  
  1231.     End Sub
  1232.  
  1233.     ''' <summary>
  1234.     ''' Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources.
  1235.     ''' </summary>
  1236.     Private Sub Dispose() Implements IDisposable.Dispose
  1237.  
  1238.         ' Do not change this code. Put cleanup code in method: Dispose(ByVal disposing As Boolean)
  1239.  
  1240.         Me.Dispose(disposing:=True)
  1241.         GC.SuppressFinalize(obj:=Me)
  1242.  
  1243.     End Sub
  1244.  
  1245. #End Region
  1246.  
  1247. End Class
  1248.  
  1249. #End Region
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement