react 0.14.0-alpha3 → 0.14.0-beta1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +5 -2
- package/addons.js +2 -2
- package/dist/JSXTransformer.js +69 -70
- package/dist/react-with-addons.js +2047 -2078
- package/dist/react-with-addons.min.js +6 -6
- package/dist/react.js +1861 -1904
- package/dist/react.min.js +5 -5
- package/lib/{AutoFocusMixin.js → AutoFocusUtils.js} +13 -3
- package/lib/ChangeEventPlugin.js +4 -2
- package/lib/DOMProperty.js +81 -116
- package/lib/DOMPropertyOperations.js +70 -25
- package/lib/EnterLeaveEventPlugin.js +3 -3
- package/lib/EventPluginHub.js +2 -2
- package/lib/EventPluginUtils.js +6 -6
- package/lib/HTMLDOMPropertyConfig.js +8 -1
- package/lib/LinkedValueUtils.js +45 -33
- package/lib/PooledClass.js +12 -0
- package/lib/React.js +1 -1
- package/lib/ReactCSSTransitionGroupChild.js +8 -0
- package/lib/ReactChildren.js +3 -3
- package/lib/ReactClass.js +29 -47
- package/lib/ReactComponent.js +11 -6
- package/lib/ReactComponentWithPureRenderMixin.js +2 -2
- package/lib/ReactCompositeComponent.js +45 -72
- package/lib/ReactDOM.js +1 -0
- package/lib/ReactDOMButton.js +15 -26
- package/lib/ReactDOMClient.js +9 -4
- package/lib/ReactDOMComponent.js +302 -24
- package/lib/ReactDOMIDOperations.js +14 -0
- package/lib/ReactDOMInput.js +78 -94
- package/lib/ReactDOMOption.js +19 -38
- package/lib/ReactDOMSelect.js +85 -95
- package/lib/ReactDOMTextarea.js +39 -52
- package/lib/ReactDefaultInjection.js +0 -47
- package/lib/ReactElement.js +18 -79
- package/lib/ReactElementValidator.js +29 -98
- package/lib/ReactErrorUtils.js +1 -1
- package/lib/ReactEventEmitterMixin.js +2 -3
- package/lib/ReactEventListener.js +43 -3
- package/lib/ReactFragment.js +12 -7
- package/lib/ReactInputSelection.js +4 -3
- package/lib/ReactInstanceHandles.js +3 -2
- package/lib/ReactMount.js +20 -40
- package/lib/ReactNativeComponent.js +0 -5
- package/lib/ReactNoopUpdateQueue.js +118 -0
- package/lib/ReactPropTypes.js +3 -3
- package/lib/ReactReconcileTransaction.js +2 -2
- package/lib/ReactReconciler.js +8 -10
- package/lib/ReactServerBatchingStrategy.js +23 -0
- package/lib/ReactServerRendering.js +13 -0
- package/lib/ReactServerRenderingTransaction.js +2 -2
- package/lib/ReactTestUtils.js +56 -33
- package/lib/ReactUpdateQueue.js +51 -26
- package/lib/ReactUpdates.js +0 -3
- package/lib/ReactWithAddons.js +0 -2
- package/lib/SelectEventPlugin.js +6 -7
- package/lib/SimpleEventPlugin.js +4 -4
- package/lib/SyntheticClipboardEvent.js +2 -2
- package/lib/SyntheticCompositionEvent.js +2 -2
- package/lib/SyntheticDragEvent.js +2 -2
- package/lib/SyntheticEvent.js +6 -5
- package/lib/SyntheticFocusEvent.js +2 -2
- package/lib/SyntheticInputEvent.js +2 -2
- package/lib/SyntheticKeyboardEvent.js +2 -2
- package/lib/SyntheticMouseEvent.js +2 -2
- package/lib/SyntheticTouchEvent.js +2 -2
- package/lib/SyntheticUIEvent.js +2 -2
- package/lib/SyntheticWheelEvent.js +2 -2
- package/lib/Transaction.js +10 -4
- package/lib/cloneWithProps.js +1 -1
- package/lib/deprecated.js +47 -0
- package/lib/findDOMNode.js +2 -3
- package/lib/forEachAccumulated.js +1 -1
- package/lib/getEventCharCode.js +1 -1
- package/lib/getEventModifierState.js +0 -1
- package/lib/getMarkupWrap.js +13 -35
- package/lib/instantiateReactComponent.js +13 -9
- package/lib/isTextInputElement.js +2 -1
- package/lib/joinClasses.js +1 -1
- package/lib/setInnerHTML.js +1 -1
- package/lib/traverseAllChildren.js +1 -1
- package/lib/warning.js +0 -4
- package/package.json +1 -1
- package/react.js +53 -1
- package/addons/CSSTransitionGroup.js +0 -1
- package/addons/LinkedStateMixin.js +0 -1
- package/addons/Perf.js +0 -1
- package/addons/PureRenderMixin.js +0 -1
- package/addons/TestUtils.js +0 -1
- package/addons/TransitionGroup.js +0 -1
- package/addons/batchedUpdates.js +0 -1
- package/addons/cloneWithProps.js +0 -1
- package/addons/createFragment.js +0 -1
- package/addons/renderSubtreeIntoContainer.js +0 -1
- package/addons/shallowCompare.js +0 -1
- package/addons/update.js +0 -1
- package/lib/LocalEventTrapMixin.js +0 -46
- package/lib/ReactContext.js +0 -32
- package/lib/ReactDOMForm.js +0 -47
- package/lib/ReactDOMIframe.js +0 -43
- package/lib/ReactDOMImg.js +0 -44
- package/lib/ReactLifeCycle.js +0 -35
- package/lib/createFullPageComponent.js +0 -51
|
@@ -61,6 +61,20 @@ var ReactDOMIDOperations = {
|
|
|
61
61
|
}
|
|
62
62
|
},
|
|
63
63
|
|
|
64
|
+
/**
|
|
65
|
+
* Updates a DOM node with new property values.
|
|
66
|
+
*
|
|
67
|
+
* @param {string} id ID of the node to update.
|
|
68
|
+
* @param {string} name A valid property name.
|
|
69
|
+
* @param {*} value New value of the property.
|
|
70
|
+
* @internal
|
|
71
|
+
*/
|
|
72
|
+
updateAttributeByID: function (id, name, value) {
|
|
73
|
+
var node = ReactMount.getNode(id);
|
|
74
|
+
!!INVALID_PROPERTY_ERRORS.hasOwnProperty(name) ? 'production' !== process.env.NODE_ENV ? invariant(false, 'updatePropertyByID(...): %s', INVALID_PROPERTY_ERRORS[name]) : invariant(false) : undefined;
|
|
75
|
+
DOMPropertyOperations.setValueForAttribute(node, name, value);
|
|
76
|
+
},
|
|
77
|
+
|
|
64
78
|
/**
|
|
65
79
|
* Updates a DOM node to remove a property. This should only be used to remove
|
|
66
80
|
* DOM properties in `DOMProperty`.
|
package/lib/ReactDOMInput.js
CHANGED
|
@@ -11,27 +11,20 @@
|
|
|
11
11
|
|
|
12
12
|
'use strict';
|
|
13
13
|
|
|
14
|
-
var
|
|
15
|
-
var DOMPropertyOperations = require("./DOMPropertyOperations");
|
|
14
|
+
var ReactDOMIDOperations = require("./ReactDOMIDOperations");
|
|
16
15
|
var LinkedValueUtils = require("./LinkedValueUtils");
|
|
17
|
-
var ReactBrowserComponentMixin = require("./ReactBrowserComponentMixin");
|
|
18
|
-
var ReactClass = require("./ReactClass");
|
|
19
|
-
var ReactElement = require("./ReactElement");
|
|
20
16
|
var ReactMount = require("./ReactMount");
|
|
21
17
|
var ReactUpdates = require("./ReactUpdates");
|
|
22
18
|
|
|
23
19
|
var assign = require("./Object.assign");
|
|
24
|
-
var findDOMNode = require("./findDOMNode");
|
|
25
20
|
var invariant = require("./invariant");
|
|
26
21
|
|
|
27
|
-
var input = ReactElement.createFactory('input');
|
|
28
|
-
|
|
29
22
|
var instancesByReactID = {};
|
|
30
23
|
|
|
31
24
|
function forceUpdateIfMounted() {
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
25
|
+
if (this._rootNodeID) {
|
|
26
|
+
// DOM component is still mounted; update
|
|
27
|
+
ReactDOMInput.updateWrapper(this);
|
|
35
28
|
}
|
|
36
29
|
}
|
|
37
30
|
|
|
@@ -51,110 +44,101 @@ function forceUpdateIfMounted() {
|
|
|
51
44
|
*
|
|
52
45
|
* @see http://www.w3.org/TR/2012/WD-html5-20121025/the-input-element.html
|
|
53
46
|
*/
|
|
54
|
-
var ReactDOMInput =
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
};
|
|
47
|
+
var ReactDOMInput = {
|
|
48
|
+
getNativeProps: function (inst, props, context) {
|
|
49
|
+
var value = LinkedValueUtils.getValue(props);
|
|
50
|
+
var checked = LinkedValueUtils.getChecked(props);
|
|
51
|
+
|
|
52
|
+
var nativeProps = assign({}, props, {
|
|
53
|
+
defaultChecked: undefined,
|
|
54
|
+
defaultValue: undefined,
|
|
55
|
+
value: value != null ? value : inst._wrapperState.initialValue,
|
|
56
|
+
checked: checked != null ? checked : inst._wrapperState.initialChecked,
|
|
57
|
+
onChange: inst._wrapperState.onChange
|
|
58
|
+
});
|
|
59
|
+
|
|
60
|
+
return nativeProps;
|
|
66
61
|
},
|
|
67
62
|
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
var props = assign({}, this.props);
|
|
71
|
-
|
|
72
|
-
props.defaultChecked = null;
|
|
73
|
-
props.defaultValue = null;
|
|
63
|
+
mountWrapper: function (inst, props) {
|
|
64
|
+
LinkedValueUtils.checkPropTypes('input', props, inst._currentElement._owner);
|
|
74
65
|
|
|
75
|
-
var
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
props.onChange = this._handleChange;
|
|
66
|
+
var defaultValue = props.defaultValue;
|
|
67
|
+
inst._wrapperState = {
|
|
68
|
+
initialChecked: props.defaultChecked || false,
|
|
69
|
+
initialValue: defaultValue != null ? defaultValue : null,
|
|
70
|
+
onChange: _handleChange.bind(inst)
|
|
71
|
+
};
|
|
82
72
|
|
|
83
|
-
|
|
73
|
+
instancesByReactID[inst._rootNodeID] = inst;
|
|
84
74
|
},
|
|
85
75
|
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
instancesByReactID[id] = this;
|
|
76
|
+
unmountWrapper: function (inst) {
|
|
77
|
+
delete instancesByReactID[inst._rootNodeID];
|
|
89
78
|
},
|
|
90
79
|
|
|
91
|
-
|
|
92
|
-
var
|
|
93
|
-
var id = ReactMount.getID(rootNode);
|
|
94
|
-
delete instancesByReactID[id];
|
|
95
|
-
},
|
|
80
|
+
updateWrapper: function (inst) {
|
|
81
|
+
var props = inst._currentElement.props;
|
|
96
82
|
|
|
97
|
-
|
|
98
|
-
var
|
|
99
|
-
if (
|
|
100
|
-
|
|
83
|
+
// TODO: Shouldn't this be getChecked(props)?
|
|
84
|
+
var checked = props.checked;
|
|
85
|
+
if (checked != null) {
|
|
86
|
+
ReactDOMIDOperations.updatePropertyByID(inst._rootNodeID, 'checked', checked || false);
|
|
101
87
|
}
|
|
102
88
|
|
|
103
|
-
var value = LinkedValueUtils.getValue(
|
|
89
|
+
var value = LinkedValueUtils.getValue(props);
|
|
104
90
|
if (value != null) {
|
|
105
91
|
// Cast `value` to a string to ensure the value is set correctly. While
|
|
106
92
|
// browsers typically do this as necessary, jsdom doesn't.
|
|
107
|
-
|
|
93
|
+
ReactDOMIDOperations.updatePropertyByID(inst._rootNodeID, 'value', '' + value);
|
|
108
94
|
}
|
|
109
|
-
}
|
|
95
|
+
}
|
|
96
|
+
};
|
|
97
|
+
|
|
98
|
+
function _handleChange(event) {
|
|
99
|
+
var props = this._currentElement.props;
|
|
100
|
+
|
|
101
|
+
var returnValue = LinkedValueUtils.executeOnChange(props, event);
|
|
102
|
+
|
|
103
|
+
// Here we use asap to wait until all updates have propagated, which
|
|
104
|
+
// is important when using controlled components within layers:
|
|
105
|
+
// https://github.com/facebook/react/issues/1698
|
|
106
|
+
ReactUpdates.asap(forceUpdateIfMounted, this);
|
|
110
107
|
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
var
|
|
114
|
-
|
|
115
|
-
|
|
108
|
+
var name = props.name;
|
|
109
|
+
if (props.type === 'radio' && name != null) {
|
|
110
|
+
var rootNode = ReactMount.getNode(this._rootNodeID);
|
|
111
|
+
var queryRoot = rootNode;
|
|
112
|
+
|
|
113
|
+
while (queryRoot.parentNode) {
|
|
114
|
+
queryRoot = queryRoot.parentNode;
|
|
116
115
|
}
|
|
117
|
-
// Here we use asap to wait until all updates have propagated, which
|
|
118
|
-
// is important when using controlled components within layers:
|
|
119
|
-
// https://github.com/facebook/react/issues/1698
|
|
120
|
-
ReactUpdates.asap(forceUpdateIfMounted, this);
|
|
121
|
-
|
|
122
|
-
var name = this.props.name;
|
|
123
|
-
if (this.props.type === 'radio' && name != null) {
|
|
124
|
-
var rootNode = findDOMNode(this);
|
|
125
|
-
var queryRoot = rootNode;
|
|
126
|
-
|
|
127
|
-
while (queryRoot.parentNode) {
|
|
128
|
-
queryRoot = queryRoot.parentNode;
|
|
129
|
-
}
|
|
130
116
|
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
}
|
|
144
|
-
var otherID = ReactMount.getID(otherNode);
|
|
145
|
-
!otherID ? 'production' !== process.env.NODE_ENV ? invariant(false, 'ReactDOMInput: Mixing React and non-React radio inputs with the ' + 'same `name` is not supported.') : invariant(false) : undefined;
|
|
146
|
-
var otherInstance = instancesByReactID[otherID];
|
|
147
|
-
!otherInstance ? 'production' !== process.env.NODE_ENV ? invariant(false, 'ReactDOMInput: Unknown radio button ID %s.', otherID) : invariant(false) : undefined;
|
|
148
|
-
// If this is a controlled radio button group, forcing the input that
|
|
149
|
-
// was previously checked to update will cause it to be come re-checked
|
|
150
|
-
// as appropriate.
|
|
151
|
-
ReactUpdates.asap(forceUpdateIfMounted, otherInstance);
|
|
117
|
+
// If `rootNode.form` was non-null, then we could try `form.elements`,
|
|
118
|
+
// but that sometimes behaves strangely in IE8. We could also try using
|
|
119
|
+
// `form.getElementsByName`, but that will only return direct children
|
|
120
|
+
// and won't include inputs that use the HTML5 `form=` attribute. Since
|
|
121
|
+
// the input might not even be in a form, let's just use the global
|
|
122
|
+
// `querySelectorAll` to ensure we don't miss anything.
|
|
123
|
+
var group = queryRoot.querySelectorAll('input[name=' + JSON.stringify('' + name) + '][type="radio"]');
|
|
124
|
+
|
|
125
|
+
for (var i = 0; i < group.length; i++) {
|
|
126
|
+
var otherNode = group[i];
|
|
127
|
+
if (otherNode === rootNode || otherNode.form !== rootNode.form) {
|
|
128
|
+
continue;
|
|
152
129
|
}
|
|
130
|
+
var otherID = ReactMount.getID(otherNode);
|
|
131
|
+
!otherID ? 'production' !== process.env.NODE_ENV ? invariant(false, 'ReactDOMInput: Mixing React and non-React radio inputs with the ' + 'same `name` is not supported.') : invariant(false) : undefined;
|
|
132
|
+
var otherInstance = instancesByReactID[otherID];
|
|
133
|
+
!otherInstance ? 'production' !== process.env.NODE_ENV ? invariant(false, 'ReactDOMInput: Unknown radio button ID %s.', otherID) : invariant(false) : undefined;
|
|
134
|
+
// If this is a controlled radio button group, forcing the input that
|
|
135
|
+
// was previously checked to update will cause it to be come re-checked
|
|
136
|
+
// as appropriate.
|
|
137
|
+
ReactUpdates.asap(forceUpdateIfMounted, otherInstance);
|
|
153
138
|
}
|
|
154
|
-
|
|
155
|
-
return returnValue;
|
|
156
139
|
}
|
|
157
140
|
|
|
158
|
-
|
|
141
|
+
return returnValue;
|
|
142
|
+
}
|
|
159
143
|
|
|
160
144
|
module.exports = ReactDOMInput;
|
package/lib/ReactDOMOption.js
CHANGED
|
@@ -11,82 +11,62 @@
|
|
|
11
11
|
|
|
12
12
|
'use strict';
|
|
13
13
|
|
|
14
|
-
var ReactBrowserComponentMixin = require("./ReactBrowserComponentMixin");
|
|
15
14
|
var ReactChildren = require("./ReactChildren");
|
|
16
|
-
var ReactClass = require("./ReactClass");
|
|
17
15
|
var ReactDOMSelect = require("./ReactDOMSelect");
|
|
18
|
-
var ReactElement = require("./ReactElement");
|
|
19
|
-
var ReactPropTypes = require("./ReactPropTypes");
|
|
20
16
|
|
|
21
17
|
var assign = require("./Object.assign");
|
|
22
18
|
var warning = require("./warning");
|
|
23
19
|
|
|
24
|
-
var option = ReactElement.createFactory('option');
|
|
25
|
-
|
|
26
20
|
var valueContextKey = ReactDOMSelect.valueContextKey;
|
|
27
21
|
|
|
28
22
|
/**
|
|
29
23
|
* Implements an <option> native component that warns when `selected` is set.
|
|
30
24
|
*/
|
|
31
|
-
var ReactDOMOption =
|
|
32
|
-
|
|
33
|
-
tagName: 'OPTION',
|
|
34
|
-
|
|
35
|
-
mixins: [ReactBrowserComponentMixin],
|
|
36
|
-
|
|
37
|
-
getInitialState: function () {
|
|
38
|
-
return { selected: null };
|
|
39
|
-
},
|
|
40
|
-
|
|
41
|
-
contextTypes: (function () {
|
|
42
|
-
var obj = {};
|
|
43
|
-
obj[valueContextKey] = ReactPropTypes.any;
|
|
44
|
-
return obj;
|
|
45
|
-
})(),
|
|
46
|
-
|
|
47
|
-
componentWillMount: function () {
|
|
25
|
+
var ReactDOMOption = {
|
|
26
|
+
mountWrapper: function (inst, props, context) {
|
|
48
27
|
// TODO (yungsters): Remove support for `selected` in <option>.
|
|
49
28
|
if ('production' !== process.env.NODE_ENV) {
|
|
50
|
-
'production' !== process.env.NODE_ENV ? warning(
|
|
29
|
+
'production' !== process.env.NODE_ENV ? warning(props.selected == null, 'Use the `defaultValue` or `value` props on <select> instead of ' + 'setting `selected` on <option>.') : undefined;
|
|
51
30
|
}
|
|
52
31
|
|
|
53
|
-
// Look up whether this option is 'selected' via
|
|
54
|
-
var context = this.context;
|
|
32
|
+
// Look up whether this option is 'selected' via context
|
|
55
33
|
var selectValue = context[valueContextKey];
|
|
56
34
|
|
|
57
35
|
// If context key is null (e.g., no specified value or after initial mount)
|
|
58
|
-
// or missing (e.g., for <datalist>)
|
|
36
|
+
// or missing (e.g., for <datalist>), we don't change props.selected
|
|
37
|
+
var selected = null;
|
|
59
38
|
if (selectValue != null) {
|
|
60
|
-
|
|
39
|
+
selected = false;
|
|
61
40
|
if (Array.isArray(selectValue)) {
|
|
62
41
|
// multiple
|
|
63
42
|
for (var i = 0; i < selectValue.length; i++) {
|
|
64
|
-
if ('' + selectValue[i] === '' +
|
|
43
|
+
if ('' + selectValue[i] === '' + props.value) {
|
|
65
44
|
selected = true;
|
|
66
45
|
break;
|
|
67
46
|
}
|
|
68
47
|
}
|
|
69
48
|
} else {
|
|
70
|
-
selected = '' + selectValue === '' +
|
|
49
|
+
selected = '' + selectValue === '' + props.value;
|
|
71
50
|
}
|
|
72
|
-
this.setState({ selected: selected });
|
|
73
51
|
}
|
|
52
|
+
|
|
53
|
+
inst._wrapperState = { selected: selected };
|
|
74
54
|
},
|
|
75
55
|
|
|
76
|
-
|
|
77
|
-
var
|
|
56
|
+
getNativeProps: function (inst, props, context) {
|
|
57
|
+
var nativeProps = assign({ selected: undefined, children: undefined }, props);
|
|
78
58
|
|
|
79
59
|
// Read state only from initial mount because <select> updates value
|
|
80
60
|
// manually; we need the initial state only for server rendering
|
|
81
|
-
if (
|
|
82
|
-
|
|
61
|
+
if (inst._wrapperState.selected != null) {
|
|
62
|
+
nativeProps.selected = inst._wrapperState.selected;
|
|
83
63
|
}
|
|
84
64
|
|
|
85
65
|
var content = '';
|
|
86
66
|
|
|
87
67
|
// Flatten children and warn if they aren't strings or numbers;
|
|
88
68
|
// invalid types are ignored.
|
|
89
|
-
ReactChildren.forEach(
|
|
69
|
+
ReactChildren.forEach(props.children, function (child) {
|
|
90
70
|
if (child == null) {
|
|
91
71
|
return;
|
|
92
72
|
}
|
|
@@ -97,9 +77,10 @@ var ReactDOMOption = ReactClass.createClass({
|
|
|
97
77
|
}
|
|
98
78
|
});
|
|
99
79
|
|
|
100
|
-
|
|
80
|
+
nativeProps.children = content;
|
|
81
|
+
return nativeProps;
|
|
101
82
|
}
|
|
102
83
|
|
|
103
|
-
}
|
|
84
|
+
};
|
|
104
85
|
|
|
105
86
|
module.exports = ReactDOMOption;
|
package/lib/ReactDOMSelect.js
CHANGED
|
@@ -11,61 +11,72 @@
|
|
|
11
11
|
|
|
12
12
|
'use strict';
|
|
13
13
|
|
|
14
|
-
var AutoFocusMixin = require("./AutoFocusMixin");
|
|
15
14
|
var LinkedValueUtils = require("./LinkedValueUtils");
|
|
16
|
-
var
|
|
17
|
-
var ReactClass = require("./ReactClass");
|
|
18
|
-
var ReactElement = require("./ReactElement");
|
|
15
|
+
var ReactMount = require("./ReactMount");
|
|
19
16
|
var ReactUpdates = require("./ReactUpdates");
|
|
20
|
-
var ReactPropTypes = require("./ReactPropTypes");
|
|
21
17
|
|
|
22
18
|
var assign = require("./Object.assign");
|
|
23
|
-
var
|
|
24
|
-
|
|
25
|
-
var select = ReactElement.createFactory('select');
|
|
19
|
+
var warning = require("./warning");
|
|
26
20
|
|
|
27
21
|
var valueContextKey = '__ReactDOMSelect_value$' + Math.random().toString(36).slice(2);
|
|
28
22
|
|
|
29
23
|
function updateOptionsIfPendingUpdateAndMounted() {
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
var
|
|
34
|
-
|
|
35
|
-
|
|
24
|
+
if (this._wrapperState.pendingUpdate && this._rootNodeID) {
|
|
25
|
+
this._wrapperState.pendingUpdate = false;
|
|
26
|
+
|
|
27
|
+
var props = this._currentElement.props;
|
|
28
|
+
var value = LinkedValueUtils.getValue(props);
|
|
29
|
+
|
|
30
|
+
if (value != null) {
|
|
31
|
+
updateOptions(this, props, value);
|
|
36
32
|
}
|
|
37
33
|
}
|
|
38
34
|
}
|
|
39
35
|
|
|
36
|
+
function getDeclarationErrorAddendum(owner) {
|
|
37
|
+
if (owner) {
|
|
38
|
+
var name = owner.getName();
|
|
39
|
+
if (name) {
|
|
40
|
+
return ' Check the render method of `' + name + '`.';
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
return '';
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
var valuePropNames = ['value', 'defaultValue'];
|
|
47
|
+
|
|
40
48
|
/**
|
|
41
49
|
* Validation function for `value` and `defaultValue`.
|
|
42
50
|
* @private
|
|
43
51
|
*/
|
|
44
|
-
function
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
52
|
+
function checkSelectPropTypes(inst, props) {
|
|
53
|
+
var owner = inst._currentElement._owner;
|
|
54
|
+
LinkedValueUtils.checkPropTypes('select', props, owner);
|
|
55
|
+
|
|
56
|
+
for (var i = 0; i < valuePropNames.length; i++) {
|
|
57
|
+
var propName = valuePropNames[i];
|
|
58
|
+
if (props[propName] == null) {
|
|
59
|
+
continue;
|
|
51
60
|
}
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
61
|
+
if (props.multiple) {
|
|
62
|
+
'production' !== process.env.NODE_ENV ? warning(Array.isArray(props[propName]), 'The `%s` prop supplied to <select> must be an array if ' + '`multiple` is true.%s', propName, getDeclarationErrorAddendum(owner)) : undefined;
|
|
63
|
+
} else {
|
|
64
|
+
'production' !== process.env.NODE_ENV ? warning(!Array.isArray(props[propName]), 'The `%s` prop supplied to <select> must be a scalar ' + 'value if `multiple` is false.%s', propName, getDeclarationErrorAddendum(owner)) : undefined;
|
|
55
65
|
}
|
|
56
66
|
}
|
|
57
67
|
}
|
|
58
68
|
|
|
59
69
|
/**
|
|
60
|
-
* @param {
|
|
70
|
+
* @param {ReactDOMComponent} inst
|
|
71
|
+
* @param {boolean} multiple
|
|
61
72
|
* @param {*} propValue A stringable (with `multiple`, a list of stringables).
|
|
62
73
|
* @private
|
|
63
74
|
*/
|
|
64
|
-
function updateOptions(
|
|
75
|
+
function updateOptions(inst, multiple, propValue) {
|
|
65
76
|
var selectedValue, i;
|
|
66
|
-
var options =
|
|
77
|
+
var options = ReactMount.getNode(inst._rootNodeID).options;
|
|
67
78
|
|
|
68
|
-
if (
|
|
79
|
+
if (multiple) {
|
|
69
80
|
selectedValue = {};
|
|
70
81
|
for (i = 0; i < propValue.length; i++) {
|
|
71
82
|
selectedValue['' + propValue[i]] = true;
|
|
@@ -107,92 +118,71 @@ function updateOptions(component, propValue) {
|
|
|
107
118
|
* If `defaultValue` is provided, any options with the supplied values will be
|
|
108
119
|
* selected.
|
|
109
120
|
*/
|
|
110
|
-
var ReactDOMSelect =
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
121
|
+
var ReactDOMSelect = {
|
|
122
|
+
valueContextKey: valueContextKey,
|
|
123
|
+
|
|
124
|
+
getNativeProps: function (inst, props, context) {
|
|
125
|
+
return assign({}, props, {
|
|
126
|
+
onChange: inst._wrapperState.onChange,
|
|
127
|
+
value: undefined
|
|
128
|
+
});
|
|
118
129
|
},
|
|
119
130
|
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
},
|
|
124
|
-
|
|
125
|
-
getInitialState: function () {
|
|
126
|
-
// Pass down initial value so initial generated markup has correct
|
|
127
|
-
// `selected` attributes
|
|
128
|
-
var value = LinkedValueUtils.getValue(this.props);
|
|
129
|
-
if (value != null) {
|
|
130
|
-
return { initialValue: value };
|
|
131
|
-
} else {
|
|
132
|
-
return { initialValue: this.props.defaultValue };
|
|
131
|
+
mountWrapper: function (inst, props) {
|
|
132
|
+
if ('production' !== process.env.NODE_ENV) {
|
|
133
|
+
checkSelectPropTypes(inst, props);
|
|
133
134
|
}
|
|
134
|
-
},
|
|
135
135
|
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
var obj = {};
|
|
144
|
-
obj[valueContextKey] = this.state.initialValue;
|
|
145
|
-
return obj;
|
|
136
|
+
var value = LinkedValueUtils.getValue(props);
|
|
137
|
+
inst._wrapperState = {
|
|
138
|
+
pendingUpdate: false,
|
|
139
|
+
initialValue: value != null ? value : props.defaultValue,
|
|
140
|
+
onChange: _handleChange.bind(inst),
|
|
141
|
+
wasMultiple: Boolean(props.multiple)
|
|
142
|
+
};
|
|
146
143
|
},
|
|
147
144
|
|
|
148
|
-
|
|
149
|
-
//
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
return select(props, this.props.children);
|
|
145
|
+
processChildContext: function (inst, props, context) {
|
|
146
|
+
// Pass down initial value so initial generated markup has correct
|
|
147
|
+
// `selected` attributes
|
|
148
|
+
var childContext = assign({}, context);
|
|
149
|
+
childContext[valueContextKey] = inst._wrapperState.initialValue;
|
|
150
|
+
return childContext;
|
|
156
151
|
},
|
|
157
152
|
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
},
|
|
153
|
+
postUpdateWrapper: function (inst) {
|
|
154
|
+
var props = inst._currentElement.props;
|
|
161
155
|
|
|
162
|
-
componentWillReceiveProps: function (nextProps) {
|
|
163
156
|
// After the initial mount, we control selected-ness manually so don't pass
|
|
164
157
|
// the context value down
|
|
165
|
-
|
|
166
|
-
|
|
158
|
+
inst._wrapperState.initialValue = undefined;
|
|
159
|
+
|
|
160
|
+
var wasMultiple = inst._wrapperState.wasMultiple;
|
|
161
|
+
inst._wrapperState.wasMultiple = Boolean(props.multiple);
|
|
167
162
|
|
|
168
|
-
|
|
169
|
-
var value = LinkedValueUtils.getValue(this.props);
|
|
163
|
+
var value = LinkedValueUtils.getValue(props);
|
|
170
164
|
if (value != null) {
|
|
171
|
-
|
|
172
|
-
updateOptions(
|
|
173
|
-
} else if (
|
|
165
|
+
inst._wrapperState.pendingUpdate = false;
|
|
166
|
+
updateOptions(inst, Boolean(props.multiple), value);
|
|
167
|
+
} else if (wasMultiple !== Boolean(props.multiple)) {
|
|
174
168
|
// For simplicity, reapply `defaultValue` if `multiple` is toggled.
|
|
175
|
-
if (
|
|
176
|
-
updateOptions(
|
|
169
|
+
if (props.defaultValue != null) {
|
|
170
|
+
updateOptions(inst, Boolean(props.multiple), props.defaultValue);
|
|
177
171
|
} else {
|
|
178
172
|
// Revert the select back to its default unselected state.
|
|
179
|
-
updateOptions(
|
|
173
|
+
updateOptions(inst, Boolean(props.multiple), props.multiple ? [] : '');
|
|
180
174
|
}
|
|
181
175
|
}
|
|
182
|
-
},
|
|
183
|
-
|
|
184
|
-
_handleChange: function (event) {
|
|
185
|
-
var returnValue;
|
|
186
|
-
var onChange = LinkedValueUtils.getOnChange(this.props);
|
|
187
|
-
if (onChange) {
|
|
188
|
-
returnValue = onChange.call(this, event);
|
|
189
|
-
}
|
|
190
|
-
|
|
191
|
-
this._pendingUpdate = true;
|
|
192
|
-
ReactUpdates.asap(updateOptionsIfPendingUpdateAndMounted, this);
|
|
193
|
-
return returnValue;
|
|
194
176
|
}
|
|
177
|
+
};
|
|
195
178
|
|
|
196
|
-
|
|
179
|
+
function _handleChange(event) {
|
|
180
|
+
var props = this._currentElement.props;
|
|
181
|
+
var returnValue = LinkedValueUtils.executeOnChange(props, event);
|
|
182
|
+
|
|
183
|
+
this._wrapperState.pendingUpdate = true;
|
|
184
|
+
ReactUpdates.asap(updateOptionsIfPendingUpdateAndMounted, this);
|
|
185
|
+
return returnValue;
|
|
186
|
+
}
|
|
197
187
|
|
|
198
188
|
module.exports = ReactDOMSelect;
|