diff --git a/core/modules/inline_form_errors/inline_form_errors.api.php b/core/modules/inline_form_errors/inline_form_errors.api.php new file mode 100644 index 0000000000..ebd4ccc362 --- /dev/null +++ b/core/modules/inline_form_errors/inline_form_errors.api.php @@ -0,0 +1,51 @@ + 'textfield', + * '#title' => 'Test 4', + * '#parents' => ['test4'], + * '#array_parents' => ['test4'], + * '#id' => 'edit-test4', + * '#error_no_message' => TRUE, + * ]; + * @endcode + * + * @section Disable the Inline Form Errors summary. + * Disable the duplicate messages from summary and inline-error elements. Set + * the #disable_inline_form_errors_summary property to TRUE on the top level of + * the $form array. + * @code + * $form['#disable_inline_form_errors_summary'] = TRUE + * @endcode + * + * If one or more elements with errors cannot be shown as inline-error (e.g. + * invisible, missing, or has no title elements), the summary will remain + * visible with those messages only. + * + * See + * @link https://www.drupal.org/docs/8/core/modules/inline-form-errors @endlink + * for more information about the Inline Form Errors module. + * + * @} + */ diff --git a/core/modules/inline_form_errors/src/FormErrorHandler.php b/core/modules/inline_form_errors/src/FormErrorHandler.php index 23cef62c48..d2f66feebf 100644 --- a/core/modules/inline_form_errors/src/FormErrorHandler.php +++ b/core/modules/inline_form_errors/src/FormErrorHandler.php @@ -94,6 +94,10 @@ protected function displayErrorMessages(array $form, FormStateInterface $form_st if (!empty($form_element['#error_no_message'])) { unset($errors[$name]); } + // Do not show links to elements when the errors summary is disabled. + elseif ($is_visible_element && !empty($form['#disable_inline_form_errors_summary'])) { + unset($errors[$name]); + } elseif ($is_visible_element && $has_title && $has_id) { $error_links[] = Link::fromTextAndUrl($title, Url::fromRoute('', [], ['fragment' => $form_element['#id'], 'external' => TRUE]))->toRenderable(); unset($errors[$name]); diff --git a/core/modules/inline_form_errors/tests/src/Unit/FormErrorHandlerTest.php b/core/modules/inline_form_errors/tests/src/Unit/FormErrorHandlerTest.php index 29865fcde9..02798431f8 100644 --- a/core/modules/inline_form_errors/tests/src/Unit/FormErrorHandlerTest.php +++ b/core/modules/inline_form_errors/tests/src/Unit/FormErrorHandlerTest.php @@ -214,4 +214,50 @@ public function testErrorMessagesNotInline() { $this->assertSame('element is invisible', $this->testForm['test6']['#errors']); } + /** + * Tests that disabling Inline Form Errors summary works. + */ + public function testDisabledInlineErrorsSummary() { + $this->messenger->expects($this->exactly(3)) + ->method('addError'); + + // Assert that messages are summarized for elements that have both no title + // and are missing or invisible. + $this->messenger->expects($this->at(0)) + ->method('addError') + ->with('no title given'); + $this->messenger->expects($this->at(1)) + ->method('addError') + ->with('element is invisible'); + $this->messenger->expects($this->at(2)) + ->method('addError') + ->with('this missing element is invalid'); + + $this->messenger->expects($this->never()) + ->method('addMessage'); + + $this->renderer->expects($this->never()) + ->method('renderPlain'); + + $this->testForm['#disable_inline_form_errors_summary'] = TRUE; + + $form_state = new FormState(); + $form_state->setErrorByName('test1', 'invalid'); + $form_state->setErrorByName('test2', 'invalid'); + $form_state->setErrorByName('fieldset][test3', 'invalid'); + $form_state->setErrorByName('test4', 'no error message'); + $form_state->setErrorByName('test5', 'no title given'); + $form_state->setErrorByName('test6', 'element is invisible'); + $form_state->setErrorByName('missing_element', 'this missing element is invalid'); + $this->formErrorHandler->handleFormErrors($this->testForm, $form_state); + + // Assert the inline error still exists. + $this->assertSame('invalid', $this->testForm['test1']['#errors']); + $this->assertSame('invalid', $this->testForm['test2']['#errors']); + $this->assertSame('invalid', $this->testForm['fieldset']['test3']['#errors']); + $this->assertSame('no error message', $this->testForm['test4']['#errors']); + $this->assertSame('no title given', $this->testForm['test5']['#errors']); + $this->assertSame('element is invisible', $this->testForm['test6']['#errors']); + } + }