Created
August 26, 2022 06:12
-
-
Save tangoabcdelta/91593a0147965ffd690c9de120ef4375 to your computer and use it in GitHub Desktop.
BarcodeDetector Experimental Web APIs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
html, body { | |
background: #111; | |
color: white; | |
height: 100%; | |
} | |
canvas { | |
display: none; | |
height: auto; | |
object-fit: contain; | |
object-position: center; | |
width: 300px; | |
} | |
pre, canvas { | |
background: black; | |
margin: 1rem auto; | |
} | |
pre { | |
box-sizing: border-box; | |
color: white; | |
padding: 1rem; | |
text-align: center; | |
white-space: pre-wrap; | |
width: 200px; | |
} | |
video { | |
opacity: 0; | |
position: fixed; | |
top: 0; | |
left: 0; | |
width: 10px; | |
height: auto; | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<canvas></canvas> | |
<video autoplay playsinline muted></video> | |
<pre>Click anywhere to start</pre> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
console.clear(); | |
const pre = document.querySelector("pre"); | |
const canvas = document.querySelector("canvas"); | |
const context = canvas.getContext("2d"); | |
const video = document.querySelector("video"); | |
async function run() { | |
canvas.style.display = "block"; | |
pre.innerText = ""; | |
pre.style.display = "none"; | |
const formats = await BarcodeDetector.getSupportedFormats(); | |
const detector = new BarcodeDetector({ formats }); | |
const stream = await navigator.mediaDevices.getUserMedia({ video: true }); | |
video.onloadedmetadata = () => { | |
canvas.height = video.videoHeight; | |
canvas.width = video.videoWidth; | |
loop(); | |
} | |
video.srcObject = stream; | |
const boxes = {}; | |
const codes = {}; | |
function drawBoxes(del = false) { | |
context.strokeStyle = "lime"; | |
context.lineWidth = 4; | |
Object.keys(boxes).forEach((key) => { | |
const { format, rawValue, minX, maxX, minY, maxY } = boxes[key]; | |
context.strokeRect(minX, minY, maxX - minX, maxY - minY); | |
if (del) delete boxes[key]; | |
}); | |
} | |
async function loop() { | |
try { | |
context.drawImage(video, 0, 0); | |
const image = context.getImageData(0, 0, canvas.width, canvas.height); | |
drawBoxes(true); | |
const barcodes = await detector.detect(image); | |
let changed = false; | |
barcodes.forEach(({ boundingBox: { x, y, width, height }, format, rawValue: value }) => { | |
codes[format] = codes[format] || {}; | |
if (!codes[format][value]) { | |
changed = true; | |
} | |
codes[format][value] = 1; | |
boxes[value] = boxes[value] || { | |
format, value, | |
minX: Infinity, maxX: -Infinity, | |
minY: Infinity, maxY: -Infinity | |
}; | |
boxes[value].minX = Math.min(x, boxes[value].minX); | |
boxes[value].maxX = Math.max(x + width, boxes[value].maxX); | |
boxes[value].minY = Math.min(y, boxes[value].minY); | |
boxes[value].maxY = Math.max(y + height, boxes[value].maxY); | |
}); | |
drawBoxes(); | |
if (changed) { | |
pre.style.display = "block"; | |
pre.innerHTML = Object.keys(codes).map((type) => | |
[type, ...Object.keys(codes[type])].join("\n") | |
).join("\n"); | |
} | |
setTimeout(loop, 150); | |
} catch(e) { | |
console.error(e); | |
} | |
} | |
} | |
if ("BarcodeDetector" in window) { | |
let running = false; | |
document.body.addEventListener("click", () => { | |
if (!running) { | |
running = true; | |
run(); | |
} | |
}); | |
} else { | |
pre.innerText = "BarcodeDetector is not supported by this browser"; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment