2013-12-02 2 views
0

Я пытаюсь создать простую систему вкладок, но код работает только для первого щелчка, а затем перестает отвечать на запросы.Как создать простую систему вкладок без jquery UI

Я не хотел идти с jquery ui, так как размер файла довольно здоров.

$("#container1").hide(); 


if ($("#container1").is(":visible")) { 
    $("#link1").click(function() { 
     $("#container1").hide(); 
     $("#container2").show(); 
    }); 
}; 

if ($("#container2").is(":visible")) { 
    $("#link2").click(function() { 
     $("#container1").show(); 
     $("#container2").hide(); 
    }); 
}; 

Это швы прямо к новичкам, как я, Может ли кто-нибудь сказать мне, где я иду не так?

здесь является fiddle

благодаря

+0

Я знаю, что вы хотите, чтобы все было просто, на всякий случай вы хотите добавить дополнительные вкладки (таким образом вам не придется копировать код n раз) http://jsfiddle.net/S8h5v/2/ – Spokey

+0

Споки, это потрясающе! – user2950370

ответ

4

Первоначальная проблема здесь состоит в том, что вы только связывание события щелчка, если контейнер виден. Вы хотите связать событие и проверить состояние внутри обратного вызова.

$("#container1").hide(); 


$("#link1").click(function() { 
    if ($("#container1").is(":visible")) { 
     $("#container1").hide(); 
     $("#container2").show(); 
    }; 
}); 

$("#link2").click(function() { 
    if ($("#container2").is(":visible")) { 
     $("#container1").show(); 
     $("#container2").hide(); 
    };  
}); 

http://jsfiddle.net/S8h5v/1/

Стоит говорить о том, почему это происходит и почему вы ожидали другого результата. Чтобы сделать это, мы должны пройти через стек выполнения для каждого примера:

hide the container1 element 
check if container1 is visible (it isn't) and if so: 
    add a callback to the click event of link1 element 
check if container2 is visible (it is) and if so: 
    add a callback to the click event of link2 element 
user clicks link2 
    callback registered to link2 click is fired 
    show container1 
    hide container2 

теперь вы можете видеть, что даже если пользователь не нажмет LINK1 будет никакого эффекта, так как обратный вызов не был зарегистрирован.

Существует несколько более идиоматических способ подойти к этой проблеме, которая должна создать JQuery плагин, что-то вроде следующего:

// http://jsfiddle.net/S8h5v/5/ 

// js: 

$.fn.tabSample = function(){ 
    $(this).each(function(idx, el){ 
     var $this = $(this); 
     $this.delegate('.tabs div', 'click', function(event){ 
      var index = $this.find(".tabs div").index(event.target); 
      $this.find(".contents div").removeClass('active'); 
      var item = $this.find(".contents div:eq(" + index + ")").addClass('active'); 
      console.log(item, index); 
     }); 
     $this.find('.contents div:eq(0)').addClass('active'); 
    }); 
}; 

// html 

<div class="tab-control"> 
    <div class="tabs"> 
    <div>Link 1</div> 
    <div>Link 2</div> 
    </div> 
    <div class="contents"> 
    <div>container 1</div> 
    <div>container 2</div> 
    </div> 
</div> 

// css 

.tab-control .tabs div { 
    display: inline-block; 
    cursor:pointer; 
    padding:10px 30px; 
    background-color:blue; 
    border: solid 1px lightblue; 
} 
.tab-control .contents div { 
    display: none; 
    width:100%; 
    height:100px; 
    background-color:red; 
} 
.tab-control .contents div.active { 
    display: inline-block; 
} 

Причина вы можете попробовать этот подход является повышает гибкость кода , Например, чтобы добавить новые элементы контента, вы можете просто добавить новый элемент div в элемент tabs и новый div к элементу контента, после чего они автоматически подключатся для поддержки табуляции. Вы также можете изменить способ, с помощью которого «показывать» и «скрывать» делаются путем улучшения определения .active css, поэтому в более современных браузерах вы можете использовать css3-переходы и анимации. Кроме того, это позволяет вашему код переносимым, поэтому если у вас есть несколько элементов управления вкладки на одной странице вы можете создать их, не прибегая к столкновениям:

$(".first-tabset").tabSample(); 
$(".second-tabset").tabSample(); 
// any elements within these sets will not affect the other. 
+0

Спасибо! Это было у меня в сучках! – user2950370

3

http://jsfiddle.net/BJ8vZ/ раствора без JQuery и клавиши клавиатуры со стрелками активированного

<style> 
    #tabs {border-bottom:1px solid #ccc;height:33px;margin:0 0 10px;padding-top:5px;background:#eee;} 
    #tabs a {float:left;margin-left:2px;border-radius:3px 3px 0 0;border:1px solid #eee;border-bottom-color:#ccc;color:#08c;height:32px;line-height:32px;padding:0 12px;text-decoration:none;} 
    #tabs a:hover {background:#ddd;color:#058;border-color:#ddd #ddd #ccc;} 
    #tabs a.active {background:#fff;color:#555;border-color:#ccC#ccC#fff;} 
    #tabs a.active:hover {background:#fff;color:#555;border-color:#ccC#ccC#fff;} 
    #tabs_data fieldset {display:none;border:0;} 
    #tabs_data fieldset div {font-size:13px;} 
</style> 
<div id="tabs"> 
    <a href="#" onclick="tab_click(0);">tab 1</a> 
    <a href="#" onclick="tab_click(1);">tab 2</a> 
    <a href="#" onclick="tab_click(2);">tab 3</a> 
</div> 
<div id="tabs_data"> 
    <fieldset> contents of tab 1</fieldset> 
    <fieldset> contents of tab 2</fieldset> 
    <fieldset> contents of tab 3</fieldset> 
</div> 
<script> 
    var tabActive=1, tabs=document.getElementById('tabs').getElementsByTagName('A'), tabs_data=document.getElementById('tabs_data').getElementsByTagName('fieldset'); 
    function tab_click(x){ 
     if(x > -1 && x < tabs.length && x < tabs_data.length){ 
      tabs[tabActive].setAttribute('class',''); 
      tabs_data[tabActive].style.display='none'; 
      tabActive=x; 
      tabs[tabActive].setAttribute('class','active'); 
      tabs_data[tabActive].style.display='block'; 
     } return false; 
    }tab_click(0); 
    document.onkeydown=function (evnt){ 
     if(evnt.keyCode==37 || evnt.keyCode==39) 
     tab_click(tabActive+evnt.keyCode-38); 
    } 
</script> 
+2

Мне это нравится - простой и настоящий простой JS. Хотя, setAttribute 'class' не работает в IE. Вместо этого мне пришлось использовать вкладки [tabActive] .className = 'active'; – Matt

Смежные вопросы