Tips for avoiding a large <ul> element from spilling over the body in a flexbox design

I struggled to articulate the problem I am facing, and I apologize if it's still unclear

So, in my app, I have 3 cards, and the 2 side ones contain lists (<ul>) that can become quite lengthy. I want the scrollbar to appear on the <ul> itself, not on the "main window".

This is the desired appearance:

https://i.stack.imgur.com/Y7UAm.png

However, this is what currently happens:

https://i.stack.imgur.com/AybkA.png

To achieve the first screenshot, I set max-height: 80vh on my lists, but this is not an ideal solution as it only works for a specific screen size.

Here's the link to the codepen, simply click on "Add more items" a few times to see the issue

Below is the CSS for the main section and the basic HTML structure, in case you prefer not to check the codepen

<div class="room-wrapper">
  <div><button class="btn btn-primary add-more-btn">Add more items</button></div>
  <div class="room-content">

    <div class="left-card app-card">
      <div class="left-card-wrapper">
        <div>
          <h3>Left Card</h3>
          <hr>
        </div>
        <ul class="my-list"></ul>
      </div>
    </div>

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

    <div class="right-card app-card">
      <div class="players-wrapper">
        <div>
          <h3>Right Card</h3>
          <hr>
        </div>
        <ul class="my-list"></ul>
      </div>
    </div>

  </div>
</div>
.room-wrapper {
  display: flex;
  flex-flow: column;
  height: 100%;
  padding: 10px;
}

.room-content {
  flex: 1 1 auto;
  text-align: center;
  
  display: flex;
  justify-content: center;
  flex-wrap: wrap;
}

.my-list {
  overflow-y: auto;
  
  /* This would "solve" it, but only for a very
  specific window size, this is what I used for
  the first screenshot
  
  max-height: 80vh;
  */
}

Answer №1

After implementing some small adjustments and utilizing flex properties, I managed to get the solution to work flawlessly.

To achieve a perfect layout, simply insert the additional CSS provided below:

.my-list {
  flex: 1 1 1px;
}

.players-wrapper,
.left-card-wrapper {
  height: 100%;
  display: flex;
  flex-direction: column;
}

$(".add-more-btn").click(() => {
  $(".list-group").append("<li class=\"list-group-item\">Item</li>");
});
body,
html {
  height: 100%;
}

body {
  background-color: #dadada;
}

/* Rest of the CSS code continues... */
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.4.1/css/bootstrap.min.css">
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script>
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.4.1/js/bootstrap.min.js"></script>
<div class="room-wrapper">
  <!-- The rest of the HTML markup continuation -->
</div>

Answer №2

* {
    margin: 0;
    padding: 0;
    box-sizing: border-box;
}

body {
    background-color: #dadada;
}

.room-wrapper {
    display: flex;
    flex-flow: column;
    height: 100%;
    padding: 10px;
}

.room-content {
    flex: 1 1 auto;
    text-align: center;
    display: flex;
    justify-content: center;
    flex-wrap: wrap;
}

.app-card {
    height: 85vh;
    border-radius: 10px;
    margin: 10px 10px;
    padding: 10px;
    background-color: white;
    flex-basis: 0;
    flex-grow: 1;
    flex-shrink: 1;
}

.main-card {
    flex-grow: 2!important;
}

.form-wrapper {
    display: flex;
    flex-direction: column;
    justify-content: space-between;
    height: 100%;
}

.my-list {
    display: block;
    height: 90%;
    overflow-y: auto;
}

.add-more-btn {
    margin: 10px;
}
<!DOCTYPE html>
<html lang="en">

<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" />
    <title>document</title>
    <link rel="stylesheet" href="style.css" />
</head>

<body>
    <div class="room-wrapper">
        <div><button class="btn btn-primary add-more-btn">Click here to Add more items!</button></div>
        <div class="room-content">

            <div class="left-card app-card">
                <div>
                    <h3>Left Card</h3>
                    <hr>
                </div>
                <ul class="my-left-list">
                   <!-- Repeating list items go here -->
                </ul>
            </div>

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

            <div class="right-card app-card">
                <div>
                    <h3>Right Card</h3>
                    <hr>
                </div>
                <ul class="my-right-list">
                  <!-- Repeating list items go here -->
                </ul>
            </div>

        </div>
    </div>
    <script src="script.js"></script>
</body>

</html>

Answer №3

Take a look at this to see if it meets your needs! You can view the code here : On codepen

body, html {
  height: 100%;
}

body {
  background-color: #dadada !important;
}


.room-wrapper {
  display: flex;
  flex-flow: column;
  height: 100%;
  padding: 10px;
}

.room-content {
  flex: 1 1 auto;
  text-align: center;
  height: calc(100% - 78px);
  display: flex;
  justify-content: center;
  flex-wrap: wrap;
}

.app-card {
  border-radius: 10px;
  margin: 10px 10px;
  padding: 10px;
  background-color: white;
  flex-basis: 0;
  flex-grow: 1;
  flex-shrink: 1;
  height:98%;
}

.main-card {
  flex-grow: 2!important;

}
.form-main{
    height:calc(100% - 78px);
  overflow:auto;
}
.form-wrapper {
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  height: 100%;
}

.my-list {
    overflow-y: auto;
    height: calc(100% - 78px);
}

.add-more-btn {
  margin: 10px;
}

.right-card>div,.left-card>div{
  height:100%;
}
<link href="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/4.6.0/css/bootstrap.min.css" rel="stylesheet"/>
<body>
  <div class="room-wrapper">
  <div><button class="btn btn-primary add-more-btn">Add more items</button> <button type="submit" class="btn btn-primary">Submit</button></div>
 
  <div class="room-content">
    <div class="left-card app-card">
      <div class="left-card-wrapper ">
        <div>
          <h3>Left Card</h3>
          <hr>
        </div>
        <ul class="list-group text-left my-list">
          <li class="list-group-item">Item</li>
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
        </ul>
      </div>
    </div>
    <div class="main-card app-card">
      <div class="form-wrapper">
        <div class="form-header">
          <h3>Form</h3>
          <hr>
        </div>
        <div class="form-main">
          <form>
            <div class="form-group">
              <label for="exampleFormControlInput1">Email address</label>
              <input type="email" class="form-control" id="exampleFormControlInput1" placeholder="<a href="/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="f39d929e96b3968b929e839f96dd909c9e">[email protected]</a>">
            </div>
            <div class="form-group">
              <label for="exampleFormControlSelect1">Example select</label>
              <select class="form-control" id="exampleFormControlSelect1">
                <option>1</option>
                <option>2</option>
                <option>3</option>
                <option>4</option>
                <option>5</option>
              </select>
            </div>
            <div class="form-group">
              <label for="exampleFormControlSelect2">Example multiple select</label>
              <select multiple class="form-control" id="exampleFormControlSelect2">
                <option>1</option>
                <option>2</option>
                <option>3</option>
                <option>4</option>
                <option>5</option>
              </select>
            </div>
            <div class="form-group">
              <label for="exampleFormControlTextarea1">Example textarea</label>
              <textarea class="form-control" id="exampleFormControlTextarea1" rows="3"></textarea>
            </div>
          </form>
        </div>
        
      </div>
    </div>
    <div class="right-card app-card">
      <div class="players-wrapper">
        <div>
          <h3>Right Card</h3>
          <hr>
        </div>
        <ul class="list-group text-left my-list">
          <li class="list-group-item">Item</li>
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
          <li class="list-group-item">Item</li>  
        </ul>
      </div>
    </div>
  </div>
</div>
</body>

Answer №4

.room-content {
  display: flex;
  box-shadow: inset 0px 0px 7px #ccc;
  padding: 1rem 2rem;
  margin-top: 2rem;
  background: #f6f6f6;
}
.room-content > div {
  flex: 1;
  border: 1px solid #e4e4e4;
  padding: 1rem;
  background: white;
  margin-right: 1rem;
  border-radius: 10px;
}
.room-content > div:last-child {
  margin-right: 0rem;
}
ul {
  padding: 0;
  overflow: scroll;
  height: 72vh;
}
.list-group-item {
  list-style-type: none;
  padding-block: 10px;
  border-bottom: 1px solid #eae9e9;
}
<!DOCTYPE html>
<html lang="en">
  <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" />
    <title>Three List</title>
  </head>

  <body>
    <div class="room-wrapper">
      <div>
        <button class="btn btn-primary add-more-btn">Add more items</button>
      </div>
      <div class="room-content">
        <div class="left-card app-card">
          <div>
            <h3>Left Card</h3>
            <hr />
          </div>
          <ul class="my-list">
            <li class="list-group-item">Item</li>
            <li class="list-group-item">Item</li>
(remaining list items have been omitted)

          </ul>
        </div>

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

        <div class="right-card app-card">
          <div>
            <h3>Right Card</h3>
            <hr />
          </div>
          <ul class="my-list">
            <li class="list-group-item">Item</li>
            <li class="list-group-item">Item</li>
(remaining list items have been omitted)

          </ul>
        </div>
      </div>
    </div>
    <script src="script.js"></script>
  </body>
</html>

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Checkbox's checked attribute fails to toggle

Encountered a peculiar issue while trying to implement jQuery functionality triggered by a checkbox. The checkbox seems to be toggling the check mark visually on click, but the "checked" attribute remains unchanged. For a demo of the problem, check out: h ...

What is the best way to align the logo image to the left side of the Material UI app bar without any gaps?

Currently, I am working on a material UI app bar to serve as my navigation bar. The issue I am encountering involves the logo image on the left side of the page having excessive spacing from the edge, as shown in the image below. I've tried adjusting ...

Position a button to be aligned with the bottom of its container

My goal is to have the button positioned at the bottom of the red div, nested inside it. .grand-parent { display: flex; flex-direction: row; flex-wrap: wrap; height: 300px; background-color: green; } .pa ...

Exploring the possibilities with JavaScript options

I am currently working on a project that involves a dropdown list... to complete unfinished sentences. Unfortunately, I am facing an issue with a message stating Uncaught TypeError: Cannot read property 'options' of null Below is a portion of m ...

Delete the div if it exists following another div and place it within the main div

<div class="error"> <input type="text" name="email"> <div class="error-message">Please Enter Email</div> </div> <div class="i-icon-div">Lorem Ipsum</div> I am trying to identify the div with the class of i-icon-di ...

Is dividing a container into equal sections possible with flexbox?

Is there a way to create an HTML/CSS structure that divides a fixed-size container into three sections horizontally? The first section should expand based on its content, while the remaining two sections should evenly split the leftover space, with scrollb ...

Is the height of the element determined by the parent rather than the content?

I need help with a layout featuring three containers - Total (with a red border), Left (yellow border containing an image), and Right (blue border containing text). Left is set to approximately 30% width with float: left, while Right is set to 70% width w ...

Guide to connecting a different HTML page to a thumbnail image using jQuery

let newColumnBlock = $('<div class="col-md-2">'); let newImagePoster = $('<img>'); let newSelectButton = $('<a href="secondPage.html"><button class="selectButton"></button></a>'); let movie ...

The static background and fixed header are locked in a perpetual battle

I am currently working on creating a fixed header that remains at the top of the page. However, I am facing an issue where the background seems to be overlapping and hiding the header. <style type="text/css> html, body {height:100%; margin:0; paddin ...

Exploring the dimensions of checkboxes in Fluent UI Northstar

Is there a specific method for controlling the size of checkboxes in Fluent UI Northstar? My attempts to modify the font size and height have only impacted the label, not the checkbox itself. Unfortunately, I couldn't find any guidance on this in the ...

JavaScript fails to focus on dynamically inserted input fields

Within my HTML template, there is an input element that I am loading via an Ajax call and inserting into existing HTML using jQuery's $(selector).html(response). This input element is part of a pop-up box that loads from the template. I want to set f ...

Using jquery and Ajax to extract data from nested JSON structures

Need help with modifying a code snippet for parsing nested JSON format [ { "name":"Barot Bellingham", "shortname":"Barot_Bellingham", "reknown":"Royal Academy of Painting and Sculpture", "bio":"Barot has just finished his final year at T ...

Is there a way to design a table that is responsive and automatically converts to a list when viewed on a mobile device

I am trying to design a responsive table showcasing artists' names. The goal is to have it look similar to this example: After finding and customizing code for the table, I encountered an issue when the table collapses on mobile view. The invisible e ...

I aim to have the capability to read numbers entered into text fields within a form prior to the form being submitted

I am currently working on a website where users can create brackets for the World Cup by guessing scores and winning teams. Right now, they have to manually fill in the bracket. I would like to implement a feature that reads what users are inputting while ...

What is the best way to use jQuery to set the height of one div equal to another div

Edited: I am facing a situation with a 3-column layout - Column A, Column B, Column C. The height of Column A is dynamic and I need to set the same height for both Column B and C. For instance, Column A contains a tabbed panel with varying heights based ...

bespoke HTML elements and properties

I'm currently facing some difficulties and I am unsure of how challenging it can be. I have tried following various tutorials, including those on SO and YouTube, but they all provide different approaches leaving me stuck. My goal is to create a custo ...

Tips for hiding a bootstrap modal in Angular4 when it has no content

I am currently working on an Angular 4 e-commerce application. One of the requirements is to hide a bootstrap modal when there are no products in the cart. When a user selects some products, they are added to the mycart modal screen. The user also has the ...

What is the best way to extract the body content from a Markdown file that includes Frontmatter

How can I retrieve the content of the body from my markdown file using front matter? Currently, it is displaying as undefined. What steps should I take to fix this issue? {latest.map(({ url, frontmatter }) => ( <PostCard url={url} content={frontmat ...

What is the best method for aligning buttons in a row with all the other buttons?

I have been attempting to display two buttons, id="strength" and id="minion", when a certain button, id="expandButton", is clicked. I want these two buttons to be positioned on either side of the button that triggers their cre ...

Header Dropdown Problems

Hey there, I have a question regarding my header setup. I currently have two headers in place: Whenever I click the notification button, the dropdown menu seems to disrupt the layout of the header. Here is a screenshot for reference: Below is the CSS cod ...