Hi,
I'm writing a little program at the moment and I'm trying to animate the buttons so that they spin when I click them.
Now I've managed to do this using screenshots, a PictureBox and a Timer, but the PictureBox has an Opaque background so it covers other controls when it runs.
Can anyone tell me how to change the PictureBox so it has a transparent background? By this I meant transparent in a way that allows you to put the PictureBox in front of a button but still see the button.
Also, I'm guessing that since my screenshot is a Bitmap, that would not be transparent so it would also cover the other controls with a grey background.
The code I currently have is below, to implement this, create a form with 4 buttons (Button1, Button2, Button3 and Button4) and then add the code onto the form.
When you click the buttons, they will spin, but if they are too close to another, it will obscure the other buttons.
Any help would be much appreciated
Thanks
I'm writing a little program at the moment and I'm trying to animate the buttons so that they spin when I click them.
Now I've managed to do this using screenshots, a PictureBox and a Timer, but the PictureBox has an Opaque background so it covers other controls when it runs.
Can anyone tell me how to change the PictureBox so it has a transparent background? By this I meant transparent in a way that allows you to put the PictureBox in front of a button but still see the button.
Also, I'm guessing that since my screenshot is a Bitmap, that would not be transparent so it would also cover the other controls with a grey background.
The code I currently have is below, to implement this, create a form with 4 buttons (Button1, Button2, Button3 and Button4) and then add the code onto the form.
When you click the buttons, they will spin, but if they are too close to another, it will obscure the other buttons.
Code:
Public Class Form1
Dim bmpScreenGrab(999) As Bitmap
Dim gScreenGrab(999) As System.Drawing.Graphics
Dim intCurAngle(999) As Integer
Dim intAngleChange(999) As Integer
Dim ctrlCtrl(999) As Control
Dim intNewMax As Integer = -1
Private Sub Button_Click(sender As Object, e As System.EventArgs) Handles Button1.Click, Button2.Click, Button3.Click, Button4.Click
SpinIt(sender, 1, 10)
End Sub
Private Sub SpinIt(Ctrl As Control, Optional intDelay As Integer = 1, Optional intAngle As Integer = 1)
Dim pntOrig As Point = Ctrl.Location
Dim blnOrigVis As Boolean = Ctrl.Visible
Dim TmpBMP As Bitmap
intNewMax += 1
intAngleChange(intNewMax) = intAngle
' Move Ctrl to 0,0 and make sure visible so a screenshot can be taken
Ctrl.Location = New Point(0, 0)
Ctrl.Visible = True
' Create new bitmap
TmpBMP = New Bitmap(Ctrl.Width, Ctrl.Height)
bmpScreenGrab(intNewMax) = TmpBMP
Me.Refresh()
' Get screenshot
gScreenGrab(intNewMax) = System.Drawing.Graphics.FromImage(bmpScreenGrab(intNewMax))
gScreenGrab(intNewMax).CopyFromScreen(Ctrl.PointToScreen(New Point(0, 0)), New Point(0, 0), New Size(Ctrl.Width, Ctrl.Height), CopyPixelOperation.SourceCopy)
' Move Ctrl back to original location and set visibility to original visibility
Ctrl.Location = pntOrig
Ctrl.Visible = blnOrigVis
Me.Refresh()
' Set Tag as intNewMax so it has some sort of identifier for the later code
Ctrl.Tag = intNewMax
' Set the Ctrl's current angle to 0 as it hasn't yet moved
intCurAngle(intNewMax) = 0
' Create new PictureBox for the bmpScreenGrab
Dim NewPB As New PictureBox
With NewPB
' So none of the graphics are missing we need to set the Height and Width to the same value
' the value needs to be the higher value of the Ctrl's height or width.
' Since the height or width may be changed, we also need to offset the PictureBox by half the difference
If bmpScreenGrab(intNewMax).Width > bmpScreenGrab(intNewMax).Height Then
.Size = New Size(bmpScreenGrab(intNewMax).Width, bmpScreenGrab(intNewMax).Width)
.Left = Ctrl.Left
.Top = Ctrl.Top - ((bmpScreenGrab(intNewMax).Width - bmpScreenGrab(intNewMax).Height) / 2)
Else
.Size = New Size(bmpScreenGrab(intNewMax).Height, bmpScreenGrab(intNewMax).Height)
.Left = Ctrl.Left - ((bmpScreenGrab(intNewMax).Height - bmpScreenGrab(intNewMax).Width) / 2)
.Top = Ctrl.Top
End If
' Give the PicturBox a unique name so it's unlikely to be accidentalyy used in other code
.Name = "_SpinItPB" & intNewMax
.Tag = intNewMax
' Make it visible
.Visible = True
End With
' Add the PictureBox Paint handler so the animation is visible
AddHandler NewPB.Paint, AddressOf PictureBox_Paint
' Add the PictureBox to the Form
Me.Controls.Add(NewPB)
NewPB.BringToFront()
' Create a new Timer for this Ctrl alone
Dim NewTimer As New Timer
AddHandler NewTimer.Tick, AddressOf NewTimer_Tick
' Set the NewTimers interval and Tag then start it
With NewTimer
.Tag = intNewMax
.Interval = intDelay
.Start()
End With
End Sub
Private Sub NewTimer_Tick(sender As Object, e As System.EventArgs)
Dim TmpPB As PictureBox = Nothing
' Increase the Current Angle by the intAngleChange
intCurAngle(CInt(sender.tag)) += intAngleChange(CInt(sender.tag))
' Find the relevant PictureBox for this Timer
For Each TmpCtrl As Control In Me.Controls
If TypeOf TmpCtrl Is PictureBox Then
If TmpCtrl.Name = "_SpinItPB" & sender.Tag Then
TmpPB = TmpCtrl
Exit For
End If
End If
Next TmpCtrl
' Refresh the PictureBox to show the new Angle
TmpPB.Refresh()
' If the Angle is up to 360 then it has done a full rotation
' in this case, make the PictureBox invisible so the original
' control is showing and then stop the timer
If intCurAngle(CInt(sender.tag)) >= 360 Then
TmpPB.Visible = False
Me.Controls.Remove(TmpPB)
sender.Stop()
End If
End Sub
Private Sub PictureBox_Paint(sender As Object, e As System.Windows.Forms.PaintEventArgs)
' When the form is first loaded there are no Bitmaps so trying to use
' them will cause an error.
' The Bitmap will be Nothing so Exit Sub
If bmpScreenGrab(CInt(sender.tag)) Is Nothing Then Exit Sub
' Rotate the screenshot image
With e.Graphics
' Move the centre of rotation to the centre of the image
.TranslateTransform(sender.Width \ 2, sender.Height \ 2)
' Rotate the image
.RotateTransform(intCurAngle(CInt(sender.tag)))
' Draw the image
.DrawImage(bmpScreenGrab(CInt(sender.tag)), -bmpScreenGrab(CInt(sender.tag)).Width \ 2, -bmpScreenGrab(CInt(sender.tag)).Height \ 2)
End With
End Sub
End ClassThanks