tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

nsIConstraintValidation.cpp (4463B)


      1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
      2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */
      3 /* This Source Code Form is subject to the terms of the Mozilla Public
      4 * License, v. 2.0. If a copy of the MPL was not distributed with this
      5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
      6 
      7 #include "nsIConstraintValidation.h"
      8 
      9 #include "mozilla/dom/CustomEvent.h"
     10 #include "mozilla/dom/HTMLFieldSetElement.h"
     11 #include "mozilla/dom/HTMLFormElement.h"
     12 #include "mozilla/dom/HTMLInputElement.h"
     13 #include "mozilla/dom/ValidityState.h"
     14 #include "nsContentUtils.h"
     15 #include "nsGenericHTMLElement.h"
     16 #include "nsIFormControl.h"
     17 #include "nsISimpleEnumerator.h"
     18 
     19 const uint16_t nsIConstraintValidation::sContentSpecifiedMaxLengthMessage = 256;
     20 
     21 using namespace mozilla;
     22 using namespace mozilla::dom;
     23 
     24 nsIConstraintValidation::nsIConstraintValidation()
     25    : mValidityBitField(0)
     26      // By default, all elements are subjects to constraint validation.
     27      ,
     28      mBarredFromConstraintValidation(false) {}
     29 
     30 nsIConstraintValidation::~nsIConstraintValidation() = default;
     31 
     32 mozilla::dom::ValidityState* nsIConstraintValidation::Validity() {
     33  if (!mValidity) {
     34    mValidity = new mozilla::dom::ValidityState(this);
     35  }
     36 
     37  return mValidity;
     38 }
     39 
     40 bool nsIConstraintValidation::CheckValidity(nsIContent& aEventTarget,
     41                                            bool* aEventDefaultAction) const {
     42  if (!IsCandidateForConstraintValidation() || IsValid()) {
     43    return true;
     44  }
     45 
     46  nsContentUtils::DispatchTrustedEvent(
     47      aEventTarget.OwnerDoc(), &aEventTarget, u"invalid"_ns, CanBubble::eNo,
     48      Cancelable::eYes, Composed::eDefault, aEventDefaultAction);
     49  return false;
     50 }
     51 
     52 bool nsIConstraintValidation::ReportValidity() {
     53  nsCOMPtr<Element> element = do_QueryInterface(this);
     54  MOZ_ASSERT(element, "This class should be inherited by HTML elements only!");
     55 
     56  bool defaultAction = true;
     57  if (CheckValidity(*element, &defaultAction)) {
     58    return true;
     59  }
     60 
     61  if (!defaultAction) {
     62    return false;
     63  }
     64 
     65  AutoTArray<RefPtr<Element>, 1> invalidElements;
     66  invalidElements.AppendElement(element);
     67 
     68  AutoJSAPI jsapi;
     69  if (!jsapi.Init(element->GetOwnerGlobal())) {
     70    return false;
     71  }
     72  JS::Rooted<JS::Value> detail(jsapi.cx());
     73  if (!ToJSValue(jsapi.cx(), invalidElements, &detail)) {
     74    return false;
     75  }
     76 
     77  RefPtr<CustomEvent> event =
     78      NS_NewDOMCustomEvent(element->OwnerDoc(), nullptr, nullptr);
     79  event->InitCustomEvent(jsapi.cx(), u"MozInvalidForm"_ns,
     80                         /* CanBubble */ true,
     81                         /* Cancelable */ true, detail);
     82  event->SetTrusted(true);
     83  event->WidgetEventPtr()->mFlags.mOnlyChromeDispatch = true;
     84 
     85  element->DispatchEvent(*event);
     86  return false;
     87 }
     88 
     89 void nsIConstraintValidation::SetValidityState(ValidityStateType aState,
     90                                               bool aValue) {
     91  bool previousValidity = IsValid();
     92 
     93  if (aValue) {
     94    mValidityBitField |= aState;
     95  } else {
     96    mValidityBitField &= ~aState;
     97  }
     98 
     99  // Inform the form and fieldset elements if our validity has changed.
    100  if (previousValidity != IsValid() && IsCandidateForConstraintValidation()) {
    101    nsCOMPtr<nsIFormControl> formCtrl = do_QueryInterface(this);
    102    NS_ASSERTION(formCtrl, "This interface should be used by form elements!");
    103 
    104    if (HTMLFormElement* form = formCtrl->GetForm()) {
    105      form->UpdateValidity(IsValid());
    106    }
    107    if (HTMLFieldSetElement* fieldSet = formCtrl->GetFieldSet()) {
    108      fieldSet->UpdateValidity(IsValid());
    109    }
    110  }
    111 }
    112 
    113 void nsIConstraintValidation::SetBarredFromConstraintValidation(bool aBarred) {
    114  bool previousBarred = mBarredFromConstraintValidation;
    115 
    116  mBarredFromConstraintValidation = aBarred;
    117 
    118  // Inform the form and fieldset elements if our status regarding constraint
    119  // validation is going to change.
    120  if (!IsValid() && previousBarred != mBarredFromConstraintValidation) {
    121    nsCOMPtr<nsIFormControl> formCtrl = do_QueryInterface(this);
    122    NS_ASSERTION(formCtrl, "This interface should be used by form elements!");
    123 
    124    // If the element is going to be barred from constraint validation, we can
    125    // inform the form and fieldset that we are now valid. Otherwise, we are now
    126    // invalid.
    127    if (HTMLFormElement* form = formCtrl->GetForm()) {
    128      form->UpdateValidity(aBarred);
    129    }
    130    HTMLFieldSetElement* fieldSet = formCtrl->GetFieldSet();
    131    if (fieldSet) {
    132      fieldSet->UpdateValidity(aBarred);
    133    }
    134  }
    135 }