Guides
A second, independent scanner mode: point the camera at a paper document, get a straightened, multi-page PDF back in your own code. A self-contained edge detector (no external CV library) tracks the document in the frame and auto-captures once it's held steady, with a manual shutter and an adjustable crop step always available as a fallback.
Add a second trigger button next to (or instead of) the barcode one. Same script tag, no extra include:
<button type="button" data-jsscanner-document-trigger>
Scan Document
</button>
<script src="https://your-app.test/embed/YOUR_TOKEN.js"></script>
| Attribute | Default | Effect |
|---|---|---|
data-document-accent | #fb476a | Highlight color for the live tracking outline and primary buttons. |
data-jsscanner-ondocument | — | Name of a global function to call with the finished PDF (see below). |
<button type="button" data-jsscanner-document-trigger
data-document-accent="#00c2a8">
Scan Document
</button>
Same three capture methods as scan data, all firing with the same payload:
document.addEventListener("jsscanner:document", (event) => {
const { pdf, pageCount } = event.detail; // pdf is a Blob, type "application/pdf"
const url = URL.createObjectURL(pdf);
window.open(url, "_blank");
});
<button type="button" data-jsscanner-document-trigger
data-jsscanner-ondocument="handleDocument">
Scan Document
</button>
<script>
function handleDocument(pdfBlob, meta) {
const form = new FormData();
form.append("file", pdfBlob, "scan.pdf");
fetch("/my-api/upload", { method: "POST", body: form });
}
</script>
document.addEventListener("jsscanner:ready", () => {
document.getElementById("my-button").addEventListener("click", () => {
JSScannerEmbed.openDocumentScanner({
accentColor: "#00c2a8",
onDocument(pdfBlob, meta) {
console.log(meta.pageCount + " pages, " + pdfBlob.size + " bytes");
},
});
});
});