2012-02-22 32 views
6

Tôi đang ràng buộc dữ liệu đến một trang sử dụng KnockoutJS, ViewModel đang được dân cư bởi một phản ứng JSON từ một cuộc gọi AJAX sử dụng mapping plugin, như thế này:KnockoutJS - Thêm giá trị tính đến một mảng quan sát

$(function() { 
    $.getJSON("@Url.Action("Get")", 
     function(allData) { 
      viewModel = ko.mapping.fromJS(allData); 

      viewModel.Brokers.Url = ko.computed(function() 
      { 
       return 'BASEURLHERE/' + this.BrokerNum(); 
      }); 

      ko.applyBindings(viewModel); 
    }); 
}); 

Phần giữa không hoạt động (nó hoạt động tốt mà không có thuộc tính được tính toán đó). "Nhà môi giới" là một mảng có thể quan sát được và tôi muốn thêm giá trị được tính vào mọi phần tử trong mảng được gọi là URL. Tôi đang ràng buộc rằng mảng môi giới cho một foreach, và tôi muốn sử dụng URL đó là thuộc tính href của một neo. Bất kỳ ý tưởng?

Trả lời

12

Vâng, nếu bạn muốn Url trong mỗi nhà môi giới, bạn phải thêm nó vào từng môi giới:

$.each(viewModel.Brokers(), function(index, broker){ 
    broker.Url = ko.computed(function(){return 'BASEURLHERE/' + broker.BrokerNum();}); 
}); 

Tôi đoán BrokerNum sẽ không thay đổi, vì vậy bạn cũng có thể chỉ tính toán Url lần:

$.each(viewModel.Brokers(), function(index, broker){ 
    broker.Url = 'BASEURLHERE/' + broker.BrokerNum(); 
}); 

Bạn cũng có thể thêm thuộc tính Url trong khi ánh xạ bằng cách cung cấp gọi lại "tạo" cho hàm ko.mapping.fromJS. Xem mapping plugin docs để biết chi tiết.

Nếu bạn chỉ cần url liên kết với href, chỉ ràng buộc các biểu hiện trong html (trong vòng foreach ràng buộc):

<a data-bind="attr: {href: 'BASEURLHERE/' + BrokerNum()}">link to broker details</a> 
11

Tôi đã làm việc thông qua các vấn đề rất giống nhau và tôi đã phát hiện ra rằng bạn có thể ngăn chặn việc tạo ra các đối tượng môi giới và chèn các lĩnh vực của riêng bạn bằng cách sử dụng tùy chọn lập bản đồ tham số:

var data = { "Brokers":[{"BrokerNum": "2"},{"BrokerNum": "10"}] }; 

var mappingOptions = { 
    'Brokers': { 
     create: function(options) { 
      return (new (function() { 
       this.Url = ko.computed(function() { 
        return 'http://BASEURLHERE/' + this.BrokerNum(); 
       }, this); 

       ko.mapping.fromJS(options.data, {}, this); // continue the std mapping 
      })()); 
     } 
    } 
}; 

viewModel = ko.mapping.fromJS(data, mappingOptions); 

ko.applyBindings(viewModel); 

Dưới đây là một fiddle để chứng minh điều này: http://jsfiddle.net/pwiles/ZP2pg/

+0

Cách tiếp cận này hoạt động như một sự quyến rũ! – Tobscher

0

Cám ơn Peter Wiles tôi có giải pháp rất giống nhau:

var ViewModel = function (data, ranges) { 
    var self = this; 

    this.productList = ko.observableArray(); 
    var productListMapping = { 
     create: function (options) { 
      return (new (function() { 
      //this row above i don't understand... 
       this.len = ko.computed(function() { 
        //just test function returning lenght of object name 
        // and one property of this model 
        return this.name().length + ' ' + self.cons_slider_1(); 
       }, this); 

       ko.mapping.fromJS(options.data, {}, this); // continue the std mapping 
      })()); 
     } 
    } 

    this.cons_slider_1 = ko.observable(100); 

    ko.mapping.fromJS(data, productListMapping, this.productList); 
}; 

Một số khác biệt: Tôi không lập bản đồ tự, nhưng trên this.product. Các json đầu vào có tên không mẹ như 'môi giới' trong ví dụ trên:

var products = [ 
    { "id": "pp1", "name": "Blue windy" }, 
    { "id": "pp1", "name": "Blue windy" }]; 

Vì vậy, trong productMapping tôi đang gõ chỉ 'tạo:'

Nhưng, những gì tôi không hiểu là cấu trúc của tạo hàm. Ai đó có thể giải thích cho tôi tại sao hàm trả về hàm mới, có thuộc tính. Nó có thể được đơn giản hóa bằng cách nào đó?

Các vấn đề liên quan