C# 二维码扫描
阅读原文时间:2023年07月15日阅读:1

Zint类用于产生二维码。https://sourceforge.net/projects/zint/

Zxing类用于读取二维码. https://github.com/zxing/zxing

AForge类用于初始摄像头等。http://www.aforgenet.com/framework/downloads.html

以上三个类为开源的第三方类,可直接引用。

以下为用AForge和ZXing实时读取二维码的代码:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using ZXing;
using ZXing.Common;
using System.Drawing.Imaging;
using AForge;
using AForge.Controls;
using AForge.Imaging;
using AForge.Video;
using AForge.Video.DirectShow;

namespace AutoScan
{
public partial class Form1 : Form
{
private FilterInfoCollection videoDevices;
private VideoCaptureDevice videoSource;
Bitmap bmp = null; //全局变量,保存每一次捕获的图像
int itop = ;// 全局变量,记录扫描线距离顶端的距离
public Form1()
{
InitializeComponent();
}
private void getVideoDevices()
{
cboDevices.Items.Clear();
try
{
videoDevices=new FilterInfoCollection(FilterCategory.VideoInputDevice);
if (videoDevices.Count>)
{
foreach(FilterInfo device in videoDevices)
cboDevices.Items.Add(device.Name);
}
}
catch(Exception ex)
{
MessageBox.Show("not found camera");
}
}
private void Open()
{
if (cboDevices.SelectedIndex == -)
return;
try
{
btnOpen.Enabled = false;
btnClose.Enabled = true;
CloseVideoSource();
videoSource = new VideoCaptureDevice(videoDevices[cboDevices.SelectedIndex].MonikerString);
videoSource.DesiredFrameRate = ;
videoSource.DesiredFrameSize = new Size(, );

            videoSource.NewFrame += new NewFrameEventHandler(newframe);  
            videoSource.Start();  
        }  
        catch  
        {  
            btnOpen.Enabled = true;  
            btnClose.Enabled = false;  
            return;  
        }  
        timer1.Enabled = true;//解析二维码  
        timer2.Enabled = true;//启动绘制视频中的扫描线  
    }

    private void Stop()  
    {  
        CloseVideoSource();  
    }

    private void newframe(object sender, NewFrameEventArgs args)  
    {  
        bmp = (Bitmap)args.Frame.Clone();  
    }  
    private void Form1\_Load(object sender, EventArgs e)  
    {  
        timer1.Enabled = false;  
        timer2.Enabled = false;  
        getVideoDevices();  
    }  
    private void CloseVideoSource()  
    {

        timer1.Enabled = false;  
        timer2.Enabled = false;  
        if (videoSource == null) return;  
        if (videoSource.IsRunning)  
        {  
            videoSource.SignalToStop();  
            videoSource.WaitForStop();  
            videoSource = null;  
            pictureBox1.Image = null;  
        }  
        btnOpen.Enabled = true;  
        btnClose.Enabled = false;  
        txtMsg.Clear();  
    }  
    private void ScanBarcode()  
    {  
        if (pictureBox1.Image == null)  
        {  
            MessageBox.Show("请载入图像资源!");  
            return;  
        }  
        //设置读取二维码  
        DecodingOptions decodeOption = new DecodingOptions();  
        decodeOption.PossibleFormats = new List<BarcodeFormat>(){  
            BarcodeFormat.QR\_CODE  
        };

        //读取操作  
        BarcodeReader bar = new BarcodeReader();  
        bar.Options = decodeOption;  
        ZXing.Result rs = bar.Decode(pictureBox1.Image as Bitmap);  
        if (rs == null)  
        {  
            txtMsg.Text = "读取失败";  
            MessageBox.Show("读取失败");  
        }  
        else  
        {  
            txtMsg.Text = rs.Text;  
            MessageBox.Show("读取成功,内容:" + rs.Text);  
        }  
    }

    private void timer2\_Tick(object sender, EventArgs e)  
    {  
        timer2.Enabled = false;  
        try  
        {  
            if (bmp == null) return;  
            Bitmap bmp2 = (Bitmap)bmp.Clone();  
            Pen p = new Pen(Color.GreenYellow);  
            p.Width = ;  
            Graphics g=Graphics.FromImage(bmp2);  
            System.Drawing.Point p1 = new System.Drawing.Point(, itop);  
            System.Drawing.Point p2 = new System.Drawing.Point(pictureBox1.Width,itop);  
            g.DrawLine(p, p1, p2);  
            g.Dispose();  
            itop += ;

            itop = itop % pictureBox1.Height;  
            pictureBox1.Image = bmp2;  
        }  
        finally  
        {  
            timer2.Enabled = true;  
        }  
    }

    private void timer1\_Tick(object sender, EventArgs e)  
    {  
        Result result;  
        try  
        {  
            if (bmp == null) return;  
            try  
            {  
                BarcodeReader br = new BarcodeReader();

                result = br.Decode(bmp);  
            }  
            catch(Exception ex)  
            {  
                return;  
            }

            /\*  
            #region  
            //将图片转换成byte数组  
            MemoryStream ms = new MemoryStream();  
            bmp.Save(ms, ImageFormat.Bmp);  
            byte\[\] bt = ms.GetBuffer();  
            ms.Close();

            #endregion  
            LuminanceSource source = new RGBLuminanceSource(bt, bmp.Width, bmp.Height);  
            BinaryBitmap bitmap = new BinaryBitmap(new ZXing.Common.HybridBinarizer(source));

            try  
            {                  

                result = new MultiFormatReader().decode(bitmap);  
            }  
            catch (ReaderException ex)  
            {  
                return;  
            }\*/

            if (result != null)  
            {  
                txtMsg.Text = result.Text;  
            }  
        }  
        finally  
        {  
            timer1.Enabled = true;  
        }          

    }

    private void btnClose\_Click(object sender, EventArgs e)  
    {  
        CloseVideoSource();  
    }

    private void btnOpen\_Click(object sender, EventArgs e)  
    {  
        Open();  
    }  
}  

}

界面(黄绿色条为扫描时上下滚动的线条,把条形码放在摄像头处即可扫描):