Vue implementiert die browserseitige Code-Scan-Funktion

Vue implementiert die browserseitige Code-Scan-Funktion

Hintergrund

Vor nicht allzu langer Zeit habe ich eine Funktion zum Abrufen der Browserkamera und zum Scannen der Codeerkennung erstellt. Dieser Artikel sortierte die beteiligten Wissenspunkte und die spezifische Codeimplementierung und organisierte sie in den Inhalt dieses Artikels.

In diesem Artikel wird hauptsächlich die Verwendung der auf dem vue -Technologiestapel basierenden Front-End-Entwicklungstechnologie zum Aufrufen der Kamera 📷 auf der Browserseite, zum Scannen und Erkennen von Codes sowie zum Springen oder Ausführen anderer Vorgänge auf dem erkannten QR-Code beschrieben. Der Inhalt dieses Artikels ist in Hintergrundeinführung, Implementierungswirkung, technische Einführung, Codeimplementierung, Zusammenfassung und andere Teile unterteilt.

Ergebnisse erzielen

In diesem Beispiel gibt es zwei Hauptseiten: die Homepage und die Seite zum Scannen des QR-Codes. Der spezifische Implementierungseffekt ist in der folgenden Abbildung dargestellt.

  • Startseite: Klicken Sie auf die Schaltfläche SCAN QRCODE um die Seite zum Scannen des QR-Codes aufzurufen.
  • Code-Scan-Seite: Wenn Sie die Seite zum ersten Mal aufrufen, wird möglicherweise獲取攝像頭訪問權限的系統提示框angezeigt. Klicken Sie auf Zugriff zulassen. Die Seite beginnt mit dem Laden von Kameradaten und dem Erfassen von QR-Codes. Wenn ein QR-Code erfasst wird, wird der QR-Code analysiert. Nach erfolgreicher Analyse wird ein Popup-Fenster angezeigt, das die erfolgreiche Erkennung anzeigt.

Online-Erfahrung: https://dragonir.github.io/h5-scan-qrcode

Tipp: Sie müssen im Hochformat in einem Browser mit einem Kameragerät darauf zugreifen. Weitere Tipps zur horizontalen und vertikalen Bildschirmerkennung von Mobiltelefonen finden Sie in meinem anderen Artikel „Front-End-Wissen im Gokudō-Spiel“.

Technische Einführung

WebRTC-API

WebRTC (Web Real-Time Communications) ist eine Echtzeit-Kommunikationstechnologie, die es Netzwerkanwendungen oder Sites ermöglicht, ohne die Hilfe eines Vermittlers點對點(Peer-to-Peer) Verbindungen zwischen Browsern herzustellen, um die Übertragung von Video- und/oder Audio-Streams oder anderen Daten zu erreichen. Die in WebRTC enthaltenen Standards ermöglichen es Benutzern點對點(Peer-to-Peer) Datenaustausch und Konferenzgespräche zu erstellen, ohne Plug-Ins oder Software von Drittanbietern installieren zu müssen.

Drei Hauptschnittstellen:

  • MediaStream : Kann synchronisierte Video- und Audio-Streams über die Kamera und das Mikrofon des Geräts abrufen.
  • RTCPeerConnection : Dies ist eine von WebRTC verwendete Komponente zum Aufbau einer stabilen und effizienten Streaming-Übertragung zwischen Peers.
  • RTCDataChannel : ermöglicht die Einrichtung eines Kanals mit hohem Durchsatz und geringer Latenz zwischen Browsern zur Übertragung beliebiger Daten.

🔗 Informationen finden Sie auf MDN : WebRTC_API

WebRTC-Adapter

Obwohl die WebRTC Spezifikation relativ solide und stabil ist, haben nicht alle Browser alle Funktionen implementiert. Einige Browser müssen einigen oder allen WebRTC API Präfixe hinzufügen, um sie richtig verwenden zu können.

WebRTC -Organisation stellt auf github einen WebRTC適配器(WebRTC adapter) bereit, um die Kompatibilitätsprobleme bei der Implementierung WebRTC auf verschiedenen Browsern zu lösen. Der Adapter ist ein JavaScript墊片, der es Ihnen ermöglicht, Code wie in WebRTC Spezifikation beschrieben zu schreiben, ohne Präfixe oder andere Kompatibilitäts-Workarounds in allen Browsern schreiben zu müssen, die WebRTC unterstützen.

🔗 Informationen finden Sie auf MDN : WebRTC-Adapter

Kern-API navigator.mediaDevices.getUserMedia

Die Webseite muss getUserMedia API aufrufen, um die Kamera aufzurufen. MediaDevices.getUserMedia() fordert den Benutzer auf, die Berechtigung zur Verwendung der Medieneingabe zu erteilen. Die Medieneingabe generiert einen MediaStream , der den Titel des angeforderten Medientyps enthält. Dieser Stream kann eine Videospur (von einer Hardware- oder virtuellen Videoquelle, etwa einer Kamera, einem Videoaufnahmegerät, einem Bildschirmfreigabedienst usw.), eine Audiospur (ebenfalls von einer Hardware- oder virtuellen Audioquelle, etwa einem Mikrofon, A/D轉換器usw.) und möglicherweise andere Spurtypen enthalten.

Es gibt ein Promise -Objekt zurück, das bei Erfolg ein MediaStream對象resolve und zurückruft. Wenn der Benutzer die Berechtigung zur Verwendung verweigert oder die erforderliche Medienquelle nicht verfügbar ist, wird promise reject und ein PermissionDeniedError oder NotFoundError zurückgerufen. (Das zurückgegebene promise對象kann weder resolve noch reject , da der Benutzer sich nicht unbedingt dafür entscheiden muss, das Versprechen zuzulassen oder abzulehnen.)

MediaDevices können normalerweise über navigator.mediaDevices abgerufen werden, zum Beispiel:

navigator.mediaDevices.getUserMedia(Einschränkungen)
  .dann(Funktion(Stream) {
    // Diesen Stream verwenden
  })
  .catch(Funktion(Fehler) {
    // Fehler behandeln
  })

🔗 Informationen finden Sie auf MDN : navigator.mediaDevices.getUserMedia

QR-Code-Analysebibliothek JSQR

jsQR ist eine reine JavaScript Bibliothek zur Analyse von QR-Codes, die ein Rohbild oder einen Kamera-Feed liest und alle darin enthaltenen QR碼findet, extrahiert und analysiert.

Wenn Sie einen Webcam-Stream mit jsQR scannen möchten, müssen Sie ImageData aus dem Videostream extrahieren, die Sie dann an jsQR übergeben können.

jsQR exportiert eine Methode, die 4 Parameter akzeptiert, nämlich die dekodierten圖像數據,,und可選的對象zur weiteren Konfiguration des Scanverhaltens.

imageData : rgba Pixelwerte im [r0, g0, b0, a0, r1, g1, b1, a1, ...] Uint8ClampedArray( 8位無符號整型固定數組) .

const code = jsQR(imageData, Breite, Höhe, Optionen);
wenn (Code) {
  console.log('QR-Code gefunden!', Code);
}

🔗 Informationen finden Sie auf github : jsQR

Code-Implementierung

Verfahren

Der gesamte Code-Scanvorgang ist in der folgenden Abbildung dargestellt: Die Seite wird initialisiert. Zuerst wird geprüft, ob der Browser die API für mediaDevices unterstützt. Der Browser ruft die Kamera auf. Wenn der Aufruf fehlschlägt, wird der Fehlerrückruf ausgeführt. Wenn der Aufruf erfolgreich ist, wird der Videostream erfasst und anschließend der Code zur Erkennung gescannt. Wenn kein erkennbarer QR-Code gescannt wird, wird der Scanvorgang fortgesetzt. Nachdem der Code erfolgreich gescannt wurde, wird ein Scan-Erfolgsmuster gezeichnet und ein Erfolgsrückruf ausgeführt.

Der folgende Inhalt unterteilt den Prozess und implementiert jeweils die entsprechenden Funktionen.

Scaner

Seitenstruktur

Schauen wir uns zunächst die Seitenstruktur an, die im Wesentlichen aus 4 Teilen besteht:

  • Eingabeaufforderungsfeld.
  • Codefeld scannen.
  • video : Zeigt den von der Kamera aufgenommenen Videostream an.
  • canvas : Zeichnen Sie Videobilder zur QR-Code-Erkennung.
<Vorlage>
  <div Klasse="Scanner" ref="Scanner">
    <!-- Eingabeaufforderungsfeld: wird verwendet, um Eingabeaufforderungen in inkompatiblen Browsern anzuzeigen-->
    <div Klasse="Banner" v-if="showBanner">
      <i class="close_icon" @click="() => showBanner = false"></i>
      <p class="text">Wenn der aktuelle Browser den Code nicht scannen kann, wechseln Sie bitte zu einem anderen Browser und versuchen Sie es</p>
    </div>
    <!-- Scancode-Feld: Scancode-Animation anzeigen-->
    <div Klasse="Abdeckung">
      <p Klasse="Zeile"></p>
      <span class="Quadrat oben links"></span>
      <span class="Quadrat oben rechts"></span>
      <span class="Quadrat unten rechts"></span>
      <span class="Quadrat unten links"></span>
      <p class="tips">Legen Sie den QR-Code in das Feld ein und er wird automatisch gescannt</p>
    </div>
    <!-- Videostream-Anzeige -->
    <Video
      v-show="Wiedergeben anzeigen"
      Klasse="Quelle"
      ref="Video"
      :Breite="videoWH.Breite"
      :Höhe="videoWH.Höhe"
      Bedienelemente
    ></video>
    <canvas v-show="!showPlay" ref="canvas" />
    <button v-show="showPlay" @click="run">Starten</button>
  </div>
</Vorlage>

Methode: Zeichnen

  • Zeichne eine Linie.
  • Bilderrahmen (wird zum Zeichnen einer rechteckigen Form nach erfolgreichem Scannen des Codes verwendet).

// Zeichne eine Linie drawLine (beginn, Ende) {
  dies.canvas.beginPath();
  dies.canvas.moveTo(begin.x, begin.y);
  dies.canvas.lineTo(end.x, end.y);
  diese.canvas.lineWidth = diese.lineWidth;
  dies.canvas.strokeStyle = diese.lineColor;
  dies.canvas.stroke();
},
// drawBox (Standort) {
  wenn (dies.drawOnfound) {
    dies.drawLine(Standort.oberelinkeEcke, Standort.obererechteEcke);
    this.drawLine(Standort.obereRechteEcke, Standort.untereRechteEcke);
    dies.drawLine(standort.untereRechteEcke,standort.untereLinkeEcke);
    dies.drawLine(Standort.unterelinkeEcke, Standort.oberelinkeEcke);
  }
},

Methode: Initialisierung

  • Überprüfen Sie, ob es unterstützt wird.
  • Schalten Sie die Kamera ein.
  • Erfolgs- und Fehlerverarbeitung.

// Initialisierung setup () {
  // Bestimmen Sie, ob der Browser die an MediaDevices.getUserMedia() gemountete Methode unterstützt, wenn (navigator.mediaDevices && navigator.mediaDevices.getUserMedia) {
    dieser.vorherigerCode = null;
    diese.parität = 0;
    dies.aktiv = wahr;
    dies.canvas = dies.$refs.canvas.getContext("2d");
    // Kameramodus abrufen. Die Standardeinstellung ist die Rückkamera const facingMode = this.useBackCamera ? { exact: 'environment' } : 'user';
    // Kamera-Videoverarbeitung const handleSuccess = stream => {
       wenn (this.$refs.video.srcObject !== undefiniert) {
        dies.$refs.video.srcObject = Stream;
      } sonst wenn (window.videoEl.mozSrcObject !== undefiniert) {
        dies.$refs.video.mozSrcObject = Stream;
      } sonst wenn (window.URL.createObjectURL) {
        dies.$refs.video.src = Fenster.URL.createObjectURL(Stream);
      } sonst wenn (window.webkitURL) {
        dies.$refs.video.src = Fenster.webkitURL.createObjectURL(Stream);
      } anders {
        dies.$refs.video.src = Stream;
      }
      // Wenn Sie nicht möchten, dass der Benutzer den Fortschrittsbalken zieht, können Sie direkt das Attribut „playsinline“ verwenden, das Webkit-Attribut „playsinline“ this.$refs.video.playsInline = true;
      const playPromise = this.$refs.video.play();
      playPromise.catch(() => (this.showPlay = true));
      //Scannen Sie den Code regelmäßig zur Identifizierung, wenn die Videowiedergabe beginntplayPromise.then(this.run);
    };
    // Videostream erfassen navigator.mediaDevices
      .getUserMedia({ video: { facingMode } })
      .then(HandleErfolg)
      .fangen(() => {
        navigator.mediaDevices
          .getUserMedia({ video: true })
          .then(HandleErfolg)
          .catch(Fehler => {
            dies.$emit("Fehler erfasst", Fehler);
          });
      });
  }
},

Methode: Periodisches Scannen

laufen () {
  wenn (dies.aktiv) {
    // Der Browser ruft die Scan-Methode requestAnimationFrame(this.tick) in einer Schleife vor dem nächsten Neuzeichnen auf;
  }
},

Methode: Erfolgsrückruf

// QR-Code-Erkennung erfolgreich, Ereignisverarbeitung gefunden (Code) {
  wenn (dieser.vorherigerCode !== code) {
    dieser.vorherigerCode = Code;
  } sonst wenn (dieser.vorherigerCode === Code) {
    diese.parität += 1;
  }
  wenn (diese.Parität > 2) {
    this.active = this.stopOnScanned ? false : wahr;
    diese.parität = 0;
    dies.$emit("Code gescannt", Code);
  }
},

Methode: Stopp

// Punkt fullStop () {
  wenn (dieses.$refs.video && dieses.$refs.video.srcObject) {
    // Stoppen Sie die Video-Stream-Sequenzverfolgung this.$refs.video.srcObject.getTracks().forEach(t => t.stop());
  }
}

Methode: Scannen

  • Zeichnen Sie den Video-Frame.
  • Zur Identifikation den QR-Code scannen.

// Periodisches Scannen und Erkennen des Codes tick () {
  // Das Video befindet sich in der Vorbereitungsphase und hat genügend Daten geladen, wenn (this.$refs.video && this.$refs.video.readyState === this.$refs.video.HAVE_ENOUGH_DATA) {
    // Beginnen Sie, das Video auf der Leinwand zu zeichnen. this.$refs.canvas.height = this.videoWH.height;
    dies.$refs.canvas.width = dies.videoWH.width;
    dies.canvas.drawImage(dieses.$refs.video, 0, 0, dies.$refs.canvas.width, dies.$refs.canvas.height);
    // getImageData() kopiert die Pixeldaten des angegebenen Rechtecks ​​auf die Leinwand const imageData = this.canvas.getImageData(0, 0, this.$refs.canvas.width, this.$refs.canvas.height);
    lass Code = false;
    versuchen {
      // QR-Code erkennen code = jsQR(imageData.data, imageData.width, imageData.height);
    } fangen (e) {
      konsole.fehler(e);
    }
    // Wenn der QR-Code erkannt wird, zeichne ein rechteckiges Kästchen if (code) {
      dies.drawBox(code.location);
      // Erfolgreiche Ereignisverarbeitung identifizieren this.found(code.data);
    }
  }
  dies.laufen();
},

Übergeordnete Komponente

Die übergeordnete Komponente des Scaner lädt hauptsächlich die Seite und zeigt den Rückruf der Scan-Ergebnisse Scaner an.

Seitenstruktur

<Vorlage>
  <div Klasse="scan">
    <!-- Seitennavigationsleiste-->
    <div Klasse="nav">
      <a class="schließen" @click="() => $router.go(-1)"></a>
      <p class="title">QR-Code scannen</p>
    </div>
    <div Klasse="Scroll-Container">
      <!-- Unterkomponente des Scancodes-->
      <Scanner
        v-on:code-scanned="Code gescannt"
        v-on:error-captured="Fehler erfasst"
        :Stopp beim Scannen="true"
        :draw-on-found="wahr"
        :responsive="false"
      />
    </div>
  </div>
</Vorlage>

Methode der übergeordneten Komponente

importiere Scaner aus „../components/Scaner“;

Standard exportieren {
  Name: 'Scannen',
  Komponenten:
    Scanner
  },
  Daten () {
    zurückkehren {
      Fehlermeldung: "",
      gescannt: ""
    }
  },
  Methoden: {
    codeGescannt(code) {
      dies.gescannt = Code;
      setzeTimeout(() => {
        alert(`Code scannen und erfolgreich analysieren: $[code]`);
      }, 200)
    },
    Fehler erfasst (Fehler) {
      Schalter (Fehlername) {
        Fall „Nicht zulässiger Fehler“:
          this.errorMessage = "Kameraberechtigung verweigert.";
          brechen;
        Fall „Nicht gefundener Fehler“:
          this.errorMessage = "Es ist keine Kamera angeschlossen.";
          brechen;
        Fall „Nicht unterstützter Fehler“:
          diese.Fehlernachricht =
            "Diese Seite scheint in einem nicht sicheren Kontext bereitgestellt zu werden.";
          brechen;
        Fall „Nicht lesbar“:
          diese.Fehlernachricht =
            "Auf Ihre Kamera konnte nicht zugegriffen werden. Wird sie bereits verwendet?";
          brechen;
        Fall „Überbeschränkter Fehler“:
          this.errorMessage = "Die Einschränkungen stimmen mit keiner installierten Kamera überein.";
          brechen;
        Standard:
          this.errorMessage = "UNBEKANNTER FEHLER: " + error.message;
      }
      Konsole.Fehler(diese.Fehlernachricht);
     alert('Kameraaufruf fehlgeschlagen');
    }
  },
  montiert () {
    var str = navigator.userAgent.toLowerCase();
    var ver = str.match(/cpu iphone os (.*?) wie mac os/);
    // Nach dem Testen kann die Kamera auf Systemen unter iOS 10.3.3 nicht erfolgreich aufgerufen werden if (ver && ver[1].replace(/_/g,".") < '10.3.3') {
     alert('Kameraaufruf fehlgeschlagen');
    }
  }

Vollständiger Code

🔗 github: https://github.com/dragonir/h5-scan-qrcode

Zusammenfassen

Anwendungserweiterungen

Ich denke, dass die folgenden Funktionen durch Aufrufen der Kamera und Scannen und Identifizieren über den Browser realisiert werden können. Welche anderen很哇塞🌟 Funktionen und Anwendungen können Ihrer Meinung nach durch Scannen des Codes auf der Browserseite realisiert werden 😂

  • Linksprung.
  • Preisanfrage.
  • Login-Authentifizierung.
  • Dateidownload.

Kompatibilität

  • wenn adapter verwendet wird, wird getUserMedia API in einigen Browsern nicht unterstützt.
  • mit niedriger Version (z. B. unter iOS 10.3 ) und Android Nischenbrowser (z. B. der integrierte Browser IQOO ) sind nicht kompatibel.
  • Die integrierten Browser von QQ und微信können nicht aufgerufen werden.

Verweise

[1]. Aufnehmen von Standbildern mit WebRTC

[2]. Kameraauswahl in JavaScript mit der mediaDevices API

[3]. So verwenden Sie JavaScript, um auf die Vorder- und Rückkameras eines Geräts zuzugreifen

Autor: dragonir Artikel-URL: https://www.cnblogs.com/dragonir/p/15405141.html

Dies ist das Ende dieses Artikels über die Implementierung der browserseitigen Code-Scan-Funktion von Vue. Weitere relevante Inhalte zum Code-Scannen im Vue-Browser finden Sie in den vorherigen Artikeln von 123WORDPRESS.COM oder in den folgenden verwandten Artikeln. Ich hoffe, dass jeder 123WORDPRESS.COM in Zukunft unterstützen wird!

Das könnte Sie auch interessieren:
  • Implementierungsbeispiel für Scan-Code-Zahlung im Vue-Projekt (mit Demo)
  • Vue implementiert QR-Code-Scanfunktion (mit Stil)
  • Vue implementiert Code-Scan-Funktion
  • Vue+abp WeChat Scan-Code-Anmeldeimplementierungscodebeispiel
  • Vue WeChat-Scancode-Anmeldung (benutzerdefinierter Stil)

<<:  So installieren Sie OpenJDK in Docker und führen das JAR-Paket aus

>>:  Tutorial zur HTML-Tabellenauszeichnung (29): Farbattribut für helle Zellenränder BORDERCOLORLIGHT

Artikel empfehlen

So simulieren Sie eine Aufzählung mit JS

Vorwort Im aktuellen JavaScript gibt es kein Konz...

MySQL-Update-Fall Update-Feldwert ist keine feste Operation

Wenn bei der Verarbeitung von Batch-Updates besti...

10 sehr gute CSS-Fähigkeiten sammeln und teilen

Hier können Sie durch geschickten Einsatz von CSS-...

Tastenkombinationsvorgang für SQL Server-Kommentare

Batchkommentare in SQL Server Batch-Annotation St...

HTML+CSS-Implementierungscode für abgerundete Rechtecke

Mir war langweilig und plötzlich fiel mir die Impl...

Verwendung des Linux-Befehls ln

1. Befehlseinführung Mit dem Befehl ln werden Lin...

NodeJS realisiert die Bildtextsegmentierung

In diesem Artikel wird der spezifische Code von N...

js zur Implementierung einer Überprüfungscode-Interferenz (dynamisch)

In diesem Artikelbeispiel wird der spezifische Co...

Grafische Schritte zur Zabbix-Überwachung des VMware Exsi-Hosts

1. Rufen Sie das Virtualisierungscenter auf, meld...