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
400 views
in Technique[技术] by (71.8m points)

javascript - Is there a way to watch attribute changes triggered from outside the AngularJS world?

I’m trying to understand interactions between the Angular world and the non-Angular world.

Given a directive that one declares like this:

<dir1 id="d1" attr1="100"/>

If code outside angular changes the directive this way:

$("#d1").attr("attr1", 1000);

How can the directive know that one of its attribute has changed?

See Question&Answers more detail:os

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

1 Reply

0 votes
by (71.8m points)

It would be best to make this change inside the directive instead. If, for whatever reason, that's not possible, then there are a couple of options.

Outside the app, get a reference to any DOM element within the app. Using that reference, you can then get a reference to its scope. You could use your element with id d1. For example:

var domElement = document.getElementById('d1');
var scope = angular.element(domElement).scope();

Here are a couple of options:

Option 1

Modify the model instead of making a direct change to the view. In the link function, store the initial attribute value in a scope variable like:

scope.myvalue = attrs.attr1;

Then you can change the value outside the app (using the above reference to scope) like:

scope.$apply(function(){
    scope.myvalue = 1000;
    console.log('attribute changed');
});

Here is a fiddle

Option 2

If the view is manipulated directly with jQuery, I don't know of any use of $observe, $watch, or an isolate scope binding to the attribute that will work, because they all bind to the attribute expression itself, just once, when the link function is first run. Changing the value will cause those bindings to fail. So you'd have to $watch the attribute on the DOM element itself (rather than through attrs):

scope.$watch(function(){         
    return $(el).attr('attr1');    // Set a watch on the actual DOM value
}, function(newVal){
    scope.message = newVal;
});

Then you can change the value outside the app (using the above reference to scope) like:

scope.$apply(function(){
    $("#d1").attr("attr1",1000);
});

Here is a fiddle


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

...