SmartyでDjangoみたいなテンプレート継承してみた

仕事で1年ぶりにPHPを使った。テンプレートエンジンはSmartyということだったのだけど、今見直すとテンプレート継承できないのがつらいので、できるようなプラグインを書いた。多段階の継承もできるよ。

はじめに

DjangoとかZopeのTALとかrhacoとか最近のテンプレートエンジンはみんなテンプレート継承ができる。で、Smartyでもできたらいいのになぁ、ということで作った。

テンプレート継承は、オブジェクト指向の継承だと、親クラスで定義されたメソッドを子供のクラスでオーバーライドしたり、abstractなやつを実装したりして、子供のほうで詳細な部分を指定していく。ソレと同じように、親テンプレートで定義してあるブロックを、子供テンプレートでオーバーライドしたりできたらいいなぁ、というもの。

なんでテンプレート継承がしたいかというと・・・。Smartyのテンプレートの作り方って言うと、hoge.tplの中で最初にinclude file=”header.tpl”つぎに内容を書いて、include file=”footer.tpl”ってやるかんじ。

で、それだとだるいよねって感じで、 SmartyでRailsライクなレイアウトテンプレートを使う という記事があったりする。しかし、この方法だとコンテンツに表示するテンプレートファイルを別途PHPのコード側で指定しないといけなくて、できればそれはテンプレートの側で完結していてほしいなぁ、と思った。

使い方

ダウンロード先

ソースコード

index.php:

 <?php
 require_once 'Pearified/Smarty/Smarty.class.php';
 $smarty = new Smarty();
 SmartyBlocks::registerTo(&$smarty);
 $smarty->display('subtemplate1.html');
 ?>

base.html:

 <html>
 <head>
 {include file="block:css"}
 {include file="block:javascript"}
 </head>
 <body>
 <div class="base">
 base template
 </div>
 <div class="base">
 {include file="block:sub"}
 </div>
 </body>

 </html>

subtemplate1.html:

{block name="sub"}
<div class="subtemplate1">
subtemplate1
{include file="block:subsub"}
</div>
{/block}
{block name="css" mode="append"}
<link rel="stylesheet" href="subtemplate1.css" type="text/css" />
{/block}
{include file="base.html"}

結果

こんなかんじ:

 <html>
 <head>
 <link rel="stylesheet" href="subtemplate1.css" type="text/css" />
 </head>
 <body>
 <div class="base">
 base template
 </div>
 <div class="base">
 <div class="subtemplate1">
 subtemplate1
 </div>
 </div>
 </body>

 </html>

構成要素

blockブロックプラグイン

{block name=”body”} 今日はいい天気だ。雪だけど。 {/block}

として使える。そうすると、後でblockスキーマを使ってインクルードできる。

  • nameパラメータ
    • 任意の文字列
    • このタグで囲まれた内容を、なんと言うブロックに割り当てるか
  • modeパラメータ
    • [insert|replace|append]のいずれか
    • タグの内容をnameに指定されたブロックの先頭に追加するのか、置き換えるのか、最後に追加するのか。多段継承するときに便利。

blockリソースプラグイン

{include file=”block:body”} でつかえる。

事前にblockブロックプラグインを用いて定義されたブロックを{include file=”block:body”}とかして読み込む。

制限

  • 継承するテンプレートの指定は必ずテンプレートの最後で行う。先にblockブロックプラグインでブロックに入る内容を定義して、そのあとでblockスキーマでインクルードする。
  • block:のリソースプラグインではキャッシュが効かない。常に現在の時刻を返すので。これはなんとかできそう。

参考

ウノウラボ Unoh Labs: SmartyでRailsライクなレイアウトテンプレートを使う

やたーーSmartyでTTのWRAPPERエミュレーションができたよーー - サタケ家

This entry was posted on Sun, 03 Feb 2008 09:20:00 GMT . You can follow any any response to this entry through the Atom feed. You can leave a comments, Or a trackback from your own site.
Tags ,


Trackbacks

Use the following link to trackback from your own site:
http://www.jaro68.jp/sett4/blog/trackbacks?article_id=smarty-template-inheritance&day=03&month=02&year=2008

Comments

Leave a response

Leave a comment