/ / AngularJS - função de passagem para diretiva - angularjs

AngularJS - passa a função para diretiva - angularjs

Eu tenho um exemplo angularJS

<div ng-controller="testCtrl">

<test color1="color1" updateFn="updateFn()"></test>
</div>
<script>
angular.module("dr", [])
.controller("testCtrl", function($scope) {
$scope.color1 = "color";
$scope.updateFn = function() {
alert("123");
}
})
.directive("test", function() {
return {
restrict: "E",
scope: {color1: "=",
updateFn: "&"},
template: "<button ng-click="updateFn()">Click</button>",
replace: true,
link: function(scope, elm, attrs) {
}
}
});

</script>
</body>

</html>

Eu quero que quando eu clicar no botão, a caixa de alerta aparecerá, mas nada aparecerá.

Alguém pode me ajudar?

Respostas:

222 para resposta № 1

Para chamar uma função de controlador no escopo pai de dentro de uma diretiva de escopo isolado, use dash-separated nomes de atributos no HTML como o OP disse.

Além disso, se você quiser enviar um parâmetro para sua função, chame a função passando um objeto:

<test color1="color1" update-fn="updateFn(msg)"></test>

JS

var app = angular.module("dr", []);

app.controller("testCtrl", function($scope) {
$scope.color1 = "color";
$scope.updateFn = function(msg) {
alert(msg);
}
});

app.directive("test", function() {
return {
restrict: "E",
scope: {
color1: "=",
updateFn: "&"
},
// object is passed while making the call
template: "<button ng-click="updateFn({msg : "Hello World!"})">
Click</button>",
replace: true,
link: function(scope, elm, attrs) {
}
}
});

Violino


139 para resposta № 2

Talvez eu esteja perdendo algo, mas embora as outras soluções chamem a função de escopo pai, não há capacidade de passar argumentos do código de diretiva, isso ocorre porque o update-fn está chamando updateFn() com parâmetros fixos, por exemplo {msg: "Hello World"}. Uma ligeira alteração permite que a diretiva passe argumentos, o que eu considero muito mais útil.

<test color1="color1" update-fn="updateFn"></test>

Observe que o HTML está passando uma referência de função, ou seja, sem () colchetes.

JS

var app = angular.module("dr", []);

app.controller("testCtrl", function($scope) {
$scope.color1 = "color";
$scope.updateFn = function(msg) {
alert(msg);
}
});

app.directive("test", function() {
return {
restrict: "E",
scope: {
color1: "=",
updateFn: "&"
},
// object is passed while making the call
template: "<button ng-click="callUpdate()">
Click</button>",
replace: true,
link: function(scope, elm, attrs) {
scope.callUpdate = function() {
scope.updateFn()("Directive Args");
}
}
}
});

Então, acima, o HTML está chamando o escopo local callUpdate , que então "busca" o updateFn do escopo pai e chama a função retornada com parâmetros que a diretiva pode gerar.

http://jsfiddle.net/mygknek2/


36 para resposta № 3

Na tag Html da diretiva "test", o nome do atributo da função não deveria ser camelCased, mas baseado em traços.

então - em vez de:

<test color1="color1" updateFn="updateFn()"></test>

Escreva:

<test color1="color1" update-fn="updateFn()"></test>

Esta é uma maneira angular de saber a diferença entre atributos de diretiva (como a função update-fn) e funções.


3 para resposta № 4

Que tal passar a função de controlador com ligação bidirecional? Em seguida, você pode usá-lo na diretiva exatamente da mesma maneira que em um modelo regular (retirei as partes irrelevantes para simplificar):

<div ng-controller="testCtrl">

<!-- pass the function with no arguments -->
<test color1="color1" update-fn="updateFn"></test>
</div>

<script>
angular.module("dr", [])
.controller("testCtrl", function($scope) {
$scope.updateFn = function(msg) {
alert(msg);
}
})
.directive("test", function() {
return {
scope: {
updateFn: "=" // "=" bidirectional binding
},
template: "<button ng-click="updateFn(1337)">Click</button>"
}
});
</script>

Aterrei nesta questão, porque tentei o método acima antes, mas de alguma forma não funcionou. Agora funciona perfeitamente.


2 para resposta № 5

use travessão e minúsculas para o nome do atributo (como outras respostas disseram):

 <test color1="color1" update-fn="updateFn()"></test>

E use "=" em vez de "&" no escopo da diretiva:

 scope: { updateFn: "="}

Em seguida, você pode usar updateFn como qualquer outra função:

 <button ng-click="updateFn()">Click</button>

Ai está!


0 para a resposta № 6

Tive de usar a ligação "=" em vez de "&" porque não estava funcionando. Comportamento estranho.