如何绘制签名并将其作为位图保存到光盘? [英] How to draw a signature and save it to disc as a Bitmap?

查看:71
本文介绍了如何绘制签名并将其作为位图保存到光盘?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试执行签名捕获程序,并将客户签名保存为PNGBMP格式.我的Picturebox代码运行良好,结果看起来比使用draw更好.我无法保存图像.

I'm trying to do a signature capture program and save the customer signature to a PNG or BMP format. I have the Picturebox code working great and the results look better than using draw. I can't get the image to save.

Imports System.Drawing
Public Class Form1
    Dim color As System.Drawing.Pen = Pens.Black
    Dim bmp As Bitmap

    Private Sub form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
        bmp = New Bitmap(PictureBox1.Width, PictureBox1.Height)
        PictureBox1.Image = bmp
    End Sub

    Private Sub PictureBox1_MouseMove(sender As Object, e As MouseEventArgs) Handles PictureBox1.MouseMove
        Static last As New Point
        If e.Button = Windows.Forms.MouseButtons.Left Then
            PictureBox1.CreateGraphics.DrawLine(color, last.X, last.Y, e.X, e.Y)
        End If
        last = e.Location
    End Sub

    Private Sub CmdClear_Click(sender As Object, e As EventArgs) Handles cmdClear.Click
        bmp = New Bitmap(PictureBox1.Width, PictureBox1.Height)
        PictureBox1.Image = bmp
    End Sub

    Private Sub CmdSave_Click(sender As Object, e As EventArgs) Handles cmdSave.Click
        If PictureBox1.Image IsNot Nothing Then
            bmp = PictureBox1.Image
            bmp.Save("c:\temp\test1.bmp")
        End If
    End Sub
End Class

我想看签名的图像.

推荐答案

请勿使用 [Control].CreateGraphics ,除非您需要此对象在特定环境中立即使用.例如,当在特定图形上下文中绘制时,用于测量文本的大小.
当需要保留图形时,就像在控件表面上进行绘制一样,请使用 PaintEventArgs .绘画" rel ="nofollow noreferrer">绘画事件(或类似的事件,如

Never use [Control].CreateGraphics, unless you need this object for immediate use in a specific environment. To measure the size of text when drawn in a specific graphics context, for example.
When you need the drawing to persist, as painting on the surface of a control, use the Graphics object provided by the PaintEventArgs of the Paint event (or similar event, as the DrawItem event of the ComboBox, ListBox, ListView controls).
You'll find this kind of recommendations all over SO (and the Web, in general).

如何进行:

  1. 我们需要一个可以存储定义手工曲线的鼠标/笔运动的对象.
  2. 每次释放鼠标左键(或丢失并重新获取笔触摸)时,对象都需要存储新的曲线定义.
  3. 我们需要一个Graphics对象,该对象可以将鼠标/笔运动定义的点转换为贝塞尔曲线(曲线组合在矢量图形中通常称为路径).
  1. We need an object that can store the Mouse/Pen movements that define a hand-made curve.
  2. The object needs to store a new curve definition each time the left button of the mouse is released (or the Pen touch is lost and re-acquired).
  3. We need a Graphics object that can convert the points defined by the Mouse/Pen movements to Bezier curves (combinations of curves are often referred to as Paths in vector graphics).

在这里,存储运动的对象是 Dictionary(Of Integer, List(Of Point)) ,其中 Key 代表曲线,而 Value 代表定义该曲线的点的集合.
每次按下鼠标左键,都会创建一个新的Key并将新的List(Of Point)Key关联.
移动鼠标/笔时,新的点"位置将添加到当前曲线的List(Of Point)中.

Here, the object that stores the movements is a Dictionary(Of Integer, List(Of Point)), where the Key represents a curve and the Value represents the collection of Points that define that curve.
Each time the Left Button of the Mouse is pressed, a new Key is created and a new List(Of Point) is associated with the Key.
When the Mouse/Pen is moved, the new Point location is added to the current curve's List(Of Point).

GraphicsPath 类可以转换使用 GraphicsPath.AddCurve()方法.
此方法接受点数组和 Tension 值作为参数. Tension01之间的值,用于定义连接点时应用于曲线的弯曲量.此处使用0.5f的值.

The GraphicsPath class can convert the List(Of Point) collection to Control Points of a Bezier curve, using the GraphicsPath.AddCurve() method.
This method accepts an array of Points and a Tension value as arguments. The Tension is a value between 0 and 1 that defines the amount of bending applied to a curve when connecting Points. A values of 0.5f is used here.

当我们需要在位图上绘制图形以将结果保存到磁盘时,我们对从位图对象派生的Graphics对象应用相同的逻辑.
因此,仅使用一种方法既可以在控件的表面上绘制,也可以在位图对象上绘制.
这段代码中的 DrawSignature(g As Graphics) 方法.

When we need to paint the drawing on a Bitmap to save the results to disc, we apply the same logic to the Graphics object derived, in this case, from a Bitmap object.
Thus, just one method is used to draw both on the surface of a Control and onto a Bitmap object.
The DrawSignature(g As Graphics) method in this code.

这是它的工作方式:

用于复制所描述过程的代码:

Code that reproduces the procedure described:

Private signatureObject As New Dictionary(Of Integer, List(Of Point))
Private signaturePen As New Pen(Color.Black, 4)
Private currentCurvePoints As List(Of Point)
Private currentCurve As Integer = -1

Private Sub pBoxSignature_MouseDown(sender As Object, e As MouseEventArgs) Handles pBoxSignature.MouseDown
    currentCurvePoints = New List(Of Point)
    currentCurve += 1
    signatureObject.Add(currentCurve, currentCurvePoints)
End Sub

Private Sub pBoxSignature_MouseMove(sender As Object, e As MouseEventArgs) Handles pBoxSignature.MouseMove
    If e.Button <> MouseButtons.Left OrElse currentCurve < 0 Then Return
    signatureObject(currentCurve).Add(e.Location)
    pBoxSignature.Invalidate()
End Sub

Private Sub btnClearSignature_Click(sender As Object, e As EventArgs) Handles btnClearSignature.Click
    currentCurve = -1
    signatureObject.Clear()
    pBoxSignature.Invalidate()
End Sub

Private Sub btnSaveSignature_Click(sender As Object, e As EventArgs) Handles btnSaveSignature.Click
    Dim signatureFileName = txtSignatureFileName.Text.Trim()
    If String.IsNullOrEmpty(signatureFileName) Then Return
    If currentCurve < 0 OrElse signatureObject(currentCurve).Count = 0 Then Return
    Using imgSignature As Bitmap = New Bitmap(pBoxSignature.Width, pBoxSignature.Height, PixelFormat.Format32bppArgb)
        Using g As Graphics = Graphics.FromImage(imgSignature)
            DrawSignature(g)
            Dim signaturePath As String = Path.Combine(Application.StartupPath, $"{signatureFileName}.png")
            imgSignature.Save(signaturePath, ImageFormat.Png)
            pBoxSavedSignature.Image = New Bitmap(imgSignature)
        End Using
    End Using
End Sub

Private Sub pBoxSignature_Paint(sender As Object, e As PaintEventArgs) Handles pBoxSignature.Paint
    If currentCurve < 0 OrElse signatureObject(currentCurve).Count = 0 Then Return
    DrawSignature(e.Graphics)
End Sub

Private Sub DrawSignature(g As Graphics)
    g.CompositingMode = CompositingMode.SourceOver
    g.CompositingQuality = CompositingQuality.HighQuality
    g.SmoothingMode = SmoothingMode.AntiAlias
    For Each curve In signatureObject
        If curve.Value.Count < 2 Then Continue For
        Using gPath As New GraphicsPath()
            gPath.AddCurve(curve.Value.ToArray(), 0.5F)
            g.DrawPath(signaturePen, gPath)
        End Using
    Next
End Sub

这篇关于如何绘制签名并将其作为位图保存到光盘?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆