Jump to content
Fr0sT.Brutal

[solved] Dragging a control - TControl.BeginDrag oddity

Recommended Posts

SOLVED - SEE BELOW

 

I have a control that starts dragging on mouse down and finishes on up. I noticed weird bug - the drag won't start though MouseDown is executed and  TControl.BeginDrag is called. Stepping into that method I found this:

...
  if (DragControl = nil) or (DragControl = FlagControl) then
  begin
    DragControl := nil;
    if csLButtonDown in ControlState then
    begin
      GetCursorPos(P);
      Perform(WM_LBUTTONUP, 0, PointToLParam(ScreenToClient(P))); // ???
    end;
...

for some reason the method calls my MouseUp which, in turn, finishes dragging.

I tried adding a check to my MouseUp (ignore if in dragging mode, finish it in DragOver) but this doesn't work when the dragging starts from MouseDown handler. Of course I could add internal flag field like

fCallingBeginDrag := True;
BeginDrag;
fCallingBeginDrag := False

but this looks too awkward. Probably there's any smarter way?

Edited by Fr0sT.Brutal
solved

Share this post


Link to post

You can check the tab dragging in AE.Comp.PageControl, I'm handling the dragging of tabs almost the same way. The only difference I see is creating a DragObject in DoStartDrag but that shouldn't affect the check above as it's called from DragInitControl, which is called later.

Share this post


Link to post

Thanks, I'll take a look.

I see you are using zero point as null value but it's a valid click point in fact. I'm using to (-1,-1) for this purpose

Share this post


Link to post

That makes a lot of sense, thanks for pointing it out! As it caused no issues until now I didn’t even notice :)

Maybe I’ll update it if I have to make a change in the component.

Share this post


Link to post

I guess I figured things out. The catch is that when dragging, no "mouse up" event is fired when a user releases the button. I wasn't aware of that. So the solution is:

- in MouseUp ignore the event when in dragging mode (it's a MLB Up event fired by TControl.BeginDrag)

- in DragOver finish dragging mode when State is dsDragLeave

Share this post


Link to post
3 hours ago, Fr0sT.Brutal said:

- in DragOver finish dragging mode when State is dsDragLeave

Update: this is unreliable. The event is not called if there was just a simple click. I had to catch DoEndDrag as well.

Share this post


Link to post

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×