<script>
	import { onMount, createEventDispatcher } from "svelte";
	import {
		Html5QrcodeScanner,
		Html5QrcodeScanType,
		Html5QrcodeSupportedFormats,
	} from "html5-qrcode";
	import { debounce } from "underscore";

	export let width;
	export let height;
	export let paused = false;

	const dispatch = createEventDispatcher();

	const debouncedDispatch = debounce(
		function (decodedText) {
			// console.log("dispatchEvent");
			dispatch("detect", { decodedText });
		},
		500,
		true
	);

	function onScanSuccess(decodedText, decodedResult) {
		// console.log("onScanSuccess", decodedText);
		if (!paused) {
			debouncedDispatch(decodedText);
		}
	}

	// usually better to ignore and keep scanning
	function onScanFailure(message) {
		if (!paused) {
			dispatch("error", { message });
		}
	}

	let scanner;
	onMount(() => {
		scanner = new Html5QrcodeScanner(
			"qr-scanner",
			{
				fps: 10,
				showTorchButtonIfSupported: true,
				rememberLastUsedCamera: true,
				qrbox: { width, height },
				aspectRatio: 1,
				supportedScanTypes: [Html5QrcodeScanType.SCAN_TYPE_CAMERA],
				formatsToSupport: [
					Html5QrcodeSupportedFormats.CODE_39,
					Html5QrcodeSupportedFormats.EAN_8,
					Html5QrcodeSupportedFormats.EAN_13,
					Html5QrcodeSupportedFormats.QR_CODE,
					Html5QrcodeSupportedFormats.CODE_128,
				],
			},
			false // non-verbose
		);
		scanner.render(onScanSuccess, onScanFailure);
	});
</script>

<div id="qr-scanner" class={$$props.class} />

<style>
	/* Hide unwanted icons */
	#qr-scanner :global(img[alt="Info icon"]),
	#qr-scanner :global(img[alt="Camera based scan"]) {
		display: none;
	}

	/* Change camera permission button text */
	#qr-scanner :global(#html5-qrcode-button-camera-permission) {
		visibility: hidden;
	}
	#qr-scanner :global(#html5-qrcode-button-camera-permission::after) {
		position: absolute;
		inset: auto 0 0;
		display: block;
		content: "Allow camera access";
		visibility: visible;
		padding: 10px 0;
	}
</style>
