Quantcast
Channel: Grafikart | Derniers Sujets du forum
Viewing all articles
Browse latest Browse all 1542

Formulaire dynamique (4 listes liées) Symfony/EventListener

$
0
0

Bonsoir à tous (bonjour pour ceux qui liront ce post en journée).
Je suis confronté à un petit problème concernant l'ajout d'un EventListener sur mon formType dans mon prjet Symfony. J'ai suivi la doc ici (en anglais bien sûr), mais sans succès. J'ai aussi pas mal cherché sur d'autre forum, mais en vain.

Je vous explique mon problème:
Je dois créer un formulaire où les listes déroulantes se remplissent suivant nos choix dans les précédantes. Je pense que je ne suis pas le seul à vouloir faire et a avoir été confronté à ce problème.

J'ai plusieurs entités:Parcsimmobilier.php, Ensembles.php, Batiments.php et Zonestechnique.php.

Un Parcs peut avoir plusieurs ensembles (ManyToOne), un ensemble peut avoir plusieurs Batiments (ManyToOne) et un batiment peut avoir plusieurs Zonestechnique (ManyToOne). Enfin une ZonesTechniqus peut avoir plusieurs categories, et une categories peut avoir plusieurs ZonesTechnique (ManyToMany).

1- La route appel un formulaire qui fait apparaître dans un select la liste de tous les parcs immobiliers.

2- Je choisis mon parc et ensuitedans la liste suivante la liste des ensemble correspondant à ce parc.

3- Une fois l'ensemble sélectionné, deux choix s'offre à l'utilisateur. Il doit sélectionner le type de catégorie de la zone technique (il peut y en avoir plusieurs d'ailleurs). Toutefois, si la catégorie "extérieure" est sélectionnée dans ce "multiple select, alors la liste des bâtiments se fige sur une valeur "aucun bâtiment" (qui est une valeur null), mais il ne peut pas choisir un bâtiment car la catégorie est extérieure. Par contre si une autre catégorie est sélectionnée que "extérieure", alors la liste des bâtiments appartenant à l'ensemble auparavant choisi apparaît.

4- Une fois le bâtiment choisit (donc soit un bâtiment, soit la valeur "aucun"), le reste du formulaireest à nous.

Voici le code pour mes entités

//Parcsimmobilier.php
class Parcsimmobilier
{
    /**
     * @var integer
     *
     * @ORM\Column(name="id", type="integer", nullable=false)
     * @ORM\Id
     * @ORM\GeneratedValue(strategy="IDENTITY")
     */
    private $id;

    /**
     * @var string
     *
     * @ORM\Column(name="nom", type="string", length=150, nullable=false)
     */
    private $nom;

     /**
     * @var \Doctrine\Common\Collections\Collection
     *
     * @ORM\OneToMany(targetEntity="Ensembles", mappedBy="parcsimmobilier")
     */
    private $ensembles

    //Ensembles.php
    class Ensembles
{
    /**
     * @var integer
     *
     * @ORM\Column(name="id", type="integer", nullable=false)
     * @ORM\Id
     * @ORM\GeneratedValue(strategy="IDENTITY")
     */
    private $id;

     /**
     * @var string
     *
     * @ORM\Column(name="nom", type="string", length=150, nullable=false)
     */
    private $nom;

     /**
     * @var \Parcsimmobilier
     *
     * @ORM\ManyToOne(targetEntity="Parcsimmobilier")
     * @ORM\JoinColumns({
     *   @ORM\JoinColumn(name="parcsimmobilier_id", referencedColumnName="id")
     * })
     */
    private $parcsimmobilier;

//Batiments.php
   class Batiments
{
    /**
     * @var integer
     *
     * @ORM\Column(name="id", type="integer", nullable=false)
     * @ORM\Id
     * @ORM\GeneratedValue(strategy="IDENTITY")
     */
    private $id;

    /**
     * @var string
     *
     * @ORM\Column(name="nom", type="string", length=150, nullable=true)
     */
    private $nom;

    /**
     * @var \Ensembles
     *
     * @ORM\ManyToOne(targetEntity="Ensembles")
     * @ORM\JoinColumns({
     *   @ORM\JoinColumn(name="ensembles_id", referencedColumnName="id")
     * })
     */
    private $ensembles;

    class Zonestechnique
{
    /**
     * @var integer
     *
     * @ORM\Column(name="id", type="integer", nullable=false)
     * @ORM\Id
     * @ORM\GeneratedValue(strategy="IDENTITY")
     */
    private $id;

    /**
     * @var string
     *
     * @ORM\Column(name="nom", type="string", length=150, nullable=false)
     */
    private $nom;

    /**
     * @var \Batiments
     *
     * @ORM\ManyToOne(targetEntity="Batiments")
     * @ORM\JoinColumns({
     *   @ORM\JoinColumn(name="batiments_id", referencedColumnName="id")
     * })
     */
    private $batiments;

    /**
     * @var \Doctrine\Common\Collections\Collection
     *
     * @ORM\ManyToMany(targetEntity="Categorieszonestechnique")
     * @ORM\JoinTable(name="zonestechnique_categorieszonestechnique",
     *   joinColumns={
     *     @ORM\JoinColumn(name="zonestechnique_id", referencedColumnName="id")
     *   },
     *   inverseJoinColumns={
     *     @ORM\JoinColumn(name="categorieszonestechnique_id", referencedColumnName="id")
     *   }
     * )
     */

     private $categorieszonestechnique;

Bien sûr mes getter et setters sont implémentés dans leur classe respective, si je vous fournis tout le code il y en aurait pour un moment.

Suivant le doc, j'ai donc créer un formulaire, qui n'est pas lié à une entité de base. Voici le code:

// appel des entités
...
// FormType Components
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\Form\FormInterface;
use Symfony\Component\OptionsResolver\OptionsResolverInterface;
use Symfony\Component\Form\FormEvent;
use Symfony\Component\Form\FormEvents;

class AjaxZonestechniqueType extends AbstractType
{

    public function buildForm(FormBuilderInterface $builder, array $options)
    {
        $builder
          ->add('parcsimmobilier', 'entity', array(
                                    'class'    => 'DatabaseBundle:Parcsimmobilier',
                                    'property' => 'nom',
                                    'multiple' => false,
                                    'required' => true,
                                    'empty_value' => '-- sélectionner un parc --',
                                    'label'    => 'Choisir le parc immobilier : ',
                                    ))
         ->add('categorieszonestechnique')
         ->add('batiments')
         ->add('nom')
          ->add('localisation')
          ->add('commentaire')
          ;
          $formModifier = function (FormInterface $form, Parcsimmobilier $parcsimmobilier = null) {
                $ensembles = null === $parcsimmobilier ? array() : $parcsimmobilier->getEnsembles();

                $form->add('ensembles', 'entity', array(
                                    'class'    => 'DatabaseBundle:Ensembles',
                                    'multiple' => false,
                                    'required' => true,
                                    'mapped' => true,
                                    'empty_value' => '-- sélectionner un ensemble --',
                                    'label'    => 'Choisir l\'ensemble : ',
                ));
            };

            $builder->addEventListener(
                FormEvents::PRE_SET_DATA,
                function (FormEvent $event) use ($formModifier) {
                    // this would be your entity, i.e. SportMeetup
                    $data = $event->getData();

                    $formModifier($event->getForm(), $data->getParcsimmobilier());
                }
            );

            $builder->get('parcsimmobilier')->addEventListener(
                FormEvents::POST_SUBMIT,
                function (FormEvent $event) use ($formModifier) {
                    // It's important here to fetch $event->getForm()->getData(), as
                    // $event->getData() will get you the client data (that is, the ID)
                    $parcsimmobilier = $event->getForm()->getData();

                    // since we've added the listener to the child, we'll have to pass on
                    // the parent to the callback functions!
                    $formModifier($event->getForm()->getParent(), $parcsimmobilier);
                }
            );

Bien sûr j'ai une** belle erreur** quand j'affiche ma page:

Error: Call to a member function getParcsimmobilier() on a non-object
500 Internal Server Error - FatalErrorException

Mon controller est tout ce qu'il y a de plus basic, je lui demande faire apparaître le formulaire dans ma twig, et ma twig l'affiche (enfin pas vraiment d'où l'erreur).

J'ai fait un var_dump($data), et bien sûr $data est null.

Voilà je patauge correctement donc si vous avez des suggestions je suis preneur. J'ai fait énormément de recherche sur internet, et pour l'instant aucun forum n'a pu vraiment m'aider, je vous avouerai ne pas totalement comprendre le fonctionnement des Event Listener sur Symfony.

Merci d'avance.


Viewing all articles
Browse latest Browse all 1542

Trending Articles