2013-01-11 151 views
2

我有一個分層視圖模型更新子屬性

我的視圖模型在一定程度上構成這樣與淘汰賽js和映射插件的問題:

VM = { 
    members:[ 
     { 
      name:"name 1", 
      volunteering:[{...},{...},{...}] 
     }, 
     { 
      name:"name 1", 
      volunteering:[{...},{...},{...}] 
     } 
    ] 
} 

每個成員在一個標籤中,每個標籤都有一個志願活動網格。點擊網格中的項目,彈出一個對話框來編輯志願活動。 此時我克隆對象,以促進「取消編輯」功能

var Volunteer = {}; 
var koContext=ko.contextFor(this); 
Volunteer = ko.mapping.toJS(koContext.$data); //plain js volunteer 
Volunteer.index=koContext.$parent.EventVolunteers().indexOf(koContext.$data); //index of volunteer in member volunteer array 
ko.applyBindings(ko.mapping.fromJS(Volunteer),$("#dialog-EditVolunteer")[0]); //bind new volunteer obj to dialog 

到目前爲止似乎確定,單擊保存對話框上導致該問題。

var volunteer = ko.mapping.toJS(ko.contextFor(this).$data); 
ko.mapping.fromJS(volunteer,{},ko.contextFor(currentTab).$data.EventVolunteers()[volunteer.index]); 

此時的屬性得到的視圖模型更新,但不是在主屏幕上的網格。

看起來ko.mapping.fromJS取代了observable而不是更新它。

回答

0

在這種情況下,我最終的解決方案是使用「克隆」視圖模型中的編輯值設置原始VM上的屬性。

對於新的項目不過,我現在用一個knockout plugin

0

就我個人而言,我是創建模型的粉絲。這裏的抽象只是更有意義。

function VolunteerInfo(data){ 
    var self = this; 
    self.activitiesName = ko.observable(data.name); 
    // any other info not all of it has to be mapped 
    // unless you plan on sending it back. 
} 
function MembersInfo(data){ 
    var self = this; 
    self.name = ko.observable(data.name)// w.e it is labeled as under json 
    self.volunteering = ko.observableArray([]); 
    var mappedVolunteers = $.map(data.volunterring, function(item){ 
    var volunteer = new VolunteerInfo(item); 
    return volunteer; 
    }); 
    self.volunterring(mappedVolunteers); 
} 
function VM(){ 
    var self = this; 
    self.members = ko.o 
    var request = $.getJSON("webservice address"); 
    request.done(function() { 
    var mappedMembers = $.map(data.volunterring, function(item){ 
     var member = new MemberInfo(item); 
     return member; 
    }); 
    self.members(mappedMembers); 
    } 
} 
// apply bindings to VM ect ect. 
+0

希望避免這是有問題的對象圖大,比這更復雜,這只是其中的一個部分,因此使用ko.mapping的首先插件。 – stevenrcfox

+0

同樣在這個模型中,你如何支持取消更新(本質上是我的問題的來源) – stevenrcfox

+0

爲什麼你需要克隆對象。只需將彈出窗口綁定到同一個對象。或者,如果您希望能夠取消更新,請保留對原始對象的引用,然後將克隆對象的值更新爲原始對象。 –

0

我不確定我完全明白你在做什麼。

但我試圖做的項目列表撤消功能,我用這個陣列上:

observableArray.replace(newData, ko.mapping.fromJS(original)) 

我得到的新數據,單擊處理程序的參數。

當我保存原來的,我基本上有這樣的:

 //Dupe check 
     self.undoCache.Emails.pop(jQuery.grep(self.undoCache.Emails, function (element, index) { return element.Id == data.Id(); })[0]); 
     //Store original 
     self.undoCache.Emails.push(ko.mapping.toJS(data)); 

的「電子郵件」是我編輯的對象。我只存儲原始數據,而不是可觀察數據。這讓我可以使用替換。我不確定這本身有多正確,但取消了我的作品。