logo

额外区块类型 (EBT) - 全新的布局构建器体验❗

额外区块类型 (EBT) - 样式化、可定制的区块类型:幻灯片、标签页、卡片、手风琴等更多类型。内置背景、DOM Box、JavaScript 插件的设置。立即体验布局构建的未来。

演示 EBT 模块 下载 EBT 模块

❗额外段落类型 (EPT) - 全新的 Paragraphs 体验

额外段落类型 (EPT) - 类似的基于 Paragraph 的模块集合。

演示 EPT 模块 滚动

滚动
29/09/2025, by Ivan

Menu

在之前的文章中,我们已经讨论了什么是 Services、Dependency Injection (DI),以及如何在控制器和区块中使用它们:

12.15. Services 和 Dependency Injection
12.15.1. 控制器中的 Dependency Injection
12.15.2. 区块中的 Dependency Injection

在本文中,我们将演示如何通过 DI 向继承自 FormBase 的表单类中添加服务:

<?php

namespace Drupal\drupalbook\Form;

use Symfony\Component\DependencyInjection\ContainerInterface;
use Drupal\Core\Form\FormBase;
use Drupal\Core\Form\FormStateInterface;
use Egulias\EmailValidator\EmailValidator;

/**
 * Class ModalForm.
 */
class ModalForm extends FormBase {

  /**
   * 邮箱验证器.
   *
   * @var \Egulias\EmailValidator\EmailValidator
   */
  protected $emailValidator;

  /**
   * 构造函数.
   *
   * @param \Egulias\EmailValidator\EmailValidator $email_validator
   *   邮箱验证器.
   */
  public function __construct(EmailValidator $email_validator) {
    $this->emailValidator = $email_validator;
  }

  /**
   * {@inheritdoc}
   */
  public static function create(ContainerInterface $container) {
    return new static(
      $container->get('email.validator')
    );
  }

  /**
   * {@inheritdoc}
   */
  public function getFormId() {
    return 'drupalbook_contact_form';
  }

  /**
   * {@inheritdoc}
   */
  public function buildForm(array $form, FormStateInterface $form_state, $options = NULL) {
    $form['email'] = [
      '#type' => 'email',
      '#title' => $this->t('Email'),
      '#description' => $this->t('Your email address'),
      '#required' => TRUE,
    ];

    $form['actions']['send'] = [
      '#type' => 'submit',
      '#value' => $this->t('Send'),
    ];

    return $form;
  }


  /**
   * 邮箱验证.
   */
  protected function validateEmail(array &$form, FormStateInterface $form_state) {
    if (!$this->emailValidator->isValid($form_state->getValue('email'))) {
      return FALSE;
    }
    return TRUE;
  }

  /**
   * {@inheritdoc}
   */
  public function validateForm(array &$form, FormStateInterface $form_state) {
    $email = $form_state->getValue('email');

    if (!empty($email)) {
      if (!$this->validateEmail($form, $form_state)) {
        $form_state->setErrorByName('email', $this->t('%email 不是一个有效的邮箱地址。', array('%email' => $email)));
      }
    }
    else {
      $form_state->setErrorByName('email', $this->t("请输入一个邮箱地址。"));
    }
    $form_state->setValue('email', $email);
  }

  /**
   * {@inheritdoc}
   */
  public function submitForm(array &$form, FormStateInterface $form_state) {
    
  }

  /**
   * 获取可编辑的配置名称.
   *
   * @return array
   *   可编辑的配置对象名称数组,当与 trait 的 config() 方法结合使用时返回.
   */
  protected function getEditableConfigNames() {
    return ['config.drupalbook_contact_form'];
  }
}

在表单中通过 DI 调用服务时,我们使用 __constructcreate() 方法,就像在区块中所做的一样。