Hobby Graphics

WordPressのthe_content()出力内容に表示を割り込ませたい

要約WordPressのテンプレートタグthe_content()で出力されるHTMLのまとまりの中に、the_title()など他のテンプレートタグで出力される内容を割り込ませるレイアウトをCSS Gridで手軽に実装するという内容です。

カテゴリーによるページの振り分けはできたけど…

このサイトでは投稿記事のタイトル、サムネイルと本文をそれぞれテンプレートタグ the_title()、the_post_thubnail()、the_content() で投稿用のファイル single.phpに読み込んでいます。
一般的なブログ記事を出力するページではタイトルを優先していますが、以前の仕事を表示するページでは写真を優先して見出しとサムネイルの配置を入れ替えました。これを投稿ページ全般用のテンプレートファイルsingle.phpと、worksカテゴリー用のファイルsingle-works.php に振り分けています。

シリーズ写真がタイトルで分割されてしまう

しかしworksカテゴリーの中でも商品の写真が1点だけの場合と複数の商品をまとめて掲載したい場合とでレイアウトを調整する必要が出てきました。シリーズとして紹介したい商品の写真を投稿ページで追加しても、サムネイルと追加した写真との間にタイトルの見出し(商品名)が入ってしまい、一体化して見えないためです。

まずテンプレートファイルを追加することを考えましたが、そこでこまったのは変更を加えたいのがWordPressのthe_content()でまとめて出力される部分だということです。the_content()はWordPressのブロックエディターで編集した内容をHTMLとしてまとめて出力します。その内容を取り出して構成しなおすのは今の私のスキルではハードルが高すぎます。そこで、CSS Gridで指定すれば良いのではないかと考えて、フローレイアウトからグリッドレイアウトに変更することにしました。

single-works.php

<article id="post-<?php the_ID(); ?>" <?php post_class(); ?>>
    <?php if (has_post_thumbnail()): ?>
        <figure class="works-image">
            <?php the_post_thumbnail('large') ?>
        </figure>
    <?php endif; ?>
    <h2 class="post-heading"><?php the_title(); ?></h2>
    <?php the_content(); ?>
</article>

こちらはPHPファイルの抜粋。下から2行目がthe_content()の出力です。ブロックエディターで作成した記事部分をまとめて出力してくれますが、それゆえ初心者にとってはブラックボックスのような、触ってはいけない部分のような…

index.html

<link rel="stylesheet" href="styles.css" />
<body>
    <main>
        <article id="post-518" class="post-518 post type-post status-publish format-standard has-post-thumbnail hentry category-works tag-sales-promotion">
            <figure class="works-image">
                <img src="blog-002-image_05.jpg" class="attachment-large size-large wp-post-image" alt="" />
            </figure>
            <h2 class="post-heading">WordPressのthe_content()出力内容に表示を割り込ませる</h2>
            <p>出版社・販売メーカー名など</p>
            <div class="wp-block-group double-columns">
                <div class="wp-block-group__inner-container is-layout-constrained wp-block-group-is-layout-constrained">
                    <figure class="wp-block-image size-full">
                        <img src="blog-002-image_06.jpg" alt="" />
                    </figure>
                    <figure class="wp-block-image size-full">
                        <img src="blog-002-image_07.jpg" alt="" />
                    </figure>
                </div>
            </div>
            <p>簡単な商品説明が入る本文ブロック</p>
            <p>発売年 : 0000年</p>
        </article>
    </main>
</body>

でも出力されるHTMLは、こうしてみるといつも見慣れたHTMLと変わりありません。
the_content()で出力されるのは<p>出版社・販売メーカー名など</p>から<p>発売年 : 0000年</p>の部分。今回まとめて表示したいのは<figure class=”works-image”>と<div class=”wp-block-group double-columns”>です。その間に<h2 class=”post-heading”>と<p>が割り込んでいます。

※実際に出力されるHTMLにはWordPressが追加する属性などが付与されていますが、説明に不要な部分はaltやwidth属性も含めて削除しました。

styles.css(フローレイアウト)

@charset "UTF-8";
* {
    margin: 0;
    padding: 0;
    box-sizing: border-box;
}
body {
    padding-block: 2em;
    display: grid;
    grid-template-columns: 1fr 640px 1fr;
}
h2 {
    line-height: 1.25;
    margin-block: 1em 0;
}
main {
    grid-column: 2;
}
p {
    margin-block: 1em;
}
h2 + p {
    margin-top: 0.25em;
}
.double-columns .wp-block-group__inner-container {
    display: flex;
    gap: 0.5em;
    & figure {
        width: calc((100% - 0.5em) / 2);
        img {
            max-width: 100%;
            height: auto;
        }
    }
}
.works-image {
    width: 75%;
    margin-inline: auto;
    img {
        max-width: 100%;
        height: auto;
    }
}

先のHTMLに適用したCSSとその結果です。
the_conntent()出力部分は、画像を横並びにするためにflexを使っていますが、基本的にフローレイアウトのままなので、HTML構造に従ってレイアウトされています。

CSS Gridでレイアウトを変更する

途中までフローレイアウトで組んでいた場合、グリッドに変更するとマージンの扱いが変わってしまい、調整に苦労する可能性があります。文章の流れで最後にスタイルを追加していますが、このような変更が予期されていれば最初からグリッドにするのが良いと思います。
下記はグリッドの指定を追加したCSSとその結果です。

styles.css(グリッドの追加指定)

article {
    display: grid;
    grid-template-columns: auto;
    grid-template-rows: repeat(3, auto);
    grid-auto-flow: row;
    align-items: start;
    .post-heading {
        grid-row: 2;
    }
    .works-image {
        grid-row: 1;
    }
    &:has(.wp-block-group) {
        .post-heading {
            grid-row: 3;
        }
        .wp-block-group {
            margin-top: 0.5em;
            grid-row: 2;
        }
    }
}

article.category-worksにdisplay: grid; を適用し、子要素が増えたときは縦方向に増えるようにgrid-auto-flow: rows; を指定しました。また、.wp-block-groupが無い場合をデフォルトとして、サムネイルの.works-imageにはgrid-row: 1; を、見出し.post-headingにgrind-row: 2; を指定しています。
また .wp-block-groupがある場合の設定として、article.category-works:has(.wp-block-group)の.wp-block-groupにgrid-row: 2; を指定し、.post-headingにはgrid-row: 3; を上書きしました。
グリッドへの配置の明示は以上としました。見出し以下にはクラスがついていない要素もありますが、グリッドには暗示的に配置されるようになっています。

手軽にレイアウト変更できました

CSS Gridを使い始めた時は随分面倒なシステム、と思いましたが、慣れてくると使い勝手も良く便利なツールだと思うようになりました。PHPのテンプレートの中身など、少し手を出しにくいものにも使えることがわかったので、なおさら使い所が増える気がします。

blog 一覧へ