我正在尝试在 Angular/IonicFramework 中实现 Google map 。我正在使用指令、服务和 Controller 。我在 $scope
中有一个 map 、标记和地理定位对象。 View 中的 map 对象和标记对象会从服务更新,但地理定位对象不会。
模板/ View :
<div class="item item-input item-stacked-label item-icon-right">
<div>
Location
<a ng-click="centerOnMe()">
<i class="icon ion-android-locate" style="font-size:24px"></i>
</a>
</div>
<textarea style="margin-top: 0px; margin-bottom: 0px; height: 45px;" placeholder="Location not found." disabled>{{geoloc.addr}}</textarea>
</div>
<div class="item item-input">
<div class="input-label">Map</div>
</div>
<div class="item item-input" style="height:15em;">
<ion-content scroll="false">
<map on-create="mapCreated(map, geoloc, marker)"></map>
</ion-content>
</div>
map 指令:
angular.module('starter.directives', [])
.directive('map', function(MapService) {
return {
restrict: 'E',
scope: {
onCreate: '&'
},
link: function ($scope, $element, $attr) {
function initialize() {
var mapOptions = {
center: new google.maps.LatLng(43.07493, -89.381388),
zoom: 16,
mapTypeId: google.maps.MapTypeId.ROADMAP
};
var map = new google.maps.Map($element[0], mapOptions);
var geoloc = {
lat: null, lng: null, str: null, brgy: null,
muni: null, reg: null, addr: null
};
var marker = new google.maps.Marker({
map: map
});
$scope.onCreate(
{
map: map, //link map to map in controller
geoloc: geoloc, //link geoloc to geoloc in controller
marker: marker //link marker to marker in controller
});
// Stop the side bar from dragging when mousedown/tapdown on the map
google.maps.event.addDomListener($element[0], 'mousedown', function (e) {
e.preventDefault();
return false;
});
}
if (document.readyState === "complete") {
initialize();
} else {
google.maps.event.addDomListener(window, 'load', initialize);
}
}
}
});
map Controller :
angular.module('starter.controllers', [])
.controller('MapCtrl', function($scope, $ionicLoading, MapService) {
$scope.mapCreated = function(map, geoloc, marker) {
$scope.map = map; //sets the map from the directive to the $scope
$scope.geoloc = geoloc; //sets the geoloc from the directive to the $scope
$scope.marker = marker; //sets the marker from the directive to the $scope
};
$scope.centerOnMe = function () {
console.log('Centering..');
if (!$scope.map && !$scope.marker && !$scope.geoloc) {
return;
}
$scope.loading = $ionicLoading.show({
template: 'Getting current location...',
noBackdrop: true
});
$scope.geoloc = MapService.getCurrentLocation($ionicLoading, $scope.map, $scope.geoloc, $scope.marker);
// ^^^ This doesn't seem to work. $scope.geoloc doesn't get updated immediately, while $scope.map and $scope.marker gets updated immediately. Has to be invoked twice for $scope.geoloc to be updated.
}
});
map 服务:
angular.module('starter.services', [])
.factory('MapService', function() {
return {
getCurrentLocation: function($ionicLoading, map, geoloc, marker) {
navigator.geolocation.getCurrentPosition(function (pos) { //callback if get location succeeds
geoloc.lat = pos.coords.latitude;
geoloc.lng = pos.coords.longitude;
var latlngpos = new google.maps.LatLng(pos.coords.latitude, pos.coords.longitude);
var geocoder = new google.maps.Geocoder();
geocoder.geocode({'latLng': latlngpos}, function(results, status) {
if (status == google.maps.GeocoderStatus.OK) {
if (results[0]) {
map.setZoom(16);
marker.setOptions({
position: latlngpos,
map: map
});
geoloc.str = results[0].address_components[0].short_name; //type:route
geoloc.brgy = results[0].address_components[1].short_name; //type:neighborhood
geoloc.muni = results[0].address_components[2].short_name; //type:locatlity
geoloc.reg = results[0].address_components[3].short_name; //type:admnistrative_area_level_1
geoloc.addr = results[0].formatted_address;
} else {
console.log('No results found');
}
} else {
console.log('Geocoder failed due to: ' + status);
}
});
map.setCenter(latlngpos);
$ionicLoading.hide();
}, function (error) { //callback if get location fails
alert('Unable to get location: ' + error.message);
});
return geoloc;
}
}
})
;
我的实现基于这里:
http://www.jeffvandalsum.com/integrating-google-maps-api-with-angular/
我已经按照此处建议的解决方案进行操作,但是 $scope.geoloc
对象仍然没有更新:
Angular directive scope between google maps and a controller
Phonegap not firing GoogleMaps v3 domListener function inside Angularjs directive
最佳答案
尝试换行
$scope.geoloc = MapService.getCurrentLocation($ionicLoading,$scope.map, $scope.geoloc, $scope.marker);
使用 $timeout
angular.module('starter.controllers', [])
.controller('MapCtrl', function($scope,$timeout, $ionicLoading, MapService) {
$scope.mapCreated = function(map, geoloc, marker) {
$scope.map = map; //sets the map from the directive to the $scope
$scope.geoloc = geoloc; //sets the geoloc from the directive to the $scope
$scope.marker = marker; //sets the marker from the directive to the $scope
};
$scope.centerOnMe = function () {
console.log('Centering..');
if (!$scope.map && !$scope.marker && !$scope.geoloc) {
return;
}
$scope.loading = $ionicLoading.show({
template: 'Getting current location...',
noBackdrop: true
});
$timeout(function(){
$scope.geoloc = MapService.getCurrentLocation($ionicLoading, $scope.map, $scope.geoloc, $scope.marker);
// ^^^ This doesn't seem to work. $scope.geoloc doesn't get updated immediately, while $scope.map and $scope.marker gets updated immediately. Has to be invoked twice for $scope.geoloc to be updated.
});
}
});
旁注:这不一定是最佳方式,但它应该会触发您的 $scope.geoloc
正确更新。
我还建议 Gajotres's tutorial .
希望这对您有所帮助!
关于javascript - 更新 AngularJS 服务中的 $scope 对象不会更新 View ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30980487/