通过淘汰赛更新剃刀收集

问题描述 投票:1回答:1

我有这个UI

enter image description here

我的目标是在根据Id和Description参数单击Update按钮后更新表

我有以下代码

HTML

<table class="table table-bordered table-striped table-hover">
    <thead>
        <tr>
            <th>Id</th>
            <th>Description</th>
        </tr>
    </thead>
    <tbody>
        @foreach (var item in Model.Products)
        {
            <tr>
                <td>@item.Id</td>
                <td>@item.Description</td>
            </tr>
        }
    </tbody>
</table>

<label>Id</label>
<input data-bind="value: productId" type="text" class="form-control" />

<br />

<label>Description</label>
<input data-bind="value: productDescription" type="text" class="form-control" />

<br />

<button class="btn btn-primary" data-bind="click: update">Update</button>

JavaScript的

<script type='text/javascript'>

            // Plain javascript alternative to jQuery.ready.
            (function () {

                // Convert server model to json object.
                var json = {"products":[{"id":1,"description":"Product A"},{"id":2,"description":"Product B"},{"id":3,"description":"Product C"}],"categoryName":"chocolates"};

                function viewModel()
                {
                    var index;

                    // Store default this to self, to be able use self in subfunctions.
                    var self = this;

                    // Product array from server.
                    self.products = json.products;

                    // Automatic refreshed parameter in UI.
                    self.categoryName = ko.observable(json.categoryName);

                    // Update form parameters.
                    self.productId = null;
                    self.productDescription = null;

                    // Update function.
                    self.update = function () {

                        // Get products collection index.
                        index = self.products.findIndex(function (product) {
                            return product.Id == self.productId
                        });

                        // Throws -1, index was not found !
                        alert(index);

                        // Assign new value.
                        // self.products[index].description(self.productDescription);
                    };
                }

                // Apply viewModel to UI
                ko.applyBindings(new viewModel());

            })();

    </script>

我需要帮助两件事

  1. 更新knockout viewmodel(基于viewModel.Update函数中Id和Description输入的self.products集合)
  2. 更新表(我不知道如何绑定行,当使用razor foreach时)

编辑:

当我用Knockout foreach更改Razor循环时

<tbody data-bind="foreach: products">
        <tr>
            <td data-bind="text: id"></td>
            <td data-bind="text: description"></td>
        </tr>
    </tbody>

它也不起作用:/我尝试使用observable进行一些更改

 <script type='text/javascript'>

            // Plain javascript alternative to jQuery.ready.
            (function () {

                // Convert server model to json object.
                var json = {"products":[{"id":1,"description":"Product A"},{"id":2,"description":"Product B"},{"id":3,"description":"Product C"}],"categoryName":"chocolates"};

                function viewModel()
                {
                    var index;

                    // Store default this to self, to be able use self in subfunctions.
                    var self = this;

                    // Product array from server.
                    self.products = ko.observable(json.products);

                    // Automatic refreshed parameter in UI.
                    self.categoryName = ko.observable(json.categoryName);

                    // Update form parameters.
                    self.productId = ko.observable();
                    self.productDescription = ko.observable();

                    // Update function.
                    self.update = function () {

                        self.products()[self.productId()-1].description = self.productDescription()    
                    };
                }

                // Apply viewModel to UI
                ko.applyBindings(new viewModel());

            })();

    </script>

我没有收到错误,但是html表中的值没有改变。

asp.net-mvc razor knockout.js
1个回答
0
投票

你的淘汰代码看起来大部分是正确的,但你的UI没有更新,因为你正在改变的值是不可观察的。如果希望对表中的项进行更改以反映在表中,则需要使每个字段更新一个observable,而不是为整个json对象提供单个observable属性。

以下代码仅在整个对象引用更改时才会更新。 IE,如果你用一个新对象填充self.products。如果更改现有对象的属性,它将不会更新。

// Product array from server.
self.products = ko.observable(json.products);

当来自服务器时,您需要更改代码以将可观察属性单独应用于json对象。

// Product array from server.
self.products = ko.observableArray([]); //Changed to array type
for(var i = 0; i < json.products.length; i++){
    self.products.push({
        id: json.products[i].id,
        description: ko.observable(json.products[i].description)
    });
}

然后你必须使用函数样式getter / setter更新值。

// Update function.
self.update = function () {
    self.products()[Number(self.productId())-1].description(self.productDescription());
};

  // Convert server model to json object.
  var json = {"products":[{"id":1,"description":"Product A"},{"id":2,"description":"Product B"},{"id":3,"description":"Product C"}],"categoryName":"chocolates"};

  function viewModel()
  {
    var index;

    // Store default this to self, to be able use self in subfunctions.
    var self = this;

    // Product array from server.
    self.products = ko.observableArray([]); //Changed to array type
    for(var i = 0; i < json.products.length; i++){
        self.products.push({
            id: json.products[i].id,
            description: ko.observable(json.products[i].description)
        });
    }

    // Automatic refreshed parameter in UI.
    self.categoryName = ko.observable(json.categoryName);

    // Update form parameters.
    self.productId = ko.observable();
    self.productDescription = ko.observable();

    // Update function.
    // Update function.
    self.update = function () {
        self.products()[Number(self.productId())-1].description(self.productDescription());
    };
    
  }

  // Apply viewModel to UI
  ko.applyBindings(new viewModel());
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.4.2/knockout-min.js"></script>

<table class="table table-bordered table-striped table-hover">
    <thead>
        <tr>
            <th>Id</th>
            <th>Description</th>
        </tr>
    </thead>
    <tbody data-bind="foreach: products">
        <tr>
            <td data-bind="text: id"></td>
            <td data-bind="text: description"></td>
        </tr>
    </tbody>
</table>
<br/>

<label>Id: </label>
<input data-bind="value: productId" type="text" class="form-control" />

<br />

<label>Description: </label>
<input data-bind="value: productDescription" type="text" class="form-control" />

<br />

<button class="btn btn-primary" data-bind="click: update">Update</button>
© www.soinside.com 2019 - 2024. All rights reserved.