Linux.com

Feature: PHP

Smarty templating and presentation library for PHP

By Eddie Tejeda on December 09, 2005 (8:00:00 AM)

Share    Print    Comments   

PHP has historically been a simple scripting language used for quickly developing small web sites with dynamic content. But newer features have given the language the structure and libraries for building larger applications. One such library is Smarty, a templating and presentation engine. Smarty helps developers build applications in modules by separating the presentation layer from the application code. This article covers some of the basic features of Smarty for developers.

Smarty provides the framework for creating a distinct layer for the user interface. A distinct interface layer gives designers the flexibility to modify or redo the interface without altering any of the application code. The template code looks just like HTML and allows designers to work in a familiar environment. Designers need only learn a few simple commands that retrieve the data from PHP. They do not need to know how or where the data comes from or how it got there. The same goes for the application code; changing the logic or the way the application gets data does not affect the presentation layer. Having this strict separation of code and presentation can sometimes be cumbersome, but results in code that is easier to maintain.

To use Smarty, download the latest version and read the documentation. The installation process is easy and involves moving Smarty into a location that PHP can access and creating a few directories for Smarty to hold templates and temporary files. To manage the initialization process use this class:

<?php
define(SMARTY_INSTALL_PATH, "/path/to/Smarty-2.6.9/");

$current_include_path = ini_get("include_path");
ini_set($include_path.":".SMARTY_INSTALL_PATH);

require_once('Smarty.class.php');

class SmartyManager {

  function &smartyInitialize($path) {
     //detect if the proper directories exist
     if(!is_dir( $path."/templates/") )
	die("SmartyManager::smartyInitialize Error: create templates directory");
     if(!is_dir( $path."/templates_c/") )
	die("SmartyManager::smartyInitialize Error: create template_c directory");
     if(!is_dir( $path."/cache/") )
	die("SmartyManager::smartyInitialize Error: create cache directory");
     if(!is_dir( $path."/config/") )
	die("SmartyManager::smartyInitialize Error: create config directory");

     if(!is_writeable( $path."/templates_c/") )
	die("SmartyManager::smartyInitialize Error: templates_c needs to writable");

     $smarty = new Smarty();
     $smarty->template_dir = $path."/templates/";
     $smarty->compile_dir = $path."/templates_c/";
     $smarty->cache_dir = $path."/cache/";
     $smarty->config_dir = $path."/config/";
     return $smarty;
  }
}
?>

This class detects whether the installation process is complete and then initializes a Smarty object. To use the SmartyManager class, specify the path in SMARTY_INSTALL_PATH in SmartyManager and include it in your application. Next, instantiate a SmartyManager object and pass it the directory where you want to hold your templates and temporary files. The directory you pass it to must have four subdirectories: config, templates, templates_c (which holds compiled templates -- that is, ones which have already merged the application data with the presentation), and cache. When you create a template make sure it goes inside the templates directory.

Here is an example that uses SmartyManager:

<?php
require_once('SmartyManager.class.php'); //include the SmartyManager.class
$manager = SmartyManager(); //create an object;
/* get smarty object from SmartyManager */
$smarty = $manager->smartyInitialize("/var/www/application/presentation");

/* now we are using smarty */
$smarty->assign("items", $items);
$smarty->display('Users.tpl');
?>

After you initialize Smarty you can pass variables for the designer using the assign() method in PHP. The first argument is the name variable used in Smarty and the second will be the value, as shown in the example above. You can assign as many variables as you need. Calling the display() method with the name of the template, Users.tpl in this case, will handle the display. Don't worry about giving a full path to the template -- Smarty always looks at files relative to the templates directory.

Looping though arrays

Now that you have Smarty running, it's time to start creating pages with dynamic data. In most cases, the data structure passed down to Smarty will be arrays, especially associative arrays, because most data will probably come from a database, which are already organized in rows and columns. Here is an example of a 2D array created in PHP:

<php
// filename: users.php
$items = array( 1 => array("first_name" => "eddie","last_name" => "smith" ),
                2 => array("first_name" => "jane","last_name" => "doe" ),
                3 => array("first_name" => "gregory","last_name" => "adams" ));
?>

When you send a 2D array to a Smarty template, you can iterate through the items using a foreach loop. Smarty comes with a few other built-in functions, but here we will only focus on the most common ones. In the template, to get values from an associative array, use dot syntax, similar to the way you access public properties of an object. While foreach provides an easy way to iterate through an array, using the method section provides a bit more control when iterating through the array. The following examples demonstrate a template looping through an array using foreach and then section. (Note: Everything inside {* *} delimiters is a comment.):

{* filename: users.tpl *}
<table>

{if $printUser == "true"}
  {foreach from=$items key=key item=item}
    <tr style="background-color:{cycle values="#EEEEEE, #FFFFFF"}">
      <td>{$item.first_name}</td>
      <td>{$item.last_name}</td>
    </tr>
  {/foreach}
{else}
  <tr><td>We're Not Printing Users Today</td></tr>
{/if}

</table>

In this example, you'll notice that the if and else statements are enclosed in braces, as all Smarty functions (even control functions) are called. The if statement also encloses all of the else statements, and the condition is not closed until the if statement is closed.

Some variable names have a dollar sign, while others do not, and some are enclosed in curly brackets. Variable names that use a dollar sign prefix, as in PHP, already have data in them and can be passed to other functions. If any variable is enclosed in braces and has the dollar sign then it will be printed to the screen no matter what type of quoting surrounds it. Finally, variables that do not have a dollar sign or braces are used when assigning a value to it within a function, but to retrieve their values the previous rules apply.

The actual foreach code is very similar to the foreach code in PHP. The foreach function takes three possible parameters: from is the array you want to iterate through, key is the current position in the array, and item holds the current item.

{* filename: users.tpl *}
{* in this example we print all the values in the array *}
<table>
{section name=user_id loop=$users start=2 step=2 }
  {$users[user_id].first_name}</td>
  {$users[user_id].last_name}</td>
{/section}
</table>

In this example you can see how section works a bit different from foreach. You have a few more options not available in foreach, such as start and step, which tell the loop to begin execution in a specific point in the array, and step specifies how to count through the array. Giving step a negative number causes the loop to count backwards. For a complete list of all the parameters section can take, look at the Smarty documentation.

Variable modifiers

Variable modifiers provide a final opportunity for designers to edit the data before it gets printed to the screen. The syntax is simple, though a bit different from many common programming languages. The function to modify the variable is called directly from the braces enclosing the variable. This is similar to Unix piping (|), which directs the output to a function which will then display. This example demonstrates how to use modifiers:

{* Modifiers1.tpl *}
{* Note: the dots in the end are not done by the function;
 they were added to shorten example *}
{* $paragraph is "The horse raced past the barn fell.\n\nThis sentence is false." *}

{$paragraph|capitalize} {* result: THE HORSE RACED PAST... *}
{$paragraph|count_words} {* result: 11 *}
{$paragraph|count_sentences} {* result: 2 *}
{$paragraph|count_paragraphs} {* result: 2 *}

A list of all modifiers can be found in the variable modifiers section of the Smarty site. None of the functions above take any arguments, but passing arguments to modifiers is simple. If a modifier takes arguments, the arguments are passed with a colon-separated list, as in the following example:

{* Modifiers2.tpl *}
{$paragraph|indent:10}
{* the result would be indented 10 spaces *}
{$paragraph|replace:"Wasn't":"Was"}
{* this modifier replaces all occurrences of the first string with the second *}
{$paragraph|count_characters:true}
{* if the argument is true then the result counts spaces, otherwise it doesn't *}

If you perform any of these functions to an array, then all the values of that array will be modified respectively.

Passing objects to Smarty

In order for Smarty to use objects created by PHP, you first need to instantiate an object in PHP and pass to Smarty using the register_object() method. You access an object in a template similar to the way you call Smarty's built-in functions. Here's an example of how to pass an object to Smarty:

<?php
// this is the example class
class Classname {
    function methodname($name) {
        return "$name";
    }
}
//we create an object
$obj = new Classname;
// registering the object by reference
$smarty->register_object("obj",$obj);
$smarty->display("index.tpl");
?>

The following is an example of a template accessing the methods of an object. The code passes parameters to the function, and will store the result in a variable if assign is defined with a name of a variable.

{* template of an object calling a method *}
{foobar->methodname p1="eddie" assign="output"}
the name is {$output}

That covers most of the basics of Smarty. Smarty's features, such as letting you build your own functions and modifiers, make it a useful tool for building large applications.

Share    Print    Comments   

Comments

on Smarty templating and presentation library for PHP

Note: Comments are owned by the poster. We are not responsible for their content.

templating and php

Posted by: Anonymous Coward on December 09, 2005 11:56 PM
You can already do this with php as is, so why bother.

#

CSS and HTML

Posted by: Anonymous Coward on December 10, 2005 12:45 AM
You can already do presentation in HTML, so why bother with CSS?

#

Re:CSS and HTML

Posted by: Anonymous Coward on December 10, 2005 01:18 AM
I didn't know that css was implemented in html.

#

Re:CSS and HTML

Posted by: Anonymous Coward on December 11, 2005 10:06 AM
How many times do you want to type cellpadding=0 cellspacing=0 border=0 ??

Whatever you answer, CSS is your solution. However SMARTY does not do anything that a good coder should be doing in the first place.

#

Re:CSS and HTML

Posted by: Anonymous Coward on December 12, 2005 02:23 PM
With HTML and CSS (with which I've worked for several years now) the power isn't in saving some typing or bandwidth, though those are nice side effects. The point is that by separating style and content, you enable the client to deal directly with the information and mix and mesh with other information in ways you yourself may not have been able to predict or accommodate.

It's reasonable to assume that the same thing could apply here. At the very least, it's possible that a good coder with lousy graphic design or user interface skills would make a well coded but hard to navigate web app. A graphic designer with poor coding skills might make the reverse kind of mistake. Separating the two means that, at the very least, a well coded project with a bad theme can be easily re-themed by someone who doesn't know much about programming but does know about good interfaces.

Another possibility might be a powerful application that's been designed to output information in one format, but now needs to do it in another. Say shifting from HTML to some new XML standard for song lyrics or something. If your application was designed with something like SMARTY handling the actual presentation, that'd be a very quick and easy transition. If you instead have to understand and rewrite certain parts of the applications code, it could turn into a nice mess.

#

Re:CSS and HTML

Posted by: Anonymous Coward on December 13, 2005 04:55 AM
If you ever used Smarty, you would know it is not an alternative to CSS. CSS markup within the template files is no different with or without Smarty (or PHP for that matter.)

Smarty is a tool to separate your application code from its presentation. It's all about saving precious programming/designing cycles during application development and ongoing maintentance. How you end up contructing your templates (using CSS/HTML/Javascript/etc.) is entirely up to you, it has nothing to do with Smarty directly.

#

Re:templating and php

Posted by: Anonymous Coward on December 10, 2005 11:44 AM
I agree, solutions like <a href="http://www.phpsavant.com/" title="phpsavant.com">Savant</a phpsavant.com> are much easier to use (and faster) than Smarty will ever be. If you really want something as painfully complex as smarty, you might as well use something more cross-platform like XSLT.

#

Re:templating and php

Posted by: Anonymous Coward on December 13, 2005 04:46 AM
Why use PHP? You can do the same thing in C.

#

I happen to like Smarty

Posted by: superbenk on December 10, 2005 05:44 AM
I did an early PHP application using Smarty for the first time and didn't really know what I was doing. I ended up coming away from that experience really disliking Smarty as I felt it was extremely redundant. However, I've recently started using it again with the new knowledge I've gained since then and I can say I really see the usefulness of something like Smarty. Are there ways to do similar things with PHP alone? Sure. Does Smarty abstract from PHP the most useful things for templating? Definitely. In my opinion, it's not so much a matter of what you use, but how you use it. Whether you extract your display code from your logic with pure PHP or you use Smarty, it's still a good thing to do if done properly. Smarty just adds some features that are very useful in creating the abstracted display code and they do it in such a way that is easy to work with on the logic side as well.

#

This story has been archived. Comments can no longer be posted.



 
Tableless layout Validate XHTML 1.0 Strict Validate CSS Powered by Xaraya