Arhn - архитектура программирования

Symfony — форма рендеринга (с прототипом)

У меня есть графическая проблема с формой прототипа Symfony. Моя сущность "CompetenceGroupe" может иметь много объектов сущности "CompetenceItem". Все работает нормально, но рендеринг не идеален.

Когда я создаю новую CompetenceGroupe, в моей форме я могу добавлять и удалять подформы CompetenceItems. Форма правомочности имеет текстовый ввод, выбор ввода и кнопку «удалить» (выделена красным цветом, сгенерирована javascript).

Я пытаюсь выровнять эти три элемента, но кнопка удаления всегда находится под двумя другими элементами.

Что я хочу отобразить в представлении:

введите здесь описание изображения

И что я имею сейчас:

введите здесь описание изображения

В моем инструменте разработчика из Google Chrome я вижу, что кнопка удаления (с классом «btn-danger») находится не в том же div, что и два других элемента моего прототипа (с классом «competence_groupe_competence_items_0»):

введите здесь описание изображения

Я даю вам код моего представления прототипа (competence_item_prototype.html.twig)

{% block competence_item_widget %}

    <div id="{{ form.vars.id }}" class="row">

        <div class="col-md-7">
            {{ form_label(form.libelle, "Libelle", {'label_attr': {'class': 'sr-only control-label'}}) }}
            {{ form_errors(form.libelle) }}
                {{ form_widget(form.libelle, {'attr': {'class': 'form-control', 'placeholder': 'Libellé'}}) }}
        </div>

        <div class="col-md-3">
            {{ form_label(form.niveau, "Niveau", {'label_attr': {'class': 'sr-only control-label'}}) }}
            {{ form_errors(form.niveau) }}
                {{ form_widget(form.niveau, {'attr': {'class': 'form-control selectModal'}}) }}
        </div>

    </div>

{% endblock %}

И мой основной вид (с формой CompetenceGroupe) и код Javascript для создания кнопок «удалить» в каждой форме прототипа:

{% form_theme formAddCompetence 'espaceUtilisateur/forms/prototypes/competence_item_prototype.html.twig' %}

{{ form_start(formAddCompetence, { 'attr': {'class': 'formCompetenceAdd'} }) }}

    <div class="modal-header">
        <button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
        <h4 class="modal-title" id="myModalLabel">{{ libelleCategorie }}</h4>
    </div>

    <div class="modal-body">

        <h4><span class="label label-default">Les champs marqués d'un astérisque sont obligatoires.</span></h4>

        {{ form_row(formAddCompetence.titre) }}

        {{ form_row(formAddCompetence.competence_items) }}

        {{ form_widget(formAddCompetence._token) }}

        <br>
        <a href="#" id="add_category" class="btn btn-default">Ajouter une catégorie</a>

    </div>

    <div class="modal-footer">
        <button type="button" class="btn btn-default" data-dismiss="modal">Annuler</button>

        {% if objectCompetence.idCompetenceGroupe is not empty %}
            {{ form_widget(formAddCompetence.edit) }}
            <input type="hidden" name="idCompetenceGroupe" id="idCompetenceGroupe" value="{{ objectCompetence.idCompetenceGroupe }}">
        {% else %}
            {{ form_widget(formAddCompetence.save) }}
        {% endif %}
    </div>

</form>

<script type="text/javascript">
    $(document).ready(function() {
        // On récupère la balise <div> en question qui contient l'attribut « data-prototype » qui nous intéresse.
        var $container = $('div#competence_groupe_competence_items');

        // On définit un compteur unique pour nommer les champs qu'on va ajouter dynamiquement
        var index = $container.find(':input').length;

        // On ajoute un nouveau champ à chaque clic sur le lien d'ajout.
        $('#add_category').click(function(e) {
            addCategory($container);

            e.preventDefault(); // évite qu'un # apparaisse dans l'URL
            return false;
        });

        // On ajoute un premier champ automatiquement s'il n'en existe pas déjà un (cas d'une nouvelle annonce par exemple).
        if (index == 0) {
            addCategory($container);
        } else {
            // S'il existe déjà des catégories, on ajoute un lien de suppression pour chacune d'entre elles
            $container.children('div').each(function() {
                addDeleteLink($(this));
            });
        }

        // La fonction qui ajoute un formulaire CategoryType
        function addCategory($container) {
            // Dans le contenu de l'attribut « data-prototype », on remplace :
            // - le texte "__name__label__" qu'il contient par le label du champ
            // - le texte "__name__" qu'il contient par le numéro du champ
            var template = $container.attr('data-prototype')
                            .replace(/__name__label__/g, 'Catégorie n°' + (index+1))
                            .replace(/__name__/g,        index)
                    ;


            // On crée un objet jquery qui contient ce template
            var $prototype = $(template);

            // On ajoute au prototype un lien pour pouvoir supprimer la catégorie
            addDeleteLink($prototype);

            // On ajoute le prototype modifié à la fin de la balise <div>
            $container.append($prototype);

            // Enfin, on incrémente le compteur pour que le prochain ajout se fasse avec un autre numéro
            index++;
        }

        // La fonction qui ajoute un lien de suppression d'une catégorie
        function addDeleteLink($prototype) {

            // Création du lien
            //var $deleteLink = $('<div><a href="#" class="btn btn-danger">Supprimero</a></div>'); // OLD
            var $deleteLink = $('<div class="col-md-1"><button class="btn btn-danger"><i class="fa fa-trash-o"></i></button></div>');

            // Ajout du lien
            $prototype.last().append($deleteLink); // OLD

            // Ajout du listener sur le clic du lien pour effectivement supprimer la catégorie
            $deleteLink.click(function(e) {
                $prototype.remove();

                e.preventDefault(); // évite qu'un # apparaisse dans l'URL
                return false;
            });
        }
    });
</script>

Спасибо всем, кто может найти время, чтобы помочь мне.

31.08.2017

Ответы:


1

Не можете ли вы просто добавить его к .row?

    function addDeleteLink($prototype) {

        // Création du lien
        //var $deleteLink = $('<div><a href="#" class="btn btn-danger">Supprimero</a></div>'); // OLD
        var $deleteLink = $('<div class="col-md-1"><button class="btn btn-danger"><i class="fa fa-trash-o"></i></button></div>');

        // Ajout du lien
        $prototype.find('.row').append($deleteLink); // OLD

        // Ajout du listener sur le clic du lien pour effectivement supprimer la catégorie
        $deleteLink.click(function(e) {
            $prototype.remove();

            e.preventDefault(); // évite qu'un # apparaisse dans l'URL
            return false;
        });
    }
31.08.2017
Новые материалы

Коллекции публикаций по глубокому обучению
Последние пару месяцев я создавал коллекции последних академических публикаций по различным подполям глубокого обучения в моем блоге https://amundtveit.com - эта публикация дает обзор 25..

Представляем: Pepita
Фреймворк JavaScript с открытым исходным кодом Я знаю, что недостатка в фреймворках JavaScript нет. Но я просто не мог остановиться. Я хотел написать что-то сам, со своими собственными..

Советы по коду Laravel #2
1-) Найти // You can specify the columns you need // in when you use the find method on a model User::find(‘id’, [‘email’,’name’]); // You can increment or decrement // a field in..

Работа с временными рядами спутниковых изображений, часть 3 (аналитика данных)
Анализ временных рядов спутниковых изображений для данных наблюдений за большой Землей (arXiv) Автор: Рольф Симоэс , Жильберто Камара , Жильберто Кейрос , Фелипе Соуза , Педро Р. Андраде ,..

3 способа решить квадратное уравнение (3-й мой любимый) -
1. Методом факторизации — 2. Используя квадратичную формулу — 3. Заполнив квадрат — Давайте поймем это, решив это простое уравнение: Мы пытаемся сделать LHS,..

Создание VR-миров с A-Frame
Виртуальная реальность (и дополненная реальность) стали главными модными терминами в образовательных технологиях. С недорогими VR-гарнитурами, такими как Google Cardboard , и использованием..

Демистификация рекурсии
КОДЕКС Демистификация рекурсии Упрощенная концепция ошеломляющей О чем весь этот шум? Рекурсия, кажется, единственная тема, от которой у каждого начинающего студента-информатика..