Javascript 你能不能指定一个";“数据目标”;对于引用同级DOM元素而不使用ID的引导?

Javascript 你能不能指定一个";“数据目标”;对于引用同级DOM元素而不使用ID的引导?,javascript,twitter-bootstrap,jquery-selectors,Javascript,Twitter Bootstrap,Jquery Selectors,我正在动态地向页面添加可折叠元素。引导使用“数据目标”属性指定折叠切换应用于哪个元素 从文档中: The data-target attribute accepts a css selector 有没有办法编写一个选择器来指定父元素的下一个同级元素?文档中的所有示例似乎都使用了ID选项 具体而言,HTML如下所示: <div class="accordion-group"> <div class="accordion-heading"> <a class="a

我正在动态地向页面添加可折叠元素。引导使用“数据目标”属性指定折叠切换应用于哪个元素

从文档中:

The data-target attribute accepts a css selector
有没有办法编写一个选择器来指定父元素的下一个同级元素?文档中的所有示例似乎都使用了ID选项

具体而言,HTML如下所示:

<div class="accordion-group">
<div class="accordion-heading">
  <a class="accordion-toggle" data-toggle="collapse" data-target="#collapseOne">
    Generated Title
  </a>
</div>
<div id="collapseOne" class="accordion-body collapse in">
  <div class="accordion-inner">
    Generated Content... this is big and sometimes needs collapsing
  </div>
</div>
</div>

生成的标题
生成的内容。。。这个很大,有时需要折叠
我想写一些类似(非法使用jquery语法的伪代码):


但我开始怀疑这可能不可能与CSS选择器

现在,作为一种解决方法,在创建元素时,我正在生成一个新ID(附加到字符串的递增数字)


使用选择器有更好的方法吗?我应该使用一些创建后javascript来设置数据目标属性吗?为动态内容生成ID是标准方法吗?

我认为最好的方法是迭代所有
accordion toggle
元素,并通过jquery动态设置它们的
数据目标
属性,然后放置引导中提到的accordion代码

示例:

$(function(){
    $("a.accordion-toggle").each(function(index) {
        $(this).attr("data-target", "#" + $(this).parent().next().attr("id"));
    });

    // accoridon code
});

希望这会有所帮助。

虽然
数据目标
属性中的选择器确实是一个jQuery选择器,但此插件的数据api规范没有提供在执行范围内引用
的方法(请参阅其用法)

但是,我想提供另一种替代方法,即使用您自己的自定义切换说明符扩展数据api。我们称之为“下一步折叠”

JS(见更新说明) HTML

这里的缺点是它是一种紧密耦合的方法,因为JS假定标记具有特定的结构


关于IE问题的说明
在使用我的答案的早期版本时,IE9及以下版本显然在第一次单击时失败。原因实际上根本不是IE的问题,而是引导的问题。如果对其
Carousel
对象未初始化的目标调用
.collapse('toggle')
,则
toggle()
方法将被调用两次—一次在初始化期间,然后在初始化后显式再次调用。这肯定是一个引导错误,希望能得到修复。在Chrome、FF、IE10等中,它不会出现问题的唯一原因是它们都支持CSS转换,因此当第二次调用时,它会短路,因为第一次调用仍然处于活动状态。上面更新的解决方法只是通过先检查初始化并以不同方式处理来避免双重调用问题。

@merv的解决方案在IE9及以下版本中对我不起作用,因为只有在每个项目上单击一次,可折叠状态才可用。不过,它在Firefox和Chrome中运行良好。所以在点击两下之后,一切都会正常工作

我所做的是将一个
.collapse next
类设置为触发元素,然后强制它们的
ul
同级将
toggle
设置为
false

$(".collapse-next").closest('li').each(function(){
  if ($(this).hasClass('active')) {
    // pop up active menu items
    $(this).children("ul").collapse('show');
  } else {
    // just make it collapsible but don't expand
    $(this).children("ul").collapse({ toggle: false });
  }
});
这用于实际切换菜单状态:

$('.collapse-next').click(function(e){
  e.preventDefault();
  $(this).parent().next().collapse('toggle');
});
使用
数据-
属性似乎是一种更现代、更干净的方法,但对于使用类和jQuery的旧浏览器来说,似乎也能做到这一点。

TYPO3 FCE和Bootstrap Accordion 我在这个问题上也遇到了一些麻烦,我在TYPO3中使用它是为了一个客户,他希望能够为手风琴添加无限多的元素。因此,我创建了一个灵活的内容元素并映射了这些元素

使用data toggle=“collapse next”的想法并没有像预期的那样对我有效,因为它没有关闭打开的元素。我创建了一个新的javascript函数,请在这里找到代码。希望有人发现这些东西有用

Javascript HTML

可折叠组项目#1
动物教区的陈词滥调。。。

是的,你可以很容易地做到 没有javascript解决方案,或者该解决方案依赖于已经在使用的bootstrap的JS,只是利用DOM结构-

请参阅
数据目标=”

一个避免笨重解决方案的提示,不需要ID或额外的JS,使用标记放置技巧-

<button data-toggle="collapse" data-target=".dropdown-toggle:hover + .more-menu" type="button" class="btn btn-primary dropdown-toggle" >
  Show More Menu +
</button>
<div class="collapse more-menu">More menu here...</div>

显示更多菜单+
更多菜单在这里。。。
此CSS选择结构将选择所需的DOM
。下拉切换:hover+。更多菜单
,在那里我们可以应用所需的CSS。
有更多的方法来利用我们所拥有的<代码>:悬停
或:活动或其他许多方式。

以下是一种避免需要唯一ID和避免特定html结构的方法

这将折叠触发器和目标的每个实例封装在html的“部分”中。我喜欢使用类选择器,特别是对于多个实例。在这种情况下,它避免了创建人工唯一ID

借用@merv的优秀答案,我将数据切换命名为
collapse section
,类似于他的
collapse next
,并添加了一个数据节属性。 这将查找最接近的()节名,而不是parent().next(),然后向下查找给定的目标名称。他们可以是兄弟姐妹或任何其他级别

(我有一个命名约定,使用“id…”作为用作jquery选择器的类名的前缀,以避免与样式混淆。)

HTML
您介意发布获取
数据目标
属性值并执行搜索的代码吗
$(".collapse-next").closest('li').each(function(){
  if ($(this).hasClass('active')) {
    // pop up active menu items
    $(this).children("ul").collapse('show');
  } else {
    // just make it collapsible but don't expand
    $(this).children("ul").collapse({ toggle: false });
  }
});
$('.collapse-next').click(function(e){
  e.preventDefault();
  $(this).parent().next().collapse('toggle');
});
$(document).on('click.collapse-next.data-api', '[data-toggle=collapse-next]', function (e) {
  var $container = $(this).parents(".accordion");
  var $opencontainers = $container.find(".in");
  var $target = $(this).parent().next();
  $target.data('collapse') ? $target.collapse('toggle') : $target.collapse();
  $opencontainers.each(function() {$(this).collapse('toggle')});
})
<html>
    <div class="accordion">
        <div class="accordion-section">
            <div class="accordion-group">
                <div class="accordion-heading">
                    <a class="accordion-toggle" data-toggle="collapse-next">
                        Collapsible Group Item #1
                    </a>
                </div>
                <div class="accordion-body collapse">
                    <div class="accordion-inner">
                        Anim pariatur cliche...
                    </div>
                </div>
            </div>
        </div>
    </div>
</html>
<button data-toggle="collapse" data-target=".dropdown-toggle:hover + .more-menu" type="button" class="btn btn-primary dropdown-toggle" >
  Show More Menu +
</button>
<div class="collapse more-menu">More menu here...</div>
<div class="accordion-group idCollapseSection">
  <div class="accordion-heading">
    <a class="accordion-toggle" data-toggle="collapse-section"
       data-section=".idCollapseSection" data-target=".idCollapseTarget">
      Generated Title
    </a>
  </div>
  <div>Any other html, at various depths.
    <div class="accordion-body collapse in idCollapseTarget">
      <div class="accordion-inner">
        Generated Content... this is big and sometimes needs collapsing
      </div>
    </div>
  </div>
</div>
//------------------------------
// Bootstrap Collapse.
//------------------------------
// Extend collapse to contain trigger and target within an enclosing section.
$('body').on('click.collapse-section.data-api', '[data-toggle=collapse-section]', function (e) {
  var thisTrigger = $(this);
  var sectionSelector = thisTrigger.data("section");
  var targetSelector = thisTrigger.data("target");
  var target = thisTrigger.closest(sectionSelector).find(targetSelector);
  target.data('bs.collapse') ? target.collapse('toggle') : target.collapse();
});