PowerPoint (or Excel) VBA Capture Coordinates of Mouse Click

Saladsamurai picture Saladsamurai · Jun 25, 2015 · Viewed 8.2k times · Source

Some Background:

The quick background is that I am in the research stages of building an add-in for PowerPoint. My end goal is to develop a CAD Dimensioning Add-in to help expedite the creating of Engineering Presentations. We have to do a lot of "PowerPoint Engineering" where the general sizes of components are shown on simplified versions of said components created with PPT shapes or screenshots of the CAD geometry itself. But creating dimensions over and over is tedious. Each one generally consists of an arrow, 2 lines, and a text box with the dimension value.

Here is where I need some help.

(If you know how to do the following in Excel, that would work too and I will work to figure the PPT equivalent later.)

In a PowerPoint slide, while in design mode (i.e. not Slide Show Mode), I want to do the following workflow:

  1. In an open UserForm, the user clicks a button called "START"
  2. The code starts to listen for a left mouse click (LMC) out in the field of the slide itself (It should not respond to a LMC on the actual UserForm, for example if the user needs to drag the UserForm out of the way)
  3. Upon LMC, coordinates of the cursor are recorded as (x1,y1)
  4. Repeat steps 2 & 3 to record (x2, y2)
  5. Do stuff with these coordinates (e.g. draw a dimension between the two coordinates

I believe I can handle all of the coding with the exception step 2, which is why I am here. I am having much trouble finding a starting point. Specifically, I need help with how to listen for a LMC. In words, what envision is the following:

While Listening:
  If LMC = TRUE
    Do Stuff
  End If
End While 

But I don't have the knowledge to code the While Listening part. I need a nudge in the right direction.

My searches have landed me on the MouseDown event handler pages at MSDN, but in my testing, I don't think that this is what I need. Its seem as though MouseDown is intended to start a routine when the Mouse is Down on a CommandButton in the UserForm it self.

I have also found this SO post where the only answer seemed to imply that this was not possible without going to great lengths AND the code was possible detrimental to the file itself: How to record mouse clicks in Excel VBA?. (I have no problem going to great lengths and putting in the work, but not if the resulting code has a high likelihood of doing damage as the post seems to suggest.) (Also, the OP was downvoted with no explanation, maybe someone can tell me why so I don't make the same mistake.)

Answer

JGoldz75 picture JGoldz75 · Jun 25, 2015

You can accomplish what you are looking to do by doing the following (the bottom part may be the most helpful to you): First, Declare the following:

Public Declare Function SetCursorPos Lib "user32" (ByVal x As Long, ByVal y As Long) As Long
Public Declare Sub mouse_event Lib "user32" (ByVal dwFlags As Long, ByVal dx As Long, ByVal dy As Long, ByVal cButtons As Long, ByVal dwExtraInfo As Long)
Public Const MOUSEEVENTF_LEFTDOWN = &H2
Public Const MOUSEEVENTF_LEFTUP = &H4
Public Const MOUSEEVENTF_RIGHTDOWN As Long = &H8
Public Const MOUSEEVENTF_RIGHTUP As Long = &H10

and the following code snippets will allow you do either click, double click, or right click:

Private Sub SingleClick()
  SetCursorPos 100, 100 'x and y position
  mouse_event MOUSEEVENTF_LEFTDOWN, 0, 0, 0, 0
  mouse_event MOUSEEVENTF_LEFTUP, 0, 0, 0, 0
End Sub

Private Sub DoubleClick()
  'Double click as a quick series of two clicks
  SetCursorPos 100, 100 'x and y position
  mouse_event MOUSEEVENTF_LEFTDOWN, 0, 0, 0, 0
  mouse_event MOUSEEVENTF_LEFTUP, 0, 0, 0, 0
  mouse_event MOUSEEVENTF_LEFTDOWN, 0, 0, 0, 0
  mouse_event MOUSEEVENTF_LEFTUP, 0, 0, 0, 0
End Sub

Private Sub RightClick()
  Right Click
  SetCursorPos 200, 200 'x and y position
  mouse_event MOUSEEVENTF_RIGHTDOWN, 0, 0, 0, 0
  mouse_event MOUSEEVENTF_RIGHTUP, 0, 0, 0, 0
End Sub

All you need to do is change the cursor position to the coordinates on the screen. To do this, I made a new macro with the following code and assigned it to the "Ctrl+Y" button. This will tell you the coordinates of your current mouse location.

Declare Function GetCursorPos Lib "user32" (lpPoint As POINTAPI) As Long
Type POINTAPI
    x As Long
    y As Long
End Type

Sub CurosrXY_Pixels()

    Dim lngStatus As Long
    Dim typWhere As POINTAPI

    lngStatus = GetCursorPos(typWhere)
    MsgBox "x: " & typWhere.x & Chr(13) & "y: " & typWhere.y, vbInformation, "Pixels"

End Sub