2017-05-29 185 views
1

调用控制器函数在一个angularjs项目中,我使用一个指令来上传文件,方法是将它们拖放到一个dropzone中。在指令中,我需要调用在我的控制器中定义的函数。AngularJs - 从指令

下面是我在做什么:

(function() { 
'use strict'; 

angular 
    .module('app') 
    .controller('myController', myController) 
    .directive('fileDropzone', function() { 
     return { 
      restrict: 'A', 
      scope: { 
       file: '=', 
       fileName: '=', 
       test: '&callbackFn', 
      }, 
      link: function (scope, element, attrs) { 
       var processDragOverOrEnter; 
       processDragOverOrEnter = function (event) { 
        if (event != null) { 
         event.preventDefault(); 
        } 
        event.dataTransfer.effectAllowed = 'copy'; 
        return false; 
       }; 
       element.bind('dragover', processDragOverOrEnter); 
       element.bind('dragenter', processDragOverOrEnter); 
       return element.bind('drop', function (event) { 
        var file, reader; 
        if (event != null) { 
         event.preventDefault(); 
        } 
        reader = new FileReader(); 
        reader.onload = function (evt) { 
         console.log(reader.result); 

         scope.test({}); 
        }; 
        file = event.dataTransfer.files[0]; 
        reader.readAsText(file); 
        return false; 
       }); 
      } 
     }; 
    }); 

    function myController() 
    { 
     var vm = this; 

     vm.test = function() { 
      console.log("It works !"); 
     }; 
    } 
})(); 

HTML文件:

<div class="container"> 
    <md-content file-dropzone layout="column" layout-align="center center" class="md-list-item-text" md-whiteframe="1" style="padding:1em;margin:0.5em 0.5em;" flex> 
     File drop zone 
    </md-content> 
</div> 

虽然执行console.log(reader.result)指令确实显示在控制台中的文件内容,消息“有用 !”没有显示,这意味着函数test()永远不会被调用。

我在做什么错?

+2

添加HTML文件信息也.. –

+1

为您创建隔离范围,然后在那里你使用任何控制器的内部指令,在那里你会得到它的实例使用''CTRL作为第四个参数链接功能 –

+0

然后你可以调用控制器的功能 –

回答

7

var app = angular.module('exApp', []); 
 

 
app.controller("Ctrl", function ($scope) { 
 
    $scope.test = function() { 
 
    console.log("Hi you called ctrl function"); 
 
    }; 
 
    $scope.param = function(name){ 
 
    console.log("My name is " + name); 
 
    } 
 
    $scope.testing = function(role){ 
 
    console.log("I'm a "+ role); 
 
    } 
 
}); 
 

 
app.directive("testDir", function() { 
 
    return { 
 
    scope: { 
 
     test: "&callFuc", 
 
     param:"&withparam", 
 
     testing:"&" 
 
    }, 
 
    template: `<button ng-click="test()">Call Test! 
 
       </button> 
 
       <button ng-click="param({name:'Mani'})">With param! 
 
       </button> 
 
       <button ng-click="clickHere()">Click Me! 
 
       </button>`, 
 
    link:function(scope){ 
 
     scope.clickHere = function(){ 
 
      scope.testing({msg:"Javascript Developer"}); 
 
     }; 
 
    } 
 
    }; 
 
});
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.8/angular.min.js"></script> 
 
<div ng-app="exApp"> 
 
    <div ng-controller="Ctrl"> 
 
    <div test-dir call-fuc="test()" withparam="param(name)" testing="testing(msg)"></div> 
 
    </div> 
 
</div>

这个例子是无参数;

scope: { 
       file: '=', 
       fileName: '=', 
       test: '&', 
      } 
<a ng-click="test()">Call test</a> // in directive 

<md-content file-dropzone layout="column" test="vm.test()" 
      layout-align="center center" class="md-list-item-text" 
      md-whiteframe="1" style="padding:1em;margin:0.5em 0.5em;" 
      flex> 
    File drop zone 
</md-content> 
+0

经过进一步测试,这是唯一对我有用的解决方案,谢谢。 – Hal

+0

欢迎@Hal ... –

-1

您可以通过在链接功能中指定第四个变量来访问指令控制器。

更新的链接功能: -

link: function (scope, element, attrs, ctrl) { 
    console.log(ctrl.test()); 
} 
+0

请在downvoting答案前添加评论。这将有助于在未来的答案 – Ajay

+0

我没有downvoted的答案,但它不适合我。我有以下错误:“无法读取未定义的属性”测试“。如果我尝试在控制台中显示ctrl,它确实显示“未定义”。 – Hal

+0

@Hal,我问那些压倒这个答案的人。 你可以将myController注册为指令控制器吗? – Ajay

-1

你需要传递CTRL作为第四个参数里面链接功能。