Bug 610687 - Make all the radio button group suffering from being missing instead of only radio's with the required attribute. r+a=sicking

--HG--
extra : rebase_source : 804f50ebb47feeac9328a47e86fa387fc07ab32d
This commit is contained in:
Mounir Lamouri 2010-12-16 11:51:59 -08:00
parent c14568541d
commit 54f6748d69
37 changed files with 696 additions and 39 deletions

View File

@ -76,8 +76,6 @@ public:
NS_IMETHOD GetValidationMessage(nsAString& aValidationMessage);
protected:
enum ValidityStateType
{
VALIDITY_STATE_VALUE_MISSING = 0x01, // 0b00000001
@ -90,6 +88,11 @@ protected:
VALIDITY_STATE_CUSTOM_ERROR = 0x80 // 0b10000000
};
void SetValidityState(ValidityStateType mState,
PRBool mValue);
protected:
// You can't instantiate an object from that class.
nsIConstraintValidation();
@ -101,9 +104,6 @@ protected:
return mValidityBitField & mState;
}
void SetValidityState(ValidityStateType mState,
PRBool mValue);
void SetBarredFromConstraintValidation(PRBool aBarred);
virtual nsresult GetValidationMessage(nsAString& aValidationMessage,

View File

@ -41,6 +41,7 @@
#include "nsISupports.h"
class nsIFormControl;
class nsIDocument;
// IID for the nsIRadioControl interface
#define NS_IRADIOVISITOR_IID \
@ -104,4 +105,30 @@ NS_GetRadioGetCheckedChangedVisitor(PRBool* aCheckedChanged,
nsIRadioVisitor*
NS_GetRadioUpdateValueMissingVisitor();
/**
* This visitor will return (via aRequired) if an element of the group has the
* required attribute set.
*
* @param aExcludeElement an element to exclude (for optimization purpose), can be null
* @param aRequired whether there is a radio in the group with the required attribute [OUT]
* @return the visitor
*/
nsIRadioVisitor*
NS_GetRadioGroupRequiredVisitor(nsIFormControl* aExcludeElement,
bool* aRequired);
/**
* This visitor will update the validity states of all radio in the group and
* call ContentStatesChanged if needed.
*
* @param aExcludeElement an element to exclude (for optimization purpose), can be null
* @param aDocument the document owning the group
* @param aNotify whether we should call ContentStatesChanged
* @return the visitor
*/
nsIRadioVisitor*
NS_SetRadioValueMissingState(nsIFormControl* aExcludeElement,
nsIDocument* aDocument,
bool aValidity, bool aNotify);
#endif // nsIRadioVisitor_h___

View File

@ -3506,14 +3506,8 @@ nsHTMLInputElement::WillRemoveFromRadioGroup()
if (container) {
container->SetCurrentRadioButton(name, nsnull);
}
// Removing a checked radio from the group can change the validity state.
// Let's ask other radio to update their value missing validity state.
nsCOMPtr<nsIRadioVisitor> visitor =
NS_GetRadioUpdateValueMissingVisitor();
VisitGroup(visitor, PR_FALSE);
}
//
// Remove this radio from its group in the container
//
@ -3526,6 +3520,9 @@ nsHTMLInputElement::WillRemoveFromRadioGroup()
}
gotName = PR_TRUE;
}
UpdateValueMissingValidityStateForRadio(true);
container->RemoveFromRadioGroup(name,
static_cast<nsIFormControl*>(this));
}
@ -3808,11 +3805,6 @@ nsHTMLInputElement::IsValueMissing()
{
case NS_FORM_INPUT_CHECKBOX:
return !GetChecked();
case NS_FORM_INPUT_RADIO:
{
nsCOMPtr<nsIDOMHTMLInputElement> selected = GetSelectedRadioButton();
return !selected;
}
case NS_FORM_INPUT_FILE:
{
const nsCOMArray<nsIDOMFile>& files = GetFiles();
@ -3895,9 +3887,44 @@ nsHTMLInputElement::UpdateTooLongValidityState()
#endif
}
void
nsHTMLInputElement::UpdateValueMissingValidityStateForRadio(bool aIgnoreSelf)
{
PRBool notify = !GET_BOOLBIT(mBitField, BF_PARSER_CREATING);
nsCOMPtr<nsIDOMHTMLInputElement> selection = GetSelectedRadioButton();
// If there is no selection, that might mean the radio is not in a group.
// In that case, we can look for the checked state of the radio.
bool selected = selection ? true
: aIgnoreSelf ? false : GetChecked();
bool required = aIgnoreSelf ? false
: HasAttr(kNameSpaceID_None, nsGkAtoms::required);
bool valueMissing = false;
// If the current radio is required, don't check the entire group.
if (!required) {
nsCOMPtr<nsIRadioVisitor> visitor =
NS_GetRadioGroupRequiredVisitor(this, &required);
VisitGroup(visitor, notify);
}
valueMissing = required && !selected;
SetValidityState(VALIDITY_STATE_VALUE_MISSING, valueMissing);
nsCOMPtr<nsIRadioVisitor> visitor =
NS_SetRadioValueMissingState(this, GetCurrentDoc(), valueMissing,
notify);
VisitGroup(visitor, notify);
}
void
nsHTMLInputElement::UpdateValueMissingValidityState()
{
if (mType == NS_FORM_INPUT_RADIO) {
UpdateValueMissingValidityStateForRadio(false);
return;
}
SetValidityState(VALIDITY_STATE_VALUE_MISSING, IsValueMissing());
}
@ -4256,6 +4283,74 @@ public:
}
};
class nsRadioGroupRequiredVisitor : public nsRadioVisitor {
public:
nsRadioGroupRequiredVisitor(nsIFormControl* aExcludeElement, bool* aRequired)
: mRequired(aRequired)
, mExcludeElement(aExcludeElement)
{ }
NS_IMETHOD Visit(nsIFormControl* aRadio, PRBool* aStop)
{
if (aRadio == mExcludeElement) {
return NS_OK;
}
*mRequired = static_cast<nsHTMLInputElement*>(aRadio)
->HasAttr(kNameSpaceID_None, nsGkAtoms::required);
if (*mRequired) {
*aStop = PR_TRUE;
}
return NS_OK;
}
protected:
bool* mRequired;
nsIFormControl* mExcludeElement;
};
class nsRadioSetValueMissingState : public nsRadioVisitor {
public:
nsRadioSetValueMissingState(nsIFormControl* aExcludeElement,
nsIDocument* aDocument, bool aValidity,
bool aNotify)
: mExcludeElement(aExcludeElement)
, mDocument(aDocument)
, mValidity(aValidity)
, mNotify(aNotify)
{ }
NS_IMETHOD Visit(nsIFormControl* aRadio, PRBool* aStop)
{
if (aRadio == mExcludeElement) {
return NS_OK;
}
nsHTMLInputElement* input = static_cast<nsHTMLInputElement*>(aRadio);
input->SetValidityState(nsIConstraintValidation::VALIDITY_STATE_VALUE_MISSING,
mValidity);
if (mNotify && mDocument) {
mDocument->ContentStatesChanged(input, nsnull,
NS_EVENT_STATE_VALID |
NS_EVENT_STATE_INVALID |
NS_EVENT_STATE_MOZ_UI_VALID |
NS_EVENT_STATE_MOZ_UI_INVALID);
}
return NS_OK;
}
protected:
nsIFormControl* mExcludeElement;
nsIDocument* mDocument;
bool mValidity;
bool mNotify;
};
nsresult
NS_GetRadioSetCheckedChangedVisitor(PRBool aCheckedChanged,
nsIRadioVisitor** aVisitor)
@ -4342,6 +4437,22 @@ NS_GetRadioUpdateValueMissingVisitor()
return new nsRadioUpdateValueMissingVisitor();
}
nsIRadioVisitor*
NS_GetRadioGroupRequiredVisitor(nsIFormControl* aExcludeElement,
bool* aRequired)
{
return new nsRadioGroupRequiredVisitor(aExcludeElement, aRequired);
}
nsIRadioVisitor*
NS_SetRadioValueMissingState(nsIFormControl* aExcludeElement,
nsIDocument* aDocument,
bool aValidity, bool aNotify)
{
return new nsRadioSetValueMissingState(aExcludeElement, aDocument, aValidity,
aNotify);
}
NS_IMETHODIMP_(PRBool)
nsHTMLInputElement::IsSingleLineTextControl() const
{

View File

@ -110,7 +110,6 @@ private:
PRBool mInPrivateBrowsing;
};
class nsIRadioGroupContainer;
class nsIRadioVisitor;
class nsHTMLInputElement : public nsGenericHTMLFormElement,
@ -283,6 +282,15 @@ public:
void UpdateBarredFromConstraintValidation();
nsresult GetValidationMessage(nsAString& aValidationMessage,
ValidityStateType aType);
/**
* Update the value missing validity state for radio elements when they have
* a group.
*
* @param aIgnoreSelf Whether the required attribute and the checked state
* of the current radio should be ignored.
* @note This method shouldn't be called if the radio elemnet hasn't a group.
*/
void UpdateValueMissingValidityStateForRadio(bool aIgnoreSelf);
/**
* Returns the filter which should be used for the file picker according to

View File

@ -248,6 +248,7 @@ _TEST_FILES = \
test_bug613979.html \
test_bug615833.html \
test_bug601030.html \
test_bug610687.html \
$(NULL)
libs:: $(_TEST_FILES)

View File

@ -258,13 +258,13 @@ function checkInputRequiredValidityForRadio()
checkNotSufferingFromBeingMissing(element);
// If a radio button is not required but another radio button is required in
// the same group, the not required radio button should not suffer from value
// the same group, the not required radio button should suffer from value
// missing.
element2.disabled = false;
element2.checked = false;
element.required = false;
element2.required = true;
checkNotSufferingFromBeingMissing(element);
checkSufferingFromBeingMissing(element);
checkSufferingFromBeingMissing(element2);
element.checked = true;

View File

@ -0,0 +1,154 @@
<!DOCTYPE HTML>
<html>
<!--
https://bugzilla.mozilla.org/show_bug.cgi?id=610687
-->
<head>
<title>Test for Bug 610687</title>
<script type="application/javascript" src="/MochiKit/packed.js"></script>
<script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
</head>
<body>
<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=610687">Mozilla Bug 610687</a>
<p id="display"></p>
<div id="content" style="display: none">
<form>
<input type='radio' name='a'>
<input type='radio' name='a'>
<input type='radio' name='b'>
</form>
<input type='radio' name='a'>
<input type='radio' name='a'>
<input type='radio' name='b'>
</div>
<pre id="test">
<script type="application/javascript">
/** Test for Bug 610687 **/
function checkPseudoClasses(aElement, aValid, aValidUI, aInvalidUI)
{
if (aValid) {
ok(aElement.mozMatchesSelector(":valid"), ":valid should apply");
} else {
ok(aElement.mozMatchesSelector(":invalid"), ":invalid should apply");
}
is(aElement.mozMatchesSelector(":-moz-ui-valid"), aValidUI,
aValid ? ":-moz-ui-valid should apply" : ":-moz-ui-valid should not apply");
is(aElement.mozMatchesSelector(":-moz-ui-invalid"), aInvalidUI,
aInvalidUI ? ":-moz-ui-invalid should apply" : ":-moz-ui-invalid should not apply");
if (aInvalidUI && (aValid || aValidUI)) {
ok(false, ":invalid can't apply with :valid or :-moz-valid-ui");
}
}
/**
* r1 and r2 should be in the same group.
* r3 should be in another group.
* form can be null.
*/
function checkRadios(r1, r2, r3, form)
{
// Default state.
checkPseudoClasses(r1, true, false, false);
checkPseudoClasses(r2, true, false, false);
checkPseudoClasses(r3, true, false, false);
// Suffering from being missing (without ui-invalid).
r1.required = true;
checkPseudoClasses(r1, false, false, false);
checkPseudoClasses(r2, false, false, false);
checkPseudoClasses(r3, true, false, false);
// Suffering from being missing (with ui-invalid).
r1.checked = false;
checkPseudoClasses(r1, false, false, true);
checkPseudoClasses(r2, false, false, true);
checkPseudoClasses(r3, true, false, false);
// Do not suffer from being missing (with ui-valid).
r1.checked = true;
checkPseudoClasses(r1, true, true, false);
checkPseudoClasses(r2, true, true, false);
checkPseudoClasses(r3, true, false, false);
// Do not suffer from being missing (with ui-valid).
r1.checked = false;
r1.required = false;
checkPseudoClasses(r1, true, true, false);
checkPseudoClasses(r2, true, true, false);
checkPseudoClasses(r3, true, false, false);
// Suffering from being missing (with ui-invalid) with required set on one radio
// and the checked state changed on another.
r1.required = true;
r2.checked = false;
checkPseudoClasses(r1, false, false, true);
checkPseudoClasses(r2, false, false, true);
checkPseudoClasses(r3, true, false, false);
// Do not suffer from being missing (with ui-valid) by checking the radio which
// hasn't the required attribute.
r2.checked = true;
checkPseudoClasses(r1, true, true, false);
checkPseudoClasses(r2, true, true, false);
checkPseudoClasses(r3, true, false, false);
// .setCustomValidity() should not affect the entire group.
r1.checked = r2.checked = r3.checked = false;
r1.required = false;
r1.setCustomValidity('foo');
checkPseudoClasses(r1, false, false, true);
checkPseudoClasses(r2, true, true, false);
checkPseudoClasses(r3, true, true, false);
r1.setCustomValidity('');
r2.setCustomValidity('foo');
checkPseudoClasses(r1, true, true, false);
checkPseudoClasses(r2, false, false, true);
checkPseudoClasses(r3, true, true, false);
r2.setCustomValidity('');
r3.setCustomValidity('foo');
checkPseudoClasses(r1, true, true, false);
checkPseudoClasses(r2, true, true, false);
checkPseudoClasses(r3, false, false, true);
// Removing the radio with the required attribute should make the entire
// group invalid.
r1.setCustomValidity('');
r2.setCustomValidity('');
r1.required = false;
r2.required = true;
r1.checked = r2.checked = false;
checkPseudoClasses(r1, false, false, true);
checkPseudoClasses(r2, false, false, true);
var p = r2.parentNode;
p.removeChild(r2);
checkPseudoClasses(r1, true, true, false);
checkPseudoClasses(r2, false, false, true);
p.appendChild(r2);
checkPseudoClasses(r1, false, false, true);
checkPseudoClasses(r2, false, false, true);
}
var r1 = document.getElementsByTagName('input')[0];
var r2 = document.getElementsByTagName('input')[1];
var r3 = document.getElementsByTagName('input')[2];
checkRadios(r1, r2, r3);
r1 = document.getElementsByTagName('input')[3];
r2 = document.getElementsByTagName('input')[4];
r3 = document.getElementsByTagName('input')[5];
checkRadios(r1, r2, r3);
</script>
</pre>
</body>
</html>

View File

@ -0,0 +1,17 @@
<!DOCTYPE html>
<html class="reftest-wait">
<!-- Test: if one radio in a group is suffering from a custom error, the other
radio should not be invalid. -->
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i1').setCustomValidity('foo');
if (!document.getElementById('i1').mozMatchesSelector(':invalid') ||
document.getElementById('i2').mozMatchesSelector(':invalid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' name='foo' type='radio'>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -0,0 +1,17 @@
<!DOCTYPE html>
<html class="reftest-wait">
<!-- Test: when there are no radio suffering from being missing in the radio
group, all radio should not suffer from being missing. -->
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i1').checked = true;
if (document.getElementById('i1').mozMatchesSelector(':invalid') ||
document.getElementById('i2').mozMatchesSelector(':invalid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' name='foo' type='radio' required>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -0,0 +1,17 @@
<!DOCTYPE html>
<html class="reftest-wait">
<!-- Test: when there are no radio suffering from being missing in the radio
group, all radio should not suffer from being missing. -->
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i1').required = false;
if (document.getElementById('i1').mozMatchesSelector(':invalid') ||
document.getElementById('i2').mozMatchesSelector(':invalid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' name='foo' type='radio' required>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -0,0 +1,12 @@
<!DOCTYPE html>
<html class="reftest-wait">
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="if (document.getElementById('i').mozMatchesSelector(':invalid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i' type='radio' checked required>
</body>
</html>

View File

@ -0,0 +1,12 @@
<!DOCTYPE html>
<html class="reftest-wait">
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="if (!document.getElementById('i').mozMatchesSelector(':invalid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i' type='radio' required>
</body>
</html>

View File

@ -0,0 +1,16 @@
<!DOCTYPE html>
<html class="reftest-wait">
<!-- Test: if one radio in a group has the required attribute and no radio is
checked, all radio in the group should suffer from being missing. -->
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="if (!document.getElementById('i1').mozMatchesSelector(':invalid') ||
!document.getElementById('i2').mozMatchesSelector(':invalid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' name='foo' type='radio' required>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -23,4 +23,10 @@
== input-disabled-fieldset-1.html input-fieldset-ref.html
== input-disabled-fieldset-2.html input-fieldset-ref.html
== input-fieldset-legend.html input-fieldset-legend-ref.html
== input-radio-required.html success-ref.html
== input-radio-customerror.html success-ref.html
== input-radio-dyn-valid-1.html success-ref.html
== input-radio-dyn-valid-2.html success-ref.html
== input-radio-nogroup-required-valid.html success-ref.html
== input-radio-nogroup-required-invalid.html success-ref.html
# input type='hidden' shouldn't show

View File

@ -0,0 +1,6 @@
<!DOCTYPE html>
<html>
<body>
SUCCESS
</body>
</html>

View File

@ -0,0 +1,18 @@
<!DOCTYPE html>
<html class="reftest-wait">
<!-- Test: if one radio in a group is suffering from a custom error, the other
radio should not be invalid. -->
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i1').checked = false;
document.getElementById('i1').setCustomValidity('foo');
if (!document.getElementById('i1').mozMatchesSelector(':-moz-ui-invalid') ||
document.getElementById('i2').mozMatchesSelector(':-moz-ui-invalid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' name='foo' type='radio'>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -0,0 +1,17 @@
<!DOCTYPE html>
<html class="reftest-wait">
<!-- Test: when there are no radio suffering from being missing in the radio
group, all radio should not suffer from being missing. -->
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i1').checked = true;
if (document.getElementById('i1').mozMatchesSelector(':-moz-ui-invalid') ||
document.getElementById('i2').mozMatchesSelector(':-moz-ui-invalid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' name='foo' type='radio' required>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -0,0 +1,18 @@
<!DOCTYPE html>
<html class="reftest-wait">
<!-- Test: when there are no radio suffering from being missing in the radio
group, all radio should not suffer from being missing. -->
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i1').checked = true;
document.getElementById('i1').required = false;
if (document.getElementById('i1').mozMatchesSelector(':-moz-ui-invalid') ||
document.getElementById('i2').mozMatchesSelector(':-moz-ui-invalid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' name='foo' type='radio' required>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -0,0 +1,13 @@
<!DOCTYPE html>
<html class="reftest-wait">
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i').checked = true;
if (document.getElementById('i').mozMatchesSelector(':-moz-ui-invalid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i' type='radio' required>
</body>
</html>

View File

@ -0,0 +1,13 @@
<!DOCTYPE html>
<html class="reftest-wait">
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i').checked = false;
if (!document.getElementById('i').mozMatchesSelector(':-moz-ui-invalid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i' type='radio' required>
</body>
</html>

View File

@ -0,0 +1,18 @@
<!DOCTYPE html>
<html class="reftest-wait">
<!-- Test: if one radio in a group has the required attribute and no radio is
checked, all radio in the group should have :-moz-ui-invalid
pseudo-class. -->
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i1').checked = false;
if (!document.getElementById('i1').mozMatchesSelector(':-moz-ui-invalid') ||
!document.getElementById('i2').mozMatchesSelector(':-moz-ui-invalid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' name='foo' type='radio' required>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -33,8 +33,12 @@
== input-checkbox-required-invalid-default.html success-ref.html
== input-radio-required-invalid-changed.html success-ref.html
== input-radio-required-invalid-default.html success-ref.html
== input-radio-required-invalid-changed-2.html success-ref.html
== input-radio-required-invalid-default-2.html success-ref.html
== input-file-required-invalid-changed.html input-file-ref.html
== input-file-required-invalid-default.html input-file-ref.html
== input-radio-required.html success-ref.html
== input-radio-customerror.html success-ref.html
== input-radio-dyn-valid-1.html success-ref.html
== input-radio-dyn-valid-2.html success-ref.html
== input-radio-nogroup-required-valid.html success-ref.html
== input-radio-nogroup-required-invalid.html success-ref.html
# input type='hidden' shouldn't show

View File

@ -1,18 +1,16 @@
<!DOCTYPE html>
<html class="reftest-wait">
<!-- Test: if input isn't valid nor barred from constraint validation,
and its checkedness has changed,
it should be affected by :-moz-ui-invalid pseudo-class. -->
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i2').checked = false;
if (document.getElementById('i1').mozMatchesSelector(':-moz-ui-invalid') ||
!document.getElementById('i2').mozMatchesSelector(':-moz-ui-invalid')) {
<body onload="document.getElementById('i1').checked = false;
document.getElementById('i1').setCustomValidity('foo');
if (document.getElementById('i1').mozMatchesSelector(':-moz-ui-valid') ||
!document.getElementById('i2').mozMatchesSelector(':-moz-ui-valid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' type='radio'>
<input id='i2' type='radio' required>
<input id='i1' name='foo' type='radio'>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -0,0 +1,15 @@
<!DOCTYPE html>
<html class="reftest-wait">
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i1').checked = true;
if (!document.getElementById('i1').mozMatchesSelector(':-moz-ui-valid') ||
!document.getElementById('i2').mozMatchesSelector(':-moz-ui-valid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' name='foo' type='radio' required>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -0,0 +1,16 @@
<!DOCTYPE html>
<html class="reftest-wait">
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i1').checked = true;
document.getElementById('i1').required = false;
if (!document.getElementById('i1').mozMatchesSelector(':-moz-ui-valid') ||
!document.getElementById('i2').mozMatchesSelector(':-moz-ui-valid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' name='foo' type='radio' required>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -0,0 +1,13 @@
<!DOCTYPE html>
<html class="reftest-wait">
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i').checked = true;
if (!document.getElementById('i').mozMatchesSelector(':-moz-ui-valid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i' type='radio' required>
</body>
</html>

View File

@ -0,0 +1,13 @@
<!DOCTYPE html>
<html class="reftest-wait">
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i').checked = false;
if (document.getElementById('i').mozMatchesSelector(':-moz-ui-valid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i' type='radio' required>
</body>
</html>

View File

@ -0,0 +1,15 @@
<!DOCTYPE html>
<html class="reftest-wait">
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i1').checked = false;
if (document.getElementById('i1').mozMatchesSelector(':-moz-ui-valid') ||
document.getElementById('i2').mozMatchesSelector(':-moz-ui-valid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' name='foo' type='radio' required>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -32,8 +32,12 @@
== input-fieldset-legend.html input-fieldset-legend-ref.html
== input-checkbox-valid-changed.html success-ref.html
== input-checkbox-valid-default.html success-ref.html
== input-radio-valid-changed.html success-ref.html
== input-radio-valid-default.html success-ref.html
== input-file-valid-changed.html input-file-ref.html
== input-file-valid-default.html input-file-ref.html
== input-radio-required.html success-ref.html
== input-radio-customerror.html success-ref.html
== input-radio-dyn-valid-1.html success-ref.html
== input-radio-dyn-valid-2.html success-ref.html
== input-radio-nogroup-required-valid.html success-ref.html
== input-radio-nogroup-required-invalid.html success-ref.html
# input type='hidden' shouldn't show

View File

@ -0,0 +1,15 @@
<!DOCTYPE html>
<html class="reftest-wait">
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i1').setCustomValidity('foo');
if (document.getElementById('i1').mozMatchesSelector(':valid') ||
!document.getElementById('i2').mozMatchesSelector(':valid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' name='foo' type='radio'>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -0,0 +1,15 @@
<!DOCTYPE html>
<html class="reftest-wait">
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i1').checked = true;
if (!document.getElementById('i1').mozMatchesSelector(':valid') ||
!document.getElementById('i2').mozMatchesSelector(':valid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' name='foo' type='radio' required>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -0,0 +1,15 @@
<!DOCTYPE html>
<html class="reftest-wait">
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="document.getElementById('i1').required = false;
if (!document.getElementById('i1').mozMatchesSelector(':valid') ||
!document.getElementById('i2').mozMatchesSelector(':valid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' name='foo' type='radio' required>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -0,0 +1,12 @@
<!DOCTYPE html>
<html class="reftest-wait">
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="if (!document.getElementById('i').mozMatchesSelector(':valid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i' type='radio' checked required>
</body>
</html>

View File

@ -0,0 +1,12 @@
<!DOCTYPE html>
<html class="reftest-wait">
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="if (document.getElementById('i').mozMatchesSelector(':valid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i' type='radio' required>
</body>
</html>

View File

@ -1,17 +1,14 @@
<!DOCTYPE html>
<html class="reftest-wait">
<!-- Test: if input isn't valid nor barred from constraint validation,
and its checkedness hasn't changed,
it should not be affected by :-moz-ui-invalid pseudo-class. -->
<link rel='stylesheet' type='text/css' href='style.css'>
<body onload="if (document.getElementById('i1').mozMatchesSelector(':-moz-ui-invalid') ||
document.getElementById('i2').mozMatchesSelector(':-moz-ui-invalid')) {
<body onload="if (document.getElementById('i1').mozMatchesSelector(':valid') ||
document.getElementById('i2').mozMatchesSelector(':valid')) {
document.body.textContent='FAIL';
} else {
document.body.textContent='SUCCESS';
}
document.documentElement.className='';">
<input id='i1' type='radio'>
<input id='i2' type='radio' required>
<input id='i1' name='foo' type='radio' required>
<input id='i2' name='foo' type='radio'>
</body>
</html>

View File

@ -23,4 +23,10 @@
== input-disabled-fieldset-1.html input-fieldset-ref.html
== input-disabled-fieldset-2.html input-fieldset-ref.html
== input-fieldset-legend.html input-fieldset-legend-ref.html
== input-radio-required.html success-ref.html
== input-radio-customerror.html success-ref.html
== input-radio-dyn-valid-1.html success-ref.html
== input-radio-dyn-valid-2.html success-ref.html
== input-radio-nogroup-required-valid.html success-ref.html
== input-radio-nogroup-required-invalid.html success-ref.html
# input type='hidden' shouldn't show

View File

@ -0,0 +1,6 @@
<!DOCTYPE html>
<html>
<body>
SUCCESS
</body>
</html>