引用在挖空组件中创建的Id

时间:2016-12-28 17:06:00

标签: javascript jquery knockout.js bootstrap-datetimepicker

我在这里展示了我的问题http://jsfiddle.net/LkqTU/33025/

使用组件制作的日期选择器不会触发

下面是我原来的帖子......

我正在使用bootstrap 3日期时间选择器,它的工作原理如下。

HTML

<div data-bind="css: formControlCss">
                                                 <label class="control-label" for="earlyPickup">Early Pickup:</label>  
                                                   <div class='input-group date' id='earlyPickup'>
                                                     <input type='text' class="form-control" />
                                                     <span class="input-group-addon">
                                                        <span class="glyphicon glyphicon-calendar"></span>
                                                     </span>
                                                   </div>
                                            </div>

的JavaScript。

 $('#earlyPickup').datetimepicker(
                                  {
                                   defaultDate: d.DB2VXRVSMRecord.DtErlstPickup + " " + d.DB2VXRVSMRecord.TiErlstPickup
                                  });

这很好但是我有几个这样的日期时间选择器所以我试图创建一个淘汰组件。

组件。

 ko.components.register('datetime-picker', {
            viewModel: function (params) {
                this.label = params.label
                this.id = params.id
                this.hasError = params.hasError
                this.formControl = ko.pureComputed(function () {
                    return (this.hasError()) ? "form-group has-error" : "form-group";
                }, this);
            },
            template:
               '<div data-bind="css: formControl">\
                 <label class="control-label" \
                 data-bind ="attr: {for: id}"> \
                  <span data-bind="text: label"></span>:</label>\
                  <div class="input-group date"\
                  data-bind= "attr: {id: id}" >\
                      <input type="text" class="form-control" />\
                         <span class="input-group-addon">\
                              <span class="glyphicon glyphicon-calendar"></span>\
                         </span>\
                   </div>\
                 </div>'
        });

我将HTML更改为。

<datetime-picker
                                         params="label: 'Early Pickup', 
                                         id: 'earlyPickup',
                                         hasError: ErlstPickupHasErrors">
                                      </datetime-picker>

遗憾的是,我的日期时间选择器不再被实例化。我假设因为我现在使用的是组件,我不能直接引用id?当调用日期时间选择器$('#earlyPickup').datetimepicker(时,它不知道此时的EarlyPickup是什么?

1 个答案:

答案 0 :(得分:1)

问题是组件是异步加载的。在您尝试附加日期选择器时,您的组件可能已经或可能没有在页面上呈现。此外,ID为必需,以便选择器工作。因此,您必须等待呈现组件,然后应用绑定。

解决此问题的一种方法是添加preprocessNode处理程序,以便在遍历节点时检查它们。然后,您可以确定节点是否需要将选择器连接到它。如果设置了id,则附加选择器,否则重试一段时间。

如,

ko.components.register('form-input', {
  viewModel: function(params) {
    this.inputValue = params.value;
    this.label = params.label;
    this.id = params.id;
  },
  template: '<div class ="form-group">\
    <label class="control-label col-sm-2" \
           data-bind ="attr: {for: id}"> \
      <span data-bind="text: label"></span>:\
    </label>\
    <div class="col-sm-9">\
      <input type="text"\
             class="form-control datepicker"\
             data-bind="textInput: inputValue, attr: {id: id}"/>\
    </div>\
  </div>'
});

ko.bindingProvider.instance.preprocessNode = function (node) {
  if (node.nodeType == 1) {
    if ($(node).hasClass('datepicker')) {
      if (node.id) { // an id is required
        attachDatepicker(node);
      } else {
        retryAttachDatepicker(node, 3);
      }
    }
  }

  function attachDatepicker(node) {
    $(node).datepicker();
    ko.utils.domNodeDisposal.addDisposeCallback(node, function () {
      $(node).datepicker('destroy');
    });
  }

  // would be easier to use a microtask but this is pre 3.4
  function retryAttachDatepicker(node, tries) {
    if (tries > 0) {
      setTimeout(function () {
        if (node.id) {
          attachDatepicker(node);
        } else {
          retryAttachDatepicker(node, tries - 1)
        }
      }, 10);
    } else {
      console.warn('unable to attach datepicker to node %o', node);
    }
  }
};

fiddle