[JS] jQuery を使わずにスクロールでふわっと出現し、クリックするとページトップへスムーススクロールで戻るボタンを作る
スクロールするとふわっとフェードインしてくるページトップへ戻るボタンは今や定番ですね。前回に引き続き jQuery などのライブラリーを使わずに、JavaScript と CSS のみでページトップへ戻るボタンを作ってみました。今回のアニメーションは CSS3 は使わず JavaScript のみで実装しました。
IE7+、Andoroid 3.2+、その他のブラウザでも動作確認できました。
サンプルデモ
スクロールでふわっと出現しクリックするとページトップへスムーススクロールで戻るボタンのサンプルデモです。
ページトップへ戻るボタンサンプルデモ|memocarilog-demo
HTML コード
HTML は通常のリンクボタンのように作り親要素に ID名 “pagetop”とつけ、HTML 内の適当な場所へおきます。
<div id="pagetop"> <a href="#">↑PageTop</a> </div>
CSS コード
親要素に position:fixed を指定して表示位置を設定します。filter と zoom の設定は IE の旧ブラウザ向けのものなので場合により削除して下さい。z-index で一番上の層にくるようにします。子の a 要素へはボタンの装飾の指定をしています。
#pagetop{
position: fixed;
right: 10%;
bottom: 10%;
opacity: 0;
-ms-filter: "alpha( opacity=0 )";
filter:alpha(opacity:0);
zoom:1;
z-index: 9999;
}
#pagetop a{
display: block;
padding: 20px;
background: #1EA6BB;
color:#fff;
text-decoration: none;
}
JavaScript コード
JavaScript のコードはまた長くなってしまったのですが、options でスクロールのスピードなどは変更できます。コードの説明はメモを兼ねてコード内にコメントで残しました。このコードをヘッド内もしくは外部のJSファイルへ記入すればOKのはずです。
options について
options のpageTopBtn で、トップへ戻るボタンのid名を変更できます。デフォルトは ‘pagetop’ としているので、ちがうID名を付けたい場合はここを変更して下さい。Class名には対応していませんのでご注意下さい。
showScroll でボタンが出現するスクロール位置を設定出来ます。デフォルトは200pxの位置です。
scrollSpeed でトップへ戻る時のスピードを変更できます。推奨値は 5〜20 くらいまでの間です。
fadeSpeed でボタンのフェードイン・アウトのスピードが変更できます。推奨値は 5 〜 30 くらいまでの間です。
<script>
//スピードなどの設定
var options = {
pageTopBtn : 'pagetop', // トップへ戻るボタンのID名(”名”のみで#はつけない)
showScroll : 200, // ボタンの出現するスクロール位置 PX単位
scrollSpeed : 10, //早い→5 普通→10 ゆっくり→20
fadeSpeed : 10 // 早い 5 〜 30 ゆっくり
};
window.onload = function(){
var btn = document.getElementById(options.pageTopBtn) ;
// ページトップへ戻るアニメーション
var scroll_timer;
function pageTop(x, y){
if (y >= 1) {
var scTop = Math.floor(y - (y / (options.scrollSpeed * 2)));
window.scrollTo(x, scTop);
scroll_timer = setTimeout(function(){pageTop(x, scTop)}, options.scrollSpeed);
// ↑ y の値が1以下になるまで 少しの数値分だけスクロールアップするのを
// scrollSpeed の設定時間ごとに繰り返す
} else {
clearTimeout(scroll_timer);
// ↑ y の値が1以下になったらタイマーを止めて数値を引くのをやめる
window.scrollTo(x, 0);
}
}
// フェイドインアニメーション設定
var fadeIn_timer;
function fadeInTimer(opaValue){
if (opaValue < 1){
opaValue = opaValue + 0.05;
btn.style.filter = "alpha(opacity:"+(opaValue*100)+")";
btn.style.opacity = opaValue;
fadeIn_timer = setTimeout(function(){fadeInTimer(opaValue);}, options.fadeSpeed);
// ↑opaValue が1になるまで透明度を 0.05 ずつ足して行くのを
// fadeSpeed に設定された時間毎に繰り返す
} else {
clearTimeout(fadeIn_timer);
// ↑opaValue が1になったら繰り返し処理を止める
btn.style.filter = "alpha(opacity:100)";
btn.style.opacity = 1;
}
}
// フェイドアウトアニメーション設定
var fadeOut_timer;
function fadeOutTimer(opaValue){
if ( opaValue >= 0.05){
opaValue = opaValue - 0.05;
btn.style.filter = "alpha(opacity:"+(opaValue*100)+")";
btn.style.opacity = opaValue;
fadeOut_timer = setTimeout(function(){ fadeOutTimer(opaValue); }, options.fadeSpeed);
// opaValue が1になるまで透明度を 0.05 ずつ引いて行くのを
// fadeSpeed に設定された時間毎に繰り返す
} else {
clearTimeout(fadeIn_timer);
// ↑ opaValue が0.05以下になったら繰り返し処理を止めて
// 完全な0にしておく(↓)
btn.style.filter = "alpha(opacity:0)";
btn.style.opacity = 0;
}
}
// スクロールイベント
btn.style.opacity = 0;
btn.style.filter = "alpha(opacity:0)";
window.onscroll = function(){
var winSc = document.body.scrollTop || document.documentElement.scrollTop;
if(winSc >= options.showScroll){
clearTimeout(fadeOut_timer);
var opaValue = parseFloat(btn.style.opacity);
fadeInTimer(opaValue);
} else {
clearTimeout(fadeIn_timer);
var opaValue = parseFloat(btn.style.opacity);
fadeOutTimer(opaValue);
}
}
// クリックイベント
btn.onclick = function(){
// 現在のスクロール位置を取得する
var x = document.body.scrollLeft || document.documentElement.scrollLeft;
var y = document.body.scrollTop || document.documentElement.scrollTop;
// スクロール位置を pageTop() 関数へ渡して呼び出す
pageTop(x, y);
return false;
}
}
</script>
jQuery でこの動きを実装したい場合は、むかし webdesignerwall さんのコードをメモした記事(スクロールでtopへ戻るボタンを表示するjQueryコード(スムーススクロール))があるので参考になるかもしれません…。
こんにちは。
こちらのスクロールボタンを使わせていただきました。とても丁寧な書き方で、すごくわかりやすくあっという間に出来ました。ありがとうございます。
ところで、IEでは表示できないのですが、しかたないのでしょうか。
お返事いただけると助かります。よろしくお願い致します。
イシカワ さま
ご参考いただきありがとうございます。
当方の環境では、IE でも動いています。コード自体も IE で動かないようなコードは使っていないつもりですが、必ず動くという保証もできかねますので、あくまでもご参考程度にご覧いただければ幸いです。
また、このコードでは jQuery を使用していませんが、IE での動作がどうしても不安定なようでしたら jQuery を使用したコードの方が安定的にご使用いただけるのではないかなと思います。よろしくお願いいたします。