WordPressのカテゴリーやタグ、カスタムタクソノミーにそれぞれ独自の入力欄を追加する方法を調べていたんですが、webopixelさんの記事「WordPressのカテゴリーにカスタムフィールドを追加する」がわかりやすくて、とても参考になりました。
そこで、掲載されているコードを参考にさせて頂いて自分なりにカスタマイズして扱いやすくしました。
もし似たようなことをされたい方は、ご参考ください。
カテゴリー、タグ、カスタムタクソノミーに独自の入力欄追加
ご使用中のテーマフォルダ内にある「functions.php」ファイルの最後尾などに以下のコードを追記します。
<?php //入力欄を追加 add_action('category_edit_form_fields','add_taxonomy_fields'); //カテゴリー add_action('post_tag_edit_form_fields','add_taxonomy_fields'); //タグ add_action('pref_edit_form_fields','add_taxonomy_fields'); //都道府県(カスタムタクソノミー) add_action('product_edit_form_fields','add_taxonomy_fields'); //製品(カスタムタクソノミー) function add_taxonomy_fields($term) { $term_id = $term->term_id; //タームID $taxonomy = $term->taxonomy; //タームIDに所属しているタクソノミー名 //すでにデータが保存されている場合はDBから取得する $term_meta = get_option( $term->taxonomy . '_' . $term_id ); ?> <tr class="form-field"> <th scope="row"><label for="term_meta[free_input]">自由入力</label></th> <td><textarea name="term_meta[free_input]" id="term_meta[free_input]" rows="5" cols="50" class="large-text"><?php echo isset($term_meta['free_input']) ? esc_attr( $term_meta['free_input'] ) : ''; ?></textarea> <p class="description">何でも自由に書いてね</p></td> </tr> <?php } ?>
コードがやっていること
アクションフック「{$taxonomy}_edit_form_fields」を使って、カテゴリー、タグ、カスタムタクソノミーに対して「自由入力」という項目で入力欄を追加しています。
「{$taxonomy}_edit_form_fields」の使い方は「{$taxonomy}」の部分をタクソノミー名に変更することがポイントだなぁと思います。
下の表は「カテゴリー」「タグ」「カスタムタクソノミー」で「{$taxonomy}_edit_form_fields」を使用する時の例です。
タクソノミーの名前 | タクソノミー名 | アクションフック名 |
---|---|---|
カテゴリー | category | category_edit_form_fields |
タグ | post_tag | post_tag_edit_form_fields |
都道府県(カスタムタクソノミー) | pref | pref_edit_form_fields |
製品(カスタムタクソノミー) | product | product_edit_form_fields |
というわけで、うまくコードが動いているかどうか確認しましょう。WordPressの管理画面から「タグ」をクリック(またはタップ)します。
タグの一覧が表示されますので、一つ選びます。ここでは「上野駅」のタグを選んで編集ボタンをクリックします。
「説明」の下に「自由入力」が追加されました。
タグの他にもコードで指定したとおり、「カテゴリー」「都道府県(カスタムタクソノミー)」「製品(カスタムタクソノミー)」にも同じ場所に自由入力が追加されています。
今回はテキストエリアを追加しましたが、selectやoption要素などを使って選択式の項目を追加することもできます。
項目も複数追加できます。今回は、自由入力について「for」「name」「id」属性に配列名「term_meta[free_input]」を指定しましたが、他の項目と配列名は重複しないように注意しましょう。
- 自由入力→term_meta[free_input]
- ID指定→term_meta[ids](別の配列名にする)
などです。
また、入力欄にはすでに値がDBに保存されているかどうかで条件分岐をしています。こちらも同様に、複数項目を追加する際には出力に注意しましょう。
「自由入力」を出力
<?php echo isset($term_meta['free_input']) ? esc_attr( $term_meta['free_input'] ) : ''; ?>
「ID指定」を出力
<?php echo isset($term_meta['ids']) ? esc_attr( $term_meta['ids'] ) : ''; ?>
値を保存するにはこの方法でOK
入力欄を作っただけでは値を保存できないので、保存するためのコードを書きます。
タクソノミー名を動的に取得するコードにしました。先ほどの入力欄を追加したように、「functions.php」の最後尾などに追記します。
<?php //カテゴリー入力欄の保存 add_action( 'edited_term', 'save_taxonomy_fileds' ); function save_taxonomy_fileds( $term_id ) { global $taxonomy; //タクソノミー名を取得 if ( isset( $_POST['term_meta'] ) ) { //自由入力欄に値が入っていたら処理する $term_meta = get_option( $taxonomy . '_' . $term_id ); $term_keys = array_keys($_POST['term_meta']); foreach ($term_keys as $key){ if (isset($_POST['term_meta'][$key])){ $term_meta[$key] = stripslashes_deep( $_POST['term_meta'][$key] ); } } update_option( $taxonomy . '_' . $term_id, $term_meta ); //保存 } }
コードがやっていること
アクションフック「edited_term」を使って、「term_meta」の値が入力されていたら保存するという仕組みになっています。
値はどこに保存されているのか確認する
独自で追加した入力欄はどこに保存されているのか確認をすると、wp_optionsテーブルに保存されていることがわかります。
上野駅のタクソノミー名は「post_tag」で、IDは43なので、「post_tag_43」という値で「option_name」フィールドに保存されます。
まとめ
カテゴリー、タグ、カスタムタクソノミーのアーカイブページなどに独自で入力した値を表示したり、「1か0か」みたいな条件分岐のフラグっぽく利用することもできますね。
これは使える!
関連:プロフィールにも入れられるよ
この記事に関連する内容として、プロフィール欄に独自の入力欄を追加する方法も以下のページに書いていますので、あわせてご参考ください。
いつもお世話になっています!
タグ管理画面ページへのフィールド追加のソースが今村さんのブログにしかなくて、すごい助かっています。
質問なのですが、この記事で追加したフォームに入力した内容をWPのテンプレート側に出力する際に、
追加された入力欄の内容が空っぽだった場合、元からあるタグの名前を出力するといった条件分岐の方法ができずに居ます。。今は「日本語名」の入力欄を追加しまして、タグの名前のフォームには「英語名」を入れています。
ここで日本語名がなかった場合に英語名を出すという分岐と、
タグの一覧(Archive)ページでh1で括りまして、<h1>日本語名 ・ 英語名</h1>と表示させる場合に、日本語名が無かった場合に中黒表示させないように出来ずに居ます、、
初心者で申し訳ないのですが何かしらヒントありましたら、ご教授いただけると助かります。><
2015/09/15 20:09:18
ツイート
シェア
どうもはじめまして。
記事をご参考頂きましてありがとうございます。
「日本語名」の入力欄のフォームは、この記事のルールに沿って「$term_meta['jp_name']」と作ったとしますね。タグのアーカイブページに以下のコードを入れるとできるかもです。
<?php
$queried_object = get_queried_object(); //オブジェクト取得
$data = get_option( $queried_object->taxonomy . '_' . $queried_object->term_id ); //独自の入力欄のデータ取得
if( !empty($data['jp_name']) ){ //「日本語名」が入っているかどうかで条件分岐
$jp_name = $data['jp_name'] . '・';
} else {
$jp_name = '';
}
$en_name = single_term_title('', false); //英語名取得
echo '<h1>' . $jp_name . $en_name . '</h1>'; //出力
?>
私の認識とご質問の意図が違っていましたらすみません。
2015/09/17 23:41:20
ツイート
シェア
お世話になっています!
質問書いていまして、わかりづらかったと思いもうしわけなかったです。
まさにそのとおりの認識でした、テストさせて頂いて無事出来ました。
お忙しい中返信ありがとうございます!!!
2015/09/18 17:01:38
ツイート
シェア
いえいえ、こういった使い方をすることもあるなぁと私も気が付くことができまして、勉強になりました。よかったです!
2015/09/19 09:47:22
ツイート
シェア