Forms Symfony 2.8.x:自定义FormType覆盖表单变量

Forms Symfony 2.8.x:自定义FormType覆盖表单变量,forms,symfony,Forms,Symfony,我有一个有多个字段的表单。 我还使用一些自定义表单类型,例如DivType来添加文本、按钮、图片或其他未映射到数据库的内容 将代码升级到Symfony 2.8语法会导致不需要的行为 我的表格: class ExampleType extends AbstractType { public function buildForm(FormBuilderInterface $builder, array $options) { // A couple of fields, f

我有一个有多个字段的表单。 我还使用一些自定义表单类型,例如DivType来添加文本、按钮、图片或其他未映射到数据库的内容

将代码升级到Symfony 2.8语法会导致不需要的行为

我的表格:

class ExampleType extends AbstractType {
    public function buildForm(FormBuilderInterface $builder, array $options) {

        // A couple of fields, for example field1
        $builder->add('field1', 'text', array(
            //  text field
        ));

        // A div element
        $builder->add('div_id_1', new DivType(), array(
            'content' => 'Just some content in the first div',
        ));

        // Another div
        $builder->add('div_id_2', new DivType(), array(
            'content' => 'A div with some images, buttons or other cool stuff',
        ));

    }
}
My DivType.php:

class DivType extends AbstractType {

    private $content;
    private $id;

    public function buildForm(FormBuilderInterface $builder, array $options) {
        $this->content = $options['content'];
        $this->id = $builder->getName();
    }

    public function buildView(FormView $view, FormInterface $form, array $options) {
        $view->vars['div_content'] = $this->content;
        $view->vars['div_id'] = $this->id;
    }

    public function configureOptions(OptionsResolver $resolver) {
        $resolver->setDefaults(array (
            'mapped' => false,
            'content' => false,
        ));
        $resolver->setDefined(array('div_id'));
    }

    public function getName() {
        return 'div';
    }
    public function getBlockPrefix() {
        return 'div';
    }

}
我的模板代码:

{% block div_row %}
    <div id="{{ div_id }}">
    {% if div_content is defined and div_content %}
        {{ div_content }}
    {% endif %}
    </div>
{% endblock %}
现在结果不是我所期望的。 我得到了添加到表单中的div的数量,但所有div都被最后添加的元素的值覆盖,这显然不是很有用

<div id="div_id_2">
    A div with some images, buttons or other cool stuff
</div>
<div id="div_id_2">
    A div with some images, buttons or other cool stuff
</div>

有一些图片、按钮或其他很酷的东西的div
有一些图片、按钮或其他很酷的东西的div
有人知道我做错了什么吗?

或者有没有其他方法可以用来添加自定义表单类型?

多亏了Cerad,我才能够解决这个问题! 显然我把事情弄得太复杂了。。。在buildView方法中使用$options并将其从buildForm方法中删除,就完成了这项工作

我的新类型:

class DivType extends AbstractType {

    public function buildForm(FormBuilderInterface $builder, array $options) {

    }

    public function buildView(FormView $view, FormInterface $form, array $options) {
        $view->vars['div_content'] = $options['content'];
        $view->vars['div_id'] = $options['div_id'];
    }

    public function configureOptions(OptionsResolver $resolver) {
        $resolver->setDefaults(array (
            'mapped' => false,
            'content' => false,
        ));
        $resolver->setDefined(array('div_id'));
    }

    public function getBlockPrefix() {
        return 'div';
    }

}
也许更好更干净的方法是直接在twig中使用元素id,使用变量'form.vars.name'作为id,而不是添加额外的变量'div_id':

<div id="{{ form.vars.name }}">


我怀疑问题可能出在getName中,它在2.8中也被贬值,在3.0中消失了。尝试改用getBlockPrefix,尽管我不确定这是否会为您提供一个单独的div\u id。getName()函数是否存在并不重要。我得到了同样的结果,值被覆盖了。在symfony中可用的FormTypes中,它们使用“return$this->getBlockPrefix();”实现向后兼容。尝试此操作会得到相同的结果。您的代码将id设置为:$this->id=$builder->getName();我有点惊讶,它似乎在2.7中起作用。或者唯一id实际上是在其他地方设置的?我想你可以尝试通过选项数组来设置它。谢谢,我传递id(或其他变量)的实际代码是:如果(array_key_存在('div_id',$options)){$this->id=$options['div_id'];}否则{$this->id=$builder->getName();}没有什么区别:所有变量都被覆盖了。上面的代码是解释问题的最低限度。我还没有深入研究2.8/3.0表单代码,但我怀疑两个表单字段现在使用的是同一个DivType实例,因此将内容存储为实例数据是行不通的。尝试从buildView中的选项数组中提取它,看看会发生什么。
class DivType extends AbstractType {

    public function buildForm(FormBuilderInterface $builder, array $options) {

    }

    public function buildView(FormView $view, FormInterface $form, array $options) {
        $view->vars['div_content'] = $options['content'];
        $view->vars['div_id'] = $options['div_id'];
    }

    public function configureOptions(OptionsResolver $resolver) {
        $resolver->setDefaults(array (
            'mapped' => false,
            'content' => false,
        ));
        $resolver->setDefined(array('div_id'));
    }

    public function getBlockPrefix() {
        return 'div';
    }

}
<div id="{{ form.vars.name }}">