I am working on a project so that users can find music concerts based on a start date, an end date, an artist, and a city.
When I submit my search form, it shows no result.
I hope you can help me solve both of these problems.
Ps: I have an event entity owner of the artist and city entities.
Controller
class HomeController extends AbstractController
{
/**
* Display formsearch and events on index Page
*
* #Route("/", name="home")
* #param Request $request
*/
public function search(Request $request)
{
$events=[];
$searchData = new searchData();
$form = $this->createForm(SearchType::class, $searchData);
if ($request->isMethod('Post')) {
$form->handleRequest($request);
if ($form->isValid()) {
$events = $this->getDoctrine()->getRepository(Event::class)->findDataByCriteria($searchData);
}
} else {
$events = $this->getDoctrine()->getRepository(Event::class)->findLastThreeMonths();
}
return $this->render('home/index.html.twig',
['form' => $form->createView(), 'events' => $events]);
}
}
Twig (template)
{% extends 'base.html.twig.' %}
{% block title %}Os Concerts{% endblock %}
{% block body %}
{#<!-- Form search --> #}
<div class="jumbotron text-center">
<h1>Concerts en France</h1>
<div class="jumbotron">
<div class="container">
<h3 class="text-left">Rechercher un évènement</h3>
{{ form_start(form) }}
<div class="form-row">
<div class="col">
{{ form_row(form.startDate) }}
</div>
<div class="col">
{{ form_row(form.endDate) }}
</div>
<div class="col">
{{ form_row(form.artist) }}
</div>
<div class="col">
{{ form_row(form.city) }}
</div>
<div class="col">
<button class="btn btn-secondary align-bottom">Rechercher</button>
</div>
</div>
{{ form_end(form) }}
</div>
</div>
</div>
{#<!-- search result display or events for the next 3 months --> #}
<div class="container" mt-4>
<table class="table table-striped" id="liste">
<thead>
<th scope="col">Où
</td>
<th scope="col">Quand
</td>
<th scope="col">Qui
</td>
</thead>
<tbody>
{% for event in events %}
<tr>
<td>{{ event.city.name }}</td>
<td>{{ event.date|date }}</td>
<td>{{ event.artist.name }}</td>
</tr>
{% endfor %}
</tbody>
</table>
</div>
{% endblock %}
Repository
public function findDataByCriteria(SearchData $searchData)
{
$qb = $this->createQueryBuilder('e');
$qb->select('e, a, c')
->leftJoin('e.artist', 'a')
->leftJoin('e.city', 'c');
if (($searchData->getStartDate() != null && $searchData->getEndDate()) != null) {
$qb->andWhere('e.date BETWEEN :startDate AND :endDate')
->setParameter('startDate', $searchData->getStartDate())
->setParameter('endDate', $searchData->getEndDate());
}
if ($searchData->getCity() != null) {
$qb->andWhere('c = :city')
->setParameter('city', $searchData->getCity());
}
if ($searchData->getArtist() != null) {
$qb->andWhere('a.name LIKE :artist')
->setParameter('artist', '%' . $searchData->getArtist() . '%');
}
return $qb
->getQuery()
->getResult();
}
Entity SearchData
class SearchData
{
private $startDate;
private $endDate;
private $artist;
private $city;
public function getStartDate(): ?\DateTime
{
return $this->startDate;
}
public function setStartDate(\DateTime $startDate = null): void
{
$this->startDate = $startDate;
}
public function getEndDate(): ?\DateTime
{
return $this->endDate;
}
public function setEndDate(\DateTime $endDate = null): void
{
$this->endDate = $endDate;
}
public function getArtist(): ?string
{
return $this->artist;
}
public function setArtist(string $artist): void
{
$this->artist = $artist;
}
public function getCity(): ?string
{
return $this->city;
}
public function setCity(string $city): void
{
$this->city = $city;
}
public function __toString()
{
return $this->name;
}
}
Formtype
class SearchType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('startDate', DateTimeType::class, [
'widget' => 'single_text',
'format' => 'dd/MM/yyyy',
'html5' => false,
'attr' => ['class' => 'from'],
])
->add('endDate', DateTimeType::class, [
'widget' => 'single_text',
'format' => 'dd/MM/yyyy',
'html5' => false,
'attr' => ['class' => 'to'],
])
->add('artist', TextType::class)
->add('city', EntityType::class, [
'class' => City::class,
]);
}
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults([
'data_class' => SearchData::class,
'csrf_protection' => false,
'translation_domain' => 'forms'
]);
}
}
Related
I want to send information from different input fields : 1st language, 2nd language, 3rd language... (this could be infinite). I built my form with Symfony in where I am asking to the user what languages he wants to learn.
I have several questions about it :
Do I need to change string field to an array field ?
In UserType.php, do I need to use CollectionType class ?
Also with JavaScript, I am able to clone the select tag that I am interested :
Do I need to do it ?
Thank you in advance if you could give a hand.
registration.html.twig
{% extends 'base.html.twig' %}
{% block title %}Incris-toi !{% endblock %}
{% block main %}
{{ form_start(userform) }}
<div class="alert alert-danger text-center" role="alert">
{{ form_errors(userform.email) }}
{{ form_errors(userform.password) }}
{{ form_errors(userform.gender) }}
{{ form_errors(userform.firstname) }}
{{ form_errors(userform.lastname) }}
{{ form_errors(userform.birthdate) }}
{{ form_errors(userform.occupation) }}
{{ form_errors(userform.nationality) }}
{{ form_errors(userform.nativelanguage) }}
{{ form_errors(userform.wishedlanguages) }}
</div>
<div class="form container">
<div class="formpage">
<div class="form-floating mb-3">
{{ form_widget(userform.email, {'attr' : {'placeholder' : 'Mon adresse e-mail', 'class' : 'form-control'}}) }}
{{ form_label(userform.email, 'Mon adresse e-mail', {'label_attr' : {'class' : 'label'}}) }}
</div>
<div class="form-floating mb-3">
{{ form_widget(userform.password.first, {'attr' : {'placeholder' : 'Mon mot de passe', 'class' : 'form-control'}}) }}
{{ form_label(userform.password.first, 'Mon mot de passe', {'label_attr' : {'class' : 'label'}}) }}
</div>
<div class="form-floating">
{{ form_widget(userform.password.second, {'attr' : {'placeholder' : 'Confirmation de mon mot de passe', 'class' : 'form-control'}}) }}
{{ form_label(userform.password.second, 'Confirmation de mon mot de passe', {'label_attr' : {'class' : 'label'}}) }}
</div>
<div class="form-checkbox">
{{ form_widget(userform.roles) }}
<span class="checkbox"></span>
<span class="checkmark"></span>
</div>
<div>
<button type="button" class="next btn btn-lg btn-outline-primary mt-4 d-flex mx-auto">Je m'inscris</button>
</div>
</div>
<div class="formpage">
<div class="mb-3">
<p>Es-tu un homme ou une femme ?</p>
{{ form_widget(userform.gender, {'attr' : {'placeholder' : 'Es-tu un homme ou une femme ?', 'class' : 'form-control'}}) }}
</div>
<div class="form-floating mb-3">
{{ form_widget(userform.firstname, {'attr' : {'placeholder' : 'Quel est ton prénom ?', 'class' : 'form-control'}}) }}
{{ form_label(userform.firstname, 'Quel est ton prénom ?', {'label_attr' : {'class' : 'label'}}) }}
</div>
<div class="form-floating mb-3">
{{ form_widget(userform.lastname, {'attr' : {'placeholder' : 'Quel est ton nom de famille ?', 'class' : 'form-control'}}) }}
{{ form_label(userform.lastname, 'Quel est ton nom de famille ?', {'label_attr' : {'class' : 'label'}}) }}
</div>
<div class="form-floating mb-3">
<p>Quelle est ta date de naissance ?</p>
{{ form_widget(userform.birthdate) }}
</div>
<div class="d-flex">
<button type="button" class="prev btn btn-lg btn-outline-secondary mt-4 d-flex align-items-center me-auto"><<span class="previous">Précédent</span></button>
<button type="button" class="next btn btn-lg btn-outline-primary mt-4 d-flex ms-auto">Suivant</button>
</div>
</div>
<div class="formpage">
<div class="form-floating mb-3">
{{ form_widget(userform.occupation, {'attr' : {'placeholder' : 'Quelle est ton occupation (ton métier, tes études…) ?', 'class' : 'form-control'}}) }}
{{ form_label(userform.occupation, 'Quelle est ton occupation (ton métier, tes études…) ?', {'label_attr' : {'class' : 'label'}}) }}
</div>
<div class="mb-3">
<p>De quel pays es-tu originaire ?</p>
{{ form_widget(userform.nationality) }}
</div>
<div class="mb-3">
<p>Quelle est ta langue maternelle ?</p>
{{ form_widget(userform.nativelanguage) }}
</div>
<div class="d-flex">
<button type="button" class="prev btn btn-lg btn-outline-secondary mt-4 d-flex align-items-center me-auto"><<span class="previous">Précédent</span></button>
<button type="button" class="next optional btn btn-lg btn-outline-primary mt-4 d-flex ms-auto">Suivant</button>
<button class="btn optional-validation btn-lg btn-outline-primary mt-4 d-flex ms-auto">Je valide</button>
</div>
</div>
<div class="formpage">
<div class="mb-3">
<p>Quelle langue souhaites-tu pratiquer ?</p>
<div id="wishedlanguageslist">
{{ form_widget(userform.wishedlanguages, {'attr' : {'class' : 'wishedlanguage form-control mb-3', 'novalidate': 'novalidate'}}) }}
</div>
<div class="d-flex justify-content-between">
<button type="button" class="question-button btn btn-outline-secondary" id="addwishedlanguage">+ Ajouter une langue</button>
<button type="button" class="question-button btn btn-outline-secondary" id="removewishedlanguage">- Supprimer la dernière langue</button>
</div>
</div>
<div class="d-flex">
<button type="button" class="prev btn btn-lg btn-outline-secondary mt-4 d-flex align-items-center me-auto"><<span class="previous">Précédent</span></button>
{{ form_row(userform.save, {'attr' : {'class' : 'btn btn-lg btn-outline-primary mt-4 d-flex ms-auto'}}) }}
</div>
</div>
</div>
{{ form_end(userform) }}
{% endblock %}
{% block js %}
<script src="../assets/js/scripts.js"></script>
{% endblock %}
UserType.php
<?php
namespace App\Form;
use App\Entity\User;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\CallbackTransformer;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
use Symfony\Component\Form\Extension\Core\Type\ChoiceType;
use Symfony\Component\Form\Extension\Core\Type\SubmitType;
use Symfony\Component\Form\Extension\Core\Type\CountryType;
use Symfony\Component\Form\Extension\Core\Type\BirthdayType;
use Symfony\Component\Form\Extension\Core\Type\CheckboxType;
use Symfony\Component\Form\Extension\Core\Type\LanguageType;
use Symfony\Component\Form\Extension\Core\Type\PasswordType;
use Symfony\Component\Form\Extension\Core\Type\RepeatedType;
use Symfony\Component\Form\Extension\Core\Type\CollectionType;
class UserType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options): void
{
$builder
->add('gender', ChoiceType::class, [
'choices' => [
'Je suis ...' => '',
'un homme' => 'male',
'une femme' =>'female',
'non-binaire' => 'non-binary'
]
])
->add('lastname')
->add('firstname')
->add('birthdate', BirthdayType::class, [
'placeholder' => [
'year' => 'Année', 'month' => 'Mois', 'day' => 'Jour',
],
'choice_translation_domain' => true
])
->add('occupation')
->add('nationality', CountryType::class, [
'placeholder' => 'Je choisis un pays',
])
->add('nativelanguage', LanguageType::class, [
'placeholder' => 'Je choisis ta langue maternelle',
])
->add('wishedlanguages', CollectionType::class, [
/* 'placeholder' => 'Je choisis une langue étrangère', */
'entry_type' => LanguageType::class,
'entry_options' => [
'attr' => ['class' => 'wishedlanguage'],
],
'required' => false,
'compound' => true,
])
->add(
$builder
->get('wishedlanguages')
->setRequired(false)
)
->add('email')
->add('password', PasswordType::class, [
'mapped' => false
])
->add('password', RepeatedType::class, [
'type' => PasswordType::class,
'invalid_message' => 'Les deux mots de passe doivent être identiques.',
'options' => ['attr' => ['class' => 'password-field']],
'required' => true,
'first_options' => ['label' => 'Password'],
'second_options' => ['label' => 'Repeat Password'],
])
->add('roles', CheckboxType::class, [
'label' => 'Je m\'inscris uniquement en tant qu\'organisateur.',
'required' => false,
'compound' => true,
])
->add(
$builder
->get('roles')
->addModelTransformer(new CallbackTransformer(
function ($arrayAsBool) {
return in_array("ROLE_ADMIN", $arrayAsBool);
},
function ($boolAsArray) {
return $boolAsArray ? ["ROLE_ADMIN"] : ["ROLE_USER"];
}))
)
->add('save', SubmitType::class, [
'label' => 'Je valide',
])
;
;
}
public function configureOptions(OptionsResolver $resolver): void
{
$resolver->setDefaults([
'data_class' => User::class,
'translation_domain' => 'forms'
]);
}
}
User.php
<?php
namespace App\Entity;
use App\Repository\UserRepository;
use Doctrine\DBAL\Types\Types;
use Doctrine\ORM\Mapping as ORM;
use Symfony\Component\Security\Core\User\PasswordAuthenticatedUserInterface;
use Symfony\Component\Security\Core\User\UserInterface;
#[ORM\Entity(repositoryClass: UserRepository::class)]
class User implements UserInterface, PasswordAuthenticatedUserInterface
{
#[ORM\Id]
#[ORM\GeneratedValue]
#[ORM\Column]
private ?int $id = null;
#[ORM\Column(length: 180, unique: true)]
private ?string $email = null;
#[ORM\Column]
private array $roles = [];
/**
* #var string The hashed password
*/
#[ORM\Column]
private ?string $password = null;
#[ORM\Column(length: 255)]
private ?string $gender = null;
#[ORM\Column(length: 255)]
private ?string $lastname = null;
#[ORM\Column(length: 255)]
private ?string $firstname = null;
#[ORM\Column(type: Types::DATE_MUTABLE)]
private ?\DateTimeInterface $birthdate = null;
#[ORM\Column(length: 255)]
private ?string $occupation = null;
#[ORM\Column(length: 255)]
private ?string $nationality = null;
#[ORM\Column(length: 255)]
private ?string $nativelanguage = null;
#[ORM\Column(type: Types::ARRAY, nullable: true)]
private array $wishedlanguages = [];
#[ORM\Column(length: 255, nullable: true)]
private ?string $photo = null;
public function getId(): ?int
{
return $this->id;
}
public function getEmail(): ?string
{
return $this->email;
}
public function setEmail(string $email): self
{
$this->email = $email;
return $this;
}
/**
* A visual identifier that represents this user.
*
* #see UserInterface
*/
public function getUserIdentifier(): string
{
return (string) $this->email;
}
/**
* #see UserInterface
*/
public function getRoles(): array
{
$roles = $this->roles;
// guarantee every user at least has ROLE_USER
$roles[] = 'ROLE_USER';
return array_unique($roles);
}
public function setRoles(array $roles): self
{
$this->roles = $roles;
return $this;
}
/**
* #see PasswordAuthenticatedUserInterface
*/
public function getPassword(): string
{
return $this->password;
}
public function setPassword(string $password): self
{
$this->password = $password;
return $this;
}
/**
* #see UserInterface
*/
public function eraseCredentials()
{
// If you store any temporary, sensitive data on the user, clear it here
// $this->plainPassword = null;
}
public function getGender(): ?string
{
return $this->gender;
}
public function setGender(string $gender): self
{
$this->gender = $gender;
return $this;
}
public function getLastname(): ?string
{
return $this->lastname;
}
public function setLastname(string $lastname): self
{
$this->lastname = $lastname;
return $this;
}
public function getFirstname(): ?string
{
return $this->firstname;
}
public function setFirstname(string $firstname): self
{
$this->firstname = $firstname;
return $this;
}
public function getBirthdate(): ?\DateTimeInterface
{
return $this->birthdate;
}
public function setBirthdate(\DateTimeInterface $birthdate): self
{
$this->birthdate = $birthdate;
return $this;
}
public function getOccupation(): ?string
{
return $this->occupation;
}
public function setOccupation(string $occupation): self
{
$this->occupation = $occupation;
return $this;
}
public function getNationality(): ?string
{
return $this->nationality;
}
public function setNationality(string $nationality): self
{
$this->nationality = $nationality;
return $this;
}
public function getNativelanguage(): ?string
{
return $this->nativelanguage;
}
public function setNativelanguage(string $nativelanguage): self
{
$this->nativelanguage = $nativelanguage;
return $this;
}
public function getWishedlanguages(): array
{
return $this->wishedlanguages;
}
public function setWishedlanguages(?array $wishedlanguages): self
{
$this->wishedlanguages = $wishedlanguages;
return $this;
}
public function getPhoto(): ?string
{
return $this->photo;
}
public function setPhoto(?string $photo): self
{
$this->photo = $photo;
return $this;
}
}
I've been trying to add a edit-user page where they can change username, email address and password.
One thing I am trying to implement is they have to type in the old password to be able to change it to a new one.
I've been reading these pages:
https://symfony.com/doc/current/validation.html
https://symfony.com/doc/current/reference/constraints/UserPassword.html
but I'm really struggling on the implementation side.
Here's my Controller for the form:
<?php
namespace App\Controller\User;
use App\Entity\User;
use App\Form\User\EditUserType;
use App\Repository\UserRepository;
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\Security\Core\Encoder\UserPasswordEncoderInterface;
class EditController extends Controller
{
public function edit(Request $request, UserPasswordEncoderInterface $encoder)
{
$userInfo = ['username' => null, 'plainPassword' => null, 'password' => null, 'email' => null];
$form = $this->createForm(EditUserType::class, $userInfo);
$form->handleRequest($request);
$user = new User();
$oldPassword = $user->getPassword();
if ($form->isSubmitted() && $form->isValid()) {
$userInfo = $form->getData();
$username = $userInfo['username'];
$email = $userInfo['email'];
$newPass = $userInfo['plainPassword'];
$oldPass = $userInfo['password'];
$encryptOldPass = $encoder->encodePassword($user, $oldPass);
if ($oldPassword === $encryptOldPass) {
$this->addFlash('danger', $oldPass. ' ' .$encryptOldPass. ' ' .$oldPassword);
return $this->redirectToRoute('user_edit');
} else {
$this->addFlash('success', $oldPassword. '-' .$encryptOldPass);
return $this->redirectToRoute('user_edit');
}
$pass = $encoder->encodePassword($user, $newPass);
$user->setPassword($pass);
$user->setEmail($email);
$user->setUsername($username);
echo 'trey was here';
$this->addFlash('success', 'User Details Edited');
return $this->redirectToRoute('user_edit');
}
return $this->render('user/edit.html.twig', array('form' => $form->createView()));
}
}
my EditUserType file:
<?php
namespace App\Form\User;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Extension\Core\Type\EmailType;
use Symfony\Component\Form\Extension\Core\Type\PasswordType;
use Symfony\Component\Form\Extension\Core\Type\RepeatedType;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
class EditUserType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder->add('email', EmailType::class)
->add('username', TextType::class)
->add('password', PasswordType::class, array())
->add('plainPassword', RepeatedType::class, array(
'type' => PasswordType::class,
'first_options' => array('label' => 'New Password'),
'second_options' => array('label' => 'New Repeat Password')
));
}
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults(array());
}
}
my validation (file: config/validator/validation.yaml)
App\Form\User\EditUserType:
properties:
oldPassword:
- Symfony\Component\Security\Core\Validator\Constraints\UserPassword:
message: 'Invalid Password'
my template file:
{% include 'builder/header.html.twig' %}
<div class="user-container" id="user-content">
{% block body %}
{% include 'builder/notices.html.twig' %}
<div class="user-container">
<i class="fas fa-user-edit fa-5x"></i>
</div>
<hr />
{{ form_start(form) }}
{{ form_row(form.username, { 'attr': {'class': 'form-control', 'value': app.user.username} }) }}
{{ form_row(form.email, { 'attr': {'class': 'form-control', 'value': app.user.email} }) }}
{{ form_row(form.password, { 'attr': {'class': 'form-control'} }) }}
{{ form_row(form.plainPassword.first, { 'attr': {'class': 'form-control'} }) }}
{{ form_row(form.plainPassword.second, { 'attr': {'class': 'form-control'} }) }}
<div class="register-btn-container">
<button class="btn btn-danger" id="return-to-dash-btn" type="button">Cancel!</button>
<button class="btn btn-primary" type="submit">Update!</button>
</div>
{{ form_end(form) }}
{% endblock %}
</div>
{% include 'builder/footer.html.twig' %}
Typing in any old password for the old password fields seems to get by and not update the password to the newly typed value.. so how do I validate the old password against the database so the user can update it to a new password?
Thanks
Found the solution, using cerad comment on previous (now removed) answer:
updated controller:
<?php
namespace App\Controller\User;
use App\Form\User\EditUserType;
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\Security\Core\Encoder\UserPasswordEncoderInterface;
class EditController extends Controller
{
public function edit(Request $request, UserPasswordEncoderInterface $encoder)
{
$userInfo = ['username' => null, 'plainPassword' => null, 'password' => null, 'email' => null];
$form = $this->createForm(EditUserType::class, $userInfo);
$form->handleRequest($request);
$user = $this->getUser();
$entityManager = $this->getDoctrine()->getManager();
if ($form->isSubmitted() && $form->isValid()) {
$userInfo = $form->getData();
$username = $userInfo['username'];
$email = $userInfo['email'];
$newPass = $userInfo['plainPassword'];
$oldPass = $userInfo['password'];
if (!$encoder->isPasswordValid($user, $oldPass)) {
$this->addFlash('danger', 'Old password is invalid. Please try again');
return $this->redirectToRoute('user_edit');
}
$pass = $encoder->encodePassword($user, $newPass);
$user->setPassword($pass);
$user->setEmail($email);
$user->setUsername($username);
$entityManager->persist($user);
$entityManager->flush();
$this->addFlash('success', 'User Details Edited - Please Login Again');
return $this->redirectToRoute('login');
}
return $this->render('user/edit.html.twig', array('form' => $form->createView()));
}
}
the issue was, I wasn't checking the logged in user details, and I thought persist meant insert, not insert/update - so lack of knowledge on this one.
I would like to create a function to search for a movie through the query builder
I have a table Movie:
1. Id
2. Titre
3. Content
And i have class MovieRepository :
class MovieRepository extends EntityRepository
{
public function myFindAll()
{
return $this->createQueryBuilder('a')
->getQuery()
->getResult();
}
public function getSearchMovies($movie){
$qb = $this->createQueryBuilder('m')
->where('m.title LIKE :title')
->setParameter('title', '%' . $movie->getTitle() . '%')
->orderBy('m.title', 'DESC')
->getQuery();
}
}
Also i have MovieController :
public function indexAction()
{
$movie = new Movie;
$form = $this->createForm(new SearchMovieType(), $movie);
$request = $this->getRequest();
if ($request->getMethod() == 'POST') {
$form->bind($request);
$movies = $this->getDoctrine()
->getManager()
->getRepository('AreaDownloadBundle:Movie')
->getSearchUsers($movie);
return $this->render('AreaDownloadBundle:Download:index.html.twig', array('form' => $form->createView(),array('movies' => $movies)));
} else {
$movies = $this->getDoctrine()
->getManager()
->getRepository('AreaDownloadBundle:Movie')
->myFindAll();
return $this->render('AreaDownloadBundle:Download:index.html.twig',array('form' => $form->createView(), 'movies' => $movies));
}
}
SearchMovieType :
class SearchMovieType extends AbstractType
{
/**
* #param FormBuilderInterface $builder
* #param array $options
*/
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('title','text', array('required' => false, ))
;
}
And i have index.hml.twig, which can display movies with a search bar :
{% extends "::template.html.twig" %}
{% block body %}
<form action="{{ path('area_download_index') }}" method="post">
<div id="bar">
{{ form_widget(form.title) }}
<input type="submit" value="Chercher">
{{ form_rest(form) }}
</div>
</form>
{% for movie in movies %}
{{ movie.title }}
{{ movie.content }}
{% endfor %}
{% endblock %}
when I seized a title of a movie he sends me this error
Variable "movies" does not exist in AreaDownloadBundle:Download:index.html.twig at line 12
Instead of posting it as a comment, it should have been posted as an answer in the correct formatting; like so:
return $this->render(
'AreaDownloadBundle:Download:index.html.twig',
array(
'form' => $form->createView(),
'movies' => $movies
)
);
This definitely should fix the problem!
i need your help please , I want to display my created form in Symfony2. I want to display my created form 92 times becouse i have 92 numbers in my database(every number is a form) , i didn't know how to do it here is my code:
controller:
class DefaultController extends Controller
{
public function QuestionsAction(Request $request)
{
$questions = $this->getDoctrine()->getEntityManager()
->getRepository('Tests\TestsPhpBundle\Entity\Question')
->findAll();
$task = new Question();
$forms = $this->createForm(new QuestionType(), $task);
if ($request->getMethod() == 'POST') {
$forms->bindRequest($request);
if ($forms->isValid())
{
$em = $this->getDoctrine()->getEntityManager();
$em->persist($task);
$em->flush();
}
}
{
return $this->render('TestsTestsPhpBundle:Default:index.html.twig', array(
'questions' => $questions,
'forms' => $forms->createView()
));
}
}
}
my form file:
class QuestionType extends AbstractType
{
public function buildForm(FormBuilder $builder, array $options)
{
$builder
->add('categories', null, array('required' => false,
))
->add('text', 'entity', array(
'class' => 'TestsTestsPhpBundle:Question',
'query_builder' => function($repository) {
return $repository->createQueryBuilder('p')->orderBy('p.id', 'ASC'); },
'property' => 'text'))
;
}
public function getDefaultOptions(array $options)
{
return array(
'data_class' => 'Tests\TestsPhpBundle\Entity\Question',);
}
public function getName()
{
return 'question';
}
}
my twig file:
{% block content %}
<h2>Questions</h2>
{% for question in questions %}
<dl>
<dt>Number</dt>
<dd>{{ question.number }}<dd>
{% for form in forms %}
{{ form_row(forms.categories) }}
{{ form_row(forms.text) }}
</dl>
{% endfor %}
<hr />
{% endfor %}
{% endblock %}
I recommend to read capter: Embedding Controller
http://symfony.com/doc/2.0/book/templating.html
<div id="sidebar">
{% render "AcmeArticleBundle:Article:recentArticles" with {'max': 3} %}
</div>
You can make a for loop within Twig Template and call an action (with parameter if needed) where you render the form. -> QuestionsAction in your case.
This is my file:
<?php
namespace EM\ExpensesBundle\Entity;
use Symfony\Component\Form\FormBuilder;
use Symfony\Component\Form\AbstractType;
class ChooseCatType extends AbstractType
{
public function buildForm(FormBuilder $builder, array $options)
{
$builder->add('name', 'entity', array(
'class' => 'EMMyFriendsBundle:Category',
'property' => 'name',
'empty_value' => 'All items',
'required' => false,
'query_builder' => function ($repository)
{ return $repository->createQueryBuilder('cat')
->select('cat')
->orderBy('cat.name', 'ASC');
}, ));
}
public function getName()
{
return 'choose_category';
}
}
Here I create the form:
namespace EM\ExpensesBundle\Controller;
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
use EM\ExpensesBundle\Entity\Category;
use EM\ExpensesBundle\Entity\ChooseCatType;
class HomeController extends Controller
{
public function indexAction()
{
//Categories
$cat = new Category();
$dd_form = $this->createForm(new ChooseCatType(), $cat);
return $this->render('EMExpensesBundle:Home:index.html.twig', array(
'dd_form' => $dd_form->createView()));
}
}
and template:
{% extends "::base.html.twig" %}
{% block title %}
Expenses
{% endblock %}
{% block body %}
<div class="content">
<p> Choose category: </p>
<form class="cat" action="" method="post" {{ form_enctype(dd_form) }}>
{{ form_widget(dd_form.name) }}
{{ form_rest(dd_form) }}
<input type="submit" value="Show items" />
</form>
Manage Categories
</div>
{% endblock %}
but I get an error:
Fatal error: Declaration of EM\ExpensesBundle\Entity\ChooseCatType::buildForm()
must be compatible with that
of Symfony\Component\Form\FormTypeInterface::buildForm()
in C:\xampp\htdocs\Expenses\src\EM\ExpensesBundle\Entity\ChooseCatType.php
on line 9
Any ideas?
Use FormBuilderInterface in your method signature:
public function buildForm(FormBuilderInterface $builder, array $options)