Tuesday, July 3, 2012

Reusing views with partials in YII frameworks

Yii supports partials, so if you have a block without much logic that you want to reuse or want
to implement e-mail templates, partials are the right way to look.
Getting ready
1. Set up a new application using yiic webapp.
2. Create a WebsiteController as follows:
class WebsiteController extends CController
{
function actionIndex()
{
$this->render('index');
}
}
How to do it...
We will start with a reusable block. For example, we need to embed a YouTube video at
several website pages. Let's implement a reusable template for it.
1. Create a view file named protected/views/common/youtube.php and paste an
embed code from YouTube. You will get something like:
<object width="480" height="385"><param name="movie"
value="http://www.youtube.com/v/S6u7ylr0zIg?fs=1 "></
param><param name="allowFullScreen" value="true"></
param><param name="allowscriptaccess" value="always"></
param><embed src="http://www.youtube.com/v/S6u7ylr0zIg?fs=1"
type="application/x-shockwave-flash" allowscriptaccess="always"
allowfullscreen="true" width="480" height="385"></embed></object>
2. Now, we need to make it reusable. We want to be able to set video ID, width, and
height. Let's make width and height optional, as follows:
<object width="<?php echo!empty($width) ? $width : 480?>"
height="<?php echo!empty($height) ? $height: 385?>"><param
name="movie" value="http://www.youtube.com/v/<?php echo
$id?>?fs=1 "></param><param name="allowFullScreen" value="true"></
param><param name="allowscriptaccess" value="always"></
param><embed src="http://www.youtube.com/v/<?php echo $id?>?fs=1"
type="application/x-shockwave-flash" allowscriptaccess="always"
allowfullscreen="true" width="<?php echo !empty($width) ? $width
: 480?>" height="<?php echo !empty($height) ? $height: 385?>"></
embed></object>
3. Now, you can use it in your protected/views/website/index.php like this:
<?php $this->renderPartial('////common/youtube', array(
'id' => '8Rp-CaIKvQs', // you can get this id by simply looking
at video URL
'width' => 320,
'height' => 256,
))?>
Looks better, right? Note that we have used // to reference a view. This means that
Yii will look for a view starting from protected/views not taking controller name
into account.
4. Now, let's send some e-mails. As we are unable to write unique letters to thousands
of users, we will use a template but will make it customized. Let's add a new method
to protected/controllers/WebsiteController.php as follows:
class WebsiteController extends CController
{
function actionSendmails()
{
$users = User::model->findAll();
foreach($users as $user)
{
$this->sendEmail('welcome', $user->email, 'Welcome to the
website!', array('user' => $user));
}
echo 'Emails were sent.';
}
function sendEmail($template, $to, $subject, $data)
{
mail($to, $subject, $this->renderPartial
('//email/'.$template, $data, true));
}
}
5. Here is our template protected/views/email/welcome.php:
Hello <?php echo $user->name?>,
Welcome to the website!
You can go check our new videos section. There are funny raccoons.
Yours,
Website team.
How it works...
CController::renderPartial does the same template processing as
CController::render except the former does not use layout. As we can access current
controller in a view using $this, we can use its renderPartial to use view within another
view. renderPartial is also useful when dealing with AJAX as you don't need layout
rendered in this case.

No comments:

Post a Comment