Data-binding in a directive template

不羁的心 提交于 2019-12-10 20:14:04

问题


I'm trying to build a really basic Angular directive that generates a "div" that can have two states: "on" and "off".

I've naively come up with an implementation that you can find here: http://jsfiddle.net/wSz2f/

The initial display is correct but the visual state is not updated when the scope state changes.

Here is the Angular directive definition:

var test = angular.module("test", []);
test.directive("led", function()
{   
    return {
        restrict: "E",
        replace: true,
        template: "<div class='led led-off' ng-class='{ \"led-on\": isOn }'>{{isOn}}</div>",
        link: function(scope, element, attributes, controller)
        {
            scope.isOn = false;

            element.bind("click", function()
            {
                scope.isOn = !scope.isOn;
            });
        }
    };
});

I guess I'm doing something stupid but what...?

Moreover, in term of design, am doing it the "Angular way" or is there better practices?

Thanks for any input. :)


Final edit:

Thanks to Mark, Bertrand and James for their input:

  • you have to either call scope.$apply() after updating the "isOn" property to make Angular aware of its change (thinking about it this is how it works too in other frameworks like WPF/Silverlight with the INotifyPropertyChanged interface, but not in Flex with all its magic binding) or use ng-click like suggested by Bertrand
  • you have to provide "ng-class" a condition for each CSS class

回答1:


In your case you have to fire the digest

element.bind("click", function()
{
    scope.isOn = !scope.isOn;
    scope.$apply();
});

or even better, you could use the ng-click directive in your template to change the state of isOn.

var test = angular.module("test", []);
test.directive("led", function()
{   
    return {
        restrict: "E",
        replace: true,
        template: "<div class='led led-off' ng-class='{ \"led-on\": isOn, \"led-off\": !isOn }' ng-click='onOff()'>{{isOn}}</div>",
        link: function(scope, element, attributes, controller)
        {
            scope.isOn = false;

            scope.onOff = function () {
                scope.isOn = !scope.isOn;
            }
        }
   };
});

Here is a fiddle




回答2:


You're code looks good. You are missing the scope.$appy(); after updating the data. The exact internal reasons of why you need to call scope.$apply(); are only partly clear to me. I've read a few articles on it but am no expert yet.

Updated fiddle: http://jsfiddle.net/wSz2f/1/

Reading: http://jimhoskins.com/2012/12/17/angularjs-and-apply.html



来源:https://stackoverflow.com/questions/16798610/data-binding-in-a-directive-template

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!