From b62e4f5b5f51087d032fb716b6e1d02e2570470b Mon Sep 17 00:00:00 2001 From: Ben Vars Date: Fri, 28 Jul 2017 11:34:57 -0400 Subject: [PATCH 1/5] added drawing library and got basic box zoom working --- src/google_map.js | 76 ++++++++++++++++++++++++-- src/utils/loaders/google_map_loader.js | 2 +- 2 files changed, 72 insertions(+), 6 deletions(-) diff --git a/src/google_map.js b/src/google_map.js index 6acf687f..cc268953 100644 --- a/src/google_map.js +++ b/src/google_map.js @@ -1,5 +1,4 @@ -import React, { Component } from 'react'; -import PropTypes from 'prop-types'; +import React, { PropTypes, Component } from 'react'; import ReactDOM from 'react-dom'; import shallowEqual from 'fbjs/lib/shallowEqual'; @@ -53,14 +52,14 @@ export default class GoogleMap extends Component { apiKey: PropTypes.string, bootstrapURLKeys: PropTypes.any, - defaultCenter: PropTypes.oneOfType([ + defaultCenter: React.PropTypes.oneOfType([ PropTypes.array, PropTypes.shape({ lat: PropTypes.number, lng: PropTypes.number, }), ]), - center: PropTypes.oneOfType([ + center: React.PropTypes.oneOfType([ PropTypes.array, PropTypes.shape({ lat: PropTypes.number, @@ -96,6 +95,8 @@ export default class GoogleMap extends Component { layerTypes: PropTypes.arrayOf(PropTypes.string), // ['TransitLayer', 'TrafficLayer'] geoJsonUrls: PropTypes.arrayOf(PropTypes.string), // [url1, url2] geoJsonFeatures: PropTypes.object, // { key: json, key2: json2} + zoomBoxMode: PropTypes.bool, + mapMode: PropTypes.string, polylines: PropTypes.array, polygons: PropTypes.array, circles: PropTypes.array, @@ -161,6 +162,8 @@ export default class GoogleMap extends Component { this.geoJsonFeatureDict = {}; this.geoJsonRendered = false; + this.zoomBoxMode = false; + this.mapMode = "DARK_MODE"; this.polylines = []; this.polygons = []; this.circles = []; @@ -374,6 +377,70 @@ export default class GoogleMap extends Component { } } } + if (nextProps.zoomBoxMode) { + // add drawingManager for boxZoom + const drawingManager = new this.maps_.drawing.DrawingManager(); + if (nextProps.mapMode === "DARK_MODE") { + drawingManager.setOptions({ + drawingMode : google.maps.drawing.OverlayType.RECTANGLE, + drawingControl : false, // hides control bar + rectangleOptions : { + strokeColor : '#00C2FF', + strokeWeight : 1, + fillColor : '#00C2FF', + fillOpacity : 0.1, + } + }); + } else { + drawingManager.setOptions({ + drawingMode : google.maps.drawing.OverlayType.RECTANGLE, + drawingControl : false, // hides control bar + rectangleOptions : { + strokeColor : '#FFFFFF', + strokeWeight : 1, + fillColor : '#FFFFFF', + fillOpacity : 0.1, + } + }); + } + + // Loading the drawing Tool in the Map. + drawingManager.setMap(this.map_); + const map = this.map_; + + // listen for rectangle to be drawn + this.maps_.event.addListener(drawingManager, 'rectanglecomplete', function(event) { + // turn off drawCursor + drawingManager.setMap(null); + + const mapBounds = map.getBounds(); + const mapHeight = mapBounds.getNorthEast().lat() - mapBounds.getSouthWest().lat(); + const mapWidth = mapBounds.getNorthEast().lng() - mapBounds.getSouthWest().lng(); + + const rectBounds = event.getBounds(); + const rectHeight = rectBounds.getNorthEast().lat() - rectBounds.getSouthWest().lat(); + const rectWidth = rectBounds.getNorthEast().lng() - rectBounds.getSouthWest().lng(); + + // calc how much to zoom + const widthZoom = mapWidth/rectWidth; + const heightZoom = mapHeight/rectHeight; + + // apply new zoomLevel and center map + let newZoom; + if (heightZoom < widthZoom) { + newZoom = Math.floor(Math.log2(heightZoom)); + } else { + newZoom = Math.floor(Math.log2(widthZoom)); + } + if (newZoom > 0) { + map.setZoom(map.getZoom() + newZoom); + } + map.setCenter(event.getBounds().getCenter()); + + // remove rectangle + event.setMap(null); + }); + } if (this.props.polylines !== nextProps.polylines) { this.polylines.map(polyline => polyline.setMap(null)); if (!nextProps.polylines) { @@ -687,7 +754,6 @@ export default class GoogleMap extends Component { overlay.setMap(map); - if (this.props.polylines) { this.polylines = this.props.polylines.map(polylineConfig => { const polyline = new this.maps_.Polyline(polylineConfig); diff --git a/src/utils/loaders/google_map_loader.js b/src/utils/loaders/google_map_loader.js index 80692c92..0cda49b2 100644 --- a/src/utils/loaders/google_map_loader.js +++ b/src/utils/loaders/google_map_loader.js @@ -59,7 +59,7 @@ export default function googleMapLoader(bootstrapURLKeys) { ); $script_( - `https://maps.googleapis.com/maps/api/js?callback=_$_google_map_initialize_$_${queryString}`, + `https://maps.googleapis.com/maps/api/js?callback=_$_google_map_initialize_$_${queryString}&libraries=drawing`, () => typeof window.google === 'undefined' && reject(new Error('google map initialization error (not loaded)')) From 21027e7c744ffe63e7061e5dd93f08cb4f7a8c24 Mon Sep 17 00:00:00 2001 From: Ben Vars Date: Thu, 17 Aug 2017 10:47:59 -0400 Subject: [PATCH 2/5] enable box zoom using the google maps drawing manager --- src/google_map.js | 94 +++++++++++++++++++++++++++-------------------- 1 file changed, 55 insertions(+), 39 deletions(-) diff --git a/src/google_map.js b/src/google_map.js index cc268953..49f3a964 100644 --- a/src/google_map.js +++ b/src/google_map.js @@ -95,6 +95,7 @@ export default class GoogleMap extends Component { layerTypes: PropTypes.arrayOf(PropTypes.string), // ['TransitLayer', 'TrafficLayer'] geoJsonUrls: PropTypes.arrayOf(PropTypes.string), // [url1, url2] geoJsonFeatures: PropTypes.object, // { key: json, key2: json2} + googleZoom: PropTypes.number, zoomBoxMode: PropTypes.bool, mapMode: PropTypes.string, polylines: PropTypes.array, @@ -168,6 +169,8 @@ export default class GoogleMap extends Component { this.polygons = []; this.circles = []; + this.drawingManager_ = null; + if (process.env.NODE_ENV !== 'production') { if (this.props.apiKey) { console.warn('GoogleMap: ' + // eslint-disable-line no-console @@ -201,6 +204,7 @@ export default class GoogleMap extends Component { this.state = { overlayCreated: false, + drawingManagerCreated: false }; } @@ -379,9 +383,51 @@ export default class GoogleMap extends Component { } if (nextProps.zoomBoxMode) { // add drawingManager for boxZoom - const drawingManager = new this.maps_.drawing.DrawingManager(); + if (!this.state.drawingManagerCreated) { + this.setState({ drawingManagerCreated: true }); + this.drawingManager_ = new this.maps_.drawing.DrawingManager(); + + const map = this.map_; + const this_ = this; + + // listen for rectangle to be drawn + this.maps_.event.addListener(this_.drawingManager_, 'rectanglecomplete', function(event) { + // turn off drawCursor + this_.drawingManager_.setMap(null); + this_.drawingManager_ = null; + this_.setState({ drawingManagerCreated: false }); + + const mapBounds = map.getBounds(); + const mapHeight = mapBounds.getNorthEast().lat() - mapBounds.getSouthWest().lat(); + const mapWidth = mapBounds.getNorthEast().lng() - mapBounds.getSouthWest().lng(); + + const rectBounds = event.getBounds(); + const rectHeight = rectBounds.getNorthEast().lat() - rectBounds.getSouthWest().lat(); + const rectWidth = rectBounds.getNorthEast().lng() - rectBounds.getSouthWest().lng(); + + // calc how much to zoom + const widthZoom = mapWidth/rectWidth; + const heightZoom = mapHeight/rectHeight; + + // apply new zoomLevel and center map + let newZoom; + if (heightZoom < widthZoom) { + newZoom = Math.floor(Math.log2(heightZoom)); + } else { + newZoom = Math.floor(Math.log2(widthZoom)); + } + if (newZoom > 0) { + map.setZoom(map.getZoom() + newZoom); + } + map.setCenter(event.getBounds().getCenter()); + + // remove rectangle + event.setMap(null); + }); + } + // Update style based on the map mode if (nextProps.mapMode === "DARK_MODE") { - drawingManager.setOptions({ + this.drawingManager_.setOptions({ drawingMode : google.maps.drawing.OverlayType.RECTANGLE, drawingControl : false, // hides control bar rectangleOptions : { @@ -392,7 +438,7 @@ export default class GoogleMap extends Component { } }); } else { - drawingManager.setOptions({ + this.drawingManager_.setOptions({ drawingMode : google.maps.drawing.OverlayType.RECTANGLE, drawingControl : false, // hides control bar rectangleOptions : { @@ -403,43 +449,13 @@ export default class GoogleMap extends Component { } }); } - // Loading the drawing Tool in the Map. - drawingManager.setMap(this.map_); - const map = this.map_; - - // listen for rectangle to be drawn - this.maps_.event.addListener(drawingManager, 'rectanglecomplete', function(event) { - // turn off drawCursor - drawingManager.setMap(null); - - const mapBounds = map.getBounds(); - const mapHeight = mapBounds.getNorthEast().lat() - mapBounds.getSouthWest().lat(); - const mapWidth = mapBounds.getNorthEast().lng() - mapBounds.getSouthWest().lng(); - - const rectBounds = event.getBounds(); - const rectHeight = rectBounds.getNorthEast().lat() - rectBounds.getSouthWest().lat(); - const rectWidth = rectBounds.getNorthEast().lng() - rectBounds.getSouthWest().lng(); - - // calc how much to zoom - const widthZoom = mapWidth/rectWidth; - const heightZoom = mapHeight/rectHeight; - - // apply new zoomLevel and center map - let newZoom; - if (heightZoom < widthZoom) { - newZoom = Math.floor(Math.log2(heightZoom)); - } else { - newZoom = Math.floor(Math.log2(widthZoom)); - } - if (newZoom > 0) { - map.setZoom(map.getZoom() + newZoom); - } - map.setCenter(event.getBounds().getCenter()); - - // remove rectangle - event.setMap(null); - }); + this.drawingManager_.setMap(this.map_); + } else if (this.state.drawingManagerCreated) { + // turn off drawing if zoomBoxMode is false and were currently drawing + this.drawingManager_.setMap(null); + this.drawingManager_ = null; + this.setState({ drawingManagerCreated: false }); } if (this.props.polylines !== nextProps.polylines) { this.polylines.map(polyline => polyline.setMap(null)); From b01a5e533ac7b3ba212f6f44fc4f7460af727631 Mon Sep 17 00:00:00 2001 From: Ben Vars Date: Thu, 17 Aug 2017 16:30:07 -0400 Subject: [PATCH 3/5] fixed bug where rectangle would stop drawing after a second --- src/google_map.js | 148 +++++++++++++++++++++++++--------------------- 1 file changed, 79 insertions(+), 69 deletions(-) diff --git a/src/google_map.js b/src/google_map.js index 49f3a964..a5070ed6 100644 --- a/src/google_map.js +++ b/src/google_map.js @@ -382,79 +382,40 @@ export default class GoogleMap extends Component { } } if (nextProps.zoomBoxMode) { - // add drawingManager for boxZoom - if (!this.state.drawingManagerCreated) { - this.setState({ drawingManagerCreated: true }); - this.drawingManager_ = new this.maps_.drawing.DrawingManager(); - - const map = this.map_; - const this_ = this; - - // listen for rectangle to be drawn - this.maps_.event.addListener(this_.drawingManager_, 'rectanglecomplete', function(event) { - // turn off drawCursor - this_.drawingManager_.setMap(null); - this_.drawingManager_ = null; - this_.setState({ drawingManagerCreated: false }); - - const mapBounds = map.getBounds(); - const mapHeight = mapBounds.getNorthEast().lat() - mapBounds.getSouthWest().lat(); - const mapWidth = mapBounds.getNorthEast().lng() - mapBounds.getSouthWest().lng(); - - const rectBounds = event.getBounds(); - const rectHeight = rectBounds.getNorthEast().lat() - rectBounds.getSouthWest().lat(); - const rectWidth = rectBounds.getNorthEast().lng() - rectBounds.getSouthWest().lng(); - - // calc how much to zoom - const widthZoom = mapWidth/rectWidth; - const heightZoom = mapHeight/rectHeight; - - // apply new zoomLevel and center map - let newZoom; - if (heightZoom < widthZoom) { - newZoom = Math.floor(Math.log2(heightZoom)); - } else { - newZoom = Math.floor(Math.log2(widthZoom)); - } - if (newZoom > 0) { - map.setZoom(map.getZoom() + newZoom); - } - map.setCenter(event.getBounds().getCenter()); - - // remove rectangle - event.setMap(null); - }); + // Update style based on the map mode only on change + if (this.props.mapMode !== nextProps.mapMode) { + if (nextProps.mapMode === "DARK_MODE") { + this.drawingManager_.setOptions({ + rectangleOptions: { + strokeColor: '#00C2FF', + strokeWeight: 1, + fillColor: '#00C2FF', + fillOpacity: 0.1, + } + }); + } else { + this.drawingManager_.setOptions({ + rectangleOptions: { + strokeColor: '#FFFFFF', + strokeWeight: 1, + fillColor: '#FFFFFF', + fillOpacity: 0.1, + } + }); + } } - // Update style based on the map mode - if (nextProps.mapMode === "DARK_MODE") { - this.drawingManager_.setOptions({ - drawingMode : google.maps.drawing.OverlayType.RECTANGLE, - drawingControl : false, // hides control bar - rectangleOptions : { - strokeColor : '#00C2FF', - strokeWeight : 1, - fillColor : '#00C2FF', - fillOpacity : 0.1, - } - }); - } else { + // turn on rectangle drawingManager for boxZoom + if (!this.state.drawingManagerCreated) { this.drawingManager_.setOptions({ - drawingMode : google.maps.drawing.OverlayType.RECTANGLE, - drawingControl : false, // hides control bar - rectangleOptions : { - strokeColor : '#FFFFFF', - strokeWeight : 1, - fillColor : '#FFFFFF', - fillOpacity : 0.1, - } + drawingMode: google.maps.drawing.OverlayType.RECTANGLE }); + this.setState({ drawingManagerCreated: true }); } - // Loading the drawing Tool in the Map. - this.drawingManager_.setMap(this.map_); } else if (this.state.drawingManagerCreated) { - // turn off drawing if zoomBoxMode is false and were currently drawing - this.drawingManager_.setMap(null); - this.drawingManager_ = null; + // turn off drawing if zoomBoxMode is false and you were currently drawing + this.drawingManager_.setOptions({ + drawingMode : null + }); this.setState({ drawingManagerCreated: false }); } if (this.props.polylines !== nextProps.polylines) { @@ -689,11 +650,24 @@ export default class GoogleMap extends Component { mapOptions.minZoom = this._checkMinZoom(mapOptions.minZoom, minZoom); const map = new maps.Map(ReactDOM.findDOMNode(this.refs.google_map_dom), mapOptions); - //console.log('map init OMGO OMG OM G'); + // console.log('map init OMGO OMG OM G'); this.map_ = map; this.maps_ = maps; + this.drawingManager_ = new this.maps_.drawing.DrawingManager(); + this.drawingManager_.setOptions({ + drawingMode: null, + drawingControl: false, // hides control bar + rectangleOptions : { + strokeColor: '#00C2FF', + strokeWeight: 1, + fillColor: '#00C2FF', + fillOpacity: 0.1, + } + }); + this.drawingManager_.setMap(this.map_); + this._setLayers(this.props.layerTypes); // render in overlay @@ -795,6 +769,42 @@ export default class GoogleMap extends Component { }); } + // listen for rectangle to be drawn + maps.event.addListener(this.drawingManager_, 'rectanglecomplete', function(event) { + // turn of draw + this_.drawingManager_.setOptions({ + drawingMode: null, + }); + this_.setState({ drawingManagerCreated: false }); + + const mapBounds = map.getBounds(); + const mapHeight = mapBounds.getNorthEast().lat() - mapBounds.getSouthWest().lat(); + const mapWidth = mapBounds.getNorthEast().lng() - mapBounds.getSouthWest().lng(); + + const rectBounds = event.getBounds(); + const rectHeight = rectBounds.getNorthEast().lat() - rectBounds.getSouthWest().lat(); + const rectWidth = rectBounds.getNorthEast().lng() - rectBounds.getSouthWest().lng(); + + // calc how much to zoom + const widthZoom = mapWidth/rectWidth; + const heightZoom = mapHeight/rectHeight; + + // apply new zoomLevel and center map + let newZoom; + if (heightZoom < widthZoom) { + newZoom = Math.floor(Math.log2(heightZoom)); + } else { + newZoom = Math.floor(Math.log2(widthZoom)); + } + if (newZoom > 0) { + map.setZoom(map.getZoom() + newZoom); + } + map.setCenter(event.getBounds().getCenter()); + + // remove rectangle + event.setMap(null); + }); + maps.event.addListener(map, 'zoom_changed', () => { // recalc position at zoom start if (this_.geoService_.getZoom() !== map.getZoom()) { From 69988bcad68bfe178cb52f67d610e57ab82ded70 Mon Sep 17 00:00:00 2001 From: Ben Vars Date: Thu, 17 Aug 2017 17:29:11 -0400 Subject: [PATCH 4/5] version bump --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index 55e1ecab..e480c6ad 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "google-map-react-mark43", - "version": "0.21.11", + "version": "0.22.0", "description": "isomorphic google map react component, allows render react components on the google map", "main": "lib/index", "scripts": { From d784ebbe242aab103a439d5d98b7512ee538ec27 Mon Sep 17 00:00:00 2001 From: Ben Vars Date: Thu, 17 Aug 2017 17:41:07 -0400 Subject: [PATCH 5/5] style --- src/google_map.js | 26 ++++++++++++-------------- 1 file changed, 12 insertions(+), 14 deletions(-) diff --git a/src/google_map.js b/src/google_map.js index a5070ed6..f826f107 100644 --- a/src/google_map.js +++ b/src/google_map.js @@ -164,7 +164,7 @@ export default class GoogleMap extends Component { this.geoJsonRendered = false; this.zoomBoxMode = false; - this.mapMode = "DARK_MODE"; + this.mapMode = 'DARK_MODE'; this.polylines = []; this.polygons = []; this.circles = []; @@ -243,7 +243,6 @@ export default class GoogleMap extends Component { } } - componentWillReceiveProps(nextProps) { if (process.env.NODE_ENV !== 'production') { if (this.props.defaultCenter !== nextProps.defaultCenter) { @@ -384,13 +383,13 @@ export default class GoogleMap extends Component { if (nextProps.zoomBoxMode) { // Update style based on the map mode only on change if (this.props.mapMode !== nextProps.mapMode) { - if (nextProps.mapMode === "DARK_MODE") { + if (nextProps.mapMode === 'DARK_MODE') { this.drawingManager_.setOptions({ rectangleOptions: { strokeColor: '#00C2FF', strokeWeight: 1, fillColor: '#00C2FF', - fillOpacity: 0.1, + fillOpacity: 0.1 } }); } else { @@ -399,7 +398,7 @@ export default class GoogleMap extends Component { strokeColor: '#FFFFFF', strokeWeight: 1, fillColor: '#FFFFFF', - fillOpacity: 0.1, + fillOpacity: 0.1 } }); } @@ -414,7 +413,7 @@ export default class GoogleMap extends Component { } else if (this.state.drawingManagerCreated) { // turn off drawing if zoomBoxMode is false and you were currently drawing this.drawingManager_.setOptions({ - drawingMode : null + drawingMode: null }); this.setState({ drawingManagerCreated: false }); } @@ -650,7 +649,6 @@ export default class GoogleMap extends Component { mapOptions.minZoom = this._checkMinZoom(mapOptions.minZoom, minZoom); const map = new maps.Map(ReactDOM.findDOMNode(this.refs.google_map_dom), mapOptions); - // console.log('map init OMGO OMG OM G'); this.map_ = map; this.maps_ = maps; @@ -659,7 +657,7 @@ export default class GoogleMap extends Component { this.drawingManager_.setOptions({ drawingMode: null, drawingControl: false, // hides control bar - rectangleOptions : { + rectangleOptions: { strokeColor: '#00C2FF', strokeWeight: 1, fillColor: '#00C2FF', @@ -770,13 +768,13 @@ export default class GoogleMap extends Component { } // listen for rectangle to be drawn - maps.event.addListener(this.drawingManager_, 'rectanglecomplete', function(event) { + maps.event.addListener(this.drawingManager_, 'rectanglecomplete', event => { // turn of draw this_.drawingManager_.setOptions({ drawingMode: null, }); this_.setState({ drawingManagerCreated: false }); - + const mapBounds = map.getBounds(); const mapHeight = mapBounds.getNorthEast().lat() - mapBounds.getSouthWest().lat(); const mapWidth = mapBounds.getNorthEast().lng() - mapBounds.getSouthWest().lng(); @@ -786,9 +784,9 @@ export default class GoogleMap extends Component { const rectWidth = rectBounds.getNorthEast().lng() - rectBounds.getSouthWest().lng(); // calc how much to zoom - const widthZoom = mapWidth/rectWidth; - const heightZoom = mapHeight/rectHeight; - + const widthZoom = mapWidth / rectWidth; + const heightZoom = mapHeight / rectHeight; + // apply new zoomLevel and center map let newZoom; if (heightZoom < widthZoom) { @@ -800,7 +798,7 @@ export default class GoogleMap extends Component { map.setZoom(map.getZoom() + newZoom); } map.setCenter(event.getBounds().getCenter()); - + // remove rectangle event.setMap(null); });