Introduction

This article is a guide to Flexy template engine used in X-Cart.

Table of Contents

Syntax

Basics

Generally, Flexy template is a file where you specify plain text that will be displayed to a customer. However, some part of this text can be dynamically generated. For instance, if some part should be generated by a function, it will look as follows:

My name is {getMyName()}

{getMyName()} is a call of function getMyName() function defined in the current viewer class or controller class.

If you need to pass some string value to a function, it will look as follows: 

My name is {getMyName(#value#)}

If you need to pass an array, it will look as follows: 

{functionName( _ARRAY_(#key1#^#value1#,#key2#^getValue2() ))}

If you want to add some condition to the template, then it can look as follows: 

{* straight-forward implementation *}
{if:getCondition()}
<div>block</div>
{else:}
<div>else-clause block</div>
{end:}

{* shorthand construction for better readability *}
{* if getCondition() is true, then this <div> will be shown *
<div IF="{getCondition()}">block</div>

{* shorthand implementation for self-enclosed tags *}
<img IF="{getCondition()}" /> 

Flexy also supports comments, as you may have noted: 

{* I am Flexy comment*}

Foreach

Flexy supports walking through an array and generate content in a cycle: 

{* the straight-forward implementation *}
{foreach:getArrayData(),key,value}
	These are values from getArrayData() function. key: {key} and value: {value}
{end:}

{* shorthand implementation for better readability *}
<div FOREACH="getArrayData(),key,value">
	These are values from getArrayData() function. key: {key} and value: {value}
</div>
{* in this case foreach() will produce as many divs as many key-value pairs will be returned by getArrayData() method *}

{* shorthand implementation for self-enclosed tags *}
<img FOREACH="getArrayData(),key,value" id="{key}" src="{value}" /> 

If you want to use foreach() without key, you can do it as follows: 

{* the straight-forward implementation *}
{foreach:getArrayData(),value}
	<div>value: {value}</div>
{end:}

{* shorthand implementation for better readability *}
<div FOREACH="getArrayData(),value">
	value: {value}
</div>

{* shorthand implementation for self-enclosed tags *}
<img FOREACH="getArrayData(),value" src="{value}" /> 

Modifiers

Flexy outputs text from methods with applied htmlspecialchars() conversion. You might want to output text differently and Flexy supports output filters for that purpose. Here is a list of ones exist by default: 

{getOutput():h} {* disable htmlspecialchars() encoding *}

{getOutput():r} {* replace the quote symbol with the &quot; entity. *}

{getOutput():t} {* use htmlentities() encoding. *}

{getOutput():u} {* use urlencode() encoding. *}

{getOutput():nl2br}

{getOutput():ltrim}

{getOutput():rtrim}

{getOutput():trim}

You can also create output filter yourself. The mod below will give you an example.

Including templates and widgets

If you want to include another template into your one, you can do it as follows: 

<widget template="path/to/template.tpl" />

<widget template="path/to/another/template.tpl" foo="bar" />
{* in this case, {foo} variable in the path/to/another/template.tpl template will have value "bar" *}

The same way you can include viewer classes into templates: 

<widget class="\XLite\View\Header" />

<widget class="\XLite\View\Form\Countries\Countries" foo="baz" />
{* the same way, {foo} variable will have "baz" value in this viewer class *}

Finally, you can include view lists – view list is a collection of templates and viewer classes – into the template as follows: 

<list name="list-name" />
{* "list-name" must be replaced with the actual name of view list *}

Output filter example

This section introduces a module that will show you an example of creating Flexy output filter and then displaying some text with this output filter applied. For the sake of example, our output filter will remove spaces in a string given.

Implementation

We start with creating an empty module with developer ID Tony and module ID OutputFilterDemo. Then we create a target=output_filter page in customer area in this module. For that we create: 

  • an empty controller class \XLite\Module\Tony\OutputFilterDemo\Controller\Customer\OutputFilter (more about classnames in X-Cart);
  • a page viewer class \XLite\Module\Tony\OutputFilterDemo\View\Page\Customer\OutputFilter with the following content: 

    <?php
    // vim: set ts=4 sw=4 sts=4 et:
    
    namespace XLite\Module\Tony\OutputFilterDemo\View\Page\Customer;
    
    /**
     * Output filter page view
     *
     * @ListChild (list="center")
     */
    class OutputFilter extends \XLite\View\AView
    {
        /**
         * Return list of allowed targets
         *
         * @return array
         */
        public static function getAllowedTargets()
        {
            return array_merge(parent::getAllowedTargets(), array('output_filter'));
        }
    
        /**
         * Return widget default template
         *
         * @return string
         */
        protected function getDefaultTemplate()
        {
            return 'modules/Tony/OutputFilterDemo/page/output_filter/body.tpl';
        }
    }
    
  • an empty page template <X-Cart>/skins/default/en/modules/Tony/OutputFilterDemo/page/output_filter/body.tpl.

Now we need to decorate the \XLite\View\AView class and implement our Flexy output filter. We create the <X-Cart>/classes/XLite/Module/Tony/OutputFilterDemo/View/AView.php file with the following content: 

<?php
// vim: set ts=4 sw=4 sts=4 et:

namespace XLite\Module\Tony\OutputFilterDemo\View;

/**
 * Abstract widget
 */
abstract class AView extends \XLite\View\AView implements \XLite\Base\IDecorator
{
    protected function flexyModifierRemoveSpaces($string)
    {
        return str_replace(' ', '', $string);
    }
}

The flexyModifierRemoveSpaces() function is an implementation of our output filter, which will be called as follows: 

{string():removeSpaces}

In other words, in order to implement removeSpaces filter, we create the flexyModifier**RemoveSpaces**() method, so the modifier name is incapsulated right into the method’s name.

Now, it is time to test our output filter in action. We go to our <X-Cart>/skins/default/en/modules/Tony/OutputFilterDemo/page/output_filter/body.tpl template and define its content as follows: 

{#I am an example string.#:removeSpaces}

I am an example string is our test string.

Then, we have to re-deploy the store and once the process is finished, we should go to the cart.php?target=output_filter page and we will see the following result: 

As you can see all spaces have been removed from our test string.

Module pack

You can download this module example from here: https://dl.dropboxusercontent.com/u/23858825/Tony-OutputFilterDemo-v5_1_0.tar