2013-07-29 18 views
5

że mam tę tablicę obiektów tego samego typu:Turn pewien observableArray właściwości obiektów do zaobserwowania

var people = [ 
    { status: 0, name: "name1"}, 
    { status: 1, name: "name2"} 
]; 

i chcę to nie tylko być observableArray, ale również chcę obserwować jedynie np właściwość statusu każdego obiektu.

Wyobraź sobie, że same obiekty mogą zostać dodane lub usunięte. Własność nazwy któregokolwiek z tych obiektów nie zmieni się, więc naprawdę nie muszę obserwować nazwy, ale status każdego obiektu może się zmienić, więc byłoby fajnie uczynić to zauważalnym.

Czy można go zamapować za pomocą nokautów z pewną fajną składnią hackowania, czy też muszę przetestować każdy obiekt i odwzorować jego własność statusową na obserwowalną lub mieć widoczną całą tablicę i jej właściwości?

Odpowiedz

5

Można użyć ko.mapping.fromJS

var vm = ko.mapping.fromJS(people,{ 
    create: function(options){  
     return { 
      status : ko.observable(options.data.status), // observable 
      name: options.data.name, // non observable 
     } 
    } 
}); 

Teraz VM jest observableArray który zawiera obiekty, w których stan jest obsevable i nazwa jest regularny nieruchomość.

See fiddle

@Patryk:

Można to zrobić, jeśli masz wiele właściwości i chcesz przekonwertować tylko jeden do zaobserwowania.

var o = ko.mapping.fromJS(people,{create: function(options){ 
    // clone item 
    var item = ko.utils.extend(options.data, {}); 
    // replace status property by an observable 
    item.status = ko.observable(options.data.status); 
    return item; 
}}); 

See updated fiddle

Można również użyć observe z parametrem mapowania

var mapping = { 
    create: function (options) { 
     return ko.mapping.fromJS(options.data, {'observe': ["status"]}); 
    } 
}; 
var o = ko.mapping.fromJS(people, mapping); 

See fiddle

Mam nadzieję, że to pomaga.

+1

A jeśli obiekt ma znacznie więcej właściwości, z których chcę, aby jeden był zauważalny, czy muszę jawnie wymieniać każdą właściwość, niezależnie od tego, czy jest obserwowalna czy nie? – patryk

+0

Przyszło coś takiego, ale twoja droga wygląda bardziej profesjonalnie: D co mnie ciekawi jest prostą rzeczą: jest 'var vm = ko.mapping.fromJS (data, {});' taki sam jak 'var vm; ko.mapping.fromJS (data, {}, vm); ' – patryk

+0

Pierwsze połączenie dotyczy pierwszego połączenia, a drugie dotyczy aktualizacji. Aktualizacja "oznacza", gdy otrzymujesz "świeże" dane z serwera i musisz zaktualizować istniejący model podglądu. – Damien

1

Proponuję użyć copy

więc można podać szereg właściwości, które mają nie być obserwable.

var mappingPeople = { 
    'copy': ["name"] 
}; 

var mapping = { 
    create: function (opts) { 
     return ko.mapping.fromJS(opts.data, mappingPeople); 
    } 
}; 
var PeopleArr = ko.mapping.fromJS(people, mapping); 

tutaj jest Working Demo

Aktualizacja

W przypadku trzeba zaznaczyć jedną właściwość jako obserwowalne i reszta „ll być normalne właściwości to proponuję użyć observe.

tutaj jest aktualizacja do mojego Example użyciu observe

+0

To wciąż sprawia, że ​​muszę wymienić wszystkie właściwości, których nie chcę być obserwowalne, które stanowią większość. Moim celem było wymienić tylko tych, których chcę obserwować. Zrobiłem to w sposób, który sugerował Damien, niezupełnie taki czysty i nokautowy, ale zadziałało. – patryk

+0

@patryk w takim przypadku musisz użyć "obserwuj" http://knockoutjs.com/documentation/plugins-mapping.html#observing_only_certain_properties_using_observe –

+0

@patryk sprawdź moją aktualizację –

0

Wiem, że to pytanie jest stary, ale w obliczu tego samego problemu i znaleźć proste rozwiązanie bez użycia wtyczek.

Załóżmy, że wykonujesz żądanie pobrania i zwrócisz tablicę wpisów.Dla każdego wpisu masz właściwość o nazwie "Ulubiony", która jest wartością logiczną wskazującą, czy post jest preferowany przez użytkownika, czy nie, i chcesz uczynić tę właściwość obserwowalną, abyś mógł pracować w funkcji zmieniającej jej stan.

Można wykonać następujące czynności:

function ViewModel() { 
    var self = this; 
    self.posts = ko.observableArray([]); 

    $.getJSON("/api/getPosts", function(data) { 
    ko.utils.arrayForEach(data, function(post) { 
    post.Favorited = ko.observable(post.Favorited) 
    }); 
    self.posts(data) 
    }); 
} 

ten sposób można włączyć Ulubione właściwości obserwowanej z jego wartości, a można przekształcić dowolny obiekt obserwowalne robi to samo wewnątrz metody arrayForEach.

Powiązane problemy