Reputation: 1882
I'm using Angular google Maps trying to get an info window working. When a marker is selected, the window is placed there and shown. Its content is some text and also some directives. The directives inside even work, except for when I try to bind some data its attributes.
In this case I'm having a rating directive (shows a bunch of stars) that takes a number attribute, as so:
<div stars number="person.rating"></div>
Note that this directives works just fine in a couple of other places in my app. Also, when I replace person.rating' for
3, the directive renders perfectly. when I use
person.rating` outside of this div, it returns a number as expected.
Only when I combine the person.rating
inside the number
attribute, inside the window
directive, do things go awry:
<ui-gmap-google-map center='map.center' class="big-maps" options='map.options' events="map.events" zoom='map.zoom'>
<ui-gmap-window coords="selectedCoords" show="windowOptions.visible" closeClick="closeWindow">
<div>
Name: {{person.firstName}}, Rating: {{person.rating}} <!-- these work just fine. -->
<div> So here we are. {{person.rating}}</div> <!-- this also works just fine. -->
<div stars number="3"></div> <!-- Even this works fine. -->
<div stars number="person.rating"></div> <!-- But this doesn't... -->
</div>
</ui-gmap-window>
<ui-gmap-markers
models='markers'
idKey='id'
coords="'coords'"
icon="'icon'"
options="'options'"
doCluster="false"
click="showWindow"
>
</ui-gmap-markers>
</ui-gmap-google-map>
The directive:
ndtApp.directive('stars', stars);
function stars() {
return {
restrict: "AE",
replace: 'true',
scope: {
number: "=",
size: "@"
},
templateUrl: "shared/stars/stars.html",
controller: controller
};
}
function controller($scope){
$scope.getEmptyStarsArray = getEmptyStarsArray;
$scope.getStarsArray = getStarsArray;
$scope.ratingSize = "";
activate();
function activate(){
if ($scope.size == 'sm'){
$scope.ratingSize = 'rating-sm';
} else if ($scope.size == 'lg'){
$scope.ratingSize = 'rating-lg';
}
console.log($scope.number);
}
function getEmptyStarsArray(){
if ($scope.number === undefined) return 0;
var rating = Math.round($scope.number);
if (rating > 4) return null;
return new Array(5 - rating);
}
function getStarsArray(){
if ($scope.number === undefined) return 0;
var rating = Math.round($scope.number);
if (rating === 0) return null;
if (rating > 5) return new Array(5);
return new Array(rating);
}
}
stars.html:
<div class="stars">
<span ng-repeat="i in getStarsArray() track by $index" class="{{ratingSize}} rating glyphicon glyphicon-star"></span><span ng-repeat="i in getEmptyStarsArray() track by $index" class="{{ratingSize}} rating glyphicon glyphicon-star-empty"></span>
</div>
Any help is highly appreciated!
Upvotes: 1
Views: 613
Reputation: 59368
It seems directive scope property is not getting bound, try to change scope for number
property from number: "="
to number: "@"
and directive initialization from <div stars number="person.rating"></div>
to <div stars number="{{person.rating}}"></div>
Below is provided a working similar example:
var appMaps = angular.module('appMaps', ['uiGmapgoogle-maps']);
appMaps.controller('mainCtrl', function($scope,uiGmapIsReady) {
$scope.map = {
center: { latitude: 40.1451, longitude: -99.6680 },
zoom: 4,
options: { scrollwheel: false }
};
$scope.windowOptions = { visible: false };
var getRandomLat = function() {
return Math.random() * (90.0 + 90.0) - 90.0;
};
var getRandomLng = function () {
return Math.random() * (180.0 + 180.0) - 180.0;
};
var getRandomRating = function() {
return Math.floor(Math.random() * 11);
};
var createRandomMarker = function(i) {
var ret = {
latitude: getRandomLat(),
longitude: getRandomLng(),
title: 'Hotel #' + i,
show: false,
id: i
};
return ret;
};
$scope.onClick = function(marker, eventName, model) {
$scope.windowOptions.visible = true;
$scope.selectedHotel = model;
$scope.rating = { number: getRandomRating()};
};
$scope.closeWindow = function () {
$scope.windowOptions.visible = false;
};
$scope.hotels = [];
for (var i = 0; i < 256; i++) {
$scope.hotels.push(createRandomMarker(i));
}
});
appMaps.directive('rating',
function() {
return {
restrict: "AE",
replace: true,
scope: {
//number: "=",
number: "@"
},
controller: ratingController,
//template: '<div >Rating: {{ ::number }}</div>',
template: function(tElem, tAttrs){
return '<div class="rating"> Rating:' + tAttrs.number + '</div>';
}
};
});
function ratingController($scope){
console.log($scope.number);
}
html, body, #map_canvas {
height: 100%;
width: 100%;
margin: 0px;
}
#map_canvas {
position: relative;
}
.angular-google-map-container {
position: absolute;
top: 0;
bottom: 0;
right: 0;
left: 0;
}
<script src="https://code.angularjs.org/1.3.14/angular.js"></script>
<script src="//cdnjs.cloudflare.com/ajax/libs/lodash.js/2.4.1/lodash.js"></script>
<script src="http://rawgit.com/angular-ui/angular-google-maps/2.0.X/dist/angular-google-maps.js"></script>
<div id="map_canvas" ng-app="appMaps" ng-controller="mainCtrl">
<ui-gmap-google-map center="map.center" zoom="map.zoom" draggable="true" options="options" events="map.events">
<ui-gmap-window coords="selectedHotel" show="windowOptions.visible" closeclick="closeWindow">
<div>
<div>{{selectedHotel.title}}</div>
<div rating number="{{rating.number}}"></div>
</div>
</ui-gmap-window>
<ui-gmap-markers models="hotels" coords="'self'" icon="'icon'" click="onClick">
</ui-gmap-markers>
</ui-gmap-google-map>
</div>
Upvotes: 2