Integrate Google Maps to your Address Form

Do you have an address form on your website? What do you do with it? Collecting address details of users who may be your potential customer? alright. In this article, I am gonna introduce a simple mapping interface with which you can collect geolocation of your users, as they type their address.  To be more precise, we are gonna embed a map by Google Maps next to the address form. This embedded map will zoom into the address typed by the user. The user can move the marker on the map to mark their location. 

VIEW DEMO

That’s very similar to dynamic geocoding. But the only difference in this approach is we are involving users in the process (by allowing them to mark their own location).

Embedding Google Maps next to your address form to collect geolocation

The complete HTML code is as below.

<html lang="en">
<head>
	<meta charset="utf-8">
	<meta http-equiv="X-UA-Compatible" content="IE=edge">
	<meta name="viewport" content="width=device-width, initial-scale=1">
	<meta name="description" content="">
	<meta name="author" content="">
	<meta http-equiv="content-type" content="text/html; charset=utf-8">
	<title>New customer Registration - bind 2.0 | Paperman</title>
	
	<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.2/css/bootstrap.min.css">
	<script type="text/javascript" src="http://maps.google.com/maps/api/js?sensor=false"></script>
	<script type="text/javascript">
	
    function initialize_map() {
       geocoder = new google.maps.Geocoder();
       var myOptions = {
                   zoom: 2,
                   center: new google.maps.LatLng(13.288828765662416, 80.945261001586914),
                   mapTypeControl: true,
                   mapTypeControlOptions: {style: google.maps.MapTypeControlStyle.DROPDOWN_MENU},
                   navigationControl: true,
                   mapTypeId: google.maps.MapTypeId.ROADMAP
             };
				

				
				
        map = new google.maps.Map(document.getElementById("map_canvas"), myOptions);
	   
	   	   // initialize marker
		   
			var marker = new google.maps.Marker({
				position: map.getCenter(),
				draggable: true,
				map: map
			});
			
			// intercept map and marker movements
			google.maps.event.addListener(map, "idle", function() {
				marker.setPosition(map.getCenter());
				
				var latitude = map.getCenter().lat().toFixed(6);
				var longitude = map.getCenter().lng().toFixed(6);
				document.getElementById("latitude").value = latitude;
				document.getElementById("longitude").value = longitude;
				google.maps.event.trigger(map, "resize");
			});
			google.maps.event.addListener(marker, "dragend", function(mapEvent) {
				map.panTo(mapEvent.latLng);
			});

	   
	   findAddress("New York");
    }
	
function findAddress(address) {
	if ((address != '') && geocoder) {
		geocoder.geocode( { 'address': address}, function(results, status) {
			if (status == google.maps.GeocoderStatus.OK) {
				if (status != google.maps.GeocoderStatus.ZERO_RESULTS) {
					if (results && results[0]
						&& results[0].geometry && results[0].geometry.viewport)
						map.fitBounds(results[0].geometry.viewport);
				} else {
					alert("No results found");
				}
			} else {
				alert("Geocode was not successful for the following reason: " + status);
			}
		});
	}
}	
	
</script>
</head>
<body onload="initialize_map()">
	<div class="col-md-12">
		<div class="col-md-6">
			<h1 class="text-center" >Enter your Address</h1>
			<form class="form-horizontal">
				<div class="form-group">
					<label for="country_name" class="col-sm-2 control-label">Country</label>
					<div class="col-sm-10">
						<input type="text" class="form-control" id="country_name" placeholder="Country">
					</div>
				</div>
				
				<div class="form-group">
					<label for="state" class="col-sm-2 control-label">State</label>
					<div class="col-sm-10">
						<input type="text" class="form-control" id="state" placeholder="State">
					</div>
				</div>

				<div class="form-group">
					<label for="city" class="col-sm-2 control-label">City</label>
					<div class="col-sm-10">
						<input type="text" class="form-control" id="city" placeholder="City">
					</div>
				</div>

				<div class="form-group">
					<label for="area" class="col-sm-2 control-label">Area</label>
					<div class="col-sm-10">
						<input type="text" class="form-control" id="area" placeholder="Area">
					</div>
				</div>
				
				<div class="form-group">
					<label for="street_name" class="col-sm-2 control-label">Street Name</label>
					<div class="col-sm-10">
						<input type="text" class="form-control" id="street_name" placeholder="Street Name">
					</div>
				</div>				
				
				
				
			</form>
		</div>
		<div class="col-md-6">
			<h1 class="text-center">Mark your Location</h1>
			<div id="map_canvas" style="width:100%;height:70%;">
			</div>
			<!-- Text boxes to show lat long values -->
			<div class="input-group col-md-6 pull-left">
				<span class="input-group-addon">Latitude</span>
				<input type="text" id="latitude" class="form-control">
			</div>
			<div class="input-group col-md-6 pull-left">
				<span class="input-group-addon" >Longitude</span>
				<input type="text" class="form-control" id="longitude">
			</div>

			
		
		</div>		
	</div>
	<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/2.1.4/jquery.min.js"></script>
	<script src="https://maxcdn.bootstrapcdn.com/bootstrap/2.3.2/js/bootstrap.min.js"></script>
	<script type="text/javascript">
	$( document ).ready(function() {
		$( "#country_name" ).blur(function() {
			var address = $("#country_name").val();
			findAddress(address);
		});
		$( "#state" ).blur(function() {
			var address = $("#country_name").val()+' '+$("#state").val();
			findAddress(address);
		});
		
		$( "#city" ).blur(function() {
			var address = $("#city").val()+' '+$("#state").val()+' '+$("#country_name").val();
			findAddress(address);
		});

		$( "#area" ).blur(function() {
			var address = $("#area").val()+' '+$("#city").val()+' '+$("#state").val()+' '+$("#country_name").val();
			findAddress(address);
		});

		$( "#street_name" ).blur(function() {
			var address = $("#street_name").val()+' '+$("#area").val()+' '+$("#city").val()+' '+$("#state").val()+' '+$("#country_name").val();
			findAddress(address);
		});		
		
		
	});
	</script>
</body>
</html>

How it works

  1. The initialize_map function is used initialize the map with options specified in myOptions object.
  2. An instance of google.maps.Map() is created. This object named map will be used henceforth in the application to control the behaviour of the map.
  3. An instance of google.maps.Marker() is created. The marker object is what is the red colored movable thing you see on the map.
  4. 	google.maps.event.addListener(map, "idle", function() {
    				marker.setPosition(map.getCenter());
    				
    				var latitude = map.getCenter().lat().toFixed(6);
    				var longitude = map.getCenter().lng().toFixed(6);
    				document.getElementById("latitude").value = latitude;
    				document.getElementById("longitude").value = longitude;
    				google.maps.event.trigger(map, "resize");
    			});
    

    When you complete moving the map, it comes to “idle” state. This calls the anonymous function that centers the map in the canvas and sets the new latitude and the longitude values in the appropriate text boxes below.

  5. Similarly when you move the marker and place it, the “dragend” event is triggered, the map centers itself. Then the “idle” event is triggers and the above function is called again.
  6. The findAddress() function zooms the map to the area passed to it.
  7. Whenever a user completes filling any one of the text boxes, the findAddress function is called by onblur event with the text entered in the current text field and previous fields.

Advantages of this approach over conventional geocoding

You might think, why do this when we can actually query the Google Maps Geocoding API with the address after the form is submitted. But I’m telling you from my experience, Geocoding is not so reliable (at least in countries where a lot of street names and area names are yet to be mapped). And the google maps geocoding API only returns the latitude longitude of the closest known address. That means the geocoding response may be “APPROXIMATE”.

To prove this, I just queried the Google Maps Geocoding API with the address of a very popular location in Chennai, India.

Google Maps Geocoding API response approximate

You can also have a look at it at https://maps.googleapis.com/maps/api/geocode/json?address=Panagal%20Park%20T%20Nagar%20Chennai%20Tamil%20Nadu%20India

The above JSON response clearly shows that the response geocode location type is “APPROXIMATE”, although the geocode is right in this particular case. More than 50% the times I queried the API, the returned geocode was for a location 1KM – 15KM away from the actual intended response.

 

Note:

  1. Don’t make it mandatory for users to mark their location. Give options like “I prefer not to mark my location”.
  2. Add to the site’s privacy policy that your site collects geolocation and how it is used.

I will soon write an article on how you can collect geolocation using device’s location sensor such as GPS.

ALSO READ  5 Best JSON Online Editor Tools

2 Comments

  1. ijaz July 12, 2015
  2. Tomek August 24, 2015

Leave a Reply