I am using C#, Winforms, VS 2017 Enterprise, and the full .NET Framework 4.7.2.
[TLDR section at end!]
I have been working extensively with the System.ComponentModel.Design
namespace to create working Visual Studio-like Winforms designer. Setting up the environment for such an end-user forms designer requires deep understanding of objects and interfaces in the aforementioned namespace (and how to wire-up them all) along with toolbox and property grid components. Therefore, it's not possible for me to post a sample of the code. This question requires knowledge of the DesignSurface
class (https://learn.microsoft.com/en-us/dotnet/api/system.componentmodel.design.designsurface?view=netframework-4.7.2).
The design surface seems to fire no event when a user drags a selected control across the designer surface. I need to hook into "begin-drag"/"end-drag" events so that I can perform clear and then re-render an information panel that reflects the current position of all controls. (I do not want to use timers to intermittently refresh that information.)
There is an ISelectionService
interface, which I've implemented. But that gives information only about which controls/components are selected. It doesn't help capture the event that fires when a control-drag operation begins or ends.
Details of design-surface events appear here: https://learn.microsoft.com/en-us/dotnet/api/system.componentmodel.design?view=netframework-4.7.2
I have tried to leverage IComponentChangeService's
ComponentChanged
event, but that fires only after a control-drag operation ends (and I need to detect when the control-drag operation begins and ends)...
As a last resort, I used Spy++ to see what events fire when a control is selected and dragged across the design surface. Spy++ helped me identify the initial WM.LBUTTONDOWN
message and various mouse-move messages, etc., but leveraging those messages would require a lot of additional coding to ensure that the mouse button was clicked on a designer-surface control, that the control was in fact selected, and that the mouse button remains down, etc.--and even then, I still would have no assurance that the control isn't being resized versus moved. Of course, ideally, I would want to hook into the designer-surface's logic that responds to drag-begin event.
Finally, my requirement is to detect when a single selected control is dragged or when multiple-selected controls are dragged as a group. In both cases, I need to know when the drag starts and when it ends. (To be clear: I'm referring to controls that already are on the design surface--I am not referring to controls on the toolbox that are drag-dropped onto the designer surface...)
TLDR: What I'm seeking is a way to hook into the event that fires as soon as a control or a group of controls already on a designer surface is/are dragged, and a way to hook into the event that fires when that drag operation has ended.
Any thoughts?
IComponentChangeService
hasComponentAdded
andComponentRemoved
events, which helps you to track component collection changes. – KepnerBehaviorService
and handlingBeginDrag
andEndDrag
events. – Kepner