2013-04-02 51 views
0

我有一個使用Knockout的CRUD單頁,一切正常,我從JSON調用中獲取數據,它使用對象列表填充自動映射的可觀察數組。 我可以在該數組中添加或編輯單個項目。具有格式化(計算?)列的自動映射陣列

問題出現在格式化一個貨幣(數字)列,我在表中顯示的對象列表。我試過用很多方法使用js函數,但是當我更新一個項目時,表格的格式化貨幣數量不會更新。 如果我使用綁定來格式化字段,那麼我無法編輯它,因爲它轉換爲字符串。

我需要的是我的貨幣列的單向綁定(自動更新)格式化列。但我無法立即創建計算列,因爲我使用的是自動映射的對象數組。我嘗試使用http://knockoutjs.com/documentation/plugins-mapping.html中的示例添加計算,但我不知道如何將其與映射數組一起使用。

我的視圖模型是這樣的:

//--Accounts - Viewmodel Knockout 
function accountViewModel() { 
    var self = this; 
    self.accounts = ko.observableArray(); //this is the list of objects 
    self.account = ko.observable(); //single item for creating or editing 

    //--get list------ 
    self.getAccounts = function() { 
     $.postJSON(appURL + 'Accounts/GetList', function (data) { 
      ko.mapping.fromJS(data.Records, {}, self.accounts); 

     }); 

    }; 

    self.getAccounts(); 
} 

每個帳戶的項目有這樣的字段: -Id 雜牌 - 剩餘< - 這是我想格式化

使用列它在頁面中:

<table data-bind="visible: accounts().length > 0"> 
<thead> 
    <tr> 
     <th scope="col">Id</th> 
     <th scope="col">Name</th> 
     <th scope="col">Balance</th> 
    </tr> 
</thead> 
<tbody id="accounts" data-bind="foreach: accounts"> 
<tr> 
    <td><span data-bind="text: Id"></span></td> 
    <td><a href="" data-bind="text: Name, click: $root.getdetails" style="display:block;"></a></td> 
    <td style="text-align:right;"> 
     <span data-bind="text: formatCurrency(Balance), css: { negative: Balance() < 0, positive: Balance() > 0 }"></span> 

    </td> 
</tr> 
</tbody> 
</table> 

formatCurrency是格式化的js函數數字:

formatCurrency = function (value) { 
    debugger; 
    if (value!=undefined) 
     return "$" + withCommas(value().toFixed(2)); 
    //had to use value() instead of value, because of toFixed 
} 

謝謝!

+0

可能重複如何使用映射插件並對映射對象進行計算:http://stackoverflow.com/questions/15480316/knockout-dynamic-binding-issue/15480602#15480602 –

回答

0

將文本設置爲函數的返回值(text: formatCurrency(Balance))時,它只運行一次。這不是可觀察的,所以它的價值永遠不會再更新。你需要的是一個真正的藍色計算觀察值。爲了得到這個,你必須定製映射。因此,簡單地爲您的個人賬戶對象創建一個視圖模型,然後將返回的數據映射到該模型上。

var SingleAccountViewModel = function (account) { 
    var model = ko.mapping.fromJS(account); 

    model.FormattedBalance = ko.computed(function() { 
     return formattedCurrency(model.Balance); 
    }); 

    return model; 
} 

然後,當你從你的Ajax響應讓您的數據備份:

$.postJSON(appURL + 'Accounts/GetList', function (data) { 
    self.accounts($.map(data.Records, SingleAccountViewModel)); 
}); 

的jQuery.map方法將通過遍歷數組,並返回傳遞的函數的返回值組成的新數組。在這種情況下,這是您的視圖模型,現在將有一個您可以綁定到的計算上的FormattedBalance

+0

剛剛實現,現在我在我的模型中得到了計算列。但是,在更新餘額時,FormattedBalance仍然不會更新。 – pedroren

+0

這是使用帶有observableArray的foreach的問題。只有對數組本身所做的更改纔會觸發更新,而不會更改數組中的對象*。所以你必須觸發對數組的更改以強制更新值。這樣做的懶惰方式是簡單地獲取並設置observableArray的值,它將更新整個塊。這個問題有一個稍微更多的方式來做到這一點:http://stackoverflow.com/questions/8861106/updating-an-observablearray-does-not-update-ui –

+0

對不起,執行計算列後,我didn'噸通知我修改餘額字段後得到另一個錯誤。由於某種原因,Knockout將它轉換爲String,所以我在formatCurrency函數內得到了一個「對象沒有固定的方法」。我通過明確地將該值轉換爲浮動來解決這個問題。現在它工作了!謝謝! – pedroren