Я использую symfony 3.4 с пакетом sonata media. Использование MediaType в форме отлично работает следующим образом:
$this->builder->->add('document', MediaType::class,
['label' => 'Document',
'provider' => 'sonata.media.provider.file',
'context' => 'default']) ;
Теперь я хотел бы изменить поля, которые генерирует MediaType.
Я только что скопировал шаблон Twig \ vendor \ sonata-project \ media-bundle \ src \ Resources \ views \ Form \ media_widgets.html.twig в свой проект (\ AppBundle \ SonataMediaBundle \ views \ Form), и теперь я могу изменить макет. Пока все работает отлично.
Наконец, в шаблоне используется {{блок ('form_widget')}} для записи кнопки загрузки и флажка для удаления загруженных файлов, включая метки. Это делается в классе \ sonata-project \ media-bundle \ src \ Forms \ Type \ MediaType.php в методе buildForm.
Теперь я хочу изменить этот метод buildForm. Изменение классов в пакетах поставщиков не является хорошей практикой, поэтому я хотел создать новый класс, который расширяет класс MediaType и перезаписывает метод buildForm, например:
namespace AppBundle\Form\SonataMediaBundle ;
class MyMediaType extends \Sonata\MediaBundle\Form\Type\MediaType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
... copy code from original MediaType class and modify it after my needs ...
... e.g. just remove the unlink checkbox ...
}
}
Я получаю сообщение об ошибке Не удается выполнить автоматическое подключение службы «AppBundle \ Form \ SonataMediaBundle \ EwMediaType»: аргумент «$ pool» метода «Sonata \ MediaBundle \ Form \ Type \ MediaType :: __ construct ()» ссылается на класс «Sonata \ MediaBundle \ Provider \ Pool», но не имеет такого услуга существует. Возможно, вам следует присвоить этому классу псевдоним существующей службы sonata.media.pool.
Я предполагаю, что мне нужно выполнить некоторые настройки, прежде чем я смогу расширить MediaType в своем собственном проекте. Я пробовал использовать следующий код в моем services.yml
Sonata\MediaBundle\Provider\Pool:
tags: ['sonata.media.pool']
Но теперь возникает другая ошибка: Не удается выполнить автоматическое подключение службы «AppBundle \ Form \ SonataMediaBundle \ EwMediaType»: аргумент «$ class» метода «Sonata \ MediaBundle \ Form \ Type \ MediaType :: __ construct ()» не имеет подсказки типа, вам следует явно указать его значение.
Я новичок в symfony и не очень знаком с его конфигурацией. Может ли кто-нибудь помочь мне составить список шагов, которые мне нужно сделать, чтобы я мог расширить и изменить класс MediaType?
Большое спасибо.
Саша




Вы можете сделать следующее. Вам необходимо создать собственное определение службы.
AppBundle\Form\Type\CustomMediaType:
class: AppBundle\Form\Type\CustomMediaType
autowire: true
autoconfigure: true
arguments:
- "@sonata.media.pool"
- "Application\\Sonata\\MediaBundle\\Entity\\Media"
Затем в CustomMediaType создайте свой тип формы как обычно.
namespace AppBundle\Form\Type;
use Sonata\MediaBundle\Form\Type\MediaType;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Extension\Core\Type\UrlType;
use Symfony\Component\OptionsResolver\OptionsResolver;
class CustomMediaType extends MediaType
{
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults([
]);
}
public function getBlockPrefix()
{
return 'custom_media_type';
}
public function getParent()
{
return MediaType::class;
}
}
Затем где-нибудь во включениях ветки вы можете добавить свой собственный HTML ...
{% block custom_media_type_widget %}
// Your HTML here
{% endblock %}
Привет Layke, спасибо за ответ. Я попробовал это, и все работало очень хорошо до тех пор. Теперь я могу изменить вывод HTML с помощью шаблона веточки.
Затем я попытался перезаписать метод buildForm в моем классе CustomMediaType.php и удалил строку, которая создает флажок ($ builder-> add ('разъединить', CheckboxType :: class, [...]);, но все же метод buildForm в исходном классе MediaType.php, похоже, вызывается. Что мне не хватает? У вас есть подсказка, как я могу перезаписать метод buildForm? Большое спасибо!
Я не уверен. Однако, если вы хотите что-то удалить, вероятно, имеет смысл просто -> remove () элемент в построителе. Это все, что вы пытаетесь сделать?
Спасибо Layke, это прекрасный намек. Я пробовал удалить, но проблема в том, что MediaType создает подчиненную форму с несколькими полями, и я хочу удалить одно из полей в этой подчиненной форме. Могу ли я удалить поле в подтипе в методе buildForm основной формы?
Вы когда-нибудь находили на это ответ?