Минимальная ширина каждой колонки
Есть такая разметка:
var $table = $('.table');
if ($table.length) {
var $tr = $table.find('.tr');
var minWidth = 1;
$tr.each(function() {
var $td = $(this).find('.td:nth-of-type(1)');
$td.each(function() {
var letWidth = $(this).outerWidth();
if (letWidth > minWidth) minWidth = letWidth;
});
});
$table.find('.td:nth-of-type(1)').css({
'width': minWidth
});
}
* {
box-sizing: border-box;
}
.tr {
display: flex;
align-items: center;
justify-content: space-between;
}
.td {
border: 1px solid;
padding: 2px 20px;
-webkit-box-flex: 0;
-ms-flex-positive: 0;
flex-grow: 0;
-ms-flex-negative: 0;
flex-shrink: 0;
flex: 1;
}
<script src="https://code.jquery.com/jquery-3.1.0.js"></script>
<div class="table">
<div class="tr">
<div class="td">1</div>
<div class="td">22222222</div>
<div class="td">33</div>
<div class="td">4</div>
<div class="td">5555</div>
<div class="td">6</div>
<div class="td">7777777777</div>
<div class="td">88</div>
<div class="td">9</div>
<div class="td">100000</div>
</div>
<div class="tr">
<div class="td">11111111</div>
<div class="td">22</div>
<div class="td">3333333</div>
<div class="td">444</div>
<div class="td">555</div>
<div class="td">6</div>
<div class="td">77</div>
<div class="td">88</div>
<div class="td">9</div>
<div class="td">1000</div>
</div>
<div class="tr">
<div class="td">11</div>
<div class="td">22222</div>
<div class="td">3333</div>
<div class="td">444444</div>
<div class="td">55</div>
<div class="td">6</div>
<div class="td">77777</div>
<div class="td">8</div>
<div class="td">9</div>
<div class="td">100000</div>
</div>
</div>
Сейчас вычисляется ширина первой колонки и ширина максимальная.
Вопрос: как вычислить минимальную ширину каждой ячейки (колонки) для каждой строки и задать ее (независимо от содержания)? Так чтобы колонки в каждой строке совпадали как в таблице.
!!! Без задания ширины в стилях для каждой колонки!
Т.е. в первой колонке, например, минимум "1" - ширина там 20px значит у всей колонки столько должно быть. Во второй например "22" и ширина 40px - значит у всей колонки 40px. Надеюсь понятно
Ответы (2 шт):
Автор решения: Михаил Камахин
→ Ссылка
Без jQuery
function calcLengthTd(table) {
const allTr = table.querySelectorAll('.tr');
let lastLength = 0;
for (tr of allTr) {
const lengthTd = tr.querySelectorAll('.td').length;
if (lastLength < lengthTd) {
lastLength = lengthTd;
}
}
return lastLength;
}
function calcMaxWidth(elems) {
let maxWidth = 0;
for (item of elems) {
if (item.offsetWidth > maxWidth) {
maxWidth = item.offsetWidth;
}
}
return maxWidth;
}
function addMinWidth(table, lengthTd, maxWidth) {
for (let i = 0; i < lengthTd; i++) {
const td_s_Column = table.querySelectorAll(`.tr .td:nth-of-type(${i + 1})`);
const maxWidth = calcMaxWidth(td_s_Column); // посчитать максимальную ширину для блоков в колонке
for (td of td_s_Column) {
td.style.minWidth = maxWidth + 'px';
}
}
}
const table = document.querySelector('.table');
const lengthTd = calcLengthTd(table); // количество колонок
addMinWidth(table, lengthTd);
* {
box-sizing: border-box;
}
.tr {
display: flex;
align-items: center;
}
.td {
padding: 2px 20px;
}
.table .td:nth-of-type(n) {
border-left: 1px solid black;
border-bottom: 1px solid black;
}
.table .tr:nth-of-type(1) .td {
border-top: 1px solid black;
}
.table .td:last-child {
border-right: 1px solid black;
}
<div class="table">
<div class="tr">
<div class="td">1</div>
<div class="td">22222222</div>
<div class="td">33</div>
<div class="td">4</div>
<div class="td">5555</div>
<div class="td">6</div>
<div class="td">7777777777</div>
<div class="td">88</div>
<div class="td">9</div>
<div class="td">100000</div>
</div>
<div class="tr">
<div class="td">11111111</div>
<div class="td">22</div>
<div class="td">3333333</div>
<div class="td">444</div>
<div class="td">555</div>
<div class="td">6</div>
<div class="td">77</div>
<div class="td">88</div>
<div class="td">9</div>
<div class="td">1000</div>
</div>
<div class="tr">
<div class="td">11</div>
<div class="td">22222</div>
<div class="td">3333</div>
<div class="td">444444</div>
<div class="td">55</div>
<div class="td">6</div>
<div class="td">77777</div>
<div class="td">8</div>
<div class="td">9</div>
<div class="td">100000</div>
</div>
</div>
Автор решения: UModeL
→ Ссылка
Извиняюсь, что много кода и минимум jQuery... Думаю, что Вы найдёте подходящий вариант:
let aWidth = [], aRulesInd = [];
/* Создание массива исходных размеров ячеек */
$('.tr').each(function(i) {
aWidth.push([]);
$(this).find('.td').each(function() {
aWidth[i].push($(this).outerWidth());
});
});
/* Исходные размеры */
function fWInitial() {
if (aRulesInd.length) {
aRulesInd.reverse().forEach(e => document.styleSheets[0].deleteRule(e)); aRulesInd.length = 0;
}
}
/* На основе первой строки */
function fWFirstCol() {
fWInitial();
aWidth[0].forEach((e, i) => {
aRulesInd[i] = document.styleSheets[0].insertRule(`.td:nth-child(${i + 1}) { min-width: ${e}px; max-width: ${e}px; }`, 0);
});
}
/* Одинаковый максимум */
function fWEqualMax() {
fWInitial();
aRulesInd.push(document.styleSheets[0].insertRule(`.td { min-width: ${Math.max(...aWidth.flat())}px; }`, 0));
}
/* Одинаковый минимум */
function fWEqualMin() {
fWInitial();
aRulesInd.push(document.styleSheets[0].insertRule(`.td { max-width: ${Math.min(...aWidth.flat())}px; }`, 0));
}
/* На основе максимума в колонке */
function fWMaxInCol() {
fWInitial();
aWidth[0].forEach((e, i) => {
aRulesInd[i] = document.styleSheets[0].insertRule(`.td:nth-child(${i + 1}) { min-width: ${Math.max(...aWidth.map(value => value[i]))}px; }`, 0);
});
}
/* На основе минимума в колонке */
function fWMinInCol() {
fWInitial();
aWidth[0].forEach((e, i) => {
aRulesInd[i] = document.styleSheets[0].insertRule(`.td:nth-child(${i + 1}) { max-width: ${Math.min(...aWidth.map(value => value[i]))}px; }`, 0);
});
}
* { box-sizing: border-box; }
.tr {
display: flex;
align-items: center;
justify-content: space-between;
}
.td {
border: 1px solid;
padding: 2px 20px;
-webkit-box-flex: 0;
-ms-flex-positive: 0;
flex-grow: 0;
-ms-flex-negative: 0;
flex-shrink: 0;
flex: 1;
}
.controls { display: flex; flex-flow: column wrap; justify-content: space-around; height: 50px; }
<script src="https://code.jquery.com/jquery-3.1.0.js"></script>
<div class="table">
<div class="tr">
<div class="td">1</div>
<div class="td">22222222</div>
<div class="td">33</div>
<div class="td">4</div>
<div class="td">5555</div>
<div class="td">6</div>
<div class="td">7777777777</div>
<div class="td">88</div>
<div class="td">9</div>
<div class="td">100000</div>
</div>
<div class="tr">
<div class="td">11111111</div>
<div class="td">22</div>
<div class="td">3333333</div>
<div class="td">444</div>
<div class="td">555</div>
<div class="td">6</div>
<div class="td">77</div>
<div class="td">88</div>
<div class="td">9</div>
<div class="td">1000</div>
</div>
<div class="tr">
<div class="td">11</div>
<div class="td">22222</div>
<div class="td">3333</div>
<div class="td">444444</div>
<div class="td">55</div>
<div class="td">6</div>
<div class="td">77777</div>
<div class="td">8</div>
<div class="td">9</div>
<div class="td">100000</div>
</div>
</div>
<div class="controls"><label><input onclick="fWInitial()" type="radio" name="variant" checked>Исходные размеры</label><label><input onclick="fWFirstCol()" type="radio" name="variant">На основе первой строки</label><label><input onclick="fWEqualMax()" type="radio" name="variant">Одинаковый максимум</label><label><input onclick="fWEqualMin()" type="radio" name="variant">Одинаковый минимум</label><label><input onclick="fWMaxInCol()" type="radio" name="variant">На основе максимума в колонке</label><label><input onclick="fWMinInCol()" type="radio" name="variant">На основе минимума в колонке</label></div>