領域にピタッとスクロールする「scroll-snap-type」#2 Javascript設定

2020年11月3日

テクノロジー

eyecatch お腹が冷えるのが嫌なので、夏場以外は必ずシャツをインする、下駄です。 前回に引き続いて、ライブラリに頼らずに自力で構築できるカルーセル機能を追求してみたいと思います。 今回のテーマは、カルーセルの下に付いている、現在位置を表す丸ポッチです。 カルーセルの内容をピタッと固定できるようにsnap設定をcssで行ったら、それに連動して今どの位置にいるのかというのを表示(切り替え)する必要があります。 cssだけではどうしてもうまく機能しないので、これをjavascriptでも簡単に実装してみたいと思います。

Navigator機能

ナビゲータと言われる丸ポッチは、Amazonなどでも使われているカルーセルの基本機能です。 今、自分がどこの位置にいるのか、全体的にどのくらいの数のスライドが存在するのかが分かるので、非常に重要な要素です。 実装方法としては、スライドを切り替えた時に、scrollイベントが発生するので、そのイベント発生時に基準(画面の左端)に一番近い座標のスライドを選択して、ナビゲータに反映するという方式です。

ソース

<div class="slider"> <div class="content-1"></div> <div class="content-2"></div> <div class="content-3"></div> </div> <div class="navigator"> <div class="navi-1"></div> <div class="navi-2"></div> <div class="navi-3"></div> </div>   .content-1{background-color:red;} .content-2{background-color:blue;} .content-3{background-color:green;} .slider{ width:300px; } .slider > *{ display:inline-block; width:100%; height:200px; } /* Snap */ .slider{ white-space:nowrap; overflow:auto; scroll-snap-type: x mandatory; } .slider > *{ scroll-snap-align: start; } /* Scrollbar-hidden */ .slider{ -ms-overflow-style: none; scrollbar-width: none; } .slider::-webkit-scrollbar{ display:none; } /* Navigator */ .navigator{ width:300px; height:16px; display:flex; justify-content: center; } .navigator > *{ width:10px; height:10px; border:1px solid black; background-color:white; border-radius:50%; margin :2px; } .navigator > *[data-active="1"]{ background-color:black; }   window.onload = function(){ var navigator = document.querySelector(".slider"); navigator.onscroll = setNavigator; setNavigator(); }; function setNavigator(e){ var active = { num:0, distance:0 }; if(e && e.target){ var target = e.target; var contents = target.querySelectorAll(":scope > *"); var abs = 0; for(var i=0; i<contents.length; i++){ abs = Math.abs(contents[i].offsetLeft - target.scrollLeft); if(i === 0 || abs < active.distance){ active = { num : i, distance : abs }; } } } var navigators = document.querySelectorAll(".navigator > *"); if(typeof navigators[active.num] === "undefined"){return;} for(var i=0; i<navigators.length; i++){ if(active.num === i){ navigators[i].setAttribute("data-active","1"); } else{ navigators[i].setAttribute("data-active","0"); } } }  

プレビュー

See the Pen own-slider-js by YugetaKoji (@geta1972) on CodePen.

解説

前回のHTML+CSSにナビゲータ要素を追加しました。 slider部分のscrollイベントが発生したら、内部の座標を確認して、ナビゲータのスクロール値と、それぞれのスライドのleft座標の差分が一番小さいものをピックアップして、data-activeに"1"をセットしています。 スライド数が多くなると、処理が重くなるので、スクロールが終わったらというタイミングで行っても良いんですが、リアルタイムに計算した方が、触りごこちが一番しっくり来ます。

まだ足りてない機能あるよ

今回搭載したナビゲーターですが、本来はボタンの役割もするのが一般的で、クリックした箇所に自動的にスライドを移動するという機能が入っていません。 そもそも、このナビゲータも、htmlで地味にセットをするのではなく、自動的にスライド数に応じて自動的にセットできるようにしてもいいかもですね。 でも、簡易なカルーセル機能は、今回の分で十分な場合もあるので、バージョン1.0として、公開したいと思います。

このブログを検索

ごあいさつ

このWebサイトは、独自思考で我が道を行くユゲタの少し尖った思考のTechブログです。 毎日興味がどんどん切り替わるので、テーマはマルチになっています。 もしかしたらアイデアに困っている人の助けになるかもしれません。