2016-04-22 61 views
2

我有以下的(https://jsfiddle.net/f30bj43t/5/)HTML:Angular定製驗證指令。獲得從視圖模型錯誤

<div ng-controller="DataController as vm"> 
    <div ng-repeat="name in vm.users track by $index">{{name}}</div> 
    <form name="form" validation="vm.errors"> 
    <input validator ng-model="vm.name" name="vm.name" placeholder="name" type="text" /> 
    <a href="#" ng-click="vm.add(vm.name)">Add</a> 
    </form> 
</div> 

這種形式增加了名稱列表,並且控制器是:

app.controller("DataController", DataController); 

function DataController() { 
    var vm = this; 
    vm.name = "Mary"; 
    vm.users = ["Alice", "Peter"]; 
    vm.errors = []; 
    vm.add = function(name) { 
    if (name == "Mary") { 
     var error = { property: "name", message: "name cannot be Mary"}; 
     if (vm.errors.length == 0) 
     vm.errors.push(error);   
     } else { 
     vm.users.push(name);  
     vm.errors = []; 
     }  
    } 
} 

在我加入validation="vm.errors"形式它定義了哪個變量保存了要在每個驗證器指令中使用的錯誤...

Th連接在每個驗證指令,我將使用該變量來選擇正確的錯誤,並顯示它...

app.directive("validation", validation); 

function validation() { 

    var validation = { 
    controller: ["$scope", controller], 
    replace: false, 
    restrict: "A", 
    scope: { 
     validation: "=" 
    } 
    }; 

    return validation; 

    function controller($scope) { 
    this.getErrors = function() { 
     return $scope.validation; 
    }  
    } 

} 

app.directive("validator", validator); 

function validator() { 

    var validator = { 
    link: link, 
    replace: false, 
    require: "^validation", 
    restrict: "A" 
    }; 

    return validator; 

    function link(scope, element, attributes, controller) {  
    var errors = controller.getErrors(); 
    console.log(errors);  
    // do something with errors 
    } 

} 

問題

在驗證指令鏈接功能,我需要跟蹤變更通過驗證=「vm.errors」傳遞的變量,所以我可以在每個驗證程序檢查是否發生錯誤並採取行動。

但執行console.log(錯誤)似乎沒有任何效果...

我怎樣才能解決這個問題?

+0

您是否測試的jsfiddle?它不能正常工作 –

+0

只是更新它:https://jsfiddle.net/f30bj43t/5/。順便說一句,前一個提琴手的問題是,將驗證器從窗體移動到外部div,我有控制器給了我那個錯誤......這也是我想要解決的問題。 –

回答

1

您可以使用$watch$broadcast$on
我主張使用$on,因爲觀看一個變量比聽一個事件消耗的更多,我會說你的情況最好使用$ broadcast和$ on,因爲你沒有看範圍變量,但是來自控制器的變量。

如果您想了解更多關於$上$手錶,這裏有一個建議:Angular JS $watch vs $on

而且這裏是你的JSFiddle與修改。

+0

Gabriel,不幸的是我不能使用你的例子,因爲我需要在指令方面完成所有工作......所以它必須是一個指令,以監視在validation =「vm.errors」中定義的變量中發生了什麼。所以我認爲這樣做的方式是使用手錶。我的想法是這樣的:https://jsfiddle.net/q0dy20nv/1/ ...你能幫我做這項工作...這是我最大的問題。 –

+0

對不起,我花了這麼長時間來回答,我一直很忙。現在我剛剛更新了JSFiddle,請檢查並告訴它是否滿足您的需求。 =) –

+0

我遵循你的例子,但發生了一些奇怪的事情。如果這個變量不是一個數組,而是我觀察它而不是看它的長度,那麼這隻手錶只會觸發一次......你知道爲什麼嗎?我用這個改變分叉了你的例子:https://jsfiddle.net/qb8o006h/2/ –

1

在這裏,你有一個工作的jsfiddle:https://jsfiddle.net/f30bj43t/8/

我登錄了vm.errors變量到控制檯在它每次更改時間:

function link(scope, element, attributes, controller) { 
    scope.$watch('vm.errors.length', function() { 
     if(scope.vm.errors){ 
      console.log(scope.vm.errors); 
     } 
    }); 
} 

這是可能的,因爲範圍繼承。在你的情況下,vm是一個添加到控制器作用域的變量,默認情況下,此作用域內的所有指令都會繼承它(有辦法避免這種情況)。

無論如何,它似乎是你創造了太多的指令。在你的情況下,對我來說,掌握控制器中的所有東西就足夠了。

乾杯

哈維爾

+0

對不起,但那對我不起作用......我已經這樣做了。問題是在一個頁面中,我可能有多個控制器與vm1,vm2等...這就是爲什麼我使用驗證=「vm.errors」。指出錯誤在哪裏。這是我的主要問題......我需要能夠在validation =「vm1.errors」中指明要監視的變量。看看爲什麼你的例子不起作用:https://jsfiddle.net/cLqa1gqd/1/。 –