So I am making a documentation program for a physical therapy environment, and am trying to encorporate the ability to export the form with the data on it to a pdf or image of some sort. My form looks like this:
I have tried using the following code to create an image from it
Private Sub Button1_Click_1(sender As Object, e As EventArgs) Handles Button1.Click
Dim bmpScreenshot As Bitmap = New Bitmap(Width, Height, PixelFormat.Format32bppArgb)
' Create a graphics object from the bitmap
Dim gfxScreenshot As Graphics = Graphics.FromImage(bmpScreenshot)
' Take a screenshot of the entire Form1
gfxScreenshot.CopyFromScreen(Me.Location.X, Me.Location.Y, 0, 0, Me.Size, CopyPixelOperation.SourceCopy)
' Save the screenshot
bmpScreenshot.Save("C:\Student.jpg", ImageFormat.Jpeg)
End Sub
But every time it comes back as only part of the form.
Any help would be appreciated!
You can use this code:
Private Function GetFormImage(ByVal include_borders As Boolean) As Bitmap
' Make the bitmap.
Dim wid As Integer = Me.Width
Dim hgt As Integer = Me.Height
Dim bm As New Bitmap(wid, hgt)
' Draw the form onto the bitmap.
Me.DrawToBitmap(bm, New Rectangle(0, 0, wid, hgt))
' Make a smaller bitmap without borders.
wid = Me.ClientSize.Width
hgt = Me.ClientSize.Height
Dim bm2 As New Bitmap(wid, hgt)
' Get the offset from the window's corner to its client
' area's corner.
Dim pt As New Point(0, 0)
pt = PointToScreen(pt)
Dim dx As Integer = pt.X - Me.Left
Dim dy As Integer = pt.Y - Me.Top
' Copy the part of the original bitmap that we want
' into the bitmap.
Dim gr As Graphics = Graphics.FromImage(bm2)
gr.DrawImage(bm, 0, 0, New Rectangle(dx, dy, wid, hgt), GraphicsUnit.Pixel)
Return bm
End Function
From https://social.msdn.microsoft.com/Forums/vstudio/en-US/3d258c2b-64b9-431f-9df8-398a7866de40/vbnet-save-windows-form-as-an-image-getformimage?forum=vbgeneral
And then call the function as so:
GetFormImage(*True to include the borders*).Save("C:\Student.jpg", ImageFormat.Jpeg)
Related
How can I change the hitbox of a PictureBox where the image is circular? By hitbox, I mean where the ClickEvent registers.
You can use the Control.Region property, to create a Region using a circular GraphicsPath. This Region is used for the Click event, as well as the MouseEnter, MouseHover, and MouseLeave events.
Example with a PictureBox:
Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
Dim path As New Drawing2D.GraphicsPath()
path.AddArc(0, 0, PictureBox1.Width, PictureBox1.Height, 0, 360) 'A circle at 0,0 relative to the PictureBox, sharing its Width and Height
PictureBox1.Region = New Region(path)
End Sub
If you want a circle in the middle (instead of an oval), then use something like:
Dim path As New Drawing2D.GraphicsPath()
Dim radius As Integer = Math.Min(PictureBox1.Width - 1, PictureBox1.Height - 1) / 2
Dim rc As New Rectangle(New Point(PictureBox1.Width / 2, PictureBox1.Height / 2), New Size(1, 1))
rc.Inflate(radius, radius)
path.AddEllipse(rc)
PictureBox1.Region = New Region(path)
I'm trying to create a simple program that will allow you to enter a degree and have a dial fill to that exact degree, and then also display the degree inside of the dial. The project builds without errors, and will display correctly until a value is entered into the textbox, and then I will get the error on the line
g.SmoothingMode = Drawing2D.SmoothingMode.AntiAlias
If I comment out that line it will go down to the line below it. This is my first time using vb.net, so I'm guessing there is something small I'm just doing incorrectly. My full code is:
Public Class Form1
Dim degree As Double
Dim ge As Graphics
Private Sub Form2_Paint(sender As Object, e As PaintEventArgs) Handles Me.Paint
ge = e.Graphics
DrawProgress(ge, New Rectangle(150, 25, 400, 400), degree)
End Sub
Private Sub DrawProgress(g As Graphics, rect As Rectangle, degree As Double)
'work out the angles for each arc
Dim progressAngle = CSng(degree)
Dim remainderAngle = 360 - progressAngle
'create pens to use for the arcs
Using progressPen As New Pen(Color.LightSeaGreen, 2), remainderPen As New Pen(Color.LightGray, 2)
'set the smoothing to high quality for better output
g.SmoothingMode = Drawing2D.SmoothingMode.AntiAlias
'draw the blue and white arcs
g.DrawArc(progressPen, rect, -90, progressAngle)
g.DrawArc(remainderPen, rect, progressAngle - 90, remainderAngle)
End Using
'draw the text in the centre by working out how big it is and adjusting the co-ordinates accordingly
Using fnt As New Font(Me.Font.FontFamily, 50)
Dim text As String = degree.ToString
Dim textSize = g.MeasureString(text, fnt)
Dim textPoint As New Point(CInt(rect.Left + (rect.Width / 2) - (textSize.Width / 2)), CInt(rect.Top + (rect.Height / 2) - (textSize.Height / 2)))
'now we have all the values draw the text
g.DrawString(text, fnt, Brushes.Black, textPoint)
End Using
End Sub
Private Sub TextBox1_TextChanged(sender As Object, e As EventArgs) Handles TextBox1.TextChanged
Dim input_s As String
input_s = TextBox1.Text
If (String.IsNullOrEmpty(input_s)) Then
degree = 0
Else
degree = CDec(input_s)
End If
DrawProgress(ge, New Rectangle(150, 25, 400, 400), degree)
End Sub
End Class
So I have this code:
Private Sub button28_Click(sender As Object, e As EventArgs) Handles button28.Click
Dim bounds As Rectangle
Dim screenshot As System.Drawing.Bitmap
Dim graph As Graphics
bounds = PicOuterBorder.Bounds
screenshot = New System.Drawing.Bitmap(bounds.Width, bounds.Height, System.Drawing.Imaging.PixelFormat.Format32bppArgb)
graph = Graphics.FromImage(screenshot)
graph.CopyFromScreen(bounds.X, bounds.Y, 0, 0, bounds.Size, CopyPixelOperation.SourceCopy)
picFinal.Image = screenshot
'this takes a screenshot
End Sub
PicOuterBorder is a picturebox on my form. PicFinal is another display picturebox. But this code gets me this: Which is basically a screenshot of a window in the size of PicOuterBorder starting from the origin of my screen. However, Me.Bounds instead of PicOuterBorder.Bounds works and gets a perefect screenshot of just my form. I want picFinal to have a screenshot of just PicOuterBorder
Try below code. You have to map the control coordinates to screen coordinates using PointToScreen. I have placed PicOuterBorder inside the panel PanelPicture. PanelPicture is without any border, while PicOuterBorder can have any type of border style. Below code takes the snapshot of the panel.
Private Sub button28_Click(sender As Object, e As EventArgs) Handles button28.Click
Dim graph As Graphics = Nothing
Dim bounds As Rectangle = Nothing
Dim screenshot As System.Drawing.Bitmap
Dim location As Drawing.Point = PanelPicture.PointToScreen(Drawing.Point.Empty)
screenshot = New System.Drawing.Bitmap(PanelPicture.Width, PanelPicture.Height, System.Drawing.Imaging.PixelFormat.Format32bppArgb)
graph = Graphics.FromImage(screenshot)
graph.CopyFromScreen(location.X, location.Y, 0, 0, PanelPicture.Size, CopyPixelOperation.SourceCopy)
picFinal.Image = screenshot
graph.Dispose()
End Sub
Adapt your code for something like this:
Public Sub SaveImage(filename As String, image As Image, Encoder As ImageCodecInfo, EncParam As EncoderParameter)
Dim path As String = System.IO.Path.Combine(My.Application.Info.DirectoryPath, filename & ".jpg")
Dim mySource As New Bitmap(image.Width, image.Height)
Dim grfx As Graphics = Graphics.FromImage(mySource)
grfx.DrawImageUnscaled(image, Point.Empty)
grfx.Dispose()
mySource.Save(filename, System.Drawing.Imaging.ImageFormat.Jpeg)
mySource.Dispose()
End Sub
In VB.Net, how can I call thePublic Sub using a button click?
Here's what I have so far:
Public Sub SetThreshold(ByVal e As PaintEventArgs)
' Open an Image file, and draw it to the screen.
Dim Image As New Bitmap(PictureBox1.Image)
PictureBox1.Image = Image
e.Graphics.DrawImage(Image, 20, 20)
' Create an ImageAttributes object, and set its color threshold.
Dim imageAttr As New ImageAttributes
imageAttr.SetThreshold(0.7F)
' Draw the image with the colors bifurcated.
Dim rect As New Rectangle(300, 20, 200, 200)
e.Graphics.DrawImage(Image, rect, 0, 0, 200, 200, GraphicsUnit.Pixel, imageAttr)
End Sub
I'm using a picture box as a 'preview' screen for a webbrowser control on a another winform. It works well apart from that in order to update the picturebox control I'm finding that the code needs to run twice (double click the button) linked to the below code. Any ideas why the picturebox isn't updating in the first pass to show the newly navigated page?
Private Sub mOutput_Click(sender As Object, e As EventArgs) Handles mOutput.Click
If Not mFiles.SelectedItem Is Nothing Then
Formloading.fDisplay.WebBrowser1.Navigate(folderloc.ToString & "\" & mFiles.SelectedItem.ToString)
End If
Dim Bounds As System.Drawing.Rectangle
Dim outputscreen As System.Drawing.Bitmap
Dim graph As System.Drawing.Graphics
Dim LO As Integer = 0
With Bounds
.Height = fDisplay.WebBrowser1.Height
.Width = fDisplay.WebBrowser1.Width
.X = Formloading.fDisplay.Location.X
.Y = Formloading.fDisplay.Location.Y
.Size = Formloading.fDisplay.Size
End With
outputscreen = New System.Drawing.Bitmap(Bounds.Width, Bounds.Height, System.Drawing.Imaging.PixelFormat.Format32bppRgb)
graph = System.Drawing.Graphics.FromImage(outputscreen)
graph.CopyFromScreen(Bounds.X, Bounds.Y, 0, 0, Bounds.Size, Drawing.CopyPixelOperation.SourceCopy)
PictureBox1.Image = outputscreen
End Sub