Как зафиксировать блок в сайдбаре - Просто, жизненный опыт
838

Немного обо всем, просто, жизненный опыт.
Разбираю по полочкам, что могу…

Один из вариантов фиксации нижнего блока в сайдбаре на сайте (если хочется чтобы этот блок не потерялся с экрана)

Обновлено: 24.07.2018 года.

Здравствуйте, дорогие читатели блога MaratKX.ru. Зачем делать фиксированный блок на сайте? Причин тому множество, перечислять их здесь смысла никакого нет. Например, когда контент сайта, точнее основная часть страницы гораздо длиннее боковой панели (сайдбара), то после прокрутки место под сайдбаром остается пустым, что может создавать некоторый дискомфорт при просмотре. Плюсом, этот блок может быть рекламным, отправляющим на самую нужную страницу на сайте.

Как сделать фиксированный блок на сайте

Как сделать фиксированный блок?

Собственно, фиксация блока не вызывает никаких сложностей. Просто при прокрутке страницы до определенного уровня, с помощью JavaScript необходимо установить параметры блока, которые зафиксируют данный блок на определенном месте страницы.

На просторах интернета полно вариантов решения данной задачи. Но большинство из них подходят для сайтов с фиксированной шириной.

Фиксированный блок на сайте с фиксированной шириной шаблона.

Когда шаблон сайта имеет фиксированную ширину, нам заранее известна ширина фиксируемого блока. Остается только поймать момент, когда блок будет прокручен на необходимое количество пикселей, после чего зафиксировать блок на необходимой высоте от верхнего края окна браузера.

Фиксированный блок на сайте с "резиновой" разметкой.

В данном случае задача фиксации блока становится несколько сложнее. Нам необходимо вычислить верхнюю границу, а также левую и правую границы блока, так как при изменении ширины окна браузера ширина сайдбара тоже меняется.

Разная ширина блока на различных экранах компьютеров

Определяемся с размерами фиксированного блока.

Для получения границ нашего блока, будем использовать JS. Так как, при запрете выполнения скриптов на сайте, с нашим блоком ничего не должно происходить, то есть, другими словами, он должен себя вести также, как и остальные блоки, стили этого блока ничем не будут отличаться от остальных блоков в сайдбаре.

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

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

Сделаем для примера следующую разметку:

 <div id="fixblock_razm"></div>  <div id="fixblock">  Содержимое блока  </div> 

Первый блок <div id="fixblock_razm"></div> мы будем использовать для определения необходимых нам размеров. Второй блок будем фиксировать, согласно полученных размеров.

Определяем верхние левую и правую границы блока.

Для определения координат границ блока используем метод elem.getBoundingClientRect(). Метод elem.getBoundingClientRect() возвращает координаты элемента, под которыми понимаются размеры "воображаемого прямоугольника", который охватывает весь элемент.

Разная ширина блока на различных экранах компьютеров

Координаты возвращаются в виде объекта со свойствами:

  • top – Y-координата верхней границы элемента,
  • left – X-координата левой границы,
  • right – X-координата правой границы,
  • bottom – Y-координата нижней границы.

Необходимо учесть, что координаты right/bottom отличаются от CSS-свойств.

Если взглянуть на позиционирование элемента при помощи CSS-свойства position, то там тоже указываются left, right, top, bottom.

Однако, в каскадных таблицах стилей (CSS) свойство right задаёт расстояние от правой границы, а bottom – от нижней.

JavaScript выдает нам несколько иные данные. Если взглянуть на иллюстрацию выше, то Вы увидите, что в JavaScript координаты работают по-другому. Все координаты отсчитываются слева/сверху, в том числе и эти.

Мы сделаем проще. Мы будем использовать в качестве параметра ширину блока. Все данные для вычисления ширины у нас уже есть.

Итак, что мы имеем, и что должны получить?

Что мы имеем для фиксации блока?

На текущий момент, благодаря методу elem.getBoundingClientRect() мы имеем координаты размещения нашего блока. Также нам известно, что пользователь может прокрутить страницу или, например, изменить ширину окна браузера.

Итак, исходя из высоты шапки сайта, которая останется видимой на экране (при любой ширине экрана, не забываем про мобильники), мы должны установить координату, после которой наш блок должен фиксироваться, другими словами это количество пикселей, которое останется до верхнего края окна браузера до нашего блока перед его фиксацией.

Данное значение можно подобрать опытным путем. А мы тем временем, начнем потихоньку. Начнем писать скрипт.

 <script>  var graniza_bl = 50; /*граница для начала фиксации блока*/  </script> 

Да, совсем забыл. Нам ведь, необходимо еще указать размер высоты окна браузера, при котором данная функция выполняться не будет. В противном случае (если к примеру, z-index нашего блока больше, чем этот же параметр у футера) мы можем увидеть некрасивую картину, когда наш блок налезает на футер, а если еще он длинный (речь конечно, о нашем фиксируемом блоке), то его и не видно на половину…

Необходимо установить высоту окна браузера, при которой будет выполняться фиксация блока

Поэтому добавим еще одну переменную, которая будет указывать, при какой минимальной высоте окна браузера должен исполняться наш скрипт:

 <script>  var graniza_bl = 50; /*граница для начала фиксации блока*/  var min_height_screen = 550; /*минимальная высота окна браузера для начала фиксации блока*/   var fixblock_razm, razm_wrap, fixblock_css, newcss; /*переменные для координат*/  var bl_top, result, new_css; /*переменные для работы скрипта*/  </script> 

Что должны получить на выходе.

Добавил еще переменных сразу. Теперь нам нужна функция, которая будет вычислять необходимые нам координаты:

 /*функция для вычисления размеров для фиксации блока*/ 
function razmer(){
fixblock_razm = document.getElementById("fixblock_razm"); /*собственно элемент, по которому определяем координаты*/
razm_wrap = fixblock_razm.getBoundingClientRect(); /*массив с координатами размеров исходного элемента*/
/*вычисление координат фиксируемого блока, а также оформление этих координат в качестве стиля блока*/
fixblock_css = 'left:' + razm_wrap.left + 'px; width:' + (razm_wrap.right - razm_wrap.left) + 'px; top:' + graniza_bl + 'px; position:fixed; padding-top: 2%;';
return {
bl_top: razm_wrap.top,
newcss: fixblock_css
}; };

Теперь у нас есть все данные для фиксации блока.

Правила и ограничения при фиксации блока.

Теперь нам нужна функция, которая как раз и будет производить фиксацию блока (менять стили нашего блока). Но мы помним про ограничения, о которых говорилось выше. Да, кстати, при проверке скрипта на различных браузерах, сейчас не помню почему, но я пришел к выводу, что на телефонах не надо использовать данную функцию. Поэтому введем еще одно ограничение, на ширину экрана.

 /*Функция замены стилей*/ 
function postavit(new_css,tops){
/*Если ширина окна шире чем 768px, а также высота экрана больше, указанной нами*/
if (document.body.clientWidth > 768 && screen.height > min_height_screen && innerHeight > min_height_screen){
/*если расстояние до блока меньше, чем указана нами*/
if (tops < graniza_bl){
fixblock.setAttribute( 'style', new_css ); /*установить наши параметры стиля*/
}else{
fixblock.removeAttribute( 'style', new_css ); /*удалить наши параметры стиля*/
}
}else{
fixblock.removeAttribute( 'style', new_css ); /*удалить наши параметры стиля*/
};
};

Ну вот, теперь у нас уже почти все есть: мы можем получить координаты, а также теперь, мы можем зафиксировать блок при определенных условиях. Осталось только указать ситуации, когда необходимо выполнить фиксацию блока.

Тут все будет зависеть от действий посетителя сайта. Посетитель у нас может изменить размер окна браузера, а также прокрутить страницу. Таким образом, получается, что у нас есть два события, на которые должен реагировать наш скрипт, это скроллинг window.onscroll и изменение размеров window.onresize. Давайте и попробуем обработать эти два события:

 window.onscroll = function(){ 
result = razmer();
postavit(result.newcss,result.bl_top);
};

window.onresize = function(){
result = razmer();
postavit(result.newcss,result.bl_top);
};

Код скрипта. Собранный вариант.

Осталось, для полноты картины, только собрать все наши части скрипта, который зафиксирует, указанный блок внизу сайдбара, в одну кучу.

 <script> 
var graniza_bl = 50; /*граница для начала фиксации блока*/
var min_height_screen = 550; /*минимальная высота окна браузера для начала фиксации блока*/

var fixblock_razm, razm_wrap, fixblock_css, newcss; /*переменные для координат*/
var bl_top, result, new_css; /*переменные для работы скрипта*/

/*функция для вычисления размеров для фиксации блока*/
function razmer(){
fixblock_razm = document.getElementById("fixblock_razm"); /*собственно элемент, по которому определяем координаты*/
razm_wrap = fixblock_razm.getBoundingClientRect(); /*массив с координатами размеров исходного элемента*/
/*вычисление координат фиксируемого блока, а также оформление этих координат в качестве стиля блока*/
fixblock_css = 'left:' + razm_wrap.left + 'px; width:' + (razm_wrap.right - razm_wrap.left) + 'px; top:' + graniza_bl + 'px; position:fixed; padding-top: 2%;';
return {
bl_top: razm_wrap.top,
newcss: fixblock_css
};
};

/*Функция замены стилей*/
function postavit(new_css,tops){
/*Если ширина окна шире чем 768px, а также высота экрана больше, указанной нами*/
if (document.body.clientWidth > 768 && screen.height > min_height_screen && innerHeight > min_height_screen){
/*если расстояние до блока меньше, чем указана нами*/
if (tops < graniza_bl){
fixblock.setAttribute( 'style', new_css ); /*установить наши параметры стиля*/
}else{
fixblock.removeAttribute( 'style', new_css ); /*удалить наши параметры стиля*/
}
}else{
fixblock.removeAttribute( 'style', new_css ); /*удалить наши параметры стиля*/
};
};

window.onscroll = function(){
result = razmer();
postavit(result.newcss,result.bl_top);
};

window.onresize = function(){
result = razmer();
postavit(result.newcss,result.bl_top);
};
</script>

Вот такой скрипт у нас получился (оригинальный курс по JS и jQuery). Этот скрипт был написан именно для этого сайта, так что, когда увидите фиксированный блок, знайте, он фиксируется, благодаря данному скрипту.

Удачи вам! До скорых встреч на страницах сайта MaratKx.ru