Search code examples
javascriptgetelementbyid

Scan to elementbyid on button click?


This example prompts for barcode scan, and then places the value into "scan-input" box. This works great for ONE input/ONE button.

My issue is i want to be able to add multiple inputs/buttons, and have the scan then place the value in the corresponding input text box.

<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <title>Scandit Web SDK</title>
    <link rel="stylesheet" href="style.css">
    <meta name='viewport' content='width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=0'/>

    <!-- Add the library, as explained on http://docs.scandit.com/stable/web/index.html -->
    <script src="https://cdn.jsdelivr.net/npm/scandit-sdk@4.x"></script>
</head>

<body onclick="console.log('body clicked')">
    <div id="scandit-barcode-picker"></div>
    <div id="input-container">
        <input id="scan-input" type="text" placeholder="Scan Receiver...">
        <button id="scan" onclick="scan()">SCAN
        </button>
    </div>

    <script>
        function scan() {
            startScanning();
        }
        function showScanner() {
            scannerContainer.style.opacity = "1";
            scannerContainer.style.zIndex = "1";
        }
        function hideScanner() {
            scannerContainer.style.opacity = "0";
            scannerContainer.style.zIndex = "-1";
        }
        function startScanning() {
            showScanner();
            if (picker) {
                picker.resumeScanning();
            }
        }
        function stopScanning() {
            hideScanner();
            if (picker) {
                picker.pauseScanning();
            }
        }
        // Configure the library and activate it with a license key
        const licenseKey = "LICENSE_KEY_HERE";
        // Configure the engine location, as explained on http://docs.scandit.com/stable/web/index.html
        const engineLocation = "https://cdn.jsdelivr.net/npm/scandit-sdk@4.x/build"
        ScanditSDK.configure(licenseKey, { engineLocation: engineLocation });
        const scannerContainer = document.getElementById("scandit-barcode-picker");
        scannerContainer.style.opacity = "0";
        scannerContainer.style.zIndex = "-1";
        const scanInput = document.getElementById("scan-input");
        let picker;
        // Create & start the picker
        ScanditSDK.BarcodePicker.create(scannerContainer)
            .then(barcodePicker => {
                picker = barcodePicker;
                // Create the settings object to be applied to the scanner
                const scanSettings = new ScanditSDK.ScanSettings({
                    enabledSymbologies: ["ean8", "ean13", "upca", "upce", "code128", "code39"]
                });
                picker.applyScanSettings(scanSettings);
                picker.on("scan", scanResult => {
                    stopScanning();
                    scanInput.value = scanResult.barcodes[0].data;
                });
                picker.on("scanError", error => alert(error.message));
                picker.resumeScanning();
            })
            .catch(alert);
    </script>
</body>
    <style>#scan:after {display:none;}</style>
</html>`

I want to be able to add multiple buttons/inputs. and have the corresponding button place it into the scan-input spot.

`<input id="scan-input" type="text" placeholder="Scan Receiver...">
<button id="scan" onclick="scan()">SCAN</button>

<input id="scan-input2" type="text" placeholder="Scan Receiver #2...">
<button id="scan2" onclick="scan()">SCAN</button>`

[text1] [button1] ----- scan places value into text1 [text2] [button2] ----- scan places value into text2


Solution

  • Here's a slightly adapted version of your HTML (using a digit in every id will help us keep things simpler):

    <input type="text" id="scan-input1" />
    <button type="button" id="scan1">SCAN</button>
    <br />
    <input type="text" id="scan-input2" />
    <button type="button" id="scan2">SCAN</button>
    

    Then, in our JavaScript, we can use the following function to send a message to scan-input1 if scan1 is pressed, scan-input2 if scan-2 is pressed, and so on:

    [...document.getElementsByTagName('button')].forEach((el) => {
      el.addEventListener('click', (e) => {
        const num = e.currentTarget.id.match(/\d+$/)[0];
        document.getElementById(`scan-input${num}`).value = "Scan Complete";
      });
    });
    

    The code above:

    • Adds a click event listener to every button,

    • Gets the number from the id of whichever button is clicked,

    • Uses that number to target the correct input.

    The advantage of the solution above is that it scales automatically. As long as you follow the same naming convention for each id (scan3, scan-input3, etc.), every a new button and input will have identical behaviour.

    Edit: Your Code

    Below, I've inserted my suggestion into your code - only changing the bare minimum:

    <!DOCTYPE html>
    <html lang="en">
    
    <head>
      <meta charset="UTF-8">
      <title>Scandit Web SDK</title>
      <link rel="stylesheet" href="style.css">
      <meta name='viewport' content='width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=0' />
    
      <!-- Add the library, as explained on http://docs.scandit.com/stable/web/index.html -->
      <script src="https://cdn.jsdelivr.net/npm/scandit-sdk@4.x"></script>
    </head>
    
    <body onclick="console.log('body clicked')">
      <div id="scandit-barcode-picker"></div>
      <div id="input-container">
        <input type="text" id="scan-input1" />
        <button type="button" id="scan1" placeholder="Scan Receiver...">SCAN</button>
        <br />
        <input type="text" id="scan-input2" />
        <button type="button" id="scan2" placeholder="Scan Receiver...">SCAN</button>
        <br />
        <input type="text" id="scan-input3" />
        <button type="button" id="scan3" placeholder="Scan Receiver...">SCAN</button>
        </button>
      </div>
    
      <script>
        let scanInput;
    
        [...document.getElementsByTagName('button')].forEach((el) => {
          el.addEventListener('click', (e) => {
            const num = e.currentTarget.id.match(/\d+$/)[0];
            scanInput = document.getElementById(`scan-input${num}`);
            scan();
          });
        });
    
        function scan() {
          startScanning();
        }
    
        function showScanner() {
          scannerContainer.style.opacity = "1";
          scannerContainer.style.zIndex = "1";
        }
    
        function hideScanner() {
          scannerContainer.style.opacity = "0";
          scannerContainer.style.zIndex = "-1";
        }
    
        function startScanning() {
          showScanner();
          if (picker) {
            picker.resumeScanning();
          }
        }
    
        function stopScanning() {
          hideScanner();
          if (picker) {
            picker.pauseScanning();
          }
        }
        // Configure the library and activate it with a license key
        const licenseKey = "LICENSE_KEY_HERE";
        // Configure the engine location, as explained on http://docs.scandit.com/stable/web/index.html
        const engineLocation = "https://cdn.jsdelivr.net/npm/scandit-sdk@4.x/build"
        ScanditSDK.configure(licenseKey, {
          engineLocation: engineLocation
        });
        const scannerContainer = document.getElementById("scandit-barcode-picker");
        scannerContainer.style.opacity = "0";
        scannerContainer.style.zIndex = "-1";
        let picker;
        // Create & start the picker
        ScanditSDK.BarcodePicker.create(scannerContainer)
          .then(barcodePicker => {
            picker = barcodePicker;
            // Create the settings object to be applied to the scanner
            const scanSettings = new ScanditSDK.ScanSettings({
              enabledSymbologies: ["ean8", "ean13", "upca", "upce", "code128", "code39"]
            });
            picker.applyScanSettings(scanSettings);
            picker.on("scan", scanResult => {
              stopScanning();
              scanInput.value = scanResult.barcodes[0].data;
            });
            picker.on("scanError", error => alert(error.message));
            picker.resumeScanning();
          })
          .catch(alert);
    
      </script>
    </body>
    <style>
      #scan:after {
        display: none;
      }
    
    </style>
    
    </html>`