Reputation: 71
I created a GuiWindow class that held a texture, title, and rectangle so I can draw the texture and title. I've been trying to make it draggable, though I am having a bit of trouble. Originally I had the GuiWindow's bounds rectangle just lock onto the mouse positions:
if(bounds.contains(MouseHandle.Update()) && MouseHandle.Pressed()) //checks if the bounds rectangle contains the mouse rectangle and the mouse left button is pressed
{
bounds.X = MouseHandle.Update().X;
bounds.Y = MouseHandle.Update().Y;
}
which would allow me to drag, though only in a single direction. I then tried
if(bounds.contains(MouseHandle.Update()) && MouseHandle.Pressed())
{
int offx = bounds.X - MouseHandle.Update().X;
int offy = bounds.Y - MouseHandle.Update().Y;
bounds.X = MouseHandle.Update().X + offx;
bounds.Y = MouseHandle.Update().Y + offy;
}
this time the window just stayed still when I tried dragging. I'm pretty sure I have the basic concept of dragging down. Am I doing something wrong?
Upvotes: 1
Views: 822
Reputation: 66
Alright this is some code that I've been using to move objects with the mouse in some of my XNA applications. Hopefully this will help you with your problem.
//Fields
Texture2D object;
Vector2 object_position;
Rectangle collisionRectangle;
MouseState preMouse;
bool moving = false;
Vector2 mouseOffset;
//initialize fields in LoadContent method
protected override void LoadContent()
{
object = Content.Load<Texture2D>("nameOfYourImage");
object_position = new Vector2((graphics.PreferredBackBufferWidth - object.Width)/2, graphics.PreferredBackBufferHeight - object.Height - 60);
collisionRectangle = new Rectangle((int)object_position.X, (int)object_position.Y, (int)object.Width, (int)object.Height);
}
//add code to Update method
public void MouseInput(MouseState mouse)
{
if (collsionRectangle.Contains(mouse.X, mouse.Y) && //mouse is over the object
//the user is clicking the left mousebutton
mouse.LeftButton == ButtonState.Pressed &&
//in the previous Update() call the left mousebutton was released,
//meaning the user has just clicked the object
preMouse.LeftButton == ButtonState.Released)
{
moving = true;
//stores what the objects position should be offset by so it doesn't
//snap to the mouse's position every time you click on it
mouseOffset = new Vector2(Position.X - mouse.X, Position.Y - mouse.Y);
}
if (moving)
{
//if the player stops holding down the mousebutton i.e stops moving the object
if (mouse.LeftButton == ButtonState.Released)
moving = false;
//modifies the position
Position.X = mouse.X + mouseOffset.X;
Position.Y = mouse.Y + mouseOffset.Y;
//prevents object from going off the screen and getting lost
if (Convert.ToInt32(object_position.X) < 0)
object_position.X = 0;
if (object_position.X + object.Width > graphics.PreferredBackBufferWidth)
object_position.X = graphics.PreferredBackBufferWidth - object.Width;
if (Convert.ToInt32(object_position.Y) < 0)
object_position.Y = 0;
if (object_position.Y + object.Height > graphics.PreferredBackBufferHeight)
object_position.Y = graphics.PreferredBackBufferHeight - object.Height;
//updates the collision rectangle
collisionRectangle = new Rectangle(Postion.X, Position.Y, WIDTH, HEIGHT);
}
preMouse = mouse; //stores the current mouseState for use in the next Update() call
}
This will make you able to drag the object with the mouse. Now of course this won't be directly copyable to your application, as i don't know how the code of your GuiWindow, but it should be easy to convert to your needs. Hope this helps :)
Upvotes: 2
Reputation: 16991
Here is a section of my window base class that handled moving and resizing in XNA. My appologies for it being in VB.NET, but you should be able to easily convert it. You probably wont be able to use any of it directly, but hopefully it will point you in the right direction.
Public Overrides Sub OnMouseDown(e As Ui.MouseEventArgs)
MyBase.OnMouseDown(e)
Dim localLoc As Point = ScreenToWindow(e.Location)
'If Movable AndAlso localLoc.Y >= 0 AndAlso localLoc.Y <= mBackground.TopMargin Then
If Closable AndAlso Me.CloseButtonBounds.Contains(e.Location) Then
Me.OnCloseButton()
ElseIf Movable AndAlso Me.DragArea.Contains(e.Location) Then
mMouseAnchor = localLoc
mDragType = DragType.Move
' ElseIf Resizable AndAlso localLoc.X > Me.Bounds.Width - mBackground.RightMargin AndAlso localLoc.Y > Me.Bounds.Height - mBackground.BottomMargin Then
ElseIf Resizable AndAlso Me.ResizeArea.Contains(e.Location) Then
mMouseAnchor = New Point(Me.Bounds.Right - e.Location.X, Me.Bounds.Bottom - e.Location.Y)
mDragType = DragType.Resize
End If
End Sub
Public Overrides Sub OnMouseUp(e As Ui.MouseEventArgs)
MyBase.OnMouseUp(e)
mDragType = DragType.None
End Sub
Public Overrides Sub OnMouseMove(e As Ui.MouseEventArgs)
MyBase.OnMouseMove(e)
If mDragType = DragType.Move Then
Dim change As New Vector2((e.Location.X - mMouseAnchor.X) - Me.X, (e.Location.Y - mMouseAnchor.Y) - Me.Y)
Me.Bounds = New Rectangle(e.Location.X - mMouseAnchor.X,
e.Location.Y - mMouseAnchor.Y,
Me.Bounds.Width,
Me.Bounds.Height)
UpdateControlLocations(change)
ElseIf mResizable AndAlso mDragType = DragType.Resize Then
Me.Bounds = New Rectangle(Me.Bounds.X,
Me.Bounds.Y,
Me.Bounds.Width - (Me.Bounds.Right - e.Location.X) + mMouseAnchor.X,
Me.Bounds.Height - (Me.Bounds.Bottom - e.Location.Y) + mMouseAnchor.Y)
System.Windows.Forms.Cursor.Current = System.Windows.Forms.Cursors.SizeNWSE
ElseIf mDragType = DragType.None Then
If mResizable AndAlso Me.ResizeArea.Contains(e.Location) Then
System.Windows.Forms.Cursor.Current = System.Windows.Forms.Cursors.SizeNWSE
Else
System.Windows.Forms.Cursor.Current = System.Windows.Forms.Cursors.Default
End If
End If
End Sub
Upvotes: 0