Main  /  Edit  /  History  /   /  Users Area

Templates: Flow Control (v 1.x)

Conditions

Syntax

Begin or continue conditional statement:

( 'if' | 'elif' ) [ 'not' ] [ 'empty' ] ( VARIABLE | 'rtl' )
( 'if' | 'elif' ) '(' any-c++-expression ')'

Else block:

'else'

Each if/else block should be ended with end statement. For example:

<% if not empty username %>
  <h1>Hello <% username %></h1>
<% else %>
  <h1>Hello Visitor</h1>
<% end %>
<% if ( content.n % 2==0 ) %>
  <% n %> is odd.
<% elif ( content.n % 3 ==0) % >
  <% n %> can be divided by 3 without reminder.
<% end %>

Description

This is ordinary if/else if statement. You can specify following conditions:

Foreach block

Syntax

Major loop:

'foreach' NAME ['as' IDENTIFIER ] [ 'rowid' IDENTIFIER [ 'from' NUMBER ] ] [ 'reverse' ] 'in' VARIABLE 

In case of empty collection:

'empty'

Specify central body:

'item'
'separator'

For example:

<% foreach student in students %>
  <ul>
  <% item %>
     <li><% student.id %>, <% student.name %></li>
  <% end %>
  </ul>
<% empty %>
  <h2>No students</h2>
<% end %>

You can specify delimiter for elements between separator and item block:

<% foreach student in students %>
<% separator %>, <% item %><% student.name %><% end %>
<% end %>

Would generate a list like: "Ron, John, Moshe"

Description

foreach loop creates a for loop that iterates any STL collection. The given name is a reference to the type returned by iterator. For example, if students is std::list<student_t> then student in above example is defined as student_t &student.

For example

<% foreach line rowid num from 1 in code %>
<% item %><%= num %>:<%=line%><% end %>
<% end %>

Note: reverse and rowid are supported starting from CppCMS 0.99.10

Type detection

Template system uses one of following method for automatic type detection:

  1. C++0x auto
  2. C++0x decltype
  3. GCC's style typeof or __typeof__

At least one of them should be supported by the compiler in order to provide correct template generation without using as keyword.

But some compilers, most noticeable is MSVC8, MSVC9 still not support automatic type detection, thus, specific iterator type should be explicitly specified.

For example:

<% foreach student as students_type::iterator in students %>

Would give you correct solution for MSVC compiler and student would a variable of type students_type::iterator::value_type

Body

empty statement is equivalent to "else" so:

<% foreach a in b %>
<ul>
<% item %><% a %><% end %>
</ul>
<% empty %>
   nothing
<% end %>

Is generated into code like:

if(!content.b.empty()) {
  out()<<"<ul>";
  for(auto a_it=content.b.begin();a_it!=content.b.end();++a_it) {
    auto &a=*a_it;
    out()<<a;
  }
  out()<<"</ul>";
}else{
  out()<<"nothing";
}

You must provide <% item %>...<% end %> block for any foreach statement. If separator is used it should be added between separator and item blocks.

Custom form rendering

CppCMS forms system provides several options for rendering form widgets, but sometimes custom rendering may be needed. In this case, foreach can be used to iterate over cppcms::form as over ordinary collation.

For example, rendering with "new line" separator:

<% foreach w in form %>
  <% separator %><br/><% item %>
    <% if w.has_message() %><% w.message() %>:<% end %>
    <% form input w %>
    <% if not w.valid() %>:<% w.error_message() %><% end %>
  <% end %>
<% end %>

Caching Elements

Syntax

The cached block begins with cache statement

'cache' ( VARIABLE | STRING ) [ 'for' NUMBER ] ['on' 'miss' VARIABLE() ] [ 'no' 'triggers' ] [ 'no' 'recording' ]

and ends with end statement.

For example

<% cache "sidebar" for 10 %> 
  ...
<% end cache %>

Description

This block allows to cache parts of rendered templates. The first parameter ( VARIABLE | STRING ) is mandatory and defines the key that is used to retrieve the frame from the cache. It should be either constant predefined string or some variable stored in the context.

Adding Cache Triggers

Strictly speaking this is not flow block but it is strongly connected to the cache block described above.

trigger ( STRING | VARIABLE )

Says to add trigger to the current context effectively calling cache().add_trigger(value)

For example:

<% cache "foo" %>
   ...
   <% trigger "bar" %>
<% end cache %>

Now rising bar as trigger would invalidate foo object.

It is useful for some complex relations where you want to add triggers to cached frames explicitly.

About

CppCMS is a web development framework for performance demanding applications.

Support This Project

SourceForge.net Logo

Поддержать проект

CppCMS needs You


Navigation

Main Page



Valid CSS | Valid XHTML 1.0