一、以Ajax的方式提交表单后重定向:
要实现重定向到一个指定的url,需要用到RedirectCommand类。首先引入RedirectCommand类的命名空间:
use Drupal\Core\Ajax\RedirectCommand;
1、如果需要在提交成功后立即跳转,可以使用RedirectCommand()构造方法。
$redirect_command = new RedirectCommand('/custom/path');
$response->addCommand($redirect_command);
这样在表单提交成功后,将跳转到/custom/path
页面。
2、如果需要在请求完成后延迟几秒钟再进行重定向,则需要结合 JavaScript 来实现,需要在模块中定义一个新的 AJAX 命令。这个命令需要继承 Drupal\Core\Ajax\CommandInterface
接口,并实现 render()
方法。在 render()
方法中,需要返回一个数组,其中包含你想要在客户端执行的 JavaScript
代码。
(1)、新建一个module_name/src/AjaxCommand/DelayedRedirectCommand.php
DelayedRedirectCommand.php
文件内容如下:
<?php
namespace Drupal\demo_form\AjaxCommand;
use Drupal\Core\Ajax\CommandInterface;
class DelayedRedirectCommand implements CommandInterface
{
/**
* 重定向的url
* @var
*/
protected $url;
/**
* 延迟的时间
* @var
*/
protected $delay;
public function __construct($url, $delay) {
$this->url = $url;
$this->delay = $delay;
}
/**
* @return array
*/
public function render() {
return [
'command' => 'delayedRedirect',
'url' => $this->url,
'delay' => $this->delay,
];
}
}
(2)、在JS中实现跳转
(function ($,Drupal,drupalSettings) {
'use strict';
Drupal.AjaxCommands.prototype.delayedRedirect = function(ajax, response, status) {
setTimeout(function() {
window.location.href = response.url;
}, response.delay);
};
})(jQuery, Drupal, drupalSettings)
(3)、调用
引入命名空间:
use Drupal\demo_form\AjaxCommand\DelayedRedirectCommand;
调用:
$redirect_command = new DelayedRedirectCommand('/custom/path', 5000);
$response->addCommand($redirect_command);
完整示例:表单提交成功后延迟跳转到指定url
namespace Drupal\demo_form\Form;
use Drupal\Core\Form\FormBase;
use Drupal\Core\Form\FormStateInterface;
use Drupal\Core\Ajax\AjaxResponse;
use Drupal\Core\Ajax\HtmlCommand;
use Drupal\Core\Ajax\InvokeCommand;
use Drupal\Component\Utility\EmailValidator;
use Drupal\Core\Database\Database;
use Drupal\demo_form\AjaxCommand\DelayedRedirectCommand;
class DemoForm extends FormBase{
/**
* {@inheritdoc }
* 设置表单id
*/
public function getFormId()
{
return 'demo_form_form';
}
/**
* {@inheritdoc }
* 构建表单中的字段及属性
*/
public function buildForm(array $form, FormStateInterface $form_state)
{
$form['title'] = [
'#type' => 'select',
'#title' => $this->t('称呼'),
'#options' => [
'mr' => $this->t('先生'),
'ms' => $this->t('女士'),
'dr' => $this->t('博士')
],
'#default_value' => 'mr'
];
$form['name'] = [
'#type' => 'textfield',
'#title' => $this->t('姓名'),
'#maxlength' => 30,
'#suffix' => '<div class="error" id="name_message"></div>'
];
$form['age'] = [
'#type' => 'textfield',
'#title' => $this->t('年龄'),
'#suffix' => '<div class="error" id="age_message"></div>'
];
$form['email'] = [
'#type' => 'textfield',
'#title' => $this->t('邮箱'),
'#suffix' => '<div class="error" id="email_message"></div>'
];
$form['actions'] = [
'#type' => 'submit',
'#value' => $this->t('提交'),
'#ajax' => [
'callback' => '::submitData'//表单以ajax方式提交后处理表单数据的方法
]
];
$form['message'] = [
'#type' => 'markup',
'#markup' => '<div class="message"></div>'
];
$form['#attached']['library'][] = 'demo_form/demo_form_js_css';
return $form;
}
/**
* {@inheritdoc}
*/
public function submitForm(array &$form, FormStateInterface $form_state) {}
/**
* 处理ajax提交的方法
* @param array $form
* @param FormStateInterface $form_state
* @return AjaxResponse
*/
public function submitData(array &$form, FormStateInterface $form_state){
$ajax_response = new AjaxResponse();
$connection = Database::getConnection();//获取数据库链接对象
$formFields = $form_state->getValues();
$formData['title'] = $formFields['title'];
$formData['name'] = $formFields['name'];
$formData['age'] = $formFields['age'];
$formData['email'] = $formFields['email'];
if (empty(trim($formData['name']))){
$ajax_response->addCommand(new HtmlCommand('#name_message','请填写姓名'));
}
if (empty(trim($formData['age'])) || $formData['age'] <= 0 || $formData['age'] > 100){
$ajax_response->addCommand(new HtmlCommand('#age_message','年龄填写不符合规范'));
}
$email_validator = new EmailValidator();
if (!$email_validator->isValid($formData['email'])){
$ajax_response->addCommand(new HtmlCommand('#email_message','请填写有效的邮箱地址'));
}
if (!empty($ajax_response->getCommands())) {
$ajax_response->addCommand(new InvokeCommand('.message', 'addClass', ['failure']));
$ajax_response->addCommand(new HtmlCommand('.message','表单有误'));
}else{
try {
$res = $connection->insert('employee')->fields($formData)->execute();
$ajax_response->addCommand(new InvokeCommand('.message', 'addClass', ['success']));
$ajax_response->addCommand(new HtmlCommand('.message','提交成功'));
//提交成功后延迟5秒跳转到指定url中
$redirect_command = new DelayedRedirectCommand('/custom/path', 5000);
$ajax_response->addCommand($redirect_command);
}catch (\Exception $e){
$ajax_response->addCommand(new InvokeCommand('.message', 'addClass', ['failure']));
\Drupal::logger('demo_form')->error($e->getMessage());
$ajax_response->addCommand(new HtmlCommand('.message','提交过程中产生了异常,请查看错误日志'));
}
}
return $ajax_response;
}
}