Home > Mobile >  Check if element count is odd, or else using CSS only
Check if element count is odd, or else using CSS only

Time:03-03

I want to set layout dynamically by number of item, using display:flex, as below layout:

// If number of child element is odd, first item width is 100% else 50%
 --------- 
|    1    |
 --------- 
 ---   --- 
| 2 | | 3 |
 ---   --- 
 ---   --- 
| 4 | | 5 |
 ---   --- 
...
// If number of child element is even, all items width is 50%
 ---   --- 
| 1 | | 2 |
 ---   --- 
 ---   --- 
| 3 | | 4 |
 ---   --- 
...

The items example is as below:

<!-- Count : 1 -->
<div id="box">
    <div >1</div>
</div>

<!-- Count : 2 -->
<div id="box">
    <div >1</div>
    <div >2</div>
</div>

<!-- Count : 3 -->
<div id="box">
    <div >1</div>
    <div >2</div>
    <div >3</div>
</div>

<!-- Count : 4 -->
<div id="box">
    <div >1</div>
    <div >2</div>
    <div >3</div>
    <div >4</div>
</div>
<!-- ... -->

So, I want to setup layout like below code, but I want to do it using CSS only.

function setLayout() {
    if (items.length % 2 === 0) {
        // Even
        // ... All items width set to 50%
    }
    else {
        // Odd
        // ... First item width set to 100%
        // ... All items width set to 50%, except first item
    }
}

I refer the document, but I don't know how to "count" items and apply CSS for count condition(if odd/even). https://developer.mozilla.org/en-US/docs/Web/CSS/Pseudo-classes#tree-structural_pseudo-classes

So, how can I gets number of items is odd or even, and apply different setting, using CSS only?

CodePudding user response:

You can do it like below:

#box {
  display: flex;
  flex-wrap:wrap;
  gap: 10px;
  border:5px solid blue;
  margin:10px;
}

#box > div {
  flex: 40%;
  height: 40px;
  background: red;
}

/* select the first element of it's an "odd" child counting from the end */
#box > div:first-child:nth-last-child(odd) {
  flex-basis:100%;
}
<!-- Count : 1 -->
<div id="box">
  <div >1</div>
</div>

<!-- Count : 2 -->
<div id="box">
  <div >1</div>
  <div >2</div>
</div>

<!-- Count : 3 -->
<div id="box">
  <div >1</div>
  <div >2</div>
  <div >3</div>
</div>

<!-- Count : 4 -->
<div id="box">
  <div >1</div>
  <div >2</div>
  <div >3</div>
  <div >4</div>
</div>
<!-- ... -->

<!-- Count : 5 -->
<div id="box">
  <div >1</div>
  <div >2</div>
  <div >3</div>
  <div >4</div>
  <div >5</div>
</div>
<!-- ... -->

CodePudding user response:

You can do this with css. but before that remember one id can only be applied to one element (ids cannot be repeated). what you can do is add to the divs and use :nth-child() as below code

.box .item:nth-child(1){
 // your code
}


.box .item:nth-child(odd){
 // your code for elements 1,3,etc
}

.box .item:nth-child(even){
 // your code for elements 2,4,etc
}

Edit:

You can create 2 classes called count-odd and count-even add your desired styles to them and use below js code to add classes dynamically, as given in below snippet

function setCountClass() {
  var boxes = document.querySelectorAll(".box"); 
  boxes.forEach((e, i) => {
    if (e.children.length % 2 === 0) {
      e.classList.add("count-even");
    } else {
      e.classList.add("count-odd");
    }
  });
}

setCountClass();
.box{
  margin: 2rem;
  padding: 1rem;
  display: flex;
  gap: 1rem;
}

.count-even{
  background: red;
  color: white;
}

.count-odd{
  background: blue; 
  color: white;
}

.count-odd div:first-child{
  margin: 0.5rem;
  padding: 0.5rem;
  border: 1px solid;
}
<!-- Count : 1 -->
<div >
    <div >1</div>
</div>

<!-- Count : 2 -->
<div >
    <div >1</div>
    <div >2</div>
</div>

<!-- Count : 3 -->
<div >
    <div >1</div>
    <div >2</div>
    <div >3</div>
</div>

<!-- Count : 4 -->
<div >
    <div >1</div>
    <div >2</div>
    <div >3</div>
    <div >4</div>
</div>
<!-- ... -->

CodePudding user response:

You need only to check if the count of whole elements odd or even. Then you can assign byusing Javascript a class to the wrapped box element. Two working examples. One with odd and one with even elments.

Odd Elements

const elements = 5;
const box = document.querySelector('.box');
let className = (elements % 2) ? 'odd' : 'even';

for (let i = 0; i < elements; i  ) {  
  let item = document.createElement('div')
  item.setAttribute('class','item');
  item.innerHTML = (i   1);
  box.append(item);  
}
console.log(className)
box.classList.add(className);
.box {
  display: flex;  
  flex-wrap: wrap;
  background: #e2eaf4;
  padding: 10px; 
}

.item {
  flex: 1 1 40%;  
  font-family: "Open Sans", Arial;
  font-size: 20px;
  color: #FFF;
  text-align: center;
  background: #3794fe;
  border-radius: 6px;
  padding: 20px;
  margin: 12px;  
}


.odd .item:first-child {
  width: 100%;
  flex: 1 1 100%;
}
<div ></div>

Even Elements

const elements = 4;
const box = document.querySelector('.box');
let className = (elements % 2) ? 'odd' : 'even';

for (let i = 0; i < elements; i  ) {  
  let item = document.createElement('div')
  item.setAttribute('class','item');
  item.innerHTML = (i   1);
  box.append(item);  
}
console.log(className)
box.classList.add(className);
.box {
  display: flex;  
  flex-wrap: wrap;
  background: #e2eaf4;
  padding: 10px; 
}

.item {
  flex: 1 1 40%;  
  font-family: "Open Sans", Arial;
  font-size: 20px;
  color: #FFF;
  text-align: center;
  background: #3794fe;
  border-radius: 6px;
  padding: 20px;
  margin: 12px;  
}


.odd .item:first-child {
  width: 100%;
  flex: 1 1 100%;
}
<div ></div>

  • Related