使用表单实体fieldtype(Symfony3)在Twig模板中使用自定义html包装复选框

时间:2017-02-12 16:24:18

标签: twig symfony symfony-forms

当Symfony3呈现表单时,我想用twig模板中的自定义HTML包装复选框。

而不是:

<input type="checkbox" id="form_role_1" name="form[role][]" value="1" />
<label for="form_role_1">ROLE 1</label>
<input type="checkbox" id="form_role_2" name="form[role][]" value="2" />
<label for="form_role_2">ROLE 2</label>
<input type="checkbox" id="form_role_3" name="form[role][]" value="3" />
<label for="form_role_3">ROLE 3</label>

我想得到这样的东西:

<div class="input-group">
    <input type="checkbox" id="form_role_1" name="form[role][]" value="1" />
    <label for="form_role_1">ROLE 1</label>
</div>

<div class="input-group">
    <input type="checkbox" id="form_role_2" name="form[role][]" value="2" />
    <label for="form_role_2">ROLE 2</label>
</div>

<div class="input-group">
    <input type="checkbox" id="form_role_3" name="form[role][]" value="3" />
    <label for="form_role_3">ROLE 3</label>
</div>

在控制器动作中:

    $form = $this->createForm(RolesFormType::class, $roles);
    $form->handleRequest($request);

    return $this->render(
        'role/edit_roles.html.twig',
        array(
            'form' => $form->createView()
        )
    );
表单类型中的

class RolesFormType extends AbstractType
{

    public function buildForm(FormBuilderInterface $builder, array $options) {
        $builder
            ->add('role', EntityType::class, array(
                'label' => 'form.elements.roles',
                'class' => 'RoleBundle\Entity\Role',
                'choice_label' => 'role_name',
                'expanded' => true,
                'multiple' => true
        ));
    }
}

经典模板如下所示:

    <div class="container-fluid">
        <div class="row">

            {{ form_start(form, {'method': "POST"}) }}

            <div class="col-md-12">

                <div class="form-group">
                    {{ form_errors(form.role) }}
                    {{ form_widget(form.role, {}) }}
                </div>

            </div>

            {{ form_rest(form) }}
            {{ form_end(form) }}

        </div>
    </div>

我在树枝模板中尝试了这种方式,但只渲染了标签:

    <div class="container-fluid">
        <div class="row">

            {{ form_start(form, {'method': "POST"}) }}

            <div class="col-md-12">

                {% for role in form.role %}
                <div class="input-group">
                    {{ form_label(role) }}
                    {{ form_widget(role) }}
                </div>
                {% endfor %}

            </div>

            {{ form_rest(form) }}
            {{ form_end(form) }}

        </div>
    </div>

是否可以在不创建新字段类型的情况下使用?

溶液

关于@ xabbuh的回答我在How to Customize Form Rendering in Symfony 3

找到了解决方案

我在Bundle中创建了一个文件夹: src/RoleBundle/Resources/views/form

我用这个内容将新文件(fields.html.twig)放入其中

{%- block choice_widget_expanded -%}
    <div {{ block('widget_container_attributes') }}>
        {%- for child in form %}
        <div class="input-group">
            {{- form_widget(child) -}}
            {{- form_label(child, null, {translation_domain: choice_translation_domain}) -}}
        </div>
        {% endfor -%}
    </div>
{%- endblock choice_widget_expanded -%}

与此同时,我找到另一个问题来处理这个问题: Overriding symfony radio widget

2 个答案:

答案 0 :(得分:2)

您可以使用自定义表单主题自定义表单的呈现。您可以在项目级别上执行此操作,也可以仅针对特定表单执行此操作(有关详细信息,请参阅How to Customize Form RenderingHow to Work with Form Themes)。

您的示例似乎需要覆盖choice_widgetchoice_label

答案 1 :(得分:1)

当我玩symfony不是很熟练时,我不经常使用这个公认的解决方案来解决它

视图:

ParseClient.Configuration

控制器:

<label class="layui-form-label">所属地市:</label>
                <div class="layui-inline">
                    <select name="{{ form.cityId.vars.full_name }}"  lay-verify="" id="{{ form.cityId.vars.id }}" lay-filter="case_city">
                        <option value="0">请选择</option>
                        {% if citylist is not empty %}
                            {% for list in citylist %}
                                <option value="{{ list.id is defined ? list.id : 0 }}">{{ list.areaName is defined ? list.areaName : '' }}</option>
                            {% endfor %}
                        {% endif %}
                    </select>
                </div>

这也可以解决我的问题,但是当我迟到来优化它或者必须改变它们。但我希望这个答案可以解决你目前的问题。