-2

I can't use ng-click event in my Controller with style guide definitions.

(function() {
    'use strict';

    angular.module('starter.controllers')
        .controller('MapsCtrl', maps);

    function maps($ionicLoading, $compile, $stateParams) {
        var vm = this;

        var citiesList = [
            {
                id: 1,
                city: 'City One',
                desc: 'This is the best city in the world!',
                lat: -25.5511123,
                long: -49.4059869
            },
            {
                id: 2,
                city: 'City Two',
                desc: 'This city is aiiiiite!',
                lat: -25.481642,
                long: -49.293805
            },
            {
                id: 3,
                city: 'City Three',
                desc: 'This is the second best city in the world!',
                lat: -25.5867087,
                long: -49.1551404
            },
            {
                id: 4,
                city: 'City Four',
                desc: 'This city is live!',
                lat: -25.424667,
                long: -49.1605463
            }
        ];

        var _siteLatLng = new google.maps.LatLng(-25.5511123, -49.4059869); // city One default
        var _hospitalLatLng = new google.maps.LatLng(-25.481642, -49.293805); // city Two default

        var _mapOptions = {
            zoom: 4,
            center: _siteLatLng,
            mapTypeId: google.maps.MapTypeId.TERRAIN
        };

        var _map = new google.maps.Map(document.getElementById('map'), _mapOptions);
        var _markers = [];

        var createMarker = function(info) {
            var _marker = new google.maps.Marker({
                map: _map,
                position: new google.maps.LatLng(info.lat, info.long),
                title: info.city
            });
            _marker.content = '<div class="infoWindowContent">' + info.desc + '</div>';

            var _htmlInfo = '<div><a ng-click="vm.clickTest(' + info.id + ')"><h2>' + _marker.title + '</h2></a>' + _marker.content + "</div>";
            var _compiled = $compile(_htmlInfo)(vm);

            var _infoWindow = new google.maps.InfoWindow({
                content: _compiled[0]
            });

            google.maps.event.addListener(_marker, 'click', function() {
                // infoWindow.setContent(_htmlInfo);
                _infoWindow.open(_map, _marker);
            });

            _markers.push(_marker);
        }

        for (var i = 0; i < citiesList.length; i++) {
            createMarker(citiesList[i]);
        };

        // BEGIN -- Destionation
        var _directionsService = new google.maps.DirectionsService();
        var _directionsDisplay = new google.maps.DirectionsRenderer();

        var _request = {
            origin: _siteLatLng,
            destination: _hospitalLatLng,
            travelMode: google.maps.TravelMode.DRIVING
        };
        _directionsService.route(_request, function(response, status) {
            if (status == google.maps.DirectionsStatus.OK) {
                _directionsDisplay.setDirections(response);
            }
        });

        _directionsDisplay.setMap(_map);
        // END -- Destination

        // Declare variables as vm
        vm.map = _map;
        vm.markers = _markers;


        vm.centerOnMe = function() {
            if (!vm.map)
                return;

            vm.loading = $ionicLoading.show({
                content: 'Getting current location...',
                showBackdrop: false
            });
            navigator.geolocation.getCurrentPosition(function(pos) {
                vm.map.setCenter(
                    new google.maps.LatLng(pos.coords.latitude, pos.coords.longitude)
                );
                $ionicLoading.hide();

                var _position = new google.maps.LatLng(pos.coords.latitude, pos.coords.longitude);
                var _marker = new google.maps.Marker({
                    map: vm.map,
                    position: _position,
                    title: 'You are here!',
                    icon: 'images/places/place_black.png'
                });

                console.log( _position );
                console.log( pos);
                console.log( vm.map );

                var _htmlInfo = '<div><h1>You!</h1> Content text.</div>';
                var _compiled = $compile(_htmlInfo)(vm);
                var _infoWindow = new google.maps.InfoWindow({
                    content: _compiled[0]
                });

                google.maps.event.addListener(_marker, 'click', function() {
                    // infoWindow.setContent(_htmlInfo);
                    _infoWindow.open(_map, _marker);
                });
            },
            function(error) {
                alert('Unable to get location: ' + error.message);
            });
        };

        vm.clickTest = function(_id) {
            console.log('Clicked!!!', _id);

            alert(citiesList[_id - 1].city + ' is clicked! :D');
        };
    };

})();

Console error:

Uncaught TypeError: scope.$apply is not a function
(anonymous function)    @   ionic.bundle.js:53438
eventHandler    @   ionic.bundle.js:11713


//ionic.bundle.js  line: 53438

/**
 * @private
 */
.factory('$ionicNgClick', ['$parse', function($parse) {
  return function(scope, element, clickExpr) {
    var clickHandler = angular.isFunction(clickExpr) ?
      clickExpr :
      $parse(clickExpr);

    element.on('click', function(event) {
      scope.$apply(function() {  // (x) Uncaught TypeError: scope.$apply is not a function
        clickHandler(scope, {$event: (event)});
      });
    });

    // Hack for iOS Safari's benefit. It goes searching for onclick handlers and is liable to click
    // something else nearby.
    element.onclick = noop;
  };
}])

Please, help me, if possible! Thanks!


Screenshot

If I click in title from Window, return the error in the console.

Francis Rodrigues
  • 1,470
  • 4
  • 25
  • 61

2 Answers2

0

Inside the controller used as ControllerAs you reference the scope with this.

try something like:

var _compiled = $compile(_htmlInfo)(this);
...
this.clickTest =...

See here for more details

zmii
  • 4,123
  • 3
  • 40
  • 64
  • Thanks to answer @zmii, but a Style guide definition I do not use `$scope` but use `vm` in Controller. You did not know? https://github.com/johnpapa/angular-styleguide#function-declarations-to-hide-implementation-details – Francis Rodrigues Jun 08 '15 at 00:35
  • It was rhetorical question. You my use ControllerAs syntax. Still you've got error inside FACTORY, not controller. So please ming that factories doesn't have scopes defined. You may inject one there – zmii Jun 08 '15 at 00:37
  • Thanks @zmii, but I do not understand how make in this case. – Francis Rodrigues Jun 08 '15 at 00:40
  • http://stackoverflow.com/questions/19642138/how-to-include-inject-functions-which-use-scope-into-a-controller-in-angularjs – zmii Jun 08 '15 at 00:43
  • This $ionicNgClick factory is a native angular. I must overwrite his? – Francis Rodrigues Jun 08 '15 at 00:43
  • No. that is something interesting then... Please provide more code of controller. – zmii Jun 08 '15 at 00:50
  • In controllerAs in controller you make this is the beginning `var vm = this;` ? If not why do you play with `vm`? – zmii Jun 08 '15 at 00:53
  • Inside the controller used as ControllerAs you reference the scope with `this`. See here for more details http://toddmotto.com/digging-into-angulars-controller-as-syntax/ – zmii Jun 08 '15 at 00:54
  • There is an issue here that you may be interested to read https://github.com/driftyco/ionic/issues/3058 – zmii Jun 08 '15 at 18:24
  • This is a style guide definition, @zmii https://github.com/johnpapa/angular-styleguide#function-declarations-to-hide-implementation-details – Francis Rodrigues Jun 10 '15 at 23:29
  • Thanks for answer @zmii – Francis Rodrigues Jun 13 '16 at 22:47
0

Thanks for help @zmii

I could not solve this problem so I decided to use $ scope for the Click event. Look:

function maps($scope, $ionicLoading, $compile, $stateParams) {

   ...

   var _compiled = $compile(_htmlInfo)($scope);

Reference;

https://stackoverflow.com/a/25384592/3332734

Community
  • 1
  • 1
Francis Rodrigues
  • 1,470
  • 4
  • 25
  • 61