首页 > 解决方案 > 从 ChoiceType 扩展的自定义类型 Enum。Symfony

问题描述

在表单的类型中,使用了自定义类型“enum”。当我在表单选择中选择一个值并保存它时,当我在选择中重新打开表单时,这个值不会排在第一位。例如,如果我选择“次要”保存并再次打开表单,那么首先在选择中它仍然是“主要”。如何将实例的值放在select的首位?

 /**
 * Class SomethingType
 *
 * @method static SomethingType PRIMARY()
 * @method static SomethingType SECONDARY()
 */
final class SomethingType extends AbstractEnum
{
    const PRIMARY = 'primary';
    const SECONDARY = 'secondary';
}

在自定义类型中:

public function buildForm(FormBuilderInterface $builder, array $options)
{
    $builder
        ->add('type', 'enum', [
            'class' => 'SomethingType',
        ]);
}

枚举:

class EnumType extends AbstractType
{

    public function buildForm(FormBuilderInterface $builder, array $options)
    {
        $builder
            ->resetViewTransformers()
            ->addModelTransformer(new EnumTransformer($options['class']));
    }

    /**
     * @param OptionsResolver $resolver Validates options and merges them with
     *                                  default values.
     * @return void
     */
    public function configureOptions(OptionsResolver $resolver)
    {
        $resolver
            ->setDefined('class')
            ->setDefault('choices', function (Options $options) {
                $data = [];
                if (isset($options['class'])) {
                    $enum = call_user_func($options['class'] . '::values');
                    /** @var AbstractEnum $item */
                    foreach ($enum as $item) {
                        $value = $item->getValue();
                        $data[$value] = $value;
                    }
                }
                return $data;
            });
    }

    public function getParent()
    {
        return 'choice';
    }

    public function getName()
    {
        return $this->getBlockPrefix();
    }

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

标签: symfonyenumsformbuilder

解决方案


您应该创建自定义树枝模板:

{% block enum_widget %}
    {% if form is defined %}
        {% if instanceof(form.vars.value, 'AbstractEnum')  %}
            {% spaceless %}
                {%- set currentValue = form.vars.value.getValue -%}
                <select {{ block('widget_attributes') }}{% if multiple %} multiple="multiple"{% endif %}>
                    {%- set options = choices -%}
                    {% for group_label, choice in options %}
                        <option value="{{ choice.value }}"
                                {% if choice.attr %}{% with { attr: choice.attr } %}{{ block('attributes') }}{% endwith %}{% endif %}
                                {% if choice.value == currentValue %} selected="selected"{% endif %}>
                            {{ choice_translation_domain is same as(false) ? choice.label : choice.label|trans({}, choice_translation_domain) }}
                        </option>
                    {% endfor %}
                </select>
            {% endspaceless %}
        {% else %}
            {{ block('choice_widget') }}
        {% endif %}
    {% endif %}
{% endblock %}

推荐阅读