diff --git a/fixtures/dom/src/components/fixtures/text-inputs/index.js b/fixtures/dom/src/components/fixtures/text-inputs/index.js
index a3514377452..010738d8cdc 100644
--- a/fixtures/dom/src/components/fixtures/text-inputs/index.js
+++ b/fixtures/dom/src/components/fixtures/text-inputs/index.js
@@ -42,6 +42,46 @@ class TextInputFixtures extends React.Component {
+
+
+
View this test in Firefox
+
+
+
+ You should
+ {' '}
+ not
+ {' '}
+ see a red aura, indicating the input is invalid.
+
+ This aura looks roughly like:
+
+
+
+
+
+
+
+
+ Checking the date type is also important because of a
+ prior fix for iOS Safari that involved assigning over
+ value/defaultValue properties of the input to prevent a
+ display bug. This also triggered input validation.
+
+
+
Type "user@example.com"
diff --git a/src/renderers/dom/fiber/wrappers/ReactDOMFiberInput.js b/src/renderers/dom/fiber/wrappers/ReactDOMFiberInput.js
index 89f1056bc41..0c4718fcdc1 100644
--- a/src/renderers/dom/fiber/wrappers/ReactDOMFiberInput.js
+++ b/src/renderers/dom/fiber/wrappers/ReactDOMFiberInput.js
@@ -14,7 +14,8 @@ type InputWithWrapperState = HTMLInputElement & {
_wrapperState: {
initialValue: ?string,
initialChecked: ?boolean,
- controlled?: boolean,
+ controlled: boolean,
+ detached: boolean,
},
};
@@ -141,6 +142,7 @@ var ReactDOMInput = {
: props.defaultChecked,
initialValue: props.value != null ? props.value : defaultValue,
controlled: isControlled(props),
+ detached: false,
};
},
@@ -218,6 +220,13 @@ var ReactDOMInput = {
}
} else {
if (props.value == null && props.defaultValue != null) {
+ // Whenever setting defaultValue, ensure that the value
+ // property is detatched
+ if (node._wrapperState.detached === false) {
+ node.value = node.value;
+ node._wrapperState.detached = true;
+ }
+
// In Chrome, assigning defaultValue to certain input types triggers input validation.
// For number inputs, the display value loses trailing decimal points. For email inputs,
// Chrome raises "The specified value is not a valid email address".
@@ -239,16 +248,7 @@ var ReactDOMInput = {
postMountWrapper: function(element: Element, props: Object) {
var node = ((element: any): InputWithWrapperState);
- // Detach value from defaultValue. We won't do anything if we're working on
- // submit or reset inputs as those values & defaultValues are linked. They
- // are not resetable nodes so this operation doesn't matter and actually
- // removes browser-default values (eg "Submit Query") when no value is
- // provided.
-
switch (props.type) {
- case 'submit':
- case 'reset':
- break;
case 'color':
case 'date':
case 'datetime':
@@ -258,11 +258,13 @@ var ReactDOMInput = {
case 'week':
// This fixes the no-show issue on iOS Safari and Android Chrome:
// https://github.com/facebook/react/issues/7233
- node.value = '';
- node.value = node.defaultValue;
+ //
+ // Important: use setAttribute instead of node.type = "x" to avoid
+ // an exception in IE10/11 due to an unrecognized input type
+ node.setAttribute('type', 'text');
+ node.setAttribute('type', props.type);
break;
default:
- node.value = node.value;
break;
}
diff --git a/src/renderers/dom/shared/wrappers/__tests__/ReactDOMInput-test.js b/src/renderers/dom/shared/wrappers/__tests__/ReactDOMInput-test.js
index 0e289c0d80f..1e676594774 100644
--- a/src/renderers/dom/shared/wrappers/__tests__/ReactDOMInput-test.js
+++ b/src/renderers/dom/shared/wrappers/__tests__/ReactDOMInput-test.js
@@ -1190,7 +1190,6 @@ describe('ReactDOMInput', () => {
'set min',
'set max',
'set value',
- 'set value',
'set checked',
'set checked',
]);
@@ -1232,11 +1231,6 @@ describe('ReactDOMInput', () => {
spyOn(document, 'createElement').and.callFake(function(type) {
var el = originalCreateElement.apply(this, arguments);
if (type === 'input') {
- Object.defineProperty(el, 'value', {
- set: function(val) {
- log.push(`node.value = ${strify(val)}`);
- },
- });
spyOn(el, 'setAttribute').and.callFake(function(name, val) {
log.push(`node.setAttribute(${strify(name)}, ${strify(val)})`);
});
@@ -1250,8 +1244,8 @@ describe('ReactDOMInput', () => {
expect(log).toEqual([
'node.setAttribute("type", "date")',
'node.setAttribute("value", "1980-01-01")',
- 'node.value = ""',
- 'node.value = ""',
+ 'node.setAttribute("type", "text")',
+ 'node.setAttribute("type", "date")',
'node.setAttribute("checked", "")',
'node.setAttribute("checked", "")',
]);