0

How can I improve the script below to be able to add global template parts such as start and end of the page?

  <?php
    class simpleTemplate {
        var $variables;
        var $variables_callback;
        var $contents;
        var $preg;
        var $regexps;
        // Constructor, initialize default variables
        function simpleTemplate(){
            // default sub regexp matches
            $this->preg['var'] = '[a-zA-Z.\-_]{1,50}';

            //INSERT REGEXP

            $this->php_start = "\necho '";
            $this->php_end = "';\n";
            // Main find-replace regexps
            $this->regexps = array(
                // echo-variable statement: {(var)}
                'echo' => array(
                    'search' => '~\{((?:'.$this->preg['var'].')(?:\.)?)\}~sU',
                    'replace' => "'.\$this->_get('\\1').'"
                )
       'include' => array(
           'search' => '', // UPDATE
                    'replace' => "" // UPDATE
       )
            );
        }
        // Load a file and convert it into native PHP code
        function load($file){
            if (!is_readable($file))
                return FALSE;
            $this->file = $file;
            $this->contents = NULL;
            if (!isset($this->contents)){
                $this->contents = file_get_contents($this->file);
                $this->parse();
            }
        }
        // Load a converted template, apply variables and echo the output
        function show(){
            ob_start();
            eval($this->contents);
            ob_end_flush();
        }
        // Main converter, call sub-convertors and perform some cleaning
        function parse(){
            $this->contents = str_replace("'", "\'", $this->contents);
            $this->contents = $this->php_start.$this->contents.$this->php_end;
            foreach ($this->regexps as $regexp)
                do {
                    if (isset($contents))
                        $this->contents = $contents;
                    $contents = preg_replace($regexp['search'], $regexp['replace'], $this->contents);
                } while ($contents != $this->contents);
            $this->clean();
        }
        // Clean trash in generated PHP code
        function clean(){
            $this->contents = preg_replace("~([^\\\])''\.~", '\1', $this->contents);
            $this->contents = str_replace(".''", "", $this->contents);
            $this->contents = str_replace("\necho '';\n", "", $this->contents);
            $this->contents = str_replace("else {}", "", $this->contents);
            // Remove all whitespace from the template output
            //$this->contents = preg_replace("~(\s{2,}|\n)~", '', $this->contents);
            return;
        }
        // Get a variable from internal, or an external source
        function _get($variableName){
            $variable = @eval('return $this->variables[\''.str_replace('.', "']['", $variableName).'\'];');
            if (!isset($variable)) {
                if (isset($this->variables[$variableName]))
                    $variable = $this->variables[$variableName];
                else {
                    // Support for an external variable-source
                    $function_name = $this->variables_function;
                    if (isset($variables_callback))
                        $variable = call_user_func($variables_callback, $variableName);
                }
            }
            if (!isset($variable))
                return FALSE;
            else
                return $variable;
        }
        // Set an internal variable
        function _set($variableName, $value){
            $this->variables[$variableName] = $value;
            return TRUE;
        }
    }
    ?>

Sample .php page looks like that

<?php
require_once('tpl.php');     
$tpl = new simpleTemplate();
$data['user'] = array(
        'name' => 'Denis',
        'surname' => 'Bobrovnikov'
);
$tpl->variables = $data;
$tpl->load('index.tpl');
$tpl->show();
?>

And the template is the following

My name is {user.name} {user.surname}

I want to be able to do so in the template file

{include=header.tpl}
My name is {user.name} {user.surname}
{include=footer.tpl}

where header and footer are also parsed

1
  • 1
    smarty.net does exactly what you are trying to do. Give it a shot... Commented Jun 30, 2010 at 15:25

3 Answers 3

2

Use an existing template engine if you want something on top of PHP, don't reinvent the wheel.
Give twig a go http://www.twig-project.org/

Sign up to request clarification or add additional context in comments.

Comments

1

1) use MVC pattern instead.
2) PHP is template engine. Why just dont use it?

3 Comments

PHP is lousy template engine. Template engines in MVC are way to implement V and communication from M and C to V.
Models should not communicate with Views in MVC. And what does not let PHP controller to comunicate with PHP template?
Yes but parts of models might be directly fed to view by controller. I'm not saying pure PHP can't do anything that templates can. I'm saying that pure PHP requires some very lousy syntax to implement some features templates have. Also I'm saying that MVC does not exclude use of templates because templates are just one possible implementation of V from MVC.
-1

It is my duty as a programmer to toot my own horn in the hope that I might be helpful.

2 Comments

Your project does not seem like template engine for PHP.
@Kamil: My project is a template language that can easily and effectively be used in conjunction with PHP, so what is the real difference?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.