Как с помощью jquery назначить класс последнему блоку в строке и всем блокам последней строки

327
12 августа 2017, 03:11

Есть следующая конструкция:

.mb { 
display: table; 
} 
 
.bl { 
width:100px; 
float:left; 
border-bottom: 1px solid #d5d5d5; 
border-right: 1px solid #d5d5d5; 
text-align:center; 
padding: 10px 0px; 
box-sizing: border-box; 
}
<div class="mb"> 
<div class="bl"> 
<a href="#" title="#">Ссылка </a> 
</div> 
<div class="bl"> 
<a href="#" title="#">Ссылка </a> 
</div> 
<div class="bl"> 
<a href="#" title="#">Ссылка </a> 
</div> 
<div class="bl"> 
<a href="#" title="#">Ссылка </a> 
</div> 
<div class="bl"> 
<a href="#" title="#">Ссылка </a> 
</div> 
<div class="bl"> 
<a href="#" title="#">Ссылка </a> 
</div> 
<div class="bl"> 
<a href="#" title="#">Ссылка </a> 
</div> 
<div class="bl"> 
<a href="#" title="#">Ссылка </a> 
</div> 
<div class="bl"> 
<a href="#" title="#">Ссылка </a> 
</div> 
</div>

В зависимости от ширины экрана, последний блок в строке будет меняться, также как и количество блоков в последней строке. Требуется вычислить последний блок в строке и добавить ему дополнительный класс "lastblock", а также вычислить все блоки в последней строке и тоже добавить им дополнительный класс "lastrow".

Подскажите, как это реализовать с помощью jquery если это вообще возможно?

Answer 1

Возможно есть вариант изящнее, но пока могу предложить такой.

Суть решения заключается в следующем. Очевидно, что последний элемент в списке будет находится в последней строке. Значит элементы, у которых точно такой же offset.top, как и у последнего элемента, также будут находится в последней строке.

Начнем проверять элементы с конца списка. И первый элемент, у которого offset.top отличается от offset.top последнего элемента в списке, будет последним элементом в предпоследней строке, а его offset.left будет такой же как у всех последних элементов в строках.

Полный код примера

var $list = $('.mb .bl'); 
 
$(window).resize(function() { 
 
  var top = $list.last().offset().top; // верхняя координата элементов последнего ряда 
  var left; // левая граница последнего элемента в ряду (пока неизвестна) 
 
  // начинаем проверять элементы последней строки с конца списка 
  for (var i = $list.length - 1; i >= 0; --i) { 
    var $current = $list.eq(i); 
    $current.removeClass('lastrow lastblock') 
 
    // проверяем верхнюю координату, если равна top,  
    // значит текущий элемент из последнего ряда 
    if ($current.offset().top === top) { 
      $current.addClass('lastrow'); 
      continue; 
    } 
 
    // первый элемент, у которого верхняя координата не равна top 
    // является последним элементом в предпоследней строке 
    $current.addClass('lastblock'); 
    left = $current.offset().left; 
    break; 
  } 
 
  // продолжаем проверять элементы,  
  // только теперь ищем последние элементы в строке 
  for (i -= 1; i >= 0; --i) { 
    var $current = $list.eq(i); 
    $current.removeClass('lastrow lastblock') 
 
    if ($current.offset().left === left) { 
      $current.addClass('lastblock') 
    } 
  } 
}); 
 
$(window).trigger('resize')
.mb { 
  display: table; 
} 
 
.bl { 
  width: 100px; 
  float: left; 
  border-bottom: 1px solid #d5d5d5; 
  border-right: 1px solid #d5d5d5; 
  text-align: center; 
  padding: 10px 0px; 
  box-sizing: border-box; 
} 
 
.lastrow a { 
  color: red 
} 
 
.lastblock a { 
  color: green 
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> 
 
<div class="mb"> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
</div>

Не гарантируется, что это решение будет работать, если размеры блоков будут различны.

Answer 2

Можно узнавать ширину блока и контейнера и просто считать количество ячеек в ряду. При этом не производить манипуляций, если не изменилось количество.

var itemsInRow = 0; 
 
$(window).resize(function() { 
  var blw = $('.mb .bl').outerWidth(); 
  var mbw = $('.mb').outerWidth(); 
  if (itemsInRow !== Math.floor(mbw / blw)) { 
    itemsInRow = Math.floor(mbw / blw); 
    $('.mb .bl.lastblock').removeClass('lastblock'); 
    $('.mb .bl.lastrow').removeClass('lastrow'); 
    $('.mb .bl:nth-child('+itemsInRow+'n)').addClass('lastblock'); 
    $('.mb .bl.lastblock').last().nextAll().addClass('lastrow'); 
    if (!$('.lastrow').length) { 
      $('.mb .bl:gt('+($('.mb .bl').length - itemsInRow-1)+')').addClass('lastrow'); 
    } 
  } 
}); 
 
$(window).trigger('resize');
.mb { 
  display: table; 
} 
 
.bl { 
  width: 100px; 
  float: left; 
  border-bottom: 1px solid #d5d5d5; 
  border-right: 1px solid #d5d5d5; 
  text-align: center; 
  padding: 10px 0px; 
  box-sizing: border-box; 
} 
 
.lastblock a { 
  color: green 
} 
 
.lastrow a { 
  color: red 
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> 
 
<div class="mb"> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
  <div class="bl"> 
    <a href="#" title="#">Ссылка </a> 
  </div> 
</div>

READ ALSO
Вращение блока при движении мышкой

Вращение блока при движении мышкой

Нужна анимация как на сайте https://openaicom/ Карточка сверху в правом блоке и ряд внизу

531
Не работают стили с подгружаемых файлов

Не работают стили с подгружаемых файлов

Стили на сайте работают если добавлять с внешнего источника, если со своих файлов нетСайт на CakePHP

187
Как добавить header в запросы? Java Selenium CromeDriver

Как добавить header в запросы? Java Selenium CromeDriver

Как добавить header в запросы в ChromeDriver? Мне нужно пройти http basic autentication при коннекте через проксиПодсказали что можно добавить в хидеры данные...

277
Как использовать полиморфизм в Spring?

Как использовать полиморфизм в Spring?

Есть несколько вариантов реализации DAO интерфейсаОдин из компонентов может принимать в качестве параметра в конструктор этот интерфейс

362