Symfony 4 / Sonata: Tạo Một Loại Trường Form Tùy Chỉnh

Chúng ta sẽ xem làm thế nào để tạo một loại trường tùy chỉnh.

Trong ví dụ của chúng ta, chúng ta muốn một trường có cùng cách hiển thị như trường MoneyType nhưng chúng ta có thể thêm bất kỳ hậu tố nào, vì trường tiền tệ chỉ chấp nhận các loại tiền tệ.

Tuy nhiên, trong dự án của chúng ta, chúng ta muốn sử dụng kilogram, tháng hoặc thậm chí là kilômét. Nói chung, một loạt các loại dữ liệu có thể có.

Chúng ta bắt đầu bằng cách tạo lớp Type của chúng ta:

<?php 
// src/Form/Type/NumberSuffixType.php
namespace App\Form\Type;

use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Component\Form\Extension\Core\Type\IntegerType;
use Symfony\Component\Form\Extension\Core\Type\NumberType;
use Symfony\Component\OptionsResolver\Options;
use Symfony\Component\OptionsResolver\OptionsResolver;
use Symfony\Component\Form\FormViewInterface;
use Symfony\Component\Form\FormInterface;
use Symfony\Component\Form\FormTypeInterface;
use Symfony\Component\Form\FormView;

class NumberSuffixType extends AbstractType
{
    public function getParent()
    {
        return NumberType::class;
        //return TextType::class;
    }
    
    public function configureOptions(OptionsResolver $resolver)
    {
    
        $resolver->setDefaults([
            'suffix' => 'suffix',
            'field_options' => [],
        ]);
    
    }
    
    public function buildView(FormView $view, FormInterface $form, array $options)
    {
        $view->vars['field_name']=$form->getName();
        $view->vars['data']=$form->getData();
        $view->vars['suffix']=$options['suffix'];
        $view->vars['type'] = 'number';
        $view->vars['attr']['class'] = 'number_suffix';
    
    }
    
    public function getBlockPrefix()
    {
        return 'number_suffix';
    }
    
    
}

?>

Sau đó chúng ta thêm mẫu của mình

{# templates/Adminform/number_suffix_type.html.twig #}
{% block number_suffix_widget %}
    {% spaceless %}
       <div class="input-group">
                {{- block('form_widget_simple') -}}
                {% if suffix is not empty %}
                	<span class="input-group-addon"> {{ suffix }}</span>
                {% endif %}
                
            </div>
    {% endspaceless %}
{% endblock %}

Chúng ta phải đăng ký mẫu của mình

# config/packages/twig.yaml
twig:
    form_themes:
        - 'Admin/form/number_suffix_type.html.twig'

Bên cạnh đó, chúng ta thêm một quy tắc CSS để loại bỏ các mũi tên từ trường số HTML5.
Để làm điều này, chúng ta phải tham chiếu một tệp CSS trong admin

sonata_admin:
    assets:
        extra_stylesheets:
            - css/admin.css

Và chúng ta thêm chỉ thị của mình vào tệp CSS của mình

input[class*="number_suffix"] {
    -moz-appearance: textfield;
}
input[class*="number_suffix"]:hover,
input[class*="number_suffix"]:focus {
    -moz-appearance: number-input;
}

Sau đó chỉ cần sử dụng nó như thế này:

            ->add('dureePossible1', NumberSuffixType::class, ['label'=>'Durée possible 1','suffix'=>'Mois','required'   => false])
            ->add('dureePossible2', NumberSuffixType::class, ['label'=>'Durée possible 2','suffix'=>'Mois','required'   => false])
            ->add('dureePossible3', NumberSuffixType::class, ['label'=>'Durée possible 3','suffix'=>'Mois','required'   => false])
            ->add('dureePossible4', NumberSuffixType::class, ['label'=>'Durée possible 4','suffix'=>'Mois','required'   => false])

Sau đó, nó sẽ cho chúng ta một trường như thế này

image-1