views:

95

answers:

2

I do not understand how I can send an array with options to my custom filter. Can you please help me?

class Core_Filter_MyFilter implements Zend_Filter_Interface

{   
    public function __construct($options = null)
    ...
}
class Blog_Form_Comment extends Zend_Form
{
    public function init()
    {
        $this->setMethod('post');
        $this->addElementPrefixPath('Core_Filter', 'Core/Filter/', 'filter');
     $this->addElement('textarea', 'entry', array(
      'filters' => array(MyFilter)));

I have tried several different ways and I have only managed to send a string as a option to the constructor, but I need to be able to send an array.

+3  A: 

Instead of relying on the PluginLoader to load your filter class from the string name representation, you can pass an instance of your filter directly to the element.

    $this->addElement('textarea', 'entry', array(
            'filters' => array(new Core_Filter_MyFilter($filterOptions))
    ));

This works with the addFilter() method as well.

Also, while it is not mentioned in the Reference Manual, filters support a similar syntax to validators. So, utilizing the plugin loader, you can use the short name, and an array of arguments to pass to the constructor, like so:

    $this->addElement('textarea', 'entry', array(
            'filters' => array(
               array('MyFilter', array($filterOptions)
             )
    ));

However, note that relying on the plugin loader in this fashion can produce unnecessary overhead if you are in a performance critical situation. The form element relies on PHP's reflection system to create the filter instance and pass it your options. PHP's runtime reflection is not exactly known for speed. This may or may not be a micro/premature optimization, and I'm not suggesting either way, just listing the relevant caveats.

jason
Thank you for the great answer.
unkown
+1  A: 

The Zend_Form_Element::addFilters() function can help you understand this process a bit.

The array passed contains one filter per element. If that element is a string or an instanceof Zend_Filter_Interface it passes it along to addFilter() with no 'options'

If the element is an array, the first element of that becomes the filter name, the second element becomes the options. The options array is used in _loadFilter() which passes the options array to the constructor of the filter. An example of using a PregReplace filter:

//  Zend_Filter_PregReplace::__construct($matchPattern = null, $replacement = null)
$this->addElement('textarea', 'entry', array(
  'filters' => array(
     array('PregReplace', array('/test/', 'passed'))
   ),
);
// equivalent to:
$this->addElement('textarea', 'entry', array(
  'filters' => array(
     new Zend_Filter_PregReplace('/test', 'passed');
   ),
);

If you want to pass an array as a first argument, you'll need to wrap it in another array:

$this->addElement('textarea', 'entry', array(
   'filters'=>array(
       array('MyFilter', array(array(
          'option1'=>'test',
          'option2'=>'test',
       ))),
   ),
);
gnarf
Thank you for the help
unkown