Augmented Reality: Vielleicht kennen Sie es schon

Wenn Sie die WebXR Device API bereits verwendet haben, sind Sie bereits erfolgreich.

Joe Medley
Joe Medley

Die WebXR Device API wurde letzten Herbst in Chrome 79 ausgeliefert. Wie bereits erwähnt, ist die Implementierung der API in Chrome noch in der Entwicklung. Chrome freut sich, mitteilen zu können, dass einige Arbeiten abgeschlossen sind. In Chrome 81 sind zwei neue Funktionen verfügbar:

In diesem Artikel geht es um Augmented Reality. Wenn Sie die WebXR Device API bereits verwendet haben, wird es Sie freuen, dass es so wenig Neues gibt. Der Beginn einer WebXR-Sitzung ist weitgehend gleich. Das Ausführen einer Frameschleife ist weitgehend identisch. Die Unterschiede liegen in Konfigurationen, mit denen Inhalte für Augmented Reality angemessen angezeigt werden können. Wenn Sie mit den grundlegenden Konzepten von WebXR nicht vertraut sind, sollten Sie meine früheren Beiträge zur WebXR Device API lesen oder zumindest mit den darin behandelten Themen vertraut sein. Sie sollten wissen, wie Sie eine Sitzung anfordern und betreten, und wie Sie eine Frameschleife ausführen.

Informationen zu Treffertests finden Sie im zugehörigen Artikel Virtuelle Objekte in realen Ansichten positionieren. Der Code in diesem Artikel basiert auf dem Beispiel für eine immersive AR-Sitzung (Demo Quelle) aus den WebXR Device API-Beispielen der Immersive Web Working Group.

Bevor Sie sich mit dem Code befassen, sollten Sie mindestens einmal das Beispiel für eine immersive AR-Sitzung verwenden. Sie benötigen ein modernes Android-Smartphone mit Chrome 81 oder höher.

Wofür ist er nützlich?

Augmented Reality ist eine wertvolle Ergänzung zu vielen bestehenden oder neuen Webseiten, da sie AR-Anwendungsfälle implementieren können, ohne den Browser verlassen zu müssen. Nutzer können so beispielsweise auf Bildungswebsites lernen, während potenzielle Käufer sich beim Einkaufen Objekte in ihrem Zuhause ansehen können.

Betrachten wir den zweiten Anwendungsfall. Stellen Sie sich vor, Sie könnten eine lebensgroße Darstellung eines virtuellen Objekts in einer realen Szene simulieren. Nach dem Platzieren bleibt das Bild auf der ausgewählten Oberfläche und wird in der Größe angezeigt, die es hätte, wenn sich das tatsächliche Element auf dieser Oberfläche befände. Der Nutzer kann sich auf der Oberfläche sowie näher an ihr oder weiter von ihr bewegen. So erhalten Betrachter ein tiefergehendes Verständnis des Objekts als mit einem zweidimensionalen Bild.

Ich bin etwas weiter weg. Für das, was ich beschrieben habe, brauchen Sie AR-Funktionen und eine Möglichkeit, Oberflächen zu erkennen. In diesem Artikel geht es um Ersteres. Letztere wird im zugehörigen Artikel zur WebXR Hit Test API (siehe oben) behandelt.

Sitzung anfordern

Das Anfordern einer Sitzung ist im Wesentlichen ähnlich wie das, was Sie bisher gesehen haben. Prüfen Sie zuerst, ob der gewünschte Sitzungstyp auf dem aktuellen Gerät verfügbar ist. Rufen Sie dazu xr.isSessionSupported() auf. Anstatt wie zuvor 'immersive-vr' anzufordern, können Sie 'immersive-ar' anfordern.

if (navigator.xr) {
  const supported = await navigator.xr.isSessionSupported('immersive-ar');
  if (supported) {
    xrButton.addEventListener('click', onButtonClicked);
    xrButton.textContent = 'Enter AR';
    xrButton.enabled = supported; // supported is Boolean
  }
}

Wie zuvor wird dadurch die Schaltfläche „AR-Eingabe starten“ aktiviert. Wenn der Nutzer darauf klickt, wird xr.requestSession() aufgerufen und dabei 'immersive-ar' übergeben.

let xrSession = null;
function onButtonClicked() {
  if (!xrSession) {
    navigator.xr.requestSession('immersive-ar')
    .then((session) => {
      xrSession = session;
      xrSession.isImmersive = true;
      xrButton.textContent = 'Exit AR';
      onSessionStarted(xrSession);
    });
  } else {
    xrSession.end();
  }
}

Eine Convenience-Property

Sie haben wahrscheinlich bemerkt, dass ich im letzten Codebeispiel zwei Zeilen hervorgehoben habe. Das Objekt XRSession scheint die Eigenschaft isImmersive zu haben. Dies ist eine Convenience-Property, die ich selbst erstellt habe. Sie ist nicht Teil der Spezifikation. Ich werde sie später verwenden, um zu entscheiden, was ich dem Zuschauer zeigen möchte. Warum ist diese Eigenschaft nicht Teil der API? Weil Ihre Anwendung diese Eigenschaft eventuell unterschiedlich erfassen muss, haben die Spezifikationsautoren beschlossen, die API sauber zu halten.

Sitzung starten

Erinnern Sie sich daran, wie onSessionStarted() in meinem vorherigen Artikel aussah:

function onSessionStarted(xrSession) {
  xrSession.addEventListener('end', onSessionEnded);

  let canvas = document.createElement('canvas');
  gl = canvas.getContext('webgl', { xrCompatible: true });

  xrSession.updateRenderState({
    baseLayer: new XRWebGLLayer(session, gl)
  });

  xrSession.requestReferenceSpace('local-floor')
  .then((refSpace) => {
    xrRefSpace = refSpace;
    xrSession.requestAnimationFrame(onXRFrame);
  });
}

Für das Rendern von Augmented Reality muss ich ein paar Dinge hinzufügen. Den Hintergrund ausschalten Zuerst prüfe ich, ob ich den Hintergrund brauche. Das ist die erste Anlaufstelle, in der ich meine Convenience-Property verwende.

function onSessionStarted(xrSession) {
  xrSession.addEventListener('end', onSessionEnded);

  if (session.isImmersive) {
    removeBackground();
  }

  let canvas = document.createElement('canvas');
  gl = canvas.getContext('webgl', { xrCompatible: true });

  xrSession.updateRenderState({
    baseLayer: new XRWebGLLayer(session, gl)
  });

  refSpaceType = xrSession.isImmersive ? 'local' : 'viewer';
  xrSession.requestReferenceSpace(refSpaceType).then((refSpace) => {
    xrSession.requestAnimationFrame(onXRFrame);
  });

}

Referenzbereiche

In meinen früheren Artikeln habe ich mich nur über Referenzflächen gedämpft. Im Beispiel werden zwei von ihnen verwendet, also korrigieren Sie die Auslassung.

Ein Referenzraum beschreibt die Beziehung zwischen der virtuellen Welt und der physischen Umgebung des Nutzers. Dies geschieht durch:

  • Ursprung für das Koordinatensystem angeben, mit dem Positionen in der virtuellen Welt ausgedrückt werden.
  • Festlegen, ob der Nutzer sich innerhalb dieses Koordinatensystems bewegen soll.
  • Gibt an, ob dieses Koordinatensystem vorab festgelegte Grenzen hat. In den hier gezeigten Beispielen werden keine Koordinatensysteme mit vorab festgelegten Grenzen verwendet.

Für alle Referenzräume drückt die X-Koordinate links und rechts, die Y nach oben und unten und Z die Koordinaten nach vorne und rückwärts aus. Positive Werte sind rechts, oben und rückwärts.

Die von XRFrame.getViewerPose() zurückgegebenen Koordinaten hängen vom angeforderten Referenzraumtyp ab. Mehr darüber, wenn wir zur Frameschleife kommen. Jetzt müssen wir einen Referenztyp auswählen, der für Augmented Reality geeignet ist. Auch hier kommt meine bietende Eigenschaft zum Einsatz.

let refSpaceType
function onSessionStarted(xrSession) {
  xrSession.addEventListener('end', onSessionEnded);

  if (session.isImmersive) {
    removeBackground();
  }

  let canvas = document.createElement('canvas');
  gl = canvas.getContext('webgl', { xrCompatible: true });

  xrSession.updateRenderState({
    baseLayer: new XRWebGLLayer(session, gl)
  });

  refSpaceType = xrSession.isImmersive ? 'local' : 'viewer';
  xrSession.requestReferenceSpace(refSpaceType).then((refSpace) => {
    xrSession.requestAnimationFrame(onXRFrame);
  });
}

Wenn Sie sich das Beispiel für immersive AR-Session angesehen haben, werden Sie feststellen, dass die Szene anfangs statisch und keine Augmented Reality ist. Sie können sich durch Ziehen und Wischen mit dem Finger in der Szene bewegen. Wenn Sie auf „AR starten“ klicken, verschwindet der Hintergrund und Sie können sich bewegen, indem Sie das Gerät bewegen. Die Modi verwenden verschiedene Arten von Referenzbereichen. Der hervorgehobene Text oben zeigt, wie diese Option ausgewählt wird. Sie verwendet die folgenden Referenztypen:

local: Der Ursprung befindet sich zum Zeitpunkt der Sitzungserstellung an der Position des Betrachters. Das bedeutet, dass die Nutzung nicht unbedingt einen klar definierten Mindestpreis hat und die genaue Position des Startorts je nach Plattform variieren kann. Obwohl es keine vorab festgelegten Grenzen für den Raum gibt, wird erwartet, dass Inhalte nur mit Drehung ohne Bewegung dargestellt werden können. Wie Sie an unserem eigenen AR-Beispiel sehen, sind einige Bewegungen innerhalb des Raums möglich.

viewer: Wird am häufigsten für Inline-Inhalte auf der Seite verwendet. Dieser Bereich folgt dem Anzeigegerät. Wenn sie an getViewerPose übergeben wird, stellt sie kein Tracking bereit und meldet daher immer eine Pose am Ursprung, sofern die Anwendung sie nicht mit XRReferenceSpace.getOffsetReferenceSpace() ändert. Im Beispiel wird dies verwendet, um das berührungsbasierte Schwenken der Kamera zu ermöglichen.

Frameschleife ausführen

Das Konzept der VR-Sitzung, die in meinen vorherigen Artikeln beschrieben wurde, ändert sich nichts. Übergeben Sie den Typ des Referenzbereichs an XRFrame.getViewerPose(). XRViewerPose wird für den aktuellen Referenzbereichstyp zurückgegeben. Wenn Sie viewer als Standard verwenden, kann eine Seite eine Vorschau des Inhalts anzeigen, bevor die Nutzereinwilligung für AR oder VR eingeholt wird. Dies verdeutlicht einen wichtigen Punkt: Der Inline-Inhalt verwendet dieselbe Frameschleife wie der immersive Inhalt, wodurch der erforderliche Code reduziert wird.

function onXRFrame(hrTime, xrFrame) {
  let xrSession = xrFrame.session;
  xrSession.requestAnimationFrame(onXRFrame);
  let xrViewerPose = xrFrame.getViewerPose(refSpaceType);
  if (xrViewerPose) {
    // Render based on the pose.
  }
}

Fazit

Diese Artikelreihe behandelt nur die Grundlagen der Implementierung von immersiven Inhalten im Web. In den WebXR Device API-Beispielen der Immersive Web Working Group werden viele weitere Funktionen und Anwendungsfälle vorgestellt. Gerade haben wir einen Artikel zu Treffertests veröffentlicht, in dem eine API zum Erkennen von Oberflächen und Platzieren virtueller Elemente in einer realen Kameraansicht erläutert wird. Weitere Artikel finden Sie in Zukunft im web.dev-Blog.

Foto von David Grandmougin bei Unsplash