Matthew Weier O'Phinney schreef:
-- fire-eyed-boy <[email protected]> wrote
(on Wednesday, 01 April 2009, 10:54 AM -0700):
Eventhough I see it's use; in my current setup, setElementsBelongTo()
doesn't offer me the solution I was hoping for. But maybe I am overlooking
something.

Yep. You're using the ViewScript decorator to render your elements, so
you need to do a couple of things manually.

First, for each element, you need to do the following:

    // simplified -- you should refactor to cache the form name
    $element->setBelongsTo($form->getElementsBelongTo());

This is done implicitly in the FormElements decorator -- but since
you're using ViewScript on your form, you have to do it manually. I
would do this at the start of my view script before rendering anything,
using something like this:
$belongsTo = $this->element->getElementsBelongTo();
    foreach ($this->element->getElements() as $element) {
        $element->setBelongsTo($belongsTo);
    }

Second, when rendering your elements, if you don't use the ViewHelper
decorator, you'll need to fetch the name and/or ID manually:

    $element->getFullyQualifiedName(); // gets the fully qualified name
    $element->getId();                 // will use the FQN to create the id


Hi Matthew,

Thanks for the response.

Ok, this basically solves my first problem. But to tell you the truth this doesn't stray too far from generating my own unique id's. Although your example is slightly more elegant.

The thing is, unfortunately this doesn't solve my second problem. That is, how to automatically validate the form(s) in my Controller.

Let's say I've generated 10 delete forms with their own namespaces (like you demonstrated) based on my generic form. In my controller I then need some way to automatically detect the namespaces again.


$myForm = My_Generic_Delete_Form();
if( $myForm->isValid( $request->getPost() ) )
{
 // will always fail
 // because the namespace is unknown to my My_Generic_Delete_Form
}

Ideally, I should be able to automatically re-assign the namespace to $myForm before I validate it.

Any ideas on how I could achieve this in a sleek manner (in stead of analyzing the POST data in some cumbersome manner)?

Thanks again.




In short (for examplary purposes) this roughly is what I have:


=====================

## a few generic forms like this one:

class Form_ResourceDelete extends Zend_Form
{
        protected $_name = 'resourceDelete';

        public function init()
        {
                $this->setName( $this->_name )
                        ->setMethod( 'post' )
                        ->setAttribs( array( 'accept-charset' => 'utf-8' ) )
                        ->setDecorators( array(
                                'PrepareElements',
                                array( 'ViewScript', array( 'viewScript' =>
'resource/partials/form-delete.phtml' ) ),
                                'Form'
                        ) );

                $decorators = array(
                'ViewHelper',
                'Label',
                'Errors'
                );

                $resourceId = new Zend_Form_Element_Hidden( 'resourceId' );

                $resourceId->setDecorators( $decorators ); // I add a few 
validators too

                $submit = new Zend_Form_Element_Button( 'submit' );
                $submit->setDecorators( $decorators )
                                ->setAttribs( array( 'type' => 'submit', 'escape' 
=> false ) );
        }

        public function setResourceId( $resourceId )
        {
                $this->resourceId->setValue( $resourceId );
                $this->_updateElements();
                return $this;
        }

        protected function _updateElements()
        {
                $this->setElementsBelongTo( $this->_name . '_' .
$this->resourceId->getValue() );
                // actually much more is happening here, so this function isn't 
as
redundant as it looks
        }
}


## a ViewScript decorator along the lines of:

<?
        $form = $this->element;
        $form->setAction( $this->url( array( 'module' => 'cms', 'controller' =>
'page-manager', 'action' => 'delete' ) ) );
?>
<div>
        <?= $form->resourceId->renderViewHelper(); ?>
        <?= $form->submit->renderViewHelper(); ?>
</div>


## a partialLoop viewhelper that iterates through all pages along the lines
of:

<?
        $resourceDeleteForm = new Form_ResourceDelete();
?>
<div class="page">
        <?= $this->title ?>
        
                <?= $resourceDeleteForm->setResourceId( $this->id ); ?>
                // and then some other resource option forms such as "sort up" "sort 
down"
"edit" etc....
        
</div>

=====================


Now, two problems occur.
One: it seems I have to clone the Form in the partialLoop viewhelper in
order to let the setElementsBelongTo() have effect. Otherwise it simply
renders all forms with namespaces containing the first resourceId I assigned
in the partialLoop's first iteration (see _updateElements method in my
Form).

Two: I have a generic deleteAction() in my controller which validates the
form:

$deleteForm = new Form_ResourceDelete();
if( $deleteForm->isValid( $formData ) )
{
// etc
}

But this doesn't work of course, since I am unable to determine the
namespace of the Form up front. Otherwise I could do setElementsBelongTO(
$namespace ) right before validating.
So, I am kind of stuck here. If you, or anyone else, has some pointers on
how I could address this issue, I'ld love to here it.

Thanks up front.



Matthew Weier O'Phinney-3 wrote:
-- [email protected] <[email protected]> wrote
(on Wednesday, 01 April 2009, 12:59 PM +0000):
I wasn't aware of the setElementsBelongTo method. I will look into that.
It was created in large part for this very purpose. A common pattern in
PHP is to namespace your forms using array notation, and this was built
into Zend_Form.

Are you sure that it will prefix elements with "<name>-" is stead of
"<name>_"
(dash instead of underscore?). If so, I believe this is not Javascript
compliant (or at least not cross platform/browser). To my knowledge some
(or
maybe all?) Javascript engines have trouble with addressing elements with
dashes in their id's, since a dash is simply a minus sign.

So I would not be able to do:
document.forms[0].hidden-elements-id.

I know this maybe a little oldskool, and it would be possible with DOM:
document.getElementById( 'hidden-elements-id' );
Dashes are acceptable in DOM IDs (the HTML specification specifically
lists that as a valid ID character). Typical JS usage anymore uses
getElementById() -- or, even more typically, proxies to that via
library-specific mechanisms; I cannot remember the last time I used
document.forms to retrieve form elements, honestly.

<snip>

--
Matthew Weier O'Phinney
Software Architect      | [email protected]
Zend Framework          | http://framework.zend.com/


--
View this message in context: 
http://www.nabble.com/Disable-id-attribute-for-form-elements--tp22821260p22832122.html
Sent from the Zend Framework mailing list archive at Nabble.com.



Reply via email to