I'm trying to make a sidebar that aligns vertically an undetermined number of list items. When the number of items reaches the bottom of the sidebar, they are grouped in columns via flex.
My problem is that I want the width of the sidebar to be 100px wide when closed and when opened, I want it to be the width of the columns. If I use a fixed width for the open state, this happens:
HTML:
<nav class="sidebar">
<ul>
<li>
1
</li>
<li>
2
</li>
<li>
3
</li>
<li>
4
</li>
<li>
5
</li>
<li>
...
</li>
</ul>
</nav>
SCSS:
.sidebar {
background: #ccc;
width: 100px;
ul {
list-style-type: none;
height: 100vh;
display: flex;
flex-wrap: wrap;
flex-direction: column;
align-content: flex-start;
li {
background: #000;
height: 80px;
width: 80px;
}
}
&:hover
{
//width: !?!?!?!
}
}
How can i accomplish this? How can a open sidebar and show all the columns?
UPDATE: The height of the sidebar can vary depending on the screen size. I updated the code with the original settings.
UPDATE #2: I tested both solutions, although @itay-gal was a clever CSS only option, it lacked the ability to animate. Since i'm already using JS, i ended up using @pablo-darde solution.
I made a small change in @pablo-darde's so that it could work with a variable height sidebar:
const sidebar = document.querySelector('.sidebar');
const ul = sidebar.querySelector('ul');
const li = ul.querySelector('li');
const showRemainder = () => {
const ulHeight = ul.clientHeight;
const liHeight = li.clientHeight;
const width = ul.clientWidth * Math.ceil(ul.children.length / (ulHeight / liHeight));
sidebar.style.maxWidth = `${width}px`;
}