Google Maps API async loading in AngularJs

by dsubiros

HTML

<div ng-app="myApp" ng-controller="MyCtrl">
  <my-map id="map_div" center='{ "lat": -34.397, "lng": 150.644 }' zoom="4"  key=""></my-map>
</div>

CSS

#map_div {
    height: 480px;
    width:100%;
}

JavaScript

angular.module('myApp', [])
    .factory('googleMapsApi', function ($rootScope,$window, $q) {
        return {
            load: function (key) {
                var deferred = $q.defer()

                if ($window.google && $window.google.maps) {
                    deferred.resolve($window.google);
                }
                else {
                        var url = 'https://maps.googleapis.com/maps/api/js?callback=googleMapsLoad';
                        if (key) url += "&key=" + key;
                        var script = document.createElement('script');
                        script.type = 'text/javascript'
                        script.src = url;
                        $window.googleMapsLoad = function () {
                            deferred.resolve($window.google);
                        }
                        document.body.appendChild(script);
                }
                return deferred.promise;
            },
            createMap : function(scope,id,options){
                 var mapObject = new google.maps.Map(document.getElementById(id), options);  
                 scope.$emit('google-maps-loaded',mapObject);
            },
            onMapReady : function(scope, ready){
                var handler = $rootScope.$on('google-maps-loaded', function(evnt,data){ return ready(data);});
                scope.$on('$destroy', handler);
            }
        }
    })
    .directive('myMap', function (googleMapsApi) {
        return {
            restrict: 'E',
            template: '<div></div>',
            replace: true,
            scope: {
                key: '@key',
                center: '=center',
                zoom: '=zoom'
             },
            link: function (scope, element, attributes) {
                googleMapsApi.load(scope.key)
                .then(function () {
                    var mapOptions = {
                        center: scope.center,
                        zoom: scope.zoom,
                       ...