バーコードリーダーを作ることになったのでその時メモです。
今回はJavascriptのQuaggaJSを使用することにしました。
フォルダ構成
今回のフォルダ構成は以下の通りです。
/js
/css
index.html
js・・・javascriptを保存するディレクトリ
css ・・・スタイルシートを保存するディレクトリ
事前準備
カメラアクセス機能を使用するにはhttpsが必要なので証明証が入ったサーバーなりを用意。
手順
1. ライブラリのインストール
https://serratus.github.io/quaggaJS/
npmでインストールできますが、今回はzipファイルをダウンロードしてquagga.min.jsを/jsフォルダに保存します。
2. htmlファイルの作成
とりあえず、最低限のhtmlファイルを作成します。
photo-areaで指定した部分がバーコードの読み取り部分です。
<html>
<head>
<link rel="stylesheet" href="css/test.css" />
</head>
<body>
<h3>バーコード</h3>
<div id="photo-area" class="viewport"></div>
<script src="js/jquery-3.4.1.min.js" type="text/javascript"></script>
<script src="js/quagga.min.js" type="text/javascript"></script>
<script src="js/test.js" type="text/javascript"></script>
</body>
</html>
3. Quaggaの設定を記述する。
javascriptファイル(test.js)に下記内容を記述する。
$(function () {
startScanner();
});
const startScanner = () => { Quagga.init({ inputStream: { name: "Live", type: "LiveStream", target: document.querySelector('#photo-area'), constraints: { decodeBarCodeRate: 3, successTimeout: 500, codeRepetition: true, tryVertical: true, frameRate: 15, width: 352, height: 288, facingMode: "environment" }, }, decoder: { readers: [ "i2of5_reader" ] }, }, function (err) { if (err) { console.log(err); return } console.log("Initialization finished. Ready to start"); Quagga.start(); // Set flag to is running _scannerIsRunning = true; }); Quagga.onProcessed(function (result) { var drawingCtx = Quagga.canvas.ctx.overlay, drawingCanvas = Quagga.canvas.dom.overlay; if (result) { if (result.boxes) { drawingCtx.clearRect(0, 0, parseInt(drawingCanvas.getAttribute("width")), parseInt(drawingCanvas.getAttribute("height"))); result.boxes.filter(function (box) { return box !== result.box; }).forEach(function (box) { Quagga.ImageDebug.drawPath(box, { x: 0, y: 1 }, drawingCtx, { color: "green", lineWidth: 2 }); }); } if (result.box) { Quagga.ImageDebug.drawPath(result.box, { x: 0, y: 1 }, drawingCtx, { color: "#00F", lineWidth: 2 }); } if (result.codeResult && result.codeResult.code) { Quagga.ImageDebug.drawPath(result.line, { x: 'x', y: 'y' }, drawingCtx, { color: 'red', lineWidth: 3 }); } } }); //barcode read call back Quagga.onDetected(function (result) { console.log(result.codeResult.code); }); }
Quagga.onProcessed部分は、バーコードに枠を表示する部分です。
4.スタイルシートの設定
このままだと枠が正しい位置に表示されないのでスタイルシート(test.css)で調整します。
#photo-area.viewport { height: 288px; } #photo-area.viewport canvas, video { float: left; height: 288px; } #photo-area.viewport canvas.drawingBuffer, video.drawingBuffer { margin-left: -352px; }
注意点は以下の2つです。
- Quagga.initのheightとviewport canvas, videoのheightを合わせる。
- Quagga.initのwidthの値分、viewport canvas, videoのmargin-leftをマイナス設定する。
バーコードリーダーの感度
このままでiphoneなどで実際にバーコードを読もうとすると中々認識してくれません。
おそらくスマフォのカメラのサイズが1600×1200だとすると、videoのサイズを320x240にしているので画像を縮小した際に画像が劣化して読めないんじゃないかと。
そこで思いついたのが、video自体は640x480のサイズにして、表示は320x240の中央のみを表示すれば感度が上がるのではないかと。
先ず、javascriptファイル(test.js)のQuaggaの設定を640x480に変更します。
const startScanner = () => { Quagga.init({ inputStream: { name: "Live", type: "LiveStream", target: document.querySelector('#photo-area'), constraints: { decodeBarCodeRate: 3, successTimeout: 500, codeRepetition: true, tryVertical: true, frameRate: 15, width: 640, height: 480, facingMode: "environment" }, }, }
続いてvideoの中央部分を320x240で表示するようにobject-fit: noneをcssに設定します。
#photo-area.viewport { height: 240px; width:320px; } #photo-area.viewport canvas, video { float: left; width:320px; height: 240px; } #photo-area.viewport canvas.drawingBuffer, video.drawingBuffer { margin-left: -320px; }
なお、object-fitはIE/Edgeが対応していないので対応させる場合はfitie.jsなんかで。
このバージョンで確認してみるとサクサクっとバーコードを認識してくれます👍