Knockout.js从来自ajax请求'options'中选择'value'作为js对象



非顶部:标题很混乱,但我找不到正确的词语来描述我的处境,很抱歉。如果你能找到更好的,请推荐你的。我想我犯了一个简单的错误,因为我是knockout.js的新手,但我一整天都找不到它

这是我的:

<select data-bind="
    value: SelectedPm,
    options: PmList, 
    optionsText: 'Name'"></select>
<b>Selected PM:</b> <span data-bind="text: SelectedPm().Name"></span>

JavaScript:

function PmModel(data) {
    this.Name = data.Name;
    this.Company = data.Company;
    this.Division = data.Division;
    this.EmpNo = data.EmpNo;
}
function ViewModel() {
    // Data
    var self = this;
    self.PmList = ko.observableArray([]);
    self.SelectedPm = ko.observable();
    // Operations
    ko.computed(function () {
        $.getJSON("/CumulativeReport/GetPmList", function (allData) {
            var mappedTasks = $.map(allData, function (item) { return new PmModel(item); });
            self.PmList(mappedTasks);
        });
    });
}
ko.applyBindings(new ViewModel());

在这种情况下,我在控制台中得到下一个错误:未捕获错误:无法分析绑定。消息:TypeError:无法读取未定义的属性"Name";绑定值:text:SelectedPm((。名称

但当我不使用getJSON和使用一些模拟阵列时,它工作得很好

    function PmModel(data) {
        this.Name = data.Name;
        this.Company = data.Company;
        this.Division = data.Division;
        this.EmpNo = data.EmpNo;
    }
    function ViewModel() {
    // Data
    var self = this;
    self.PmList = ko.observableArray([]);
    self.SelectedPm = ko.observable();
    // Operations
    ko.computed(function () {
        self.PmList([{Name:'aaaa'}, {Name:'bbbb'}]);    
    });
}
ko.applyBindings(new ViewModel());

或者我是否将使用js字符串对象作为选项值

<select data-bind="
    value: SelectedPm,
    options: PmList, 
    optionsText: 'Name',
    optionsValue: 'Id'"></select>
<b>Selected PM:</b> <span data-bind="text: SelectedPm"></span>

JavaScript

function PmModel(data) {
    var self = this;
    this.Name = ko.observable(data.Name);
    this.Company = ko.observable(data.Company);
    this.Division = ko.observable(data.Division);
    this.EmpNo = ko.observable(data.EmpNo);
    this.Id = ko.computed(function () { return self.Company() + "-" + self.Division() + "-" + self.EmpNo(); });
}
function ViewModel() {
    // Data
    var self = this;
    self.PmList = ko.observableArray([]);
    self.SelectedPm = ko.observable();
    // Operations
    ko.computed(function () {
        $.getJSON("/CumulativeReport/GetPmList", function (allData) {
            var mappedTasks = $.map(allData, function (item) { return new PmModel(item); });
            self.PmList(mappedTasks);
        });
    });
}
ko.applyBindings(new ViewModel());

有人能指出我做错了什么吗?提前谢谢。


UPD1

我找到了让它发挥作用的方法。看起来不是很好,但至少它能

<select data-bind="
    value: SelectedPm,
    options: PmList, 
    optionsText: 'Name'"></select>
<!-- ko if: SelectedPm -->
<b>Selected PM:</b> <span data-bind="text: SelectedPm().Name"></span>
<!--/ko-->

我的猜测是,当ajax调用被触发时,敲除触发了PmList(SelectedPm(的依赖关系,并试图在UI中重新呈现依赖关系值,但请求处理的时间太长,新值没有及时传递到SelectedPm。它看起来不合法,首先是因为optionsValue版本运行良好。但我没有任何其他想法来解释它,所以这只是我的猜测,如果有人对它有更清晰的看法或答案,请分享。

问题是,当您将视图模型绑定到页面时,SelectedPm只是一个空的可观察对象,因此调用SelectedPm().Name会失败,因为没有name属性。我不知道这样做是否正确,但我只是用我想要的命名属性初始化变量:

self.SelectedPm = ko.observable({ Name: '' });

这样,第一次绑定到页面时就不会出现问题。

最新更新