简体   繁体   中英

Access (in Controller) an unmapped field nestled in a form collection

In a form I have nestled a delete checkbox in a collection of Answers . (each answer have a delete checkbox so that I can delete any answer easily)

But I do not succeed to access the delete value from the controller

Here the code: First I populated my form with the Answers

 $Answers = $repository->liste_Answers_Child_Of_A_Question($question); // return a list of answers  
 $Answers = array('Answers' => $Answers);
 $form = $this->createform(new AnswersType(),$Answers);

AnswersType (with as)

$builder->add('Answers','collection', array('type'=> new AnswerType()));

AnswerType

$builder->add('Answer_text','text')
        ->add('delete','checkbox',array(
              'mapped'=> false,))

public function setDefaultOptions(OptionsResolverInterface $resolver)
{
    $resolver->setDefaults(array('data_class' => 'Site\BlogBundle\Entity\Answer'))
}

PS: I do not want to use the 'allow_delete' option combined with jquery.

You can always attach a 'data' attribute to your 'checkbox' field, like so:

$builder->add('Answer_text','text')
        ->add('delete','checkbox',array(
              'mapped'=> false,
              'data' => $options['data'] instanceof Answer ? $options['data']->getId() : true // where $options['data'] is your Answer entity. In case you have a "create" action for this type, $options['data'] is null, so we provide 'true' as an alternative
            )
        )

After this, in your controller after $form->handleRequest($request), in your $answer object you can do $answer->getDelete() and it will return the answer id.

If you need any more help with this, please let me know.
PS: This can also be achieved with form events via the FormEvents::POST_SET_DATA event.

EDIT: Cleaner solution

Instead of trusting the form type to give you the data, you can use, as mentioned above, event listeners like so:
First, remove the 'delete' field from your builder, and leave only 'answer_text'. Then, via a form listener(FormEvents::PRE_SET_DATA) you create the 'delete' field like so:

$builder->add('answer_text' ...); // initialy, you don't add the delete button

// then, when the form is populated with data, you also add the delete functionality
$builder->addEventListener(FormEvents::PRE_SET_DATA, function (DataEvent $event) use ($builder)
  {
    $form = $event->getForm(); // this is your form builder
    $data = $event->getData(); // this is your data entity, aka Answer

    /* Check we're looking at the right data/form */
    if ($data instanceof Answer)
    {
        $answerId = $data->getId(); // here, you no longer have to validate the id. It is automaticaly set to null by the data binding provided by the form.

        $form->add('delete', 'checkbox', [
            'mapped'=> false,
            'data' => $answerId
        ]);
    }
  });
}

Let me know if this worked for you.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM