くぜのメモ

メモのように色々なことを書いていく雑記ブログ

【はてなブログ】サイドバーのコンテンツをスクロールに合わせて追従させる方法【脱jQuery】

f:id:CXE:20220331105001p:plain

はてなブログにおいて、サイドバーに配置したコンテンツをスクロールに合わせて追従させる方法を、備忘録がてら書いていこうと思います。

紹介方法を用いて、本ブログのサイドバー最後尾に配置した広告をスクロールに合わせて追従するように設定しているので、使用感を見たい方は確認してみてください。

前提として

今回の記事は、はてなブログでのカスタマイズ方法を既に知っていることを前提に書いています。知らない方は、事前にはてなブログのヘルプページなどで確認をお願いします。

紹介する方法は、ブログで使用しているデザインテーマなど、ブログの設定によっては正常に動作しない可能性があります。本記事の内容は、はてなブログのデザインテーマ『Smooth』での動作を確認しています。

Google AdSenseを導入している場合、box2-innerのheightが、element.styleにimportantを使用して書き換えられています。そのため、CSSのみで値を変更することができず、JavaScriptの使用が必要になります。本記事では、Google AdSenseを導入しているかで別々のコードを紹介していますが、使用しているデザインテーマなどによってはGoogle AdSenseを導入していても影響を受けていない可能性もありますので、事前に確認いただくことをお勧めします。

コンテンツを追従させるコード

Google AdSenseを導入している場合、heightの値を上書きできない形で設定されるため、コードを分けています。Google AdSenseを導入している場合には【共通】と【Google AdSenseあり】を、導入していない場合は【共通】と【Google AdSenseなし】を参照してください。 

【共通】CSS

はてなブログを使用している場合は、デザインCSSに以下のコードを追記します。

以下のコードは最後尾のコンテンツを指定していますが、最後尾から2番目のコンテンツを指定したい場合には、.hatena-module:nth-last-child(2)などと指定すればOKです。

.hatena-module:last-of-type {
    position: sticky;
    top: 10px;
}
  処理説明

.hatena-module:last-of-typeで、サイドバーにある各コンテンツの中で最後尾のコンテンツを指定しています。

positionの値にstickyを指定した要素は、通常の位置に配置されますが、スクロール等でtop, right, bottom, leftに指定した位置に達したとき、その位置に名前の通り「粘着」するような形で配置されます。

今回でいえばtop: 10px;と指定しているため、コンテンツの上端が、ウインドウの上端から10pxの箇所に達したときにその場所で固定配置されます。

【Google AdSenseなし】CSS

Google AdSenseを導入していない場合はこちらのコードを利用してください。

はてなブログを使用している場合は、デザインCSSに以下のコードを追記します。

#box2-inner {
    height: 100%;
}

【Google AdSenseあり】JavaScript

Google AdSenseを導入している場合はこちらのコードを利用してください。

はてなブログを使用している場合は、フッタ等に以下のコードを<script>タグで囲んで追記します。

(window.onload = function() {
    const box2Inner = document.getElementById('box2-inner');
    box2Inner.style.height = '100%';
})();
  処理説明

position: stickyで指定した要素は、その親要素内でしか機能しません

しかし、親要素box2-innerの高さは、サイドバーの最前列コンテンツの上端から最後尾コンテンツの下端までとなっており、スクロールしても追従させる余白が無い状態です。

ですので、記事が十分に長く、コンテンツを追従させる余裕がある場合、box2-innerの高さをサイドバーbox2の高さと同じ高さに設定し、追従可能にさせます。

まず、DOM要素が読み込まれた後に本処理が実行されるよう、window.onloadを使用します。

次に、document.getElementById('main').offsetHeightで記事の高さ、document.getElementById('box2').offsetHeightでサイドバーの高さを取得します。

この記事の高さ、サイドバーの高さですが、基本的には同じ値になります。しかし、記事の文量が少なかった場合、サイドバーの高さが記事の高さを上回る場合があります。

この時は処理を回す必要がないので、if文を使って、以降は記事の高さとサイドバーの高さが一致する場合のみ処理させます。

あとは、box2-innerbox2の高さを代入するだけです。

この時、box2の高さを-100していますが、これはbox2paddingが設定されているためです。

そのまま高さを代入してしまうと、記事の高さよりサイドバーの高さがpadding値の2倍分長くなってしまいます。

対応しようかと思いましたが、1emが設定されていて計算が面倒なので適当に-100しています。

上手いやり方をご存じの方はコメントなどで教えていただけると幸いです。

まとめ

以上、『サイドバーのコンテンツを追従させる方法』でした!

本記事の内容ですが、コピペなどは自由にしていただいて大丈夫です。また、記事として投稿する場合は、本記事のリンクを貼っていただけると助かります。

以上、ここまで読んでいただき、ありがとうございました!

参考:はてなブログのサイドバーにスクロールに追従するコンテンツを置く - めも