Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
433 views
in Technique[技术] by (71.8m points)

javascript - 如何在自定义指令中获取评估属性(How to get evaluated attributes inside a custom directive)

I'm trying to get an evaluated attribute from my custom directive, but I can't find the right way of doing it.

(我试图从我的自定义指令获取一个评估属性,但我找不到正确的方法。)

I've created this jsFiddle to elaborate.

(我已经创建了这个jsFiddle来详细说明。)

<div ng-controller="MyCtrl">
    <input my-directive value="123">
    <input my-directive value="{{1+1}}">
</div>

myApp.directive('myDirective', function () {
    return function (scope, element, attr) {
        element.val("value = "+attr.value);
    }
});

What am I missing?

(我错过了什么?)

  ask by Shlomi Schwartz translate from so

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

Notice: I do update this answer as I find better solutions.

(注意:我找到更好的解决方案,我会更新这个答案。)

I also keep the old answers for future reference as long as they remain related.

(只要它们保持相关,我也会保留旧答案以供将来参考。)

Latest and best answer comes first.

(最新和最好的答案是第一位的。)

Better answer:(更好的答案:)

Directives in angularjs are very powerful, but it takes time to comprehend which processes lie behind them.

(angularjs中的指令非常强大,但需要时间来理解它们背后的流程。)

While creating directives, angularjs allows you to create an isolated scope with some bindings to the parent scope.

(在创建指令时,angularjs允许您创建一个隔离的作用域 ,其中包含一些与父作用域的绑定。)

These bindings are specified by the attribute you attach the element in DOM and how you define scope property in the directive definition object .

(这些绑定由您在DOM中附加元素的属性以及如何在指令定义对象中定义scope属性指定 。)

There are 3 types of binding options which you can define in scope and you write those as prefixes related attribute.

(您可以在范围中定义3种类型的绑定选项,并将它们写为前缀相关属性。)

angular.module("myApp", []).directive("myDirective", function () {
    return {
        restrict: "A",
        scope: {
            text: "@myText",
            twoWayBind: "=myTwoWayBind",
            oneWayBind: "&myOneWayBind"
        }
    };
}).controller("myController", function ($scope) {
    $scope.foo = {name: "Umur"};
    $scope.bar = "qwe";
});

HTML

(HTML)

<div ng-controller="myController">
    <div my-directive my-text="hello {{ bar }}" my-two-way-bind="foo" my-one-way-bind="bar">
    </div>
</div>

In that case, in the scope of directive (whether it's in linking function or controller), we can access these properties like this:

(在这种情况下,在指令范围内(无论是在链接函数还是控制器中),我们可以像这样访问这些属性:)

/* Directive scope */

in: $scope.text
out: "hello qwe"
// this would automatically update the changes of value in digest
// this is always string as dom attributes values are always strings

in: $scope.twoWayBind
out: {name:"Umur"}
// this would automatically update the changes of value in digest
// changes in this will be reflected in parent scope

// in directive's scope
in: $scope.twoWayBind.name = "John"

//in parent scope
in: $scope.foo.name
out: "John"


in: $scope.oneWayBind() // notice the function call, this binding is read only
out: "qwe"
// any changes here will not reflect in parent, as this only a getter .

"Still OK" Answer:(“还好”答案:)

Since this answer got accepted, but has some issues, I'm going to update it to a better one.

(由于这个答案已被接受,但有一些问题,我将把它更新为更好的答案。)

Apparently, $parse is a service which does not lie in properties of the current scope, which means it only takes angular expressions and cannot reach scope.

(显然, $parse是一种服务,它不属于当前范围的属性,这意味着它只需要角度表达式而无法达到范围。)

{{ , }} expressions are compiled while angularjs initiating which means when we try to access them in our directives postlink method, they are already compiled.

({{}}表达式是在angularjs启动时编译的,这意味着当我们尝试在我们的指令postlink方法中访问它们时,它们已经被编译。)

( {{1+1}} is 2 in directive already).

(( {{1+1}}已经是指令2 )。)

This is how you would want to use:

(这就是你想要使用的方式:)

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

myApp.directive('myDirective', function ($parse) {
    return function (scope, element, attr) {
        element.val("value=" + $parse(attr.myDirective)(scope));
    };
});

function MyCtrl($scope) {
    $scope.aaa = 3432;
}?

.

(。)

<div ng-controller="MyCtrl">
    <input my-directive="123">
    <input my-directive="1+1">
    <input my-directive="'1+1'">
    <input my-directive="aaa">
</div>????????

One thing you should notice here is that, if you want set the value string, you should wrap it in quotes.

(你应该注意的一件事是,如果你想设置值字符串,你应该用引号括起来。)

(See 3rd input)

((见第3条输入))

Here is the fiddle to play with: http://jsfiddle.net/neuTA/6/

(这是一个小提琴: http//jsfiddle.net/neuTA/6/)

Old Answer:(旧答案:)

I'm not removing this for folks who can be misled like me, note that using $eval is perfectly fine the correct way to do it, but $parse has a different behavior, you probably won't need this to use in most of the cases.

(我不会为那些像我一样被误导的人删除这个,请注意使用$eval是完全正确的方法,但$parse有不同的行为,你可能不需要在大多数情况下使用它案件。)

The way to do it is, once again, using scope.$eval .

(这样做的方法是再次使用scope.$eval 。)

Not only it compiles the angular expression, it has also access to the current scope's properties.

(它不仅可以编译角度表达式,还可以访问当前作用域的属性。)

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

myApp.directive('myDirective', function () {
    return function (scope, element, attr) {
        element.val("value = "+ scope.$eval(attr.value));
    }
});

function MyCtrl($scope) {

}?

What you are missing was $eval .

(你缺少的是$eval 。)

http://docs.angularjs.org/api/ng.$rootScope.Scope#$eval

(http://docs.angularjs.org/api/ng.$ro??otScope.Scope#$eval)

Executes the expression on the current scope returning the result.

(在返回结果的当前作用域上执行表达式。)

Any exceptions in the expression are propagated (uncaught).

(表达式中的任何异常都会被传播(未捕获)。)

This is useful when evaluating angular expressions.

(这在评估角度表达式时很有用。)


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...