gpt4 book ai didi

angularjs - 将函数传递给指令以在链接中执行的正确方法

转载 作者:行者123 更新时间:2023-12-04 02:55:16 25 4
gpt4 key购买 nike

我知道我们通常通过一个孤立的范围将函数传递给指令:

.directive('myComponent', function () {
return {
scope:{
foo: '&'
}
};
})

然后在模板中我们可以这样调用这个函数:

<button class="btn" ng-click="foo({ myVal: value })">Submit</button>

在哪里 myVal是函数的参数名称 foo在父范围内需要。

现在,如果我打算从 link 使用它函数而不是模板,我将不得不使用以下命令调用它: scope.foo()(value) , 自 scope.foo用作原始函数的包装器。这对我来说似乎有点乏味。

如果我将函数传递给 myComponent使用 = 的指令:

.directive('myComponent', function () {
return {
scope:{
foo: '='
}
};
})

然后我就可以使用 scope.foo(value)从我的链接功能。那么这是在函数上使用 2 路绑定(bind)的有效用例,还是我在做某种我不应该做的黑客行为?

最佳答案

这就是我否决答案的原因。

首先,你不应该使用 '=' 将函数引用传递给指令。

'=' 创建两个监视并使用它们来确保指令范围和父范围引用相同(双向绑定(bind))。允许指令更改父作用域中函数的定义是一个非常糟糕的主意,当您使用这种类型的绑定(bind)时会发生这种情况。此外, watch 应该最小化——虽然它会起作用,但两个额外的 $watches 是不必要的。所以这不好 - 部分否决票是为了暗示它是。

第二 - 答案歪曲了 '&' 的作用。 & 不是“单向绑定(bind)”。它之所以用词不当,仅仅是因为与 '=' 不同,它不会创建任何 $watches,并且在指令范​​围内更改属性的值不会传播到父级。

根据文档:

& or &attr - provides a way to execute an expression in the context of the parent scope



当您在指令中使用 & 时,它会生成一个函数,该函数返回针对父范围评估的表达式的值。表达式不必是函数调用。它可以是任何有效的 Angular 表达式。此外,这个生成的函数接受一个对象参数,该参数可以覆盖在表达式中找到的任何局部变量的值。

为了扩展 OP 的示例,假设父级以下列方式使用此指令:
<my-component foo="go()">

在指令(模板或链接函数)中,如果您调用
foo({myVal: 42});

您正在做的是评估表达式“go()”,它恰好在父作用域上调用函数“go”,不传递任何参数。

或者,
<my-component foo="go(value)">

您正在评估父作用域上的表达式“go(value)”,它基本上是调用 $parent.go($parent.value)"
<my-component foo="go(myVal)">

您正在计算表达式“go(myVal)”,但在计算表达式之前,myVal 将被替换为 42,因此计算的表达式将为“go(42)”。
<my-component foo="myVal + value + go()">

在这种情况下, $scope.foo({myVal: 42}) 将返回以下结果:
42 + $parent.value + $parent.go()

本质上,这种模式允许指令“注入(inject)”指令的使用者可以选择在 foo 表达式中使用的变量。

你可以这样做:
<my-component foo="go">

并在指令中:
$scope.foo()(42)

$scope.foo() 将评估表达式“go”,它将返回对 $parent.go 函数的引用。然后它将调用它为 $parent.go(42)。这种模式的缺点是,如果表达式不计算为函数,则会出现错误。

否决票的最后一个原因是断言 ng-event 指令使用 &。事实并非如此。没有任何内置指令创建隔离范围:
scope:{
}

'&foo' 的实现是(为清楚起见进行了简化),归结为:
$scope.foo = function(locals) {
return $parse(attr.foo)($scope.$parent, locals);
}

ng-click 的实现类似,但(也简化了):
link: function(scope, elem, attr) {
elem.on('click', function(evt) {
$parse(attr.ngClick)(scope, {
$event: evt
}
});
}

所以要记住的关键是当你使用'&'时,你不是在传递一个函数——你是在传递一个表达式。该指令可以通过调用生成的函数随时获取此表达式的结果。

关于angularjs - 将函数传递给指令以在链接中执行的正确方法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29857998/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com