PhpRiot
Become Zend Certified

Prepare for the ZCE exam using our quizzes (web or iPad/iPhone). More info...


When you're ready get 7.5% off your exam voucher using voucher CJQNOV23 at the Zend Store

Creating Your First Decorator

Zend_Form decorators all implement a common interface, Zend_Form_Decorator_Interface. That interface provides the ability to set decorator-specific options, register and retrieve the element, and render. A base decorator, Zend_Form_Decorator_Abstract, provides most of the functionality you will ever need, with the exception of the rendering logic.

Let's consider a situation where we simply want to render an element as a standard form text input with a label. We won't worry about error handling or whether or not the element should be wrapped within other tags for now -- just the basics. Such a decorator might look like this:

class My_Decorator_SimpleInput extends Zend_Form_Decorator_Abstract
{
    protected $_format = '<label for="%s">%s</label>'
                       . '<input id="%s" name="%s" type="text" value="%s"/>';

    public function render($content)
    {
        $element = $this->getElement();
        $name    = htmlentities($element->getFullyQualifiedName());
        $label   = htmlentities($element->getLabel());
        $id      = htmlentities($element->getId());
        $value   = htmlentities($element->getValue());

        $markup  = sprintf($this->_format, $name, $label, $id, $name, $value);
        return $markup;
    }
}

Let's create an element that uses this decorator:

$decorator = new My_Decorator_SimpleInput();
$element   = new Zend_Form_Element('foo', array(
    'label'      => 'Foo',
    'belongsTo'  => 'bar',
    'value'      => 'test',
    'decorators' => array($decorator),
));

Rendering this element results in the following markup:

<label for="bar[foo]">Foo</label>
<input id="bar-foo" name="bar[foo]" type="text" value="test"/>

You could also put this class in your library somewhere, inform your element of that path, and refer to the decorator as simply "SimpleInput" as well:

$element = new Zend_Form_Element('foo', array(
    'label'      => 'Foo',
    'belongsTo'  => 'bar',
    'value'      => 'test',
    'prefixPath' => array('decorator' => array(
        'My_Decorator' => 'path/to/decorators/',
    )),
    'decorators' => array('SimpleInput'),
));

This gives you the benefit of re-use in other projects, and also opens the door for providing alternate implementations of that decorator later.

In the next section, we'll look at how to combine decorators in order to create composite output.

Zend Framework