Hello Everyone, has been a long time since i wrote my last blog :(.
So i am back with some helpful tips that might help someone.So lets quickly jump to different topics to customise google maps and how to use it in the way we want.Let start -
2. Moreover, what if you want to check if the location selected from the autocomplete are within a state or a region.The below code bounds the users search based on bounds object and then return true or false, if its within the bound or outside of it.
To start with, firstly you need to define a bounding box or bounds, which is a box containing your location/state/region/area...any area on earth :).You must provide NorthEast and SouthWest coordinates to create a bound object.Now, you can try the json responses on the google maps documentation here and pass on the required location /state name to get NE/SW coordinates.
Then, once you have your bounding box defined, you can use the contains method, which returns true/false if the selected address is not within the box.Here's the code -
//this is the NE/SW coodinates for Maharashtra, one of the state in India
var southWest = new google.maps.LatLng(15.6024121,72.659363);
var northEast = new google.maps.LatLng(22.028441,80.890924);
///HERE, i define my bounding box using NE/SW coordinates
var bounds = new google.maps.LatLngBounds(southWest,northEast);
//i will bind the bounds with my input field
var input = document.getElementById('geocomplete_and_load');
//obviously, i need the options too
var options = {
bounds: bounds,
componentRestrictions: {country: 'in'},
types: ["geocode", "establishment"]};
}
/// here , now i have binded all the settings with my input field
var autocomplete = new google.maps.places.Autocomplete(input, options);
//LIFE SAVER :), check if location is within the state or not
if (bounds.contains(place.geometry.location)) {
console.log("========Hurray, the selected place lies within Maharashtra");
} else {
console.log("========Oops, the state is outside of Maharashtra");
}
3. Using markerCluster.js - google map library, along with rails(yeah, i know we all love it).
Now clustering of markers(where all the markers are grouped into one cluster/marker)is something like the image below - .
This awwwwsome javascript will group the nearby latlng and then combine it into one.You can read more about it on the google api page
So its obvious, you need to pass an array of markers(which requires latlng too)to the cluster api.Now i have implemented this using rails json and then i pass the json to the api.
The below code is self-explanatory with comments added wherever necessary.
//Firstly, get the json.- either from controller/ model(your choice 👍)
##my model - using Geocoder gem enabled to store latitude/longitude.
@products = Product.all_available_products
##we need the latlng to create dynamic markers and then pass those markers to the api.
@products_json = @products.map do |h|
{ :id => h.id, :latitude=>h.address.latitude, :longitude=>h.address.longitude}
end
//Then, pass the json structured object to the view, so in the view its like this -
<%= javascript_tag do%>
window.show_map_nearbys= <%=raw @products_json.to_json %>;
<%end%>
//Most important part - in js, play around with the json values by iterating them and then using the marker cluster.
//array to store infowindows(because you need to show something when you click on the marker), lat, lng
var locations = [];
//array to store markers
var gmarkers = [];
//just a variable to be used to define marker dynamically before pushing it to gmarkers above
var markers =[];
////FIRSTLY, loop around the json and create infowindows - to show on click of the markers, you may just add a simple title, thats it.
$.each(show_map_nearbys, function(index) {
var info = '<div class="infowindowContainer pad0" style="border:none;overflow:hidden;" >' +
'<div class="thumbnail pad0">'+
'<p class="viewed_count_show_page_infowindow">'+
'<span class="fa fa-eye marR5"></span>'+
'Viewed '+show_map_nearbys[index]['page_views_count']+ ' time(s)' +
'</p>'+
//add more dynamic details
'</div>';
locations.push({['lat']: show_map_nearbys[index]['latitude'], ['lng']: show_map_nearbys[index]['longitude'], ['info']: info});
});//each loop ends
//create google map infowindow object
var infoWindow = new google.maps.InfoWindow({ maxWidth: 400 });
//create map object with default settings of location/zoom
var map = new google.maps.Map(document.getElementById('show_map'), {
zoom: 10 ,
center: {lat: show_map_nearbys[0]['latitude'], lng: show_map_nearbys[0]['longitude']}
});
//use the variable to create individual marker object using latlng.You may remove the icon
var markers = locations.map(function(location, i) {
var marker = new google.maps.Marker({
position: location,
//copying as it from the documentation
icon: new google.maps.MarkerImage("http://chart.apis.google.com/chart?chst=d_map_pin_letter&chld="+first_letter+"|5c5cd6|ffffff&ext=.png", new google.maps.Size(24, 32));
});
//add onClick listener on each marker to show infowindow on click and bind the infowindow with the marker
google.maps.event.addListener(marker, 'click', function(evt) {
infoWindow.setContent(location.info);
infoWindow.open(map, marker);
})
//get all markers binded with their infowindows respectively
gmarkers.push(marker);
return marker;
});
// Add a marker clusterer to manage the markers.
//markeraCluster is a global object available after including the markerClusterer.js script on your page
var markerCluster = new MarkerClusterer(map, markers, {imagePath: 'https://developers.google.com/maps/documentation/javascript/examples/markerclusterer/m'});
Hope this helps someone.Happy coding.
So i am back with some helpful tips that might help someone.So lets quickly jump to different topics to customise google maps and how to use it in the way we want.Let start -
- Customise Google Places Autocomplete, so that it can only provide place nearby or relevant instead of global suggestions.Its simple, just use strictBounds
var options ={///all options in English language: 'en-US',///IMP -> LIFE SAVER :)strictBounds: true,//limit only to searching of places in INDIA ONLYcomponentRestrictions: { country: "IN" }}
And then pass the options, along with the input field to the Autocomplete api.
var input = document.getElementById('find_locations');
var autocomplete = new google.maps.places.Autocomplete(input, options);
2. Moreover, what if you want to check if the location selected from the autocomplete are within a state or a region.The below code bounds the users search based on bounds object and then return true or false, if its within the bound or outside of it.
To start with, firstly you need to define a bounding box or bounds, which is a box containing your location/state/region/area...any area on earth :).You must provide NorthEast and SouthWest coordinates to create a bound object.Now, you can try the json responses on the google maps documentation here and pass on the required location /state name to get NE/SW coordinates.
Then, once you have your bounding box defined, you can use the contains method, which returns true/false if the selected address is not within the box.Here's the code -
//this is the NE/SW coodinates for Maharashtra, one of the state in India
var southWest = new google.maps.LatLng(15.6024121,72.659363);
var northEast = new google.maps.LatLng(22.028441,80.890924);
///HERE, i define my bounding box using NE/SW coordinates
var bounds = new google.maps.LatLngBounds(southWest,northEast);
//i will bind the bounds with my input field
var input = document.getElementById('geocomplete_and_load');
//obviously, i need the options too
var options = {
bounds: bounds,
componentRestrictions: {country: 'in'},
types: ["geocode", "establishment"]};
}
/// here , now i have binded all the settings with my input field
var autocomplete = new google.maps.places.Autocomplete(input, options);
//LIFE SAVER :), check if location is within the state or not
if (bounds.contains(place.geometry.location)) {
console.log("========Hurray, the selected place lies within Maharashtra");
} else {
console.log("========Oops, the state is outside of Maharashtra");
}
3. Using markerCluster.js - google map library, along with rails(yeah, i know we all love it).
Now clustering of markers(where all the markers are grouped into one cluster/marker)is something like the image below - .
This awwwwsome javascript will group the nearby latlng and then combine it into one.You can read more about it on the google api page
So its obvious, you need to pass an array of markers(which requires latlng too)to the cluster api.Now i have implemented this using rails json and then i pass the json to the api.
The below code is self-explanatory with comments added wherever necessary.
//Firstly, get the json.- either from controller/ model(your choice 👍)
##my model - using Geocoder gem enabled to store latitude/longitude.
@products = Product.all_available_products
##we need the latlng to create dynamic markers and then pass those markers to the api.
@products_json = @products.map do |h|
{ :id => h.id, :latitude=>h.address.latitude, :longitude=>h.address.longitude}
end
//Then, pass the json structured object to the view, so in the view its like this -
<%= javascript_tag do%>
window.show_map_nearbys= <%=raw @products_json.to_json %>;
<%end%>
//Most important part - in js, play around with the json values by iterating them and then using the marker cluster.
//array to store infowindows(because you need to show something when you click on the marker), lat, lng
var locations = [];
//array to store markers
var gmarkers = [];
//just a variable to be used to define marker dynamically before pushing it to gmarkers above
var markers =[];
////FIRSTLY, loop around the json and create infowindows - to show on click of the markers, you may just add a simple title, thats it.
$.each(show_map_nearbys, function(index) {
var info = '<div class="infowindowContainer pad0" style="border:none;overflow:hidden;" >' +
'<div class="thumbnail pad0">'+
'<p class="viewed_count_show_page_infowindow">'+
'<span class="fa fa-eye marR5"></span>'+
'Viewed '+show_map_nearbys[index]['page_views_count']+ ' time(s)' +
'</p>'+
//add more dynamic details
'</div>';
locations.push({['lat']: show_map_nearbys[index]['latitude'], ['lng']: show_map_nearbys[index]['longitude'], ['info']: info});
});//each loop ends
//create google map infowindow object
var infoWindow = new google.maps.InfoWindow({ maxWidth: 400 });
//create map object with default settings of location/zoom
var map = new google.maps.Map(document.getElementById('show_map'), {
zoom: 10 ,
center: {lat: show_map_nearbys[0]['latitude'], lng: show_map_nearbys[0]['longitude']}
});
//use the variable to create individual marker object using latlng.You may remove the icon
var markers = locations.map(function(location, i) {
var marker = new google.maps.Marker({
position: location,
//copying as it from the documentation
icon: new google.maps.MarkerImage("http://chart.apis.google.com/chart?chst=d_map_pin_letter&chld="+first_letter+"|5c5cd6|ffffff&ext=.png", new google.maps.Size(24, 32));
});
//add onClick listener on each marker to show infowindow on click and bind the infowindow with the marker
google.maps.event.addListener(marker, 'click', function(evt) {
infoWindow.setContent(location.info);
infoWindow.open(map, marker);
})
//get all markers binded with their infowindows respectively
gmarkers.push(marker);
return marker;
});
// Add a marker clusterer to manage the markers.
//markeraCluster is a global object available after including the markerClusterer.js script on your page
var markerCluster = new MarkerClusterer(map, markers, {imagePath: 'https://developers.google.com/maps/documentation/javascript/examples/markerclusterer/m'});
Hope this helps someone.Happy coding.
Comments