Recent

Author Topic: Why mouse wheel scrolling generates CM_MOUSELEAVE message?  (Read 4819 times)

furious programming

  • Hero Member
  • *****
  • Posts: 858
Why mouse wheel scrolling generates CM_MOUSELEAVE message?
« on: December 17, 2017, 06:21:09 pm »
In my application I use custom package of controls, written from scratch. Some of them inherit from TGraphicControl, others from the TCustomControl. All controls works properly under Lazarus 1.6.4 with FPC 3.0.2 but after I update IDE to stable 1.8, all the controls began to wrongly handle the mouse wheel messages. All are 32-bit, old and new IDE/FPC and my application.

For example, I have a custom panel with several embedded custom buttons. When I place the cursor over the button and turn the mouse wheel, the button receives the CM_MOUSELEAVE message. It receives this message even though the cursor is still above that button…

I prepared a simple package of components and a small test application - see attachment. The second attachment contains a window recording during runtime. To reproduce the bug:
  • install controls package from attachment,
  • compile project and run,
  • when the window appears on the screen, move the cursor over any TStupidButton button and rotate the mouse wheel.
The problem occurs on WinXP 32-bit and Win7 64-bit, but not on Win10 64-bit (I have not tested on Win8). Even if I compile the project on Win10 64-bit (as 32-bit application) and transfer it to WinXP, the problem still occurs.

So, why is it like that? Does LCL have a bug in handling messages? Or maybe the code of my controls is bad? If anyone can fix this code, I am asking for guidance.
« Last Edit: December 17, 2017, 06:45:42 pm by furious programming »
Lazarus 3.2 with FPC 3.2.2, Windows 10 — all 64-bit

Working solo on an acrade, action/adventure game in retro style (pixelart), programming the engine and shell from scratch, using Free Pascal and SDL. Release planned in 2026.

jamie

  • Hero Member
  • *****
  • Posts: 6131
Re: Why mouse wheel scrolling generates CM_MOUSELEAVE message?
« Reply #1 on: December 18, 2017, 12:49:26 am »
I also had a strange problem when switching from 1.6.4 to 1.8 but from trial and
error it all got compiled and now is working as before and I didn't change anything
in the code other than putting in some Asserts to test for possible issues.

 I think what happen is when I opened all of the source file and looked at each one
the compiler at some point recompiled them all to give new updated bin unit files.

 That is all I can come up with at the moment..

 Have you tried recompiling all of your files to create new units?

 also, make sure you have not forgotten to initialize some variables.
 
The only true wisdom is knowing you know nothing

furious programming

  • Hero Member
  • *****
  • Posts: 858
Re: Why mouse wheel scrolling generates CM_MOUSELEAVE message?
« Reply #2 on: December 18, 2017, 01:07:28 am »
After every update of the environment, I rebuild the entire project. If there are any obvious problems (and they happen after every update) then I am correcting the code. If the problems are strange – I remove all binaries and rebuild the project.

This time it was not different. I rebuilt and reinstall the component package, then the main application project. Compilation in both cases did not show any problems – compiler does not show any notes, hints or warnings. The only problem is the redundant message CM_MOUSELEAVE, unnecessarily sent after turning the mouse wheel (only on WinXP/7).

I have no idea where it comes from. Not from my code, because neither in the final classes nor in the base classes, the LM_MOUSEWHEEL message is not supported (and certainly not in the button classes). Debugging did not let me know the cause of the problem.

I will add that this problem is not related to my main project. It is very easy to reproduce this glitch in a simple test application (I've added this app to attachments in my previous post).
« Last Edit: December 18, 2017, 01:19:38 am by furious programming »
Lazarus 3.2 with FPC 3.2.2, Windows 10 — all 64-bit

Working solo on an acrade, action/adventure game in retro style (pixelart), programming the engine and shell from scratch, using Free Pascal and SDL. Release planned in 2026.

jamie

  • Hero Member
  • *****
  • Posts: 6131
Re: Why mouse wheel scrolling generates CM_MOUSELEAVE message?
« Reply #3 on: December 18, 2017, 01:20:18 am »
I just ran a test over hear myself using a Tbutton and implementing the
the OnMouseleave event..

 It seems when I move the mouse into the control the leave event triggers and
it also triggers when the mouse leaves the control. However, If for example you
move the mouse into the button on the left side the second time without moving the
mouse up/down, in other words, keep the vertical position the same, the
leave event does not trigger. Hmm...  BUt once you move the mouse up/down and
then reenter the control on the sides, it then triggers a leave message once..

 I don't normally use that event so I wouldn't see it...
 I think I'll report it. It most likely is what's bothering your code.
The only true wisdom is knowing you know nothing

furious programming

  • Hero Member
  • *****
  • Posts: 858
Re: Why mouse wheel scrolling generates CM_MOUSELEAVE message?
« Reply #4 on: December 18, 2017, 06:55:35 pm »
I just ran a test over hear myself using a Tbutton and implementing the
the OnMouseleave event..

What are you talking about? I do not have a problem with the OnMouseLeave event. I have a problem with the redundant CM_MOUSELEAVE message in my own component, not in the standard TButton. Please, read the content of the first post carefully again.



The problem is real, it still exists. As long as the cause of the problem is not known to me, I implement a small patch in the code of my components, that will block the execution of the CMMouseLeave logic, if the cursor is still over the control. It is quite simple to do and works properly, regardless of the operating system.

Old code of CMMouseLeave method:

Code: Pascal  [Select][+][-]
  1. procedure TStupidButton.CMMouseLeave(var AMessage: TLMessage);
  2. begin
  3.   FHover := False;
  4.   inherited Invalidate();
  5. end;

New code:

Code: Pascal  [Select][+][-]
  1. procedure TStupidButton.CMMouseLeave(var AMessage: TLMessage);
  2. var
  3.   LControl: TControl;
  4.   LPoint: TPoint;
  5. begin
  6.   GetCursorPos(LPoint);
  7.   LControl := FindLCLControl(LPoint);
  8.  
  9.   if Assigned(LControl) and (LControl <> Self) then
  10.   begin
  11.     FHover := False;
  12.     inherited Invalidate();
  13.   end;
  14. end;

It may be temporarily, but it is not a good solution.
« Last Edit: December 18, 2017, 07:05:47 pm by furious programming »
Lazarus 3.2 with FPC 3.2.2, Windows 10 — all 64-bit

Working solo on an acrade, action/adventure game in retro style (pixelart), programming the engine and shell from scratch, using Free Pascal and SDL. Release planned in 2026.

jamie

  • Hero Member
  • *****
  • Posts: 6131
Re: Why mouse wheel scrolling generates CM_MOUSELEAVE message?
« Reply #5 on: December 18, 2017, 11:03:04 pm »
Yes I fully understand you, I didn't get confused.

 My Point was, if you have more than one control on the pad when you move
from one to the other depending on the opposite axes, it may send a CMMouseLeave
when it should not be.

 I am trying to point out an experiment I did using a Tbutton, it generates a
MouseLeave message to the control when moving into it the first time, that is
what I am trying to convey to you. This should not be happening..

 In your case you are receiving this message when you shouldn't be,...

 Also while I was experimenting, I found the Trect.Contains(SomePoint) does not
work correctly but the PtInRect does with the same Rect past to it..
Hmm..
 Something is very strange with this release of 1.8, because I looked at the
code for that method and its fine, but it does not do what the code saids it should
do?
 
 Maybe I got a corrupt copy when I downloaded it, twice!

The only true wisdom is knowing you know nothing

furious programming

  • Hero Member
  • *****
  • Posts: 858
Re: Why mouse wheel scrolling generates CM_MOUSELEAVE message?
« Reply #6 on: December 19, 2017, 04:10:19 pm »
Ok, sorry about that, I understand now.

Quote from: jamie
In your case you are receiving this message when you shouldn't be,...

Yes. Unfortunately, I can ignore redundant messages, but I can't block sending them, which means I need to patch all component classes. And I have dozens of these classes.

Situation is even worst, because when I receive an unwanted CM_MOUSELEAVE message and then I move cursor (still within the control), the CM_MOUSEENTER will be received. So I have two methods to patch – CMMouseEnter and CMMouseLeave.

Under Lazarus 1.6.4, LCL classes works different, but not good too. Parent form sometimes did not send CM_MOUSELEAVE message, when I quickly moved the cursor and it left the area of the component, outside the window. The component did not receive this message, so it still looked like the cursor was over it. I made a patch inside two of my custom base classes, based on simple timer. If control did not receive message, then the timer check the cursor position and  if it was outside the component, send it to the control – it works very good. Under Lazarus 1.8, the window does not forget to send this message, now it sends too much.
« Last Edit: December 19, 2017, 04:14:07 pm by furious programming »
Lazarus 3.2 with FPC 3.2.2, Windows 10 — all 64-bit

Working solo on an acrade, action/adventure game in retro style (pixelart), programming the engine and shell from scratch, using Free Pascal and SDL. Release planned in 2026.

jamie

  • Hero Member
  • *****
  • Posts: 6131
Re: Why mouse wheel scrolling generates CM_MOUSELEAVE message?
« Reply #7 on: December 20, 2017, 12:26:29 am »
I am curious if you are using the methods of Trect?

 Rect.Contains(SomePoint) for example?

 And also The Rect.Contains(SomeRect)?

 When I was testing for your issue, I was getting failures using the helper members
of TRect.. so in the case of Rect.Contains(SomePoint), It would report wong and
thus was really throughing my test of...
  I ended using the PtInRect and other direct APIs and those worked as they
should.

  Also, are you overriding the DoMouseLeave handler and calling the inherited
method at some point?

 When I was looking at the code, the TCONTROL sends that message down to the
parent, so if you did override it, you need to call the inherited..

 Hope you find your problems.
The only true wisdom is knowing you know nothing

furious programming

  • Hero Member
  • *****
  • Posts: 858
Re: Why mouse wheel scrolling generates CM_MOUSELEAVE message?
« Reply #8 on: December 20, 2017, 05:31:15 pm »
I am curious if you are using the methods of Trect?

Yes – in main project, many methods use this data type and its methods. But it is not a problem, because the problem exists in test application too (see attachment), which does not use TRect. So this type of data is not the essence of the problem, because it is not the reason for sending a CM_MOUSELEAVE message. Maybe in LCL classes, but not in my code.

Before I even found out that TRect has the Contains method, I wrote my own (custom TRect helper) and I still use it. I do not have any problems with this method - it works properly, I checked it under the debugger.

I will try to check it out under the debugger. Maybe I will finally find the cause.
« Last Edit: December 20, 2017, 05:41:27 pm by furious programming »
Lazarus 3.2 with FPC 3.2.2, Windows 10 — all 64-bit

Working solo on an acrade, action/adventure game in retro style (pixelart), programming the engine and shell from scratch, using Free Pascal and SDL. Release planned in 2026.

jamie

  • Hero Member
  • *****
  • Posts: 6131
Re: Why mouse wheel scrolling generates CM_MOUSELEAVE message?
« Reply #9 on: December 30, 2017, 03:51:39 am »
If you are still interested the CM_MouseLeave message issue that I found which I also think
is effecting your code has been identified and fixed.

 The fix is currently in the trunk (1.9) and will be merged at some point to 1.8.2 I guess.

 I am waiting for the 1.8.2 to come out cause the TRect.Conatains was also fixed ... Hoping that
gets merged into 1.8.2 too!
The only true wisdom is knowing you know nothing

furious programming

  • Hero Member
  • *****
  • Posts: 858
Re: Why mouse wheel scrolling generates CM_MOUSELEAVE message?
« Reply #10 on: December 30, 2017, 06:21:45 pm »
If you are still interested the CM_MouseLeave message issue that I found which I also think is effecting your code has been identified and fixed.

Yes, I'm still interested, but that problem is different than mine.
« Last Edit: December 30, 2017, 06:40:41 pm by furious programming »
Lazarus 3.2 with FPC 3.2.2, Windows 10 — all 64-bit

Working solo on an acrade, action/adventure game in retro style (pixelart), programming the engine and shell from scratch, using Free Pascal and SDL. Release planned in 2026.

Ondrej Pokorny

  • Full Member
  • ***
  • Posts: 220
Re: Why mouse wheel scrolling generates CM_MOUSELEAVE message?
« Reply #11 on: January 02, 2018, 05:19:35 am »
If you are still interested the CM_MouseLeave message issue that I found which I also think is effecting your code has been identified and fixed.

Yes, I'm still interested, but that problem is different than mine.

@furious programming: please retest with trunk. I don't see any problem with your project. If it persist, report the issue on mantis.

 

TinyPortal © 2005-2018