MouseLeave not fired C# WinForms - c#

I have a user control with 2 buttons, that should only be visible when the mouse is inside the area of the control.
I'm showing the buttons like this:
private void Node_MouseEnter(object sender, EventArgs e)
{
btn1.Show();
btn2.Show();
}
And hiding like this:
protected override void OnMouseLeave(EventArgs e)
{
if (this.ClientRectangle.Contains(this.PointToClient(Control.MousePosition)))
return;
else base.OnMouseLeave(e);
}
private void Node_MouseLeave(object sender, EventArgs e)
{
btn1.Hide();
btn2.Hide();
}
The problem is that sometimes (random situations) the MouseLeave event is not fired, and the buttons stay visible, even with the mouse outside the control.
Is it possible that multiple events get in conflict ?

As this link states:
Mouse move messages are not accurate enough, they don't guarantee that every traversed pixel is reported. When you have a child window close to the edge of its parent, it is quite easy to not get the MouseEnter for the parent when you move the mouse fast enough.
So, the solution was to listen only for the MouseEnterevent, and when this event is fired, i send a notification to the other controls, to hide its buttons.
Is not the most elegant solution, but it works as expected.

Related

Changing visiblity screwing up events in C#?

I have setup a Panel that has a number of Buttons on it. These Buttons Visible Property is set to false. When I move the mouse over the Panel they became Visible and when I move the mouse out of the Panel they once again became invisible. This all works fine.
The code to do this is:
private void _Display_MouseEnter(object sender, EventArgs e)
{
foreach (Control C in _Display.Controls)
{
C.Visible = true;
}
}
private void _Display_MouseLeave(object sender, EventArgs e)
{
foreach (Control C in _Display.Controls)
{
C.Visible = false;
}
}
The problem is the Events I have set for the Buttons seem to get removed by doing this. If I don't change the Buttons visiblity the events fire as normal. I have set the events in the Designer.
Am I missing something or is this how its supposed to work and I have to resubscribe my events each time I change the Buttons visiblity?
Thanks
Danny
I did some research on that and apparently when the cursor enters one of the buttons the Panel's MouseEnter and MouseLeave events fire until the cursor leaves that button so what it does is not allowing your buttons to catch the Click event.
I think the best solution would be to get the cursor position and check if it is within your panel and then set your buttons visibility.

Event getting triggered multiple times on scroll event handler

While I was adding code to scroll event of a panel in c#, I found a strange behavior.
I have added a panel and inside the panel (auto-Scroll = true) there is a groupbox.
As shown below clicking the scroll moves scroll bar to a small distance.
At the same time, when I add a message box in the event to display a notification that a scroll has taken place, multiple message box are popping out.
Why is that?
I have already planned to add some logic when scrolling, but if it occurs multiple times then how it could be possible?
Here is the event handler:
private void panel1_Scroll_1(object sender, ScrollEventArgs e)
{
MessageBox.Show("ScrollBar is clicked");
}
This is just how scroll event works, it fires many times while the panel is scrolling.
Try ScrollEventArgs.Type EndScroll which should be the last scroll event.
private void panel1_Scroll_1(object sender, ScrollEventArgs e)
{
if (e.Type == ScrollEventType.EndScroll)
MessageBox.Show("ScrollBar is clicked");
}
If above doesn't help for your case you will need to handle those multiple events by using one of approaches explains in this thread.

Capture mouse messages when a ToolStripDropDown is shown

I am trying to create a "tooltip" which contains a custom control. I implemented it using ToolStripDropDown which does what I need - closes when the user clicks somewhere else, or activates another window etc.
However, I'd like to be able to get the MouseMove event in the parent control even when the ToolStripDropDown is shown. I tried to set the Capture property of the parent control at various stages (before showing the dropdown, in its Opened event handler etc.) but it is always immediately set back to false. Is there a way (not necessarily employing the Capture property) to get the MouseMove event in the parent control? And no, I don't want to consider ugly hacks like using a timer and periodically checking the mouse position.
If you want to know the mouse position all the time, then you should register MouseDown event for both the parent control and the ToolStripDropDown control, something like this:
private void Form1_MouseMove(object sender, MouseEventArgs e)
{
lblPosition.Text = e.Location.ToString();
}
private void toolStripDropDownButton2_MouseMove(object sender, MouseEventArgs e)
{
lblPosition.Text = e.Location.X + toolStripDropDownButton2.Bounds.Location.X + ", " + toolStripDropDownButton2.Bounds.Location.Y + e.Location.Y;
}
For ToolStripDropDown you should calculate the relative location to its parent

ToolStripButton "Reset Appearance" / "Fire Leave Event"

I have a ToolStripButton that performs an action. The user clicks the button and the button is disabled to prevent the action being performed twice. After the action is complete the button is re-enabled. It all works perfectly...except:
Because the button is disabled it does not fire the "MouseLeave" event and as a result the appearance of the button is not updated. To be absolutely clear, when the mouse enters a ToolStripButton the button is highlighted in orange (by default) with a black box around it. This highlight is not being removed when I re-enable the button. The mouse cursor is, by this time, long gone from the control. Mousing over the button naturally fixes the button by redrawing it.
What I would like to do would be some method on the ToolStripButton that "resets" its appearance. Such a method may even exist on the ToolStrip, but despite searching I have been unable to find anything like this.
As an alternative I could fire the "Mouse Leave" event on the button directly. As far as I know there is no way to easily do this in C# .NET.
Any advice at this point in time would be most appreciated, naturally I don't want to tear up my application and replace the tool strip.
Update:
I reproduced your problem, trying figuring out!
I didn't get a better way other than reset the style in the click event
private void toolStripButton1_Click(object sender, EventArgs e)
{
toolStripButton1.BackColor = Color.FromKnownColor(KnownColor.Control);
toolStripButton1.Enabled = false;
}
private void toolStripButton1_MouseEnter(object sender, EventArgs e)
{
toolStripButton1.BackColor = Color.Red;
}
private void toolStripButton1_MouseLeave(object sender, EventArgs e)
{
toolStripButton1.BackColor = Color.FromKnownColor(KnownColor.Control);
}
Hope this helps!
Have you tried Control.Invalidate()?
from MSDN: Invalidates the entire surface of the control and causes the control to be redrawn.
I had the same problem. I "fixed" it by hiding and then showing back the ToolStripButton using the Visible property after the task was complete.
Before disabling ToolStrip or ToolStripItem:
private void RemoveHighlightFromToolStrip(ToolStrip toolStrip)
{
foreach (ToolStripItem item in toolStrip.Items)
{
if (item.Pressed || item.Selected)
{
item.Visible = false;
item.Visible = true;
}
}
}
also you can just hide and show entire ToolStrip, but this may affect other controls in your form (i.e. if you have some docked DataGridView it would be redrawn)

Mouse Click event

I have a picture on background in a picture box and i have another picturebox small one above the first.now second picbox is not visible its hidden i want that if user clicks and holds mouse button small picturebox displays and as soon he removes hold i.e releases click picturebox vanishes.
now i thought of doing in click event i should make small one visiable but how to check if click is pressed not released?
sorry if i messed up with question
Use the mouse down event:
private void pictureBox1_MouseDown(object sender, MouseEventArgs e)
{
}
there you can set the focus on whatever you want
and when you release:
private void pictureBox1_MouseUp(object sender, MouseEventArgs e)
{
}
Why not use the MouseDown event in that case?

Categories

Resources