#prefix ってプリフィクスじゃないのね。。。
親テーマ
Web 制作会社なら(そうでなくても)自社ルールに則って構築されたテーマのひな形が存在すると思います。無い場合は、この際だから作ってしまいましょう!いつまでもまんま TwentyTen でいいハズないじゃない。そういうテーマを自社の親テーマにして、各々のクライアントにフィットさせた子テーマを納品するようにすると制作効率が向上したりテーマ管理がし易くなったり彼女ができたりと色々ステキです。
そんなわけで、以下 テーマ(の functions.php)をクラス化して子テーマも使う場合の最少コード例です。
親テーマの style.css
正規の親テーマの書き方と同じです。
/*
Theme Name: Wpxtreme Parent
Theme URI: http://wpxtreme.jp/
Author: kz
Author URI: http://kzxtreme.com/
Description: 当社の親テーマであります
Version: 1.0
*/
/* スタイルの記述は省略 */
親テーマの functions.php
ポイントは、after_setup_theme
アクションの優先度です。functions.php は 子テーマ ---> 親テーマ の順に読み込まれますが、アクションの優先度により 親テーマのクラス定義 ---> 子テーマのクラス定義 の順に実行されるように指定します。で、最後に現在のテーマのクラスのオブジェクトを作って完了です。ののの気になる。
PHP 的なポイントは new static()
辺り。この、親クラスに書いてるけど「子クラスの」という扱いができる late bind は PHP 5.3.0〜使えます。
<?php
// テーマオブジェクトをグローバル変数にします。
// the_theme なんて危険な名前は避けるといいかもね!
add_action( 'after_setup_theme', 'instantiate_theme', 99999 );
function instantiate_theme() {
$GLOBALS['the_theme'] = call_user_func( array( str_replace( ' ', '_', get_current_theme() ), 'get_object' ) );
}
// 親テーマは最優先でアクション実行!
add_action( 'after_setup_theme', 'setup_parent_theme', 0 );
function setup_parent_theme() {
if ( ! class_exists( 'Wpxtreme_Parent' ) ) { // テーマ名のスペースを '_' で置換してクラス名にしましょう!
class Wpxtreme_Parent {
static private $classobj = NULL;
public function __construct() {
// construct self
// add_theme_support(), add_filter(), add_action() などなど
}
public static function get_object() {
if ( NULL === self :: $classobj ) {
self :: $classobj = new static();
}
return self :: $classobj;
}
}
}
}
子テーマの style.css
これも正規の子テーマの書き方と同じです。
/*
Theme Name: Wpxtreme Child
Theme URI: http://wpxtreme.jp/
Author: kz
Author URI: http://kzxtreme.com/
Description: クライアントA様向けテーマです!
Version: 1.0
Template: wpxtremeparent
*/
@import url("../wpxtremeparent/style.css");
/* スタイルの記述は省略 */
子テーマの functions.php
<?php
// 親テーマより後にアクション実行!
add_action( 'after_setup_theme', 'setup_child_theme',1 );
function setup_child_theme() {
if ( ! class_exists( 'Wpxtreme_Child' ) ) {
class Wpxtreme_Child extends Wpxtreme_Parent {
public function __construct() {
// construct parent
parent :: __construct();
// construct self
// add_theme_support(), add_filter(), add_action() などなど
}
}
}
}
これだけで OK です。楽チン!ってこれだけじゃ何だかよくわかりませんネ。
もうちょっと具体的に
サンプル的にそれらしい処理を書いてみますね。※コードはクラスの定義部分だけです。
親テーマの functions.php
class Wpxtreme_Parent {
static private $classobj = NULL;
static protected $domain; // text domain
static protected $userdata; // 'name' => array( 'label' => 'label to display', 'type' => 'text'|'textarea'|..., 'description' => 'description.' )
static public $path; // stylesheet directory uri
/**
* Constructor, init on defined hooks of WP and include second class
*
* @access public
* @since 0.0.1
* @uses add_filter, add_action
* @return void
*/
public function __construct() {
// member variables
self :: $domain = strtolower( str_replace( '_', '', get_class( $this ) ) );
self :: $path = get_stylesheet_directory_uri();
load_theme_textdomain( self :: $domain, TEMPLATEPATH . '/languages' );
// supports
add_editor_style();
add_theme_support( 'post-thumbnails' );
// user profile
add_filter( 'user_contactmethods', array( $this, 'user_contactmethods' ) );
if ( isset( self :: $userdata ) ) {
add_action( 'personal_options_update', array( $this, 'update_profile' ) );
add_action( 'edit_user_profile_update', array( $this, 'update_profile' ) );
add_action( 'show_user_profile', array( $this, 'user_profile' ) );
add_action( 'edit_user_profile', array( $this, 'user_profile' ) );
}
}
/**
* Handler for the action 'init'. Instantiates this class.
*
* @access public
* @since 0.0.1
* @return object $classobj
*/
public static function get_object() {
if ( NULL === self :: $classobj ) {
self :: $classobj = new static();
}
return self :: $classobj;
}
/**
* Delete obsolete contact methods.
*
* @access public
* @since 0.0.1
* @return array $contactmethods
*/
public function user_contactmethods( $contactmethods ) {
unset( $contactmethods['aim'] );
unset( $contactmethods['jabber'] );
unset( $contactmethods['yim'] );
return $contactmethods;
}
/**
* Update user meta.
*
* @access public
* @since 0.0.1
* @return void
*/
public function update_profile( $user_id ) {
if ( !current_user_can( 'edit_user', $user_id ) )
return false;
foreach ( array_keys( (array) self :: $userdata ) as $field )
update_user_meta( $user_id, $field, $_POST[$field] );
}
/**
* Print form for user profile.
*
* @access public
* @since 0.0.1
* @return void
*/
public function user_profile( $user ) {
if ( !current_user_can( 'edit_user', $user->ID ) )
return false;
?><table class="form-table"><?php
foreach ( (array) self :: $userdata as $name => $data )
printf( '<tr><th><label for="%1$s">%2$s</label></th>'
. '<td><input type="%3$s" name="%1$s" id="%1$s" value="%4$s" class="regular-text" />'
. '<br /><span class="description">%5$s</span></td></tr>',
esc_attr( $name ),
esc_html( isset( $data['label'] ) ? $data['label'] : $name ),
esc_attr( isset( $data['type' ] ) ? $data['type' ] : 'text' ),
esc_attr( get_user_meta( $user->ID, $name, true ) ),
esc_html( isset( $data['description' ] ) ? $data['description' ] : '' )
);
?></table><?php
}
/**
* Prints HTML with meta information for the current post-date/time.
*
* @access public
* @since 0.0.1
* @return void
*/
public function posted_on() {
printf( __( '<time class="entry-date" datetime="%1$s" pubdate>%2$s</time>', self :: $domain ),
esc_attr( get_the_time() ),
esc_html( get_the_date() )
);
}
}
子テーマの functions.php
class Wpxtreme_Child extends Wpxtreme_Parent {
/**
* Constructor, init on defined hooks of WP and include second class
*
* @access public
* @since 0.0.1
* @uses add_filter, add_action
* @return void
*/
public function __construct() {
// set protected variables
self :: $userdata = array(
'yakusyoku' => array( 'label' => '役職', 'type' => 'text', 'description' => '社長、平社員、などを書いて!' ),
);
// construct parent
parent :: __construct();
// construct $this
}
/**
* Add contact methods.
*
* @access public
* @since 0.0.1
* @return array $contactmethods
*/
public function user_contactmethods( $contactmethods ) {
$contactmethods = parent :: user_contactmethods( $contactmethods );
$contactmethods['skype'] = 'Skype 名';
$contactmethods['twitter'] = 'Twitter ユーザー名';
$contactmethods['facebook'] = 'Fecebook ユーザー名';
return $contactmethods;
}
/**
* Prints HTML with meta information for the current post-date/time and author.
*
* @access public
* @since 0.0.1
* @return void
*/
public function posted_on() {
$user = get_userdata( get_the_author_meta( 'ID' ) );
printf( __( '<time class="entry-date" datetime="%1$s" pubdate>%2$s %3$s</time>%4$s', self :: $domain ),
esc_attr( get_the_time() ),
esc_html( get_the_time( get_option( 'date_format' ) ) ),
esc_html( get_the_time( get_option( 'time_format' ) ) ),
get_avatar( $user->user_email, 40, self :: $path . '/images/default.gif' )
);
}
}
- $domain
テキストドメインはクラス名を英数小文字にし、'_' を無くしたものです。
親テーマ:wpxtremeparent
子テーマ:wpxtremechild - $userdata
子テーマで label, type, description を設定すると、親テーマでプロフィールページに入力欄を追加します。 - user_contactmethods()
プロフィールページの「連絡先」欄
親テーマ:不要な項目を削除
子テーマ:新規に項目を追加 - posted_on()
子テーマで処理をまるっとオーバーライドしてます。
テンプレートファイル内で以下のように使用します。
global $the_theme;
$the_theme->posted_on();
ザッと思いつきですが、何かイケてる気がしませんか!?しませんかそうですか。全部 static function でええやんとか色々検討事項はございましょうが、たまにはこんなことを考えてみるのも息抜きになって良いかもですね!
動作確認バージョン
- WordPress 3.1.3
- PHP 5.3.5
【ブログ】WordPressテーマのfunctions.phpをクラス化する http://bit.ly/rhs6Gd #wordpressjp @wordpress_fan
【ブログ】WordPressテーマのfunctions.phpをクラス化する http://bit.ly/rhs6Gd #wordpressjp @wordpress_fan
【ブログ】WordPressテーマのfunctions.phpをクラス化する http://bit.ly/rhs6Gd #wordpressjp @wordpress_fan
あとでじっくり読む。てか、また変態なPOSTやなーw RT @kzxtreme: 【ブログ】WordPressテーマのfunctions.phpをクラス化する http://bit.ly/rhs6Gd #wordpressjp @wordpress_fan
やっぱ変態やなー。 RT @kzxtreme: 【ブログ】WordPressテーマのfunctions.phpをクラス化する http://bit.ly/rhs6Gd #wordpressjp @wordpress_fan
ちょうど昨日functions.phpをクラスで書くのにチャレンジしてたんだけど、なんと子テーマで継承できるのか。そりゃそのほうがいいじゃん – WordPressテーマのfunctions.phpをクラス化する http://t.co/NSYbOhY
変態~言うてたけど、子テーマで親テーマの関数継承はおでこもいつもやってます! | WordPressテーマのfunctions.phpをクラス化する | wpxtreme http://bit.ly/nVMMqB
http://wpxtreme.jp/use-class-in-wordpress-theme WordPressテーマのfunctions.phpをクラス化する | wpxtreme
WordPressテーマのfunctions.phpをクラス化する | wpxtreme http://bit.ly/rhdgZA #wordpress
WordPressテーマのfunctions.phpをクラス化する | wpxtreme #prefix ってプリフィクスじゃないのね。。。 親テーマ Web 制作会社なら(そうでなくても)自社ルールに則って構築されたテーマの…http://bit.ly/pkpBEv
Now Browsing: WordPressテーマのfunctions.phpをクラス化する | wpxtreme – http://bit.ly/qr0fNX
【ブログ】WordPressテーマのfunctions.phpをクラス化する http://bit.ly/rhs6Gd #wordpressjp @wordpress_fan
こういうの勉強になるなー。PHP5.3の機能とか使われてる。 – WordPressテーマのfunctions.phpをクラス化する | wpxtreme http://bit.ly/pOwZCp
こういうの勉強になるなー。PHP5.3の機能とか使われてる。 – WordPressテーマのfunctions.phpをクラス化する | wpxtreme http://bit.ly/pOwZCp
WordPressテーマのfunctions.phpをクラス化する | wpxtreme http://htn.to/MbvSnU
WordPressテーマのfunctions.phpをクラス化する http://wpxtreme.jp/use-class-in-wordpress-theme
整頓とコンフリクト回避> WordPressテーマのfunctions.phpをクラス化する | wpxtreme http://t.co/OgaY5wD
整頓とコンフリクト回避
整頓とコンフリクト回避> WordPressテーマのfunctions.phpをクラス化する | wpxtreme http://t.co/OgaY5wD
WordPressテーマのfunctions.phpをクラス化する http://t.co/V4HKj9u #WordBeach