Slimphpフレームワークを試しています
Slimでレイアウトやサブビューを作成することはできますか?ビューファイルをテンプレートとして使用し、変数を他のビューのプレースホルダーとして個別にロードしたいと思います。
どうすればいいですか?
Slimphpフレームワークを試しています
Slimでレイアウトやサブビューを作成することはできますか?ビューファイルをテンプレートとして使用し、変数を他のビューのプレースホルダーとして個別にロードしたいと思います。
どうすればいいですか?
ファイル名:myview.php
<?php
class myview extends Slim_View
{
static protected $_layout = NULL;
public static function set_layout($layout=NULL)
{
self::$_layout = $layout;
}
public function render( $template ) {
extract($this->data);
$templatePath = $this->getTemplatesDirectory() . '/' . ltrim($template, '/');
if ( !file_exists($templatePath) ) {
throw new RuntimeException('View cannot render template `' . $templatePath . '`. Template does not exist.');
}
ob_start();
require $templatePath;
$html = ob_get_clean();
return $this->_render_layout($html);
}
public function _render_layout($_html)
{
if(self::$_layout !== NULL)
{
$layout_path = $this->getTemplatesDirectory() . '/' . ltrim(self::$_layout, '/');
if ( !file_exists($layout_path) ) {
throw new RuntimeException('View cannot render layout `' . $layout_path . '`. Layout does not exist.');
}
ob_start();
require $layout_path;
$_html = ob_get_clean();
}
return $_html;
}
}
?>
index.phpの例:
<?php
require 'Slim/Slim.php';
require 'myview.php';
// instantiate my custom view
$myview = new myview();
// seems you need to specify during construction
$app = new Slim(array('view' => $myview));
// specify the a default layout
myview::set_layout('default_layout.php');
$app->get('/', function() use ($app) {
// you can override the layout for a particular route
// myview::set_layout('index_layout.php');
$app->render('index.php',array());
});
$app->run();
?>
default_layout.php:
<html>
<head>
<title>My Title</title>
</head>
<body>
<!-- $_html contains the output from the view -->
<?= $_html ?>
</body>
</html>
私は自分のビューで作業しています:
class View extends \Slim\View
{
protected $layout;
public function setLayout($layout)
{
$this->layout = $layout;
}
public function render($template)
{
if ($this->layout){
$content = parent::render($template);
$this->setData(array('content' => $content));
return parent::render($this->layout);
} else {
return parent::render($template);
}
}
}
setLayoutData(..)
またはのようなメソッドを追加できますappendLayoutData(..)
数分前:
class View extends \Slim\View
{
/** @var string */
protected $layout;
/** @var array */
protected $layoutData = array();
/**
* @param string $layout Pathname of layout script
*/
public function setLayout($layout)
{
$this->layout = $layout;
}
/**
* @param array $data
* @throws \InvalidArgumentException
*/
public function setLayoutData($data)
{
if (!is_array($data)) {
throw new \InvalidArgumentException('Cannot append view data. Expected array argument.');
}
$this->layoutData = $data;
}
/**
* @param array $data
* @throws \InvalidArgumentException
*/
public function appendLayoutData($data)
{
if (!is_array($data)) {
throw new \InvalidArgumentException('Cannot append view data. Expected array argument.');
}
$this->layoutData = array_merge($this->layoutData, $data);
}
/**
* Render template
*
* @param string $template Pathname of template file relative to templates directory
* @return string
*/
public function render($template)
{
if ($this->layout){
$content = parent::render($template);
$this->appendLayoutData(array('content' => $content));
$this->data = $this->layoutData;
$template = $this->layout;
$this->layout = null; // allows correct partial render in view, like "<?php echo $this->render('path to parial view script'); ?>"
return parent::render($template);;
} else {
return parent::render($template);
}
}
}
スリム3付き
namespace Slim;
use Psr\Http\Message\ResponseInterface;
class View extends Views\PhpRenderer
{
protected $layout;
public function setLayout($layout)
{
$this->layout = $layout;
}
public function render(ResponseInterface $response, $template, array $data = [])
{
if ($this->layout){
$viewOutput = $this->fetch($template, $data);
$layoutOutput = $this->fetch($this->layout, array('content' => $viewOutput));
$response->getBody()->write($layoutOutput);
} else {
$output = parent::render($response, $template, $data);
$response->getBody()->write($output);
}
return $response;
}
}
レイアウト:
<?=$data['content'];?>
親ビューでこれを使用できます。
$app = \Slim\Slim::getInstance();
$app->render('subview.php');
出力を変数にキャプチャする場合は、ビューのfetch()
メソッドを使用するのと同じくらい簡単です。
//assuming $app is an instance of \Slim\Slim
$app->view()->fetch( 'my_template.php', array( 'key' => $value ) );
はい、可能です。smartyやtwigなどのテンプレートエンジンを使用したくない場合。.phpビューファイルのみを使用する場合。次の手順を実行します。
手順1.プロジェクトのルートディレクトリに新しいディレクトリを作成します。例:テンプレート。
ステップ2.dependencies.phpを開き、以下のコードを貼り付けます
$container = $sh_app->getContainer();
$container['view'] = function ($c) {
$view = new Slim\Views\PhpRenderer('src/templates/');
return $view;
};
ステップ3.コントローラーのビューコードをレンダリングする方法は、次のようになります。
$this->container->view->render($response,'students/index.php',['students' => $data]);