views:

487

answers:

2

I want to create a card playing game. I the use mousemove event to drag cards through the window. The problem is if I move the mouse over another card, it is stuck because the card underneath the mouse cursor gets the mouse events, so that the MouseMove event of the window isn't fired.

This is what I do:

 private void RommeeGUI_MouseMove(object sender, MouseEventArgs e)
 {
      if (handkarte != null)
      {
                handkarte.Location = this.PointToClient(Cursor.Position);
      }
 }

I tried the following, but there was no difference:

SetStyle(ControlStyles.UserMouse,true);
SetStyle(ControlStyles.EnableNotifyMessage, true);

Iam looking for a way to implement an application-global event-handler or a way to implement so called event-bubbling. At least I want to make the mouse ignore certain controls.

A: 

Normally you do this by, before capturing the mouse, seeing if anybody else has it...

Roger Lipscombe
How can I do this?
codymanix
A: 

In order to do this you will need to keep track of a few things in your code:

  1. On which card the mouse is pointing when the mouse button is pressed; this is the card that you want to move (use the MouseDown event)
  2. Move the the card when the mouse is moved
  3. Stop moving the card when the mouse button is released (use the MouseUp event)

In order to just move around controls, there is no need to actually capture the mouse.

A quick example (using Panel controls as "cards"):

Panel _currentlyMovingCard = null;
Point _moveOrigin = Point.Empty;
private void Card_MouseDown(object sender, MouseEventArgs e)
{
    if (e.Button == MouseButtons.Left)
    {
        _currentlyMovingCard = (Panel)sender;
        _moveOrigin = e.Location;
    }
}

private void Card_MouseMove(object sender, MouseEventArgs e)
{
    if (e.Button == MouseButtons.Left && _currentlyMovingCard != null)
    {
        // move the _currentlyMovingCard control
        _currentlyMovingCard.Location = new Point(
            _currentlyMovingCard.Left - _moveOrigin.X + e.X,
            _currentlyMovingCard.Top - _moveOrigin.Y + e.Y);
    }
}

private void Card_MouseUp(object sender, MouseEventArgs e)
{
    if (e.Button == MouseButtons.Left && _currentlyMovingCard != null)
    {
        _currentlyMovingCard = null;
    }
}
Fredrik Mörk
Sorry if I wasn't clear enough but my problem is that the MouseMove event isn't fired if the mouse hovers above another card because the handler is attached to the window.
codymanix
OK, then I don't really know how to help off the top of my head. Unless there is a specific reason why you want to handle all mouse-moving logic through the Form's MouseMove event, I would recommend you to attach MouseMove event handlers to the cards; it might make your code a bit simpler.
Fredrik Mörk
Is there such such thing like an application-global event-handler? Is there no way to implement so called event-bubbling? Or to make the mouse ignore certain controls?
codymanix
Not really. You can have the form receive all KeyPress events (using the KeyPreview property) regardless of which control they occur in, but there is nothing similar when it comes to mouse events. If you wish to handle all mouse operations in one central place, your best bet is to hook up the mouse events for all controls to the same event handler.
Fredrik Mörk