jeudi 2 avril 2015

Detect in Symfony2 TypeExtension if a type is a prototype root

Form type extension problem


I'm writing a FormExtension that apply to all form type (experimenting with angularjs... another story :), but I need to detect at build time if a FormType is used as prototype root.



class MyFormTypeExtension extends AbstractTypeExtension
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
if (true /* === $iAmPrototypeRoot*/) {
$builder->setAttribute('i_need', 'magic');
}
}
}


My problem is that I need to set some attributes that I need later, but setAttribute is (or seems to be) available only at build time.


So far...


I've checked the source code for CollectionType and found this:



class CollectionType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
if ($options['allow_add'] && $options['prototype']) {
$prototype = $builder->create($options['prototype_name'], $options['type'], array_replace(array(
'label' => $options['prototype_name'].'label__',
), $options['options']));
$builder->setAttribute('prototype', $prototype->getForm());
}

// [...]
}
}


So I know that I can override this template and add a "fake" option is_prototype to the options, but this is a bit hackish since I'm overriding (not extending) the default CollectionType. Example:



class CollectionType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
if ($options['allow_add'] && $options['prototype']) {
$prototype = $builder->create($options['prototype_name'], $options['type'], array_replace(array(
'label' => $options['prototype_name'].'label__',
), $options['options'], array(
'is_prototype' => true
)));
$builder->setAttribute('prototype', $prototype->getForm());
}

// [...]
}
}


Which solution?


Up 'til now, the best solution I see is to add the 'is_prototype' to the collection option option (no pun :); but this should persist if the user override the option (maybe a Normalizer?)


Aucun commentaire:

Enregistrer un commentaire