Partage
  • Partager sur Facebook
  • Partager sur Twitter

symfony : Menu a partir d'une table sql

    5 septembre 2017 à 16:47:42

    Bonjour, 

    Dans mon symfony, sur une vue, je voudrais faire afficher le nom des catégories de mes produits et les produits disponibles de cette catégories.

    J'utilise donc mon CategoriesController avec le code suivant : 

    <?php
    
    namespace Ecommerce\EcommerceBundle\Controller;
    
    use Symfony\Bundle\FrameworkBundle\Controller\Controller;
    
    class CategoriesController extends Controller
    {
        public function menuAction()
        {
            $em = $this->getDoctrine()->getManager();
            $categories = $em->getRepository('EcommerceBundle:Categories')->findAll();
            $produits = $em->getRepository('EcommerceBundle:Produits')->findBy(array('disponible' => 1));
            
            
            return $this->render('EcommerceBundle:Default:categories/modulesUsed/menu.html.twig', array('categories' => $categories, 'produits' => $produits));
        }
    }

    Dans ma vue pour afficher les catégories et les produits j'utilise une boucle for de produit in produits

    {% for produit in produits %}
        
            <li class="dropdown">
                <a class="dropdown-toggle" href="{{ path('categorieProduits', { 'categorie' : produit.categorie.id }) }}">
                    {{ produit.categorie.nom }}
                </a>
                <ul class="dropdown-menu">
                    <li class="dropdown-submenu">
                        <a href="{{ path('categorieProduits', { 'categorie' : produit.marque.id }) }}">{{ produit.marque.nom }}</a>
                        <ul class="dropdown-menu">
                            <li class="dropdown-submenu">
                                <a href="{{ path('categorieProduits', { 'categorie' : produit.gamme.id }) }}">{{ produit.gamme.nom }}</a>
                                <ul class="dropdown-menu">
                                    <li><a href="{{ path('presentation', {'id' : produit.id} ) }}"> {{ produit.nom }}</a></li>
                                </ul>
                            </li>
                          </ul>
                    </li>
                  </ul>
            </li>
    
    {% endfor %}

    Le soucis que je rencontre c'est que si j'ai plusieurs produits disponible dans une même catégorie, il m'affiche deux fois le nom de la catégorie, je n'arrive pas à faire afficher qu'une fois la catégorie.

    Comment résoudre cela ?

    Par avance, merci 


    • Partager sur Facebook
    • Partager sur Twitter
      5 septembre 2017 à 21:55:07

      Salut !

      Le principe est le même que celui exposé ici, avec les produits étant les acteurs et les catégories les films.

      • Partager sur Facebook
      • Partager sur Twitter
        5 septembre 2017 à 22:45:49

        Ymox a écrit:

        Salut !

        Le principe est le même que celui exposé ici, avec les produits étant les acteurs et les catégories les films.


        ok je vais voir cela pour l'adapter à symfony
        Merci

        -
        Edité par JeromeDédio'Web 5 septembre 2017 à 22:47:35

        • Partager sur Facebook
        • Partager sur Twitter
          5 septembre 2017 à 22:53:43

          C'est très similaire, hein. Tu n'as même pas vraiment à te soucier de la requête (sauf pour la trier). Et pour l'affichage, tu as des objets avec des propriétés plutôt qu'un tables.

          • Partager sur Facebook
          • Partager sur Twitter
            5 septembre 2017 à 23:04:04

            ce qui me perturbe c'est que sous SF, généralement on utilise $qb = $this->createQueryBuilder('u') ? non ?
            • Partager sur Facebook
            • Partager sur Twitter
              5 septembre 2017 à 23:10:01

              En fait, avec findBy(), tu peux aussi spécifier des clauses de tri, c'est le deuxième argument. Donc vraiment très peu à modifier de ce côté-là par rapport à ton code.

              C'est à l'affichage qu'il y aura le plus d'adaptations à faire. Mais ce n'est pas un très gros souci à mon avis, il faut juste bien réfléchir à ce qu'il y a dans l'exemple que je t'ai conseillé d'aller voir, et ce que tu as toi qui correspond.

              • Partager sur Facebook
              • Partager sur Twitter
                5 septembre 2017 à 23:33:21

                donc se serait plus un

                $produits = $em->getRepository('EcommerceBundle:Produits')->findBy(array('produits' => $produits),
                                array('categories' => $categories));







                • Partager sur Facebook
                • Partager sur Twitter
                  5 septembre 2017 à 23:34:57

                  Non.

                  Il y a juste un paramètre pour trier à ajouter au code que tu nous montrais dans le premier message, rien d'autre à changer dans le contrôleur.

                  • Partager sur Facebook
                  • Partager sur Twitter
                    5 septembre 2017 à 23:58:19

                    tu vas rire, j'étais sur la même page ! :D

                    J'ai donc mis cela

                    $produits = $em->getRepository('EcommerceBundle:Produits')->findBy(array('disponible' => 1),array('categorie' => 'ASC'));


                    par contre dans ma vue, il m'affiche encore deux fois la même catégorie...

                    • Partager sur Facebook
                    • Partager sur Twitter
                      6 septembre 2017 à 0:00:21

                      Montre-moi le code actuel de ta vue, et regarde si la requête est la bonne.

                      -
                      Edité par Ymox 6 septembre 2017 à 0:00:58

                      • Partager sur Facebook
                      • Partager sur Twitter
                        6 septembre 2017 à 0:02:34

                        tu l'as dans le premier message je boucle dans produit in produits

                        Edit : 

                        correction effectué (je suis sur le bon chemin) : :D

                        {% for produits in categories %}
                            
                                <li class="dropdown">
                                    <a class="dropdown-toggle" href="{# path('categorieProduits', { 'categorie' : produit.categorie.id }) #}">
                                        {{ produits.nom }}
                                    </a>
                                    <ul class="dropdown-menu">
                                        <li class="dropdown-submenu">
                                            <a href="{# path('categorieProduits', { 'categorie' : produit.marque.id }) #}">{# produit.marque.nom #}</a>
                                            <ul class="dropdown-menu">
                                                <li class="dropdown-submenu">
                                                    <a href="{# path('categorieProduits', { 'categorie' : produit.gamme.id }) #}">{# produit.gamme.nom #}</a>
                                                    <ul class="dropdown-menu">
                                                        <li><a href="{# path('presentation', {'id' : produit.id} ) #}"> {# produit.nom #}</a></li>
                                                    </ul>
                                                </li>
                                              </ul>
                                        </li>
                                      </ul>
                                </li>
                        
                        {% endfor %}



                        -
                        Edité par JeromeDédio'Web 6 septembre 2017 à 0:07:22

                        • Partager sur Facebook
                        • Partager sur Twitter
                          6 septembre 2017 à 0:08:08

                          Alors c'est normal que sans avoir adapté la vue comme dans l'exemple que je t'avais lié il n'y ait pas encore le comportement attendu.

                          Il te manque les éléments de test pour savoir si tu changes ou pas de catégorie. Utilise {% set … %}, si jamais.

                          -
                          Edité par Ymox 6 septembre 2017 à 0:09:05

                          • Partager sur Facebook
                          • Partager sur Twitter
                            6 septembre 2017 à 0:10:59

                            là tu m'as perdu avec {%set ...%}



                            -
                            Edité par JeromeDédio'Web 6 septembre 2017 à 0:13:37

                            • Partager sur Facebook
                            • Partager sur Twitter
                              6 septembre 2017 à 0:16:58

                              Si tu regardes le code dans l'autre sujet, j'ai utilisé des variables qui nous permettent de savoir quel film on manipulait. Il t'en faudra donc pour savoir dans quelle catégorie tu es. Et en Twig, l'équivalent de $truc = $chose-&gt;getMachin(), c'est {% set truc = chose.machin %}.

                              • Partager sur Facebook
                              • Partager sur Twitter
                                6 septembre 2017 à 0:24:40

                                si je comprend

                                {% set truc = chose.machin %}

                                est a inclure dans la boucle for ?

                                {% for produits in categories %}
                                {{ produits.nom }} // affiche le nom de la catégorie, ça c'est ok
                                {% set truc = chose.machin %} // affichera le nom du produit ?
                                {% endfor %}




                                -
                                Edité par JeromeDédio'Web 6 septembre 2017 à 0:25:42

                                • Partager sur Facebook
                                • Partager sur Twitter
                                  6 septembre 2017 à 0:41:58

                                  {% set … %} ne sert qu'à créer une variable Twig, cela n'affiche rien.

                                  En revanche, fais super attention au nommage de tes variables, parce que je sens que tu vas confondre : tu boucles sur categories, pourquoi est-ce qu'un élément de cette liste serait plusieurs produits ?

                                  Reprend ton code du premier message. Il faut ajouter les tests mentionnés dans l'autre sujet (lignes 20 à 22), et pour que le test fonctionne, il faut donc créer la variable (ligne 14) et la mettre à jour (ligne 28).

                                  • Partager sur Facebook
                                  • Partager sur Twitter
                                    6 septembre 2017 à 13:44:44

                                    Ymox a écrit:

                                    En revanche, fais super attention au nommage de tes variables, parce que je sens que tu vas confondre : tu boucles sur categories, pourquoi est-ce qu'un élément de cette liste serait plusieurs produits ?

                                    Car une catégorie à plusieurs produits.

                                    Je tourne en rond depuis ce matin, je n'arrive pas à comprendre le {% set ... %} c'est très certainement tout simple... mais je ne vois pas comment écrire la chose et où le placer.

                                    • Partager sur Facebook
                                    • Partager sur Twitter
                                      6 septembre 2017 à 18:12:00

                                      JeromeDédio'Web a écrit:

                                      Ymox a écrit:

                                      En revanche, fais super attention au nommage de tes variables, parce que je sens que tu vas confondre : tu boucles surcategories, pourquoi est-ce qu'un élément de cette liste serait plusieurs produits ?

                                      Car une catégorie à plusieurs produits.

                                      Oui, mais quand tu boucles sur un tableau de catégories, tu vas avancer catégorie par catégorie, c'est le but. Donc soit c'est un tableau de produits comme dans ton premier code, et à chaque tour de boucle, tu manipules un produit, soit tu boucles sur des catégories, et à chaque tour de boucle tu as une catégorie. Mais en aucun cas tu boucles sur des catégories pour avoir un produit.

                                      Une fois de plus, il ne manque pas grand-chose à ton premier code. Mais reste sur cette base.


                                      Tu as compris l'explication qu'il y a avec le code dans l'avant-dernier message du sujet que j'ai en premier ici ?

                                      -
                                      Edité par Ymox 6 septembre 2017 à 18:13:10

                                      • Partager sur Facebook
                                      • Partager sur Twitter
                                        6 septembre 2017 à 18:56:43

                                        Ymox a écrit:


                                        Tu as compris l'explication qu'il y a avec le code dans l'avant-dernier message du sujet que j'ai en premier ici ?

                                        -
                                        Edité par Ymox il y a 42 minutes


                                        Non je n'ai pas compris justement
                                        • Partager sur Facebook
                                        • Partager sur Twitter
                                          6 septembre 2017 à 19:10:09

                                          Alors je reprends.

                                          Déjà, comprends bien que, comme dans ton premier message et ce que tu as ici, tu as bien une liste de produits. L'idée, c'est de tous les afficher sous leurs catégories respectives, mais tu as cette information depuis le produit. Tu vas donc boucler sur tous les produits.

                                          Pour savoir si tu changes de catégorie quand tu changes de produit, il te faut :

                                          1. conserver une trace de la catégorie précédente. D'où le besoin de créer une variable pour conserver cette information, et donc l'utilisation de {% set … %} avant la boucle ;
                                          2. boucler sur les produits. Ils sont dans des catégories, on ne boucle pas sur ces dernières. Dans cette boucle, il faut :

                                            1. vérifier que le produit sur lequel tu es en train de boucler est dans la même catégorie que la précédente.

                                              • Si oui, tu n'affiches pas la catégorie.
                                              • Si non, ben il faut l'afficher.

                                              Un test avec un if (produit.categorie == taVariableCrééeEn1) fera l'affaire. Sachant que le gros du travail est là : bien déterminer le HTML qui sera ou non affiché en fonction du résultat de ce test ;

                                            2. afficher le produit ;
                                            3. mettre à jour la variable créée en 1 pour bien avoir la catégorie correcte pour le produit suivant. On utilise {% set … %} à nouveau, mais cette fois-ci dans la boucle.

                                          Est-ce que tu arrives à me montrer un code Twig avec ça mis en place (ou au moins un essai), s'il te plaît ?

                                          -
                                          Edité par Ymox 6 septembre 2017 à 19:10:58

                                          • Partager sur Facebook
                                          • Partager sur Twitter
                                            6 septembre 2017 à 22:52:54

                                            je pense avoir compris :

                                            {% set ref1 = 'ref1' %}
                                                {% for produit in produits %}
                                                    {% if (produit.categorie.nom == 'ref1') %}
                                                        
                                                        {% endif %}
                                                        <li class="dropdown">
                                                            <a class="dropdown-toggle" href="#">
                                                                {{ produit.categorie.nom }}
                                                            </a>
                                                            
                                                            <ul class="dropdown-menu">
                                                                <li>{{ produit.nom }}</li>
                                                            </ul>
                                                        
                                                        {% set ref1 = 'ref1' %}
                                                    {% endfor %}

                                            Mais je me retrouve toujours avec une catégorie qui s'affiche autant de fois qu'un produit y est présent



                                            • Partager sur Facebook
                                            • Partager sur Twitter
                                              7 septembre 2017 à 1:00:21

                                              Un peu de logique, que diable !

                                              1. Actuellement, tu ne changes rien à l'affichage si la catégorie est la même que lors de la boucle précédente, ton blocif lignes 3 à 5 ne sert en l'état strictement à rien vu qu'il n'y a rien ligne 4.
                                              2. Quand bien même la ligne 4 contiendrait quelque chose, tu testes le nom de la catégorie de l'objet avec une valeur statique…
                                              3. … valeur que tu as non-seulement mise dans ta variable ref1 au début, mais que tu remets dedans à chaque boucle. A quoi te sert ta variable ref1 actuellement ? A rien, parce qu'elle n'est pas utilisée et n'est pas vraiment mise à jour. Et comme j'imagine que tu n'as absolument aucune catégorie dont le nom est "ref1", même en ayant changé les éléments 1 et 2, ça ne t'afficherait toujours pas ce que tu souhaites.

                                              Regarde bien comment est utilisée la variable $films dans le code d'exemple de l'autre sujet, c'est l'équivalent de ta variable ref1.

                                              -
                                              Edité par Ymox 7 septembre 2017 à 1:02:32

                                              • Partager sur Facebook
                                              • Partager sur Twitter
                                                7 septembre 2017 à 12:05:49

                                                Hello,

                                                J'ai revu le code : 

                                                {% set refCategorie = '' %}
                                                    {% for produit in produits %}
                                                        {% if (refCategorie != produit.categorie.nom) %}
                                                            <li class="dropdown">
                                                               <a class="dropdown-toggle" href="#">
                                                                   {{ produit.categorie.nom }}
                                                               </a>
                                                               
                                                        {% endif %}
                                                	    	   
                                                        {{ produit.nom }}</br>
                                                                                      
                                                        {% set refCategorie = produit.categorie.nom %}
                                                        
                                                           
                                                    {% endfor %}

                                                Maintenant il me reste a voir niveau mise en page html, si je me suis pas trompé dans le code :D
                                                -------------

                                                A mon avis, j'ai une erreur encore dans le code puisque l'affiche html n'est pas correct

                                                -
                                                Edité par JeromeDédio'Web 7 septembre 2017 à 19:16:57

                                                • Partager sur Facebook
                                                • Partager sur Twitter
                                                  8 septembre 2017 à 10:24:25

                                                  Si tu regardes bien, à chaque nouvelle catégorie, tu ouvres un <li>, mais tu ne le refermes jamais. Au vu de ton HTML, il va falloir adapter un petit peu l'algorithme — pas grand chose, je te rassure, il devrait suffire d'un test pour déterminer si c'est la première fois qu'on passe dans la boucle.
                                                  Parce qu'à chaque nouvelle catégorie, il faut fermer la liste précédente, et ouvrir la nouvelle. MAIS lors de la première boucle, on n'a pas de précédente à fermer, d'où le test à ajouter.
                                                  Il faut donc que, dans le if existant, on vérifie si on n'est pas dans la première boucle ({% if loop.index != 1 %}), et le cas échéant, on referme les listes ouvertes pour la catégorie précédente.

                                                  Qui plus est, il me semble que les éléments à afficher au clic sur un dropdown ne sont pas directement après le lien qui capture l'événement, il doit y avoir un autre conteneur, non ? Donc chaque produit doit être dans un <li>.
                                                  Ceci explique pourquoi j'ai bien parlé des listes précédentes au pluriel : il y en a une qui inclut le titre de la catégorie, et l'autre qui contient les produits.

                                                  • Partager sur Facebook
                                                  • Partager sur Twitter
                                                    8 septembre 2017 à 13:03:22

                                                    Hello, 

                                                    merci pour cet éclaircissement, je pense avoir trouvé : 

                                                    {% set refCategorie = '' %}
                                                        {% for produit in produits %}
                                                            {% if (refCategorie != produit.categorie.nom) %}
                                                                
                                                                    <li class="dropdown">
                                                                        <a class="dropdown-toggle" href="#">
                                                                            {{ produit.categorie.nom }}
                                                                        </a>
                                                                        <ul class="dropdown-menu">
                                                                    
                                                                        {% endif %} 
                                                                        
                                                                        <li>{{ produit.nom }}</li>
                                                                    {% if loop.index != 1 %}</ul></li>{% endif %}
                                                                                           
                                                            {% set refCategorie = produit.categorie.nom %}
                                                                        
                                                        {% endfor %}

                                                    tu en penses quoi ?

                                                    • Partager sur Facebook
                                                    • Partager sur Twitter
                                                      8 septembre 2017 à 13:11:38

                                                      Qu'il faut tester  ^^

                                                      Je n'ai jamais réussi à voir ce qui ne jouait pas sans regarder le résultat pour ce genre de boucles avec des éléments imbriqués. Mais le test que je t'ai dit d'ajouter doit être placé juste après le premier. Là, tu vas ouvrir une catégorie et la fermer juste après. Or, tu dois fermer la précédente, donc fermer avant d'ouvrir.

                                                      -
                                                      Edité par Ymox 8 septembre 2017 à 13:12:07

                                                      • Partager sur Facebook
                                                      • Partager sur Twitter
                                                        5 octobre 2017 à 0:48:42

                                                        Hello Ymox, 

                                                        je reviens avec mon menu lol, 

                                                        J'ai essayé de comprendre ce que tu me disais avec le loop.index, j'ai donc retravaillé le code, mais il ne m'affiche que le premier a chaque fois, je ne comprend pas pourquoi

                                                        Voici le code, si tu pouvais y jeter un oeil et me faire un retour, par avance, merci

                                                        {% set refCategorie = '' %}
                                                        
                                                        <nav>
                                                            <ul class="nav nav-pills" id="mainNav">
                                                                {% for produit in produits %}
                                                                    {% if (refCategorie != produit.categorie.nom) %}
                                                                      {% if loop.index != 1 %}</ul>
                                                                    </li>
                                                                  </ul>
                                                                    </li>
                                                                    {% endif %}
                                                                        <li class="dropdown">
                                                                            <a class="dropdown-toggle" href="#">{{ produit.categorie.nom }}</a>
                                                                            <ul class="dropdown-menu">
                                                                                <li class="dropdown-submenu">
                                                                                    <a href="#">{{ produit.marque.nom }}</a>
                                                                                    <ul class="dropdown-menu">
                                                                                        <li>{{ produit.gamme.nom }}</li>
                                                                                    {% set refCategorie = produit.categorie.nom %}
                                                                  {% endif %}
                                                                {% endfor %}
                                                            </ul>
                                                        </nav>
                                                        



                                                        -
                                                        Edité par JeromeDédio'Web 5 octobre 2017 à 0:50:08

                                                        • Partager sur Facebook
                                                        • Partager sur Twitter
                                                          5 octobre 2017 à 9:59:05

                                                          Tu peux montrer le HTML qui est généré avec ça (en corrigeant l'indentation des balises si besoin) ?

                                                          • Partager sur Facebook
                                                          • Partager sur Twitter

                                                          symfony : Menu a partir d'une table sql

                                                          × Après avoir cliqué sur "Répondre" vous serez invité à vous connecter pour que votre message soit publié.
                                                          × Attention, ce sujet est très ancien. Le déterrer n'est pas forcément approprié. Nous te conseillons de créer un nouveau sujet pour poser ta question.
                                                          • Editeur
                                                          • Markdown