Domanda

I have a "flawless" working code for putting a part of screen into square PictureBox.
I have a "flawless" working code for drawing on the picturebox with a pen.
I totally fail to understand, why I cannot get the pen draw on the bitmap in the PictureBox - it only draws on grey background.
The solution (also as per google) is seemingly simple, but ANY way to attempt to get gg graphics from PictureBox.Image results in ("An error occurred creating the form. See Exception.InnerException for details. The error is: Value cannot be null. Parameter name: image" and "Use the 'New' keyword to create new instance of an object...").

I think that the trouble is in the way I define the bitmap as private outside a sub, but I cannot figure out correct concept...

Private bit As New System.Drawing.Bitmap(250, 250)
Private gg As Graphics = Graphics.FromImage(Me.PictureBox1.Image)
'            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
'            ^^^^^^^^^^ HERE IS THE PROBLEM ^^^^^^^^^^^^^^^^^^^^^^
'            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
Private br As New Pen(Color.Red)
Private dwn As Boolean
Private lst As Point
Private firstrun As Boolean = True
Dim Tloustka As Integer = 10
Dim Barva As Integer

Private Sub PictureBox1_MouseDown(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseDown
    'gg = Graphics.FromImage(Me.PictureBox1.Image)
    dwn = True
End Sub


Private Sub PictureBox1_MouseMove(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseMove
    If dwn = True Then
        Dim s As Integer
        Dim xy As Point
        Dim br2 As New SolidBrush(Color.FromName("White"))
        s = Tloustka
        br.Color = Color.FromName("White")
        br.Width = Tloustka
        xy.X = e.X
        xy.Y = e.Y
        If firstrun = True Then
            lst = xy
            firstrun = False
        End If
        gg.FillEllipse(br2, xy.X - CLng(s / 2), xy.Y - CLng(s / 2), s, s)
        gg.DrawLine(br, lst, xy)
        lst = xy
        PictureBox1.Image = bit
    End If
End Sub

etc. etc. etc.
È stato utile?

Soluzione

Don't store the Graphic object. Just create it from the bitmap when you need to draw something:

Private Sub PictureBox1_MouseMove(sender As Object, e As MouseEventArgs) Handles PictureBox1.MouseMove
  If dwn = True Then
    Using g As Graphics = Graphics.FromImage(bit)
      Dim s As Integer
      Dim xy As Point
      Using br2 As New SolidBrush(Color.FromName("White"))
        s = Tloustka
        br.Color = Color.FromName("White")
        br.Width = Tloustka
        xy.X = e.X
        xy.Y = e.Y
        If firstrun = True Then
          lst = xy
          firstrun = False
        End If
        g.FillEllipse(br2, xy.X - CLng(s / 2), xy.Y - CLng(s / 2), s, s)
        g.DrawLine(br, lst, xy)
      End Using
    End Using
    lst = xy
    PictureBox1.Invalidate()
  End If
End Sub

Then use the paint event of the PictureBox to show the image:

Private Sub PictureBox1_Paint(sender As Object, e As PaintEventArgs) Handles PictureBox1.Paint
  e.Graphics.DrawImage(bit, Point.Empty)
End Sub

Make sure you dispose of your graphic objects.

Altri suggerimenti

All codes above seems a bit too complicated. In my case the simplest way was to do as follow:

Dim bm As Bitmap With PictureBox1 bm = New Bitmap(.Width, .Height) PictureBox1.DrawToBitmap(bm, New Rectangle(0, 0, .Width, .Height)) End With

... /code for printing/

bm.Dispose

P.S.: Any control can be drawn to bitmap.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top