@@ -13,7 +13,6 @@ import {
13
13
ChangeDetectionStrategy ,
14
14
Component ,
15
15
ElementRef ,
16
- EventEmitter ,
17
16
Input ,
18
17
OnChanges ,
19
18
OnDestroy ,
@@ -27,6 +26,7 @@ import {
27
26
import { isPlatformBrowser } from '@angular/common' ;
28
27
import { BehaviorSubject , combineLatest , Observable , Subject } from 'rxjs' ;
29
28
import { map , shareReplay , take , takeUntil } from 'rxjs/operators' ;
29
+ import { MapEventManager } from '../map-event-manager' ;
30
30
31
31
interface GoogleMapsWindow extends Window {
32
32
google ?: typeof google ;
@@ -64,6 +64,20 @@ export const DEFAULT_WIDTH = '500px';
64
64
encapsulation : ViewEncapsulation . None ,
65
65
} )
66
66
export class GoogleMap implements OnChanges , OnInit , OnDestroy {
67
+ private _eventManager = new MapEventManager ( ) ;
68
+
69
+ /** Whether we're currently rendering inside a browser. */
70
+ private _isBrowser : boolean ;
71
+ private _googleMapChanges : Observable < google . maps . Map > ;
72
+
73
+ private readonly _options = new BehaviorSubject < google . maps . MapOptions > ( DEFAULT_OPTIONS ) ;
74
+ private readonly _center =
75
+ new BehaviorSubject < google . maps . LatLngLiteral | google . maps . LatLng | undefined > ( undefined ) ;
76
+ private readonly _zoom = new BehaviorSubject < number | undefined > ( undefined ) ;
77
+ private readonly _destroy = new Subject < void > ( ) ;
78
+ private _mapEl : HTMLElement ;
79
+ _googleMap : UpdatedGoogleMap ;
80
+
67
81
@Input ( ) height = DEFAULT_HEIGHT ;
68
82
69
83
@Input ( ) width = DEFAULT_WIDTH ;
@@ -85,125 +99,127 @@ export class GoogleMap implements OnChanges, OnInit, OnDestroy {
85
99
* See
86
100
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.bounds_changed
87
101
*/
88
- @Output ( ) boundsChanged = new EventEmitter < void > ( ) ;
102
+ @Output ( )
103
+ boundsChanged : Observable < void > = this . _eventManager . getLazyEmitter < void > ( 'bounds_changed' ) ;
89
104
90
105
/**
91
106
* See
92
107
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.center_changed
93
108
*/
94
- @Output ( ) centerChanged = new EventEmitter < void > ( ) ;
109
+ @Output ( )
110
+ centerChanged : Observable < void > = this . _eventManager . getLazyEmitter < void > ( 'center_changed' ) ;
95
111
96
112
/**
97
113
* See
98
114
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.click
99
115
*/
100
- @Output ( ) mapClick = new EventEmitter < google . maps . MouseEvent | google . maps . IconMouseEvent > ( ) ;
116
+ @Output ( )
117
+ mapClick : Observable < google . maps . MouseEvent | google . maps . IconMouseEvent > =
118
+ this . _eventManager . getLazyEmitter < google . maps . MouseEvent | google . maps . IconMouseEvent > ( 'click' ) ;
101
119
102
120
/**
103
121
* See
104
122
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.dblclick
105
123
*/
106
- @Output ( ) mapDblclick = new EventEmitter < google . maps . MouseEvent > ( ) ;
124
+ @Output ( )
125
+ mapDblclick : Observable < google . maps . MouseEvent > =
126
+ this . _eventManager . getLazyEmitter < google . maps . MouseEvent > ( 'dblclick' ) ;
107
127
108
128
/**
109
129
* See
110
130
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.drag
111
131
*/
112
- @Output ( ) mapDrag = new EventEmitter < void > ( ) ;
132
+ @Output ( ) mapDrag : Observable < void > = this . _eventManager . getLazyEmitter < void > ( 'drag' ) ;
113
133
114
134
/**
115
135
* See
116
136
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.dragend
117
137
*/
118
- @Output ( ) mapDragend = new EventEmitter < void > ( ) ;
138
+ @Output ( ) mapDragend : Observable < void > = this . _eventManager . getLazyEmitter < void > ( 'dragend' ) ;
119
139
120
140
/**
121
141
* See
122
142
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.dragstart
123
143
*/
124
- @Output ( ) mapDragstart = new EventEmitter < void > ( ) ;
144
+ @Output ( ) mapDragstart : Observable < void > = this . _eventManager . getLazyEmitter < void > ( 'dragstart' ) ;
125
145
126
146
/**
127
147
* See
128
148
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.heading_changed
129
149
*/
130
- @Output ( ) headingChanged = new EventEmitter < void > ( ) ;
150
+ @Output ( )
151
+ headingChanged : Observable < void > = this . _eventManager . getLazyEmitter < void > ( 'heading_changed' ) ;
131
152
132
153
/**
133
154
* See
134
155
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.idle
135
156
*/
136
- @Output ( ) idle = new EventEmitter < void > ( ) ;
157
+ @Output ( ) idle : Observable < void > = this . _eventManager . getLazyEmitter < void > ( 'idle' ) ;
137
158
138
159
/**
139
160
* See
140
161
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.maptypeid_changed
141
162
*/
142
- @Output ( ) maptypeidChanged = new EventEmitter < void > ( ) ;
163
+ @Output ( )
164
+ maptypeidChanged : Observable < void > = this . _eventManager . getLazyEmitter < void > ( 'maptypeid_changed' ) ;
143
165
144
166
/**
145
167
* See
146
168
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.mousemove
147
169
*/
148
- @Output ( ) mapMousemove = new EventEmitter < google . maps . MouseEvent > ( ) ;
170
+ @Output ( )
171
+ mapMousemove : Observable < google . maps . MouseEvent > =
172
+ this . _eventManager . getLazyEmitter < google . maps . MouseEvent > ( 'mousemove' ) ;
149
173
150
174
/**
151
175
* See
152
176
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.mouseout
153
177
*/
154
- @Output ( ) mapMouseout = new EventEmitter < google . maps . MouseEvent > ( ) ;
178
+ @Output ( )
179
+ mapMouseout : Observable < google . maps . MouseEvent > =
180
+ this . _eventManager . getLazyEmitter < google . maps . MouseEvent > ( 'mouseout' ) ;
155
181
156
182
/**
157
183
* See
158
184
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.mouseover
159
185
*/
160
- @Output ( ) mapMouseover = new EventEmitter < google . maps . MouseEvent > ( ) ;
186
+ @Output ( )
187
+ mapMouseover : Observable < google . maps . MouseEvent > =
188
+ this . _eventManager . getLazyEmitter < google . maps . MouseEvent > ( 'mouseover' ) ;
161
189
162
190
/**
163
191
* See
164
192
* developers.google.com/maps/documentation/javascript/reference/map#Map.projection_changed
165
193
*/
166
- @Output ( ) projectionChanged = new EventEmitter < void > ( ) ;
194
+ @Output ( )
195
+ projectionChanged : Observable < void > =
196
+ this . _eventManager . getLazyEmitter < void > ( 'projection_changed' ) ;
167
197
168
198
/**
169
199
* See
170
200
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.rightclick
171
201
*/
172
- @Output ( ) mapRightclick = new EventEmitter < google . maps . MouseEvent > ( ) ;
202
+ @Output ( )
203
+ mapRightclick : Observable < google . maps . MouseEvent > =
204
+ this . _eventManager . getLazyEmitter < google . maps . MouseEvent > ( 'rightclick' ) ;
173
205
174
206
/**
175
207
* See
176
208
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.tilesloaded
177
209
*/
178
- @Output ( ) tilesloaded = new EventEmitter < void > ( ) ;
210
+ @Output ( ) tilesloaded : Observable < void > = this . _eventManager . getLazyEmitter < void > ( 'tilesloaded' ) ;
179
211
180
212
/**
181
213
* See
182
214
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.tilt_changed
183
215
*/
184
- @Output ( ) tiltChanged = new EventEmitter < void > ( ) ;
216
+ @Output ( ) tiltChanged : Observable < void > = this . _eventManager . getLazyEmitter < void > ( 'tilt_changed' ) ;
185
217
186
218
/**
187
219
* See
188
220
* https://developers.google.com/maps/documentation/javascript/reference/map#Map.zoom_changed
189
221
*/
190
- @Output ( ) zoomChanged = new EventEmitter < void > ( ) ;
191
-
192
- private _mapEl : HTMLElement ;
193
- _googleMap : UpdatedGoogleMap ;
194
-
195
- /** Whether we're currently rendering inside a browser. */
196
- private _isBrowser : boolean ;
197
- private _googleMapChanges ! : Observable < google . maps . Map > ;
198
-
199
- private _listeners : google . maps . MapsEventListener [ ] = [ ] ;
200
-
201
- private readonly _options = new BehaviorSubject < google . maps . MapOptions > ( DEFAULT_OPTIONS ) ;
202
- private readonly _center =
203
- new BehaviorSubject < google . maps . LatLngLiteral | google . maps . LatLng | undefined > ( undefined ) ;
204
- private readonly _zoom = new BehaviorSubject < number | undefined > ( undefined ) ;
205
-
206
- private readonly _destroy = new Subject < void > ( ) ;
222
+ @Output ( ) zoomChanged : Observable < void > = this . _eventManager . getLazyEmitter < void > ( 'zoomChanged' ) ;
207
223
208
224
constructor (
209
225
private readonly _elementRef : ElementRef ,
@@ -238,13 +254,10 @@ export class GoogleMap implements OnChanges, OnInit, OnDestroy {
238
254
if ( this . _isBrowser ) {
239
255
this . _mapEl = this . _elementRef . nativeElement . querySelector ( '.map-container' ) ! ;
240
256
this . _setSize ( ) ;
241
-
242
- const combinedOptionsChanges = this . _combineOptions ( ) ;
243
-
244
- this . _googleMapChanges = this . _initializeMap ( combinedOptionsChanges ) ;
257
+ this . _googleMapChanges = this . _initializeMap ( this . _combineOptions ( ) ) ;
245
258
this . _googleMapChanges . subscribe ( ( googleMap : google . maps . Map ) => {
246
259
this . _googleMap = googleMap as UpdatedGoogleMap ;
247
- this . _initializeEventHandlers ( this . _googleMap ) ;
260
+ this . _eventManager . setTarget ( this . _googleMap ) ;
248
261
} ) ;
249
262
250
263
this . _watchForOptionsChanges ( ) ;
@@ -254,9 +267,9 @@ export class GoogleMap implements OnChanges, OnInit, OnDestroy {
254
267
}
255
268
256
269
ngOnDestroy ( ) {
270
+ this . _eventManager . destroy ( ) ;
257
271
this . _destroy . next ( ) ;
258
272
this . _destroy . complete ( ) ;
259
- this . _clearListeners ( ) ;
260
273
}
261
274
262
275
/**
@@ -472,64 +485,7 @@ export class GoogleMap implements OnChanges, OnInit, OnDestroy {
472
485
} ) ;
473
486
}
474
487
475
- private _initializeEventHandlers ( googleMap : UpdatedGoogleMap ) {
476
- // Ensure that we don't leak if called multiple times.
477
- this . _clearListeners ( ) ;
478
-
479
- const eventHandlers = new Map < string , EventEmitter < void > > ( [
480
- [ 'bounds_changed' , this . boundsChanged ] ,
481
- [ 'center_changed' , this . centerChanged ] ,
482
- [ 'drag' , this . mapDrag ] ,
483
- [ 'dragend' , this . mapDragend ] ,
484
- [ 'dragstart' , this . mapDragstart ] ,
485
- [ 'heading_changed' , this . headingChanged ] ,
486
- [ 'idle' , this . idle ] ,
487
- [ 'maptypeid_changed' , this . maptypeidChanged ] ,
488
- [ 'projection_changed' , this . projectionChanged ] ,
489
- [ 'tilesloaded' , this . tilesloaded ] ,
490
- [ 'tilt_changed' , this . tiltChanged ] ,
491
- [ 'zoomChanged' , this . zoomChanged ] ,
492
- ] ) ;
493
- const mouseEventHandlers = new Map < string , EventEmitter < google . maps . MouseEvent > > ( [
494
- [ 'dblclick' , this . mapDblclick ] ,
495
- [ 'mousemove' , this . mapMousemove ] ,
496
- [ 'mouseout' , this . mapMouseout ] ,
497
- [ 'mouseover' , this . mapMouseover ] ,
498
- [ 'rightclick' , this . mapRightclick ] ,
499
- ] ) ;
500
- eventHandlers . forEach ( ( eventHandler : EventEmitter < void > , name : string ) => {
501
- if ( eventHandler . observers . length > 0 ) {
502
- this . _listeners . push ( googleMap . addListener ( name , ( ) => {
503
- eventHandler . emit ( ) ;
504
- } ) ) ;
505
- }
506
- } ) ;
507
- mouseEventHandlers . forEach (
508
- ( eventHandler : EventEmitter < google . maps . MouseEvent > , name : string ) => {
509
- if ( eventHandler . observers . length > 0 ) {
510
- this . _listeners . push (
511
- googleMap . addListener ( name , ( event : google . maps . MouseEvent ) => {
512
- eventHandler . emit ( event ) ;
513
- } ) ) ;
514
- }
515
- } ) ;
516
- if ( this . mapClick . observers . length > 0 ) {
517
- this . _listeners . push ( googleMap . addListener (
518
- 'click' , ( event : google . maps . MouseEvent | google . maps . IconMouseEvent ) => {
519
- this . mapClick . emit ( event ) ;
520
- } ) ) ;
521
- }
522
- }
523
-
524
- /** Clears all currently-registered event listeners. */
525
- private _clearListeners ( ) {
526
- for ( let listener of this . _listeners ) {
527
- listener . remove ( ) ;
528
- }
529
-
530
- this . _listeners = [ ] ;
531
- }
532
-
488
+ /** Asserts that the map has been initialized. */
533
489
private _assertInitialized ( ) {
534
490
if ( ! this . _googleMap ) {
535
491
throw Error ( 'Cannot access Google Map information before the API has been initialized. ' +
0 commit comments