Home
Search
 
What's New
Index
Books
Links
Q & A
Newsletter
Banners
 
Feedback
Tip Jar
 
C# Helper...
 
XML RSS Feed
Follow VBHelper on Twitter
 
 
 
MSDN Visual Basic Community
 
 
 
 
 
TitleLet the user drag a picture with the mouse or move it with the arrow keys
Description
Keywordsdrag picture, BitBlt
CategoriesGraphics
 
In the KeyDown event handler, set m_Dx or m_Dy values to indicate the direction of movement and enable a timer. When the timer fires, move the object. In the KeyUp event handler, clear m_Dx and m_Dy appropriately.
 
This program lets the user either drag an image or use the arrow keys to move an image.

The program's picMask PictureBox contains a mask of the image to be dragged. Pixels that should be drawn are black and pixels that should let the background show through are white.

In the MouseDown event handler, the program subtracts the overlay picture's current position from the mouse's coordinates to see where on the overlay picture the user clicked. If the corresponding mask pixel is white, the user is pressing where the background should show through so the event is ignored.

If the corresponding mask pixel is black, the user is pressing the mouse on part of the image and the program begins a drag.

 
' See if this point corresponds to
' a black point on the mask.
Private Sub picCanvas_MouseDown(Button As Integer, Shift As _
    Integer, x As Single, y As Single)
    If picXMask.Point(x - CurX, y - CurY) <> vbBlack Then _
        Exit Sub

    ' Start dragging.
    Dragging = True
    OffsetX = CurX - x
    OffsetY = CurY - y
End Sub
 
In the MouseMove event handler, the program determines where the picture should be placed and calls DrawPicture to draw it.
 
' Continue dragging.
Private Sub picCanvas_MouseMove(Button As Integer, Shift As _
    Integer, x As Single, y As Single)
    If Not Dragging Then Exit Sub
    
    CurX = x + OffsetX
    CurY = y + OffsetY

    If CurX < 0 Then CurX = 0
    If CurX > Xmax Then CurX = Xmax
    If CurY < 0 Then CurY = 0
    If CurY > Ymax Then CurY = Ymax

    DrawPicture
End Sub
 
Subroutine DrawPic restores the background picture by using BitBlt to copy the part of the background that is currently covered by the overlay onto picCanvas. It then uses BitBlt to copy the overlay mask onto picCanvas using the opcode MERGEPAINT. This knocks out the mask's outline on the background so a white image of the overlay appears.

Next the code copies the overlay image onto the background using the SRCAND opcode. This combines the pixel values of the overlay image with the background image. The overlay image is white where it should not show and the background image is white where the overlay should show. The result is the overlay is dropped into its correct position.

 
' Draw the picture at (CurX, CurY).
Private Sub DrawPicture()
    ' Fix the part of the image that was covered.
    BitBlt picCanvas.hDC, _
        OldX, OldY, PicWid, PicHgt, _
        picHidden.hDC, OldX, OldY, SRCCOPY
    OldX = CurX
    OldY = CurY

    ' Paint on the new image.
    BitBlt picCanvas.hDC, _
        CurX, CurY, PicWid, PicHgt, _
        picXMask.hDC, 0, 0, MERGEPAINT
    BitBlt picCanvas.hDC, _
        CurX, CurY, PicWid, PicHgt, _
        picX.hDC, 0, 0, SRCAND

    ' Update the display.
    picCanvas.Refresh
End Sub
 
The MouseUp event handler simply ends the drag.
 
' Stop dragging.
Private Sub picCanvas_MouseUp(Button As Integer, Shift As _
    Integer, x As Single, y As Single)
    Dragging = False
End Sub
 
The form's KeyDown event handler sets a variable to indicate the direction it should move the overlay image and then enables the tmrKeyMover Timer.

The KeyUp event handler modifies the direction of motion variables appropriately and disables the timer if there should be no further motion.

 
Private Sub Form_KeyDown(KeyCode As Integer, Shift As _
    Integer)
    Select Case KeyCode
        Case vbKeyLeft
            m_Dx = -5
        Case vbKeyRight
            m_Dx = 5
        Case vbKeyUp
            m_Dy = -5
        Case vbKeyDown
            m_Dy = 5
    End Select

    tmrKeyMover.Enabled = (m_Dx <> 0) Or (m_Dy <> 0)
End Sub

Private Sub Form_KeyUp(KeyCode As Integer, Shift As Integer)
    Select Case KeyCode
        Case vbKeyLeft, vbKeyRight
            m_Dx = 0
        Case vbKeyUp, vbKeyDown
            m_Dy = 0
    End Select

    tmrKeyMover.Enabled = (m_Dx <> 0) Or (m_Dy <> 0)
End Sub
 
The tmrKeyMover Timer updates the position of the overlay picture and calls DrawPicture to draw it at the proper location.
 
Private Sub tmrKeyMover_Timer()
    CurX = CurX + m_Dx
    CurY = CurY + m_Dy

    If CurX < 0 Then CurX = 0
    If CurX > Xmax Then CurX = Xmax
    If CurY < 0 Then CurY = 0
    If CurY > Ymax Then CurY = Ymax

    DrawPicture
End Sub
 
My book Visual Basic Graphics Programming has more information on this kind of graphic manipulation.

See also:

 
 
Copyright © 1997-2010 Rocky Mountain Computer Consulting, Inc.   All rights reserved.
  Updated