简体   繁体   English

重新加载页面后,如何通过Twitter Bootstrap使当前选项卡保持活动状态?

[英]How do I keep the current tab active with twitter bootstrap after a page reload?

I'm currently using tabs with Twitter Bootstrap and want to select the same tab after a user has posted data and the page reloads. 我目前在Twitter Bootstrap中使用标签,并希望在用户发布数据并重新加载页面后选择相同的标签。

How is this done? 怎么做?

My current call to inti the tabs looks like this: 我当前对inti标签的调用如下所示:

<script type="text/javascript">

$(document).ready(function() {

    $('#profileTabs a:first').tab('show');
});
</script>

My tabs: 我的标签:

<ul id="profileTabs" class="nav nav-tabs">
    <li class="active"><a href="#profile" data-toggle="tab">Profile</a></li>
    <li><a href="#about" data-toggle="tab">About Me</a></li>
    <li><a href="#match" data-toggle="tab">My Match</a></li>
</ul>

You'll have to use localStorage or cookies to manage that. 您必须使用localStorage或cookie来管理它。 Here's a quick and dirty solution that can be vastly improved, but may give you a starting point: 这是一个快速而肮脏的解决方案,可以进行很大的改进,但可能会为您提供一个起点:

$(function() { 
    // for bootstrap 3 use 'shown.bs.tab', for bootstrap 2 use 'shown' in the next line
    $('a[data-toggle="tab"]').on('shown.bs.tab', function (e) {
        // save the latest tab; use cookies if you like 'em better:
        localStorage.setItem('lastTab', $(this).attr('href'));
    });

    // go to the latest tab, if it exists:
    var lastTab = localStorage.getItem('lastTab');
    if (lastTab) {
        $('[href="' + lastTab + '"]').tab('show');
    }
});

Got this to work using cookies and also removing the 'active' class from any other tabs and tab panes... and adding the 'active' class to the current tab and tab pane. 使用Cookie可以使其正常工作,还可以从其他任何选项卡和选项卡窗格中删除“活动”类...,并将“活动”类添加到当前选项卡和选项卡窗格中。

I'm sure there's a better way to do this, but this appears to work in this case. 我敢肯定有更好的方法可以做到这一点,但是在这种情况下,这似乎行得通。

Requires the jQuery cookie plugin. 需要jQuery cookie插件。

$(function() { 
  $('a[data-toggle="tab"]').on('shown', function(e){
    //save the latest tab using a cookie:
    $.cookie('last_tab', $(e.target).attr('href'));
  });

  //activate latest tab, if it exists:
  var lastTab = $.cookie('last_tab');
  if (lastTab) {
      $('ul.nav-tabs').children().removeClass('active');
      $('a[href='+ lastTab +']').parents('li:first').addClass('active');
      $('div.tab-content').children().removeClass('active');
      $(lastTab).addClass('active');
  }
});

All other answers are correct. 所有其他答案都是正确的。 This answer will take into account the fact that one might have multiple ul.nav.nav-pills or ul.nav.nav-tabs on the same page. 该答案将考虑到一个事实,即同一页面上可能有多个ul.nav.nav-pillsul.nav.nav-tabs In this case, the previous answers will fail. 在这种情况下,先前的答案将失败。

Still using localStorage but with a stringified JSON as the value. 仍使用localStorage但使用字符串化JSON作为值。 Here is the code: 这是代码:

$(function() {
  var json, tabsState;
  $('a[data-toggle="pill"], a[data-toggle="tab"]').on('shown', function(e) {
    var href, json, parentId, tabsState;

    tabsState = localStorage.getItem("tabs-state");
    json = JSON.parse(tabsState || "{}");
    parentId = $(e.target).parents("ul.nav.nav-pills, ul.nav.nav-tabs").attr("id");
    href = $(e.target).attr('href');
    json[parentId] = href;

    return localStorage.setItem("tabs-state", JSON.stringify(json));
  });

  tabsState = localStorage.getItem("tabs-state");
  json = JSON.parse(tabsState || "{}");

  $.each(json, function(containerId, href) {
    return $("#" + containerId + " a[href=" + href + "]").tab('show');
  });

  $("ul.nav.nav-pills, ul.nav.nav-tabs").each(function() {
    var $this = $(this);
    if (!json[$this.attr("id")]) {
      return $this.find("a[data-toggle=tab]:first, a[data-toggle=pill]:first").tab("show");
    }
  });
});

This bit can be used on the entire app over all pages and will work for both tabs and pills. 此位可以在整个页面的整个应用程序中使用,并且适用于制表符和药丸。 Also, make sure the tabs or pills are not active by default , otherwise you will see a flicker effect at page load. 另外,请确保默认情况下标签或药丸未处于活动状态 ,否则在页面加载时会看到闪烁效果。

Important : Make sure the parent ul has an id. 重要提示 :确保父ul具有ID。 Thanks Alain 谢谢阿兰

For the best option, use this technique: 为了获得最佳选择,请使用以下技术:

$(function() { 
  //for bootstrap 3 use 'shown.bs.tab' instead of 'shown' in the next line
  $('a[data-toggle="tab"]').on('click', function (e) {
    //save the latest tab; use cookies if you like 'em better:
    localStorage.setItem('lastTab', $(e.target).attr('href'));
  });

  //go to the latest tab, if it exists:
  var lastTab = localStorage.getItem('lastTab');

  if (lastTab) {
    $('a[href="'+lastTab+'"]').click();
  }
});

I prefer storing the selected tab in the hashvalue of the window. 我更喜欢将选定的选项卡存储在窗口的哈希值中。 This also enables sending links to colleagues, who than see "the same" page. 这样还可以将链接发送给同事,然后再看到“同一”页面。 The trick is to change the hash of the location when another tab is selected. 技巧是在选择另一个选项卡时更改位置的哈希。 If you already use # in your page, possibly the hash tag has to be split. 如果您已经在页面中使用#,则可能必须拆分哈希标签。 In my app, I use ":" as hash value separator. 在我的应用程序中,我使用“:”作为哈希值分隔符。

<ul class="nav nav-tabs" id="myTab">
    <li class="active"><a href="#home">Home</a></li>
    <li><a href="#profile">Profile</a></li>
    <li><a href="#messages">Messages</a></li>
    <li><a href="#settings">Settings</a></li>
</ul>

<div class="tab-content">
    <div class="tab-pane active" id="home">home</div>
    <div class="tab-pane" id="profile">profile</div>
    <div class="tab-pane" id="messages">messages</div>
    <div class="tab-pane" id="settings">settings</div>
</div>

<script>
    $('#myTab a').click(function (e) {
        e.preventDefault()
        $(this).tab('show')
    });

    // store the currently selected tab in the hash value
    $("ul.nav-tabs > li > a").on("shown.bs.tab", function (e) {
        var id = $(e.target).attr("href").substr(1);
        window.location.hash = id;
    });

    // on load of the page: switch to the currently selected tab
    var hash = window.location.hash;
    $('#myTab a[href="' + hash + '"]').tab('show');
</script>

To prevent the page flashing on the first tab and then the tab that was saved by the cookie (this occurs when you determine the class "active" by default in the first TAB) 为了防止页面在第一个选项卡上然后由Cookie保存的选项卡上闪烁(在默认情况下,当您在第一个TAB中确定类为“活动”时会发生此情况)

Remove the class "active" of tabs and panes like: 删除选项卡和窗格的“活动”类,例如:

<ul class="nav nav-tabs">
<div id="p1" class="tab-pane">

Put the script below to set first tab like default (Requires the jQuery cookie plugin) 将脚本放在下面以将第一个标签设置为默认标签(需要jQuery Cookie插件)

    $(function() { 
        $('a[data-toggle="tab"]').on('shown', function(e){
            //save the latest tab using a cookie:
            $.cookie('last_tab', $(e.target).attr('href'));
        });
        //activate latest tab, if it exists:
        var lastTab = $.cookie('last_tab');
        if (lastTab) {
            $('a[href=' + lastTab + ']').tab('show');
        }
        else
        {
            // Set the first tab if cookie do not exist
            $('a[data-toggle="tab"]:first').tab('show');
        }
    });

Want fading effect? 想要褪色效果? Updated version of @Oktav's code: @Oktav的代码的更新版本:

  1. For Bootstrap 3 对于Bootstrap 3
  2. Sets up the classes on the li and tab's div to enable fading to work properly. 在li和tab的div上设置类,以使衰落正常工作。 Note that all of the content divs need class="tab-pane fade" 请注意,所有内容div都需要class="tab-pane fade"

Code: 码:

// See http://stackoverflow.com/a/16984739/64904
// Updated by Larry to setup for fading
$(function() {
  var json, tabsState;
  $('a[data-toggle="pill"], a[data-toggle="tab"]').on('shown.bs.tab', function(e) {
    var href, json, parentId, tabsState;
    tabsState = localStorage.getItem("tabs-state");
    json = JSON.parse(tabsState || "{}");
    parentId = $(e.target).parents("ul.nav.nav-pills, ul.nav.nav-tabs").attr("id");
    href = $(e.target).attr('href');
    json[parentId] = href;
    return localStorage.setItem("tabs-state", JSON.stringify(json));
  });
  tabsState = localStorage.getItem("tabs-state");
  json = JSON.parse(tabsState || "{}");
  $.each(json, function(containerId, href) {
    var a_el = $("#" + containerId + " a[href=" + href + "]");
    $(a_el).parent().addClass("active");
    $(href).addClass("active in");
    return $(a_el).tab('show');
  });
  $("ul.nav.nav-pills, ul.nav.nav-tabs").each(function() {
    var $this = $(this);
    if (!json[$this.attr("id")]) {
      var a_el = $this.find("a[data-toggle=tab]:first, a[data-toggle=pill]:first"),
          href = $(a_el).attr('href');
      $(a_el).parent().addClass("active");
      $(href).addClass("active in");
      return $(a_el).tab("show");
    }
  });
});

I had tabs in multiple pages and localStorage keeps lastTab from previous pages as well, so for next page, since it had previous page's lastTab in storage, it didn't find any matching tab here, so nothing was being displayed. 我在多个页面中都有选项卡,而localStorage也使前一页中的lastTab保持不变,因此对于下一页,由于它在存储中具有上一页的lastTab,因此在这里找不到任何匹配的选项卡,因此没有显示任何内容。 I modified it this way. 我以这种方式修改了它。

$(document).ready(function(){
    //console.log($('a[data-toggle="tab"]:first').tab('show'))
    $('a[data-toggle="tab"]').on('shown.bs.tab', function () {
        //save the latest tab; use cookies if you like 'em better:
        localStorage.setItem('lastTab', $(this).attr('href'));
    });

    //go to the latest tab, if it exists:
    var lastTab = localStorage.getItem('lastTab');
    if ($('a[href=' + lastTab + ']').length > 0) {
        $('a[href=' + lastTab + ']').tab('show');
    }
    else
    {
        // Set the first tab if cookie do not exist
        $('a[data-toggle="tab"]:first').tab('show');
    }
})

edit: I've noticed that I'll have to have different lastTab variable names for different pages, otherwise, they'll always overwrite each other. 编辑:我注意到我必须为不同的页面使用不同的lastTab变量名称,否则,它们将始终相互覆盖。 eg lastTab_klanten , lastTab_bestellingen etc. for two different pages klanten and bestellingen both having data displayed in tabs. 例如,两个不同页面klantenbestellingen lastTab_klantenlastTab_bestellingen等,都在选项卡中显示了数据。

$(document).ready(function(){
    //console.log($('a[data-toggle="tab"]:first').tab('show'))
    $('a[data-toggle="tab"]').on('shown.bs.tab', function () {
        //save the latest tab; use cookies if you like 'em better:
        localStorage.setItem('lastTab_klanten', $(this).attr('href'));
    });

    //go to the latest tab, if it exists:
    var lastTab_klanten = localStorage.getItem('lastTab_klanten');
    if (lastTab_klanten) {
        $('a[href=' + lastTab_klanten + ']').tab('show');
    }
    else
    {
        // Set the first tab if cookie do not exist
        $('a[data-toggle="tab"]:first').tab('show');
    }
})

I made it works with similar solution as @dgabriel, in this case, the links <a> don't need id , it identify the current tab based on the position. 我使它可以与@dgabriel类似的解决方案一起使用,在这种情况下,链接<a>不需要id ,它根据位置识别当前选项卡。

$(function() { 
  $('a[data-toggle="tab"]').on('shown', function (e) {
    var indexTab = $('a[data-toggle="tab"]').index($(this)); // this: current tab anchor
    localStorage.setItem('lastVisitedTabIndex', indexTab);
  });

  //go to the latest tab, if it exists:
  var lastIndexTab  = localStorage.getItem('lastVisitedTabIndex');
  if (lastIndexTab) {
      $('a[data-toggle="tab"]:eq(' + lastIndexTab + ')').tab('show');
  }
});

I suggest the following changes 我建议进行以下更改

  1. Use a plugin like amplify.store which provides a crossbrowser/ crossplatform localstorage API with builtin fallbacks. 使用amplify.store之类的插件,该插件提供具有内置后备功能的跨浏览器/跨平台本地存储API。

  2. Target the tab that needs to be saved like $('#div a[data-toggle="tab"]') so as to extend this functionality to multiple tab containers that exist on the same page. 定位需要像$('#div a[data-toggle="tab"]') ,以便将此功能扩展到同一页面上存在的多个标签容器。

  3. Use a unique identifier (url ??) to save and restore last used tabs across multiple pages. 使用唯一的标识符(url ??)在多个页面上保存和恢复上次使用的标签页。


$(function() { 
  $('#div a[data-toggle="tab"]').on('shown', function (e) {
    amplify.store(window.location.hostname+'last_used_tab', $(this).attr('href'));
  });

  var lastTab = amplify.store(window.location.hostname+'last_used_tab');
  if (lastTab) {
    $("#div a[href="+ lastTab +"]").tab('show');
  }
});

Simple solution without local storage: 无需本地存储的简单解决方案:

$(".nav-tabs a").on("click", function() {
    location.hash = $(this).attr("href");
});

Server side approach. 服务器端方法。 Be sure all html elements have class="" in case not specified or you will need to handle nulls. 确保所有html元素都具有class =“”,以防未指定,否则您将需要处理null。

    private void ActiveTab(HtmlGenericControl activeContent, HtmlGenericControl activeTabStrip)
    {
        if (activeContent != null && activeTabStrip != null)
        {
            // Remove active from content
            Content1.Attributes["class"] = Content1.Attributes["class"].Replace("active", "");
            Content2.Attributes["class"] = Content2.Attributes["class"].Replace("active", "");
            Content3.Attributes["class"] = Content3.Attributes["class"].Replace("active", "");

            // Remove active from tab strip
            tabStrip1.Attributes["class"] = tabStrip1.Attributes["class"].Replace("active", "");
            tabStrip2.Attributes["class"] = tabStrip2.Attributes["class"].Replace("active", "");
            tabStrip3.Attributes["class"] = tabStrip3.Attributes["class"].Replace("active", "");

            // Set only active
            activeContent.Attributes["class"] = activeContent.Attributes["class"] + " active";
            activeTabStrip.Attributes["class"] = activeTabStrip.Attributes["class"] + " active";
        }
    }

If you want to show the first tab the first time you enter the page use this code: 如果要在第一次进入页面时显示第一个标签,请使用以下代码:

  <script type="text/javascript"> function invokeMeMaster() { var chkPostBack = '<%= Page.IsPostBack ? "true" : "false" %>'; if (chkPostBack == 'false') { $(function () { // for bootstrap 3 use 'shown.bs.tab', for bootstrap 2 use 'shown' in the next line $('a[data-toggle="tab"]').on('shown.bs.tab', function (e) { // save the latest tab; use cookies if you like 'em better: localStorage.setItem('lastTab', $(this).attr('href')); }); }); } else { $(function () { // for bootstrap 3 use 'shown.bs.tab', for bootstrap 2 use 'shown' in the next line $('a[data-toggle="tab"]').on('shown.bs.tab', function (e) { // save the latest tab; use cookies if you like 'em better: localStorage.setItem('lastTab', $(this).attr('href')); }); // go to the latest tab, if it exists: var lastTab = localStorage.getItem('lastTab'); if (lastTab) { $('[href="' + lastTab + '"]').tab('show'); } }); } } window.onload = function() { invokeMeMaster(); }; </script> 

Here is a snippet I made that works with Bootstrap 3 and jQuery and with different URLs containing different tabs . 这是我制作的一段代码,可与Bootstrap 3jQuery 配合使用 ,并与包含不同选项卡的不同URL一起使用 It does not support multiple tabs per page though but it should be an easy modification if you need that feature. 虽然它不支持每页多个选项卡,但是如果需要该功能,则应该轻松进行修改。

/**
 * Handles 'Bootstrap' package.
 *
 * @namespace bootstrap_
 */

/**
 * @var {String}
 */
var bootstrap_uri_to_tab_key = 'bootstrap_uri_to_tab';

/**
 * @return {String}
 */
function bootstrap_get_uri()
{
    return window.location.href;
}

/**
 * @return {Object}
 */
function bootstrap_load_tab_data()
{
    var uriToTab = localStorage.getItem(bootstrap_uri_to_tab_key);
    if (uriToTab) {
    try {
        uriToTab = JSON.parse(uriToTab);
        if (typeof uriToTab != 'object') {
        uriToTab = {};
        }
    } catch (err) {
        uriToTab = {};
    }
    } else {
    uriToTab = {};
    }
    return uriToTab;
}

/**
 * @param {Object} data
 */
function bootstrap_save_tab_data(data)
{
    localStorage.setItem(bootstrap_uri_to_tab_key, JSON.stringify(data));
}

/**
 * @param {String} href
 */
function bootstrap_save_tab(href)
{
    var uri = bootstrap_get_uri();
    var uriToTab = bootstrap_load_tab_data();
    uriToTab[uri] = href;
    bootstrap_save_tab_data(uriToTab);
}

/**
 *
 */
function bootstrap_restore_tab()
{
    var uri = bootstrap_get_uri();
    var uriToTab = bootstrap_load_tab_data();
    if (uriToTab.hasOwnProperty(uri) &&
    $('[href="' + uriToTab[uri] + '"]').length) {
    } else {
    uriToTab[uri] = $('a[data-toggle="tab"]:first').attr('href');
    }
    if (uriToTab[uri]) {
        $('[href="' + uriToTab[uri] + '"]').tab('show');
    }
}

$(document).ready(function() {

    if ($('.nav-tabs').length) {

    // for bootstrap 3 use 'shown.bs.tab', for bootstrap 2 use 'shown' in the next line
    $('a[data-toggle="tab"]').on('shown.bs.tab', function (e) {
        bootstrap_save_tab($(this).attr('href'));
    });
    bootstrap_restore_tab();

    }

});

$(document).ready(function () { $(document).ready(function(){

        if (JSON.parse(localStorage.getItem('currentClass')) == "active")
        {
            jQuery('#supporttbl').addClass('active')
            $('.sub-menu').css({ "display": "block" });
        }

        $("#supporttbl").click(function () { 
            var currentClass;
            if ($(this).attr('class')== "active") { 

                currentClass = $(this).attr('class');

                localStorage.setItem('currentClass', JSON.stringify(currentClass));
                console.log(JSON.parse(localStorage.getItem('currentClass')));

                jQuery('#supporttbl').addClass('active')
                $('.sub-menu').css({ "display": "block" });

            } else {

                currentClass = "Null"; 

                localStorage.setItem('currentClass', JSON.stringify(currentClass));
                console.log(JSON.parse(localStorage.getItem('currentClass')));

                jQuery('#supporttbl').removeClass('active')
                $('.sub-menu').css({ "display": "none" });

            }  
        });

}); });

if you have more than one tab in the page, you can use the following code 如果页面中有多个标签,则可以使用以下代码

<script type="text/javascript">
$(document).ready(function(){
    $('#profileTabs').on('show.bs.tab', function(e) {
        localStorage.setItem('profileactiveTab', $(e.target).attr('href'));
    });
    var profileactiveTab = localStorage.getItem('profileactiveTab');
    if(profileactiveTab){
        $('#profileTabs a[href="' + profileactiveTab + '"]').tab('show');        
    }
    $('#charts-tab').on('show.bs.tab', function(e) {
        localStorage.setItem('chartsactiveTab', $(e.target).attr('href'));
    });
    var chartsactiveTab = localStorage.getItem('chartsactiveTab');
    if(chartsactiveTab){
        $('#charts-tab a[href="' + chartsactiveTab + '"]').tab('show');        
    }     
});
</script>

This will refresh the tabs but only after everything in the controller is loaded. 这将刷新选项卡,但仅在加载控制器中的所有内容之后。

// >= angular 1.6 angular.element(function () {
angular.element(document).ready(function () {
    //Here your view content is fully loaded !!
    $('li[href="' + location.hash + '"] a').tab('show');
});

I'm using this with MVC: 我在MVC中使用它:

  • There is a SelectedTab integer field in the model to send the value to the POST method 模型中有一个SelectedTab整数字段,用于将值发送到POST方法

JavaScript Section: JavaScript部分:

<script type="text/javascript">
    $(document).ready(function () {
       var index = $("input#SelectedTab").val();
       $("#tabstrip > ul li:eq(" + index + ")").addClass("k-state-active");

       $("#tabstrip").kendoTabStrip();
    });
    function setTab(index) {
      $("input#SelectedTab").val(index)
    }
</script>

HTML Section: HTML部分:

@using (Html.BeginForm())
{
@Html.AntiForgeryToken()
@Html.HiddenFor(model => model.SelectedTab)
<div id="tabstrip">
    <ul>
        <li onclick="setTab(0)">Content 0</li>
        <li onclick="setTab(1)">Content 1</li>
        <li onclick="setTab(2)">Content 2</li>
        <li onclick="setTab(3)">Content 3</li>
        <li onclick="setTab(4)">Content 4</li>
    </ul>
    <div>

    </div>
    <div>

    </div>
    <div>

    </div>
    <div>

    </div>
    <div>

    </div>
</div>
<div class="content">
    <button type="submit" name="save" class="btn bg-blue">Save</button>
</div>
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM