@angular/google-maps
Version:
Angular Google Maps
1 lines • 269 kB
Source Map (JSON)
{"version":3,"file":"google-maps.mjs","sources":["../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-event-manager.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/google-map/google-map.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-base-layer.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-bicycling-layer/map-bicycling-layer.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-circle/map-circle.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-directions-renderer/map-directions-renderer.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-ground-overlay/map-ground-overlay.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-info-window/map-info-window.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-kml-layer/map-kml-layer.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/marker-utilities.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-marker/map-marker.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/deprecated-map-marker-clusterer/deprecated-map-marker-clusterer.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-polygon/map-polygon.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-polyline/map-polyline.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-rectangle/map-rectangle.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-traffic-layer/map-traffic-layer.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-transit-layer/map-transit-layer.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-heatmap-layer/map-heatmap-layer.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-advanced-marker/map-advanced-marker.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-marker-clusterer/map-marker-clusterer.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/google-maps-module.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-directions-renderer/map-directions-service.ts","../../../../../k8-fastbuild-ST-46c76129e412/bin/src/google-maps/map-geocoder/map-geocoder.ts"],"sourcesContent":["/**\n * @license\n * Copyright Google LLC All Rights Reserved.\n *\n * Use of this source code is governed by an MIT-style license that can be\n * found in the LICENSE file at https://angular.dev/license\n */\n\nimport {NgZone} from '@angular/core';\nimport {BehaviorSubject, Observable, Subscriber} from 'rxjs';\nimport {switchMap} from 'rxjs/operators';\n\ntype MapEventManagerTarget =\n | {\n addListener: (\n name: string,\n callback: (...args: any[]) => void,\n ) => google.maps.MapsEventListener | undefined;\n }\n | undefined;\n\n/** Manages event on a Google Maps object, ensuring that events are added only when necessary. */\nexport class MapEventManager {\n /** Pending listeners that were added before the target was set. */\n private _pending: {observable: Observable<any>; observer: Subscriber<any>}[] = [];\n private _listeners: google.maps.MapsEventListener[] = [];\n private _targetStream = new BehaviorSubject<MapEventManagerTarget>(undefined);\n\n /** Clears all currently-registered event listeners. */\n private _clearListeners() {\n for (const listener of this._listeners) {\n listener.remove();\n }\n\n this._listeners = [];\n }\n\n constructor(private _ngZone: NgZone) {}\n\n /** Gets an observable that adds an event listener to the map when a consumer subscribes to it. */\n getLazyEmitter<T>(name: string): Observable<T> {\n return this._targetStream.pipe(\n switchMap(target => {\n const observable = new Observable<T>(observer => {\n // If the target hasn't been initialized yet, cache the observer so it can be added later.\n if (!target) {\n this._pending.push({observable, observer});\n return undefined;\n }\n\n const listener = target.addListener(name, (event: T) => {\n this._ngZone.run(() => observer.next(event));\n });\n\n // If there's an error when initializing the Maps API (e.g. a wrong API key), it will\n // return a dummy object that returns `undefined` from `addListener` (see #26514).\n if (!listener) {\n observer.complete();\n return undefined;\n }\n\n this._listeners.push(listener);\n return () => listener.remove();\n });\n\n return observable;\n }),\n );\n }\n\n /** Sets the current target that the manager should bind events to. */\n setTarget(target: MapEventManagerTarget) {\n const currentTarget = this._targetStream.value;\n\n if (target === currentTarget) {\n return;\n }\n\n // Clear the listeners from the pre-existing target.\n if (currentTarget) {\n this._clearListeners();\n this._pending = [];\n }\n\n this._targetStream.next(target);\n\n // Add the listeners that were bound before the map was initialized.\n this._pending.forEach(subscriber => subscriber.observable.subscribe(subscriber.observer));\n this._pending = [];\n }\n\n /** Destroys the manager and clears the event listeners. */\n destroy() {\n this._clearListeners();\n this._pending = [];\n this._targetStream.complete();\n }\n}\n","/**\n * @license\n * Copyright Google LLC All Rights Reserved.\n *\n * Use of this source code is governed by an MIT-style license that can be\n * found in the LICENSE file at https://angular.dev/license\n */\n\n// Workaround for: https://github.com/bazelbuild/rules_nodejs/issues/1265\n/// <reference types=\"google.maps\" preserve=\"true\" />\n\nimport {\n ChangeDetectionStrategy,\n Component,\n ElementRef,\n Input,\n OnChanges,\n OnDestroy,\n OnInit,\n Output,\n ViewEncapsulation,\n PLATFORM_ID,\n NgZone,\n SimpleChanges,\n EventEmitter,\n inject,\n} from '@angular/core';\nimport {isPlatformBrowser} from '@angular/common';\nimport {Observable} from 'rxjs';\nimport {MapEventManager} from '../map-event-manager';\nimport {take} from 'rxjs/operators';\n\ninterface GoogleMapsWindow extends Window {\n gm_authFailure?: () => void;\n google?: typeof google;\n}\n\n/** default options set to the Googleplex */\nexport const DEFAULT_OPTIONS: google.maps.MapOptions = {\n center: {lat: 37.421995, lng: -122.084092},\n zoom: 17,\n // Note: the type conversion here isn't necessary for our CI, but it resolves a g3 failure.\n mapTypeId: 'roadmap' as unknown as google.maps.MapTypeId,\n};\n\n/** Arbitrary default height for the map element */\nexport const DEFAULT_HEIGHT = '500px';\n/** Arbitrary default width for the map element */\nexport const DEFAULT_WIDTH = '500px';\n\n/**\n * Angular component that renders a Google Map via the Google Maps JavaScript\n * API.\n * @see https://developers.google.com/maps/documentation/javascript/reference/\n */\n@Component({\n selector: 'google-map',\n exportAs: 'googleMap',\n changeDetection: ChangeDetectionStrategy.OnPush,\n template: '<div class=\"map-container\"></div><ng-content />',\n encapsulation: ViewEncapsulation.None,\n})\nexport class GoogleMap implements OnChanges, OnInit, OnDestroy {\n private readonly _elementRef = inject(ElementRef);\n private _ngZone = inject(NgZone);\n private _eventManager = new MapEventManager(inject(NgZone));\n private _mapEl: HTMLElement;\n private _existingAuthFailureCallback: GoogleMapsWindow['gm_authFailure'];\n\n /**\n * The underlying google.maps.Map object\n *\n * See developers.google.com/maps/documentation/javascript/reference/map#Map\n */\n googleMap?: google.maps.Map;\n\n /** Whether we're currently rendering inside a browser. */\n _isBrowser: boolean;\n\n /** Height of the map. Set this to `null` if you'd like to control the height through CSS. */\n @Input() height: string | number | null = DEFAULT_HEIGHT;\n\n /** Width of the map. Set this to `null` if you'd like to control the width through CSS. */\n @Input() width: string | number | null = DEFAULT_WIDTH;\n\n /**\n * The Map ID of the map. This parameter cannot be set or changed after a map is instantiated.\n * See: https://developers.google.com/maps/documentation/javascript/reference/map#MapOptions.mapId\n */\n @Input() mapId: string | undefined;\n\n /**\n * Type of map that should be rendered. E.g. hybrid map, terrain map etc.\n * See: https://developers.google.com/maps/documentation/javascript/reference/map#MapTypeId\n */\n @Input() mapTypeId: google.maps.MapTypeId | undefined;\n\n @Input()\n set center(center: google.maps.LatLngLiteral | google.maps.LatLng) {\n this._center = center;\n }\n private _center: google.maps.LatLngLiteral | google.maps.LatLng;\n\n @Input()\n set zoom(zoom: number) {\n this._zoom = zoom;\n }\n private _zoom: number;\n\n @Input()\n set options(options: google.maps.MapOptions) {\n this._options = options || DEFAULT_OPTIONS;\n }\n private _options = DEFAULT_OPTIONS;\n\n /** Event emitted when the map is initialized. */\n @Output() readonly mapInitialized: EventEmitter<google.maps.Map> =\n new EventEmitter<google.maps.Map>();\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/events#auth-errors\n */\n @Output() readonly authFailure: EventEmitter<void> = new EventEmitter<void>();\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.bounds_changed\n */\n @Output() readonly boundsChanged: Observable<void> =\n this._eventManager.getLazyEmitter<void>('bounds_changed');\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.center_changed\n */\n @Output() readonly centerChanged: Observable<void> =\n this._eventManager.getLazyEmitter<void>('center_changed');\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.click\n */\n @Output() readonly mapClick: Observable<google.maps.MapMouseEvent | google.maps.IconMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent | google.maps.IconMouseEvent>(\n 'click',\n );\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.dblclick\n */\n @Output() readonly mapDblclick: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('dblclick');\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.drag\n */\n @Output() readonly mapDrag: Observable<void> = this._eventManager.getLazyEmitter<void>('drag');\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.dragend\n */\n @Output() readonly mapDragend: Observable<void> =\n this._eventManager.getLazyEmitter<void>('dragend');\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.dragstart\n */\n @Output() readonly mapDragstart: Observable<void> =\n this._eventManager.getLazyEmitter<void>('dragstart');\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.heading_changed\n */\n @Output() readonly headingChanged: Observable<void> =\n this._eventManager.getLazyEmitter<void>('heading_changed');\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.idle\n */\n @Output() readonly idle: Observable<void> = this._eventManager.getLazyEmitter<void>('idle');\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.maptypeid_changed\n */\n @Output() readonly maptypeidChanged: Observable<void> =\n this._eventManager.getLazyEmitter<void>('maptypeid_changed');\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.mousemove\n */\n @Output()\n readonly mapMousemove: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('mousemove');\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.mouseout\n */\n @Output() readonly mapMouseout: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('mouseout');\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.mouseover\n */\n @Output() readonly mapMouseover: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('mouseover');\n\n /**\n * See\n * developers.google.com/maps/documentation/javascript/reference/map#Map.projection_changed\n */\n @Output() readonly projectionChanged: Observable<void> =\n this._eventManager.getLazyEmitter<void>('projection_changed');\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.rightclick\n */\n @Output() readonly mapRightclick: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('rightclick');\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.tilesloaded\n */\n @Output() readonly tilesloaded: Observable<void> =\n this._eventManager.getLazyEmitter<void>('tilesloaded');\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.tilt_changed\n */\n @Output() readonly tiltChanged: Observable<void> =\n this._eventManager.getLazyEmitter<void>('tilt_changed');\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.zoom_changed\n */\n @Output() readonly zoomChanged: Observable<void> =\n this._eventManager.getLazyEmitter<void>('zoom_changed');\n\n constructor(...args: unknown[]);\n\n constructor() {\n const platformId = inject<Object>(PLATFORM_ID);\n this._isBrowser = isPlatformBrowser(platformId);\n\n if (this._isBrowser) {\n const googleMapsWindow: GoogleMapsWindow = window;\n if (!googleMapsWindow.google && (typeof ngDevMode === 'undefined' || ngDevMode)) {\n throw Error(\n 'Namespace google not found, cannot construct embedded google ' +\n 'map. Please install the Google Maps JavaScript API: ' +\n 'https://developers.google.com/maps/documentation/javascript/' +\n 'tutorial#Loading_the_Maps_API',\n );\n }\n\n this._existingAuthFailureCallback = googleMapsWindow.gm_authFailure;\n googleMapsWindow.gm_authFailure = () => {\n if (this._existingAuthFailureCallback) {\n this._existingAuthFailureCallback();\n }\n this.authFailure.emit();\n };\n }\n }\n\n ngOnChanges(changes: SimpleChanges) {\n if (changes['height'] || changes['width']) {\n this._setSize();\n }\n\n const googleMap = this.googleMap;\n\n if (googleMap) {\n if (changes['options']) {\n googleMap.setOptions(this._combineOptions());\n }\n\n if (changes['center'] && this._center) {\n googleMap.setCenter(this._center);\n }\n\n // Note that the zoom can be zero.\n if (changes['zoom'] && this._zoom != null) {\n googleMap.setZoom(this._zoom);\n }\n\n if (changes['mapTypeId'] && this.mapTypeId) {\n googleMap.setMapTypeId(this.mapTypeId);\n }\n }\n }\n\n ngOnInit() {\n // It should be a noop during server-side rendering.\n if (this._isBrowser) {\n this._mapEl = this._elementRef.nativeElement.querySelector('.map-container')!;\n this._setSize();\n\n // Create the object outside the zone so its events don't trigger change detection.\n // We'll bring it back in inside the `MapEventManager` only for the events that the\n // user has subscribed to.\n if (google.maps.Map) {\n this._initialize(google.maps.Map);\n } else {\n this._ngZone.runOutsideAngular(() => {\n google.maps\n .importLibrary('maps')\n .then(lib => this._initialize((lib as google.maps.MapsLibrary).Map));\n });\n }\n }\n }\n\n private _initialize(mapConstructor: typeof google.maps.Map) {\n this._ngZone.runOutsideAngular(() => {\n this.googleMap = new mapConstructor(this._mapEl, this._combineOptions());\n this._eventManager.setTarget(this.googleMap);\n this.mapInitialized.emit(this.googleMap);\n });\n }\n\n ngOnDestroy() {\n this.mapInitialized.complete();\n this._eventManager.destroy();\n\n if (this._isBrowser) {\n const googleMapsWindow: GoogleMapsWindow = window;\n googleMapsWindow.gm_authFailure = this._existingAuthFailureCallback;\n }\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.fitBounds\n */\n fitBounds(\n bounds: google.maps.LatLngBounds | google.maps.LatLngBoundsLiteral,\n padding?: number | google.maps.Padding,\n ) {\n this._assertInitialized();\n this.googleMap.fitBounds(bounds, padding);\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.panBy\n */\n panBy(x: number, y: number) {\n this._assertInitialized();\n this.googleMap.panBy(x, y);\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.panTo\n */\n panTo(latLng: google.maps.LatLng | google.maps.LatLngLiteral) {\n this._assertInitialized();\n this.googleMap.panTo(latLng);\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.panToBounds\n */\n panToBounds(\n latLngBounds: google.maps.LatLngBounds | google.maps.LatLngBoundsLiteral,\n padding?: number | google.maps.Padding,\n ) {\n this._assertInitialized();\n this.googleMap.panToBounds(latLngBounds, padding);\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.getBounds\n */\n getBounds(): google.maps.LatLngBounds | null {\n this._assertInitialized();\n return this.googleMap.getBounds() || null;\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.getCenter\n */\n getCenter(): google.maps.LatLng | undefined {\n this._assertInitialized();\n return this.googleMap.getCenter();\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.getClickableIcons\n */\n getClickableIcons(): boolean | undefined {\n this._assertInitialized();\n return this.googleMap.getClickableIcons();\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.getHeading\n */\n getHeading(): number | undefined {\n this._assertInitialized();\n return this.googleMap.getHeading();\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.getMapTypeId\n */\n getMapTypeId(): google.maps.MapTypeId | string | undefined {\n this._assertInitialized();\n return this.googleMap.getMapTypeId();\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.getProjection\n */\n getProjection(): google.maps.Projection | null {\n this._assertInitialized();\n return this.googleMap.getProjection() || null;\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.getStreetView\n */\n getStreetView(): google.maps.StreetViewPanorama {\n this._assertInitialized();\n return this.googleMap.getStreetView();\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.getTilt\n */\n getTilt(): number | undefined {\n this._assertInitialized();\n return this.googleMap.getTilt();\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.getZoom\n */\n getZoom(): number | undefined {\n this._assertInitialized();\n return this.googleMap.getZoom();\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.controls\n */\n get controls(): google.maps.MVCArray<Node>[] {\n this._assertInitialized();\n return this.googleMap.controls;\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.data\n */\n get data(): google.maps.Data {\n this._assertInitialized();\n return this.googleMap.data;\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.mapTypes\n */\n get mapTypes(): google.maps.MapTypeRegistry {\n this._assertInitialized();\n return this.googleMap.mapTypes;\n }\n\n /**\n * See\n * https://developers.google.com/maps/documentation/javascript/reference/map#Map.overlayMapTypes\n */\n get overlayMapTypes(): google.maps.MVCArray<google.maps.MapType | null> {\n this._assertInitialized();\n return this.googleMap.overlayMapTypes;\n }\n\n /** Returns a promise that resolves when the map has been initialized. */\n _resolveMap(): Promise<google.maps.Map> {\n return this.googleMap\n ? Promise.resolve(this.googleMap)\n : this.mapInitialized.pipe(take(1)).toPromise();\n }\n\n private _setSize() {\n if (this._mapEl) {\n const styles = this._mapEl.style;\n styles.height =\n this.height === null ? '' : coerceCssPixelValue(this.height) || DEFAULT_HEIGHT;\n styles.width = this.width === null ? '' : coerceCssPixelValue(this.width) || DEFAULT_WIDTH;\n }\n }\n\n /** Combines the center and zoom and the other map options into a single object */\n private _combineOptions(): google.maps.MapOptions {\n const options = this._options || {};\n return {\n ...options,\n // It's important that we set **some** kind of `center` and `zoom`, otherwise\n // Google Maps will render a blank rectangle which looks broken.\n center: this._center || options.center || DEFAULT_OPTIONS.center,\n zoom: this._zoom ?? options.zoom ?? DEFAULT_OPTIONS.zoom,\n // Passing in an undefined `mapTypeId` seems to break tile loading\n // so make sure that we have some kind of default (see #22082).\n mapTypeId: this.mapTypeId || options.mapTypeId || DEFAULT_OPTIONS.mapTypeId,\n mapId: this.mapId || options.mapId,\n };\n }\n\n /** Asserts that the map has been initialized. */\n private _assertInitialized(): asserts this is {googleMap: google.maps.Map} {\n if (!this.googleMap && (typeof ngDevMode === 'undefined' || ngDevMode)) {\n throw Error(\n 'Cannot access Google Map information before the API has been initialized. ' +\n 'Please wait for the API to load before trying to interact with it.',\n );\n }\n }\n}\n\nconst cssUnitsPattern = /([A-Za-z%]+)$/;\n\n/** Coerces a value to a CSS pixel value. */\nfunction coerceCssPixelValue(value: any): string {\n if (value == null) {\n return '';\n }\n\n return cssUnitsPattern.test(value) ? value : `${value}px`;\n}\n","/**\n * @license\n * Copyright Google LLC All Rights Reserved.\n *\n * Use of this source code is governed by an MIT-style license that can be\n * found in the LICENSE file at https://angular.dev/license\n */\n\n// Workaround for: https://github.com/bazelbuild/rules_nodejs/issues/1265\n/// <reference types=\"google.maps\" preserve=\"true\" />\n\nimport {Directive, NgZone, OnDestroy, OnInit, inject} from '@angular/core';\n\nimport {GoogleMap} from './google-map/google-map';\n\n@Directive({\n selector: 'map-base-layer',\n exportAs: 'mapBaseLayer',\n})\nexport class MapBaseLayer implements OnInit, OnDestroy {\n protected readonly _map = inject(GoogleMap);\n protected readonly _ngZone = inject(NgZone);\n\n constructor(...args: unknown[]);\n constructor() {}\n\n ngOnInit() {\n if (this._map._isBrowser) {\n this._ngZone.runOutsideAngular(() => {\n this._initializeObject();\n });\n this._assertInitialized();\n this._setMap();\n }\n }\n\n ngOnDestroy() {\n this._unsetMap();\n }\n\n private _assertInitialized() {\n if (!this._map.googleMap) {\n throw Error(\n 'Cannot access Google Map information before the API has been initialized. ' +\n 'Please wait for the API to load before trying to interact with it.',\n );\n }\n }\n\n protected _initializeObject() {}\n protected _setMap() {}\n protected _unsetMap() {}\n}\n","/**\n * @license\n * Copyright Google LLC All Rights Reserved.\n *\n * Use of this source code is governed by an MIT-style license that can be\n * found in the LICENSE file at https://angular.dev/license\n */\n\n// Workaround for: https://github.com/bazelbuild/rules_nodejs/issues/1265\n/// <reference types=\"google.maps\" preserve=\"true\" />\n\nimport {Directive, EventEmitter, NgZone, OnDestroy, OnInit, Output, inject} from '@angular/core';\n\nimport {GoogleMap} from '../google-map/google-map';\n\n/**\n * Angular component that renders a Google Maps Bicycling Layer via the Google Maps JavaScript API.\n *\n * See developers.google.com/maps/documentation/javascript/reference/map#BicyclingLayer\n */\n@Directive({\n selector: 'map-bicycling-layer',\n exportAs: 'mapBicyclingLayer',\n})\nexport class MapBicyclingLayer implements OnInit, OnDestroy {\n private _map = inject(GoogleMap);\n private _zone = inject(NgZone);\n\n /**\n * The underlying google.maps.BicyclingLayer object.\n *\n * See developers.google.com/maps/documentation/javascript/reference/map#BicyclingLayer\n */\n bicyclingLayer?: google.maps.BicyclingLayer;\n\n /** Event emitted when the bicycling layer is initialized. */\n @Output() readonly bicyclingLayerInitialized: EventEmitter<google.maps.BicyclingLayer> =\n new EventEmitter<google.maps.BicyclingLayer>();\n\n ngOnInit(): void {\n if (this._map._isBrowser) {\n if (google.maps.BicyclingLayer && this._map.googleMap) {\n this._initialize(this._map.googleMap, google.maps.BicyclingLayer);\n } else {\n this._zone.runOutsideAngular(() => {\n Promise.all([this._map._resolveMap(), google.maps.importLibrary('maps')]).then(\n ([map, lib]) => {\n this._initialize(map, (lib as google.maps.MapsLibrary).BicyclingLayer);\n },\n );\n });\n }\n }\n }\n\n private _initialize(map: google.maps.Map, layerConstructor: typeof google.maps.BicyclingLayer) {\n this._zone.runOutsideAngular(() => {\n this.bicyclingLayer = new layerConstructor();\n this.bicyclingLayerInitialized.emit(this.bicyclingLayer);\n this._assertLayerInitialized();\n this.bicyclingLayer.setMap(map);\n });\n }\n\n ngOnDestroy() {\n this.bicyclingLayer?.setMap(null);\n }\n\n private _assertLayerInitialized(): asserts this is {bicyclingLayer: google.maps.BicyclingLayer} {\n if (!this.bicyclingLayer) {\n throw Error(\n 'Cannot interact with a Google Map Bicycling Layer before it has been initialized. ' +\n 'Please wait for the Transit Layer to load before trying to interact with it.',\n );\n }\n }\n}\n","/**\n * @license\n * Copyright Google LLC All Rights Reserved.\n *\n * Use of this source code is governed by an MIT-style license that can be\n * found in the LICENSE file at https://angular.dev/license\n */\n\n// Workaround for: https://github.com/bazelbuild/rules_nodejs/issues/1265\n/// <reference types=\"google.maps\" preserve=\"true\" />\n\nimport {\n Directive,\n EventEmitter,\n Input,\n NgZone,\n OnDestroy,\n OnInit,\n Output,\n inject,\n} from '@angular/core';\nimport {BehaviorSubject, combineLatest, Observable, Subject} from 'rxjs';\nimport {map, take, takeUntil} from 'rxjs/operators';\n\nimport {GoogleMap} from '../google-map/google-map';\nimport {MapEventManager} from '../map-event-manager';\n\n/**\n * Angular component that renders a Google Maps Circle via the Google Maps JavaScript API.\n * @see developers.google.com/maps/documentation/javascript/reference/polygon#Circle\n */\n@Directive({\n selector: 'map-circle',\n exportAs: 'mapCircle',\n})\nexport class MapCircle implements OnInit, OnDestroy {\n private readonly _map = inject(GoogleMap);\n private readonly _ngZone = inject(NgZone);\n private _eventManager = new MapEventManager(inject(NgZone));\n private readonly _options = new BehaviorSubject<google.maps.CircleOptions>({});\n private readonly _center = new BehaviorSubject<\n google.maps.LatLng | google.maps.LatLngLiteral | undefined\n >(undefined);\n private readonly _radius = new BehaviorSubject<number | undefined>(undefined);\n private readonly _destroyed = new Subject<void>();\n\n /**\n * Underlying google.maps.Circle object.\n *\n * @see developers.google.com/maps/documentation/javascript/reference/polygon#Circle\n */\n circle?: google.maps.Circle; // initialized in ngOnInit\n\n @Input()\n set options(options: google.maps.CircleOptions) {\n this._options.next(options || {});\n }\n\n @Input()\n set center(center: google.maps.LatLng | google.maps.LatLngLiteral) {\n this._center.next(center);\n }\n\n @Input()\n set radius(radius: number) {\n this._radius.next(radius);\n }\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.center_changed\n */\n @Output() readonly centerChanged: Observable<void> =\n this._eventManager.getLazyEmitter<void>('center_changed');\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.click\n */\n @Output() readonly circleClick: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('click');\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.dblclick\n */\n @Output() readonly circleDblclick: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('dblclick');\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.drag\n */\n @Output() readonly circleDrag: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('drag');\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.dragend\n */\n @Output() readonly circleDragend: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('dragend');\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.dragstart\n */\n @Output() readonly circleDragstart: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('dragstart');\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.mousedown\n */\n @Output() readonly circleMousedown: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('mousedown');\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.mousemove\n */\n @Output() readonly circleMousemove: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('mousemove');\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.mouseout\n */\n @Output() readonly circleMouseout: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('mouseout');\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.mouseover\n */\n @Output() readonly circleMouseover: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('mouseover');\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.mouseup\n */\n @Output() readonly circleMouseup: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('mouseup');\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.radius_changed\n */\n @Output() readonly radiusChanged: Observable<void> =\n this._eventManager.getLazyEmitter<void>('radius_changed');\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.rightclick\n */\n @Output() readonly circleRightclick: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('rightclick');\n\n /** Event emitted when the circle is initialized. */\n @Output() readonly circleInitialized: EventEmitter<google.maps.Circle> =\n new EventEmitter<google.maps.Circle>();\n\n constructor(...args: unknown[]);\n constructor() {}\n\n ngOnInit() {\n if (!this._map._isBrowser) {\n return;\n }\n\n this._combineOptions()\n .pipe(take(1))\n .subscribe(options => {\n if (google.maps.Circle && this._map.googleMap) {\n this._initialize(this._map.googleMap, google.maps.Circle, options);\n } else {\n this._ngZone.runOutsideAngular(() => {\n Promise.all([this._map._resolveMap(), google.maps.importLibrary('maps')]).then(\n ([map, lib]) => {\n this._initialize(map, (lib as google.maps.MapsLibrary).Circle, options);\n },\n );\n });\n }\n });\n }\n\n private _initialize(\n map: google.maps.Map,\n circleConstructor: typeof google.maps.Circle,\n options: google.maps.CircleOptions,\n ) {\n // Create the object outside the zone so its events don't trigger change detection.\n // We'll bring it back in inside the `MapEventManager` only for the events that the\n // user has subscribed to.\n this._ngZone.runOutsideAngular(() => {\n this.circle = new circleConstructor(options);\n this._assertInitialized();\n this.circle.setMap(map);\n this._eventManager.setTarget(this.circle);\n this.circleInitialized.emit(this.circle);\n this._watchForOptionsChanges();\n this._watchForCenterChanges();\n this._watchForRadiusChanges();\n });\n }\n\n ngOnDestroy() {\n this._eventManager.destroy();\n this._destroyed.next();\n this._destroyed.complete();\n this.circle?.setMap(null);\n }\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.getBounds\n */\n getBounds(): google.maps.LatLngBounds | null {\n this._assertInitialized();\n return this.circle.getBounds();\n }\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.getCenter\n */\n getCenter(): google.maps.LatLng | null {\n this._assertInitialized();\n return this.circle.getCenter();\n }\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.getDraggable\n */\n getDraggable(): boolean {\n this._assertInitialized();\n return this.circle.getDraggable();\n }\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.getEditable\n */\n getEditable(): boolean {\n this._assertInitialized();\n return this.circle.getEditable();\n }\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.getRadius\n */\n getRadius(): number {\n this._assertInitialized();\n return this.circle.getRadius();\n }\n\n /**\n * @see\n * developers.google.com/maps/documentation/javascript/reference/polygon#Circle.getVisible\n */\n getVisible(): boolean {\n this._assertInitialized();\n return this.circle.getVisible();\n }\n\n private _combineOptions(): Observable<google.maps.CircleOptions> {\n return combineLatest([this._options, this._center, this._radius]).pipe(\n map(([options, center, radius]) => {\n const combinedOptions: google.maps.CircleOptions = {\n ...options,\n center: center || options.center,\n radius: radius !== undefined ? radius : options.radius,\n };\n return combinedOptions;\n }),\n );\n }\n\n private _watchForOptionsChanges() {\n this._options.pipe(takeUntil(this._destroyed)).subscribe(options => {\n this._assertInitialized();\n this.circle.setOptions(options);\n });\n }\n\n private _watchForCenterChanges() {\n this._center.pipe(takeUntil(this._destroyed)).subscribe(center => {\n if (center) {\n this._assertInitialized();\n this.circle.setCenter(center);\n }\n });\n }\n\n private _watchForRadiusChanges() {\n this._radius.pipe(takeUntil(this._destroyed)).subscribe(radius => {\n if (radius !== undefined) {\n this._assertInitialized();\n this.circle.setRadius(radius);\n }\n });\n }\n\n private _assertInitialized(): asserts this is {circle: google.maps.Circle} {\n if (typeof ngDevMode === 'undefined' || ngDevMode) {\n if (!this.circle) {\n throw Error(\n 'Cannot interact with a Google Map Circle before it has been ' +\n 'initialized. Please wait for the Circle to load before trying to interact with it.',\n );\n }\n }\n }\n}\n","/**\n * @license\n * Copyright Google LLC All Rights Reserved.\n *\n * Use of this source code is governed by an MIT-style license that can be\n * found in the LICENSE file at https://angular.dev/license\n */\n\n// Workaround for: https://github.com/bazelbuild/rules_nodejs/issues/1265\n/// <reference types=\"google.maps\" preserve=\"true\" />\n\nimport {\n Directive,\n EventEmitter,\n Input,\n NgZone,\n OnChanges,\n OnDestroy,\n OnInit,\n Output,\n SimpleChanges,\n inject,\n} from '@angular/core';\nimport {Observable} from 'rxjs';\nimport {GoogleMap} from '../google-map/google-map';\nimport {MapEventManager} from '../map-event-manager';\n\n/**\n * Angular component that renders a Google Maps Directions Renderer via the Google Maps\n * JavaScript API.\n *\n * See developers.google.com/maps/documentation/javascript/reference/directions#DirectionsRenderer\n */\n@Directive({\n selector: 'map-directions-renderer',\n exportAs: 'mapDirectionsRenderer',\n})\nexport class MapDirectionsRenderer implements OnInit, OnChanges, OnDestroy {\n private readonly _googleMap = inject(GoogleMap);\n private _ngZone = inject(NgZone);\n private _eventManager = new MapEventManager(inject(NgZone));\n\n /**\n * See developers.google.com/maps/documentation/javascript/reference/directions\n * #DirectionsRendererOptions.directions\n */\n @Input()\n set directions(directions: google.maps.DirectionsResult) {\n this._directions = directions;\n }\n private _directions: google.maps.DirectionsResult;\n\n /**\n * See developers.google.com/maps/documentation/javascript/reference/directions\n * #DirectionsRendererOptions\n */\n @Input()\n set options(options: google.maps.DirectionsRendererOptions) {\n this._options = options;\n }\n private _options: google.maps.DirectionsRendererOptions;\n\n /**\n * See developers.google.com/maps/documentation/javascript/reference/directions\n * #DirectionsRenderer.directions_changed\n */\n @Output()\n readonly directionsChanged: Observable<void> =\n this._eventManager.getLazyEmitter<void>('directions_changed');\n\n /** Event emitted when the directions renderer is initialized. */\n @Output() readonly directionsRendererInitialized: EventEmitter<google.maps.DirectionsRenderer> =\n new EventEmitter<google.maps.DirectionsRenderer>();\n\n /** The underlying google.maps.DirectionsRenderer object. */\n directionsRenderer?: google.maps.DirectionsRenderer;\n\n constructor(...args: unknown[]);\n constructor() {}\n\n ngOnInit() {\n if (this._googleMap._isBrowser) {\n if (google.maps.DirectionsRenderer && this._googleMap.googleMap) {\n this._initialize(this._googleMap.googleMap, google.maps.DirectionsRenderer);\n } else {\n this._ngZone.runOutsideAngular(() => {\n Promise.all([this._googleMap._resolveMap(), google.maps.importLibrary('routes')]).then(\n ([map, lib]) => {\n this._initialize(map, (lib as google.maps.RoutesLibrary).DirectionsRenderer);\n },\n );\n });\n }\n }\n }\n\n private _initialize(\n map: google.maps.Map,\n rendererConstructor: typeof google.maps.DirectionsRenderer,\n ) {\n // Create the object outside the zone so its events don't trigger change detection.\n // We'll bring it back in inside the `MapEventManager` only for the events that the\n // user has subscribed to.\n this._ngZone.runOutsideAngular(() => {\n this.directionsRenderer = new rendererConstructor(this._combineOptions());\n this._assertInitialized();\n this.directionsRenderer.setMap(map);\n this._eventManager.setTarget(this.directionsRenderer);\n this.directionsRendererInitialized.emit(this.directionsRenderer);\n });\n }\n\n ngOnChanges(changes: SimpleChanges) {\n if (this.directionsRenderer) {\n if (changes['options']) {\n this.directionsRenderer.setOptions(this._combineOptions());\n }\n\n if (changes['directions'] && this._directions !== undefined) {\n this.directionsRenderer.setDirections(this._directions);\n }\n }\n }\n\n ngOnDestroy() {\n this._eventManager.destroy();\n this.directionsRenderer?.setMap(null);\n }\n\n /**\n * See developers.google.com/maps/documentation/javascript/reference/directions\n * #DirectionsRenderer.getDirections\n */\n getDirections(): google.maps.DirectionsResult | null {\n this._assertInitialized();\n return this.directionsRenderer.getDirections();\n }\n\n /**\n * See developers.google.com/maps/documentation/javascript/reference/directions\n * #DirectionsRenderer.getPanel\n */\n getPanel(): Node | null {\n this._assertInitialized();\n return this.directionsRenderer.getPanel();\n }\n\n /**\n * See developers.google.com/maps/documentation/javascript/reference/directions\n * #DirectionsRenderer.getRouteIndex\n */\n getRouteIndex(): number {\n this._assertInitialized();\n return this.directionsRenderer.getRouteIndex();\n }\n\n private _combineOptions(): google.maps.DirectionsRendererOptions {\n const options = this._options || {};\n return {\n ...options,\n directions: this._directions || options.directions,\n map: this._googleMap.googleMap,\n };\n }\n\n private _assertInitialized(): asserts this is {\n directionsRenderer: google.maps.DirectionsRenderer;\n } {\n if (typeof ngDevMode === 'undefined' || ngDevMode) {\n if (!this.directionsRenderer) {\n throw Error(\n 'Cannot interact with a Google Map Directions Renderer before it has been ' +\n 'initialized. Please wait for the Directions Renderer to load before trying ' +\n 'to interact with it.',\n );\n }\n }\n }\n}\n","/**\n * @license\n * Copyright Google LLC All Rights Reserved.\n *\n * Use of this source code is governed by an MIT-style license that can be\n * found in the LICENSE file at https://angular.dev/license\n */\n\n// Workaround for: https://github.com/bazelbuild/rules_nodejs/issues/1265\n/// <reference types=\"google.maps\" preserve=\"true\" />\n\nimport {\n Directive,\n EventEmitter,\n Input,\n NgZone,\n OnDestroy,\n OnInit,\n Output,\n inject,\n} from '@angular/core';\nimport {BehaviorSubject, Observable, Subject} from 'rxjs';\nimport {takeUntil} from 'rxjs/operators';\n\nimport {GoogleMap} from '../google-map/google-map';\nimport {MapEventManager} from '../map-event-manager';\n\n/**\n * Angular component that renders a Google Maps Ground Overlay via the Google Maps JavaScript API.\n *\n * See developers.google.com/maps/documentation/javascript/reference/image-overlay#GroundOverlay\n */\n@Directive({\n selector: 'map-ground-overlay',\n exportAs: 'mapGroundOverlay',\n})\nexport class MapGroundOverlay implements OnInit, OnDestroy {\n private readonly _map = inject(GoogleMap);\n private readonly _ngZone = inject(NgZone);\n private _eventManager = new MapEventManager(inject(NgZone));\n private readonly _opacity = new BehaviorSubject<number>(1);\n private readonly _url = new BehaviorSubject<string>('');\n private readonly _bounds = new BehaviorSubject<\n google.maps.LatLngBounds | google.maps.LatLngBoundsLiteral | undefined\n >(undefined);\n private readonly _destroyed = new Subject<void>();\n private _hasWatchers: boolean;\n\n /**\n * The underlying google.maps.GroundOverlay object.\n *\n * See developers.google.com/maps/documentation/javascript/reference/image-overlay#GroundOverlay\n */\n groundOverlay?: google.maps.GroundOverlay;\n\n /** URL of the image that will be shown in the overlay. */\n @Input()\n set url(url: string) {\n this._url.next(url);\n }\n\n /** Bounds for the overlay. */\n @Input()\n get bounds(): google.maps.LatLngBounds | google.maps.LatLngBoundsLiteral {\n return this._bounds.value!;\n }\n set bounds(bounds: google.maps.LatLngBounds | google.maps.LatLngBoundsLiteral) {\n this._bounds.next(bounds);\n }\n\n /** Whether the overlay is clickable */\n @Input() clickable: boolean = false;\n\n /** Opacity of the overlay. */\n @Input()\n set opacity(opacity: number) {\n this._opacity.next(opacity);\n }\n\n /**\n * See\n * developers.google.com/maps/documentation/javascript/reference/image-overlay#GroundOverlay.click\n */\n @Output() readonly mapClick: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('click');\n\n /**\n * See\n * developers.google.com/maps/documentation/javascript/reference/image-overlay\n * #GroundOverlay.dblclick\n */\n @Output() readonly mapDblclick: Observable<google.maps.MapMouseEvent> =\n this._eventManager.getLazyEmitter<google.maps.MapMouseEvent>('dblclick');\n\n /** Event emitted when the ground overlay is initialized. */\n @Output() readonly groundOverlayInitialized: EventEmitter<google.maps.GroundOverlay> =\n new EventEmitter<google.maps.GroundOverlay>();\n\n constructor(...args: unknown[]);\n constructor() {}\n\n ngOnInit() {\n if (this._map._isBrowser) {\n // The ground overlay setup is slightly different from the other Google Maps objects in that\n // we have to recreate the `GroundOverlay` object whenever the bounds change, because\n // Google Maps doesn't provide an API to update the bounds of an existing overlay.\n this._bounds.pipe(takeUntil(this._destroyed)).subscribe(bounds => {\n if (this.groundOverlay) {\n this.groundOverlay.setMap(null);\n this.groundOverlay = undefined;\n }\n\n if (!bounds) {\n return;\n }\n\n if (google.maps.GroundOverlay && this._map.googleMap) {\n this._initialize(this._map.googleMap, google.maps.GroundOverlay, bounds);\n } else {\n this._ngZone.runOutsideAngular(() => {\n Promise.all([this._map._resolveMap(), google.maps.importLibrary('maps')]).then(\n ([map, lib]) => {\n this._initialize(map, (lib as google.maps.MapsLibrary).GroundOverlay, bounds);\n },\n );\n });\n }\n });\n }\n }\n\n private _initialize(\n map: google.maps.Map,\n overlayConstructor: typeof google.maps.GroundOverlay,\n bounds: google.maps.LatLngBounds | google.maps.LatLngBoundsLiteral,\n ) {\n // Create the object outside the zone so its events don't trigger change detection.\n // We'll bring it back in inside the `MapEventManager` only for the events that the\n // user has subscribed to.\n this._ngZone.runOutsideAngular(() => {\n this.groundOverlay = new overlayConstructor(this._url.getValue(), bounds, {\n clickable: this.clickable,\n opacity: this._opacity.value,\n });\n this._assertInitialized();\n this.groundOverlay.setMap(map);\n this._eventManager.setTarget(this.groundOverlay);\n this.groundOverlayInitialized.emit(this.groundOverlay);\n\n // We only need to set up the watchers once.\n if (!this._hasWatchers) {\n this._hasWatchers = true;\n this._watchForOpacityChanges();\n this._watchForUrlChanges();\n }\n });\n }\n\n ngOnDestroy() {\n this._eventManager.destroy();\n this._destroyed.next();\n this._destroyed.complete();\n this.groundOverlay?.setMap(null);\n }\n\n /**\n * See\n * developers.google.com/maps/documentation/javascript/reference/image-overlay\n * #GroundOverlay.getBounds\n */\n getBounds(): google.maps.LatLngBounds | null {\n this._assertInitialized();\n return this.groundOverlay.getBounds();\n }\n\n /**\n * See\n * developers.google.com/maps/documentation/javascript/reference/image-overlay\n * #GroundOverlay.getOpacity\n */\n getOpacity(): number {\n this._assertInitialized();\n return this.groundOverlay.getOpacity();\n }\n\n /**\n * See\n * developers.google.com/maps/documentation/javascript/reference/image-overlay\n * #GroundOverlay.getUrl\n */\n getUrl(): string {\n this._assertInitialized();\n return this.groundOverlay.