jquery html5详细信息标签打开一个接一个javascript函数工作奇怪

hl0ma9xz  于 2023-03-17  发布在  jQuery
关注(0)|答案(5)|浏览(124)

我在一家公司的FAQ部分使用HTML5标签详细信息。一个问题是如果用户打开另一个问题,另一个问题不会自动关闭。因此,我在网上搜索并找到了以下解决方案:

function thisindex(elm){
      var nodes = elm.parentNode.childNodes, node;
      var i = 0, count = i;
      while( (node=nodes.item(i++)) && node!=elm )
        if( node.nodeType==1 ) count++;
      return count;
    }

    function closeAll(index){
      var len = document.getElementsByTagName("details").length;

      for(var i=0; i<len; i++){
        if(i != index){
          document.getElementsByTagName("details")[i].removeAttribute("open");
        }
      }
    }

这段代码在某种意义上可以正常工作,但它有一些小问题。有时它会同时打开两个问题,而且工作起来很滑稽。有没有一种方法可以让它正常工作?这应该可以在桌面、平板电脑和移动的上工作。
非预期效果:

我用所有的代码创建了一个小提琴http://jsfiddle.net/877tm/。javascript正在那里工作,IG你想看到它的现场点击here

tsm1rwdh

tsm1rwdh1#

既然您已经标记了jQuery,那么您可以这样做:

$('.info').on('click', 'details', function () {
    $('details').removeAttr('open');
    $(this).attr('open', '');
});

所有这些操作只是在您单击任何detail时删除所有detail标记的open属性,然后重新打开您刚刚单击的那个标记。
http://jsfiddle.net/877tm/3/

wecizke3

wecizke32#

  1. thisindex函数的漏洞很愚蠢,可以删除。你可以简单地将details元素传递给closeAll。
  2. closeAll是相当愚蠢的,它也在for循环中搜索细节,哇。
    //关闭全部
function closeAll (openDetails){
    var details = document.getElementsByTagName("details");
    var len = details.length;
    for(var i=0; i<len; i++){
        if(details[i] != openDetails){
            details[i].removeAttribute("open");
        }
    }
}

以防你想写干净的代码。
1.您应该使用$.on或addEventlistener。
1.试着在一个特定的上下文中,并且只在这个上下文中操作细节。(如果你想有两个可折叠区域,或者在同一个站点上有一些普通的细节,但不在组内,会发生什么。)
1.仅搜索组中的详细信息(如果详细信息已打开而未关闭)。
1.给予boolen开放属性一些爱,而不是使用内容属性
我做了个小的。

aurhwmvo

aurhwmvo3#

要将细节作为accordion标记,可以使用下面的jquery。

$("#edit-container details summary").click(function(e) {
    var clicked = $(this).attr('aria-controls');
    closeAll(clicked);
});
function closeAll (openDetailid){
      $("#edit-container details" ).each(function( index ) {
        var detailid = $(this).attr('id');
        var detailobj = document.getElementById(detailid);
          if (openDetailid != detailid ) {
           detailobj.open = false;
          }
       });
      $('html, body').stop().animate({ scrollTop: $('#'+openDetailid).offset().top -100 }, 1000);
  }
jtw3ybtb

jtw3ybtb4#

我对@MattDiamant提供的答案有一个问题,Firefox删除了open属性,但没有将open属性放在选中的detail上。我对他的代码做了一个小的修改,使其针对当前选中的detail元素的ID。
现在,当我单击一个<details>元素,然后单击另一个元素时,它会折叠第一个元素并显示第二个元素。

$('details').click(function(e){
    $('details').removeAttr('open');
    $(e.currentTarget.id).attr('open', '');
});
euoag5mw

euoag5mw5#

我有一个jQuery解决方案

$('details').on('click', function(ev){ //on a '<details>' block click
        ev.preventDefault(); //prevent the default behavior
        var attr = $(this).attr('open');
        if (typeof attr !== typeof undefined && attr !== false){ //if '<details>' block is open then close it
            $(this).removeAttr('open');
        }else{ // if '<details>' block is closed then open the one that you clicked and close all others
            var $that = $(this); //save the clicked '<details>' block
            $(this).attr('open','open'); //open the '<details>' block
            $('details').each(function(){ //loop through all '<details>' blocks
                if ($that.is($(this))){ //check if this is the one that you clicked on, if it is than open it or else close it
                    $(this).attr('open','open');
                }else{
                    $(this).removeAttr("open");
                }
            });
        }
    });

相关问题