【问题标题】:checkbox property check value not updating in knockout js复选框属性检查值未在淘汰赛 js 中更新
【发布时间】:2017-08-19 01:34:13
【问题描述】:

我正在使用 Knockout.js。我有一个页面,其中有三个复选框,它位于foreach 循环下。这是我的代码:

<div class="form-horizontal" id="ko-bind-element">
    <input type="hidden" id="serverJSON" value="@Newtonsoft.Json.JsonConvert.SerializeObject(Model)" />
    <div data-bind="foreach: procedures">
        <div data-bind="template: { name: Mode(), data: $data }"></div>
    </div>
</div>
<script type="text/html" id="procedure">
    <table class="table table-bordered">
        <tr>
            <td class="col-md-3"><span data-bind="text: Name"></span>
            </td>
            <td>
                <input type="checkbox" data-bind="attr: { name: (VId.length > 0) ? VId : Name },checked: AlreadyCompleted" />
            </td>
            <td>
                <input type="checkbox" data-bind="attr: { name: (VId.length > 0) ? VId : Name },checked: NotApplicable" />
            </td>
            <td>
                <input type="checkbox" data-bind="attr: { name: (VId.length > 0) ? VId : Name },checked: CreateNew" />
            </td>
        </tr>
        <tr>
            <td colspan="4" style="padding:0;">
                <div data-bind="if: CreateNew">
                    <textarea style="margin-top:10px; margin-bottom:10px;" class="col-md-offset-3 col-md-8" data-bind=" value : Text"></textarea>
                    <div class="clearfix"></div>
                </div>
            </td>
        </tr>
    </table>
</script>

因为每行有三个复选框,我希望只选择其中一个,所以我有这个 jQuery 函数,它在每行的时间选择一个复选框

$("input:checkbox").on('click', function() {
    debugger;
    // in the handler, 'this' refers to the box clicked on
    var $box = $(this);
    if ($box.is(":checked")) {
        // the name of the box is retrieved using the .attr() method
        // as it is assumed and expected to be immutable
        var group = "input:checkbox[name='" + $box.attr("name") + "']";
        // the checked state of the group/box on the other hand will change
        // and the current value is retrieved using .prop() method
        $(group).prop("checked", false);
        $box.prop("checked", true);
    } else {
        $box.prop("checked", false);
    }
});

但现在的问题是,当我选中第一个复选框然后取消选中它。然后选中第二个复选框并提交数据。第一场和第二场都检查了。所以不知道是不是Knockout的问题。

这里是绑定代码:

viewModel = {
    MtocFormID: 0,
    procedures: ko.observableArray(),
    dateid: null
};
$(document).ready(function() {
    var data = JSON.parse($("#serverJSON").val());
    viewModel.MtocFormID = ko.observable(data.ID);
    // viewModel.dateid = ko.observable(data.ExpiryDate)
    $(data.TemplateProcedure).each(function(index, element) {
        var mappedItem = {
            //    otherSafetyPro: ko.observableArray([]),
            VId: ko.observable(element.VId),
            TemplateID: ko.observable(element.TemplateID),
            ProcedureTemplateID: ko.observable(element.ProcedureTemplateID),
            Name: ko.observable(element.Name),
            AlreadyCompleted: ko.observable(element.AlreadyCompleted),
            NotApplicable: ko.observable(element.NotApplicable),
            CreateNew: ko.observable(element.CreateNew),
            Text: ko.observable(element.Text),
            Mode: ko.observable("procedure")
        }
        viewModel.procedures.push(mappedItem);
    });
    ko.cleanNode(document.getElementById("ko-bind-element"));
    ko.applyBindings(viewModel, document.getElementById("ko-bind-element"));
    form08wizard.submitData(getSubmitData);
});

【问题讨论】:

  • 以编程方式更改checked 属性不会影响视图模型中的基础属性。您必须为相应的 observables(NotApplicableAlreadyCompletedCreateNew)设置值,而不是更改复选框的状态。
  • 如何设置?
  • 您希望一次只选中三个复选框中的一个?听起来像你想要的输入类型收音机

标签: javascript jquery checkbox knockout.js


【解决方案1】:

您可以使用subscribe 功能来识别是否选中了一个复选框,然后修改另一个复选框。而且我更喜欢以这种方式排列视图模型。

var singleViewModel = function(element){
  var self = this;
  // self.otherSafetyPro = ko.observableArray([]);
  self.VId = ko.observable(element.VId);
  ...
  self.Completed = ko.observable(element.AlreadyCompleted);
  self.NotApplicable = ko.observable(element.NotApplicable);
  self.CreateNew = ko.observable(element.CreateNew);
  self.Completed.subscribe(function(newValue) {
    if(newValue) {
      self.NotApplicable(false);
      self.CreateNew(false);
    }
  });
  self.NotApplicable.subscribe(function(newValue) {
    if(newValue) {
      self.Completed(false);
      self.CreateNew(false);
    }
  });
  self.CreateNew.subscribe(function(newValue) {
    if(newValue) {
      self.NotApplicable(false);
      self.Completed(false);
    }
  });
}

然后这就是你分配它的方式

$(data.TemplateProcedure).each(function (index, element) {
  viewModel.procedures.push(new singleViewModel(element));
});

另一个示例:

function ViewModel() {
  var self = this;
  self.optionA = ko.observable(false);
  self.optionA.subscribe(function(newValue){
    if(newValue) {
      self.optionB(false);
      self.optionC(false); 
    }
  });
  self.optionB = ko.observable(false);
  self.optionB.subscribe(function(newValue){
    if(newValue) {
      self.optionA(false);
      self.optionC(false); 
    }
  });
  self.optionC = ko.observable(false);
  self.optionC.subscribe(function(newValue){
    if(newValue) {
      self.optionA(false);
      self.optionB(false); 
    }
  });
}   

$(document).ready(function () {
  var myViewModel = new ViewModel();
  ko.applyBindings(myViewModel);
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.2.0/knockout-min.js"></script>

<div>
  <input type="checkbox" data-bind="checked: optionA" />
  <input type="checkbox" data-bind="checked: optionB" />
  <input type="checkbox" data-bind="checked: optionC" />
</div>

【讨论】:

  • 添加订阅代码后,我收到此错误'Cannot read property 'subscribe' of undefined'
  • @Mahajan344 我做了一些修改。我个人的偏好是提供一个可用于创建淘汰对象的单一功能。然后,如果我们想使用它,我们可以使用 'new viewModel(element)' 并将值作为参数传递。这也将允许我们将实现移动到一个单独的 js 文件中。
猜你喜欢
  • 2013-08-06
  • 2015-08-27
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-03-11
  • 2016-12-03
  • 2020-08-28
  • 1970-01-01
相关资源
最近更新 更多