仅使用CSS

时间:2015-06-01 13:30:58

标签: html css css3 transition flexbox

假设我有一个可折叠的固定宽度侧边栏,如下所示:

HTML

<div class="container">
  <div class="sidebar" id="sidebar">
    SIDEBAR
  </div>
  <div class="content">
    lorem bla bla
    <button onclick="document.getElementsByClassName('sidebar')[0].classList.toggle('collapsed')">
      toggle Sidebar
    </button>
  </div>
</div>

CSS

body {
  margin:0;
}

.container {
  display: flex;
  min-height:100px;
}

.sidebar {
  position: relative;
  left: 0;
  width: 200px;
  background-color: #ccc;
  transition: all .25s;
}

.sidebar.collapsed {
  left:-200px;
  margin-right:-200px;
}

Codepen:http://codepen.io/anon/pen/pJRYJb

所以这就是问题:

如何从那里转到灵活宽度侧边栏?

以下是限制因素:

  • 没有javascript(我希望浏览器处理布局 - 不是我)
  • 侧边栏不得与内容重叠
  • 折叠时,侧边栏的右边框需要与窗口的左边框对齐(以便能够在右侧连接一个始终可见的绝对定位标签)
  • 如果折叠时侧边栏的宽度不应改变以避免在过渡期间回流
  • 没有任何突然跳跃的平稳过渡
  • 现代CSS(flexboxes,calc)很好

这里的主要问题是我无法找到margin-right: -100%的方法,其中100%指的是侧边栏的宽度

任何帮助将不胜感激!

3 个答案:

答案 0 :(得分:3)

如何点击更改width而不是position?在这种情况下我使用max-width,它的工作方式与未知宽度几乎相同。这可能会导致侧边栏上的内容重排,因此如果可以接受,请使用white-space:nowrap

http://jsfiddle.net/dn4ge901/

body {
    margin: 0;
}
.container {
    display: flex;
}
.sidebar {
    background: #ccc;
    transition: all .1s;
    max-width: 1000px;
}
.sidebar.collapsed {
    max-width: 0;
    overflow: hidden;
}
<div class="container">
    <div class="sidebar" id="sidebar">SIDEBAR</div>
    <div class="content">lorem bla bla
        <button onclick="document.getElementsByClassName('sidebar')[0].classList.toggle('collapsed')">toggle Sidebar</button>
    </div>
</div>

另一种解决方法是同时使用transform宽度position,但动画效果会略有不同。

http://jsfiddle.net/vkhyp960/

body {
    margin: 0;
}
.container {
    display: flex;
}
.sidebar {
    background: #ccc;
    transition: all .1s;
}
.sidebar.collapsed {
    transform: translateX(-100%);
    position: absolute;
}
<div class="container">
    <div class="sidebar" id="sidebar">
        <div>SIDEBAR</div>
    </div>
    <div class="content">lorem bla bla
        <button onclick="document.getElementsByClassName('sidebar')[0].classList.toggle('collapsed')">toggle Sidebar</button>
    </div>
</div>

答案 1 :(得分:0)

Pangloss建议的小猪退出:转换...如果您知道侧边栏的宽度,您可以对内容应用负边距。无需将侧边栏切换到绝对定位。

@mixin transitionAll() {
  transition: all .3s ease-out;
}
html, body {
  height: 100%;
}
.container {
  display: flex;
  width: 100%;
  height: 100%;
}
.sidebar {
  flex: 1 0 300px;
  background: #333;
  height: 100%;
  @include transitionAll();
  &.is-collapsed {
    transform: translateX(-100%);
  }
}
.content {
  width: 100%;
  height: 100%;
  padding: 1rem;
  background: #999;
  @include transitionAll();
  &.is-full-width {
    margin-left: -300px;
  }
}

-

<div class="container">
  <aside class="sidebar">
  </aside>
  <section class="content">
    <button class="btn btn-primary">Toggle</button>
  </section>
</div>

-

$(function() {
  $('.btn').on('click', function() {
    $('.sidebar').toggleClass('is-collapsed');
    $('.content').toggleClass('is-full-width');
  });
});
请参阅LxRYQB上Jason Florence(@JFlo)的笔CodePen

答案 2 :(得分:0)

对于它的价值,我部分 js解决方案。动画本身完全由CSS完成,它只解决了width:auto问题。您只需在加载元素时使用js设置侧栏domElement的宽度:

domElement.style.width = `${parseInt(domElement.offsetWidth)}px`;

这解决了“未知”的问题。宽度问题。您可以根据自己的喜好使用.collapsed方法。唯一的调整是您需要将!important添加到.collapsed {width: 300px !important;}宽度值。