如何保持嵌套<li>不扩展父</li> <li>宽度?

时间:2018-03-27 22:40:26

标签: html css css3 drop-down-menu html-lists

我的CMS通过嵌套来处理下拉菜单,如:

&#13;
&#13;
body {
  text-align: center;
}

ul.nav {
  margin: 0;
  padding: 0;
  display: inline-block;
  list-style-type: none;
}

li.top-item {
  margin: 0;
  padding: 0;
  float: left;
  padding: .5em;
}

ul.dropdown-list {
  margin: 0 0 -8em;
  padding: 0;
  display: none;
  list-style-type: none;
  background: #eee;
  position: relative;
}

a.dropdown:hover+ul.dropdown-list {
  display: block;
}
&#13;
<ul class="nav">
  <li class="top-item"><a href="#">home</a></li>
  <li class="top-item"><a href="#" class="dropdown">dropdown</a>
    <ul class="dropdown-list">
      <li class="dropdown-item">item 1</li>
      <li class="dropdown-item">item 2 expands parent :(</li>
      <li class="dropdown-item">item 3</li>
    </ul>
  </li>
  <li class="top-item"><a href="#">about</a></li>
</ul>

<p>Lorem ipsum and such...</p>
&#13;
&#13;
&#13;

问题是如果子链接的名称/标题比其父级更长,则将鼠标悬停在父级上会使父级扩展以适应最宽子级的宽度。此链接中的示例:https://codepen.io/ivorytux/pen/PObemb

这是一个很好的方法,顶级菜单保持一致的宽度,只有下拉菜单符合它的链接宽度?

2 个答案:

答案 0 :(得分:1)

您应该将顶部项目设置为相对位置:

li.top-item {
  position: relative;
  ...
}

将子菜单项设置为绝对位置:

ul.dropdown-list {
  position: absolute;
  ...
}

除此之外,您还可以设置:

ul.dropdown-list {
  position: absolute;
  white-space: nowrap; /* no wrapping */
  left: 50%; /* horizontal center */
  transform: translateX(-50%); /* horizontal center */
}

最后,您需要将悬停对象更新为:

li.top-item:hover ul.dropdown-list {
  display: block;
}

如问题中的示例所示,您无法选择子菜单。

完整的代码段:

body {
  text-align: center;
}

ul.nav {
  margin: 0;
  padding: 0;
  display: inline-block;
  list-style-type: none;
}

li.top-item {
  margin: 0;
  padding: 0;
  float: left;
  padding: 0.5em;
  position: relative;
}

ul.dropdown-list {
  margin: 0 0 -8em;
  padding: 0;
  display: none;
  list-style-type: none;
  background: #eee;
  position: absolute;
  white-space: nowrap;
  left: 50%;
  transform: translateX(-50%);
}

li.top-item:hover ul.dropdown-list {
  display: block;
}
<ul class="nav">
  <li class="top-item"><a href="#">home</a></li>
  <li class="top-item"><a href="#" class="dropdown">dropdown</a>
    <ul class="dropdown-list">
      <li class="dropdown-item">item 1</li>
      <li class="dropdown-item">item 2 this is a long item</li>
      <li class="dropdown-item">item 3</li>
    </ul>
  </li>
  <li class="top-item"><a href="#">about</a></li>
</ul>

<p>Lorem ipsum and such...</p>

答案 1 :(得分:0)

我建议您使用隐藏的ul元素 position: absolute 将其从流程中删除。这样可以防止它弄乱父级的宽度,但会稍微“抵消”它。这可以通过否定 margin-left 来抵消。在这个例子中我和margin-left: 45px一起去了,但你可能需要玩弄它。如果需要,您还可以使用 top 来抵消下拉列表的高度。

body {
  text-align: center;
}

ul.nav {
  margin: 0;
  padding: 0;
  display: inline-block;
  list-style-type: none;
}

li.top-item {
  margin: 0;
  padding: 0;
  float: left;
  padding: 0.5em;
}

ul.dropdown-list {
  margin: 0 0 -8em;
  padding: 0;
  display: none;
  list-style-type: none;
  background: #eee;
  position: relative;
}

a.dropdown:hover+ul.dropdown-list {
  display: block;
  position: absolute;
  margin-left: -45px;
  /* top: 90px; */
}
<ul class="nav">
  <li class="top-item"><a href="#">home</a></li>
  <li class="top-item"><a href="#" class="dropdown">dropdown</a>
    <ul class="dropdown-list">
      <li class="dropdown-item">item 1</li>
      <li class="dropdown-item">item 2 expands parent :(</li>
      <li class="dropdown-item">item 3</li>
    </ul>
  </li>
  <li class="top-item"><a href="#">about</a></li>
</ul>

<p>Lorem ipsum and such...</p>