无法使网格布局容器自动拉伸以填充相邻行内容器创建的折叠空间

问题描述 投票:0回答:1

我在嵌套布局中混合了 CSS Grid 和 Flexbox。外部布局是 2x2 CSS 网格。每个网格容器将包含另一个网格布局或一些 Flexbox 组件。

外部网格的左下角容器是一个可折叠侧边栏,包含 2x2 网格,右下角容器有一个 3x2 网格。

当我将整个左下容器向左折叠时,我希望右下容器向左拉伸并占据空出的空间。在此过程中,它应该自动调整其包含的元素的大小。不幸的是我无法实现它。

* {
  box-sizing: border-box;
  /* this is also essential to avoid a world of width-based pain */
}

.body {
  height: 100vh;
  width: 100vw;
  margin: 0;
  /* negates the default 8px margins */
  display: grid;
  grid-template-columns: 20% 1fr;
  grid-template-rows: 10% 1fr;
  grid-template-areas: "logo head" "side main";
}

.logo {
  background-color: #fff;
  grid-area: logo;
  display: flex;
  flex-flow: row nowrap;
  justify-content: flex-start;
  align-content: center;
}

.img {
  height: 100%;
  object-fit: cover;
}

.header {
  background-color: #fff;
  padding: 0.3rem;
  grid-area: head;
  display: flex;
  flex-flow: row nowrap;
  justify-content: center;
  align-content: center;
  display: grid;
  /* nested grid inside the header */
  grid-template-columns: 2fr 1fr;
  /* define 3 equal columns each taking same fraction of the space */
  grid-template-rows: 1fr;
  /* there's only one row; so take all the available space */
  grid-template-areas: "msg regoraccess";
  gap: 0.5em;
}

.head-card {
  border-radius: .25rem;
  display: flex;
  flex-flow: row wrap;
  justify-content: center;
  align-content: center;
}


/* place each of the six cards in their respective areas */

.head-card:nth-child(1) {
  grid-area: msg;
}

.notification {
  text-align: center;
  margin: 0;
}

.head-card:nth-child(2) {
  grid-area: regoraccess;
  display: flex;
  flex-flow: row wrap;
  justify-content: flex-end;
  align-content: center;
}

.side-bar {
  background-color: #1c1f23;
  padding: 0.1rem 0 0.1rem 0.1rem;
  grid-area: side;
  display: flex;
  flex-flow: row nowrap;
  align-content: flex-start;
  display: grid;
  grid-template-columns: 0.05fr 0.95fr;
  grid-template-rows: 0.9fr 0.1fr;
  grid-template-areas: "collapse menu" "rc rc";
}

.side-card {
  display: flex;
}


/*
    nth-child(1): Collapse button
    nth-child(2): Menu
    nth-child(3): Copyright
*/

.side-card:nth-child(1) {
  grid-area: collapse;
  display: flex;
  flex-flow: row wrap;
  justify-content: flex-end;
  align-content: center;
}

.fa-solid {
  color: #3DED97;
  /* Seafoam Color */
}

.accord-button>input {
  display: none;
}

.accord-button>input:checked+label .not-active {
  display: none;
}

.accord-button>input:not(:checked)+label .active {
  display: none;
}


/* the menu */

.side-card:nth-child(2) {
  grid-area: menu;
  display: flex;
  flex-flow: column wrap;
  justify-content: flex-start;
  align-content: flex-start;
  transition: width 300ms;
}

.nav {
  display: flex;
  flex-flow: column wrap;
  padding: 1rem;
  gap: 1rem;
}

.nav li {
  display: flex;
}

.menu-button {
  background: transparent;
  border: 0;
  color: white;
}

body:has(.accord-button > input:checked) {
  #aside {
    width: 1em;
  }
  .side-card:nth-child(2) {
    display: none;
  }
  .side-card:nth-child(3) {
    width: 1em;
  }
  .long-copyright {
    display: none;
  }
}

body:has(.accord-button > input:not(:checked)) {
  .short-copyright {
    display: none
  }
}


/* copyright */

.side-card:nth-child(3) {
  grid-area: rc;
  display: inline-flex;
  flex-flow: row wrap;
  justify-content: flex-start;
  align-content: flex-end;
}

.long-copyright {
  color: #D3D3D3;
  /* light-gray */
  font-size: 1rem;
}

.short-copyright {
  color: #D3D3D3;
  /* light-gray */
  font-size: 0.5rem;
}


/* the main engagement area */

.main {
  background-color: #c3c5ca;
  padding: 0.5rem;
  /* padding all around the main container */
  grid-area: main;
  display: grid;
  /* nested grid inside the main */
  grid-template-columns: 1fr 1fr 1fr;
  /* define 3 equal columns each taking same fraction of the space */
  grid-template-rows: 1fr 1fr 1fr;
  /* define 3 equal rows each taking same fraction of available space */
  grid-template-areas: "col-1 col-2 col-3" "col-4 col-4 col-5" "col-4 col-4 col-6";
  gap: 1em;
  /* gap between the rows and the columns */
  flex-grow: 1;
  /* <== will not work here because of the Display: Grid on Parent */
}

.card {
  background-color: #f6f7f9;
  border-radius: 1rem;
}


/* place each of the six cards in their respective areas */

.card:nth-child(1) {
  grid-area: col-1;
}

.card:nth-child(2) {
  grid-area: col-2;
}

.card:nth-child(3) {
  grid-area: col-3;
}

.card:nth-child(4) {
  grid-area: col-4;
}

.card:nth-child(5) {
  grid-area: col-5;
}

.card:nth-child(6) {
  grid-area: col-6;
}


/* media queries */

@media (max-width: 900px) {
  .main {
    grid-template-columns: 1fr;
    grid-template-rows: repeat(6, 1fr);
    grid-template-areas: initial;
  }
  .card {
    grid-area: initial !important;
  }
}
<html>

<head>
  <meta charset="UTF-8">
  <meta http-equiv="X-UA-Compatible" content="IE=edge" />
  <meta name="viewport" content="width=device-width, initial-scale=1.0" />
  <link href="https://cdn.jsdelivr.net/npm/[email protected]/dist/css/bootstrap.min.css" rel="stylesheet" />
  <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.4.2/css/all.min.css" crossorigin="anonymous">
  <link rel="stylesheet" type="text/css" href="styles.css" />
</head>

<body class="body">
  <section class="logo">
    <img class="img" src="../static/images/logo.png">
  </section>
  <header class="header">
    <div class="head-card"><span class="notification">[ some msg ]</span></div>
    <div class="head-card">
    </div>
  </header>

  <!-- Collapsible Side Nav bar for menus -->
  <section id="aside" class="side-bar">
    <div class="side-card">
      <div class='accord-button'>
        <input type='checkbox' id='accordianinput'>
        <label for='accordianinput'>
            <i class="fa-solid fa-arrow-circle-left not-active"></i>
            <i class="fa-solid fa-arrow-circle-right active"></i>
          </label>
      </div>
    </div>
    <div class="side-card">
      <ul class="nav">
        <li><button type="button" class="menu-button" onclick="#">Home</button></li>
        <li><button type="button" class="menu-button" onclick="#">About</button></li>
      </ul>
    </div>
    <div class="side-card">
      <span class="long-copyright">&copy; Runaway Company, Inc.</span>
      <span class="short-copyright">&copy;RC</span>
    </div>
  </section>

  <main class="main">
    <div class="card">
    </div>
    <div class="card">
    </div>
    <div class="card">
    </div>
    <div class="card">
    </div>
    <div class="card">
    </div>
    <div class="card">
    </div>
  </main>

</body>

</html>

我知道“flex-grow:1”不适用于“主”容器,但不知道如何处理。谁能告诉我正确的方法吗?

html css flexbox css-grid
1个回答
0
投票

如果你想让侧边栏折叠起来,我不会在主体上使用 2x2 网格。将主体设置为单列两行 (1x2)。第一行将包含您的标题,第二行将包含侧边栏和主面板。

使用 Flexbox 设置每一行的格式。对于标题行,请使用

justify-content: space-between
。第二排几乎会照顾自己。

* {
  box-sizing: border-box;
}

body, html {
  height: 100vh;
}

body {
  margin: 0;
  display: grid;
  grid-template-rows: auto 1fr;
}

header {
  background-color: #fff;
  padding: 0.3rem;
  display: flex;
  justify-content: space-between;
  align-items: center;
  gap: 0.5em;
}

main {
  display: flex;
}

.side-bar {
  background-color: #1c1f23;
  padding: 0.1rem 0 0.1rem 0.1rem;
  grid-area: side;
  display: flex;
  flex-flow: row nowrap;
  align-content: flex-start;
  display: grid;
  grid-template-columns: 0.05fr 0.95fr;
  grid-template-rows: 0.9fr 0.1fr;
  grid-template-areas: "collapse menu" "rc rc";
}

.side-card {
  display: flex;
}


/*
    nth-child(1): Collapse button
    nth-child(2): Menu
    nth-child(3): Copyright
*/

.side-card:nth-child(1) {
  grid-area: collapse;
  display: flex;
  flex-flow: row wrap;
  justify-content: flex-end;
  align-content: center;
}

.fa-solid {
  color: #3DED97;
  /* Seafoam Color */
}

.accord-button>input {
  display: none;
}

.accord-button>input:checked+label .not-active {
  display: none;
}

.accord-button>input:not(:checked)+label .active {
  display: none;
}


/* the menu */

.side-card:nth-child(2) {
  grid-area: menu;
  display: flex;
  flex-flow: column wrap;
  justify-content: flex-start;
  align-content: flex-start;
  transition: width 300ms;
}

.nav {
  display: flex;
  flex-flow: column wrap;
  padding: 1rem;
  gap: 1rem;
}

.nav li {
  display: flex;
}

.menu-button {
  background: transparent;
  border: 0;
  color: white;
}

body:has(.accord-button > input:checked) {
  #aside {
    width: 1em;
  }
  .side-card:nth-child(2) {
    display: none;
  }
  .side-card:nth-child(3) {
    width: 1em;
  }
  .long-copyright {
    display: none;
  }
}

body:has(.accord-button > input:not(:checked)) {
  .short-copyright {
    display: none
  }
}


/* copyright */

.side-card:nth-child(3) {
  grid-area: rc;
  display: inline-flex;
  flex-flow: row wrap;
  justify-content: flex-start;
  align-content: flex-end;
}

.long-copyright {
  color: #D3D3D3;
  /* light-gray */
  font-size: 1rem;
}

.short-copyright {
  color: #D3D3D3;
  /* light-gray */
  font-size: 0.5rem;
}


/* the main engagement area */

.mainpanel {
  background-color: #c3c5ca;
  padding: 0.5rem;
  /* padding all around the main container */
  grid-area: main;
  display: grid;
  /* nested grid inside the main */
  grid-template-columns: 1fr 1fr 1fr;
  /* define 3 equal columns each taking same fraction of the space */
  grid-template-rows: 1fr 1fr 1fr;
  /* define 3 equal rows each taking same fraction of available space */
  grid-template-areas: "col-1 col-2 col-3" "col-4 col-4 col-5" "col-4 col-4 col-6";
  gap: 1em;
  /* gap between the rows and the columns */
  flex-grow: 1;
  /* <== will not work here because of the Display: Grid on Parent */
}

.card {
  background-color: #f6f7f9;
  border-radius: 1rem;
}


/* place each of the six cards in their respective areas */

.card:nth-child(1) {
  grid-area: col-1;
}

.card:nth-child(2) {
  grid-area: col-2;
}

.card:nth-child(3) {
  grid-area: col-3;
}

.card:nth-child(4) {
  grid-area: col-4;
}

.card:nth-child(5) {
  grid-area: col-5;
}

.card:nth-child(6) {
  grid-area: col-6;
}


/* media queries */

@media (max-width: 900px) {
  .mainpanel {
    grid-template-columns: 1fr;
    grid-template-rows: repeat(6, 1fr);
    grid-template-areas: initial;
  }
  .card {
    grid-area: initial !important;
  }
}
<link href="https://cdn.jsdelivr.net/npm/[email protected]/dist/css/bootstrap.min.css" rel="stylesheet" />
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.4.2/css/all.min.css" crossorigin="anonymous">

<header>
  <img class="logo" src="https://picsum.photos/80/40">
  <div>header centre</div>
  <div>header right</div>
</header>

<main>

  <nav id="aside" class="side-bar">
    <div class="side-card">
      <div class='accord-button'>
        <input type='checkbox' id='accordianinput'>
        <label for='accordianinput'>
            <i class="fa-solid fa-arrow-circle-left not-active"></i>
            <i class="fa-solid fa-arrow-circle-right active"></i>
          </label>
      </div>
    </div>
    <div class="side-card">
      <ul class="nav">
        <li><button type="button" class="menu-button" onclick="#">Home</button></li>
        <li><button type="button" class="menu-button" onclick="#">About</button></li>
      </ul>
    </div>
    <div class="side-card">
      <span class="long-copyright">&copy; Runaway Company, Inc.</span>
      <span class="short-copyright">&copy;RC</span>
    </div>
  </nav>

  <div class="mainpanel">
    <div class="card">
    </div>
    <div class="card">
    </div>
    <div class="card">
    </div>
    <div class="card">
    </div>
    <div class="card">
    </div>
    <div class="card">
    </div>
  </div>

</main>

© www.soinside.com 2019 - 2024. All rights reserved.