3 列流体布局,根据面板位置扩展中间 div

3 column fluid layout with expanding middle div based on panel positions

对 not-super-descriptive 标题表示歉意,我很难用语言表达问题,所以让我再试一次更详细。

我正在使用 flexbox 创建一个 3 列布局,我希望在折叠左/右列(菜单面板)中的一个(或两个)时展开中间列。

这是我遇到的问题的屏幕截图。 https://www.dropbox.com/s/d9mcg7q71hwogog/example.jpg?dl=0

当面板打开(展开)时,所有三列都会填满屏幕宽度。这很好。但是,当两个侧面板中的任何一个处于动画状态(折叠)时,中心列不会扩展以填充额外的 space。这样不好。

我不确定这是否与我使用 translateX 来切换左/右面板这一事实有关,这只是一个理论,但也许中心栏没有意识到左/右列已移动位置,因此它不知道还有更多 space 需要填充?

要遵循的代码:

CSS:

<style>
    body {
        background-color: lightslategrey;
    }
    .red {
        background-color: lightcoral;
    }

    .green {
        background-color: lightgreen;
    }

    .grey {
        background-color: lightslategray;
    }

    * {
        box-sizing: border-box;
    }

    .ls-toggle, .rs-toggle {
        //position: fixed;
        z-index: 1;
        cursor: pointer;
        transition: 0.5s;
    }

    #left-sidebar, #right-sidebar {
        width: 250px;
        height: 100vh;
        transition: 0.5s;
    }

    #left-sidebar.is-closed {
        transform: translateX(-80%);
    }

    #right-sidebar.is-closed {
        transform: translateX(80%);
    }

    .ls-top, .rs-top {
        display: flex;
        width:100%;
        height:35px;
        align-items: center;
        justify-content: flex-end;
        background-color: lightslategrey;
    }

    .rs-top {
        justify-content: flex-start;
    }

    #mw-content {
        width: 100%;
        height: 100vh;
    }
</style>

HTML:

<div class="d-flex">
    <div id="left-sidebar" class="col- red">
        <div class='ls-top grey'>
            <button class="ls-toggle"><i class="fas fa-angle-left fa-2x"></i></button>
        </div>
    </div>

    <div id="mw-content" class="col green">
        <h3> Main Window Content.</h3>
    </div>

    <div id="right-sidebar" class="col- red">
        <div class='rs-top grey'>
            <button class="rs-toggle"><i class="fas fa-angle-right fa-2x"></i></button>
        </div>
    </div>
</div>

JS:

$(document).ready(function () {
        var lsToggleBtn = document.querySelector('.ls-toggle');
        var lsSidebar = document.querySelector('#left-sidebar');
        var rsToggleBtn = document.querySelector('.rs-toggle');
        var rsSidebar = document.querySelector('#right-sidebar');

        lsToggleBtn.addEventListener('click', function () {
            lsToggleBtn.classList.toggle('is-closed');
            lsSidebar.classList.toggle('is-closed');
        });

        rsToggleBtn.addEventListener('click', function () {
            rsToggleBtn.classList.toggle('is-closed');
            rsSidebar.classList.toggle('is-closed');
        });
    });

我尝试过的事情:

显然 none 这些想法奏效了,我承认我不是最擅长使用 flexbox 的人,所以我确定我只是遗漏了一些基本的东西,但我会很感激你的任何建议好人可能有。 :)

这是一个示例,说明如何使用原版实现此目的 javascript。

两个函数,一个是跟踪部分元素的折叠并调整中间部分的大小。它检查点击并将元素(部分)id 添加到数组,条件检查数组,如果数组 includes 两个外部部分 id,我们使用 style.transform 调整中间部分的大小 => scale()。第二个函数重置可折叠元素。

在代码片段中找到更多信息。

let clicked = [];
const middle = document.querySelector('#sect2')

let section = document.querySelectorAll('.sect')
let reset = document.querySelector('#reset')

// function 
const resizeOnCollapse = (els) => {
  // loop over the three sections
  els.forEach(sect => {
    // do not allow the middle section to be collapsed
    if (sect.id !== 'sect2') {
      // eventlistener to check a click on the outer sections
      sect.addEventListener('click', (e) => {
        // push the clicked elements into an array 
        clicked.push(e.target.id)
        // set the event targets width to 0 
        // essentially collapsing it from view
        e.target.style.width = '0px';
        // conditional that checks if the array 
        // includes the two outer sections
        if (clicked.includes('sect1') && clicked.includes('sect3')) {
          // resize the middle section using
          // transform: scale()
          middle.style.transform = 'scale(1.2)'
          // transition animation on the transform 
          middle.style.transition = 'transform .5s ease-out'
        }
      })
    }
  })
}


// function to reset the elements and reset the array
const resetEls = (el, section) => {
  // eventlistener on click 
  el.addEventListener('click', () => {
    // reset the array
    clicked = [];
    // loop over the sections
    section.forEach((sect) => {
      // reset the width essentially uncollapsing the sections 
      sect.style.width = '30vw';
      // reset the middle transform rule, scale() to 1
      sect.style.transform = 'scale(1)';
    })
  })
}

// call the functions
resetEls(reset, section)
resizeOnCollapse(section)
#main {
  display: flex;
  justify-content: space-around;
}

.sect {
  width: 30vw;
  height: 80vh;
}

#sect1 {
  background-color: red;
}

#sect2 {
  background-color: blue;
}

#sect3 {
  background-color: green;
}
<button id="reset">reset</button>
<div id="main">
  <div id="sect1" class="sect">
  </div>
  <div id="sect2" class="sect">
  </div>
  <div id="sect3" class="sect">
  </div>
</div>

您需要尝试使用“position: absolute”并添加另外两个 classList.toggle 函数

$(document).ready(function () {
  var mwContent = document.querySelector('#mw-content');          // !!
  var lsToggleBtn = document.querySelector('.ls-toggle');
  var lsSidebar = document.querySelector('#left-sidebar');
  var rsToggleBtn = document.querySelector('.rs-toggle');
  var rsSidebar = document.querySelector('#right-sidebar');

  lsToggleBtn.addEventListener('click', function () {
    lsToggleBtn.classList.toggle('is-closed');
    lsSidebar.classList.toggle('is-closed');
    mwContent.classList.toggle('ls-pos');         // here
  });

  rsToggleBtn.addEventListener('click', function () {
    rsToggleBtn.classList.toggle('is-closed');
    rsSidebar.classList.toggle('is-closed');
    mwContent.classList.toggle('rs-pos');         // here
  });
});
body {
  background-color: lightslategrey;
  margin: 0;
  overflow: hidden;
}

.red {
  background-color: lightcoral;
}

.green {
  background-color: lightgreen;
}

.grey {
  background-color: lightslategray;
}

* {
  box-sizing: border-box;
}

.d-flex {
  display: flex;
  position: relative;
}

.ls-toggle,
.rs-toggle {
  cursor: pointer;
  transition: 0.5s;
}

#left-sidebar {
  position: absolute;
  left: 0;
  width: 250px;
  height: 100vh;
  transition: 0.5s;
}

#right-sidebar {
  position: absolute;
  right: 0;
  width: 250px;
  height: 100vh;
  transition: 0.5s;
}

#left-sidebar.is-closed {
  transform: translateX(-80%);
}

#right-sidebar.is-closed {
  transform: translateX(80%);
}

.ls-top,
.rs-top {
  display: flex;
  width: 100%;
  height: 35px;
  align-items: center;
  justify-content: flex-end;
  background-color: lightslategrey;
}

.rs-top {
  justify-content: flex-start;
}

#mw-content {
  position: absolute;
  right: 250px;
  left: 250px;
  height: 100vh;
  transition: 0.5s;
}

.ls-pos {
  left: 50px !important;
  transition: 0.5s;
}

.rs-pos {
  right: 50px !important;
  transition: 0.5s;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>


  <div class="d-flex">
    <div id="left-sidebar" class="col red">
      <div class='ls-top grey'>
        <button class="ls-toggle"><i class="fas fa-angle-left fa-2x"></i></button>
      </div>
    </div>

    <div id="mw-content" class="col green">
      <h3> Main Window Content.</h3>
    </div>

    <div id="right-sidebar" class="col red">
      <div class='rs-top grey'>
        <button class="rs-toggle"><i class="fas fa-angle-right fa-2x"></i></button>
      </div>
    </div>
  </div>