Группировка EntityType в CollectionType путем перекрытия Entity - PullRequest
1 голос
/ 24 июня 2019

Я хочу создать связь «многие ко многим» между таблицами через мою форму.Я работаю над игрой с несколькими вопросами для клиента.Он может зарегистрироваться и дать ответы на поставленные вопросы.Я хочу установить связь между таблицей «Клиент» и «Таблица ответов».

Итак, я отображаю поля, необходимые для клиента.Теперь я хочу представить некоторые вопросы с возможными ответами.

В данном коде вы можете видеть, что я добавляю в свой EventListener поле формы «answers» как CollectionType EntityType для «Answer :: class», номассив, который я установил в «data», имеет тип «Question :: class».

Теперь он рендерит мои три вопроса, но с каждым положительным ответом - не в связи с реальным поставленным вопросом.

Я пытался работать с опцией query_builder, но не нашел решения.

ERM: https://i.ibb.co/bgjmPsF/adventskalender.png

Customer.php

<?php

namespace App\Entity;

use Doctrine\Common\Collections\ArrayCollection;
use Doctrine\Common\Collections\Collection;
use Doctrine\ORM\Mapping as ORM;

/**
 * @ORM\Entity(repositoryClass="App\Repository\CustomerRepository")
 */
class Customer
{
    /**
     * @ORM\Id()
     * @ORM\GeneratedValue()
     * @ORM\Column(type="integer")
     */
    private $id;

    /**
     * @ORM\Column(type="string", length=255)
     */
    private $name;

    /**
     * @ORM\Column(type="string", length=255, unique=true, nullable=false)
     */
    private $email;

    /**
     * @ORM\Column(type="boolean", nullable=true)
     */
    private $dse_checked;

    /**
     * @ORM\Column(type="boolean", nullable=true)
     */
    private $reminder_checked;

    /**
     * @ORM\Column(type="datetime", options={"default"="CURRENT_TIMESTAMP"})
     */
    private $registration;

    /**
     * @ORM\Column(type="boolean", nullable=true)
     */
    private $newsletter;

    /**
     * @ORM\ManyToMany(targetEntity="App\Entity\Answer", inversedBy="customers")
     * @ORM\JoinTable(name="customer_answer")
     */
    private $answers;

    public function __construct()
    {
        $this->registration = new \DateTime("now");
        $this->answers = new ArrayCollection();
    }

    public function getId(): ?int
    {
        return $this->id;
    }

    public function getName(): ?string
    {
        return $this->name;
    }

    public function setName(string $name): self
    {
        $this->name = $name;

        return $this;
    }

    public function getEmail(): ?string
    {
        return $this->email;
    }

    public function setEmail(string $email): self
    {
        $this->email = $email;

        return $this;
    }

    public function getDseChecked(): ?bool
    {
        return $this->dse_checked;
    }

    public function setDseChecked(?bool $dse_checked): self
    {
        $this->dse_checked = $dse_checked;

        return $this;
    }

    public function getReminderChecked(): ?bool
    {
        return $this->reminder_checked;
    }

    public function setReminderChecked(?bool $reminder_checked): self
    {
        $this->reminder_checked = $reminder_checked;

        return $this;
    }


    public function getRegistration(): ?\DateTimeInterface
    {
        return $this->registration;
    }

    public function setRegistration(\DateTimeInterface $registration): self
    {
        $this->registration = $registration;

        return $this;
    }

    public function getNewsletter(): ?bool
    {
        return $this->newsletter;
    }

    public function setNewsletter(?bool $newsletter): self
    {
        $this->newsletter = $newsletter;

        return $this;
    }

    /**
     * @return Collection|Answer[]
     */
    public function getAnswers(): Collection
    {
        return $this->answers;
    }

    public function addAnswer(Answer $answer): self
    {
        if (!$this->answers->contains($answer)) {
            $this->answers[] = $answer;
        }

        return $this;
    }

    public function removeAnswer(Answer $answer): self
    {
        if ($this->answers->contains($answer)) {
            $this->answers->removeElement($answer);
        }

        return $this;
    }

    function __toString(): string
    {
        return $this->getName();
    }
}

Question.php

<?php

namespace App\Entity;

use Doctrine\Common\Collections\ArrayCollection;
use Doctrine\Common\Collections\Collection;
use Doctrine\ORM\Mapping as ORM;

/**
 * @ORM\Entity(repositoryClass="App\Repository\QuestionRepository")
 */
class Question
{
    /**
     * @ORM\Id()
     * @ORM\GeneratedValue()
     * @ORM\Column(type="integer")
     */
    private $id;

    /**
     * @ORM\Column(type="text")
     */
    private $value;

    /**
     * @ORM\ManyToOne(targetEntity="App\Entity\Winning", inversedBy="questions")
     */
    private $winning;

    /**
     * @ORM\OneToMany(targetEntity="App\Entity\Answer", mappedBy="question", cascade={"persist"})
     */
    private $answers;

    public function __construct()
    {
        $this->answers = new ArrayCollection();
    }

    public function getId(): ?int
    {
        return $this->id;
    }

    public function getValue(): ?string
    {
        return $this->value;
    }

    public function setValue(string $value): self
    {
        $this->value = $value;

        return $this;
    }

    public function getWinning(): ?Winning
    {
        return $this->winning;
    }

    public function setWinning(?Winning $winning): self
    {
        $this->winning = $winning;

        return $this;
    }

    /**
     * @return Collection|Answer[]
     */
    public function getAnswers(): Collection
    {
        return $this->answers;
    }

    public function addAnswer(Answer $answer): self
    {
        if (!$this->answers->contains($answer)) {
            $this->answers[] = $answer;
            $answer->setQuestion($this);
        }

        return $this;
    }

    public function removeAnswer(Answer $answer): self
    {
        if ($this->answers->contains($answer)) {
            $this->answers->removeElement($answer);
            // set the owning side to null (unless already changed)
            if ($answer->getQuestion() === $this) {
                $answer->setQuestion(null);
            }
        }

        return $this;
    }

    /**
     * @return string
     */
    public function __toString(): string
    {
        return $this->getValue();
    }
}

Answer.php

<?php

namespace App\Entity;

use Doctrine\Common\Collections\ArrayCollection;
use Doctrine\Common\Collections\Collection;
use Doctrine\ORM\Mapping as ORM;

/**
 * @ORM\Entity(repositoryClass="App\Repository\AnswerRepository")
 */
class Answer
{
    /**
     * @ORM\Id()
     * @ORM\GeneratedValue()
     * @ORM\Column(type="integer")
     */
    private $id;

    /**
     * @ORM\Column(type="string", length=255)
     */
    private $value;

    /**
     * @ORM\ManyToOne(targetEntity="App\Entity\Question", inversedBy="answers")
     */
    private $question;


    /**
     * @ORM\Column(type="boolean", nullable=true)
     */
    private $isRight;

    /**
     * @ORM\ManyToMany(targetEntity="App\Entity\Customer", mappedBy="answers")
     * @ORM\JoinTable(name="customer_answer")
     */
    private $customers;

    public function __construct()
    {
        $this->customers = new ArrayCollection();
    }


    public function getId(): ?int
    {
        return $this->id;
    }

    public function getValue(): ?string
    {
        return $this->value;
    }

    public function setValue(string $value): self
    {
        $this->value = $value;

        return $this;
    }

    public function getQuestion(): ?Question
    {
        return $this->question;
    }

    public function setQuestion(?Question $question): self
    {
        $this->question = $question;

        return $this;
    }

    public function getIsRight(): ?bool
    {
        return $this->isRight;
    }

    public function setIsRight(?bool $isRight): self
    {
        $this->isRight = $isRight;

        return $this;
    }

    /**
     * @return Collection|Customer[]
     */
    public function getCustomers(): Collection
    {
        return $this->customers;
    }

    public function addCustomer(Customer $customer): self
    {
        if (!$this->customers->contains($customer)) {
            $this->customers[] = $customer;
            $customer->addAnswer($this);
        }

        return $this;
    }

    public function removeCustomer(Customer $customer): self
    {
        if ($this->customers->contains($customer)) {
            $this->customers->removeElement($customer);
            $customer->removeAnswer($this);
        }

        return $this;
    }

    /**
     * @return string|null
     */
    public function __toString()
    {
        return $this->getValue();
    }
}

CustomerType.php

    public function buildForm(FormBuilderInterface $builder, array $options)
    {
        $this->questions= $options['questions'];
        $builder
            ->add('name', TextType::class, ['label' => 'Name', 'mapped' => true,])
            ->add('email', TextType::class, ['label' => 'E-Mail'])
            ->add('dse_checked', CheckboxType::class, ['label' => 'Datenschutzbestimmungen akzeptiert'])
            ->add('reminder_checked', CheckboxType::class, ['label' => 'Tägliche Erinnerungen'])
            ->add('newsletter', CheckboxType::class, ['label' => 'Newsletter abonieren'])
            ->addEventListener(FormEvents::PRE_SET_DATA, [
                $this,
                'onPreSetData'
            ])
            ->add('submit', SubmitType::class, ['label' => 'Speichern']);
    }


    /**
     * @param FormEvent $event
     */
    public function onPreSetData(FormEvent $event)
    {
        $form = $event->getForm();
        $questions  = $this->questions;

        foreach ($questions as $wKey => $question) {
            $answers = array_merge($answers, $question->getAnswers()->getValues());
        }

        $form->add('answers', CollectionType::class, [
            'entry_type' => EntityType::class,
            'data' => $questions,
            'by_reference' => false,
            'mapped' => true,
            'entry_options' => [
                'label' => 'Label',
                'class' => Answer::class,

            ]
        ]);
    }

В конце я хочу получить список вопросов с их вариантами ответов в форме моего клиента, чтобы я мог сохранить данные ответы в моем объекте клиента.

...