Markierungen und Animationen zu einer fotorealistischen 3D-Karte hinzufügen

1. Hinweis

In dieser Anleitung erfahren Sie, wie Sie Ihrer Anwendung 3D-Markierungen hinzufügen und stylen. Außerdem erfahren Sie, wie Sie Ihre Anwendung animieren, indem Sie zu bestimmten Orten fliegen und dort herumschweben.

Diese Anleitung baut auf den Konzepten auf, die im ersten codelab behandelt wurden. Wenn Sie das noch nicht getan haben, sollten Sie dieses Codelab absolvieren, um die für diese Anwendung erforderlichen Grundlagen zu erlernen.

Aufgabe

„Die vollständige Karte mit Markierungen.

Diese App bietet einen Überblick über die wichtigsten Google-Niederlassungen in Europa. Nutzer können ein Büro auswählen, sich hineinzoomen und es erkunden und dann herauszoomen, um zur allgemeinen Ansicht zurückzukehren. Diese Funktionen, die häufig in Reise- und Erkundungsanwendungen zu finden sind, bieten Nutzern ein immersiveres Erlebnis.

In diesem Codelab erstellen Sie eine 3D-Webanwendung, die Folgendes ermöglicht:

  • Die Maps JavaScript API wird dynamisch geladen.
  • Fügen Sie der Karte 3D-Markierungen hinzu.
  • Die Markierungen werden mit SVGs formatiert.
  • Sie können jetzt zu den Markierungen fliegen und sie umkreisen.
  • Die Standorte werden aus dem Code in ein Array abstrahiert.

Lerninhalte

  • Funktionsweise von Markierungen
  • Markierungen stylen
  • So funktioniert die Animation mit den integrierten Funktionen.
  • Kamerapositionen für Posen und Punkte für eine bessere Bildkomposition
  • Hilfreiche Tipps zum Erfassen von Kameraparametern, um Artikel besser in Szene zu setzen.

Vorbereitung

Sie müssen sich mit den hier aufgeführten Elementen vertraut machen, um dieses Codelab abzuschließen. Wenn Sie bereits mit der Google Maps Platform vertraut sind, können Sie mit dem Codelab fortfahren.

Erforderliche Google Maps Platform-Produkte

In diesem Codelab verwenden Sie die folgenden Google Maps Platform-Produkte:

  • Maps JavaScript API

Weitere Anforderungen für dieses Codelab

Für dieses Codelab benötigen Sie die folgenden Konten, Dienste und Tools:

  • Ein Google Cloud-Konto mit aktivierter Abrechnung.
  • Einen Google Maps Platform API-Schlüssel mit aktivierter Maps JavaScript API.
  • Grundkenntnisse in JavaScript, HTML und CSS
  • Einen Texteditor oder eine IDE Ihrer Wahl, um eine Datei zum Ansehen zu speichern und zu bearbeiten.
  • Einen Webbrowser, in dem Sie die Datei während der Arbeit aufrufen können.

2. Einrichten

Google Maps Platform einrichten

Wenn Sie noch kein Google Cloud-Konto und kein Projekt mit aktivierter Abrechnung haben, lesen Sie den Leitfaden Erste Schritte mit der Google Maps Platform, um ein Rechnungskonto und ein Projekt zu erstellen.

  1. Klicken Sie in der Cloud Console auf das Drop-down-Menü „Projekt“ und wählen Sie das Projekt aus, das Sie für dieses Codelab verwenden möchten.

  1. Aktivieren Sie die für dieses Codelab erforderlichen APIs und SDKs der Google Maps Platform im Google Cloud Marketplace. Folgen Sie dazu der Anleitung in diesem Video oder dieser Dokumentation.
  2. Erstellen Sie auf der Seite Anmeldedaten der Cloud Console einen API-Schlüssel. Eine Anleitung dazu findest du in diesem Video oder in dieser Dokumentation. Für alle Anfragen an die Google Maps Platform ist ein API-Schlüssel erforderlich.

3. Einfacher Globus

Bevor Sie mit dem Erstellen der Anwendung beginnen, ist es wichtig, die grundlegende Einrichtung vorzunehmen. Das Ergebnis ist eine „blaue Kugel“ – eine Ansicht der Erde in ihrer einfachsten Form, wie in der Abbildung zu sehen:

„Bild, das den Globus in der ursprünglichen Einrichtung zeigt.

Code für die Startseite hinzufügen

Wenn Sie der Website den Globus hinzufügen möchten, müssen Sie Ihrer Seite den folgenden Code hinzufügen. Dadurch wird ein Bereich für den Loader der Maps JavaScript API und eine Init-Funktion hinzugefügt, mit der das 3D-Kartenelement auf der Seite erstellt wird, in der Sie den Code für die Markierungen einfügen.

Fügen Sie der Seite unbedingt Ihren eigenen Schlüssel hinzu, den Sie im Abschnitt Einrichtung erstellt haben. Andernfalls kann das 3D‑Element nicht initialisiert werden.

<!DOCTYPE html>
<html>
   <head>
       <title>Step 1 - Simple Globe</title>
       <style>
           body {
               height: 100vh;
               margin: 0;
           }
       </style>
   </head>

   <body>
       <script>
           (g => { var h, a, k, p = "The Google Maps JavaScript API", c = "google", l = "importLibrary", q = "__ib__", m = document, b = window; b = b[c] || (b[c] = {}); var d = b.maps || (b.maps = {}), r = new Set, e = new URLSearchParams, u = () => h || (h = new Promise(async (f, n) => { await (a = m.createElement("script")); e.set("libraries", [...r] + ""); for (k in g) e.set(k.replace(/[A-Z]/g, t => "_" + t[0].toLowerCase()), g[k]); e.set("callback", c + ".maps." + q); a.src = `https://maps.${c}apis.com/maps/api/js?` + e; d[q] = f; a.onerror = () => h = n(Error(p + " could not load.")); a.nonce = m.querySelector("script[nonce]")?.nonce || ""; m.head.append(a) })); d[l] ? console.warn(p + " only loads once. Ignoring:", g) : d[l] = (f, ...n) => r.add(f) && u().then(() => d[l](f, ...n)) })({
               key: "<INSERT API KEY>",
               v: "alpha",
               // Use the 'v' parameter to indicate the version to use (weekly, beta, alpha, etc.).
               // Add other bootstrap parameters as needed, using camel case.
           });
       </script>
       <script>
           let map3D = null;

           async function init() {
               const { Map3DElement, MapMode } = await google.maps.importLibrary("maps3d");

               map3D = new Map3DElement({
                   mode: MapMode.HYBRID,
               });

               document.body.append(map3D);
           }
           init();
       </script>
   </body>
</html>

Jetzt können Sie mit dem Einrichten des gewünschten Aufnahmebereichs beginnen. Das tun Sie im nächsten Schritt.

4. Ersten Frame einrahmen

Nachdem Sie eine Karte mit einer Globusansicht erstellt haben, müssen Sie als Nächstes den richtigen Startort festlegen. So erhalten Ihre Nutzer einen sofortigen Überblick darüber, wo sie sich gerade befinden.

In diesem Beispiel liegt der Schwerpunkt auf den Google-Niederlassungen in Europa. Sie können diesen Ansatz jedoch auf jeden Ort weltweit anwenden – von einem ganzen Land bis hin zu einem einzelnen Stadtblock. Dank der Geschwindigkeit und Flexibilität des Produkts können Sie Ihre Anwendung mit minimalen Codeänderungen von global auf lokal skalieren.

Sie beginnen mit dem ersten Bildausschnitt, damit die 3D‑Karte so aussieht:

„Der Globus ist auf Europa ausgerichtet.

Kamera auf Europa ausrichten

Damit das Display wie dargestellt angezeigt wird, müssen Sie es richtig positionieren, als würden Sie eine Kamera im Raum positionieren, die auf den Standort hinabblickt.

Dazu können Sie über das Kartenkontrollelement eine Reihe von Parametern festlegen, um die Kameradetails festzulegen. Im Diagramm sehen Sie, wie die Parameter in der „realen“ Welt interagieren. Dazu gehören der Mittelpunkt, auf den die Kamera gerichtet ist, und die Entfernung von der Stelle, auf die Sie schauen (der Bereich). Außerdem müssen Sie die Neigung der Kameraperspektive festlegen, da Sie sonst direkt auf die Erde blicken.

„Ein Bild mit den Kameraparametern.

Die letzte Einstellung, heading, bestimmt die Richtung der Kamera. Sie wird als Abweichung von „geradeaus nach Norden“ gemessen. Diese Werte werden als Objekt auf das 3D‑Kartenelement angewendet, um die erste Darstellung einzurichten. Das sehen Sie im Code mit dem aktualisierten Konstruktor für 3D-Elemente.

map3D = new Map3DElement({
    center: { lat: 46.717, lng: 7.075, altitude: 2175.130 },
    range: 5814650,
    tilt: 33,
    heading: 4.36,
    mode: MapMode.HYBRID
});

Kameraparameter erfassen

Für die Aufnahme einer Ansicht in einer 3D-Karte ist eine präzise Kamerapositionierung erforderlich, was allein durch Code schwierig zu erreichen ist. Mit diesem hilfreichen Hack können Sie diesen Vorgang vereinfachen: Fügen Sie Ihrer Seite eine Funktion hinzu, die die Kameraparameter erfasst, wenn Sie auf die gewünschte Ansicht klicken. Die Parameter werden in der Konsole ausgegeben und können in die Kameraeinstellungen des Objekts kopiert werden.

Den Code, den Sie später verwenden möchten, finden Sie im Beispiel dieser Seite. Er ist nicht im Beispiel der nachfolgenden Seiten enthalten, da er für das Codelab nicht erforderlich ist. Sie sollten ihn sich aber merken, wenn Sie durch eine bessere Kamerapositionierung ansprechendere Demos erstellen möchten.

map3D.addEventListener('gmp-click', (event) => {
   console.log("camera: { center: { lat: " + map3D.center.lat + ", lng : " + map3D.center.lng + ", altitude: " + map3D.center.altitude + " }, range: " + map3D.range + ", tilt: " + map3D.tilt + " ,heading: " + map3D.heading + ", }");
   console.log("{ lat: " + event.position.lat + ", lng : " + event.position.lng + ", altitude: " + event.position.altitude + " }");
   // Stop the camera animation when the map is clicked.
   map3D.stopCameraAnimation();
});

Beachten Sie die Verwendung der Funktion stopCameraAnimation. Wenn die Seite herangezoomt oder gedreht wird, ist es hilfreich, die Animation anhalten zu können, damit Sie den Standort in diesem Moment auf dem Display erfassen können. Mit diesem Code-Snippet ist das möglich. Weitere Informationen finden Sie in der Dokumentation zu stopCameraAnimation.

Beispielausgabe des Klicks in der Console

camera: { center: { lat: 51.39870122020001, lng : -0.08573187165829443, altitude: 51.66845062662254 }, range: 716.4743880553578, tilt: 50.5766672986501 ,heading: -1.048260134782318, }
step2.html:40 { lat: 51.398158351120536, lng : -0.08561139388593597, altitude: 51.860469133677626 }

Der Kameratext kann als JSON-Eingabe in einer Vielzahl von Objekten in 3D-Karten verwendet werden. Die zweite Ausgabe ist der tatsächliche Punkt, an dem der Klick erfolgt ist. Das ist auch nützlich, um Punkte zu erstellen oder Markierungen zu positionieren.

Nachdem Sie die Seite richtig eingerahmt haben, können Sie Markierungen hinzufügen. Fahren Sie mit dem nächsten Schritt fort, um zu erfahren, wie das geht.

Bereichslösung

Für diesen Schritt wird die fertige Seite als Lösung zur Überprüfung Ihrer Implementierung bereitgestellt. (Achten Sie beim Kopieren darauf, dass Sie Ihren eigenen API-Schlüssel verwenden.)

<!DOCTYPE html>
<html>

<head>
   <title>Step 2 - Europe View</title>
   <style>
       body {
           height: 100vh;
           margin: 0;
       }
   </style>
</head>

<body>
   <script>
       (g => { var h, a, k, p = "The Google Maps JavaScript API", c = "google", l = "importLibrary", q = "__ib__", m = document, b = window; b = b[c] || (b[c] = {}); var d = b.maps || (b.maps = {}), r = new Set, e = new URLSearchParams, u = () => h || (h = new Promise(async (f, n) => { await (a = m.createElement("script")); e.set("libraries", [...r] + ""); for (k in g) e.set(k.replace(/[A-Z]/g, t => "_" + t[0].toLowerCase()), g[k]); e.set("callback", c + ".maps." + q); a.src = `https://maps.${c}apis.com/maps/api/js?` + e; d[q] = f; a.onerror = () => h = n(Error(p + " could not load.")); a.nonce = m.querySelector("script[nonce]")?.nonce || ""; m.head.append(a) })); d[l] ? console.warn(p + " only loads once. Ignoring:", g) : d[l] = (f, ...n) => r.add(f) && u().then(() => d[l](f, ...n)) })({
           key: "<INSERT API KEY>",
           v: "alpha",
           // Use the 'v' parameter to indicate the version to use (weekly, beta, alpha, etc.).
           // Add other bootstrap parameters as needed, using camel case.
       });
   </script>
<script>
       let map3D = null;

       async function init() {
           const { Map3DElement, MapMode } = await google.maps.importLibrary("maps3d");

           map3D = new Map3DElement({
                center: { lat: 46.717, lng: 7.075, altitude: 2175.130 },
                range: 5814650,
                tilt: 33,
                heading: 4.36,
                mode: MapMode.HYBRID,
            });

           map3D.addEventListener('gmp-click', (event) => {
               console.log("camera: { center: { lat: " + map3D.center.lat + ", lng : " + map3D.center.lng + ", altitude: " + map3D.center.altitude + " }, range: " + map3D.range + ", tilt: " + map3D.tilt + " ,heading: " + map3D.heading + ", }");
               console.log("{ lat: " + event.position.lat + ", lng : " + event.position.lng + ", altitude: " + event.position.altitude + " }");

               map3D.stopCameraAnimation();
           });

           document.body.append(map3D);
       }
       init();
   </script>

</body>

</html>

5. Einfache Markierung

In diesem Abschnitt erfahren Sie, wie Sie Ihre erste Markierung hinzufügen. Zuerst erfahren Sie allgemeine Informationen zu Markierungen.

Für 3D-Karten können zwei verschiedene Markierungsklassen erstellt werden: die Klasse Marker3DElement und die Klasse Marker3DInteractiveElement. Welche Sie verwenden, hängt davon ab, ob Sie Klicks auf Markierungen aktivieren möchten. Abgesehen davon sind sie im Wesentlichen identisch. Sie erstellen also zuerst ein Marker3DElement und „aktualisieren“ es in den nächsten Schritten auf das Marker3DInteractiveElement.

Die vollständige Lösung für diesen Schritt finden Sie hier:

„Ein Globus mit einer Markierung, die den vollständigen Schritt zeigt.

Markierungen etwas höher anbringen

Markierungen sind wie alle anderen Elemente auf der 3D‑Karte dreidimensional. Das bedeutet, dass der Ort eine Höhe (Höhenlage) haben kann und diese Höhe als Position relativ zum Meeresspiegel, zum Boden, zum Raster oder als an den Boden angedockte Höhe festgelegt werden kann, wobei die Höhenlage ignoriert wird. Weitere Informationen finden Sie in der Dokumentation für AltitudeMode im Abschnitt „Höhenkonstanten“.

Mit dem Wert extruded können Sie festlegen, ob die Markierung extrudiert ist oder nicht. Damit wird festgelegt, ob eine kleine Linie zum Boden hin gezeichnet wird, um die tatsächliche Position in Bezug auf die Höhe anzuzeigen. Das ist nützlich, um Punkte auf dem Boden zu markieren. Ein Beispiel hierfür ist der Standort von Google UK. Beide sind extrudiert und ihre Position ist auf eine absolute Höhe festgelegt. Die erste bei 75 Metern und die zweite bei 125 Metern.

Markierung bei 75 Metern

Markierung bei 125 Metern

Höhe: 75 Meter

Höhe: 125 Meter

Markierungen bei Bedeckung und Kollision aus- oder einblenden

In unserer Demo ist das zwar nicht wichtig, da die Positionen ziemlich weit auseinander liegen, aber bei Markierungen, die sich überschneiden oder hinter Gebäuden verschwinden, können Sie mit den Werten collisionBehavior oder drawsWhenOccluded festlegen, was mit ihnen passiert.

Für das Kollisionsverhalten stehen Ihnen die folgenden Optionen zur Verfügung:

  • REQUIRED: Das ist die Standardeinstellung, bei der die Markierung immer angezeigt wird, auch bei Konflikten mit anderen Markierungen.
  • OPTIONAL_AND_HIDES_LOWER_PRIORITY: Die Markierung wird nur dann angezeigt, wenn sie sich nicht mit anderen Markierungen überschneidet. Wenn sich zwei Markierungen dieses Typs überschneiden, wird die Markierung mit dem höheren zIndex angezeigt. Falls beide denselben zIndex haben, wird die Markierung mit der niedrigeren vertikalen Bildschirmposition angezeigt.
  • REQUIRED_AND_HIDES_OPTIONAL: Die Markierung wird unabhängig von Konflikten mit anderen Markierungen immer angezeigt. OPTIONAL_AND_HIDES_LOWER_PRIORITY-Markierungen oder Labels, die sich mit ihr überschneiden würden, werden ausgeblendet.

Die Unterschiede bei der Darstellung der Markierungen je nach definiertem Kollisionsverhalten sind in den Bildern zu sehen. Wenn Sie REQUIRED festlegen, werden alle Markierungen angezeigt. Wenn Sie jedoch REQUIRED_AND_HIDES_OPTIONAL verwenden, werden in diesem Fall die Markierungen unten auf dem Bildschirm angezeigt. Sie können mit dem Z-Index spielen, um andere Markierungen übereinander anzuzeigen.

Alle Markierungen werden als erforderlich angezeigt

Markierungen, die andere Markierungen verdecken

ERFORDERLICH

REQUIRED_AND_HIDES_OPTIONAL

Bei Bedeckungen können Sie festlegen, ob Markierungen hinter Gebäuden gezeichnet werden sollen oder nicht. Das ist in der folgenden Abbildung dargestellt. Wenn drawsWhenOccluded auf „wahr“ gesetzt ist, werden die Markierungen leicht abgedunkelt, wenn sie hinter Gebäuden gezeichnet werden. Wenn „falsch“ festgelegt ist, werden die Markierungen ausgeblendet, wenn sie sich hinter einem Gebäude befinden. Weitere Informationen finden Sie in der folgenden Tabelle:

Bild einer Karte, auf der verdeckten Markierungen ausgeblendet sind

Bild einer Karte mit verdeckten Markierungen

drawsWhenOccluded : false

drawsWhenOccluded : true

Wie bereits erwähnt, werden Markierungen, die durch eine Kollision verdeckt sind, ausgegraut angezeigt, wenn das Zeichnen von verdeckten Markierungen zulässig ist. Auf dem Bild sehen Sie, dass einige Markierungen von Gebäuden und andere von anderen Markierungen verdeckt werden.

„Ein Bild mit mehreren Markierungen und der Wirkung von Bedeckungen.

Weitere Informationen finden Sie im Beispiel für das Kollisionsverhalten in einer 2D-Karte.

Canvas löschen

Jetzt ist es an der Zeit, Ihre erste Markierung zu erstellen. Damit sich der Nutzer auf die Markierungen konzentrieren kann, können Sie die Standardlabels in der 3D‑Karte deaktivieren.

Legen Sie den mode-Wert des 3D‑Kartenelements auf SATELLITE fest.

Weitere Informationen finden Sie unter Modus.

map3D = new Map3DElement({
    center: { lat: 46.717, lng: 7.075, altitude: 2175.130 },
    range: 5814650,
    tilt: 33,
    heading: 4.36,
    mode: MapMode.SATELLITE
});

Das Ergebnis ist die folgende 3D-Karte:

„Bild von Europa ohne Grenzen und Text.

Erste Markierung hinzufügen

Nachdem Sie den Canvas gelöscht haben, können Sie die erste Markierung hinzufügen. Zu den wichtigsten Parametern gehören „Position“ und „Label“.

Wenn Sie eine Markierung hinzufügen möchten, legen Sie ihre Position fest. Sie können auch ein Label hinzufügen, das über der Markierung angezeigt wird, und andere Elemente, wie in der Dokumentation zu Marker3DElement beschrieben.

Fügen Sie zum Hinzufügen der Markierung den folgenden Code nach der Zeile ein, mit der die Standardlabels ausgeblendet werden:

const marker = new Marker3DElement({
   position: { lat: 51.5332, lng: -0.1260, altitude: 75 },
   label: 'Google UK',
   altitudeMode: 'ABSOLUTE',
   extruded: true,
});

map3D.append(marker);

Nachdem Sie die Markierung erstellt haben, fügen Sie sie der 3D‑Karte mit der Methode „append“ hinzu. Denken Sie daran, dass Markierungen als Array von untergeordneten Elementen in der 3D‑Karte gespeichert werden. Wenn Sie eine Markierung ändern möchten, müssen Sie über dieses Array darauf zugreifen.

Achten Sie darauf, dass die Marker3DElement aus der Maps JavaScript API geladen wird. Fügen Sie sie beim Laden der API der Liste der Bibliotheken hinzu.

const { Map3DElement, MapMode, Marker3DElement } = await google.maps.importLibrary("maps3d");

Wenn die Seite jetzt geladen wird, ist ganz Europa mit einer Markierung über dem Büro in London zu sehen. Wie in der Animation zu sehen, können Sie manuell heranzoomen, um die Markierung über dem erstellten Standort zu sehen.

„Animation, die das manuelle Heranzoomen auf Google UK zeigt.

Nachdem Sie Ihre erste Markierung geladen haben, können Sie sie im nächsten Schritt ansprechender gestalten.

Bereichslösung

Für diesen Schritt wird die fertige Seite als Lösung zur Überprüfung Ihrer Implementierung bereitgestellt. (Achten Sie beim Kopieren darauf, dass Sie Ihren eigenen API-Schlüssel verwenden.)

<!DOCTYPE html>
<html>

<head>
   <title>Step 3 - Simple Marker</title>
   <style>
       body {
           height: 100vh;
           margin: 0;
       }
   </style>
</head>

<body>
   <script>
       (g => { var h, a, k, p = "The Google Maps JavaScript API", c = "google", l = "importLibrary", q = "__ib__", m = document, b = window; b = b[c] || (b[c] = {}); var d = b.maps || (b.maps = {}), r = new Set, e = new URLSearchParams, u = () => h || (h = new Promise(async (f, n) => { await (a = m.createElement("script")); e.set("libraries", [...r] + ""); for (k in g) e.set(k.replace(/[A-Z]/g, t => "_" + t[0].toLowerCase()), g[k]); e.set("callback", c + ".maps." + q); a.src = `https://maps.${c}apis.com/maps/api/js?` + e; d[q] = f; a.onerror = () => h = n(Error(p + " could not load.")); a.nonce = m.querySelector("script[nonce]")?.nonce || ""; m.head.append(a) })); d[l] ? console.warn(p + " only loads once. Ignoring:", g) : d[l] = (f, ...n) => r.add(f) && u().then(() => d[l](f, ...n)) })({
           key: "<INSERT API KEY>",
           v: "alpha",
           // Use the 'v' parameter to indicate the version to use (weekly, beta, alpha, etc.).
           // Add other bootstrap parameters as needed, using camel case.
       });
   </script>
   <script>
       let map3D = null;

       async function init() {
            const { Map3DElement, MapMode, Marker3DElement } = await google.maps.importLibrary("maps3d");

            map3D = new Map3DElement({
                center: { lat: 46.717, lng: 7.075, altitude: 2175.130 },
                range: 5814650,
                tilt: 33,
                heading: 4.36,
                mode: MapMode.SATELLITE,
            });

           const marker = new Marker3DElement({
               position: { lat: 51.5332, lng: -0.1260, altitude: 75 },
               label: 'Google UK',
               altitudeMode: 'ABSOLUTE',
               extruded: true,
           });
           map3D.append(marker);

           document.body.append(map3D);
       }
       init();
   </script>
</body>

</html>

6. SVG-Markierung

In diesem Schritt machen Sie die Markierung schöner, indem Sie ihr ein Flag hinzufügen, das das Land repräsentiert, in dem sie sich befindet. Sehen wir uns an, wie das geht. Dazu müssen Sie sich mit dem PinElement vertraut machen.

Am Ende sollte es so aussehen:

„Bild mit einer Markierung mit der Flagge des Vereinigten Königreichs“

Einfache Anpassung mit PinElement

Das PinElement ist eines der Elemente, das für Markierungen in der JavaScript API verwendet wird, unabhängig davon, ob es sich um 2D- oder 3D-Karten handelt. Während Sie dem Map3DElement ein Marker3DElement hinzufügen , fügen Sie dem Marker3DElement ein PinElement als untergeordnetes Element hinzu.

Mit dem PinElement können Sie die normale Markierung auf grundlegender Ebene ändern, um die Rahmenfarbe, die Farbe des inneren Punkts (oder Glyphens) und die Hintergrundfarbe festzulegen. Sie sehen sie auf dem Bild mit einer 2D-Markierung.

„Bild mit Optionen zur Anpassung von Markierungen“

Sie können die Größe einer Markierung auch über das Element festlegen, indem Sie den Skalierungswert festlegen. Ein Wert größer als 1 bedeutet, dass die Markierung größer als normal ist, ein Wert kleiner als 1, dass sie im Verhältnis kleiner ist.

Sie können das Glyph auch durch eine Bild- oder SVG-Datei ersetzen, wenn Sie ein benutzerdefiniertes Aussehen wünschen, aber dennoch das Standard-PinElement für Kartenmarkierungen beibehalten möchten.

Mehr als nur Pins

In diesem Schritt aktualisieren Sie das Standardsymbol PinElement mit einer SVG-Flagge und verschiedenen Farben. Sie können das Aussehen einer Markierung aber auch komplett ändern, sodass sie nicht einmal wie eine Markierung auf der Karte aussieht. Innerhalb des Markierungselements können Sie auch neue Grafiken mithilfe von Vorlagen wie HTMLImageElement und SVGElement einfügen. Weitere Informationen dazu finden Sie in der Dokumentation zu Marker3DElement-Slots.

In den folgenden Beispielen sehen Sie, was alles möglich ist. Dabei werden verschiedene Techniken zum Stylen von Markierungen verwendet.

Bild, das die grundlegende Anpassung von Markierungen zeigt

Bild, das die benutzerdefinierte Anpassung komplexer Markierungen zeigt

Markierungen mit einfacher Anpassung über PinElement, siehe Beispiele.

Markierungen mit komplexer Anpassung über Vorlagen, SVG und Bilder, siehe Beispiele.

PinElement hinzufügen

Wenn Sie das Aussehen der Markierung ändern möchten, müssen Sie zuerst prüfen, ob der Seite die PinElement-Bibliothek hinzugefügt wurde. Fügen Sie dazu nach dem Importieren der maps3d-Bibliothek die folgende Codezeile hinzu:

const { Map3DElement, MapMode, Marker3DElement } = await google.maps.importLibrary("maps3d");
const { PinElement } = await google.maps.importLibrary('marker');

Jetzt, da das Element geladen ist, kann auf das PinElement verwiesen und es erstellt werden. Sehen Sie sich den Code an, fügen Sie ihn zwischen die Stelle ein, an der die Markierung erstellt wird, und hängen Sie die Markierung an die 3D-Karte an.

const marker = new Marker3DElement({
   position: { lat: 51.5332, lng: -0.1260, altitude: 75 },
   label: 'Google UK',
   altitudeMode: 'ABSOLUTE',
   extruded: true,
});

const base = document.location.href.substr(0, document.location.href.lastIndexOf("/"));

const markerPin = new PinElement({
   "background": 'white',
   "glyph": new URL(base + '/images/gb.svg'),
   "scale": 1.0,
});
marker.append(markerPin);

map3D.append(marker);

Da Sie nicht nur eine einfache Markierung laden, müssen Sie nicht nur das PinElement mit der zugehörigen Hintergrundfarbe und Skalierung einrichten.

Zuerst muss eine Referenz auf ein SVG-Bild für das Flaggensymbol erstellt werden, in diesem Fall ein Union Jack. Sie können sie beispielsweise in dieser Sammlung unter https://flagicons.lipis.dev/ herunterladen.

Nachdem Sie das Symbol haben, können Sie es an einem Ort platzieren, an dem es von der Website gefunden werden kann. In diesem Fall können Sie den Speicherort des Bildes entweder hart codieren oder den aktuellen Speicherort der Website als Chunk des Verzeichnisses verwenden, wie hier mit der Basisvariablen gezeigt. Sie können dies dann mit dem Speicherort auf dem Server mit der richtigen Flagge verknüpfen, hier unter '/images/gb.svg'.

Dadurch wird ein Pin-Element erstellt, das so aussieht:

„Markierung mit dem Union Jack-Symbol.

Wenn Sie die Markierung und den Code an der richtigen Stelle platziert haben, sollte Ihre 3D-Karte so aussehen:

„Ich zoome auf die neue Markierung heran.

Jetzt können wir die Markierung auch anklickbar machen, um Interaktivität hinzuzufügen. Das geschieht im nächsten Schritt.

Bereichslösung

Für diesen Schritt wird die fertige Seite als Lösung zur Überprüfung Ihrer Implementierung bereitgestellt. (Achten Sie beim Kopieren darauf, dass Sie Ihren eigenen API-Schlüssel verwenden.)

Denken Sie auch daran, die SVG-Datei (oder eine PNG-Datei Ihrer Wahl) für die Flagge herunterzuladen und in einem Verzeichnis zu speichern, das von Ihrer Seite aus gefunden werden kann. Hier wird sie im Ordner „Bilder“ gespeichert.

<!DOCTYPE html>
<html>

<head>
   <title>Step 4 - SVG Marker</title>
   <style>
       body {
           height: 100vh;
           margin: 0;
       }
   </style>
</head>

<body>
   <script>
       (g => { var h, a, k, p = "The Google Maps JavaScript API", c = "google", l = "importLibrary", q = "__ib__", m = document, b = window; b = b[c] || (b[c] = {}); var d = b.maps || (b.maps = {}), r = new Set, e = new URLSearchParams, u = () => h || (h = new Promise(async (f, n) => { await (a = m.createElement("script")); e.set("libraries", [...r] + ""); for (k in g) e.set(k.replace(/[A-Z]/g, t => "_" + t[0].toLowerCase()), g[k]); e.set("callback", c + ".maps." + q); a.src = `https://maps.${c}apis.com/maps/api/js?` + e; d[q] = f; a.onerror = () => h = n(Error(p + " could not load.")); a.nonce = m.querySelector("script[nonce]")?.nonce || ""; m.head.append(a) })); d[l] ? console.warn(p + " only loads once. Ignoring:", g) : d[l] = (f, ...n) => r.add(f) && u().then(() => d[l](f, ...n)) })({
           key: "<INSERT API KEY>",
           v: "alpha",
           // Use the 'v' parameter to indicate the version to use (weekly, beta, alpha, etc.).
           // Add other bootstrap parameters as needed, using camel case.
       });
   </script>
   <script>
       let map3D = null;

       async function init() {
           const { Map3DElement, MapMode, Marker3DElement } = await google.maps.importLibrary("maps3d");
           const { PinElement } = await google.maps.importLibrary('marker');

           map3D = new Map3DElement({
                center: { lat: 46.717, lng: 7.075, altitude: 2175.130 },
                range: 5814650,
                tilt: 33,
                heading: 4.36,
                mode: MapMode.SATELLITE,
           });

           const marker = new Marker3DElement({
               position: { lat: 51.5332, lng: -0.1260, altitude: 75 },
               label: 'Google UK',
               altitudeMode: 'ABSOLUTE',
               extruded: true,
           });

           const base = document.location.href.substr(0, document.location.href.lastIndexOf("/"));

           const markerPin = new PinElement({
               "background": 'white',
               "glyph": new URL(base + '/images/gb.svg'),
               "scale": 1.0,
           });
           marker.append(markerPin);

           map3D.append(marker);

           document.body.append(map3D);
       }
       init();
   </script>
</body>

</html>

7. Interaktive Markierung

Im letzten Schritt wurde der Seite eine Markierung hinzugefügt. Diese hat aber keine weiteren Funktionen, außer dass sie gut aussieht. Sie müssen weiterhin auf die gleiche Weise mit der 3D‑Karte interagieren. Im nächsten Schritt fügen Sie die Möglichkeit hinzu, beim Klicken auf die Markierung etwas damit zu tun, sodass die Markierung auf Nutzerinteraktionen reagieren kann.

Damit diese Funktion hinzugefügt werden kann, müssen Sie das Marker3DElement in ein Marker3DInteractiveElement umwandeln. Am Ende sehen Sie eine ähnliche Seite, auf der aber beim Klicken auf die Markierung jetzt eine Benachrichtigung angezeigt wird. Sie sieht in etwa so aus:

„Bild, das die Antwort zeigt, wenn darauf geklickt wird.

Ändern Sie zuerst die Markierungsklasse.

Wenn Sie einer Markierung Interaktivität hinzufügen möchten, müssen Sie darauf achten, dass die richtige Klasse verwendet wird. Sie benötigen das Marker3DInteractiveElement. Da es sich jedoch um eine Erweiterung von Marker3DElement handelt, müssen Sie nur die neue Klasse laden und den Klassennamen im Konstruktor ändern.

const { Map3DElement, MapMode, Marker3DInteractiveElement } = await google.maps.importLibrary("maps3d");
const { PinElement } = await google.maps.importLibrary('marker');

map3D = new Map3DElement({
    center: { lat: 46.717, lng: 7.075, altitude: 2175.130 },
    range: 5814650,
    tilt: 33,
    heading: 4.36,
    mode: MapMode.SATELLITE,
});

const marker = new Marker3DInteractiveElement({
   position: { lat: 51.5332, lng: -0.1260, altitude: 75 },
   label: 'Google UK',
   altitudeMode: 'ABSOLUTE',
   extruded: true,
});

Zweitens: Fügen Sie der Markierung das Klickereignis hinzu.

Fügen Sie der Markierung als Nächstes ein Klickereignis hinzu, um die Nutzerinteraktion zu verarbeiten und darauf zu reagieren. Im Snippet sehen Sie, dass das Klickereignis der Markierung hinzugefügt wird. In diesem Fall wird eine Benachrichtigung ausgelöst und der Text wird eingeblendet, der das Label der Markierung enthält. Dieser wird vom Ziel des ausgelösten Ereignisses abgerufen, wodurch wir auf die Label-Property zugreifen können. Fügen Sie Ihrer Anwendung den folgenden Code direkt nach dem Erstellen der Markierung hinzu.

marker.addEventListener('gmp-click', (event) => {
   alert('You clicked on : ' + event.target.label);
   event.stopPropagation();
});

Hinweis: Mit dem Ereignis „stopPropagation“ wird sichergestellt, dass alle anderen Klick-Listener im Stack auf zugrunde liegenden Objekten wie dem Haupt-Canvas der 3D-Karte ausgelöst werden.

Wenn Sie die Anwendung jetzt ausführen, sollten Sie das folgende Ergebnis erhalten:

„Bild, das die Antwort zeigt, wenn darauf geklickt wird.

Da wir jetzt eine Aktion für den Klick auf die Markierung festgelegt haben, können wir der Seite im nächsten Schritt eine Animation hinzufügen.

Bereichslösung

Für diesen Schritt wird die fertige Seite als Lösung zur Überprüfung Ihrer Implementierung bereitgestellt. (Achten Sie beim Kopieren darauf, dass Sie Ihren eigenen API-Schlüssel verwenden.)

<!DOCTYPE html>
<html>

<head>
   <title>Step 5 - Interactive Marker</title>
   <style>
       body {
           height: 100vh;
           margin: 0;
       }
   </style>
</head>

<body>
   <script>
       (g => { var h, a, k, p = "The Google Maps JavaScript API", c = "google", l = "importLibrary", q = "__ib__", m = document, b = window; b = b[c] || (b[c] = {}); var d = b.maps || (b.maps = {}), r = new Set, e = new URLSearchParams, u = () => h || (h = new Promise(async (f, n) => { await (a = m.createElement("script")); e.set("libraries", [...r] + ""); for (k in g) e.set(k.replace(/[A-Z]/g, t => "_" + t[0].toLowerCase()), g[k]); e.set("callback", c + ".maps." + q); a.src = `https://maps.${c}apis.com/maps/api/js?` + e; d[q] = f; a.onerror = () => h = n(Error(p + " could not load.")); a.nonce = m.querySelector("script[nonce]")?.nonce || ""; m.head.append(a) })); d[l] ? console.warn(p + " only loads once. Ignoring:", g) : d[l] = (f, ...n) => r.add(f) && u().then(() => d[l](f, ...n)) })({
           key: "<INSERT API KEY>",
           v: "alpha",
           // Use the 'v' parameter to indicate the version to use (weekly, beta, alpha, etc.).
           // Add other bootstrap parameters as needed, using camel case.
       });
   </script>
   <script>
       let map3D = null;

       async function init() {
           const { Map3DElement, MapMode, Marker3DInteractiveElement } = await google.maps.importLibrary("maps3d");
           const { PinElement } = await google.maps.importLibrary('marker');

           map3D = new Map3DElement({
                center: { lat: 46.717, lng: 7.075, altitude: 2175.130 },
                range: 5814650,
                tilt: 33,
                heading: 4.36,
                mode: MapMode.SATELLITE,
           });

           const marker = new Marker3DInteractiveElement({
               position: { lat: 51.5332, lng: -0.1260, altitude: 75 },
               label: 'Google UK',
               altitudeMode: 'ABSOLUTE',
               extruded: true,
           });

           marker.addEventListener('gmp-click', (event) => {
               alert('You clicked on : ' + event.target.label);
               event.stopPropagation();
           });

           const base = document.location.href.substr(0, document.location.href.lastIndexOf("/"));

           const markerPin = new PinElement({
               "background": 'white',
               "glyph": new URL(base + '/images/gb.svg'),
               "scale": 1.0,
           });
           marker.append(markerPin);

           map3D.append(marker);

           document.body.append(map3D);
       }
       init();
   </script>
</body>

</html>

8. Anfliegen

In diesem Schritt klicken Sie auf die Markierung, um eine Animation hinzuzufügen, mit der Sie zum Standort springen. Hier können Sie sich das ansehen.

„Animation, die eine angeklickte Markierung und den Wechsel zum Standort zeigt.

Mit „flyCameraTo“ animieren

Um dies auf der Seite einzufügen, verwenden Sie die Methode flyCameraTo von Google Maps 3D. Dabei wird die Kamera zwischen der aktuellen Kameraposition und der gewünschten Kameraposition animiert, wobei zwischen den beiden Positionen interpoliert und der Flug in Google Maps 3D animiert wird.

Wenn Sie flyCameraTo verwenden, müssen Sie die FlyToAnimationOptions angeben. Diese hat zwei Properties: endCamera, die Position, auf die die Kamera am Ende der Animation zeigen soll, und durationMillis, die Dauer der Überblendung in Millisekunden.

Im Beispiel ist die Kamera auf das Gebäude ausgerichtet, das die Markierungsposition ist, mit einer Neigung von 65 Grad, einer Reichweite von 500 Metern und einer Peilung von 0 Grad nach Norden. Legen Sie für das Animationstiming 12.500 Millisekunden (12,5 Sekunden) fest.

Ersetzen Sie das aktuelle Benachrichtigungsereignis auf der Seite durch das flyCameraTo-Snippet:

marker.addEventListener('gmp-click', (event) => {
   map3D.flyCameraTo({
       endCamera: {
           center: marker.position,
           tilt: 65,
           range: 500,
           heading: 0,
       },
       durationMillis: 12500,
   });

   event.stopPropagation();
});

Das war's. Jetzt sollten Sie die Seite aktualisieren, auf die Markierung klicken und zu Google UK wechseln können, wie in der Animation gezeigt:

„Animation, die eine angeklickte Markierung und den Wechsel zum Standort zeigt.

In diesem Schritt haben Sie eine anklickbare Markierung hinzugefügt, über die die Kamera zum Standort der Markierung schwebt. Im nächsten Schritt fügen Sie die Möglichkeit hinzu, die Kamera um den Punkt herum zu schwenken, sodass sie den Standort umkreist.

Bereichslösung

Für diesen Schritt wird die fertige Seite als Lösung zur Überprüfung Ihrer Implementierung bereitgestellt. (Achten Sie beim Kopieren darauf, dass Sie Ihren eigenen API-Schlüssel verwenden.)

<!DOCTYPE html>
<html>

<head>
   <title>Step 6 - Zoom To</title>
   <style>
       body {
           height: 100vh;
           margin: 0;
       }
   </style>
</head>

<body>
   <script>
       (g => { var h, a, k, p = "The Google Maps JavaScript API", c = "google", l = "importLibrary", q = "__ib__", m = document, b = window; b = b[c] || (b[c] = {}); var d = b.maps || (b.maps = {}), r = new Set, e = new URLSearchParams, u = () => h || (h = new Promise(async (f, n) => { await (a = m.createElement("script")); e.set("libraries", [...r] + ""); for (k in g) e.set(k.replace(/[A-Z]/g, t => "_" + t[0].toLowerCase()), g[k]); e.set("callback", c + ".maps." + q); a.src = `https://maps.${c}apis.com/maps/api/js?` + e; d[q] = f; a.onerror = () => h = n(Error(p + " could not load.")); a.nonce = m.querySelector("script[nonce]")?.nonce || ""; m.head.append(a) })); d[l] ? console.warn(p + " only loads once. Ignoring:", g) : d[l] = (f, ...n) => r.add(f) && u().then(() => d[l](f, ...n)) })({
           key: "<INSERT API KEY>",
           v: "alpha",
           // Use the 'v' parameter to indicate the version to use (weekly, beta, alpha, etc.).
           // Add other bootstrap parameters as needed, using camel case.
       });
   </script>
   <script>
       let map3D = null;

       async function init() {
           const { Map3DElement, MapMode, Marker3DInteractiveElement } = await google.maps.importLibrary("maps3d");
           const { PinElement } = await google.maps.importLibrary('marker');

           map3D = new Map3DElement({
                center: { lat: 46.717, lng: 7.075, altitude: 2175.130 },
                range: 5814650,
                tilt: 33,
                heading: 4.36,
                mode: MapMode.SATELLITE,
           });

           const marker = new Marker3DInteractiveElement({
               position: { lat: 51.5332, lng: -0.1260, altitude: 75 },
               label: 'Google UK',
               altitudeMode: 'ABSOLUTE',
               extruded: true,
           });

           marker.addEventListener('gmp-click', (event) => {
               map3D.flyCameraTo({
                   endCamera: {
                       center: marker.position,
                       tilt: 65,
                       range: 500,
                       heading: 0,
                   },
                   durationMillis: 12500,
               });

               event.stopPropagation();
           });

           const base = document.location.href.substr(0, document.location.href.lastIndexOf("/"));

           const markerPin = new PinElement({
               "background": 'white',
               "glyph": new URL(base + '/images/gb.svg'),
               "scale": 1.0,
           });
           marker.append(markerPin);

           map3D.append(marker);

           document.body.append(map3D);
       }
       init();
   </script>
</body>

</html>

9. Umherfliegen

Als letztes Element unserer Animation verwenden wir die Methode flyCameraAround, um einen Orbit um das Gebäude zu animieren. Am Ende haben Sie eine Animation, die zum Gebäude fliegt und dann wie in der Animation gezeigt um das Gebäude herumfliegt. Das ist für ein echtes Beispiel wahrscheinlich etwas zu schnell, aber es ist nützlich, um zu zeigen, wie die Aktion funktioniert, ohne dass sie zu lang ist. Sie können mit den Timings herumspielen, bis Sie einen Wert gefunden haben, der für Sie funktioniert.

„Animation, in der eine Markierung angeklickt und dann zu einem Ort und um einen Ort herum geflogen wird.

Lass uns einen Flug machen!

Die Methode „flyCameraAround“ ähnelt der Funktion flyCameraTo, da sie eine Reihe von Optionen als Eingabe annimmt, die festlegen, um welchen Ort die Kamera schwenken soll, sowie Kameraparameter und die Zeit in Millisekunden, die für den Schwenk benötigt wird. Außerdem können Sie die Anzahl der Wiederholungen angeben, die innerhalb des angegebenen Zeitraums erfolgen können. Alle Optionen finden Sie hier unter FlyAroundAnimationOptions.

Aber warten Sie eine Minute!

In der Animation sehen Sie, wie die Kamera zum Standort fliegt und dann darum herum, wobei die Animationen miteinander verknüpft werden. Dazu verwenden Sie das Ereignis gmp-animationend für 3D-Karten, um sicherzustellen, dass die aktuelle Animation beendet ist, bevor die nächste ausgelöst wird. Diese Animation sollte nur einmal abgespielt werden.

Sehen Sie sich den Code an und fügen Sie ihn nach dem Code ein, der im vorherigen Abschnitt hinzugefügt wurde.

marker.addEventListener('gmp-click', (event) => {
   map3D.flyCameraTo({
       endCamera: {
           center: marker.position,
           tilt: 65,
           range: 500,
           heading: 0,
       },
       durationMillis: 5000,
   });

   map3D.addEventListener('gmp-animationend', () => {
       map3D.flyCameraAround({
           camera: {
               center: marker.position,
               tilt: 65,
               range: 500,
               heading: 0,
           },
           durationMillis: 5000,
           rounds: 1
       });
   }, { once: true });

   event.stopPropagation();
});

Wenn du die Möglichkeit hinzufügst, auf das Ereignis gmp-animationend zu warten, kann das Ereignis flyCameraAround aufgerufen werden. Wenn du den Ausgangspunkt auf denselben setzt, der für die Endkamera der „Zu-Kamera-Fliegen“-Methode verwendet wurde, wird ein flüssiger Übergang erzielt, damit es nicht zu ruckeligen Bewegungen zu einer neuen Position kommt. Auch hier wird mit durationMillis die Dauer der Animation festgelegt. In diesem Fall nimmt die Methode auch eine weitere Option, rounds, an, die auf „1“ festgelegt ist.

Das bedeutet, dass sich die Kamera alle 5 Sekunden einmal um den Punkt dreht. Sie können mit diesen Werten experimentieren, um die für Sie passende Anzahl zu finden.

An diesem Punkt endet die Animation. Da das Ereignis gmp-animationend mit diesem Code jedoch nicht noch einmal ausgelöst werden soll, würde der Orbit unendlich oft wiederholt. Um dies zu vermeiden, muss die Option für den Listener mit der Einstellung once (einmal) auf true (wahr) gesetzt werden. Das Ereignis wird also entfernt, sobald es abgeschlossen ist, wodurch ein endloser Loop verhindert wird.

Nachdem Sie dies hinzugefügt haben, sollten Sie die Lösung ausführen können und die Animation sollte am Ende wie in der Animation gezeigt um die Markierung herumfliegen:

„Animation, die einen Flug um eine Markierung herum zeigt.

In diesem Schritt haben Sie eine Markierung hinzugefügt, auf die geklickt werden kann. Die Kamera fliegt dann zum Markierungsstandort und um ihn herum. In der nächsten Phase fügen wir weitere Punkte hinzu und ermöglichen es, zwischen ihnen zu wechseln.

Bereichslösung

Für diesen Schritt wird die fertige Seite als Lösung zur Überprüfung Ihrer Implementierung bereitgestellt. (Achten Sie beim Kopieren darauf, dass Sie Ihren eigenen API-Schlüssel verwenden.)

<!DOCTYPE html>
<html>

<head>
   <title>Step 7 - Zoom Around</title>
   <style>
       body {
           height: 100vh;
           margin: 0;
       }
   </style>
</head>

<body>
   <script>
       (g => { var h, a, k, p = "The Google Maps JavaScript API", c = "google", l = "importLibrary", q = "__ib__", m = document, b = window; b = b[c] || (b[c] = {}); var d = b.maps || (b.maps = {}), r = new Set, e = new URLSearchParams, u = () => h || (h = new Promise(async (f, n) => { await (a = m.createElement("script")); e.set("libraries", [...r] + ""); for (k in g) e.set(k.replace(/[A-Z]/g, t => "_" + t[0].toLowerCase()), g[k]); e.set("callback", c + ".maps." + q); a.src = `https://maps.${c}apis.com/maps/api/js?` + e; d[q] = f; a.onerror = () => h = n(Error(p + " could not load.")); a.nonce = m.querySelector("script[nonce]")?.nonce || ""; m.head.append(a) })); d[l] ? console.warn(p + " only loads once. Ignoring:", g) : d[l] = (f, ...n) => r.add(f) && u().then(() => d[l](f, ...n)) })({
           key: "<INSERT API KEY>",
           v: "alpha",
           // Use the 'v' parameter to indicate the version to use (weekly, beta, alpha, etc.).
           // Add other bootstrap parameters as needed, using camel case.
       });
   </script>
   <script>
       let map3D = null;

       const europeCamera = {
           center: { lat: 46.717, lng: 7.075, altitude: 2175.130 },
           range: 5814650,
           tilt: 33,
           heading: 4.36,
       };

       async function init() {
           const { Map3DElement, MapMode, Marker3DInteractiveElement } = await google.maps.importLibrary("maps3d");
           const { PinElement } = await google.maps.importLibrary('marker');

           map3D = new Map3DElement({
               ...europeCamera,
               mode: MapMode.SATELLITE,
           });

           const marker = new Marker3DInteractiveElement({
               position: { lat: 51.5332, lng: -0.1260, altitude: 75 },
               label: 'Google UK',
               altitudeMode: 'ABSOLUTE',
               extruded: true,
           });

           marker.addEventListener('gmp-click', (event) => {
               map3D.flyCameraTo({
                   endCamera: {
                       center: marker.position,
                       tilt: 65,
                       range: 500,
                       heading: 0,
                   },
                   durationMillis: 5000,
               });

               map3D.addEventListener('gmp-animationend', () => {
                   map3D.flyCameraAround({
                       camera: {
                           center: marker.position,
                           tilt: 65,
                           range: 500,
                           heading: 0,
                       },
                       durationMillis: 5000,
                       rounds: 1
                   });
               }, { once: true });

               event.stopPropagation();
           });

           const base = document.location.href.substr(0, document.location.href.lastIndexOf("/"));

           const markerPin = new PinElement({
               "background": 'white',
               "glyph": new URL(base + '/images/gb.svg'),
               "scale": 1.0,
           });
           marker.append(markerPin);

           map3D.append(marker);

           document.body.append(map3D);
       }
       init();
   </script>
</body>

</html>

10. Paris!

London ist zwar eine tolle Stadt, aber auf der Seite wirkt sie ein wenig einsam. Fügen wir also einige neue Standorte hinzu, beginnend mit Paris. Dazu kann ein Array verwendet werden, um alle standortspezifischen Details zu speichern und dann als Eingabe für die Funktionen und Variablen zu verwenden, die die Parameter für die Markierungsanzeige und die Kamerastandorte festlegen. Dieser kann sich, wie bereits erwähnt, vom Standort des Markierungspunkts unterscheiden, um beispielsweise eine bessere Kameraaufnahme eines Gebäudes zu ermöglichen.

„Animation, die einen Klick und den Flug zu und um Google Frankreich zeigt.

Standort-Array

Damit Sie nicht alle Details zu einem bestimmten Ort wie Kamera, Markierungspunkt und Anzeigeoptionen hart codieren müssen, können Sie ein kleines Array von JSON-Objekten verwenden, um diese Daten zu speichern. Dieser kann dann angewendet werden, wenn die Markierungen erstellt und in der Anwendung verwendet werden. In diesem Beispiel im Code-Snippet wird eine Variable namens officeLocations erstellt, um das Array zu speichern.

Fügen Sie den folgenden Code direkt vor der Funktion „init“ ein. Beachten Sie auch, dass die Variable „base“ außerhalb der Funktion „init“ verschoben wurde, damit sie auf alle Standorte angewendet werden kann.

const base = document.location.href.substr(0, document.location.href.lastIndexOf("/"));

const europeCamera = {
   center: { lat: 46.717, lng: 7.075, altitude: 2175.130 },
   range: 5814650,
   tilt: 33,
   heading: 4.36,
};

const officeLocations = [
   {
       "name": "Google France",
       "camera": {
           "center": { lat: 48.877276, lng: 2.329978, altitude: 48 },
           "range": 178,
           "tilt": 57.48,
           "heading": -17,
       },
       "point": { lat: 48.8775183, lng: 2.3299791, altitude: 60 },
       "pin": {
           "background": 'white',
           "glyph": new URL(base + '/images/fr.svg'),
           "scale": 1.0,
       },
   },
   {
       "name": "Google UK",
       "camera": {
           "center": { lat: 51.5332, lng: -0.1260, altitude: 38.8 },
           "range": 500,
           "tilt": 56.21672368296945,
           "heading": -31.15763027564165,
       },
       "point": { lat: 51.5332, lng: -0.1260, altitude: 75 },
       "pin": {
           "background": 'white',
           "glyph": new URL(base + '/images/gb.svg'),
           "scale": 1.0,
       },
   }]
       const base = document.location.href.substr(0, document.location.href.lastIndexOf("/"));

Jedes Büro hat die folgenden Eigenschaften:

  • name :Der Name des Standorts.
  • camera :Die erste Ansicht, um sich den Ort anzusehen, zu dem Sie fliegen und den Sie sich ansehen möchten.
  • point :Ort, an dem die Markierung platziert werden soll.
  • pin :Farbe und Glypheneigenschaften der Markierung

Einen anderen Winkel

Sie sehen hier, dass sich für das Vereinigte Königreich der Kameramittelpunkt und der Markierungspunkt (abgesehen von der Höhe) decken, während sich für Frankreich Kamera und Punkt unterscheiden. Das liegt daran, dass sich die Markierung für den Standort in Frankreich an einem anderen Ort als die ursprüngliche Kameraansicht befinden muss. So wird beim Heranzoomen und Umfliegen des Gebäudes ein besserer Überblick als bei Verwendung des Markierungspunkts geboten.

Zurück nach Europa

Wenn Sie mehr Punkte haben, müssen Sie zwischen ihnen wechseln können. Sie könnten ein Drop-down-Menü verwenden, um eine Auswahl zu ermöglichen. In diesem Beispiel fliegt die Kamera jedoch jedes Mal zurück zur europäischen Ansicht, damit der Nutzer einen anderen Standort auswählen kann.

Dazu muss die Anfangsansicht in einer Variablen gespeichert werden, mit der die Kamera auf die gesamte Ansicht von Europa zurückgesetzt werden kann. Fügen Sie in diesem Beispiel eine neue Variable namens europeCamera hinzu, um sie für später zu speichern.

init-Funktion aktualisieren

Als Erstes müssen Sie das europeCamera-Objekt als Eingabe verwenden, wenn Sie das Map3DElement erstellen.

Als Nächstes müssen Sie den Abschnitt zum Erstellen von Markierungen in eine Schleife einfügen, um ihn mit den in den Variablen gespeicherten Parametern zu aktualisieren. Diese sind im angezeigten Code zu sehen:

  • office.point :die Position der Markierung.
  • office.name :Der Name der Niederlassung, der für das Label der Markierung verwendet wird.
  • office.camera :die ursprüngliche Kameraposition.
  • office.pin :Optionen für das PinElement für Anzeigeunterschiede

Vergiss auch nicht, eine SVG-Datei oder ein Bild für die französische Flagge zu besorgen.

async function init() {
   const { Map3DElement, MapMode, Marker3DInteractiveElement } = await google.maps.importLibrary("maps3d");
   const { PinElement } = await google.maps.importLibrary('marker');

   map3D = new Map3DElement({
       ...europeCamera,
       mode: MapMode.SATELLITE,
   });

   officeLocations.forEach(office => {
       const marker = new Marker3DInteractiveElement({
           position: office.point,
           label: office.name,
           altitudeMode: 'ABSOLUTE',
           extruded: true,
       });

       marker.addEventListener('gmp-click', (event) => {
           map3D.flyCameraTo({
               endCamera: office.camera,
               durationMillis: 5000,
           });

           map3D.addEventListener('gmp-animationend', () => {
               map3D.flyCameraAround({
                   camera: office.camera,
                   durationMillis: 5000,
                   rounds: 1
               });

               map3D.addEventListener('gmp-animationend', () => {
                   map3D.flyCameraTo({
                       endCamera: europeCamera,
                       durationMillis: 5000,
                   });
               }, { once: true });

           }, { once: true });

           event.stopPropagation();
       });

       const markerPin = new PinElement(office.pin);
       marker.append(markerPin);

       map3D.append(marker);
   });
   document.body.append(map3D);
}

Hinweis: Nach der flyCameraAround-Animation wird eine zweite gmp-animationend-Funktion hinzugefügt, um den Rückflug zur europäischen Ansicht mithilfe der gespeicherten europeCamera-Variablen zu steuern. Wie in der Animation dargestellt:

„Animation, die zwischen und um Büros in Frankreich und im Vereinigten Königreich fliegt.

In dieser Phase wurde die Anwendung um zwei Standorte erweitert und es ist möglich, mithilfe einer Animation und eines Standort-Arrays zwischen ihnen zu schweben. In der nächsten Phase werden dem Array die restlichen Standorte hinzugefügt.

Bereichslösung

Für diesen Schritt wird die fertige Seite als Lösung zur Überprüfung Ihrer Implementierung bereitgestellt. (Achten Sie beim Kopieren darauf, dass Sie Ihren eigenen API-Schlüssel verwenden.)

Denken Sie auch daran, die SVG-Datei (oder PNG-Datei Ihrer Wahl) für die Flagge herunterzuladen und in einem Verzeichnis zu speichern, das von Ihrer Seite aus gefunden werden kann. Hier wird sie im Ordner „Bilder“ gespeichert.

<!DOCTYPE html>
<html>

<head>
   <title>Step 8 - Paris!</title>
   <style>
       body {
           height: 100vh;
           margin: 0;
       }
   </style>
</head>

<body>
   <script>
       (g => { var h, a, k, p = "The Google Maps JavaScript API", c = "google", l = "importLibrary", q = "__ib__", m = document, b = window; b = b[c] || (b[c] = {}); var d = b.maps || (b.maps = {}), r = new Set, e = new URLSearchParams, u = () => h || (h = new Promise(async (f, n) => { await (a = m.createElement("script")); e.set("libraries", [...r] + ""); for (k in g) e.set(k.replace(/[A-Z]/g, t => "_" + t[0].toLowerCase()), g[k]); e.set("callback", c + ".maps." + q); a.src = `https://maps.${c}apis.com/maps/api/js?` + e; d[q] = f; a.onerror = () => h = n(Error(p + " could not load.")); a.nonce = m.querySelector("script[nonce]")?.nonce || ""; m.head.append(a) })); d[l] ? console.warn(p + " only loads once. Ignoring:", g) : d[l] = (f, ...n) => r.add(f) && u().then(() => d[l](f, ...n)) })({
           key: "<INSERT API KEY>",
           v: "alpha",
           // Use the 'v' parameter to indicate the version to use (weekly, beta, alpha, etc.).
           // Add other bootstrap parameters as needed, using camel case.
       });
   </script>
   <script>
       let map3D = null;

       const base = document.location.href.substr(0, document.location.href.lastIndexOf("/"));

       const europeCamera = {
           center: { lat: 46.717, lng: 7.075, altitude: 2175.130 },
           range: 5814650,
           tilt: 33,
           heading: 4.36,
       };

       const officeLocations = [
           {
               "name": "Google France",
               "camera": {
                   "center": { lat: 48.877276, lng: 2.329978, altitude: 48 },
                   "range": 178,
                   "tilt": 57.48,
                   "heading": -17,
               },
               "point": { lat: 48.8775183, lng: 2.3299791, altitude: 60 },
               "pin": {
                   "background": 'white',
                   "glyph": new URL(base + '/images/fr.svg'),
                   "scale": 1.0,
               },
           },
           {
               "name": "Google UK",
               "camera": {
                   "center": { lat: 51.5332, lng: -0.1260, altitude: 38.8 },
                   "range": 500,
                   "tilt": 56.21672368296945,
                   "heading": -31.15763027564165,
               },
               "point": { lat: 51.5332, lng: -0.1260, altitude: 75 },
               "pin": {
                   "background": 'white',
                   "glyph": new URL(base + '/images/gb.svg'),
                   "scale": 1.0,
               },
           }]

       async function init() {
           const { Map3DElement, MapMode, Marker3DInteractiveElement } = await google.maps.importLibrary("maps3d");
           const { PinElement } = await google.maps.importLibrary('marker');

           map3D = new Map3DElement({
               ...europeCamera,
               mode: MapMode.SATELLITE,
           });

           officeLocations.forEach(office => {
               const marker = new Marker3DInteractiveElement({
                   position: office.point,
                   label: office.name,
                   altitudeMode: 'ABSOLUTE',
                   extruded: true,
               });

               marker.addEventListener('gmp-click', (event) => {
                   map3D.flyCameraTo({
                       endCamera: office.camera,
                       durationMillis: 5000,
                   });

                   map3D.addEventListener('gmp-animationend', () => {
                       map3D.flyCameraAround({
                           camera: office.camera,
                           durationMillis: 5000,
                           rounds: 1
                       });

                       map3D.addEventListener('gmp-animationend', () => {
                           map3D.flyCameraTo({
                               endCamera: europeCamera,
                               durationMillis: 5000,
                           });
                       }, { once: true });

                   }, { once: true });

                   event.stopPropagation();
               });

               const markerPin = new PinElement(office.pin);
               marker.append(markerPin);

               map3D.append(marker);
           });
           document.body.append(map3D);
       }
       init();
   </script>
</body>

</html>

11. Weitere Orte

Die Anwendung verfügt zwar jetzt über alle erforderlichen Funktionen, die 3D-Karte sieht aber immer noch etwas karg aus. Sie fügen daher noch einige weitere Orte hinzu, um sie etwas geschäftiger zu gestalten. Mithilfe eines Arrays können Sie ganz einfach neue Standorte mit eigenen Markierungen hinzufügen. Im letzten Schritt fügen Sie so viele Markierungen hinzu, bis die folgende Ansicht erreicht ist.

„Ein Bild, auf dem alle Büros zu sehen sind.

Weitere Markierungen hinzufügen

Google hat eine Reihe von Niederlassungen in vielen Ländern in Europa. Fügen wir der Karte einige davon hinzu. Sie müssen nur das Array aktualisieren. Diese Daten können aus einem Webdienst stammen oder von einer statischen Datei bereitgestellt werden. In unserem Fall bleiben sie aus Gründen der Einfachheit auf derselben Seite.

Sie können beliebig viele Markierungen hinzufügen, die von der Seite übernommen und dann automatisch der Ansicht hinzugefügt werden. Denken Sie daran, die richtigen Flags zu erhalten und sie im Verzeichnis „images“ (oder an einem anderen geeigneten Ort) zu speichern.

const officeLocations = [
   {
       name: "Google France",
       camera: {
           center: { lat: 48.877276, lng: 2.329978, altitude: 48 },
           range: 178,
           tilt: 57.48,
           heading: -17,
       },
       point: { lat: 48.8775183, lng: 2.3299791, altitude: 60 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/fr.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google UK",
       camera: {
           center: { lat: 51.5332, lng: -0.1260, altitude: 38.8 },
           range: 500,
           tilt: 56.21672368296945,
           heading: -31.15763027564165,
       },
       point: { lat: 51.5332, lng: -0.1260, altitude: 75 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/gb.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Belgium",
       camera: {
           center: { lat: 50.83930408436509, lng: 4.38052394507952, altitude: 64.38932203802196},
           range: 466.62899893119175,
           tilt: 43.61569474716178,
           heading: 51.805907046332074,
       },
       point: { lat: 50.8392653, lng: 4.3808751, altitude: 25 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/be.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Czechia",
       camera: {
           center: {
               lat: 50.07004093853976,
               lng: 14.402871475443956,
               altitude: 223.39574818495532
           },
           range: 522.0365799222782,
           tilt: 62.39511972890614,
           heading: -39.150149539328304,
       },
       point: { lat: 50.0703122, lng: 14.402668199999999, altitude: 50 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/cz.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Denmark",
       details: "2, Sankt Petri Passage 5, 1165 København",
       camera: {
           center: {
               lat: 55.680359539635866,
               lng: 12.570460204526002,
               altitude: 30.447654757346044
           },
           range: 334.8786935049066,
           tilt: 55.38819319004654,
           heading: 149.63867461295067,
       },
       point: { lat: 55.6804504, lng: 12.570279099999999, altitude: 25 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/dk.svg'),
           scale: 1.0,
       },
   },
   ,
   {
       name: "Google Greece",
       camera: {
           center: {
               lat: 38.038634694028055,
               lng: 23.802924946201266,
               altitude: 196.45884670344995
           },
           range: 343.57226336076565,
           tilt: 54.97375927639567,
           heading: -33.26775344055724,
       },
       point: { lat: 38.038619, lng: 23.8031622, altitude: 25 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/gr.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Germany",
       camera: {
           center: {
               lat: 53.55397683312404,
               lng: 9.986350507286808,
               altitude: 44.83610870143956
           },
           range: 375.3474077822466,
           tilt: 71.35078443829818,
           heading: -160.76930098951416,
       },
       point: { lat: 53.5540227, lng: 9.9863, altitude: 50 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/de.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Ireland",
       camera: {
           center: { lat: 53.339816899999995, lng: -6.2362644, altitude: 38.777415761228006 },
           range: 500,
           tilt: 56.21672368296945,
           heading: -31.15763027564165,
       },
       point: { lat: 53.339816899999995, lng: -6.2362644, altitude: 50 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/ie.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Italy",
       camera: {
           center: {
               lat: 45.486361346538224,
               lng: 9.18995496294455,
               altitude: 138.55834058400072
           },
           range: 694.9398023590038,
           tilt: 57.822470255679114,
           heading: 84.10194883488619,
       },
       point: { lat: 45.4863064, lng: 9.1894762, altitude: 50 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/it.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Lithuania",
       camera: {
           center: {
               lat: 54.698040606567965,
               lng: 25.30965338542576,
               altitude: 111.80276944294413
           },
           range: 412.5808304977545,
           tilt: 43.50793332082195,
           heading: -29.181098269421028,
       },
       point: { lat: 54.6981204, lng: 25.3098617, altitude: 25 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/at.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Netherlands",
       camera: {
           center: {
               lat: 52.33773837150874,
               lng: 4.871754560171063,
               altitude: 53.68063996154723
           },
           range: 473.1982259177312,
           tilt: 56.216523350388634,
           heading: 71.78252318033718,
       },
       point: { lat: 52.337801, lng: 4.872065999999999, altitude: 100 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/nl.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Norway",
       camera: {
           center: { lat: 59.90991209999999, lng: 10.726020799999999, altitude: 38.777415761228006 },
           range: 500,
           tilt: 56.21672368296945,
           heading: -31.15763027564165,
       },
       point: { lat: 59.90991209999999, lng: 10.726020799999999, altitude: 25 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/no.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Poland",
       camera: {
           center: { lat: 52.22844380000001, lng: 20.9851819, altitude: 38.777415761228006 },
           range: 500,
           tilt: 56.21672368296945,
           heading: -31.15763027564165,
       },
       point: { lat: 52.22844380000001, lng: 20.9851819, altitude: 25 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/pl.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Portugal",
       camera: {
           center: {
               lat: 38.7240122810727,
               lng: -9.150628263172639,
               altitude: 55.299662291551044
           },
           range: 337.7474313328639,
           tilt: 56.79772652682846,
           heading: 176.0722118222208,
       },
       point: { lat: 38.723915999999996, lng: -9.150629, altitude: 35 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/pt.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Romania",
       camera: {
           center: {
               lat: 44.43076650172983,
               lng: 26.109700164718586,
               altitude: 125.57895810814505
           },
           range: 364.25249956711923,
           tilt: 38.517539223834326,
           heading: -38.81294924429363,
       },
       point: { lat: 44.4309897, lng: 26.1095719, altitude: 75 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/ro.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Spain",
       camera: {
           center: {
               lat: 40.450078762608875,
               lng: -3.6930085080020856,
               altitude: 753.6446342341894
           },
           range: 845.7279793010093,
           tilt: 46.752510050599746,
           heading: 4.718779524265234,
       },
       point: { lat: 40.450294199999995, lng: -3.6927915, altitude: 175 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/es.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Sweden",
       camera: {
           center: {
               lat: 59.33313751316038,
               lng: 18.054618219238293,
               altitude: 16.728213706832868
           },
           range: 377.5210725830039,
           tilt: 63.59478230626709,
           heading: 98.53138488367703,
       },
       point: { lat: 59.3332093, lng: 18.0536386, altitude: 50 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/se.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Switzerland",
       camera: {
           center: {
               lat: 47.365411056285275,
               lng: 8.525063594405356,
               altitude: 419.2348376754488
           },
           range: 166.74918737631742,
           tilt: 59.31431457129067,
           heading: -32.620415961949206,
       },
       point: { lat: 47.365452, lng: 8.5249253, altitude: 100 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/ch.svg'),
           scale: 1.0,
       },
   }
]

Danach sollte eine vollständige Seite wie auf dem Bild zu sehen sein, auf der Nutzer auf einen beliebigen Ort klicken und dorthin und um ihn herum schweben und dann wieder herauszoomen können.

„Amination fliegt zwischen und um die Büros in Spanien und Schweden.

Herzlichen Glückwunsch, Sie haben das Codelab abgeschlossen. Im nächsten Abschnitt können wir uns neue Dinge ansehen.

Bereichslösung

Für diesen Schritt wird die fertige Seite als Lösung zur Überprüfung Ihrer Implementierung bereitgestellt. (Achten Sie beim Kopieren darauf, dass Sie Ihren eigenen API-Schlüssel verwenden.)

Denken Sie auch daran, die SVG-Datei (oder PNG-Datei) für die Flagge herunterzuladen und in einem Verzeichnis zu speichern, das von Ihrer Seite aus gefunden werden kann. Hier wird sie im Ordner „Bilder“ gespeichert.

<!DOCTYPE html>
<html>

<head>
   <title>Step 9 - More Places!</title>
   <style>
       body {
           height: 100vh;
           margin: 0;
       }
   </style>
</head>

<body>
   <script>
       (g => { var h, a, k, p = "The Google Maps JavaScript API", c = "google", l = "importLibrary", q = "__ib__", m = document, b = window; b = b[c] || (b[c] = {}); var d = b.maps || (b.maps = {}), r = new Set, e = new URLSearchParams, u = () => h || (h = new Promise(async (f, n) => { await (a = m.createElement("script")); e.set("libraries", [...r] + ""); for (k in g) e.set(k.replace(/[A-Z]/g, t => "_" + t[0].toLowerCase()), g[k]); e.set("callback", c + ".maps." + q); a.src = `https://maps.${c}apis.com/maps/api/js?` + e; d[q] = f; a.onerror = () => h = n(Error(p + " could not load.")); a.nonce = m.querySelector("script[nonce]")?.nonce || ""; m.head.append(a) })); d[l] ? console.warn(p + " only loads once. Ignoring:", g) : d[l] = (f, ...n) => r.add(f) && u().then(() => d[l](f, ...n)) })({
           key: "<INSERT API KEY>",
           v: "alpha",
           // Use the 'v' parameter to indicate the version to use (weekly, beta, alpha, etc.).
           // Add other bootstrap parameters as needed, using camel case.
       });
   </script>
   <script>
       let map3D = null;

       const base = document.location.href.substr(0, document.location.href.lastIndexOf("/"));

       const europeCamera = {
           center: { lat: 46.717, lng: 7.075, altitude: 2175.130 },
           range: 5814650,
           tilt: 33,
           heading: 4.36,
       };

const officeLocations = [
   {
       name: "Google France",
       details: "8 Rue de Londres, 75009 Paris, France",
       camera: {
           center: { lat: 48.877276, lng: 2.329978, altitude: 48 },
           range: 178,
           tilt: 57.48,
           heading: -17,
       },
       point: { lat: 48.8775183, lng: 2.3299791, altitude: 60 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/fr.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google UK",
       details: "6 Pancras Square, London N1C 4AG, UK",
       camera: {
           center: { lat: 51.5332, lng: -0.1260, altitude: 38.8 },
           range: 500,
           tilt: 56.21672368296945,
           heading: -31.15763027564165,
       },
       point: { lat: 51.5332, lng: -0.1260, altitude: 75 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/gb.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Belgium",
       details: "Chau. d'Etterbeek 180, 1040 Brussel",
       camera: {
           center: { lat: 50.83930408436509, lng: 4.38052394507952, altitude: 64.38932203802196},
           range: 466.62899893119175,
           tilt: 43.61569474716178,
           heading: 51.805907046332074,
       },
       point: { lat: 50.8392653, lng: 4.3808751, altitude: 25 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/be.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Czechia",
       details: "Stroupežnického 3191/17, 150 00 Praha 5-Smíchov",
       camera: {
           center: {
               lat: 50.07004093853976,
               lng: 14.402871475443956,
               altitude: 223.39574818495532
           },
           range: 522.0365799222782,
           tilt: 62.39511972890614,
           heading: -39.150149539328304,
       },
       point: { lat: 50.0703122, lng: 14.402668199999999, altitude: 50 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/cz.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Denmark",
       details: "2, Sankt Petri Passage 5, 1165 København",
       camera: {
           center: {
               lat: 55.680359539635866,
               lng: 12.570460204526002,
               altitude: 30.447654757346044
           },
           range: 334.8786935049066,
           tilt: 55.38819319004654,
           heading: 149.63867461295067,
       },
       point: { lat: 55.6804504, lng: 12.570279099999999, altitude: 25 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/dk.svg'),
           scale: 1.0,
       },
   },
   ,
   {
       name: "Google Greece",
       details: "Fragkokklisias 6, Athina 151 25",
       camera: {
           center: {
               lat: 38.038634694028055,
               lng: 23.802924946201266,
               altitude: 196.45884670344995
           },
           range: 343.57226336076565,
           tilt: 54.97375927639567,
           heading: -33.26775344055724,
       },
       point: { lat: 38.038619, lng: 23.8031622, altitude: 25 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/gr.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Germany",
       details: "ABC-Straße 19, 20354 Hamburg",
       camera: {
           center: {
               lat: 53.55397683312404,
               lng: 9.986350507286808,
               altitude: 44.83610870143956
           },
           range: 375.3474077822466,
           tilt: 71.35078443829818,
           heading: -160.76930098951416,
       },
       point: { lat: 53.5540227, lng: 9.9863, altitude: 50 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/de.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Ireland",
       details: "Gordon House, 4 Barrow St, Grand Canal Dock, Dublin 4, D04 V4X7",
       camera: {
           center: { lat: 53.339816899999995, lng: -6.2362644, altitude: 38.777415761228006 },
           range: 500,
           tilt: 56.21672368296945,
           heading: -31.15763027564165,
       },
       point: { lat: 53.339816899999995, lng: -6.2362644, altitude: 50 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/ie.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Italy",
       details: "Isola Building C, Via Federico Confalonieri, 4, 20124 Milano",
       camera: {
           center: {
               lat: 45.486361346538224,
               lng: 9.18995496294455,
               altitude: 138.55834058400072
           },
           range: 694.9398023590038,
           tilt: 57.822470255679114,
           heading: 84.10194883488619,
       },
       point: { lat: 45.4863064, lng: 9.1894762, altitude: 50 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/it.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Lithuania",
       details: "Vilnius Tech Park, Antakalnis st. 17, 2nd building, LT-10312, Vilnius",
       camera: {
           center: {
               lat: 54.698040606567965,
               lng: 25.30965338542576,
               altitude: 111.80276944294413
           },
           range: 412.5808304977545,
           tilt: 43.50793332082195,
           heading: -29.181098269421028,
       },
       point: { lat: 54.6981204, lng: 25.3098617, altitude: 25 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/at.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Netherlands",
       details: "Claude Debussylaan 34, 1082 MD Amsterdam",
       camera: {
           center: {
               lat: 52.33773837150874,
               lng: 4.871754560171063,
               altitude: 53.68063996154723
           },
           range: 473.1982259177312,
           tilt: 56.216523350388634,
           heading: 71.78252318033718,
       },
       point: { lat: 52.337801, lng: 4.872065999999999, altitude: 100 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/nl.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Norway",
       details: "Bryggegata 6, 0250 Oslo",
       camera: {
           center: { lat: 59.90991209999999, lng: 10.726020799999999, altitude: 38.777415761228006 },
           range: 500,
           tilt: 56.21672368296945,
           heading: -31.15763027564165,
       },
       point: { lat: 59.90991209999999, lng: 10.726020799999999, altitude: 25 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/no.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Poland",
       details: "Rondo Daszynskiego 2, 00-843 Warsaw",
       camera: {
           center: { lat: 52.22844380000001, lng: 20.9851819, altitude: 38.777415761228006 },
           range: 500,
           tilt: 56.21672368296945,
           heading: -31.15763027564165,
       },
       point: { lat: 52.22844380000001, lng: 20.9851819, altitude: 25 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/pl.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Portugal",
       details: "R. Duque de Palmela 37 Piso 4, 1250-097 Lisboa",
       camera: {
           center: {
               lat: 38.7240122810727,
               lng: -9.150628263172639,
               altitude: 55.299662291551044
           },
           range: 337.7474313328639,
           tilt: 56.79772652682846,
           heading: 176.0722118222208,
       },
       point: { lat: 38.723915999999996, lng: -9.150629, altitude: 35 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/pt.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Romania",
       details: "Bulevardul Corneliu Coposu 6-8, București 030167",
       camera: {
           center: {
               lat: 44.43076650172983,
               lng: 26.109700164718586,
               altitude: 125.57895810814505
           },
           range: 364.25249956711923,
           tilt: 38.517539223834326,
           heading: -38.81294924429363,
       },
       point: { lat: 44.4309897, lng: 26.1095719, altitude: 75 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/ro.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Spain",
       details: "Torre Picasso, Pl. Pablo Ruiz Picasso, 1, Tetuán, 28020 Madrid",
       camera: {
           center: {
               lat: 40.450078762608875,
               lng: -3.6930085080020856,
               altitude: 753.6446342341894
           },
           range: 845.7279793010093,
           tilt: 46.752510050599746,
           heading: 4.718779524265234,
       },
       point: { lat: 40.450294199999995, lng: -3.6927915, altitude: 175 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/es.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Sweden",
       details: "Kungsbron 2, 111 22 Stockholm",
       camera: {
           center: {
               lat: 59.33313751316038,
               lng: 18.054618219238293,
               altitude: 16.728213706832868
           },
           range: 377.5210725830039,
           tilt: 63.59478230626709,
           heading: 98.53138488367703,
       },
       point: { lat: 59.3332093, lng: 18.0536386, altitude: 50 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/se.svg'),
           scale: 1.0,
       },
   },
   {
       name: "Google Switzerland",
       details: "Brandschenkestrasse 110, 8002 Zürich",
       camera: {
           center: {
               lat: 47.365411056285275,
               lng: 8.525063594405356,
               altitude: 419.2348376754488
           },
           range: 166.74918737631742,
           tilt: 59.31431457129067,
           heading: -32.620415961949206,
       },
       point: { lat: 47.365452, lng: 8.5249253, altitude: 100 },
       pin: {
           background: 'white',
           glyph: new URL(base + '/images/ch.svg'),
           scale: 1.0,
       },
   }
]

       async function init() {
           const { Map3DElement, MapMode, Marker3DInteractiveElement } = await google.maps.importLibrary("maps3d");
           const { PinElement } = await google.maps.importLibrary('marker');

           map3D = new Map3DElement({
               ...europeCamera,
               mode: MapMode.SATELLITE,
           });

           officeLocations.forEach(office => {
               const marker = new Marker3DInteractiveElement({
                   position: office.point,
                   label: office.name,
                   altitudeMode: 'RELATIVE_TO_GROUND',
                   extruded: true,
               });

               marker.addEventListener('gmp-click', (event) => {
                   map3D.flyCameraTo({
                       endCamera: office.camera,
                       durationMillis: 2000,
                   });

                   map3D.addEventListener('gmp-animationend', () => {
                       map3D.flyCameraAround({
                           camera: office.camera,
                           durationMillis: 2000,
                           rounds: 1
                       });

                       map3D.addEventListener('gmp-animationend', () => {
                           map3D.flyCameraTo({
                               endCamera: europeCamera,
                               durationMillis: 2000,
                           });
                       }, { once: true });

                   }, { once: true });

                   event.stopPropagation();
               });

               const markerPin = new PinElement(office.pin);
               marker.append(markerPin);

               map3D.append(marker);
           });
           document.body.append(map3D);
       }
       init();
   </script>
</body>

</html>

12. Nächste Schritte

In diesem Codelab haben Sie die Grundlagen der Verwendung von 3D in der Maps JavaScript API kennengelernt. Fügen Sie der Karte als Nächstes einige dieser Elemente hinzu:

  • Fügen Sie eine Drop-down-Liste hinzu, um die Auswahl eines Büros zu ermöglichen.
  • Mit den anderen Optionen für das Markierungs-Design können Sie Ihre Karte noch ansprechender gestalten.
  • Sehen Sie sich die zusätzlichen Bibliotheken an, die für die Maps JavaScript API verfügbar sind und zusätzliche Funktionen ermöglichen, z. B. die Anzeige der Bewertung jedes Büros anhand der Orts-ID.

Unter den folgenden Links finden Sie weitere Informationen zur Arbeit mit der Google Maps Platform und 3D im Web: