結論
子テーマは、wp-content/themes/ の下に新しいフォルダを作り、次の2ファイルを置けば成立します。
style.css:ヘッダーにTheme NameとTemplate: 親テーマのフォルダ名を書くfunctions.php:親テーマのCSSなどを読み込むコードを書く
Template: は、親テーマのフォルダ名と完全に一致させます(公式ハンドブックの記載)。親の機能を壊さずに上書きできる点が最大の利点で、親テーマの更新でカスタマイズが消えません。
原因・仕組み
子テーマが有効なとき、WordPress は「テンプレート(親)」と「スタイルシート(子)」の2つを区別して持ちます。
get_template()/get_template_directory()/get_template_directory_uri()→ 親テーマget_stylesheet()/get_stylesheet_directory()/get_stylesheet_directory_uri()→ 有効なテーマ(子があれば子)
functions.php は、子→親の順で両方読み込まれます。コア(wp-settings.php)では、有効なテーマの一覧をループして各 functions.php を include しており、公式ハンドブックにも、子が親の直前に読み込まれると書かれています。親の関数を上書きしたいときは、親が if ( ! function_exists() ) で定義している場合に限り、子で先に定義できます。
手順(サンプルコード)
1. style.css
/*
Theme Name: My Child
Template: twentytwentyfive
Version: 1.0
*/
2. functions.php で親と子のCSSを読み込む
add_action( 'wp_enqueue_scripts', function () {
wp_enqueue_style( 'parent-style', get_template_directory_uri() . '/style.css', array(), '1.0' );
wp_enqueue_style( 'child-style', get_stylesheet_uri(), array( 'parent-style' ), '1.0' );
} );
親テーマが自分でCSSを読み込んでいる場合は、二重読み込みになることがあります。公式も、親のコードを見て判断するよう案内しています。
3. ファイルの上書き
子テーマに親と同じ名前のテンプレート(header.php など)を置くと、子の方が優先されます。パーツの読み込みには、子→親の順で探す get_template_part() や get_theme_file_path() を使います。
4. 親のフックを外す
add_action( 'after_setup_theme', function () {
remove_action( 'wp_head', 'parent_theme_some_output', 10 );
} );
優先度が合わないと外れないため、remove_action が効かないを参照してください。
動作確認(検証環境と結果)
WordPress 7.1.2(ja)、PHP 8.2.12 の CLI 環境で、有効テーマは twentytwentyfive のみ(実際の子テーマは作成していません)。
- 子テーマなしの状態:
get_template()とget_stylesheet()はどちらもtwentytwentyfive。 pre_option_stylesheetをmy-child、pre_option_templateをtwentytwentyfiveにして子テーマ状態を擬似的に再現した結果、get_template()=twentytwentyfive、get_stylesheet()=my-child、get_template_directory_uriは.../themes/twentytwentyfive、get_stylesheet_directory_uriは.../themes/my-child。- 上記の
wp_enqueue_styleを実行してwp_print_styles()した出力の順は、parent-style→child-style(子が後)。 wp-settings.php741〜747行目で、各テーマのfunctions.phpをincludeしていることを確認した。
実際のフォルダを使った子テーマの動作、is_child_theme() の結果は、この擬似環境では確認していません(未検証)。ログは testschild-theme-functions-php-how-to.md にあります。
子テーマの作り方と functions.phpの注意点
Template:の綴りやフォルダ名が違うと、管理画面で「親テーマが見つかりません」となります。- 親テーマのバージョンアップで構造が変わると、子のテンプレートが古いままになります。更新時に差分を確認します。
@importでのCSS読み込みは遅くなるため、wp_enqueue_styleを使います。- ブロックテーマでは、子テーマに
theme.jsonを置いて設定を上書きできます。
子テーマの作り方と functions.phpでよくあるミス
- 子の
functions.phpの最初に<?phpを書かず、内容がそのまま画面に出る。 - 親の
style.cssだけを読み込み、子のstyle.cssを読み込まない。 - 画像の指定に
get_template_directory_uri()を使い、子の画像が見つからない。 - 子テーマで親の関数を再定義して、「関数の二重定義」で致命的エラーにする。
子テーマの作り方と functions.phpのチェックリスト
- [ ]
Template:が親テーマのフォルダ名と完全に一致しているか - [ ] 親と子のCSSが、重複せず読み込まれているか
- [ ] 画像・ファイルのパス関数が、親・子の使い分けに合っているか
- [ ] 親テーマ更新後に、差分を確認する運用があるか
- [ ]
WP_DEBUGでエラーがないか
子テーマの作り方と functions.phpのFAQ(よくある質問)
Q. 子テーマは必ず必要ですか?
A. 自作テーマには不要です。市販・配布テーマを改造するときに有効です。
Q. 子テーマの functions.php で親を require する必要は?
A. ありません。両方自動で読み込まれます。
Q. 子テーマから親のテンプレートパーツを指すには?
A. get_parent_theme_file_path() や、get_template_directory() を使います。
筆者の見解(子テーマの作り方と functions.php)
子テーマは、小さな修正を安全に切り分けるための手段であり、大幅な改造を重ねる場所ではないと考えます。変更が増えてきたら、親テーマとの差分を管理しやすい形(フックやフィルターでの拡張)に寄せていく方が、長く運用しやすいと思います。
子テーマの作り方と functions.phpの関連項目
- get_template_directory() の使い方|説明・引数・注意点
- get_template_directory_uri() の使い方|説明・引数・注意点
- get_template() の使い方|説明・引数・注意点
- add_theme_support() の使い方|説明・引数・注意点
- remove_action が効かない
