In brief, I want to combine these two topics:
How to add an image to InfoWindow of marker in google maps v3?
Google Maps JS API v3 - Simple Multiple Marker Example
I have my location data stored in a database and it is retrieved as an array. I want to place a marker and infowindow for each of the x amount of locations in the database. One of fields contains an Image and I want to include this in the infoWindow content.
Here is where I am so far:
Php:
// Create connection
$con=mysqli_connect("*******","*******","*******","tests");
// Check connection
if (mysqli_connect_errno($con))
{
echo "Failed to connect to MySQL: " . mysqli_connect_error();
}
$result = mysqli_query($con,"SELECT Name, Latitude, Longitude, Image FROM locate_coords");
while($row = mysqli_fetch_array($result))
{
$users[]= $row;
}
Javascript function initialize():
<?php
$js_array = json_encode($users);
echo "var locations = ". $js_array . ";\n";
?>
var styles = [
{
stylers: [
{ hue: "#00ffe6" },
{ saturation: -20 },
]
},{
featureType: "road",
elementType: "geometry",
stylers: [
{ lightness: 100 },
{ visibility: "simplified" },
]
},{
featureType: "road",
elementType: "labels",
stylers: [
{ visibility: "off" }
]
}
];
var styledMap = new google.maps.StyledMapType(styles,
{name: "Styled Map"});
var mapProp = {
zoom: 12,
center: new google.maps.LatLng(51.508742,-0.120850),
mapTypeControlOptions: {
mapTypeIds: [google.maps.MapTypeId.ROADMAP, 'map_style']
}
};
var map = new google.maps.Map(document.getElementById('map-canvas'),
mapProp);
var infowindow = new google.maps.InfoWindow();
var marker, i;
for (i = 0; i < locations.length; i++) {
//var container = document.getElementById("photo");
//var img = new Image();
//img.src = '
//container.appendChild(img);
marker = new google.maps.Marker({
position: new google.maps.LatLng(locations[i][1], locations[i][2]),
map: map
});
google.maps.event.addListener(marker, 'click', (function(marker, i) {
return function() {
//infowindow.setContent('<img id=="photo">' + locations[i][0]);
infowindow.setContent('<img src=/uploads/'. locations[i][3]'>' + locations[i][0]);
infowindow.open(map, marker);
}
})(marker, i));
}
map.mapTypes.set('map_style', styledMap);
map.setMapTypeId('map_style');
}
google.maps.event.addDomListener(window, 'load', initialize);
Putting a normal image url in works nicely, but as soon as I try putting an array value, the map doesn't want to load! At this point, I really could do with a sane head to tell me what to do :-(..
There is a typo in the line
infowindow.setContent('<img src=/uploads/'. locations[i][3]'>' + locations[i][0]);
. is not the concatenation operator and between locations[i][3]'>' there is no concatenation operator at all. The correct code would be:
infowindow.setContent('<img src=/uploads/' + locations[i][3] + '>' + locations[i][0]);
Related
I'm trying to add a marker to my google map within my HTML project. The map centres on the exact coordinates I like and is perfect except the marker I've added doesn't show up at all. I've followed the documentation but to no success.
var google;
function init() {
var myLatlng = new google.maps.LatLng(40.69847032728747, -73.9514422416687);
var mapOptions = {
// How zoomed in you want the map to start at (always required)
zoom: 7,
// The latitude and longitude to center the map (always required)
center: myLatlng,
// How you would like to style the map.
scrollwheel: false,
styles: [
{
"featureType": "administrative.country",
"elementType": "geometry",
"stylers": [
{
"visibility": "simplified"
},
{
"hue": "#ff0000"
}
]
}
]
};
I'm using a div with id="map" seen below
var mapElement = document.getElementById('map');
var map = new google.maps.Map(mapElement, mapOptions);
var addresses = ['New York'];
for (var x = 0; x < addresses.length; x++) {
$.getJSON('http://maps.googleapis.com/maps/api/geocode/json?address='+addresses[x]+'&sensor=false', null, function (data) {
var p = data.results[0].geometry.location
var latlng = new google.maps.LatLng(p.lat, p.lng);
new google.maps.Marker({
position: latlng,
map: map,
title: 'NY'
});
});
}
}
google.maps.event.addDomListener(window, 'load', init);
You have to add your API key.
$.getJSON('http://maps.googleapis.com/maps/api/geocode/json?address='+addresses[x]+'&sensor=false&key=ADD_YOUR_API_KEY', null, function (data) {
Check this out!
https://developers.google.com/maps/documentation/geocoding/intro#GeocodingResponses
I'm not able to zoom to a particular area/location in Google maps which has multiple Map Pointers. At present it automatically centers the map covering all locations. But what I need is to zoom to a particular location upon opening the webpage. Here is my code,
<script>
jQuery(function ($) {
// Asynchronously Load the map API
var script = document.createElement('script');
script.src = "//maps.googleapis.com/maps/api/js?key=AIzaSyA157quXbUlHHgm4wJJxzD49MivKgPSil8&sensor=false&callback=initialize";
document.body.appendChild(script);
});
function initialize() {
locations = <?php echo json_encode($sl_select_obj) ?>;
markerdata = JSON.parse('<?php echo json_encode($locations_data) ?>');
var map;
var bounds = new google.maps.LatLngBounds();
var mapOptions = {
mapTypeId: 'roadmap',
};
// Display a map on the page
map = new google.maps.Map(document.getElementById("map_canvas"), mapOptions);
map.setTilt(45);
// Multiple Markers''
// $info='';
var markers = locations;
<?php
$total = count($locations_data);
$markerinfo = '';
$c = 0;
foreach ($locations_data as $key => $info):
if ($c != $total):
$markerinfo .="['<div class=\"info_content\"><h2>" . $info['loctitle'] . "</h2><h3>" . $info['site'] . "</h3><h3>View Full Office Details</h3></div>'],";
else:
$markerinfo .="['<div class=\"info_content\"><h2>" . $info['loctitle'] . "</h2><h3>" . $info['site'] . "</h3><h3>View Full Office Details</h3></div>']";
endif;
$c++;
endforeach;
?>
// Info Window Content
var infoWindowContent = [<?php echo $markerinfo; ?>]; //markerdata;
// Display multiple markers on a map
var infoWindow = new google.maps.InfoWindow(), marker, i;
// Loop through our array of markers & place each one on the map
for (i = 0; i < markers.length; i++) {
var position = new google.maps.LatLng(markers[i]["lat"], markers[i]["long"]);
bounds.extend(position);
marker = new google.maps.Marker({
position: position,
map: map,
title: markers[i]["address"],
icon: '<?php bloginfo('template_directory'); ?>/images/venue-direct-icon.png'
});
// Allow each marker to have an info window
google.maps.event.addListener(marker, 'click', (function (marker, i) {
return function () {
infoWindow.setContent(infoWindowContent[i][0]);
infoWindow.open(map, marker);
}
})(marker, i));
// Automatically center the map fitting all markers on the screen
map.fitBounds(bounds);
}
// Override our map zoom level once our fitBounds function runs (Make sure it only runs once)
var boundsListener = google.maps.event.addListener((map), 'bounds_changed', function (event) {
this.setZoom(7);
google.maps.event.removeListener(boundsListener);
});
map.fitBounds(markerBounds);
}
Try to add the "center" option like this:
var mapOptions = {
center: new google.maps.LatLng(51.5287718, -0.2416803),
mapTypeId: 'roadmap',
zoom: 15,
draggable: map_draggable,
scrollwheel: map_scrollwheel
};
EDIT: To help you this is a code similar that I use in my project: multiple positions, center on the first if only one, else I use google autocenter for all positions.
jQuery( document ).ready( function( $ ) {
if($(window).width()>991){
var map_draggable = true;
var map_scrollwheel = false;
} else {
var map_draggable = false;
var map_scrollwheel = false;
}
var offices = [];
$('#map-google-container')
.find('.hidden')
.each(function(){
offices[offices.length] =
{
"latitude":$(this).attr('latitude'),
"longitude":$(this).attr('longitude'),
"content":$(this).attr('content')
};
});
var mapOptions = {
zoom: 6,
center: new google.maps.LatLng(offices[0].latitude, offices[0].longitude),
draggable: map_draggable,
scrollwheel: map_scrollwheel,
mapTypeId: google.maps.MapTypeId.ROADMAP,
mapTypeControl: false,
panControl: true
};
var map = new google.maps.Map(document.getElementById('map-google'), mapOptions);
var map_styles = [
{
featureType: "all",
stylers: [
{ hue: "#F69200" },
{ saturation: -50 }
]
},{
featureType: "water",
stylers: [
{ color: "#efefef" }
]
}
];
map.setOptions({styles: map_styles});
var image = '/include/images/marker.png';
var bounds = new google.maps.LatLngBounds();
for (i = 0; i < offices.length; i++)
{
var content = offices[i].content;
var marker = new google.maps.Marker({
position: new google.maps.LatLng(offices[i].latitude, offices[i].longitude),
map: map,
icon: image,
animation: google.maps.Animation.DROP,
title: content
});
bounds.extend(marker.position);
var infowindow = new google.maps.InfoWindow();
google.maps.event.addListener(marker,'click', (function(marker,content,infowindow){
return function() {
infowindow.setContent(content);
infowindow.open(map,marker);
};
})(marker,content,infowindow));
}
if (offices.length > 1) { map.fitBounds(bounds); }
});
In my project I have to list all the offices and show a unique map with all of them. So in the HTML I put the information of all offices (hidden for the user). In JavaScript I loop through these properties and populate the map.
Hope it helps
Yes, I can able to find the solution, for those who are facing this similar issue may find it helpful,
var map_center_position = new google.maps.LatLng(34.0059657 ,-118.4440441);
bounds.extend(map_center_position);
map.fitBounds(bounds);
I am trying to implement google maps by acf and everything works like a charm except one thing. I would like to have main icon different than other and icon will be uploaded by acf. Thanks for any hint.
Here is bunch of my code:
<script type="text/javascript">
var locations = [<?php while( $wp_query->have_posts() ){
$wp_query->the_post();
$location = get_field('carte_google');?>
['<?php the_title(); ?> <br/> <?php the_field('map_description'); ?> <?php the_field('pin'); ?>', <?php echo $location['lat']; ?>, <?php echo $location['lng'];?>, <?php $NUM++ ?>],<?php } ?> ];
var map = new google.maps.Map(document.getElementById('map'), {
zoom: 3,
center: new google.maps.LatLng(45.7830954, 24.0697979),
mapTypeId: google.maps.MapTypeId.ROADMAP
});
var infowindow = new google.maps.InfoWindow();
var image = {
url: 'probably here should be image from acf',
};
var marker, i;
for (i = 0; i < locations.length; i++) {
marker = new google.maps.Marker({
position: new google.maps.LatLng(locations[i][1], locations[i][2]),
map: map,
icon: image,
animation: google.maps.Animation.BOUNCE,
});
google.maps.event.addListener(marker, 'click', (function(marker, i) {
return function() {
infowindow.setContent(locations[i][0]);
infowindow.open(map, marker);
}
})(marker, i));
}
Thank You for Your help in advance.
There are 2 possible solutions.
1 - Create categories and set the post with these categories (this is useful to when you has many places in map with the same icon)
2 - Create a custom field to place the icon
I will describe both.
By creating categories you can easily to link many locations with the same icon. I did it once and used the categories images plugin. When in loop, just identify the post category and retrieve image for it, something like:
for (i = 0; i < locations.length; i++) {
var image = '<?php echo z_taxonomy_image($term_id); ?>';
// the $term_id is the category from the current post in loop that
// you need to retrieve
marker = new google.maps.Marker({
position: new google.maps.LatLng(locations[i][1], locations[i][2]),
map: map,
icon: image,
animation: google.maps.Animation.BOUNCE,
});
With the second solution you must to create an Advanced Custom Field for some post/page type, this custom field will be of type: "image". Set the return to be the image URI, not an object as is the default option. For this example, I suppose that you will create a field named map_icon. In your question I can see you already have a custom field named map_description, for this same ACF configuration just add the image custom field. And to show this image you can do this:
for (i = 0; i < locations.length; i++) {
var image = '<?php the_field('map_icon', $post_id); ?>';
// the $post_id is the current post in loop
marker = new google.maps.Marker({
position: new google.maps.LatLng(locations[i][1], locations[i][2]),
map: map,
icon: image,
animation: google.maps.Animation.BOUNCE,
});
Has a lot of time since I did this, but looking in some references like ACF and the Categories Images plugin these 2 solutions must to work to you.
At least I figure out how to display different icon for one post(Head-quarter - pin) and other for the rest projects. Here is code I used and it work for me. Maybe it will be useful for someone else.
I am ordering here post from the oldest to the newest and then I am adding prefix + image.png to the oldest post.
Thank You for Yours posts
<script src="http://maps.google.com/maps/api/js?sensor=false"
type="text/javascript"></script>
<?php
$args = array(
'post_type' => 'projects',
'posts_per_page' => -1,
'order' => 'ASC'
);
// query
$wp_query = new WP_Query( $args );
$NUM = 0;
?>
<div id="map"></div>
<script type="text/javascript">
var locations = [<?php while( $wp_query->have_posts() ){
$wp_query->the_post();
$location = get_field('carte_google');?>
['<?php the_title(); ?> <br/> <?php the_field('map_description'); ?>', <?php echo $location['lat']; ?>, <?php echo $location['lng'];?>, <?php $NUM++ ?>],
];
var stylowanie = [ { "featureType": "water", "stylers": [ { "visibility": "on" }, { "color": "#46bcec" } ] },{ "featureType": "landscape", "stylers": [ { "color": "#f2f2f2" } ] } ];
var map = new google.maps.Map(document.getElementById('map'), {
zoom: Math.ceil(Math.log2($(window).width())) - 8,
minZoom: Math.ceil(Math.log2($(window).width())) - 8,
maxZoom: Math.ceil(Math.log2($(window).width())) - 8,
center: new google.maps.LatLng(45.7830954, 24.0697979),
mapTypeId: google.maps.MapTypeId.ROADMAP,
disableDefaultUI: true,
styles: stylowanie,
});
var infowindow = new google.maps.InfoWindow();
var iconURLPrefix = 'http://link.to.your.images.folder/images';
var icons = [
iconURLPrefix + 'image1.png',
iconURLPrefix + 'image2.png',
]
var iconsLength = icons.length;
var marker, i;
var iconCounter = 0;
for (i = 0; i < locations.length; i++) {
marker = new google.maps.Marker({
position: new google.maps.LatLng(locations[i][1], locations[i][2]),
map: map,
icon: icons[iconCounter],
animation: google.maps.Animation.DROP,
});
google.maps.event.addListener(marker, 'click', (function(marker, i) {
return function() {
infowindow.setContent(locations[i][0]);
infowindow.open(map, marker);
}
})(marker, i));
// We only have a limited number of possible icon colors, so we may have to restart the counter
if(iconCounter > iconsLength) {
iconCounter = 0;
}
else{
iconCounter = 1;
}
}
I hope it will work for You as well
I am using Google Maps API. I want to assign colors to some countries.
To do that, i have to get each country boundaries to be able to draw polygon. So, i'm using FusionTables. For every countries, I do FusionTables query to get the layer and then set the map. Here what i have done.
var countryArray = new Array();
var nodeArray = new Array();
var companyArray = new Array();
var locationsArray = new Array();
function plotMarker() {
var rootMarker = locationsArray[companyArray.indexOf(rootCompany)];
var latlng = new google.maps.LatLng(0, 0);
var myStyle = [
{
featureType: "all",
elementType: "labels",
stylers: [
{
visibility: "off" }
]
}
];
map = new google.maps.Map(document.getElementById("map_canvas"), {
mapTypeControlOptions: {
mapTypeIds: ['mystyle', google.maps.MapTypeId.ROADMAP, google.maps.MapTypeId.TERRAIN]
},
center: latlng,
zoom: 2,
mapTypeId: 'mystyle'
});
map.mapTypes.set('mystyle', new google.maps.StyledMapType(myStyle, { name: 'My Style' }));
for (var i = 0; i < locationsArray.length; i++) {
if (locationsArray[i] != undefined) {
var latitude = locationsArray[i].lat() + verDiff;
var longitude = locationsArray[i].lng() + horDiff;
var newLatlng = new google.maps.LatLng(latitude, longitude);
var ftoptions = {
query: {
from: '419167',
select: 'kml_4326',
where: "sovereignt = '"+countryArray[i]+"'"
},
suppressInfoWindows:true,
styles: [
{
polygonOptions: {
fillColor:'#0040FF',
fillOpacity:0.7
}
}
]
};
var layer = new google.maps.FusionTablesLayer(ftoptions);
layer.setMap(map);
}
}
}
But, why does the style only work for the first country? I wonder if the queries are not successfully performed for all countries or just there's something wrong with the style? Any helps would be appreciated.
A map can only have 1 styled FusionTablesLayer, the styles of the other layers will be ignored.
Create a single FusionTablesLayer and select multiple sovereignt's via a IN()-condition
I've been playing around with the Google Maps API lately, and I have links that perform a JS function. This JS function partially works, on click it centers the map to the pin coords, but I also want it to show the infowindow; Everything works except opening the infowindow. Any help would be amazing! the code is a little cluttered with PHP / WP functions.
<script type="text/javascript">
var map;
var infowindow;
var marker;
function initialize() {
var styles = [
{
stylers: [
{ hue: "#c09c3d" },
]
},{
featureType: "road",
elementType: "geometry",
stylers: [
{ lightness: 50 },
{ visibility: "simplified" }
]
}
];
infowindow = new google.maps.InfoWindow({
maxWidth: 275
});
var mapOptions = {
zoom: 4,
center: new google.maps.LatLng(<?php echo $centerCoords; ?>),
styles: styles,
mapTypeId: google.maps.MapTypeId.ROADMAP
};
map = new google.maps.Map(document.getElementById('googleMap'), mapOptions);
var image = '<?php echo get_template_directory_uri(); ?>/images/icon_marker.png';
var locations = [
<?php
// LOOP ARGUMENTS
$args = array( 'post_type' => 'cbd_dealers', 'posts_per_page' => -1, 'orderby' => 'menu_order', 'order' => 'ASC' ); // -1 Shows ALL Posts
$loop = new WP_Query( $args );
while ( $loop->have_posts() ) : $loop->the_post();
// CUSTOM CONTENT
$dealerStreetAddress = get_post_meta($post->ID,"dealerStreetAddress",true);
$dealerCity = get_post_meta($post->ID,"dealerCity",true);
$dealerState = get_post_meta($post->ID,"dealerState",true);
$dealerZipCode = get_post_meta($post->ID,"dealerZipCode",true);
$dealerCoords = get_post_meta($post->ID,"dealerCoords",true);
$dealerPhoneNumber = get_post_meta($post->ID,"dealerPhoneNumber",true);
$dealerLink = get_post_meta($post->ID,"dealerLink",true);
?>
{
latlng : new google.maps.LatLng<?php echo $dealerCoords; ?>,
info: '<style>a{color:#000000 !important;}a:hover{color:#DCB54F !important;}</style><strong style="line-height:25px;display:block;width:230px;"><?php the_title(); ?></strong><?php echo $dealerStreetAddress; ?><br /><?php echo $dealerCity; ?>, <?php echo $dealerState; ?> <?php echo $dealerZipCode; ?><br /><?php echo $dealerPhoneNumber; ?><br />View Website'
},
<?php /* END WHILE AND RESET QUERY */ endwhile; wp_reset_query(); ?>
];
for (var i = 0; i < locations.length; i++) {
marker = new google.maps.Marker({
position: locations[i].latlng,
icon: image,
map: map
});
google.maps.event.addListener(marker, 'click', (function(marker, i) {
return function() {
infowindow.setContent(locations[i].info);
infowindow.open(map, marker);
}
})(marker, i));
}
}
function loadScript() {
var script = document.createElement('script');
script.type = 'text/javascript';
script.src = 'https://maps.googleapis.com/maps/api/js?v=3.exp&sensor=false&' + 'callback=initialize';
document.body.appendChild(script);
}
function set_map_center(lat, lng) {
var myLatLng = new google.maps.LatLng(lat, lng);
infowindow.open(map,marker);
map.setCenter(myLatLng);
map.setZoom(12);
infowindow.open(map, marker);
}
window.onload = loadScript;
</script>
Thanks to Suvi's comment, i understand better.
First off, you will need to store all of your markers in an array when you create them. Then in your set_map_center function, you can scan through the markers to find a matching Lat/Lng, and then trigger that marker's click event.
To trigger the marker click event:
google.maps.event.trigger(markers[i], 'click');
Here is how I check for a lat/lng match
function set_map_center(lat, lng){
var pos = new google.maps.LatLng(lat, lng)
for(var i=0;i<markers.length;i++){
if(markers[i].position.equals(pos))
google.maps.event.trigger(markers[i], 'click');
}
}
JSFiddle Example