Laravel4、ペギネーションリンクを取り替える
タグ: Laravel4
これは、Laravel Advent Calendar 2013 の6日目の記事です。
前日に引き続き、Laravelに巣食う悪の権化、悪魔博士改め、川瀬が担当します。
ペギネーションの表示形式は、手を加えなくても切り替えられます。Laravelが用意している3種類は、app/coinfig/view.phpの中の設定を変更し、切り替えます。
しかし、これらはCSSフレームワークのTwitter Bootstrapを利用しています。じゃあ、Bootstrap以外に切り替えられるのかと言えば、そのままでは無理で、多少工夫をしなくてはなりません。
今回、Foundationが新しいバージョンをリリースしたので、Foundation5に対応する実例をご覧ください。
ビューファイルの切り替え
Laravel4が用意しているビューファイルは、vendor/laravel/framework/src/Illuminate/Pagination/views/に存在しています。
もちろん、これらはFoundation5に対応していませんので、そのまま使えません。
通常のビューのように、app/viewsフォルダー下にビューを作成します。今回はapp/views/pagination/foundation5.phpファイルを作成します。
<?php $presenter = new Foundation5Presenter( $paginator ); ?>
<?php if( $paginator->getLastPage() > 1 ): ?>
<ul class="pagination">
<?php echo $presenter->render(); ?>
</ul>
<?php endif; ?>
ペギネーションのビューファイルは、似たような構成になります。最初にプレゼンタークラスのインスタンスを取得し、そのrenderメソッドを呼び出しています。
今回作成したのは、Foundation5Presenterクラスです。このクラスは本来PSR-0に基づきローディングさせたほうが良いと思いますが、指定の手間を省くため、modelsディレクトリー下に作成しましょう。app/models/Foundation5Presenter.phpです。
<?php
use Illuminate\Pagination\BootstrapPresenter;
/**
* Foundation 5 presenter
*
* Override methods include hard coded html tags.
*/
class Foundation5Presenter extends BootstrapPresenter{
/**
* Create a range of pagination links.
*
* @param int $start
* @param int $end
* @return string
*/
public function getPageRange($start, $end)
{
$pages = array();
for ($page = $start; $page <= $end; $page++)
{
// If the current page is equal to the page we're iterating on, we will create a
// disabled link for that page. Otherwise, we can create a typical active one
// for the link. These views use the "Twitter Bootstrap" styles by default.
if ($this->currentPage == $page)
{
$pages[] = '<li class="current"><span>'.$page.'</span></li>';
}
else
{
$pages[] = $this->getLink($page);
}
}
return implode('', $pages);
}
/**
* Get the previous page pagination element.
*
* @param string $text
* @return string
*/
public function getPrevious($text = '«')
{
// If the current page is less than or equal to one, it means we can't go any
// further back in the pages, so we will render a disabled previous button
// when that is the case. Otherwise, we will give it an active "status".
if ($this->currentPage <= 1)
{
return '<li class="allow unavailable"><span>'.$text.'</span></li>';
}
else
{
$url = $this->paginator->getUrl($this->currentPage - 1);
return '<li class="allow"><a href="'.$url.'">'.$text.'</a></li>';
}
}
/**
* Get the next page pagination element.
*
* @param string $text
* @return string
*/
public function getNext($text = '»')
{
// If the current page is greater than or equal to the last page, it means we
// can't go any further into the pages, as we're already on this last page
// that is available, so we will make it the "next" link style disabled.
if ($this->currentPage >= $this->lastPage)
{
return '<li class="allow unavailable"><span>'.$text.'</span></li>';
}
else
{
$url = $this->paginator->getUrl($this->currentPage + 1);
return '<li class="allow"><a href="'.$url.'">'.$text.'</a></li>';
}
}
/**
* Get a pagination "dot" element.
*
* @return string
*/
public function getDots()
{
return '<li class="unavailable"><span>...</span></li>';
}
/**
* Create a pagination slider link.
*
* @param mixed $page
* @return string
*/
public function getLink($page)
{
$url = $this->paginator->getUrl($page);
return '<li><a href="'.$url.'">'.$page.'</a></li>';
}
}
Illuminate\Pagination\BootstrapPresenterを拡張していますが、実際、このクラス内にハードコードされている、HTMLのclass指定をFoundation5用に書き換えているだけです。
このプレゼンテーターにはインターフェイスが定義されていません。ですから、自由に自分の好きなように作成してもかまいません。要は、ペジネーション用のコードを生成できれば良いわけです。(ですから、自作する場合は、別段renderというメソッド名にこだわる必要もありません。)
これで準備が整いました。app/config/view.phpを変更し、最初に作成した'pagination.foundation5`をビューとして指定してください。Laravel4が提供しているビューを利用する場合は'pagination::...'と書きますが、自前のビューを利用する場合は、いつもビューを指定している通りに指定します。
これで、ペギネーションを利用すれば、Foundation5用に表示されます。(実際は、Bootstrapと大して違いが出ないのですけど。:D)
注意
多分、Foundation5はリリースされたばかりで、結構バグがあるようです。例えばcssにはペジネーションのactiveクラスの属性指定がないため、現在のページがデモのように表示されません。
対応されるまで、自分で指定する必要があります。
ul.pagination li.current {
background: none repeat scroll 0 0 #008CBA;
color: #FFFFFF;
cursor: default;
font-weight: bold;
padding: 0.05556rem 0.55556rem;
border-radius: 3px;
}
ペギネーションはとても難しい問題を含んでいます。それは、ペギネーションと書くとペジネーション派の人から揶揄され、ペジネーションと書くとペギネーション派の人からブーブー言われます。願わくば、こんなことで突っ込まれないように…(最初のぺは、あの英語の時間に習ったアとエの中間という音です。その後はじぇじぇじぇのジェですから、ペジェネイションかパジェネイションが正しいと、自分で突っ込んでおきましょう。ペァジェネイションかな?)
明日の担当も、私です。明後日はまだ誰も予約していません。この程度、これより簡単でも、使用感の感想でも良いので、書きたい方はどうぞ。