使用Durandal / Knockout引导“show.bs.tab”事件

时间:2014-04-01 14:59:35

标签: jquery twitter-bootstrap knockout.js event-handling durandal

我已经尝试了几个小时的各种事情,无法让它发挥作用。基本上,我有一个选项卡式窗格,我只希望在相应的选项卡处于活动状态时加载每个窗格的内容。选项卡式窗格位于durandal视图中。

我首先尝试了正常的点击事件,但是有效。问题是,有时在导航回该屏幕时,仍会选择上次选择的选项卡。因此,没有发生点击事件。因此我认为我只会使用bootstrap中的内置触发事件 - “show.bs.tab”来找出标签何时变为“活动”。

不幸的是没有选择器组合或我尝试过的任何东西都可以。我知道触发器是由引导程序触发的,因为我已经调试过了。但是,事件没有到达我在视图模型的“compositionComplete”回调中放置的事件监听器 - 我知道durandal也在那里,因为我也调试了它。

奇怪的是,当我放置侦听器代码时:

    $('a[data-toggle="tab"]').on('show.bs.tab', function (e) {
    console.log('EVENT HAS ARRIVED! ', e);
});

直接进入上面的实际触发器触发的引导程序文件,它可以工作。因此,必须有一些东西阻止事件在durandal view-model中到达。是durandal还是淘汰?有没有我错过的东西 - 我需要配置durandal或knockout以使其工作?

我认为HTML不是问题所在,但为了完整起见,我也会发布:

<div class="col-md-10" id="view-details">

<form class="form-horizontal" role="form" data-observe="true">

    <ul class="nav nav-tabs">
        <li class="active"><a data-target="#tab1" data-toggle="tab">Tab1</a></li>
        <li><a data-target="#tab2" data-toggle="tab">Tab2</a></li>
        <li><a data-target="#tab3" data-toggle="tab">Tab3</a></li>
    </ul>

    <div class="tab-content">
        <div class="tab-pane active" id="tab1" data-bind="compose:{ model: 'path/to/tabs/tab1', activationData: $root.someId}"></div>
        <div class="tab-pane" id="tab2" data-bind="compose:{ model: 'path/to/tabs/tab2', activationData: $root.someId}"></div>
        <div class="tab-pane" id="tab3" data-bind="compose:{ model: 'path/to/tabs/tab3', activationData: $root.someId}"></div>
    </div>

</form>

非常感谢任何帮助。

谢谢, 迈克尔

1 个答案:

答案 0 :(得分:0)

我遇到了类似的问题,我的解决解决方案是覆盖bootstrap show功能。根据您使用的引导程序版本,以下内容应该有效(唯一的区别是this.activate回调中的.trigger调用):

  

var _show = $ .fn.tab.Constructor.prototype.show;

     

$。fn.tab.Constructor.prototype.show = function(){       var $ this = this.element;       var $ ul = $ this.closest('ul:not(.dropdown-menu)');       var selector = $ this.data('target');

if (!selector) {
    selector = $this.attr('href');
    selector = selector && selector.replace(/.*(?=#[^\s]*$)/, ''); //strip for ie7
}

if ($this.parent('li').hasClass('active')) return;

var previous = $ul.find('.active:last a')[0];
var e = $.Event('show.bs.tab', {
    relatedTarget: previous
});

$this.trigger(e);    

if (e.isDefaultPrevented()) return;

var $target = $(selector);

this.activate($this.parent('li'), $ul);
this.activate($target, $target.parent(), function () {
    $('a[data-toggle="tab"]').trigger({
        type: 'shown.bs.tab',
        relatedTarget: previous
    });
}); };