<ul class="scroll-anim-17" id="js-scroll-anim-17">
<li><a class="scroll-anim-17__item" href="#">リンク1</a></li>
<li><a class="scroll-anim-17__item" href="#">リンク2</a></li>
<li><a class="scroll-anim-17__item" href="#">リンク3</a></li>
</ul>
<div style="height: 1000px; padding-top: 72px">
<p>スクロール方向が上の場合、メニュー表示</p>
</div>
ul.scroll-anim-17#js-scroll-anim-17
each item in items
li
a.scroll-anim-17__item(href=item.link) #{ item.text }
div(style='height: 1000px; padding-top: 72px')
p スクロール方向が上の場合、メニュー表示
{
"items": [
{
"link": "#",
"text": "リンク1"
},
{
"link": "#",
"text": "リンク2"
},
{
"link": "#",
"text": "リンク3"
}
]
}
$BLOCK_NAME: '.scroll-anim-17';
// 変数
$duration_default: 0.5s;
#{ $BLOCK_NAME } {
position: fixed;
top: 16px;
left: 16px;
font-size: 12px;
transition: $duration_default;
&.is-hide {
pointer-events: none;
opacity: 0;
transform: translateY(-20px);
}
}
'use strict';
export const scrollAnim17 = () => {
const anim = new Anim17('#js-scroll-anim-17');
anim.init();
}
class Anim17 {
el: HTMLElement;
hidePos: Number;
scrollPos: Number;
hideClass: string;
ticking: Boolean;
constructor(elSelector: string) {
this.el = document.querySelector(elSelector);
this.hidePos = 72;
this.scrollPos = 0;
this.hideClass = 'is-hide';
this.ticking = false;
}
/**
* 初期化
*/
init(): void {
if (!this.el) return;
this.scrollHandler();
}
/**
* 要素の表示・非表示
*/
toggleEl() {
const currentPos = window.scrollY;
if (currentPos < this.hidePos) {
// 表示領域内の場合
this.el.classList.remove(this.hideClass);
} else if (currentPos < this.scrollPos) {
// 非表示領域内でスクロール方向が上の場合
this.el.classList.remove(this.hideClass);
} else {
// 非表示領域内でスクロール方向が下の場合
this.el.classList.add(this.hideClass);
}
// スクロール量を更新
this.scrollPos = currentPos;
}
/**
* スクロール連動のイベント設定
*/
scrollHandler(): void {
window.addEventListener('scroll', () => {
if (!this.ticking) {
requestAnimationFrame(() => {
this.ticking = false;
this.toggleEl();
});
this.ticking = true;
}
}, { passive: true });
}
}