Is it possible to rearrange the divs inside a container according to number of divs inside?

Viewed 58

I am new to html and css. I'd like to create an function that given a number k between 1 to 9, there will be k divs displayed inside the container div. However, the arrangement of blocks varies as k differs. For example, for k=4, the arrangement will be 2x2, while for k=6, the arrangement will be 3x2. All arrangement can be seen in the below picture. picture Is there any way I can adjust the arrangement based on the number of divs? I guess I should use flexbox for css but I somehow could not find the correct configuration of the container.

2 Answers

Here is a pure CSS solution using display: grid; and the :has() CSS pseudo-class. Using :has() we can apply styles to an element based on its children count:

#container:has(div:nth-child(3)) {
  grid-template-columns: 1fr 1fr;
  grid-template-rows: 1fr 1fr;
}

The above style will apply to the element with id="container" only when it contains at least 3 child elements.

JS Fiddle

(JavaScript only used to add divs to container for demonstration)

Sources:

Article explaining how to style elements based on their children count: https://www.matuzo.at/blog/2022/counting-children/

:has() CSS pseudo-class: https://developer.mozilla.org/en-US/docs/Web/CSS/:has

HTML:Creating Input for K value with submit & reset Buttons,creating a div container .wrapper.

CSS:giving my container 400x400 Size. declaring a :root variable --width:50%; which is being used to set width of a single box which will be generated through JS.

JS:adding EventListener on submit button. first thing i am doing is getting the value of input(K). putting an if condition to check if user has already generated any divs,if has, i remove every thing inside the wrapper with innerHTML = ""

putting another if to check if the number is greater than 4 then making the size of each box 33% to fill our 3x3 requirment by changing the value of the variable in the :root to --width:33%`.

looping inside for loop to create our box.Boxes will generate (k)Times. with html inside createBox and adding it inside wrapper. i hope you understood.if you have any questions please ask.

let wrapper = document.querySelector(".wrapper");
let btn = document.querySelector(".btn");
let resetBtn = document.querySelector(".r-btn");

btn.addEventListener("click", () => {
  let input = document.querySelector("#input").value;
  if (wrapper.innerHTML !== "") {
    wrapper.innerHTML = "";
  }
  if (input > 4) {
    document.querySelector(":root").style.setProperty("--width", "33.3%");
  } else {
    document.querySelector(":root").style.setProperty("--width", "50%");
  }
  for (let i = 0; i < input; i++) {
    let createBox = `<div class="box">${i + 1}</div>`;
    wrapper.innerHTML += createBox;
  }

  document.querySelector("#input").value = "";
});
resetBtn.addEventListener("click", () => {
  wrapper.innerHTML = "";
});
:root{
  --width:50%;
}
#input {
  width: 100px;
  margin-bottom: 10px;
}
.box {
  background-color: burlywood;
  text-align: center;
  width: var(--width);
  outline: 1px solid green;
}
.wrapper {
  display: flex;
  flex-wrap: wrap;
  width: 400px;
  height: 400px;
  outline: 1px solid red;
}
<input min="2" max="9" type="number" placeholder="Enter K Value" id="input" />
<button class="btn">Enter</button>
<button class="r-btn">Reset</button>
<div class="wrapper"></div>

Related