Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- import {Component, Input, ElementRef, ViewChild, ViewChildren, QueryList, NgZone} from '@angular/core';
- import {Content} from 'ionic-angular';
- import {formatDate} from '../../utils/formatDate';
- import {getI18n} from 'get-i18n';
- import immutable from 'immutable';
- import { NgRedux } from 'ng2-redux';
- import { bindActionCreators } from 'redux';
- import { fetchMapSearchResult, clearMapSearchResult } from '../../actions/search/index';
- declare const plugin: any;
- @Component({
- selector: 'google-maps',
- templateUrl: 'template.html',
- })
- export class GoogleMaps {
- @ViewChild('map') mapElement: ElementRef;
- @Input() private keyword: string;
- @Input() private categoryId: string;
- @Input() private initialLocation: any;
- private map: any;
- private products: any;
- private hasNextPage: any;
- private lastActiveBounds: any;
- private selectedProductsList: any;
- private productSliderVisible: boolean;
- public i18n: any;
- public zone: any;
- public unsubscribe: any;
- public clearMapSearchResult: any;
- public fetchMapSearchResult: any;
- constructor(private elementRef: ElementRef, private ngRedux: NgRedux<any>) {
- this.i18n = getI18n('googleMaps');
- this.zone = new NgZone({ enableLongStackTrace: false });
- }
- public ngOnChanges(changes): void {
- if (this.map) {
- console.log('Search keyword changed, should perform new search');
- const bounds = this.map.getVisibleRegion();
- this.clearMapSearchResult();
- this.fetchMapSearchResult(this.keyword, this.categoryId, bounds);
- }
- }
- public ngAfterContentInit(): void {
- this.zone.run(() => {
- this.map = plugin.google.maps.Map.getMap(this.mapElement.nativeElement, {
- controls: {
- compass: false,
- myLocationButton: true
- },
- gestures: {
- scroll: true,
- tilt: true,
- rotate: true,
- zoom: true
- },
- camera : {
- target: this.initialLocation || {lat: 63.1123, lng: 16.3539},
- zoom: this.initialLocation ? 12 : 4
- },
- preferences: {
- zoom: {
- minZoom: 2,
- maxZoom: 18
- },
- building: false
- },
- // styles: [{ 'featureType': 'all', 'elementType': 'labels.text.fill', 'stylers': [{ 'saturation': 36 }, { 'color': '#333333' }, { 'lightness': 40 }] }, { 'featureType': 'all', 'elementType': 'labels.text.stroke', 'stylers': [{ 'visibility': 'on' }, { 'color': '#ffffff' }, { 'lightness': 16 }] }, { 'featureType': 'all', 'elementType': 'labels.icon', 'stylers': [{ 'visibility': 'off' }] }, { 'featureType': 'administrative', 'elementType': 'geometry.fill', 'stylers': [{ 'color': '#fefefe' }, { 'lightness': 20 }] }, { 'featureType': 'administrative', 'elementType': 'geometry.stroke', 'stylers': [{ 'color': '#fefefe' }, { 'lightness': 17 }, { 'weight': 1.2 }] }, { 'featureType': 'landscape', 'elementType': 'geometry', 'stylers': [{ 'color': '#f5f5f5' }, { 'lightness': 20 }] }, { 'featureType': 'poi', 'elementType': 'geometry', 'stylers': [{ 'color': '#f5f5f5' }, { 'lightness': 21 }] }, { 'featureType': 'poi.attraction', 'elementType': 'all', 'stylers': [{ 'visibility': 'on' }] }, { 'featureType': 'poi.park', 'elementType': 'geometry', 'stylers': [{ 'color': '#dedede' }, { 'lightness': 21 }] }, { 'featureType': 'poi.park', 'elementType': 'geometry.fill', 'stylers': [{ 'color': '#e1f1e2' }] }, { 'featureType': 'road.highway', 'elementType': 'geometry.fill', 'stylers': [{ 'color': '#ffffff' }, { 'lightness': 17 }] }, { 'featureType': 'road.highway', 'elementType': 'geometry.stroke', 'stylers': [{ 'color': '#ffffff' }, { 'lightness': 29 }, { 'weight': 0.2 }] }, { 'featureType': 'road.arterial', 'elementType': 'geometry', 'stylers': [{ 'color': '#ffffff' }, { 'lightness': 18 }] }, { 'featureType': 'road.local', 'elementType': 'geometry', 'stylers': [{ 'color': '#ffffff' }, { 'lightness': 16 }] }, { 'featureType': 'transit', 'elementType': 'geometry', 'stylers': [{ 'color': '#f2f2f2' }, { 'lightness': 19 }] }, { 'featureType': 'water', 'elementType': 'geometry', 'stylers': [{ 'color': '#e9e9e9' }, { 'lightness': 17 }] }, { 'featureType': 'water', 'elementType': 'geometry.fill', 'stylers': [{ 'color': '#e4f1f2' }] }]
- });
- this.map.addEventListener(plugin.google.maps.event.MAP_READY, this.onMapReady.bind(this));
- this.map.addEventListener(plugin.google.maps.event.MAP_CLICK, this.onMapClick.bind(this));
- this.map.addEventListener(plugin.google.maps.event.CAMERA_MOVE, this.onMapMove.bind(this));
- });
- }
- public ngOnDestroy(): void {
- this.map.removeEventListener(plugin.google.maps.event.MAP_READY, this.onMapReady);
- this.map.removeEventListener(plugin.google.maps.event.CAMERA_MOVE, this.onMapMove);
- this.map.removeEventListener(plugin.google.maps.event.CAMERA_MOVE_END, this.onMapMoveEnd);
- this.map.removeEventListener(plugin.google.maps.event.MAP_CLICK, this.onMapClick);
- this.map.remove();
- this.unsubscribe();
- this.clearMapSearchResult();
- console.log('map should now be destroyed');
- }
- private plotMapMarkers(products: any) {
- console.log('A search that returned new results was performed, plotting new markers');
- const markers = [];
- products.map(product => {
- const lat = product.getIn(['zipCodeCoordinate', 'latitude']);
- const lng = product.getIn(['zipCodeCoordinate', 'longitude']);
- markers.push({
- position: {
- lat,
- lng
- },
- icon: {
- url: 'assets/img/geomap/map-pin.png',
- size: {
- width: 40,
- height: 40
- }
- },
- disableAutoPan: true,
- productId: product.get('id')
- });
- });
- this.map.clear();
- this.map.addMarkerCluster({
- boundsDraw: false,
- maxZoomLevel: 18,
- markers,
- icons: [
- {
- min: 2,
- url: 'assets/img/geomap/map-pin-zoom.png',
- anchor: { x: 24, y: 24 },
- label: {
- color: 'white',
- fontSize: 10,
- bold: true
- },
- size: {
- width: 64,
- height: 64
- }
- }
- ]
- }, (markerCluster) => {
- markerCluster.on(plugin.google.maps.event.MARKER_CLICK, this.onMarkerClick.bind(this));
- });
- }
- private onMapReady() {
- this.map.addEventListener(plugin.google.maps.event.CAMERA_MOVE_END, this.onMapMoveEnd.bind(this));
- this.zone.run(() => {
- this.unsubscribe = this.ngRedux.connect(
- (state) => this.mapStateToThis(state),
- (state) => this.mapDispatchToThis(state)
- )(this);
- });
- }
- private onMapMoveEnd() {
- this.zone.run(() => {
- const bounds = this.map.getVisibleRegion();
- console.log('CAMERA_MOVE_END');
- if (this.lastActiveBounds) {
- if (!this.hasNextPage && this.lastActiveBounds.contains(bounds.northeast) && this.lastActiveBounds.contains(bounds.southwest)) {
- console.log('User has zoomed in and there is no need to perform a new search');
- } else {
- console.log('Looks like a new location or too many hits were previously returned, will perform new search');
- this.fetchMapSearchResult(this.keyword, this.categoryId, bounds);
- this.lastActiveBounds = bounds;
- }
- } else {
- console.log('initial search');
- this.fetchMapSearchResult(this.keyword, this.categoryId, bounds);
- this.lastActiveBounds = bounds;
- }
- });
- }
- private onMapClick() {
- this.zone.run(() => {
- console.log('clicked on map');
- this.productSliderVisible = false;
- });
- }
- private onMapMove() {
- this.zone.run(() => {
- console.log('Map is moved');
- this.productSliderVisible = false;
- });
- }
- private onMarkerClick(params: any[]) {
- console.log('marker clicked');
- console.log(params); // Only returns the location object
- }
- public mapStateToThis(state): any {
- const status = state.getIn(['mapSearch', 'status']);
- const products = (state.getIn(['mapSearch', 'response', 'products']) || immutable.fromJS({}));
- const hasNextPage = state.getIn(['mapSearch', 'response', 'hasNextPage']);
- if (!immutable.is(this.products, products)) {
- console.log('Got new resulys, should call plotMapMarkers()');
- this.plotMapMarkers(products);
- }
- return {
- status,
- products,
- hasNextPage
- };
- }
- public mapDispatchToThis(dispatch) {
- const actions = { fetchMapSearchResult, clearMapSearchResult };
- return bindActionCreators(actions, dispatch);
- }
- }
Add Comment
Please, Sign In to add comment