views:

1964

answers:

4

Hi all,

I am struggling with something that I think should be easily (ish). I have a windows form and a flowgridlayout panel at the bottom of the form. Inside this form I dynamically populate it with X number of User Controls. The controls are all the same type.

The goal is when the user hoovers the mouse over the user control it opens another form and positions it where the mouse is. When mouse leaves the form the opened form disappears.

This almost works great. The problem is when the User Control has anything like a label or text box inside it. It is considered to have left the UC so the form disappears.

My thought was then to use the X and Y to tell if it is inside the UC but I can not figure this out.

Can I ask:

1) What is the best approach to this? 2) How can I code it, as the UC's are dynamic I can not know exactly where they will be.

Thanks

EDIT

I am trying to figure out the mouse pointers but not getting there. The code below is within the UC SmallTagBox_MouseLeave event:

        Point loc = this.Location;
        Point p = this.PointToScreen(this.Location);
        Point p2 = this.PointToScreen(this.Parent.Location);

        Point ms = MousePosition;
        Rectangle screenBounds = new Rectangle(this.PointToScreen(this.Location), this.Size);
        if (!screenBounds.Contains(ms))
        {
            thw.Close();
            thw = null;
        }
  • loc {X = 275 Y = 3} System.Drawing.Point
  • p {X = 808 Y = 908} System.Drawing.Point
  • p {X = 808 Y = 908} System.Drawing.Point
  • p2 {X = 545 Y = 1542} System.Drawing.Point
  • ms {X = 574 Y = 914} System.Drawing.Point
  • screenBounds {X = 808 Y = 908 Width = 62 Height = 29} System.Drawing.Rectangle

I do not understand how p2 (its parent) can have a greater Y value relative to the screen.

A: 

Idea 1) When the MouseLeave event fires, you can check the mouse coordinates (relative to screen) and check if they're still within the bounds of your usercontrol. If they are, it should be assumed that the mouse has to pass back through the control to get outside the bounds, and you can safely ignore the event this time.

Idea 2) Attach MouseEnter event handlers to the child controls. Then when the mouse enters one, you will know and can ignore the usercontrol's MouseLeave event. Then when the child's MouseLeave event fires, check for the usercontrol's MouseEnter again.

lc
I had a go at this and failed miserably.. I am sure it is possible but I could not get my bounds to work. If someone could provide a bit of an example that would be brill!.Thanks
Jon
A: 

Hi,

I think I would add an event handler for MouseLeave for every control that you have and use the Parent property to find the User Control you are after. I agree, it will be a bit painful though.

Grzenio
A: 

You can also loop through all the child controls (recursive) on your control, and attach a MouseEnter and MouseLeave event to them as well.

You have to do some bookkeeping if the mouse is in your control, or some child control.

GvS
+2  A: 

Hooking all the controls MouseEnter and MouseLeave events, then figuring out if it is still inside the form is pretty painful. A simple timer can get the job done too:

  public partial class Form1 : Form {
    private Timer mTimer;
    public Form1() {
      InitializeComponent();
      mTimer = new Timer();
      mTimer.Interval = 200;
      mTimer.Tick += mTimer_Tick;
      mTimer.Enabled = true;
    }
    private void mTimer_Tick(object sender, EventArgs e) {
      if (!this.DesktopBounds.Contains(Cursor.Position)) this.Close();
    }
  }
Hans Passant
Hi nobugz, I think that would work if the mouse was inside the form that popped up but the mouse reference is on the user control. The form appears close to it but not on top so the mouse would not enter that form. So I don't believe I can use DesktopBounds.
Jon
I decided on a compromise and put the timer on the pop up form and just let it disappear after X number of seconds even if the mouse is still there.
Jon