Ok, after some more meddling my original idea works. This means if you have the following HTML:
<ul class="grid-items">
<!-- <li>Row 1-1</li> -->
<li class="ui-grid-span-2">SPAN 2</li>
<li>Row 1-3</li>
<li>Row 1-4</li>
<li>Row 1-5</li>
<li>Row 1-6</li>
</ul>
the width of the list elements can be set as I intended:
ul > li:nth-child(-n+4).ui-grid-span-2 {
width: 33.33%;
}
ul > li:nth-child(-n+3).ui-grid-span-3 {
width: 50%;
}
ul > li:nth-child(-n+2).ui-grid-span-4 {
width: 66.66%;
}
ul > li:nth-child(-n+1).ui-grid-span-5 {
width: 83.33%;
}
Note that by spanning multiple cells, the total number of cells change, too, so the pseudo-selector must be adjusted depending on cells spanned. To make it work with multiple ranges of cells (not always 6 cells as above) it is also required to add a class on the list element to note the number of cells in a row. Otherwise larger selector (take first 8 items) will overwrite/encapsulate smaller ones (take first 7 items).
Still not happy with it and only supporting a single rowspan
per row, but... it works and it's not using any of the above proposed solutions (~ siblings, x*y cells * n rowspans rules, flexbox or tables). Keep in mind, the regular cell width declarations need to be amended, too, as a row using rowspan
will have less number of cells but require the original intended number of cells' width.
Final CSS for up to 8 cell grids (I have not combined declarations for sake of comprehensability).
Note:
- section ROWSPAN is the relevant section
- before I ensure cell width is set based on intended not actual number of cells
- selectors are cutoff for relevance.
/* base width */
ul > li {
width: auto;
}
/* "cell width" */
ul > li:first-child:nth-last-child(1) {
width: 100%;
}
ul > li:first-child:nth-last-child(2),
ul > li:first-child:nth-last-child(2) ~ li {
width: 50%;
}
ul.ui-grid-column-3 > li:first-child:nth-last-child(n),
ul.ui-grid-column-3 > li:first-child:nth-last-child(n) ~ li {
width: 33.3333%;
}
ul.ui-grid-column-4 > li:first-child:nth-last-child(n),
ul.ui-grid-column-4 > li:first-child:nth-last-child(n) ~ li {
width: 25%;
}
ul.ui-grid-column-5 > li:first-child:nth-last-child(n),
ul.ui-grid-column-5 > li:first-child:nth-last-child(n) ~ li {
width: 20%;
}
ul.ui-grid-column-6 > li:first-child:nth-last-child(n),
ul.ui-grid-column-6 > li:first-child:nth-last-child(n) ~ li {
width: 16.667%;
}
ul.ui-grid-column-7 > li:first-child:nth-last-child(n),
ul.ui-grid-column-7 > li:first-child:nth-last-child(n) ~ li {
width: 14.285714286%;
}
ul.ui-grid-column-8 > li:first-child:nth-last-child(n),
ul.ui-grid-column-8 > li:first-child:nth-last-child(n) ~ li {
width: 12.5%;
}
/* ROWSPAN */
/* 3 cells */
ul.ui-grid-column-3 > li:nth-child(-n+2).ui-grid-span-2 {
width: 66.666%;
}
/* 4 cells */
ul.ui-grid-column-4 > li:nth-child(-n+3).ui-grid-span-2 {
width: 50%;
}
ul.ui-grid-column-4 > li:nth-child(-n+2).ui-grid-span-3 {
width: 75%;
}
/* 5 cells */
ul.ui-grid-column-5 > li:nth-child(-n+4).ui-grid-span-2 {
width: 40%;
}
ul.ui-grid-column-5 > li:nth-child(-n+3).ui-grid-span-3 {
width: 60%;
}
ul.ui-grid-column-5 > li:nth-child(-n+2).ui-grid-span-4 {
width: 80%;
}
/* 6 cells */
ul.ui-grid-column-6 > li:nth-child(-n+5).ui-grid-span-2 {
width: 33.33%;
}
ul.ui-grid-column-6 > li:nth-child(-n+4).ui-grid-span-3 {
width: 50%;
}
ul.ui-grid-column-6 > li:nth-child(-n+4).ui-grid-span-4 {
width: 66.66%;
}
ul.ui-grid-column-6 > li:nth-child(-n+4).ui-grid-span-5 {
width: 83.33%;
}
/* 7 cells */
ul.ui-grid-column-7 > li:nth-child(-n+6).ui-grid-span-2 {
width: 28.571428571%;
}
ul.ui-grid-column-7 > li:nth-child(-n+5).ui-grid-span-3 {
width: 42.857142857%;
}
ul.ui-grid-column-7 > li:nth-child(-n+4).ui-grid-span-4 {
width: 57.142857142%;
}
ul.ui-grid-column-7 > li:nth-child(-n+3).ui-grid-span-5 {
width: 71.428571428%;
}
ul.ui-grid-column-7 > li:nth-child(-n+2).ui-grid-span-6 {
width: 85.714285714%;
}
/* 8 cells */
ul.ui-grid-column-8 > li:nth-child(-n+7).ui-grid-span-2 {
width: 25%;
}
ul.ui-grid-column-8 > li:nth-child(-n+6).ui-grid-span-3 {
width: 37.5%;
}
ul.ui-grid-column-8 > li:nth-child(-n+5).ui-grid-span-4 {
width: 50%;
}
ul.ui-grid-column-8 > li:nth-child(-n+4).ui-grid-span-5 {
width: 62.5%;
}
ul.ui-grid-column-8 > li:nth-child(-n+3).ui-grid-span-6 {
width: 75%;
}
ul.ui-grid-column-8 > li:nth-child(-n+2).ui-grid-span-7 {
width: 87.5%;
}
/* responsive */
@media (max-width: 32em) {
ul > li,
ul[class*="ui-grid-column"] > li {
width: 100%;
}
}