Symfony 5 - Add select form elements in a loop in twig - php

I'd like to add form elements in a twig template, but in a loop as shown there :
Example 01
Example of the code I'd need for one select element :
$form = $this->createFormBuilder()
->add('quantity', ChoiceType::class, [
'label' => false,
'choices' => [0,10,20,30]
])
->add('save', SubmitType::class,[
'label' => $this->translator->trans('Enregistrer les quantités')
]);
$form->getForm();
But I'm not that confident with dynamic forms, so first, how can I create multiform element in my controller depends on the number of line elements, pass them to my template and then display them in my twig template ?
Also, Is it possible to have ONE button to update all select elements ?
Thank you in advance.
Regards,

let say your lines are product, and your select is an attribute of your line( so of your product).
You could use imbrication form to solve this problem:
in your controller :
$form = $this->createForm(ProductsType::class, null, ['products'=>$allMyProductEntities);
then describe ProductsType as follow:
namespace App\Form;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
class ProductsType extends AbstractType
{
/**
* {#inheritdoc}
*/
public function buildForm(FormBuilderInterface $builder, array $options)
{
for($product as $options['products']){
$builder->add('product', ProductType::class, [
'label' => false,
'entity' => $product,
]);
}
}
/**
* {#inheritdoc}
*/
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults(array(
'data_class' => Product::class
'products' => [],
));
}
}
then describe ProductType as follow:
namespace App\Form;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
class ProductType extends AbstractType
{
public $translator
public function __construct(TranslatorInterface $translator){
$this->translator = $translator;
}
/**
* {#inheritdoc}
*/
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder->add('quantity', ChoiceType::class, [
'label' => false,
'choices' => [0,10,20,30],
'default' => $option['entity']->getQuantity(),
]);
}
/**
* {#inheritdoc}
*/
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults(array(
'data_class' => Product::class,
'entity' => null,
));
}
}
(Don't add submit button in your form here, do it in twig, it is best practice)
then you can loop on your form in twig:
{% for product in form.products %}
<li>
{{ form_widget(product.quantity) }}
</li>
{% endfor %}

Related

Symfony forms | Dynamic collection type values

I'm building a small tool on symfony 3.4, I'm experiencing two issue with a form that I cannot find a solution for.
For the context, the form that is causing me some difficulties is based on a doctrine entity : Event.
This event reference another entity : a Doctrine (nothing do to with the ORM). A doctrine references multiples Fittings.
For a given Event with a given Doctrine, I want to display a collectiontype built from the doctrine fittings that expose a number meant to be the required number of this fitting for this event.
This lead to 3 entities in my form : the event itself, the doctrine, and a collectiontype of fittingRequirements built on my end.
The right panel content is meant to change each time the doctrine change.
Here is the EventType :
<?php
namespace AppBundle\Form;
use AppBundle\Entity\Doctrine;
use AppBundle\Entity\Event;
use AppBundle\Form\DataTransformer\FittingRequirementTransformer;
use Doctrine\ORM\EntityRepository;
use Symfony\Bridge\Doctrine\Form\Type\EntityType;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Extension\Core\Type\ChoiceType;
use Symfony\Component\Form\Extension\Core\Type\CollectionType;
use Symfony\Component\Form\Extension\Core\Type\DateTimeType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\Form\FormEvent;
use Symfony\Component\Form\FormEvents;
use Symfony\Component\Form\FormInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
class EventType extends AbstractType
{
protected $requirementTransformer;
public function __construct(FittingRequirementTransformer $transformer)
{
$this->requirementTransformer = $transformer;
}
/**
* {#inheritdoc}
*/
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->setMethod('POST')
->add('name')
->add(
'date',
DateTimeType::class,
[
'widget' => 'single_text',
'format' => 'yyyy-MM-dd HH:mm',
]
)
->add('startLocation')
->add(
'eventType',
ChoiceType::class,
[
'choices' => [
'PvE' => 'PvE',
'PvP' => 'PvP',
'Other' => 'Other',
],
]
)
->add('target')
->add('description')
->add(
'doctrine',
EntityType::class,
[
'class' => 'AppBundle\Entity\Doctrine',
'choice_label' => 'name',
'query_builder' => function (EntityRepository $repository) {
return $repository->createQueryBuilder('d')->orderBy('d.name', 'ASC');
},
'required' => false,
]
);
$formModifier = function (FormInterface $form, Doctrine $doctrine = null, Event $event) {
$eventRequirements = [];
if ($doctrine) {
$doctrineFittings = $doctrine->getFittings();
$doctrineRequirements = $event->getDoctrineFittingRequirements($doctrine);
$eventRequirements = $this->requirementTransformer->dataToForm(
$doctrineFittings,
$doctrineRequirements,
$event
);
}
$form->add(
'eventRequirements',
CollectionType::class,
[
'entry_type' => FittingRequirementType::class,
'label' => false,
'entry_options' => ['label' => false],
'data' => $eventRequirements,
'mapped' => false,
]
);
};
$builder->addEventListener(
FormEvents::PRE_SET_DATA,
function (FormEvent $event) use ($formModifier) {
$formupEvent = $event->getData();
$formModifier($event->getForm(), $formupEvent->getDoctrine(), $formupEvent);
}
);
$builder->get('doctrine')->addEventListener(
FormEvents::POST_SUBMIT,
function (FormEvent $event) use ($formModifier) {
$eventForm = $event->getForm()->getParent();
$doctrine = $event->getForm()->getData();
$formModifier($event->getForm()->getParent(), $doctrine, $eventForm->getData());
}
);
}
/**
* {#inheritdoc}
*/
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults(
[
'data_class' => 'AppBundle\Entity\Event',
]
);
}
/**
* {#inheritdoc}
*/
public function getBlockPrefix()
{
return 'event';
}
}
I'm building the list of eventFittingRequirements and adding it on PRE_SET_DATA and POST_SUBMIT
As you can see, I use a CollectionType of FittingRequirementType you can see bellow :
<?php
namespace AppBundle\Form;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Extension\Core\Type\NumberType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
class FittingRequirementType extends AbstractType
{
/**
* {#inheritdoc}
*/
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder->add('number', NumberType::class);
}
/**
* {#inheritdoc}
*/
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults(array(
'data_class' => 'AppBundle\Entity\FittingRequirement'
));
}
/**
* {#inheritdoc}
*/
public function getBlockPrefix()
{
return 'appbundle_fittingrequirement';
}
}
This is only used to expose the number of required fittings.
All this works well when I display the form, however when I submit the form using javascript to refresh the requirement part, the field are indeed replaced, but the returned form has no value in the inputs.
The $eventRequirements variable from my $formModifier contains a proper set of data, with the number value. However, when I check the XHR with the symfony profiler, the form has no values, even if I select the original doctrine again. I don't understand what is going on and how to fix this.
Thanks for reading
I just found out what was going on and fixed my issue.
My forms are fine, however the handleRequest method clears the unmapped fields I set with my custom fittingRequirement list.
I had to manually submit my form with the clearmissing parameter to false like bellow :
$form->submit($request->request->get($form->getName()), false);

Symfony2: Specify form type as a field type of another form

So I have a base form:
public function buildForm(FormBuilderInterface $builder, array $options) {
$builder
->add('firstName')
->add('lastName')
->add('checklist);
}
Which has a specific field checklist. I created a model class, that describes all possible options in the checklist
ChecklistModel.php
class ChecklistModel {
/** #var string **/
protected $clientSatisfied;
// ... getters and setters
}
Then, I created a form type specially for Checklist.
ChecklistFormType.php
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('clientSatisfied', ChoiceType::class, array(
'choices' => array(
'yes' => 'yes',
'no' => 'no'
),
'choices_as_values' => true,
))
}
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults(array(
'data_class' => ChecklistModel::class
));
}
I want to store checklist as a simple JSON string in database, but I want to use a ChecklistModel to make sure that all fields in the checklist are submitted correctly.
My question is how to tell Symfony use ChecklistFormType as a field type of base form checklist property?
I've tried something like
->add('checklist', ChecklistFormType::class);
But I'm getting the follwing error
The form's view data is expected to be an instance of class PT\MyBundle\Models\Invoice\ChecklistModel, but is a(n) string. You can avoid this error by setting the "data_class" option to null or by adding a view transformer that transforms a(n) string to an instance of PT\MyBundle\Models\Invoice\ChecklistModel
Building on my comment above, I'd suggest not doing the data transformation in the form type (though it's certainly possible), but rather in the encapsulating model using the json_array type.
This way only that model actually knows how the data will be persisted.
The two relevant models:
src/AppBundle/Entity/FooModel.php
<?php
declare(strict_types=1);
namespace AppBundle\Entity;
use Doctrine\ORM\Mapping as ORM;
/**
* #ORM\Entity()
*/
class FooModel
{
// other properties (firstName, lastName, ...)
/**
* #var array
*
* #ORM\Column(type="json_array")
*/
private $checklist = [];
/**
* #param ChecklistModel $checklist
*/
public function setChecklist(ChecklistModel $checklist)
{
$this->checklist = $checklist->toArray();
}
/**
* #return ChecklistModel
*/
public function getChecklist(): ChecklistModel
{
return ChecklistModel::fromArray($this->checklist);
}
}
with ChecklistModel implementing the above mentioned methods:
src/AppBundle/Entity/ChecklistModel.php
<?php
declare(strict_types=1);
namespace AppBundle\Entity;
class ChecklistModel
{
// properties and getters/setters
/**
* #param array $data
*
* #return ChecklistModel
*/
public static function fromArray(array $data): ChecklistModel
{
$result = new self;
foreach (get_class_vars(self::class) as $k => $v) {
if (isset($data[$k])) {
$result->$k = $data[$k];
}
}
return $result;
}
/**
* #return array
*/
public function toArray()
{
return get_object_vars($this);
}
}
The form types:
src/AppBundle/Form/FooFormType.php
<?php
declare(strict_types=1);
namespace AppBundle\Form;
use AppBundle\Entity\FooModel;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
use Symfony\Component\Form\Extension\Core\Type as FormType;
class FooFormType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('firstName', FormType\TextType::class)
->add('lastName', FormType\TextType::class)
->add('checklist', ChecklistFormType::class)
;
}
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults([
'data_class' => FooModel::class,
'empty_data' => new FooModel(),
]);
}
}
src/AppBundle/Form/ChecklistFormType.php
<?php
declare(strict_types=1);
namespace AppBundle\Form;
use AppBundle\Entity\ChecklistModel;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
use Symfony\Component\Form\Extension\Core\Type as FormType;
class ChecklistFormType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('clientSatisfied', FormType\ChoiceType::class, [
'choices' => [
'yes' => 'yes',
'no' => 'no'
],
'choices_as_values' => true,
])
->add('clientNewCustomer', FormType\ChoiceType::class, [
'choices' => [
'yes' => 'yes',
'no' => 'no'
],
'choices_as_values' => true,
])
;
}
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults([
'data_class' => ChecklistModel::class,
'empty_data' => new ChecklistModel(),
]);
}
}
example usage
public function indexAction(Http\Request $request)
{
$em = $this->getDoctrine()->getManager();
$data = new Entity\FooModel();
$form = $this
->createForm(FooFormType::class, $data)
->handleRequest($request)
;
if ($form->isSubmitted() && $form->isValid()) {
$em->persist($data);
$em->flush();
}
return $this->render('default/index.html.twig', [
'form' => $form->createView(),
'data' => $form->getData(),
]);
}
This way the ChecklistFormType dose not need to know anything about the data being json or something else. A ChecklistModel goes in and comes out, no surprises.
That said, embeddables might be a better choice here.
You have to specify the data class as told in the error message and to define a data transformer in combination with a de/serializer.
Symfony documentation

How to add rows to CollectionType in Symfony2 Form?

I'm trying to create a "complex form" using Symfony2. One field of this form is created from another "simple form", and, 6 fields of the form are created from another "simple form" (so it's a repeated field, yes). It's like a "Form of forms" or embedded form.
The following code correspond to the first "simple form" that is only one field of the "complex form":
<?php
namespace SisEvo\ConfiguracionBundle\Form;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
class VariableReguladaElectricoValoresDatosType extends AbstractType{
/**
* #param FormBuilderInterface $builder
* #param array $options
*/
public function buildForm(FormBuilderInterface $builder, array $options) {
$builder
->add('valor');
}
/**
* #param OptionsResolver $resolver
*/
public function configureOptions(OptionsResolver $resolver) {
$resolver->setDefaults(array(
'data_class' => 'SisEvo\ConfiguracionBundle\Entity\VariableReguladaElectricoValoresDatos'
));
}
}
The other "simple form" that will be repeated 6 times in the "complex form":
<?php
namespace SisEvo\MaestroBundle\Form;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
use Symfony\Bridge\Doctrine\Form\Type\EntityType;
class VariablesMedidaType extends AbstractType{
/**
* #param FormBuilderInterface $builder
* #param array $options
*/
public function buildForm(FormBuilderInterface $builder, array $options) {
$builder->add("medida", EntityType::class, array(
'required' => true,
'class' => 'MaestroBundle:VariablesMedida',
'choice_label' => 'medida',
));
}
/**
* #param OptionsResolver $resolver
*/
public function configureOptions(OptionsResolver $resolver) {
$resolver->setDefaults(array(
'data_class' => 'SisEvo\MaestroBundle\Entity\VariablesMedida'
));
}
}
And finally, the "complex form":
<?php
namespace SisEvo\ConfiguracionBundle\Form;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
use Symfony\Component\Form\Extension\Core\Type\CollectionType;
use SisEvo\MaestroBundle\Form\VariablesMedidaType;
use SisEvo\ConfiguracionBundle\Form\VariableReguladaElectricoValoresDatosType;
class VariableReguladaElectricoValoresType extends AbstractType {
/**
* #param FormBuilderInterface $builder
* #param array $options
*/
public function buildForm(FormBuilderInterface $builder, array $options) {
$builder
->add('idDatos', CollectionType::class, array(
// each entry in the array will be an "email" field
'entry_type' => VariableReguladaElectricoValoresDatosType::class,
// these options are passed to each "email" type
'entry_options' => array(
'attr' => array(
'rows' => 6
//,'class' => 'VariableReguladaElectricoValoresDatos'
)),
))
//->add('valores', 'collection', array('type' => new VariableReguladaElectricoValoresDatosType()))
->add('idMedida', new VariablesMedidaType());
}
/**
* #param OptionsResolver $resolver
*/
public function configureOptions(OptionsResolver $resolver) {
$resolver->setDefaults(array(
'data_class' => 'SisEvo\ConfiguracionBundle\Entity\VariableReguladaElectricoValores'
, 'cascade_validation' => true
));
}
}
idMedida field is working fine, but I need some help to print idDatos field, that should be printed 6 times. I tried to do it with the option rows as you can see in the code, but is not working.
In the twig file I'm trying to print the form using {{ form_widget(myComplexForm) }}
Any idea to solve it?
When you create your form in Controller, you can create there 6 entities of SisEvo\ConfiguracionBundle\Entity\VariableReguladaElectricoValoresDatos as an ArrayCollection and set it as idDatos, then pass it to form as setData method of a form

Using two entities to create a single form

I asked a similar question to this but I think it caused confusion so I decided to ask in this post with brushed up version.
What I want is to print all fields from two different entities in a single web form, BOTH TYPE. That's it.
Note: I tried using entity and collection keywords in the form type (BOTH TYPE) but twig doesn't echo anything. Keep getting; Method "brand" OR "car" for object does not exist in twig line whatever....
Relationship: 1 Brand has N Cars. one-to-many
I read the 'How to Embed a Collection of Forms', 'entity Field Type' and 'collection Field Type' but whatever I did, didn't work.
BRAND ENTITY
namespace Car\BrandBundle\Entity;
use Doctrine\ORM\Mapping as ORM;
use Doctrine\Common\Collections\ArrayCollection;
class BrandEntity
{
protected $id;
protected $name;
protected $origin;
/**
* #ORM\OneToMany(targetEntity = "CarEntity", mappedBy = "brand")
* #var object $car
*/
protected $car;
/**
* Constructor.
*/
public function __construct()
{
$this->car = new ArrayCollection();
}
}
CAR ENTITY
namespace Car\BrandBundle\Entity;
use Doctrine\ORM\Mapping as ORM;
class CarEntity
{
protected $id;
protected $model;
protected $price;
/**
* #ORM\ManyToOne(targetEntity="BrandEntity", inversedBy="car")
* #ORM\JoinColumn(name="brand_id", referencedColumnName="id")
* #var object $brand
*/
protected $brand;
}
BRAND TYPE
namespace Car\BrandBundle\Form\Type;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolverInterface;
class BrandType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->setAction($options['action'])
->setMethod('POST')
->add('name', 'text', array('label' => 'Name'))
->add('origin', 'text', array('label' => 'Origin'))
->add('button', 'submit', array('label' => 'Add'))
;
}
public function setDefaultOptions(OptionsResolverInterface $resolver)
{
$resolver->setDefaults(array(
'data_class' => 'Car\BrandBundle\Entity\BrandEntity')
);
}
public function getName()
{
return 'brand';
}
}
CAR TYPE
namespace Car\BrandBundle\Form\Type;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolverInterface;
class CarType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->setAction($options['action'])
->setMethod('POST')
->add('model', 'text', array('label' => 'Model'))
->add('price', 'text', array('label' => 'Price'))
->add('button', 'submit', array('label' => 'Add'))
;
}
public function setDefaultOptions(OptionsResolverInterface $resolver)
{
$resolver->setDefaults(array(
'data_class' => 'Car\BrandBundle\Entity\CarEntity')
);
}
public function getName()
{
return 'car';
}
}
---------------------------------------------------------------------
-------- This section is the one I'm trying to get it working ------
---------------------------------------------------------------------
BOTH TYPE
namespace Car\BrandBundle\Form\Type;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Test\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolverInterface;
class BothType extends AbstractType
{
public function builder(FormBuilderInterface $builder, array $options)
{
$builder
->setAction($options['action'])
->setMethod('POST')
->add('brand', 'collection', array('type' => new BrandType()))
->add('car', 'collection', array('type' => new CarType()))
->add('button', 'submit', array('label' => 'Add'))
;
}
public function setDefaultOptions(OptionsResolverInterface $resolver)
{
$resolver->setDefaults(array(
'data_class' => 'Car\BrandBundle\Entity\BrandEntity',
'cascade_validation' => true
));
}
public function getName()
{
return 'both';
}
}
CONTROLLER
namespace Car\BrandBundle\Controller;
use Car\BrandBundle\Form\Type\BothType;
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
class BothController extends Controller
{
public function indexAction()
{
$form = $this->createForm(new BothType(), null,
array('action' => $this->generateUrl('bothCreate')));;
return $this->render('CarBrandBundle:Default:both.html.twig',
array('page' => 'Both', 'form' => $form->createView()));
}
}
TWIG
{% block body %}
{{ form_label(form.brand.name) }}
{{ form_widget(form.brand.name) }}
{{ form_label(form.brand.origin) }}
{{ form_widget(form.brand.origin) }}
{{ form_label(form.car.model) }}
{{ form_widget(form.car.model) }}
{{ form_label(form.car.price) }}
{{ form_widget(form.car.price) }}
{% endblock %}
Use an array to composite the two objects in your controller.
$formData = array(
'brand' = new Brand(),
'car' => new Car(),
);
$builder = $this->createFormBuilder($formData);
$builder->add('brand',new BrandFormType());
$builder->add('car', new CarFormType());
$form = $builder->getForm();
==============================================================
If you really want to make a BothType then just get rid of that collection type.
class BothType extends AbstractType
{
public function builder(FormBuilderInterface $builder, array $options)
{
$builder
->setAction($options['action'])
->setMethod('POST')
->add('brand', new BrandType())
->add('car', new CarType())
->add('button', 'submit', array('label' => 'Add'))
;
}
// Controller
$form = $this->createForm(new BothType(), $formData
collection is used when you have multiple instances of the same entity type.
By the way, creating classes for each composite form can quickly cause an explosion of form types. So unless you plan on reusing your BothFormType among multiple controllers then I'd suggest just building it right inside of the controller.

Symfony2 Form get data value in form type

I want modify a form with a content value :
I try with "PRE_BIND" event but this doesn't work if the form isn't send a first time.
I have this :
<?php
namespace YOU\CommercantBundle\Form\Type;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormEvents;
use Symfony\Component\Form\FormEvent;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolverInterface;
class LivraisonChoixType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder->addEventListener(FormEvents::PRE_BIND, function (FormEvent $event) use ($builder)
{
$form = $event->getForm();
$data = $event->getData();
if ((int)$data['pays'] > 0) {
$form->remove('livreur');
$pays = $data['pays'];
$form->add('livreur','entity',array(
'property' =>'name',
'class' => 'YOUAdminBundle:Livreur',
'label' => 'Livreur :',
'query_builder' => function($er) use ($pays){
return $er->createQueryBuilder('c')
->join('c.pays', 'p')
->andWhere('p.id= :pays')
->addOrderBy('c.name', 'ASC')
->setParameter('pays', $pays);
},
)
);
}
});
$builder
->add('pays','pays',array('label'=>'Destination :'))
->add('livreur','entity',array(
'property' =>'name',
'class' => 'YOUAdminBundle:Livreur',
'label' => 'Livreur :',
'query_builder' => function($er) {
return $er->createQueryBuilder('c')
->join('c.pays', 'p')
->andWhere('p.id= :pays')
->addOrderBy('c.name', 'ASC')
->setParameter('pays', 0);
},
)
)
->add('prix','number',array('required'=>true,'label' => 'Frais :'))
->add('prix2','number',array('required'=>false,'label' => 'Frais en second article :'))
;
}
public function setDefaultOptions(OptionsResolverInterface $resolver)
{
$resolver->setDefaults(array(
'data_class' => 'YOU\CommercantBundle\Entity\LivraisonChoix',
));
}
public function getName()
{
return 'you_commercantbundle_livraisonchoixtype';
}
}
Called by this form type :
<?php
namespace YOU\CommercantBundle\Form\Type;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolverInterface;
class LivraisonType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('name','text',array('required'=>true,'label'=>'Nom :'))
->add('choix','collection',array(
'type'=>new LivraisonChoixType(),
'options'=>array('attr'=>array('class'=>'livreur-collection')),
'allow_add' => true,
'allow_delete' => true,
'by_reference' => false,
))
;
}
public function setDefaultOptions(OptionsResolverInterface $resolver)
{
$resolver->setDefaults(array(
'data_class' => 'YOU\CommercantBundle\Entity\Livraison'
));
}
public function getName()
{
return 'you_commercantbundle_livraisontype';
}
}
Anyone know how I can get the value ?
This may not be the best answer but this is what I do when I want to assign values to forms before they are rendered. Basically I would bind the form to an entity as such:
// First create entity that will bind with form
$someEntityInstance = new myEntity();
$someEntityInstance->setPropertyOne(5);
$someEntityInstance->setPropertyTwo('another value');
// Then bind entity to form
$myForm = $this->createForm(new myFormType, $someEntityInstance);
Any properties that are mapped from the form to the entity will have the same value and when rendered in the view, this will show up. Though if I have multiple entities represented in a form, I then create a new thing class called a processor that will have properties mapped and bound to the form that can also change the form field values.
This is the easiest way that I know for changing form field values before rendering them.

Categories