I have created a FormType class called BookType. The method for generating the form is:
/**
* #param FormBuilderInterface $builder
* #param array $options
*/
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('name', 'text', array('required'=>$this->searchForm))
->add('author', 'text', array('required'=>$this->searchForm))
->add('genre', 'text', array('required'=>$this->searchForm));
if(!$this->searchForm) {
$builder
->add('picture', 'text', array('required' => false));
}
$builder
->add('description', 'text', array('required'=>$this->searchForm))
->add('submit', 'submit', array('required'=>$this->searchForm))
;
}
However, whenever I try to access this with the following code:
$book = new Book();
$form = $this->createForm(
new BookType(true),
$book,
[
'action'=> $request->getUri()
]
);
I am seeing the following error message:
The option "required" does not exist. Known options are: "attr", "auto_initialize", "block_name", "disabled", "label", "translation_domain", "validation_groups".
As far as I am aware from the various tutorials I have read, this should be a completely valid parameter. Am I wrong here?
I think error is occurring here:
->add('submit', 'submit', array('required'=>$this->searchForm));
Since 'submit' field does not have 'required' option.
Related
I've embedded forms with CollectionType:
$builder->add('battlePages', CollectionType::class, [
'label' => 'Battle Pages',
'entry_type' => BattlePageCollectionType::class,
'error_bubbling' => false,
'constraints' => [
new Valid(),
],
]);
and 'battlePages' is an ArrayCollection with many elements.
public function buildForm(FormBuilderInterface $builder, array $options) {
/** #var BattlePage $entity */
$entity = $builder->getData();
...
But '$entity' is empty however collection was walking through.
My goal would be to get BattlePage entity's data in the 'BattlePageCollectionType' which is my second in examples ($entity).
Anybody had have similar issues?
The $builder->getData(); method doesn't return an entity.
You should use Form Events
Example with PRE_SET_DATA event:
$builder->addEventListener(FormEvents::PRE_SET_DATA, function (FormEvent $event) {
$entity = $event->getData();
$form = $event->getForm();
$form->add('someField', TextType::class);
});
I'm looking to display 2 instances of the same form inside another form with twig but I can't figure out how.
Here my first form:
/**
* #param FormBuilderInterface $builder
* #param array $options
*/
public function buildForm(FormBuilderInterface $builder, array $options)
{
// build form
$builder
->add('contenu', 'text', array(
'attr' => array('maxlength' => 255),
'empty_data' => "Question par défaut"
))
->add('file', 'file', array(
'attr' => array('accept' => "image/png, image/jpeg")
))
->add('contenuQuestion', 'collection', array(
'type' => new QuizzReponseType(), // here the embedded form
'allow_add' => true,
'allow_delete' => true,
'cascade_validation' => true,
))
;
}
with in the entity:
/**
* #ORM\ManyToMany(targetEntity="OC\QuizzBundle\Entity\QuizzReponse", cascade={"remove", "persist"})
*/
private $contenuQuestion;
function __construct() {
$this->contenuQuestion = new ArrayCollection();
}
Here the embedded form:
/**
* #param FormBuilderInterface $builder
* #param array $options
*/
public function buildForm(FormBuilderInterface $builder, array $options)
{
// build form
$builder
->add('contenu', 'text', array(
'attr' => array('maxlength' => 50),
'empty_data' => "Réponse par défaut"
))
->add('file', 'file', array(
'attr' => array('accept' => "image/png, image/jpeg")
))
;
}
The problem is in my view. I want to have 2 instances of the embedded form but the collection seems empty.
It's working well with only one embedded form (NB: my first form is also inside another form but it's not relevant for my question):
// embedded form content field
{{ form_widget(form.contenuQuizz.vars.prototype.contenuQuestion.vars.prototype.contenu) }}
And I'm looking to do something like that:
// embedded form1 content field
{{ form_widget(form.contenuQuizz.vars.prototype.contenuQuestion.0.vars.prototype.contenu) }}
// embedded form2 content field
{{ form_widget(form.contenuQuizz.vars.prototype.contenuQuestion.1.vars.prototype.contenu) }}
It looks like the problem is that the collection is not initialized but I'm not sure.
Is there a way to do that ? (with twig and not JavaScript if possible)
Thanks in advance,
Maugun
I have made a simple Symfony form with only an email field. This form is used to send a document to a user. The form is not linked to any entity. Therefore the formtype looks like this:
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('email', 'email', array(
'mapped' => false
))
->add('save', 'submit');
}
So the email field is not mapped and this works fine.
Now I want to validate the email address like I do with other forms where I have the following asserts:
#Assert\Email(message = "email.not_valid", checkMX = true)
As this formtype has no entity I'm wondering how I can add the checkMX to the email field?
https://symfony.com/doc/current/form/without_class.html#form-option-constraints
use Symfony\Component\Validator\Constraints\Email;
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('email', 'email', array(
'mapped' => false,
'constraints' => array(
new Email(array('checkMX' => true)),
),
))
->add('save', 'submit');
}
EDIT checkMx -> checkMX
I have the following form that contains data from the database it still WIP ( i'm missing a few fields that i didn't add yet).
The form loads data in the first select and based on that select i use ajax to populate a second select with options based on the first select ( basically the associations to the selected value). And from there again another select with certain options and so on and at the end when i submit the form i want to generate a report from database based on the data.
For the moment i'm stuck with the second field because i always get an error:
This value is not valid.
The form class:
/**
* #param FormBuilderInterface $builder
* #param array $options
*/
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('survey', EntityType::class, [
'class' => SurveyManager::class,
'placeholder' => 'Choose option',
'attr' => [
'class' => 'field-change',
],
])
->add('headquarter', ChoiceType::class, [
'choices' => [],
])
->add('submit', SubmitType::class, [
'label' => 'Save',
])
;
}
I'm not reall sure how to fix the error or how should i handle this type of form. Can you help me out guys ?
Based on the answer i did this
$builder->addEventListener(
FormEvents::PRE_SUBMIT,
function (FormEvent $event) {
$form = $event->getForm();
$data = $event->getData();
$form->add('headquarter', EntityType::class, [
'class' => HeadQuarterManager::class,
'query_builder' => function(HeadQuarterManagerRepository $er) {
return $er->getHeadquarter($data['survey']);
},
]);
}
);
But i'm getting this error:
Notice: Undefined variable: data
Not really sure how to pass the data to the getHeadquarter method so i can return an array of id => name for the select.
When you run the function $form->isValid(), it checks against the form it built in the buildForm function. Any extra fields/value that aren't there will cause this error.
You can change this behaviour by using form events.
In the end this is how i did it:
/**
* #param FormBuilderInterface $builder
* #param array $options
*/
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('survey', EntityType::class, [
'class' => SurveyManager::class,
'attr' => [
'class' => 'field-change',
],
])
->add('submit', SubmitType::class, [
])
->addEventListener(
FormEvents::PRE_SUBMIT,
function (FormEvent $event) {
$form = $event->getForm();
$data = $event->getData();
$modifier = $data['survey'];
$form->add('headquarter', EntityType::class, [
'class' => HeadQuarterManager::class,
'query_builder' => function (HeadQuarterManagerRepository $er) use ($modifier) {
return $er->getHeadquarter($modifier);
},
]);
}
);
}
I'm on a problem related to a Symfony2 application which i'm building. The problem concerns an article (News) linked to one or many pictures (Illustration). It seems pretty simple. But i'm stacking on the controller which should persist the News, the Illustration and uploading the picture file.
My News form type:
namespace Fcbg\NewsBundle\Form\Type;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
class NewsType extends AbstractType
{
public function buildForm( FormBuilderInterface $builder, array $options )
{
$builder
->add('date', 'date')
->add('titre', 'text')
->add('contenu', 'textarea')
->add('publication', 'checkbox', array('required' => false))
->add('type', 'entity', array( 'class' => 'FcbgNewsBundle:Illustration', 'property' => 'value', 'multiple' => true ));
}
public function getName()
{
return 'News';
}
}
My picture(s) form type:
namespace Fcbg\NewsBundle\Form\Type;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolverInterface;
class IllustrationType extends AbstractType
{
public function buildForm( FormBuilderInterface $builder, array $options )
{
$builder
->add('file', 'file');
}
public function setDefaultOptions(OptionsResolverInterface $resolver)
{
$resolver->setDefaults(array(
'data_class' => 'Fcbg\NewsBundle\Entity\Illustration',
'cascade_validation' => true,
));
}
public function getName()
{
return 'News';
}
}
My controller action:
public function addAction()
{
//link works properly I think
$news = new News();
$illustration = new Illustration();
$illustration->setNews($news);
$news->addIllustration($illustration);
$form = $this->createForm(new NewsType(), $news);
$request = $this->get('request');
if ($request->getMethod() == 'POST') {
$form->bind($request);
if ($form->isValid()) {
$doctrine = $this->getDoctrine();
$newsManager = $doctrine->getManager();
$newsManager->persist($news);
$newsManager->persist($illustration);
$newsManager->flush();
return $this->redirect(...);
}
}
return $this->render('base.html.twig',
array(
'content' => 'FcbgNewsBundle:Default:formulaireNews.html.twig',
'form' => $form->createView(),
'name' => "add a news"
)
);
}
The error i get on the execution:
Entities passed to the choice field must be managed. Maybe persist them in the entity manager?
The problem here is that my entity gets a method called "getIllustrations()" which returns logically an arrey of Illustration. So i'm not able to understand this error/question. I assume that my "illustration should be a file field and not a choice field...
Any idea about how i can go further? thx a lot!
I think the problem is that you are using the 'entity' form field here:
->add('type', 'entity', array( 'class' => 'FcbgNewsBundle:Illustration', 'property' => 'value', 'multiple' => true ));
and this type of form field acts as a choice and it's used to work with elements created in the database. You can see this in http://symfony.com/doc/current/reference/forms/types/entity.html
A possible solution could be use the "prototype" like here http://symfony.com/doc/current/cookbook/form/form_collections.html#cookbook-form-collections-new-prototype
where you could have:
public function buildForm( FormBuilderInterface $builder, array $options )
{
$builder
->add('date', 'date')
->add('titre', 'text')
->add('contenu', 'textarea')
->add('publication', 'checkbox', array('required' => false))
->add('type', 'collection', array(
'type' => new IllustrationType(),
'allow_add' => true,
));
}
I hope that this be useful for you.
Kind regards.
So, the code which I was talking about:
public function buildForm( FormBuilderInterface $builder, array $options )
{
$builder
->add('date', 'date')
->add('titre', 'text')
->add('contenu', 'textarea')
->add('publication', 'checkbox', array('required' => false))
->add('illustrations', 'collection', array(
'type' => new IllustrationType(),
'allow_add' => true
));
}