Dinamik olarak ng modeli atama


82

Bir nesne dizisinden bir dizi onay kutusu oluşturmaya çalışıyorum. Diziye gönderilecek olan yeni nesnenin bir özelliği ile onay kutularının dinamik olarak kendi ng modelini eşleştirmesini hedefliyorum.

Aklımdaki şey şöyle bir şey

<li ng-repeat="item in items">
    <label>{{item.name}}</label>
    <input type="checkbox" ng-model="newObject.{{item.name}}">
</li>

Bu, JSFiddle'da görüldüğü gibi çalışmaz:

http://jsfiddle.net/GreenGeorge/NKjXB/2/

Biri yardım edebilir mi?

Yanıtlar:


146

Bu size istediğiniz sonuçları vermelidir:

<input type="checkbox" ng-model="newObject[item.name]">

İşte çalışan bir bilgi: http://plnkr.co/edit/ALHQtkjiUDzZVtTfLIOR?p=preview


1
hmm aslında bu gerçekten bana '<input ng-model = "newObject [item.name]">' verdi, eksik olan bir şey mi?
George Ananda Eman

Hmm, tuhaf, canlı bir örnek ekledi (plunker çünkü nedense jsFiddle benim tarafımda çalışmıyor).
pkozlowski.opensource

ah evet, php'de düşünmeye alışmıştım ve gerçek işaretlemenin isme değişmesini bekledim, işe yaradı. Teşekkür!
George Ananda Eman

2
Harika, tam olarak aradığım şey. Angular'ı seviyorum!
SharkofMirkwood

1
Ayrıca Angular 2'de de harika çalışıyor. Fakat çok boyutlu nesneler için bir çözüm var mı? Senin örnekte, eğer item.namebazen işaret etmelidir newObject['x']ve bazen newObject['x']['y'].
Martin Schneider

23

DÜZENLEME Bunu ng-değişikliğiyle kullanan yorumlarda doğru bir şekilde belirtildiği gibi, önceden bir "kukla" ng modelinin mevcut olmasını gerektirir. Bununla birlikte, 1.3 ile birlikte gerekli seçeneklerin çerçeve tarafından sağlandığı unutulmamalıdır. Lütfen aşağıdaki https://stackoverflow.com/a/28365515/3497830 adresini kontrol edin ! /DÜZENLE

Daha karmaşık bir göreve sahipken basit bir vakada tökezlediğim gibi, keyfi ifadeleri ng-modeline dinamik olarak bağlamak için bulduğum çözüm budur: http://plnkr.co/edit/ccdJTm0zBnqjntEQfAfx?p = önizleme

Yöntem: Standart bir açısal ifade alan, değerlendiren ve sonucu kapsam ile ng-model ve $ compile ile ilişkilendiren bir dynamicModel yönergesi oluşturdum.

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

app.controller('MainCtrl', function($scope) {
  $scope.data = {};
  $scope.testvalue = 'data.foo';
  $scope.eval = $scope.$eval;
});

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

app.controller('MainCtrl', function($scope) {
  $scope.data = {};
  $scope.testvalue = 'data.foo';
  $scope.eval = $scope.$eval;
});

app.directive('dynamicModel', ['$compile', function ($compile) {
    return {
        'link': function(scope, element, attrs) {
            scope.$watch(attrs.dynamicModel, function(dynamicModel) {
                if (attrs.ngModel == dynamicModel || !dynamicModel) return;

                element.attr('ng-model', dynamicModel);
                if (dynamicModel == '') {
                    element.removeAttr('ng-model');
                }

                // Unbind all previous event handlers, this is 
                // necessary to remove previously linked models.
                element.unbind();
                $compile(element)(scope);
            });
        }
    };
}]);

Kullanım, basitçe dynamic-model = "angularExpression" şeklindedir; burada angularExpression, ng modeli için ifade olarak kullanılan bir dizeyle sonuçlanır.

Umarım bu, birini bu çözümü bulmanın baş ağrısından kurtarır.

Saygılarımızla, Justus


3
Sen bir hayat kurtarıcısın. Bu yazıyı bulmadan önce neredeyse umutsuzluğa kapılmıştım.
Nelo Mitranim

Daha açık konuşabilir misin Brian? Ne denedin ve ne oldu?
Justus Wingert

Bu, bir çözümün rekabet mücevheri. Beni çok yapışkan bir sorundan kurtardınız - teşekkürler!
Mikebert4

1
ng-değişim bununla çalışmaz. Açısal kaynağa bakarsanız, ngChange yönergesinin gerekli bir yönerge olarak ngModel'i vardır. Hızlı bir arama sadece ngChange ve ngList'de bu sorunu gösterir. Diğer tüm direktiflerde isteğe bağlı bir denetleyici olarak ngModel vardır. Dinamik model direktifini kullanarak herhangi bir öğeye ng-model = "dummyValue" ekleyerek bu sorunu aştım. Dinamik modelde yapılan bir değişiklik $ compile, ngChange ve ng-model değerini kullanan diğer yönergeleri çağırdığından, doğru şekilde güncellenir.
EverPresent

1
Dinamik model değer değişimini izlemeniz gerekmediğinde bu daha sağlam bir çözümdür - stackoverflow.com/a/32096328/887092
Todd

6

Angular 1.3 ile ng-model-optionsmodeli dinamik olarak atamak veya bir ifadeye bağlanmak için yönergeyi kullanabilirsiniz .

İşte bir plunkr: http://plnkr.co/edit/65EBiySUc1iWCWG6Ov98?p=preview

<input type="text" ng-model="name"><br>
<input type="text" ng-model="user.name" 
ng-model-options="{ getterSetter: true }">

ngModelOptionsBurada daha fazla bilgi : https://docs.angularjs.org/api/ng/directive/ngModelOptions


Bir şeyi kaçırırsam beni affet, ama senin pisliğinle ilgili hiçbir şey dinamik model atamasını içermiyor gibi görünüyor. Ve ngModelOptions hakkında hiçbir şey açıkça bunu desteklemez. Açıklayabilir misin? Çünkü, aslında bu şekilde çalışsaydı süper yararlı olurdu ...
XML

@XMLilley "getterSetter: ngModel'e bağlı işlevlerin alıcı / ayarlayıcı olarak ele alınıp alınmayacağını belirleyen boole değeri."
Chris Bolton

Buna dikkatimi çektiğiniz için teşekkürler Rob, cevabımı güncelledim ve sizinkine bağladım.
Justus Wingert

1

Bu, daha derin ifadeyi destekleme yaklaşımımdır, örneğin 'model.level1.level2.value'

<input class="form-control" ng-model="Utility.safePath(model, item.modelPath).value">

Burada item.modelPath = 'level1.level2' ve Utility (model, 'level1.level2') model.level1.level2'yi döndüren yardımcı program işlevidir.


Bunun nasıl çalıştığını genişletebilir misin? Utility.safePath, daha sonra .value kullanabilmeniz için ne döndürür?
Devon Holcombe

Utility.safePath, yol dizesi tarafından belirtilen yuvalanmış değişkenin değerini döndürür. örneğin level1.level2, model.level1.level2'yi ifade eder.
Kanıt Mekritthikrai

0

<!DOCTYPE html>
<html>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.6.4/angular.min.js"></script>
<body>

    <div ng-app="myApp" ng-controller="myCtrl">
        <form name="priceForm" ng-submit="submitPriceForm()">
            <div ng-repeat="x in [].constructor(9) track by $index">
                <label>
                    Person {{$index+1}} <span class="warning-text">*</span>
                </label>
                <input type="number" class="form-control" name="person{{$index+1}}" ng-model="price['person'+($index+1)]" />

            </div>
            <button>Save</button>
        </form>
    </div>

    <script>
        var app = angular.module('myApp', []);
        app.controller('myCtrl', function ($scope) {
            $scope.price = [];
            $scope.submitPriceForm = function () {
                //objects be like $scope.price=[{person1:value},{person2:value}....]
                console.log($scope.price);
            }
        });
    </script>
</body>
</html>

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.