monamona
monamona

Reputation: 1246

How to access a form input when the form is rendered in a separate twig?

I want to create a search bar in my navbar, so one can simply search for a user on my page.

I have a base.html.twig, where the navbar, the header, the footer, and more are defined, to make all my pages have the same layout. I have then for every subpage e.g. a profile.html.twig, which defines the actual content of the page.

I wanted to include a search line in the navbar, so I read about embedding controllers, which seemed like a perfect idea for me. So I created a SearchForm class, which builds a form with the FormBuilderInterface like so:

class SearchForm extends AbstractType
{
     public function buildForm(FormBuilderInterface $builder, array $options)
     {
         $builder
              ->add('searched_name')
        ;
    }
}

Then I created a SearchController, which would contain the logic for what should happen when the search form would be submitted and should return a render of the form.

class SearchController extends AbstractController
{
    /**
     * @param Request $request
     *
     * @return Response|RedirectResponse
     *
     * @Route("/search", name="search", methods={"GET","POST"})
     */
    public function renderSearch(Request $request) {
        $form = $this->createForm(SearchForm::class);
        $form->handleRequest($request);

        if ($form->isSubmitted() && $form->isValid()) {
            return $this->redirectToRoute('ping');
            //TODO: Implement search logic
        }
        return $this->render('searchForm.html.twig', [
            'form' => $form->createView()
        ]);
    }
}

I thought, that I now could simply go ahead and let the search form be rendered in the base.html.twig:

<div class="topnav" id="navbar">
    <a href="/start">Startseite</a>
    <a href="/overview">Übersicht</a>
    <a href="/about">Über uns</a>
    {{ render(url('search')) }}
    <a href="/profile" style="float:right">
        {% if app.user %}
            {{ app.user.username }}
        {% else %}
            Mein Profil
        {% endif %}
    </a>
</div>

It actually does get rendered, but the problem is, that as soon as I press Enter to submit the form with the search input, the POST request is not sent to the searchController, but to whichever controller is responsible for handling, let's say, the profile page.

I guess it has to do something with the entire site being rendered there, since I just inherit the base.html.twig in all of my other pages, so the submit requests are sent there. I tested this by calling the search route directly, and that made it work completely fine.

How can I make this formwork on every site without having to reimplement the search logic in every single controller? (That's what this base is made for, after all...)

Upvotes: 1

Views: 367

Answers (1)

Frank B
Frank B

Reputation: 3697

First of all you could (of course) set the action attribute of the form. Follow this link to find out how: https://symfony.com/doc/4.2/form/action_method.html

But since you show your form on every single page on your website you should ask yourself if you want to redirect the user to an other page after form submit. The answer could be yes or could be no but if it is no then you have the opportunity to use an AJAX submit.

Upvotes: 1

Related Questions