Index: Source/core/html/HTMLFormControlElement.cpp |
diff --git a/Source/core/html/HTMLFormControlElement.cpp b/Source/core/html/HTMLFormControlElement.cpp |
index 75f2402d2c782128eb57e2c5c92b7f9adfe90112..96cd20f59e8f9f9781e326ebdd6741a02d7fcf99 100644 |
--- a/Source/core/html/HTMLFormControlElement.cpp |
+++ b/Source/core/html/HTMLFormControlElement.cpp |
@@ -264,27 +264,28 @@ void HTMLFormControlElement::removedFrom(ContainerNode* insertionPoint) |
m_hasValidationMessage = false; |
m_ancestorDisabledState = AncestorDisabledStateUnknown; |
m_dataListAncestorState = Unknown; |
+ setNeedsWillValidateCheck(); |
HTMLElement::removedFrom(insertionPoint); |
FormAssociatedElement::removedFrom(insertionPoint); |
} |
void HTMLFormControlElement::willChangeForm() |
{ |
- formOwnerSetNeedsValidityCheck(); |
FormAssociatedElement::willChangeForm(); |
+ formOwnerSetNeedsValidityCheck(ElementRemoval, isValidElement()); |
} |
void HTMLFormControlElement::didChangeForm() |
{ |
- formOwnerSetNeedsValidityCheck(); |
FormAssociatedElement::didChangeForm(); |
+ formOwnerSetNeedsValidityCheck(ElementAddition, isValidElement()); |
} |
-void HTMLFormControlElement::formOwnerSetNeedsValidityCheck() |
+void HTMLFormControlElement::formOwnerSetNeedsValidityCheck(ValidityRecalcReason reason, bool isValid) |
{ |
HTMLFormElement* form = formOwner(); |
if (form) |
- form->setNeedsValidityCheck(); |
+ form->setNeedsValidityCheck(reason, isValid); |
} |
void HTMLFormControlElement::fieldSetAncestorsSetNeedsValidityCheck(Node* node) |
@@ -413,12 +414,7 @@ bool HTMLFormControlElement::recalcWillValidate() const |
bool HTMLFormControlElement::willValidate() const |
{ |
if (!m_willValidateInitialized || m_dataListAncestorState == Unknown) { |
- m_willValidateInitialized = true; |
- bool newWillValidate = recalcWillValidate(); |
- if (m_willValidate != newWillValidate) { |
- m_willValidate = newWillValidate; |
- const_cast<HTMLFormControlElement*>(this)->setNeedsValidityCheck(); |
- } |
+ const_cast<HTMLFormControlElement*>(this)->setNeedsWillValidateCheck(true); |
} else { |
// If the following assertion fails, setNeedsWillValidateCheck() is not |
// called correctly when something which changes recalcWillValidate() result |
@@ -428,7 +424,7 @@ bool HTMLFormControlElement::willValidate() const |
return m_willValidate; |
} |
-void HTMLFormControlElement::setNeedsWillValidateCheck() |
+void HTMLFormControlElement::setNeedsWillValidateCheck(bool hideValidationMessageIfNeeded) |
{ |
// We need to recalculate willValidate immediately because willValidate change can causes style change. |
bool newWillValidate = recalcWillValidate(); |
@@ -437,8 +433,11 @@ void HTMLFormControlElement::setNeedsWillValidateCheck() |
m_willValidateInitialized = true; |
m_willValidate = newWillValidate; |
setNeedsValidityCheck(); |
- setNeedsStyleRecalc(SubtreeStyleChange, StyleChangeReasonForTracing::create(StyleChangeReason::Validate)); |
- if (!m_willValidate) |
+ // No need to trigger style recalculation here because |
+ // setNeedsValidityCheck() does it in the right away. This relies on |
+ // the assumption that valid() is always true if willValidate() is false. |
+ |
+ if (hideValidationMessageIfNeeded && !m_willValidate) |
hideVisibleValidationMessage(); |
} |
@@ -564,13 +563,14 @@ bool HTMLFormControlElement::isValidElement() |
void HTMLFormControlElement::setNeedsValidityCheck() |
{ |
bool newIsValid = valid(); |
- if (willValidate() && newIsValid != m_isValid) { |
- formOwnerSetNeedsValidityCheck(); |
+ bool changed = newIsValid != m_isValid; |
+ m_isValid = newIsValid; |
+ if (changed) { |
+ formOwnerSetNeedsValidityCheck(ElementModification, newIsValid); |
fieldSetAncestorsSetNeedsValidityCheck(parentNode()); |
// Update style for pseudo classes such as :valid :invalid. |
setNeedsStyleRecalc(SubtreeStyleChange, StyleChangeReasonForTracing::createWithExtraData(StyleChangeReason::PseudoClass, StyleChangeExtraData::Invalid)); |
} |
- m_isValid = newIsValid; |
// Updates only if this control already has a validation message. |
if (isValidationMessageVisible()) { |