Ionic 6 Google Map, Geocoder & Places Search, Draggable Marker Tutorial

In this Ionic 5/6 tutorial, you will learn how to add Google Maps in the Ionic application using the latest @angular/google-maps package module by following a few easy steps. Google Maps implementation tutorial using @angular/google-maps 2022.

The Google Map will have places search bar and Geocoder to display the address where the marker is dragged. This feature is used to enable a user to select a particular area while displaying the address in real-time to ensure the correct location.

We have always used the @agm package for our Angular based application even for Ionic, but in the latest version 13, it is causing a few type issues and problems. These have come-u to the application which is now upgraded to the latest 1 version or getting created newly.

Thankfully, we have a google-maps module which is now officially a part of the @angular core module. So, today we will be converting the previous Google Maps tutorial in which we used @agm, to use @angular/google-maps components. This will also clear the doubts on efforts required for migration of Google Maps in Angular app while moving from @agm to @angular/google-maps.

You can check our previous Ionic tutorial using @agm on the following link:

https://www.freakyjolly.com/ionic-5-angular-google-maps-using-agm/

Let’s start the implementation

How to add Google Map with Places Search and Draggable Marker using Geocoder?

We will follow these quick steps to get latitude and longitude coordinates on Google Map using a draggable Marker while displaying the address using geocoder service.

Step 1 – Create a new Ionic 6 application

Step 2 – Install @angular/google-maps package

Step 3 – Get Google API Key & Include Google Map API

Step 4 – Adding Google Map with Draggable Marker

Step 5 – See In Action

 

Step 1 – Create a new Ionic 6 application

To start from scratch we will create a new Ionic application with a blank template by running the following NPM command in terminal:

$ ionic start ionic-google-map-demo
? Starter template: blank

 

Step 2 – Install @angular/google-maps package

Next, install the Angular Google Maps package by executing the below command:

npm install @angular/google-maps

Afterwards, update the HomePageModule in our case to import the GoogleMapsModule. Open the home.module.ts file and update as shown below:

import { NgModule } from '@angular/core';
import { CommonModule } from '@angular/common';
import { IonicModule } from '@ionic/angular';
import { FormsModule } from '@angular/forms';
import { HomePage } from './home.page';

import { HomePageRoutingModule } from './home-routing.module';

import { GoogleMapsModule } from '@angular/google-maps';

@NgModule({
  imports: [
    CommonModule,
    FormsModule,
    IonicModule,
    HomePageRoutingModule,
    GoogleMapsModule, //<-- Added GoogleMapsModule
  ],
  declarations: [HomePage],
})
export class HomePageModule {}

 

Step 3 – Get Google API Key & Include Google Map API

Now, we need to include the Google Maps API library and also the API KEY to use google maps in your application. To know more about how to get your own Google API Key, please refer to the following step by step tutorial.

https://www.freakyjolly.com/how-to-get-a-google-api-key-for-using-maps/

Adding Google Maps API 

Include in Index.html file

You can simply include the API library in the <head> section of your index.html as shown below:

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

<head>
  <meta charset="utf-8" />
  <title>Ionic App</title>

  <base href="/" />

  <meta name="color-scheme" content="light dark" />
  <meta name="viewport"
    content="viewport-fit=cover, width=device-width, initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0, user-scalable=no" />
  <meta name="format-detection" content="telephone=no" />
  <meta name="msapplication-tap-highlight" content="no" />

  <link rel="icon" type="image/png" href="assets/icon/favicon.png" />

  <!-- add to homescreen for ios -->
  <meta name="apple-mobile-web-app-capable" content="yes" />
  <meta name="apple-mobile-web-app-status-bar-style" content="black" />
  <script
    src="https://maps.googleapis.com/maps/api/js?key=AIzaSyAlaa...B11bbKEUg&libraries=places"></script>
</head>

<body>
  <app-root></app-root>
</body>

</html>

 

Step 4 – Adding Google Map with Draggable Marker

Now we are ready to add and implement Google Maps in our Ionic application. Open the home.page.html file and update it with the following code:

<ion-header [translucent]="true">
  <ion-toolbar color="danger">
    <ion-title> Google Maps: FreakyJolly </ion-title>
  </ion-toolbar>
</ion-header>

<ion-content [fullscreen]="true" class="ion-padding">
  <h5>Get Address by Marker Drag</h5>

  <div>
    <input type="text" class="my-search-box" (keydown.enter)="$event.preventDefault()" placeholder="Search Location"
      type="text" #search />
  </div>

  <google-map #myGoogleMap height="430px" width="100%" [zoom]="zoom" [center]="center" [options]="options"
    (mapClick)="eventHandler($event,'mapClick')" (mapDblclick)="eventHandler($event,'mapDblclick')"
    (mapDrag)="eventHandler($event,'mapDrag')" (mapDragend)="eventHandler($event,'mapDragend')"
    (mapRightclick)="eventHandler($event,'mapRightclick')"
    (positionChanged)="eventHandler($event,'marker_positionChanged')"
    (zoomChanged)="eventHandler($event,'zoomChanged')">

    <map-marker #markerElem="mapMarker" *ngFor="let marker of markers" [position]="marker.position"
      [label]="marker.label" [title]="marker.title" [options]="marker.options"
      (mapDrag)="eventHandler($event,'mapDragMarker')" (mapDragend)="eventHandler($event,'mapDragend')">
    </map-marker>

  </google-map>

  <h6 *ngIf="address">{{address}}</h6>
</ion-content>

The <google-map> the component is used to create the maps and it supports various input and output properties. I have added mose of them which are commonly used.

The <map-marker> is used to create the draggable marker in our case. It also supports the input and output propserties to handle the behaviour required for our featue.

On top of that, we have an <input type=text> HTML field to enable the user to search places. It is having template reference variable to handle the searc/autocomplete functionalty.

 

Next, open the component class to add various required methods. open the home.page.ts file and update it with the following code in it:

import { Component, ElementRef, NgZone, ViewChild } from '@angular/core';
import {
  GoogleMap,
  MapInfoWindow,
  MapGeocoder,
  MapGeocoderResponse,
} from '@angular/google-maps';

@Component({
  selector: 'app-home',
  templateUrl: 'home.page.html',
  styleUrls: ['home.page.scss'],
})
export class HomePage {
  @ViewChild('search')
  public searchElementRef!: ElementRef;
  @ViewChild('myGoogleMap', { static: false })
  map!: GoogleMap;
  @ViewChild(MapInfoWindow, { static: false })
  info!: MapInfoWindow;

  address = '';
  latitude!: any;
  longitude!: any;
  zoom = 12;
  maxZoom = 15;
  minZoom = 8;
  center!: google.maps.LatLngLiteral;
  options: google.maps.MapOptions = {
    zoomControl: true,
    scrollwheel: false,
    disableDoubleClickZoom: true,
    mapTypeId: 'hybrid',
  };
  markers = [] as any;

  constructor(private ngZone: NgZone, private geoCoder: MapGeocoder) {}

  ngAfterViewInit(): void {
    // Binding autocomplete to search input control
    let autocomplete = new google.maps.places.Autocomplete(
      this.searchElementRef.nativeElement
    );
    // Align search box to center
    this.map.controls[google.maps.ControlPosition.TOP_CENTER].push(
      this.searchElementRef.nativeElement
    );
    autocomplete.addListener('place_changed', () => {
      this.ngZone.run(() => {
        //get the place result
        let place: google.maps.places.PlaceResult = autocomplete.getPlace();

        //verify result
        if (place.geometry === undefined || place.geometry === null) {
          return;
        }

        console.log({ place }, place.geometry.location?.lat());

        //set latitude, longitude and zoom
        this.latitude = place.geometry.location?.lat();
        this.longitude = place.geometry.location?.lng();

        // Set marker position
        this.setMarkerPosition(this.latitude, this.longitude);

        this.center = {
          lat: this.latitude,
          lng: this.longitude,
        };
      });
    });
  }

  ngOnInit() {
    navigator.geolocation.getCurrentPosition((position) => {
      this.latitude = position.coords.latitude;
      this.longitude = position.coords.longitude;
      this.center = {
        lat: position.coords.latitude,
        lng: position.coords.longitude,
      };
      // Set marker position
      this.setMarkerPosition(this.latitude, this.longitude);
    });
  }

  setMarkerPosition(latitude: any, longitude: any) {
    // Set marker position
    this.markers = [
      {
        position: {
          lat: latitude,
          lng: longitude,
        },
        options: {
          animation: google.maps.Animation.DROP,
          draggable: true,
        },
      },
    ];
  }

  eventHandler(event: any, name: string) {
    // console.log(event, name);

    switch (name) {
      case 'mapDblclick': // Add marker on double click event
        break;

      case 'mapDragMarker':
        break;

      case 'mapDragend':
        this.getAddress(event.latLng.lat(), event.latLng.lng());
        break;

      default:
        break;
    }
  }

  getAddress(latitude: any, longitude: any) {
    this.geoCoder
      .geocode({ location: { lat: latitude, lng: longitude } })
      .subscribe((addr: MapGeocoderResponse) => {
        if (addr.status === 'OK') {
          if (addr.results[0]) {
            this.zoom = 12;
            this.address = addr.results[0].formatted_address;
          } else {
            this.address = null;
            window.alert('No results found');
          }
        } else {
          this.address = null;
          window.alert('Geocoder failed due to: ' + addr.status);
        }
      });
  }
}

 

Step 5 – See In Action

Now you can run your application by hitting npm start to see your app in action. It will be shown as below:

 

Conclusion

Adding Google Maps in Angular applications is very easy and straightforward. In our demo application we have covered many important features to explore:

  • Draggable Marker
  • Places Search bar/ Autocomplete
  • Geocoder API to Fetch Address on marker drag.
  • Get Address in String Format and Show on Screen.

Hope this will be helpful…

 

 

Leave a Comment

Your email address will not be published. Required fields are marked *