Home

Castle Stronghold

FormHelper

The FormHelper allows you to output Html Input elements using the conventions necessary to use the DataBinder on the server side. It also queries the objects available on the context to automatically populate values correctly, saving you the burden of filling inputs, selects, checkboxes and radios.

General concept

The helper is inspired on two exquisite works: the Ruby on Rails' FormHelper and the Apache Jakarta Taglibs. The idea is to generate html form elements while:

When using the FormHelper you specify a target through a string. The target is evaluated and if the object is available in the context then the evaluation result is used to provide the correct output. For a simple text input element, the evaluated value will be the value of the textbox.

Getting started

Using the FormHelper is easy and in a few minutes you will understand how it works. Just remember that it requires that the controller and the view work together.

The goal is to generate proper Html elements that can be easily databound on the controller side. The most trivial case is binding single values. For example, you can have a view like the following (using NVelocity View Engine):

 

<form action="Index.rails" method="post">

$FormHelper.TextField("name")

$FormHelper.TextField("address")

</form>
${FormHelper.TextField("name")} ${FormHelper.TextField("address")}

Whenever this view is rendered, the FormHelper's TextField method will be invoked. The first thing it does is extract the root target. In the case above the targets are not chained, so the roots will be name and address.

After that it will search in the context dictionaries for the roots, in the following order:

If it finds the entry, it will extract the value and use it. If it doesn't find the entry, no value will be set on the html element.

Suppose the action using the view above (the form definition) is the following:


public void Index()
{
}

For this case, the html output will be:


<form action="Index.rails" method="post">

<input type="text" id="name" name="name" value="" />

<input type="text" id="address" name="address" value="" />

</form>

Note the "value" property of both input elements is blank.

However, if the action was:


public void Index()
{
    PropertyBag.Add("name", "hammett");
    PropertyBag.Add("address", "pereira leite, 44");
}

Then the FormHelper would have the values filled:


<form action="Index.rails" method="post">

<input type="text" id="name" name="name" value="hammett" />

<input type="text" id="address" name="address" value="pereira leite, 44" />

</form>

The support for autmatically populating Html elements goes beyond input fields. See below for more information on the FormHelper.

Complex objects

Consider a different action code now:


public void Index()
{
    PropertyBag.Add("contact", new Contact("john", "some address", "phone number") );
}

A view for this

 

<form action="Index.rails" method="post">

$FormHelper.TextField("contact.name")

$FormHelper.TextField("contact.address")

$FormHelper.TextField("contact.phone")

</form>
<#cdata-section>
${FormHelper.TextField("contact.name")} ${FormHelper.TextField("contact.address")} ${FormHelper.TextField("contact.phone")}

The FormHelper will find the contact entry in the PropertyBag, and then find the properties name, address and phone. It will extract the values from the item in the PropertyBag and render the view accordingly:


<form action="Index.rails" method="post">

<input type="text" id="contact_name" name="contact.name" value="john" />

<input type="text" id="contact_address" name="contact.address" value="some address" />

<input type="text" id="contact_phone" name="contact.phone" value="phone number" />

</form>

Arrays

Arrays are also supported. Suppose you have the following action code:


public void Index()
{
    PropertyBag.Add("list", new string[] 
    {
        "value 1", "value 2"
    } );

    PropertyBag.Add("contacts", new Contact[] 
    { 
        new Contact("john", "address 1", "phone number 1"),
        new Contact("mary", "address 2", "phone number 2")
    } );
}

In this case you have to use the indexed name convention as the target so FormHelper can know from which index it should extract the value:

 

<form action="Index.rails" method="post">

$FormHelper.TextField("list[0]")
$FormHelper.TextField("list[1]")

$FormHelper.TextField("contacts[0].name")
$FormHelper.TextField("contacts[0].address")
$FormHelper.TextField("contacts[0].phone")

$FormHelper.TextField("contacts[1].name")
$FormHelper.TextField("contacts[1].address")
$FormHelper.TextField("contacts[1].phone")

</form>

<form action="Index.rails" method="post">

${FormHelper.TextField("list[0]")}
${FormHelper.TextField("list[1]")}

${FormHelper.TextField("contacts[0].name")}
${FormHelper.TextField("contacts[0].address")}
${FormHelper.TextField("contacts[0].phone")}

${FormHelper.TextField("contacts[1].name")}
${FormHelper.TextField("contacts[1].address")}
${FormHelper.TextField("contacts[1].phone")}

</form>

The FormHelper will use the index value to find the correct entry. It will generate something like the following:


<form action="Index.rails" method="post">

<input type="text" id="list_0_" name="list[0]" value="value 1" />
<input type="text" id="list_1_" name="list[1]" value="value 2" />

<input type="text" id="contact_0_name" name="contact[0].name" value="john" />
<input type="text" id="contact_0_address" name="contact[0].address" value="address 1" />
<input type="text" id="contact_0_phone" name="contact[0].phone" value="phone number 1" />

<input type="text" id="contact_1_name" name="contact[1].name" value="mary" />
<input type="text" id="contact_1_address" name="contact[1].address" value="address 2" />
<input type="text" id="contact_1_phone" name="contact[1].phone" value="phone number 2" />

</form>

API documentation

You may also consult the API documentation for the FormHelper.

Site map

The following is a list of the documents related to FormHelper:

Google
Search WWW Search castleproject.org