WordPressの記事にプラグインなしで目次を作る方法
WordPressの記事ページに、プラグインなしで目次を作成する方法の備忘録です。
目次を表示するjQueryの作成
まずはじめに、記事内の見出し<h2>、<h3>を取得して、目次として一覧で自動表示する「toc.js」を作成します。
jQuery(function ($) {
var idcount = 1;
var toc = '<ol>';
var level = 0;
jQuery("article h2,article h3", this).each(function () {
this.id = "toc-id" + idcount;
idcount++;
if (this.nodeName.toLowerCase() == "h2") {
if (level > 0) {
toc += '</ol></li>';
level = 0;
}
} else if (this.nodeName.toLowerCase() == "h3") {
if (level == 0) {
toc += '<li><ol>';
level = 1;
}
}
toc += '<li><a href="#' + this.id + '">' + jQuery(this).html() + "</a></li>\n";
});
toc += '</ol>';
if (jQuery("article h2")[0]) {
jQuery("#toc").html('<div class="toc-title">目次</div>' + toc);
}
jQuery('a[href^="#"]').click(function(){
var speed = 400,
href= $(this).attr("href"),
target = $(href == "#" || href == "" ? 'html' : href),
position = target.offset().top;
$('body,html').animate({scrollTop:position}, speed, 'swing');
return false;
});
});
見出し<h2>と<h3>を取得して、level
に合わせた階層になるようにリストのタグを制御しています。idcount
で見出しのアンカーリンクとなるidの数字を管理しています。
最後の「click(function()」では、href
に「#」のついたアンカーリンクがクリックされた際に、スクロールするように設定しています。
作成した「toc.js」は、テーマフォルダの中に保存します。テーマファイルに直接記述する場合は、footer.phpの</body>の直前に記入します。
ちなみに「toc」は「table of contents(目次の英語表記)」の略です。
jQueryを読み込む
作成した「toc.js」を読み込むためのスクリプトをfunctions.phpに記述します。テーマファイルに直接記述する場合は不要です。
function toc_enqueue_scripts(){
wp_enqueue_script( 'toc', get_template_directory_uri() .'/js/toc.js', array('jquery') );
}
add_action( 'wp_enqueue_scripts' , 'toc_enqueue_scripts' );
function.phpを編集に誤りがあると、WordPress自体が動かなくなります。必ずバックアップをとってから慎重に作業します。
記事に目次を設置する
作成した目次は、「<div id=”toc”></div>」と記述するだけで読み込むことができます。
「<div id=”toc”></div>」を記事ページごとに記入した場合、目次を付けないことも、記事内の任意の箇所に読み込むことが可能ですが、毎度記入するのは少し手間です。
single.php内に記入して自動で読み込むこともできます。その場合は、記事内に目次を入れることはできません。
今回は、作成した目次を記事ページ内の一つ目の段落の下に表示出来るようにしてみました。functions.phpに設定を追記します。
function toc_in($the_content) {
if (is_single()) {
$toc = "<div id=\"toc\"></div>";
$inpoint = '@<p>(.*?)</p>@si';
if ( preg_match( $inpoint, $the_content, $inpoints )) {
$the_content = preg_replace($inpoint, $inpoints[0].$toc, $the_content, 1);
}
}
return $the_content;
}
add_filter('the_content','toc_in');
preg_match
で記事内の<p>タグの部分を取得し、preg_replace
で一番初めの<p>タグの後ろに目次を表示する<div id=’toc’></div>を挿入しました。
目次は、下記のようなリストの形で一覧表示されます。<h3>の見出しは<h2>の入れ子となって表示されます。
<ol>
<li><a href="#toc-id1">見出し1</a></li>
<li><a href="#toc-id2">見出し2</a></li>
<li>
<ol>
<li><a href="#toc-id3">見出し2-1</a></li>
<li><a href="#toc-id4">見出し2-2</a></li>
</ol>
</li>
</ol>
cssでデザインを設定して目次の完成です。
目次をクリックするとアンカーリンクによって、該当箇所の見出しにスクロールします。
目次があることで、記事内の情報の詳細が分かりやすくなり、目的の箇所へのページ遷移も簡単になりました。
WordPressには、目次を簡単に作ることのできるプラグインもたくさんありますが、動作が重くなってしまったり、コードやデザインがサイトにマッチしない場合は、自作してみるのも良いかもしれません。