2014-10-14 7 views
10

Gibt es ein Arbeitsbeispiel, wie Sie den zxing Barcode Scanner von einer Webseite verwenden können?Verwenden des zxing Barcode-Scanners innerhalb einer Webseite

Unter Bezugnahme auf diese Dokumentation: https://github.com/zxing/zxing/wiki/Scanning-From-Web-Pages

sollte nicht die folgenden Testcode Arbeit?

function Test1() 
 
{ 
 
\t $.ajax(
 
\t { 
 
     url: "zxing://scan/?ret=http%3A%2F%2Ffoo.com%2Fproducts%2F%7BCODE%7D%2Fdescription&SCAN_FORMATS=UPC_A,EAN_13", 
 
     success:function() 
 
\t \t { 
 
      alert("success"); 
 
     }, 
 
     error:function() 
 
\t \t { 
 
      alert("error"); 
 
     } 
 
    }); 
 
} 
 
\t 
 
function Test2() 
 
{ 
 
\t $.ajax(
 
\t { 
 
     url: "http://zxing.appspot.com/scan?ret=http%3A%2F%2Ffoo.com%2Fproducts%2F%7BCODE%7D%2Fdescription&SCAN_FORMATS=UPC_A,EAN_13", 
 
     success:function() 
 
\t \t { 
 
      alert("success"); 
 
     }, 
 
     error:function() 
 
\t \t { 
 
      alert("error"); 
 
     } 
 
    }); 
 
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script> 
 

 
<button id="button1" onClick="Test1();">Test 1</button> 
 
<br> 
 
<br> 
 
<button id="button2" onClick="Test2();">Test 2</button>

ich immer "Fehler" auf meinem Android 4.4.2 Samsung Galaxy TabPro und Samsung Galaxy S4 zu bekommen. Ich habe den Aktien-Browser, Chrome, Firefox und Dolphin Browser ausprobiert.

Auch http://zxing.appspot.com/scan funktioniert nicht, da es mich immer fragt, die (bereits installierte) App zu installieren.

Jede Hilfe würde sehr geschätzt werden.

Antwort

17

ZXing wurde nicht für die Verwendung mit AJAX entwickelt. Stattdessen wird eine geparste URL im Standardbrowser geöffnet. Das Verhalten des Browsers ist hauptsächlich verantwortlich für die Benutzererfahrung von diesem Punkt an.

Es gibt mehrere Methoden in Bezug auf diese; Leider gibt es keine Methode, die für jeden Browser funktioniert.

Einige Browser überprüfen beim Öffnen über die Befehlszeile, ob die URL bereits auf einer anderen Registerkarte geöffnet ist. Wenn dies der Fall ist, wird diese Registerkarte anstelle einer neuen verwendet. Dies führt zu einem "onhashchange" -Ereignis, wenn der zxing-Link "zxing: // scan /? Ret = mytab.html # {CODE}" enthält.

Andere Browser führen eine solche Überprüfung nicht durch. Daher haben wir mehrere Registerkarten, die alle die gleiche URL haben (mit Ausnahme des Hashs) und keines von ihnen das "hashchanged" -Ereignis auslöst. Bei diesen Browsern müssen wir die Seite nach Möglichkeit aus dem Cache wiederverwenden (um Netzwerkverkehr bei jedem Scan zu verhindern) und den Wert von localStorage in den Hashwert ändern. Wenn der Browser das Ereignis "storage" abhören kann, können wir den Code auslösen.

Der folgende Code funktioniert mit Chrome, dem eigentlichen Android-Browser und Firefox. Es könnte mit anderen arbeiten, aber ich habe es nicht versucht. Ein Firefox-Vorbehalt besteht jedoch darin, dass das Scannerfenster nur geschlossen wird, wenn die about: config-Einstellung "dom.allow_scripts_to_close_windows" auf "true" gesetzt ist.

** Dies wurde bearbeitet, um besser mit mehreren Seiten zu arbeiten, die Scans erlauben, und jetzt können Sie verschiedene Hashes verwenden, ohne den Code zu beeinflussen. **

NEUE VERSION 12/19/16

<!DOCTYPE html> 
<HTML> 
<HEAD> 
<script type="text/javascript"> 

    if(window.location.hash.substr(1,2) == "zx"){ 
     var bc = window.location.hash.substr(3); 
     localStorage["barcode"] = decodeURI(window.location.hash.substr(3)) 
     window.close(); 
     self.close(); 
     window.location.href = "about:blank";//In case self.close isn't allowed 
    } 
</script> 
<SCRIPT type="text/javascript" > 
    var changingHash = false; 
    function onbarcode(event){ 
     switch(event.type){ 
      case "hashchange":{ 
       if(changingHash == true){ 
        return; 
       } 
       var hash = window.location.hash; 
       if(hash.substr(0,3) == "#zx"){ 
        hash = window.location.hash.substr(3); 
        changingHash = true; 
        window.location.hash = event.oldURL.split("\#")[1] || "" 
        changingHash = false; 
        processBarcode(hash); 
       } 

       break; 
      } 
      case "storage":{ 
       window.focus(); 
       if(event.key == "barcode"){ 
        window.removeEventListener("storage", onbarcode, false); 
        processBarcode(event.newValue); 
       } 
       break; 
      } 
      default:{ 
       console.log(event) 
       break; 
      } 
     } 
    } 
    window.addEventListener("hashchange", onbarcode, false); 

    function getScan(){ 
     var href = window.location.href; 
     var ptr = href.lastIndexOf("#"); 
     if(ptr>0){ 
      href = href.substr(0,ptr); 
     } 
     window.addEventListener("storage", onbarcode, false); 
     setTimeout('window.removeEventListener("storage", onbarcode, false)', 15000); 
     localStorage.removeItem("barcode"); 
     //window.open (href + "#zx" + new Date().toString()); 

     if(navigator.userAgent.match(/Firefox/i)){ 
      //Used for Firefox. If Chrome uses this, it raises the "hashchanged" event only. 
      window.location.href = ("zxing://scan/?ret=" + encodeURIComponent(href + "#zx{CODE}")); 
     }else{ 
      //Used for Chrome. If Firefox uses this, it leaves the scan window open. 
      window.open ("zxing://scan/?ret=" + encodeURIComponent(href + "#zx{CODE}")); 
     } 
    } 

    function processBarcode(bc){ 
     document.getElementById("scans").innerHTML += "<div>" + bc + "</div>"; 
     //put your code in place of the line above. 
    } 

</SCRIPT> 
<META name="viewport" content="width=device-width, initial-scale=1" /> 
</HEAD> 
<BODY> 
<INPUT id=barcode type=text > 
<INPUT style="width:100px;height:100px" type=button value="Scan" onclick="getScan();"> 
<div id="scans"></div> 
</BODY> 
</HTML> 

Sie eine JS machen kann Datei für den oberen Block von Skript enthalten, und ob sie auf allen Seiten, auf denen Sie Scanfunktionen benötigen.

Dann im Textkörper Ihres Dokuments können Sie ein Ereignis festlegen, um getZxing() aufzurufen, das processBarcode (Barcode) aufrufen wird, das Sie in Ihre Seite schreiben. Enthalten ist zum Beispiel eine einfache.

Seitennotiz: Wenn Sie zxing zum ersten Mal von Ihrer Seite aus ausführen, werden Sie aufgefordert, eine Standardanwendung auszuwählen.Stellen Sie sicher, dass Sie denselben Browser auswählen, von dem Sie die Seite ausführen. Wenn Sie zuvor einen Standardbrowser für zxing ausgewählt haben und möchten, welchen Browser Sie für zxing verwenden möchten, müssen Sie die Standardeinstellungen der anderen Browser löschen.

Vielen Dank an @ Sean-Owen für seine harte Arbeit und fantastisches Produkt.

UPDATE 12/19/16

Ok, habe ich eine etwas robustere Version, die auch mit Firefox und Chrome funktioniert. Ein paar Dinge, die ich entdeckt habe:

Chrome verwendet das Ereignis , wenn der Scanner Chrome nicht automatisch öffnen soll, und verwendet das Ereignis Hash, nachdem es Standard wird.

Firefox wird nie die Hash Ereignis verwenden, aber öffnet sich ein zusätzliches Fenster, wenn Sie den Scanner mit window.location.href nennen (Danke, @Roland)

Es gibt ein paar andere Anomalien, aber keine Dealbreaker.

Ich habe das Präfix "zx" im Hash, so dass der Code zwischen Scanner-Hashes und regulären Hashes abgrenzen konnte. Wenn Sie es dort lassen, werden Sie es in der Funktion processBarcode nicht bemerken, und Non-Zx-Hashes werden wie erwartet funktionieren.

+0

Können Sie eine funktionierende Probe teilen? Das wäre toll –

+0

@ Mo-Prog, SCHLIESSLICH habe ich ein funktionierendes Beispiel mitgenommen. Entschuldigung für die 10-wöchige Verspätung! Ich habe auch den Code ein wenig optimiert, um mehrere Listener zu verhindern. – alfadog67

+0

Verwendung von Speicher-Event ist eine brillante Idee, vielen Dank für diesen Trick! :) –