Template code Chunk output
{#example_1}
{!--
  -- Starting in 2.1, you don't need to box your objects in
  -- DataCapsule's - you can just bind them directly into the template!
  --
  -- If all you want from the object are its non-private member
  -- fields, you can now bind it to a tag variable directly with set().
  --
  -- CamelCase fieldnames are converted to lowercase_with_underscores.
  --
  -- Primitives (int, long, double, float, etc.) are converted to Strings.
  --
  -- Boolean values are the string "TRUE" if true, or null/undefined
  -- when false, to facilitate {% if ($x.is_something) %} branching.
  --
  -- Arrays and Lists can be looped over with {.loop in $obj.some_list}
  --
  -- Other types of fields (besides String) are treated as nested POJOs,
  -- so you can reference a child object's properties from the template
  -- as you would expect:  {$obj.child.child_property}
  -- 
  -- Non-primitives are rendered using the object's .toString() method
  -- if one is defined.  For finer control over rendering, write a
  -- custom filter: extend com.x5.template.filters.ObjectFilter and
  -- register the filter on your Theme.
  --
  -- Object methods are *not* callable from the template, in keeping
  -- with the read-only nature of Chunk templates.
  --}

<ul>
 <li> {$obj.name}</li>
 <li> {$obj.rank}</li>
 <li> {$obj.serial}</li>
 <li> {% if ($obj.is_active) %}Active duty{% else %}Retired{% endif %}</li>
 <li> Status: {$obj.is_active|ondefined(Active):Inactive}</li>
 <li> Superior: {$obj.boss.name}</li>
 <li> Pi to two places is {% $obj.pi|sprintf(%.2f) %}</li>
</ul>

{#}
Theme theme = new Theme("examples");

// Fetch template from this file: themes/examples/pojo.chtml
// Inside that file there is a template "snippet" named #example_1
Chunk html = theme.makeChunk("contrib#example_1");

Thing pojo = new Thing("Bob Roberts", "Major", "AB231323");

// Bob is his own boss. Circular references don't tie up the interpreter.
pojo.setBoss(pojo);

html.set("obj", pojo);

html.render( out );

//...

// Annotation is optional.  Usually Chunk can figure out if a class is
// POJO-style (public fields) or bean (private fields).
@AccessAsPojo
static class Thing
{
    String name, rank, serial;
    boolean isActive;
    double pi = Math.PI;
    Thing boss;

    Thing(String name, String rank, String serial)
    {
        this.name = name;
        this.rank = rank;
        this.serial = serial;
        this.isActive = true;
    }

    public void setBoss(Thing boss)
    {
        this.boss = boss;
    }
}

<ul>
 <li> Bob Roberts</li>
 <li> Major</li>
 <li> AB231323</li>
 <li> Active duty</li>
 <li> Status: Active</li>
 <li> Superior: Bob Roberts</li>
 <li> Pi to two places is 3.14</li>
</ul>


  • Bob Roberts
  • Major
  • AB231323
  • Active duty
  • Status: Active
  • Superior: Bob Roberts
  • Pi to two places is 3.14
Template code Chunk output
{#example_2}
{!--
  -- Similar template-binding is available for java beans.
  --
  -- Standard accessors like getFullName() are exposed in the template
  -- as {$tag.full_name} - camelCase converts to lower_with_underscores
  -- with the "get" prefix removed.
  --
  -- Don't confuse this for the ability to make method calls from the
  -- template. The accessors/getters are called once during the render
  -- and the template sees a frozen copy of an object with static
  -- properties.
  --
  -- Boolean properties with accessors like isActive() appear in the
  -- template as {$tag.is_active} but only when true, with "TRUE" value.
  --
  -- This is because most typed values are coerced to strings in
  -- template evaluation, and if-tag conditional expressions work by
  -- treating NULL/undefined as false, and non-null/defined as true.
  --
  --
  -- Primitives are converted to Strings.
  --
  -- Arrays and Lists are converted to LIST types that can be looped in.
  --
  -- Nested objects are assumed to be beans as well.  You may annotate
  -- your bean classes with @AccessAsBean if they are misidentified as
  -- POJOs, or use chunk.setToBean("obj", myBean) to explicitly hint
  -- that a tag value is a bean.
  --}

<ul>
 <li> {$bean.name}</li>
 <li> {$bean.rank}</li>
 <li> {$bean.serial}</li>
 <li> {% if ($bean.is_active) %}Active duty{% else %}Retired{% endif %}</li>
 <li> Status: {$bean.is_active|ondefined(Active):Inactive}</li>
 <li> Superior: {$bean.boss.name}</li>
 <li> Pi to two places is {% $bean.pi|sprintf(%.2f) %}</li>
</ul>

{#}
Theme theme = new Theme("examples");

// Fetch template from this file: themes/examples/pojo.chtml
// Inside that file there is a template "snippet" named #example_1
Chunk html = theme.makeChunk("contrib#example_1");

ThingBean bean = new ThingBean();
bean.setName("Bob Roberts");
bean.setRank("Major");
bean.setSerial("AB231323");
bean.setActive(true);

// Bob is his own boss. Circular references don't tie up the interpreter.
bean.setBoss(bean);

// You can also just use ".set(...)" as long as your class is annotated
// with @AccessAsBean or has all private fields.
html.setToBean("bean", bean);

html.render( out );

//...

// Annotation is optional.  Usually Chunk can figure out if a class is
// POJO-style (public fields) or bean (private fields, getters).
@AccessAsBean
static class ThingBean implements java.io.Serializable
{
    private String name, rank, serial;
    private boolean isActive;
    private double pi = Math.PI;
    private ThingBean boss;

    public ThingBean() {}

    public String getName()
    {
        return this.name;
    }

    public String getRank()
    {
        return this.rank;
    }

    public String getSerial()
    {
        return this.serial;
    }

    public boolean isActive()
    {
        return this.isActive;
    }

    public double getPi()
    {
        return this.pi;
    }

    public ThingBean getBoss()
    {
        return this.boss;
    }

    public void setName(String name)
    {
        this.name = name;
    }

    public void setRank(String rank)
    {
        this.rank = rank;
    }

    public void setSerial(String serial)
    {
        this.serial = serial;
    }

    public void setActive(boolean isActive)
    {
        this.isActive = isActive;
    }

    public void setPi(double pi)
    {
        this.pi = pi;
    }

    public void setBoss(ThingBean boss)
    {
        this.boss = boss;
    }

}

<ul>
 <li> Bob Roberts</li>
 <li> Major</li>
 <li> AB231323</li>
 <li> Active duty</li>
 <li> Status: Active</li>
 <li> Superior: Bob Roberts</li>
 <li> Pi to two places is 3.14</li>
</ul>


  • Bob Roberts
  • Major
  • AB231323
  • Active duty
  • Status: Active
  • Superior: Bob Roberts
  • Pi to two places is 3.14