バーコード・QRコードリーダー |
Visual Studio Community 2019をインストールしバーコード・QRコードリーダーを作成してみました
パソコンに内蔵、もしくはUSB接続されているカメラ画像を取り込む為に “AForge” というライブラリを使用しました。接続されているカメラ、設定可能な解像度を自動で認識してくれるので、撮影は比較的簡単でした。
バーコード、QRコード解析には、“ZXing.net”というライブラリを使いました。下の写真は上側がバーコード読取、下側がQR読取した状態です。同時に取得できる座標情報を使って、赤い線を描画しています。
①バーコード認識
②QRコード認識
※プログラムで使用するコントロール名も記載しています。
ライブラリ インストール |
ライブラリインストール手順です。先ず、C#フォームアプリケーションのプロジェクトを作成し、次に以下の①~⑤の手順を実行しました。
①“プロジェクト”-“NuGetパッケージの管理”を選択
②“AForge.Video.DirectShow”を選択、インストール
③関連ライブラリのインストール確認→「OK」
④“ZXing.NET”をインストール
⑤ライブラリインストール確認→「OK」
プログラム |
USBカメラから画像を取得する箇所は、ほぼ静大ロボットファクトリー活動日誌に掲載されているプログラムを利用させて頂きました。バーコード・QRコード読み取り部は、連続読取やバーコード位置表示など少しは検討してみました。
using System; using System.Collections.Generic; using System.ComponentModel; using System.Data; using System.Drawing; using System.Linq; using System.Text; using System.Threading.Tasks; using System.Windows.Forms; using AForge.Video; using AForge.Video.DirectShow; using ZXing; namespace AForgeZxing { public partial class Form1 : Form { public Form1() { InitializeComponent(); } private FilterInfoCollection videoDevices; // 接続デバイス情報格納変数 private VideoCaptureDevice videoDevice; // 使用デバイス格納変数 private VideoCapabilities[] videoCapabilities; // デバイス機能格納配列 private void Form1_Load(object sender, EventArgs e) { comboBox2.Enabled = false; button1.Enabled = false; button2.Enabled = false; } // デバイスチェックボタン private void button3_Click(object sender, EventArgs e) { videoDevices = new FilterInfoCollection(FilterCategory.VideoInputDevice); if (videoDevices.Count != 0) { comboBox1.Items.Clear(); foreach (FilterInfo device in videoDevices) { comboBox1.Items.Add(device.Name); } comboBox1.SelectedIndex = 0; comboBox2.Enabled = true; button1.Enabled = true; } else { comboBox1.Items.Clear(); comboBox1.Items.Add("デバイスが見つかりません"); comboBox1.SelectedIndex = 0; } } // デバイス選択 private void comboBox1_SelectedIndexChanged(object sender, EventArgs e) { videoDevice = new VideoCaptureDevice(videoDevices[comboBox1.SelectedIndex].MonikerString); videoCapabilities = videoDevice.VideoCapabilities; comboBox2.Items.Clear(); foreach (VideoCapabilities capabilty in videoCapabilities) { comboBox2.Items.Add(string.Format("{0} x {1}", capabilty.FrameSize.Width, capabilty.FrameSize.Height)); } comboBox2.SelectedIndex = 0; videoCapabilities = videoDevice.VideoCapabilities; comboBox2.Items.Clear(); foreach (VideoCapabilities capabilty in videoCapabilities) { comboBox2.Items.Add(string.Format("{0} x {1}", capabilty.FrameSize.Width, capabilty.FrameSize.Height)); } comboBox2.SelectedIndex = 0; } // 解像度選択 private void comboBox2_SelectedIndexChanged(object sender, EventArgs e) { videoDevice.VideoResolution = videoCapabilities[comboBox2.SelectedIndex]; } // 撮影開始 private void button1_Click(object sender, EventArgs e) { videoDevice.NewFrame += new NewFrameEventHandler(videoDevice_NewFrame); videoDevice.Start(); button1.Enabled = false; button2.Enabled = true; button3.Enabled = false; comboBox1.Enabled = false; comboBox2.Enabled = false; } // 撮影終了 private void button2_Click(object sender, EventArgs e) { if (videoDevice.IsRunning) { videoDevice.SignalToStop(); videoDevice.WaitForStop(); } pictureBox1.Image = null; button1.Enabled = true; button2.Enabled = false; button3.Enabled = true; comboBox1.Enabled = true; comboBox2.Enabled = true; } // 新フレーム void videoDevice_NewFrame(object sender, NewFrameEventArgs eventArgs) { Bitmap img = (Bitmap)eventArgs.Frame.Clone(); pictureBox1.Image = img; } // フォーム閉じる private void Form1_FormClosed(object sender, FormClosedEventArgs e) { if (videoDevice.IsRunning) { videoDevice.SignalToStop(); videoDevice.WaitForStop(); videoDevice = null; } } // バーコードスキャン開始/終了 private void button4_Click(object sender, EventArgs e) { if (timer1.Enabled) { timer1.Enabled = false ; button4.BackColor = Color.Lime; } else { timer1.Enabled = true ; } } // バーコード検索 private void timer1_Tick(object sender, EventArgs e) { if (button4.BackColor == Color.Lime) { button4.BackColor = Color.Red; } else { button4.BackColor = Color.Lime; } ZXing.BarcodeReader reader = new ZXing.BarcodeReader() { AutoRotate=true,TryInverted=true }; reader.Options = new ZXing.Common.DecodingOptions { TryHarder = true, PossibleFormats = new[] { BarcodeFormat.CODE_39 , BarcodeFormat.EAN_13 , BarcodeFormat.QR_CODE , BarcodeFormat.CODE_128 }.ToList() }; ZXing.Result result = reader.Decode(pictureBox1.Image as Bitmap); if (result != null) { this.textBox1.Text = result.BarcodeFormat.ToString().Trim(); this.textBox2.Text = result.Text; // 描画位置マーク string tmp = this.textBox1.Text; int x1 = (int)result.ResultPoints[0].X; int x2 = (int)result.ResultPoints[1].X; int y1 = (int)result.ResultPoints[0].Y; int y2 = (int)result.ResultPoints[1].Y; Bitmap canvas = new Bitmap(pictureBox1.Image); Pen p = new Pen(Color.FromArgb(200, Color.Red), 18); Graphics g = Graphics.FromImage(canvas); g.DrawImage(canvas, 0, 0, canvas.Width, canvas.Height); g.DrawLine(p, x1, y1, x2, y2); if (tmp == "QR_CODE") { int x3 = (int)result.ResultPoints[2].X; int y3 = (int)result.ResultPoints[2].Y; g.DrawLine(p, x2, y2, x3, y3); } g.Dispose(); pictureBox1.Image = canvas; } else { this.textBox1.Text = "NO BARCODE"; this.textBox2.Text = "NO BARCODE"; } reader = null; } } }
参考サイト |
①AForgeライブラリ利用方法について
静大ロボットファクトリー活動日誌
(C#で画像処理-WEBカメラの使用)
http://robot-factory.blogspot.com/2013/10/c-web.html
②ZXing.NET利用方法について
.NET TIPS
ZXing.NETでQRコードやバーコードを解析するには?[C#/VB]https://www.atmarkit.co.jp/ait/articles/1803/14/news020.html
「C#でQRコードリーダーを作る」への1件のフィードバック