Rendu personnalisé d'un champ "répété" de Symfony 2 dans Twig

Je viens de commencer à utiliser Twig et j'essaie de créer un formulaire d'inscription. Pour ajouter un mot de passe / entrer de nouveau le champ de mot de passe, j'utilise le type de fichier "répété":

->add('password', 'repeated', array(
    'type' => 'password',
    'invalid_message' => 'Passwords have to be equal.',
    'first_name'      => 'Password',
    'second_name'     => 'Re-enter password',
));

Qui fonctionne comme prévu. Le problème que j'ai cependant est que je veux ajouter des classes personnalisées, etc. pour ma forme. Donc, mon modèle ressemble à ceci:

<form action="{{ path('register') }}" method="post" {{ form_enctype(form) }}>
    {{ form_errors(form) }}
    {{ form_errors(form.username) }}
    <div class="form-field">
        {{ form_label(form.username, null, { 'attr': {'class': 'form-label'} }) }}
        {{ form_widget(form.username, { 'attr': {'class': 'form-input'} }) }}
    </div>
    {{ form_errors(form.email) }}
    <div class="form-field">
        {{ form_label(form.email, null, { 'attr': {'class': 'form-label'} }) }}
        {{ form_widget(form.email, { 'attr': {'class': 'form-input'} }) }}
    </div>
    {{ form_errors(form.password) }}
    <div class="form-field">
        {{ form_label(form.password, null, { 'attr': {'class': 'form-label'} }) }}
        {{ form_widget(form.password, { 'attr': {'class': 'form-input'} }) }}
    </div>

    {{ form_rest(form) }}

    <input type="submit" class="contact-submit" />
</form>

Cela fonctionne bien pour tout sauf pour la partie mot de passe. Je veux rendre les deux champs séparément, maintenant ils sont juste tous les deux rendus dans le même div.

Comment puis-je résoudre ce problème? Existe-t-il un moyen de sélectionner les champs séparés dans Twig? Ou est-ce que je fais juste quelque chose de mal parce que je rencontre ce problème en premier lieu.

26
demandé sur Jonathan Leffler 2012-05-20 20:52:13

5 réponses

Après une supposition aléatoire, j'ai résolu mon propre problème. Je vais le poster ici pour que les autres qui pourraient venir à cette question en cherchant connaissent aussi la réponse:

{% for passwordField in form.password %}
    <div class="form-field">
        {{ form_label(passwordField, null, { 'attr': {'class': 'form-label'} }) }}
        {{ form_widget(passwordField, { 'attr': {'class': 'form-input'} }) }}
    </div>
{% endfor %}
54
répondu teuneboon 2012-05-20 17:01:16

Si vous voulez séparer les deux champs de mots de passe d'une méthode répétée dans votre modèle de brindille, il vous suffit de rappeler leurs noms respectifs comme:

{{ form_label(form.password.pass, "Password :") }}
{{ form_widget(form.password.pass) }}

{{ form_label(form.password.confirm, "Confirm :") }}
{{ form_widget(form.password.confirm) }}

Et, bien sûr, dans votre fonction:

/..
->add('password', 'repeated', array(
'first_name' => 'pass',
'second_name' => 'confirm',
'type' => 'password'
))

Cordialement.

22
répondu Log 2012-07-18 07:22:55

Cela fonctionne pour moi:

....
{{ form_errors(form.password.first) }}
<div class="form-field">
    {{ form_label(form.password.first, null, { 'attr': {'class': 'form-label'} }) }}
    {{ form_widget(form.password.first, { 'attr': {'class': 'form-input'} }) }}
</div>

{{ form_errors(form.password.second) }}
<div class="form-field">
    {{ form_label(form.password.second, null, { 'attr': {'class': 'form-label'} }) }}
    {{ form_widget(form.password.second, { 'attr': {'class': 'form-input'} }) }}
</div>
....
18
répondu cslucano 2013-07-06 10:00:19

Si vous utilisez un Bundle D'utilisateurs, ils utilisent le mot de passe.premier et le mot de passe.deuxièmement, essayez encore mieux d'utiliser votre profileur pour voir quelles variables proviennent de la vue et des contrôleurs;)

3
répondu Luis Lopes 2014-04-20 10:47:01

Si vous souhaitez avoir des classes à l'échelle de l'application pour vos étiquettes et vos entrées, vous pouvez personnaliser le rendu des étiquettes et des widgets. Vérifier http://symfony.com/doc/current/cookbook/form/form_customization.html

, Si vous regardez ce fichier:

vendor/symfony/src/Symfony/Bridge/Twig/Resources/views/Form/form_div_layout.html.twig

Vous pouvez voir les valeurs par défaut pour tous les widgets. Pour réaliser spécifiquement ce dont vous avez besoin, vous pouvez remplacer le bloc generic_label pour ajouter la classe Form-label:

{% block generic_label %}
{% spaceless %}
    {% if required %}
        {# We add form-label class in the next line! #}
        {% set attr = attr|merge({'class': attr.class|default('') ~ ' required form-label'}) %}
    {% endif %}
    <label{% for attrname,attrvalue in attr %} {{attrname}}="{{attrvalue}}"{% endfor %}>{{ label|trans }}</label>
{% endspaceless %}
{% endblock %}

Et widget_attributes bloquent pour ajouter une entrée de formulaire classe:

{% block widget_attributes %}
{% spaceless %}
    {# We add form-input class in the next line! #}
    {% set attr = attr|merge({'class': attr.class|default('') ~ ' form-input'}) %}
    id="{{ id }}" name="{{ full_name }}"{% if read_only %} disabled="disabled"{% endif %}{% if required %} required="required"{% endif %}{% if max_length %} maxlength="{{ max_length }}"{% endif %}{% if pattern %} pattern="{{ pattern }}"{% endif %}
    {% for attrname,attrvalue in attr %}{{attrname}}="{{attrvalue}}" {% endfor %}
{% endspaceless %}
{% endblock widget_attributes %}

Avec ces deux modèles, toutes vos entrées doivent être affichées avec les classes dont vous avez besoin, sans avoir à répéter les paramètres 'attr' dans tous vos formulaires.

Je ne l'ai pas essayé, mais cela devrait prendre en charge le problème de terrain répété. Même si ce n'est pas le cas, vous pouvez créer un modèle repeated_widget et/ou repeated_row pour personnaliser le rendu du widget répété, fixant ainsi ce widget pour toutes les formes qui l'utilisent.

0
répondu Jens 2012-05-22 01:01:10