4

I need to detect drag and drop operations in an external application, is it possible? I thought of writing a hook to detect these operations. Can anybody point me in the right direction as far as which messages or api functions I could attempt to hook to detect the Drag & Drop events? I want to do this in C#.

Thanks in advance.

Salvador
  • 16,132
  • 33
  • 143
  • 245
  • Please say a bit more about the "external" application : it's launched by ? (you ? it could be any application ?) : it's an application you have the source to (in C# ?). And please say exactly what (or what types of things) are being dragged, and where they are being dropped (into your app ?). thanks, – BillW Nov 17 '09 at 03:35
  • The external application is always running, i dont have the source code. i want to detect when the application start and finish the drag and drop of some visual elements (controls) and detect the position where they were released. – Salvador Nov 17 '09 at 03:43

3 Answers3

4

There are two obvious paths you can go down to attempt this.

The first, is to hook the OLE functions involved in mediating drag/drop operations. This assumes that the other application is using real drag and drop and not some internal only version. Determing this is beyond my ability - without access to the program - but if its possible to drag from this external application to some other applications window (including the desktop) its a good indication that the app is using the real stuff.

The function you'd need to hook is RegisterDragDrop, though DoDragDrop may also be of interest. RegisterDragDrop is called to register a drop target, and gives you an opportunity to wrap the IDropTarget in the maner you desire (presumably IPC'ing into your actual app), RevokeDragDrop and then pass the registration on, but now with your wrapper object instead. IDropTarget::Drop is presumably where you'll do the bulk of your IPC.

The second, is by injecting a Windows hook into the application. This is only tractable if you understand the user actions that trigger a drag, and can detect them as you're going to have to distinguish between a drag operation and normal keyboard/mouse actions. The hook in question is the WH_CALLWNDPROC hook, registered with SetWindowsHookEx. Basically, you define a WndProc which gets all the messages the applications window does (including mouse movement) and its up to you to determine when a drag operation starts and when it stops.

In either case, alot of the code can be written in C#. With p\invoke you can get at SetWindowsHookEx, and you can implement COM objects (and by extension, wrappers for those COM objects) in C# as well. Infact, there's an IDropTarget class already in .NET 2.0; which might be COM visible already.

Unfortunately, hooking APIs is very low level and you're generally going to have to work in C or C++ to get anything done. I've heard good things about Detours, plus its from Microsoft.

Kevin Montrose
  • 22,191
  • 9
  • 88
  • 137
  • I tried both of these with no success, although I may have been doing it incorrectly. Does this definitely work? The problem with RegisterDragDrop seems to be if the external application that you're trying to hook may already have called that function, and you can't seem to have two registrations. Edit: I tried SetWinEventHook, not SetWindowsHookEx. Will test that! – JamEnergy Dec 09 '20 at 13:40
1

The best thing that you can do is indeed to hook into the external application. In my experience (the last time I did something like this was two years ago) the only way I could achieve an accurate hook was to use a blend of C/C++ and C#.

To do all of this, you will need to be familiar with platform invocation and the Windows SDK. Some people may say you only need the p/invoke piece, but in my explorations, I found that access to the headers and library files within the SDK was invaluable. In addition, I have found that Spy++ is an awesome tool for assistance in hooking development.

There are numerous resources out there on hooking windows application and how to communicate with external processes. I could list any number of them here, but I'm not sure what your preference is when it comes to technical articles and example projects. Personally, I have found that codeproject.com has a good number of projects on hooking with some pretty good explainations.

Best of luck to you; I hope this helps.

highvoltage
  • 121
  • 1
  • 6
0

As you mentioned yourself, you will need to use the Windows-API - thus I hope you have some experience with using unsafe code in C# or consider to use C++.
One way is described here by MS.
My guess would be that you need to look at HCBT_ACTIVATE (Window gets activated) and HCBT_CLICKSKIPPED (Mouse click) - but this is just a guess.
Another idea could be to look at Auto It Window Info - it has facilities to analyse windows - maybe you can reuse this in at a good place - so that you can save some work on the analysis part.

weismat
  • 7,195
  • 3
  • 43
  • 58