Salut ,

J'aurais une question pour les pro SF2:

j'ai une vue edit.html.twig et new.html.twig.
Tous les 2 ont le meme formulaire, mais avec un titre et un texte submit différent.

Du coup je me suis demandé si ce n'etait pas plus judicieux de faire un _form.html.twig pour le formulaire et faire un include dans edit et new, et ajouter des variables pour le texte dans les vues qui seront interprété par form.

Est ce une bonne idée ?? Niveau performance cela vaut il le coup ??

Page _form.html.twig

{% extends '::base.html.twig' %}

{% block body %}

    <div class="page-header">
        <h1>{{ title }}</h1>
    </div>

    <div class="row">
        <div class="col-md-12 well">
            {{ form_start(form, {"method": "POST", "attr":{"novalidate":"novalidate"}}) }}
            {{ form_row(form.title) }}
            ...
            <button type="submit" class="btn btn-primary">{{ btnvalue }}</button>
            {{ form_end(form) }}
        </div>
    </div>

{% endblock %}

new.html.twig

{% include '_form.html.twig' with {'title': 'Ajouter une nouvelle page', 'btnvalue':'Enregistrer la page'} %}

edit.html.twig

{% include '_form.html.twig' with {'title': 'Editer la page' , 'btnvalue':'modifier les infos'} %}

7 réponses


SimonAndGarfunkel
Réponse acceptée

Salut Mikachu,

une idée comme ça : tu prends la même vue pour les 2 actions (new et edit) et tu testes:

{% if page.id is defined %}{% endif %}

Si {{ page.id }} existe, alors tu es dans le cas de l'édition d'une page, si non, c'est une nouvelle.
Tu peux aussi stoker le résultat dans une varible que tu utiliseras lorsque tu en auras besoin:

{% if page.id is defined %}
    {% set is_form_edit = true %}
{% else %}
    {% set is_form_edit = false %}
{% endif %}

Salut
L'idée est bonne mais tu gère comment à savoir si le formulaire a déjà des donnée ou non ?
sachant que soit tu envoie new Objet() soit avec le repository->findById($id)
En gros tu e gère direct dans le controller ?
Pour moi c'est la même chose car un copier coller ou un autre copier coller revien au même mais ta méthode devien plus pratique pour les éventuelles modifications !
Tu en fait pas en double ou triple etc...

Mikachu
Auteur

salut,
je le gere par le controller. Et la vue est appelé par celui ci.

En fait je me demandais si cela valait le coup de faire comme mon post précedent ou plutot mettre en variable dans le return (chose que je voulais éviter dans le sens où je me dis que cela concerne le template et non du traitement et ainsi pour modifier le texte plus logique dans view que controller, si tu vois ce que je veux dire)

Voici le new et edit du controller:

/**
     * @Route("/new", name="page_new")
     * @Method({"GET", "POST"})
     */
    public function newAction(Request $request)
    {
        $page = new Page();
        $newForm = $this->createForm(new PageType(), $page);
        $newForm->handleRequest($request);
        if($newForm->isSubmitted() && $newForm->isValid()) {
            $em = $this->getDoctrine()->getManager();
            $em->persist($page);
            $em->flush();
            return $this->redirectToRoute("page_index");
        }
        return $this->render("Page/new.html.twig", array(
            "page" => $page,
            "form" => $newForm->createView()
        ));
    }

    /**
     * @Route("/edit/{id}", requirements={"id" = "\d+"}, name="page_edit")
     * @Method({"GET", "POST"})
     */
    public function editAction(Page $page, Request $request)
    {   
        $em = $this->getDoctrine()->getManager();
        $editForm = $this->createForm(new PageType(), $page);
        $editForm->handleRequest($request);
        if($editForm->isSubmitted() && $editForm->isValid()) {
            $em->flush();
            return $this->redirectToRoute("page_index");
        }
        return $this->render("Page/edit.html.twig", array(
            "page" => $page,
            "form" => $newForm->createView()
        ));
    }
Mikachu
Auteur

Salut SimonAndGarfunkel

J'aime bien ton idée. Et niveau performance nikel je penses contrairement à moi. et tout est géré sur une meme vue (donc 1 fichier)
Du coup pour afficher le titre et le bouton en fonction de l'action je ferais

{% if page.id is defined %}
    {% set title = "Modifier la page" %}
    {% set btnvalue = "Mettre à jour" %}
{% else %}
    {% set title = "Ajout d'une nouvelle page" %}
    {% set btnvalue = "Enregistrer" %}
{% endif %}

{% extends '::base.html.twig' %}

{% block body %}

    <div class="page-header">
        <h1>{{ title }}</h1>
    </div>

    <div class="row">
        <div class="col-md-12 well">
            {{ form_start(form, {"method": "POST", "attr":{"novalidate":"novalidate"}}) }}
            {{ form_row(form.title) }}
            ...
            <button type="submit" class="btn btn-primary">{{ btnvalue }}</button>
            {{ form_end(form) }}
        </div>
    </div>

{% endblock %}

Ouai, ça semble pas déconnant... le controller et la vue sont comme cela bien séparés. N'oublie pas de mettre le sujet en "résolu".

Récemment, je suis tombé sur ce lien : http://twig.sensiolabs.org/doc/tags/import.html

Apparement, y'a moyen de faire une macro et de l'incorporer dans n'importe quel fichier de template. En plus, l'exemple montre comment gérer des formulaires.

Peut-être est-ce une autre possibilité de rendre plus modulaire ce fonctionnement, en fonction de tes besoins ?

Mikachu
Auteur

J'adopte pour le submit ca me fera economiser une variable :) .

Merci