UNPKG

7.9 kBPlain TextView Raw
1import {Directive, EventEmitter, OnChanges, OnDestroy, OnInit, SimpleChange} from '@angular/core';
2import {Subscription} from 'rxjs/Subscription';
3
4import {MouseEvent} from '../map-types';
5import {LatLng, LatLngBounds, LatLngLiteral} from '../services/google-maps-types';
6import {MouseEvent as MapMouseEvent} from '../services/google-maps-types';
7import {CircleManager} from '../services/managers/circle-manager';
8
9@Directive({
10 selector: 'sebm-google-map-circle',
11 inputs: [
12 'latitude', 'longitude', 'clickable', 'draggable: circleDraggable', 'editable', 'fillColor',
13 'fillOpacity', 'radius', 'strokeColor', 'strokeOpacity', 'strokePosition', 'strokeWeight',
14 'visible', 'zIndex'
15 ],
16 outputs: [
17 'centerChange', 'circleClick', 'circleDblClick', 'drag', 'dragEnd', 'dragStart', 'mouseDown',
18 'mouseMove', 'mouseOut', 'mouseOver', 'mouseUp', 'radiusChange', 'rightClick'
19 ]
20})
21export class SebmGoogleMapCircle implements OnInit, OnChanges, OnDestroy {
22 /**
23 * The latitude position of the circle (required).
24 */
25 latitude: number;
26
27 /**
28 * The clickable position of the circle (required).
29 */
30 longitude: number;
31
32 /**
33 * Indicates whether this Circle handles mouse events. Defaults to true.
34 */
35 clickable: boolean = true;
36
37 /**
38 * If set to true, the user can drag this circle over the map. Defaults to false.
39 */
40 draggable: boolean = false;
41
42 /**
43 * If set to true, the user can edit this circle by dragging the control points shown at
44 * the center and around the circumference of the circle. Defaults to false.
45 */
46 editable: boolean = false;
47
48 /**
49 * The fill color. All CSS3 colors are supported except for extended named colors.
50 */
51 fillColor: string;
52
53 /**
54 * The fill opacity between 0.0 and 1.0.
55 */
56 fillOpacity: number;
57
58 /**
59 * The radius in meters on the Earth's surface.
60 */
61 radius: number = 0;
62
63 /**
64 * The stroke color. All CSS3 colors are supported except for extended named colors.
65 */
66 strokeColor: string;
67
68 /**
69 * The stroke opacity between 0.0 and 1.0
70 */
71 strokeOpacity: number;
72
73 /**
74 * The stroke position. Defaults to CENTER.
75 * This property is not supported on Internet Explorer 8 and earlier.
76 */
77 strokePosition: 'CENTER'|'INSIDE'|'OUTSIDE' = 'CENTER';
78
79 /**
80 * The stroke width in pixels.
81 */
82 strokeWeight: number = 0;
83
84 /**
85 * Whether this circle is visible on the map. Defaults to true.
86 */
87 visible: boolean = true;
88
89 /**
90 * The zIndex compared to other polys.
91 */
92 zIndex: number;
93
94 /**
95 * This event is fired when the circle's center is changed.
96 */
97 centerChange: EventEmitter<LatLngLiteral> = new EventEmitter<LatLngLiteral>();
98
99 /**
100 * This event emitter gets emitted when the user clicks on the circle.
101 */
102 circleClick: EventEmitter<MouseEvent> = new EventEmitter<MouseEvent>();
103
104 /**
105 * This event emitter gets emitted when the user clicks on the circle.
106 */
107 circleDblClick: EventEmitter<MouseEvent> = new EventEmitter<MouseEvent>();
108
109 /**
110 * This event is repeatedly fired while the user drags the circle.
111 */
112 drag: EventEmitter<MouseEvent> = new EventEmitter<MouseEvent>();
113
114 /**
115 * This event is fired when the user stops dragging the circle.
116 */
117 dragEnd: EventEmitter<MouseEvent> = new EventEmitter<MouseEvent>();
118
119 /**
120 * This event is fired when the user starts dragging the circle.
121 */
122 dragStart: EventEmitter<MouseEvent> = new EventEmitter<MouseEvent>();
123
124 /**
125 * This event is fired when the DOM mousedown event is fired on the circle.
126 */
127 mouseDown: EventEmitter<MouseEvent> = new EventEmitter<MouseEvent>();
128
129 /**
130 * This event is fired when the DOM mousemove event is fired on the circle.
131 */
132 mouseMove: EventEmitter<MouseEvent> = new EventEmitter<MouseEvent>();
133
134 /**
135 * This event is fired on circle mouseout.
136 */
137 mouseOut: EventEmitter<MouseEvent> = new EventEmitter<MouseEvent>();
138
139 /**
140 * This event is fired on circle mouseover.
141 */
142 mouseOver: EventEmitter<MouseEvent> = new EventEmitter<MouseEvent>();
143
144 /**
145 * This event is fired when the DOM mouseup event is fired on the circle.
146 */
147 mouseUp: EventEmitter<MouseEvent> = new EventEmitter<MouseEvent>();
148
149 /**
150 * This event is fired when the circle's radius is changed.
151 */
152 radiusChange: EventEmitter<number> = new EventEmitter<number>();
153
154 /**
155 * This event is fired when the circle is right-clicked on.
156 */
157 rightClick: EventEmitter<MouseEvent> = new EventEmitter<MouseEvent>();
158
159 private _circleAddedToManager: boolean = false;
160
161 private static _mapOptions: string[] = [
162 'fillColor', 'fillOpacity', 'strokeColor', 'strokeOpacity', 'strokePosition', 'strokeWeight',
163 'visible', 'zIndex'
164 ];
165
166 private _eventSubscriptions: Subscription[] = [];
167
168 constructor(private _manager: CircleManager) {}
169
170 /** @internal */
171 ngOnInit() {
172 this._manager.addCircle(this);
173 this._circleAddedToManager = true;
174 this._registerEventListeners();
175 }
176
177 /** @internal */
178 ngOnChanges(changes: {[key: string]: SimpleChange}) {
179 if (!this._circleAddedToManager) {
180 return;
181 }
182 if (changes['latitude'] || changes['longitude']) {
183 this._manager.setCenter(this);
184 }
185 if (changes['editable']) {
186 this._manager.setEditable(this);
187 }
188 if (changes['draggable']) {
189 this._manager.setDraggable(this);
190 }
191 if (changes['visible']) {
192 this._manager.setVisible(this);
193 }
194 if (changes['radius']) {
195 this._manager.setRadius(this);
196 }
197 this._updateCircleOptionsChanges(changes);
198 }
199
200 private _updateCircleOptionsChanges(changes: {[propName: string]: SimpleChange}) {
201 let options: {[propName: string]: any} = {};
202 let optionKeys =
203 Object.keys(changes).filter(k => SebmGoogleMapCircle._mapOptions.indexOf(k) !== -1);
204 optionKeys.forEach((k) => { options[k] = changes[k].currentValue; });
205 if (optionKeys.length > 0) {
206 this._manager.setOptions(this, options);
207 }
208 }
209
210 private _registerEventListeners() {
211 let events: Map<string, EventEmitter<any>> = new Map<string, EventEmitter<any>>();
212 events.set('center_changed', this.centerChange);
213 events.set('click', this.circleClick);
214 events.set('dblclick', this.circleDblClick);
215 events.set('drag', this.drag);
216 events.set('dragend', this.dragEnd);
217 events.set('dragStart', this.dragStart);
218 events.set('mousedown', this.mouseDown);
219 events.set('mousemove', this.mouseMove);
220 events.set('mouseout', this.mouseOut);
221 events.set('mouseover', this.mouseOver);
222 events.set('mouseup', this.mouseUp);
223 events.set('radius_changed', this.radiusChange);
224 events.set('rightclick', this.rightClick);
225
226 events.forEach((eventEmitter, eventName) => {
227 this._eventSubscriptions.push(
228 this._manager.createEventObservable<MapMouseEvent>(eventName, this).subscribe((value) => {
229 switch (eventName) {
230 case 'radius_changed':
231 this._manager.getRadius(this).then((radius) => eventEmitter.emit(radius));
232 break;
233 case 'center_changed':
234 this._manager.getCenter(this).then(
235 (center) =>
236 eventEmitter.emit(<LatLngLiteral>{lat: center.lat(), lng: center.lng()}));
237 break;
238 default:
239 eventEmitter.emit(
240 <MouseEvent>{coords: {lat: value.latLng.lat(), lng: value.latLng.lng()}});
241 }
242 }));
243 });
244 }
245
246 /** @internal */
247 ngOnDestroy() {
248 this._eventSubscriptions.forEach(function(s: Subscription) { s.unsubscribe(); });
249 this._eventSubscriptions = null;
250 this._manager.removeCircle(this);
251 }
252
253 /**
254 * Gets the LatLngBounds of this Circle.
255 */
256 getBounds(): Promise<LatLngBounds> { return this._manager.getBounds(this); }
257
258 getCenter(): Promise<LatLng> { return this._manager.getCenter(this); }
259}
260
\No newline at end of file