Angular google maps: put image in Info window - javascript

I use google maps api angular (https://angular-ui.github.io/angular-google-maps/#!/api/windows) to display a map with a mark on it. The marked point, has its label with a few paragraphs and a picture.
The content of paragraphs displayed correctly, but not the image. The url of it is correct. Can add an image?
Some code:
HTML
<ui-gmap-google-map center='datos.mapa.center' options="datos.mapa.opciones" zoom='datos.mapa.zoom'>
<ui-gmap-marker coords="datos.marker_club.coords"
options="datos.marker_club.options"
idkey="datos.marker_club.id"
click="markerClick" >
<ui-gmap-window show="datos.marker_club.show"
closeClick="markerClose(marker)" >
<div><img class="mapa_escudo" scr="{{datos.escudo}}" width="32" height="32" />{{datos.club}}<br />Sede {{datos.sede}}</div>
</ui-gmap-windows>
</ui-gmap-marker>
</ui-gmap-google-map>
JS
$scope.datos.club = 'Club';
$scope.datos.sede = 'Sede';
$scope.datos.escudo = 'http://www.server.com/image.png';
uiGmapGoogleMapApi.then(function(maps) {
$scope.datos.mapa = { center: { latitude: latitud, longitude: longitud }, zoom: zoom };
$scope.datos.mapa.opciones = { scrollwheel: true };
var icon = "http://maps.google.com/mapfiles/ms/icons/orange-dot.png";
$scope.datos.marker_club = { id: 1,
coords: { latitude: latitud, longitude: longitud},
options:{
draggable: false,
icon: new google.maps.MarkerImage(icon),
},
}; $scope.markerClick = function(marker, eventName, model) {
$scope.datos.marker_club.show = !$scope.datos.marker_club.show;
};
$scope.markerClose = function(marker) {
$scope.datos.marker.show = false;
};

Sorry, just missing "ng-src" in the definition of the image!

Related

How to apply JSON responseText to Google Maps in Ruby on Rails?

So in my Rails app I am building out a region show page with multiple locations. Users are able to insert new locations and map markers need to be dynamically placed based on the latitude and longitude that they enter. In my Region show page I have the following:
<div class="container-fluid">
<div class="row">
<div class="banner" id="region-banner" data-region-name="<%=#region.name.downcase%>">
<script>document.addEventListener('DOMContentLoaded',app.regions);</script>
Then in my region.js file I have the following:
import { tns } from 'tiny-slider/src/tiny-slider.module';
import { mapStyle } from './styles/mapStyle';
app.regions = () => {
function init() {
startGoogleMap();
}
let startGoogleMap = () => {
let map = new google.maps.Map(document.getElementById('region-banner'), {
zoom: 3,
minZoom: 3,
disableDefaultUI: true,
gestureHandling: 'cooperative',
styles: mapStyle
});
var mapElement = document.getElementById('region-banner');
const regionName = mapElement.getAttribute('data-region-name');
let bounds = new google.maps.LatLngBounds();
let promise = $.getJSON('/locations.json');
promise.done(function(data) {
return $.each(data, function() {
return new google.maps.Marker({
position: {
lat: parseFloat(data.lat),
lng: parseFloat(data.lng) },
map: map,
icon: "/marker.png"
});
});
});
console.log(promise);
map.fitBounds(bounds);
};
return init();
};
Then in my controller I have:
def show
#locations = Location.all
respond_to do |format|
format.json { render json: #locations }
format.html
end
end
So no real errors are applying however...nothing appears. The console shows the responseText:“[{“id”: 5, “name”: “Chicago”, “abbreviation”: “CHI”, “lat”: “44.222”, “lng”: “-22.111”}, {“id”: 6, “name”: “Frankfort”, “abbreviation”: “FKT”, “lat”: “41.3232”, “lng”: “-19.5221”} ]”. Which really on this page I should only need/use the first.
Shouldn't it also be applying the markers at this stage since I put in the position?
this is the code responsible for setting your Markers.
I would focus on understanding why promise.done() does not run create the new google.maps.Marker() for each row in your (data) from your response.
Maybe the problem is connected to the /marker.png
promise.done(function(data) {
return $.each(data, function() {
return new google.maps.Marker({
position: {
lat: parseFloat(data.lat),
lng: parseFloat(data.lng) },
map: map,
icon: "/marker.png"
});
});
});

How to do on page load of dynamic pages with JavaScript and Rails?

I'm trying to set up an on page load function for dynamic pages (shows) that will only display certain variables that meet the requirements. For example if someone clicks on West Coast the map will only display California, Washington, and Idaho. If they click on Great Plains the map shows Iowa, Nebraska, Kansas. And so on.
Right now I have it set up, in my region.js file:
app.regions = () => {
function init() {
startGoogleMap();
}
let startGoogleMap = () => {
let map = new google.maps.Map(document.getElementById("region-banner"), {
zoom: 7,
// The latitude and longitude to center the map (always required)
disableDefaultUI: true,
gestureHandling: "cooperative",
styles: mapStyle
});
const cali = new google.maps.Marker({
position: new google.maps.LatLng(x, y),
map: map,
icon: '/icon.jpg',
title: 'California',
region: 'West Coast'
});
return init();
};
Then in my regions I actually have a list of regions with the following in the table:
create_table "regions", force: :cascade do |t|
t.string "name"
t.string "url_name"
end
So in a nutshell I need to compare a variable against the region name on page load.
UPDATE:
This is what is currently in my show:
<div class="container-fluid">
<div class="row">
<div class="banner" id="region-banner">
</div>
</div>
</div>
<script>document.addEventListener('DOMContentLoaded', app.regions);</script>
EDIT:
I applied the following in my show > script:
let regionContainer = document.getElementById('region-banner');
regionContainer.dataset.region
Then changed my show to:
<div class="banner" id"region-banner"><%= #region.name %></div>
Nothing happened. No errors though.
One way to achieve this is to use data attributes on the container in which your map is loaded (although you could really use any element).
Assuming you have a variable #region for the current region in your show view, and assuming you're going to load the map in a div with a "map" id, you could do something like this in the markup:
<div id="map" data-region="<%= #region.name %>"></div>
And then you could retrieve that attribute in your JS file with something like this:
var mapContainer = document.getElementById('map');
mapContainer.dataset.region // Would be the result of #region.name
So the fix for future reference I did with both JS and Rails.
In JS
const markers = {
"west/coast": [{
position: [x,y],
title: 'California'
}]};
app.regions = () => {
function init () {
startGoogleMap();
}
let startGoogleMap = () => {
let map = new google.maps.Map(document.getElementById("region-banner"), {
zoom: 3,
minZoom: 3,
disableDefaultUI: true,
gestureHandling: "cooperative",
styles: mapStyle
});
var mapElement = document.getElementById("region-banner");
const regionName = mapElement.getAttribute('data-region-name')
let bounds = new google.maps.LatLngBounds();
markers[regionName].forEach(({ position, ...opts }) => {
const marker = new google.maps.Marker({
...opts,
position: new google.maps.LatLng(...position),
map
});
bounds.extend(marker.position);
});
Then in the show:
<div class="banner" id="region-banner" data-region-name=<%=#region.name.downcase%></div>

Marker does not show up on map angularjs

I am using angular-maps to create a map, with a list of markers.
I have a problem displaying the markers. I have no errors though.
Here is my code:
Controller
var app = angular.module('mapController', []);
app.service('Map', function($q) {
this.init = function() {
var options = {
center: new google.maps.LatLng(45.7154289, 4.9317724),
zoom: 14,
disableDefaultUI: true
}
this.map = new google.maps.Map(
document.getElementById("map"), options
);
this.places = new google.maps.places.PlacesService(this.map);
var markers = [{
"title": 'Capgemini',
"lat": '45.7154289',
"lng": '4.9317724',
"description": 'Capgemini'
}];
var defaultMarkerColor = 'ff0000';
var pinImage = new google.maps.MarkerImage("http://chart.apis.google.com/chart?chst=d_map_pin_letter&chld=%E2%80%A2|" + defaultMarkerColor);
// marker object for the marker
var marker = new google.maps.Marker({
position: google.maps.LatLng(markers[0].lat,markers[0].lng),
map: this.map,
title: markers[0].title,
animation: google.maps.Animation.DROP,
icon: pinImage
});
}
this.search = function(str) {
var d = $q.defer();
this.places.textSearch({query: str}, function(results, status) {
if (status == 'OK') {
d.resolve(results[0]);
}
else d.reject(status);
});
return d.promise;
}
this.addMarker = function(res) {
if(this.marker) this.marker.setMap(null);
this.marker = new google.maps.Marker({
map: this.map,
position: res.geometry.location,
animation: google.maps.Animation.DROP
});
this.map.setCenter(res.geometry.location);
}
});
app.controller('mapController', function($scope, Map) {
$scope.place = {};
$scope.search = function() {
$scope.apiError = false;
Map.search($scope.searchPlace)
.then(
function(res) { // success
Map.addMarker(res);
$scope.place.name = res.name;
$scope.place.lat = res.geometry.location.lat();
$scope.place.lng = res.geometry.location.lng();
},
function(status) { // error
$scope.apiError = true;
$scope.apiStatus = status;
}
);
}
$scope.send = function() {
alert($scope.place.name + ' : ' + $scope.place.lat + ', ' + $scope.place.lng);
}
Map.init();
});
and the HTML :
<ion-content ng-controller="mapController" style="margin-top: 25px">
<div class="container">
<div id="map" libraries="places" data-tap-disabled="true"></div>
<form name="searchForm" novalidate
ng-submit="search()">
<div class="input-group">
<input name="place" type="text" class="form-control"
ng-model="searchPlace" required autofocus />
<br>
<span class="input-group-btn">
<button class="btn btn-primary"
ng-disabled="searchForm.$invalid">Search</button>
</span>
</div>
</form>
</div>
The map shows up correctly, and centered on the coordinates I chose, but without a marker.
I would appreciate any help.
Hi took me sometime to put in place the fiddle... :)
I made this changes to make it work:
The markers:
var markers = [{
"title": 'Capgemini',
"lat": 45.7154289,
"lng": 4.9317724,
"description": 'Capgemini'
}];
And then the marker definition
var marker = new google.maps.Marker({
position:{lat: markers[0].lat, lng: markers[0].lng},
map: this.map,
title: markers[0].title,
animation: google.maps.Animation.DROP,
icon: pinImage
});
the easiest way is to use numbers for the coords.
here you can find the fiddle
it isn't super clean and it is lot of debug stuff and most important if you can initialize and see the map you don't really need it.
hope this help

How do you show a window when clicking polygons in angular google maps?

Whenever one of the regions on the map are clicked, it should open the window for that region, but it doesn't.
The expected results would be as follows:
Here is how I want it to look.
Here is my html:
<ui-gmap-polygon static="true" ng-repeat="p in regions track by p.id" path="p.path" visible="p.visible" stroke="p.stroke" fill="p.fill" events="events" clickable="true" >
</ui-gmap-polygon>
<ui-gmap-windows models="markers" show="show">
<!-- Window Code -->
</ui-gmap-windows>
Here is the $scope.events.click function for the polygons:
for(var i = 0; i < $scope.markers.length; i++) {
//console.log(model.path[0].id + " == " + $scope.markers[i].id);
if(model.path[0].id == $scope.markers[i].id) {
console.log("Showing window " + model.path[0].id);
$scope.markers[i].show = true;
}
else
{ // hides other windows
$scope.markers[i].show = false;
}
}
Something to note. The log statement does show up, just not the window.
Here is a plunker: Plunker
I guess you want to add multiple polygons so change your html to:
<ui-gmap-google-map center="map.center" zoom="map.zoom" draggable="true" options="options" bounds="map.bounds">
<ui-gmap-polygons static="true" models="regions" path="'path'" visible="true" stroke="'stroke'" fill="'fill'" events="events" clickable="true" >
</ui-gmap-polygons>
<ui-gmap-windows models="markers" show="'show'" coords="'coords'">
<div ng-non-bindable>Test</div>
</ui-gmap-windows>
</ui-gmap-google-map>
You need to define the property which will define the value as string e.g.: show="'show'" coords="'coords'"
I added a second model just because i wanted to test it which multiple values. So my controller looks like this:
...
$scope.regions = [
{
id: 0,
path: [
{latitude: 39.13773735160255, longitude: -86.51972115039825, id: 0},
{latitude: 39.137606286024926, longitude: -86.51961386203766},
{latitude: 39.137664537422864, longitude: -86.51949316263199},
{latitude: 39.13779768329436, longitude: -86.51960045099258}
]
},
{
id: 1,
path: [
{latitude: 39.13673735160255, longitude: -86.51972115039825, id: 1},
{latitude: 39.136606286024926, longitude: -86.51961386203766},
{latitude: 39.136664537422864, longitude: -86.51949316263199},
{latitude: 39.13679768329436, longitude: -86.51960045099258}
]
}
]
$scope.markers= [{
id: 0,
show: true,
coords: { //you need an object containing latitude and longitude, so i wrapped these properties into coords
latitude: 39.13773735160255,
longitude: -86.51972115039825
}
},{
id: 1,
show: true,
coords: {
latitude: 39.13673735160255,
longitude: -86.51972115039825
}
}
]
$scope.events = {
click: function(polygon, eventName, model) {
// show the window
for(var i = 0; i < $scope.markers.length; i++) {
if(model.path[0] && model.path[0].id == $scope.markers[i].id) {
$scope.markers[i].show = true;
console.log("Window Displayed")
} else {
$scope.markers[i].show = false;
}
}
}
};
You should change your data models if you can e.g. regions where id is defined twice.
I figured out an alternative solution to the problem. Instead of using a window for every marker, I used just one:
<ui-gmap-window coords="selected" show="windowShown" closeClick="closeClick()">
<!-- Window Code -->
</ui-gmap-window>
Then in the controller we have a similar click function:
/*
Events when clicking on a polygon.
*/
$scope.events = {
click: function(polygon, eventName, model) {
// show the window
for(var i = 0; i < $scope.markers.length; i++) {
if(model.path[0].id == $scope.markers[i].id) {
$scope.selected = $scope.markers[i];
$scope.windowShow = true;
}
}
}
};
Lastly, we have a closeClick function to make sure $scope.windowShown is set to false after the window is closed. Otherwise, you cannot reopen the window on the same polygon after it has been closed.
$scope.closeClick = function() { $scope.windowShow = false; }

When clicking cluster, how to show Infowindow which has markers's values?

I have been trying to use google map with angularJS.
I have learned how to use it through https://angular-ui.github.io/angular-google-maps/#!/.
Everything goes well.
For each marker, I can show InfoWindow which has an element information of myList.
But I have got stuck in InfoWindow with cluster.
When cluster is clicked, I want to show the information list of markers in cluster.
Even I can't show simple InforWindow when clicking the cluster.
Below sources are my code.
Please tell me if it is not enough to solve my problem.
Please tell me what is wrong and how to solve this.
Have a nice day.
* javascript
$scope.map.map = {
center: { latitude: $scope.map.myList[0].lat, longitude: $scope.map.myList[0].lng },
zoom: 17,
events : {
tilesloaded: function (map) {
$scope.$apply(function () {
google.maps.event.addDomListener(window, 'resize', function() {
var lat = $scope.map.myList[$scope.map.markerPosition-1].lat;
var lng = $scope.map.myList[$scope.map.markerPosition-1].lng;
var center = new google.maps.LatLng(lat, lng);
map.setCenter(center);
});
});
}
},
markersEvents: {
click: function(marker, eventName, model) {
model.show = !model.show;
return;
}
},
clusterOptions : { // options of cluster
gridSize: 40,
ignoreHidden: true,
zoomOnClick : false,
averageCenter : true,
styles: [
{
height: 53,
url: "http://google-maps-utility-library-v3.googlecode.com/svn/trunk/markerclusterer/images/m3.png",
width: 53,
textColor : 'white'
}
]
},
clusterEvent: { // when cluster's clicked
click: function(map, markers) {
var contentString = 'ABCD';
var infowindow = new google.maps.InfoWindow({
content: contentString
});
infowindow.open(map, markers);
return;
}
}
};
$scope.map.options = {
streetViewControl : false
};
$scope.map.markers = [];
* html
<ui-gmap-google-map center='map.map.center' zoom="map.map.zoom" options="map.options" events="map.map.events">
<ui-gmap-markers models="map.markers" coords="'self'" icon="a" events="map.map.markersEvents" options="'options'"
doCluster="true" clusterOptions="map.map.clusterOptions" clusterEvents="map.map.clusterEvent">
<ui-gmap-windows show="show">
<div ng-non-bindable>{{id}}</div>
</ui-gmap-windows>
</ui-gmap-markers>
Answer myself.
var infoWindowOptions = {
content: "asdfasdf"
};
var infowindow = new google.maps.InfoWindow(infoWindowOptions);
infowindow.open(map.map_, *marker*);

Categories