How to call a method defined in an AngularJS directive?

前端 未结 13 1074
萌比男神i
萌比男神i 2020-11-22 14:39

I have a directive, here is the code :

.directive(\'map\', function() {
    return {
        restrict: \'E\',
        replace: true,
        template: \'<         


        
13条回答
  •  死守一世寂寞
    2020-11-22 15:32

    To be honest, I was not really convinced with any of the answers in this thread. So, here's are my solutions:

    Directive Handler(Manager) Approach

    This method is agnostic to whether the directive's $scope is a shared one or isolated one

    A factory to register the directive instances

    angular.module('myModule').factory('MyDirectiveHandler', function() {
        var instance_map = {};
        var service = {
            registerDirective: registerDirective,
            getDirective: getDirective,
            deregisterDirective: deregisterDirective
        };
    
        return service;
    
        function registerDirective(name, ctrl) {
            instance_map[name] = ctrl;
        }
    
        function getDirective(name) {
            return instance_map[name];
        }
    
        function deregisterDirective(name) {
            instance_map[name] = null;
        }
    });
    

    The directive code, I usually put all the logic that doesn't deal with DOM inside directive controller. And registering the controller instance inside our handler

    angular.module('myModule').directive('myDirective', function(MyDirectiveHandler) {
        var directive = {
            link: link,
            controller: controller
        };
    
        return directive;
    
        function link() {
            //link fn code
        }
    
        function controller($scope, $attrs) {
            var name = $attrs.name;
    
            this.updateMap = function() {
                //some code
            };
    
            MyDirectiveHandler.registerDirective(name, this);
    
            $scope.$on('destroy', function() {
                MyDirectiveHandler.deregisterDirective(name);
            });
        }
    })
    

    template code

    Access the controller instance using the factory & run the publicly exposed methods

    angular.module('myModule').controller('MyController', function(MyDirectiveHandler, $scope) {
        $scope.someFn = function() {
            MyDirectiveHandler.get('foo').updateMap();
        };
    });
    

    Angular's approach

    Taking a leaf out of angular's book on how they deal with

    using $parse and registering controller on $parent scope. This technique doesn't work on isolated $scope directives.

    angular.module('myModule').directive('myDirective', function($parse) {
        var directive = {
            link: link,
            controller: controller,
            scope: true
        };
    
        return directive;
    
        function link() {
            //link fn code
        }
    
        function controller($scope, $attrs) {
            $parse($attrs.name).assign($scope.$parent, this);
    
            this.updateMap = function() {
                //some code
            };
        }
    })
    

    Access it inside controller using $scope.foo

    angular.module('myModule').controller('MyController', function($scope) {
        $scope.someFn = function() {
            $scope.foo.updateMap();
        };
    });
    

提交回复
热议问题