2012-09-23 16 views
82

私はいくつかの動的な質問(フィドルhere)でフォームを移入します:AngularJSで動的モデル名を設定するにはどうすればよいですか?

<div ng-app ng-controller="QuestionController"> 
    <ul ng-repeat="question in Questions"> 
     <li> 
      <div>{{question.Text}}</div> 
      <select ng-model="Answers['{{question.Name}}']" ng-options="option for option in question.Options"> 
      </select> 
     </li> 
    </ul> 

    <a ng-click="ShowAnswers()">Submit</a> 
</div> 
​ 
function QuestionController($scope) { 
    $scope.Answers = {}; 

    $scope.Questions = [ 
    { 
     "Text": "Gender?", 
     "Name": "GenderQuestion", 
     "Options": ["Male", "Female"]}, 
    { 
     "Text": "Favorite color?", 
     "Name": "ColorQuestion", 
     "Options": ["Red", "Blue", "Green"]} 
    ]; 

    $scope.ShowAnswers = function() 
    { 
     alert($scope.Answers["GenderQuestion"]); 
     alert($scope.Answers["{{question.Name}}"]); 
    }; 
}​ 

すべてがモデルを除いて、作品は文字通り代わりに、評価の答え、[「{{question.Name}}」]回答されます["GenderQuestion"]そのモデル名をどのように動的に設定できますか?

答えて

112

http://jsfiddle.net/DrQ77/

あなたは、単にng-modelでJavaScript式を置くことができます。

+1

私はそれを試してみました誓います。どうもありがとうございました。私は実際に別のルートを行って、モデルをquestion.Answerに設定しました(ちょっと更新されたフィドルを出します)。これはより直接的な答えでした(jQueryの考え方から抜け出てください)。もともと、私が当初計画していたやり方で、私が実際にやることができることを知ってうれしいです。再度、感謝します! –

+5

fiddle:http://jsfiddle.net/2AwLM/23/ –

+0

これが他の人に役立つ場合、私は同様の問題を抱えていましたが、問題は私が 'ng-pattern =" field.pattern "'を使用していたことでした。私が本当に望んでいたのは 'pattern =" {{field.pattern}} "でした。その角度を混乱させる種類は、通常、動的属性のヘルパーを提供しますが、今回は独自のクライアント側の検証であり、同じ名前を付けました。 – colllin

10

私は何をやってしまったことは、このようなものです:コントローラで

link: function($scope, $element, $attr) { 
    $scope.scope = $scope; // or $scope.$parent, as needed 
    $scope.field = $attr.field = '_suffix'; 
    $scope.subfield = $attr.sub_node; 
    ... 

ので、私は完全に動的な名前を使用することができ、テンプレートでは、だけではなく、特定のハードコーディングされた要素の下に(あなたの「回答」の場合のように):

<textarea ng-model="scope[field][subfield]"></textarea> 

これは役に立ちます。

3

@abourgetによって提供される回答をより完全にするために、次のコード行のscopeValue [field]の値は未定義にすることができます。サブフィールド設定するときにこれはエラーになり:この問題を解決するための

<textarea ng-model="scopeValue[field][subfield]"></textarea> 

一つの方法を属性NGフォーカス=「nullSafe(フィールド)」を追加することですので、あなたのコードは以下のようになります。

<textarea ng-focus="nullSafe(field)" ng-model="scopeValue[field][subfield]"></textarea> 

次に、以下のようなコントローラにnullSafe(フィールド)を定義します。

$scope.nullSafe = function (field) { 
    if (!$scope.scopeValue[field]) { 
    $scope.scopeValue[field] = {}; 
    } 
}; 

これはscopeValue [フィールド] [サブフィールドに任意の値を設定する前にscopeValue [フィールド]が未定義されていないことを保証します]。

注:ng-modelが変更された後にng-changeが発生するため、同じ結果を得るためにng-change = "nullSafe(field)"を使用することはできません。scopeValue [field]定義されていません。

27

scopeValue[field]のようなものを使用できますが、フィールドが別のオブジェクトにある場合は別の解決策が必要です。状況のすべての種類を解決するために

、あなたはこのディレクティブを使用することができます。

this.app.directive('dynamicModel', ['$compile', '$parse', function ($compile, $parse) { 
    return { 
     restrict: 'A', 
     terminal: true, 
     priority: 100000, 
     link: function (scope, elem) { 
      var name = $parse(elem.attr('dynamic-model'))(scope); 
      elem.removeAttr('dynamic-model'); 
      elem.attr('ng-model', name); 
      $compile(elem)(scope); 
     } 
    }; 
}]); 

HTMLの例:

<input dynamic-model="'scopeValue.' + field" type="text"> 
+2

保存日: – WeMakeSoftware

+0

期待どおりに動作します。 – C0ZEN

+1

よろしく!これは私が必要なものです!ありがとうございました! – Snapman

関連する問題