react 0.8.0 → 0.10.0

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.
Files changed (160) hide show
  1. package/README.md +0 -8
  2. package/addons.js +0 -3
  3. package/lib/AutoFocusMixin.js +32 -0
  4. package/lib/CSSCore.js +23 -22
  5. package/lib/CSSProperty.js +32 -1
  6. package/lib/CSSPropertyOperations.js +1 -1
  7. package/lib/ChangeEventPlugin.js +27 -5
  8. package/lib/ClientReactRootIndex.js +30 -0
  9. package/lib/CompositionEventPlugin.js +58 -10
  10. package/lib/DOMChildrenOperations.js +39 -3
  11. package/lib/DOMProperty.js +9 -5
  12. package/lib/DOMPropertyOperations.js +21 -8
  13. package/lib/Danger.js +9 -8
  14. package/lib/DefaultDOMPropertyConfig.js +23 -14
  15. package/lib/DefaultEventPluginOrder.js +1 -1
  16. package/lib/EnterLeaveEventPlugin.js +38 -5
  17. package/lib/EventConstants.js +4 -1
  18. package/lib/EventListener.js +42 -34
  19. package/lib/EventPluginHub.js +118 -13
  20. package/lib/EventPluginRegistry.js +62 -18
  21. package/lib/EventPluginUtils.js +33 -4
  22. package/lib/EventPropagators.js +7 -43
  23. package/lib/ExecutionEnvironment.js +4 -1
  24. package/lib/LinkedStateMixin.js +1 -1
  25. package/lib/LinkedValueUtils.js +160 -0
  26. package/lib/MobileSafariClickEventPlugin.js +1 -1
  27. package/lib/PooledClass.js +7 -1
  28. package/lib/React.js +30 -4
  29. package/lib/ReactBrowserComponentMixin.js +42 -0
  30. package/lib/ReactCSSTransitionGroup.js +65 -0
  31. package/lib/{ReactTransitionableChild.js → ReactCSSTransitionGroupChild.js} +22 -36
  32. package/lib/ReactChildren.js +4 -4
  33. package/lib/ReactComponent.js +163 -83
  34. package/lib/ReactComponentBrowserEnvironment.js +55 -71
  35. package/lib/ReactCompositeComponent.js +686 -119
  36. package/lib/ReactContext.js +67 -0
  37. package/lib/ReactCurrentOwner.js +1 -1
  38. package/lib/ReactDOM.js +19 -6
  39. package/lib/ReactDOMButton.js +6 -1
  40. package/lib/ReactDOMComponent.js +66 -24
  41. package/lib/ReactDOMForm.js +13 -3
  42. package/lib/ReactDOMIDOperations.js +106 -61
  43. package/lib/ReactDOMImg.js +61 -0
  44. package/lib/ReactDOMInput.js +28 -15
  45. package/lib/ReactDOMOption.js +13 -8
  46. package/lib/ReactDOMSelect.js +38 -18
  47. package/lib/ReactDOMSelection.js +1 -1
  48. package/lib/ReactDOMTextarea.js +19 -11
  49. package/lib/ReactDefaultBatchingStrategy.js +1 -1
  50. package/lib/ReactDefaultInjection.js +60 -26
  51. package/lib/ReactDefaultPerf.js +208 -371
  52. package/lib/ReactDefaultPerfAnalysis.js +199 -0
  53. package/lib/ReactErrorUtils.js +6 -15
  54. package/lib/ReactEventEmitter.js +144 -146
  55. package/lib/ReactEventEmitterMixin.js +1 -33
  56. package/lib/ReactEventTopLevelCallback.js +75 -15
  57. package/lib/ReactInjection.js +43 -0
  58. package/lib/ReactInputSelection.js +3 -2
  59. package/lib/ReactInstanceHandles.js +36 -20
  60. package/lib/ReactLink.js +2 -2
  61. package/lib/ReactMarkupChecksum.js +1 -1
  62. package/lib/ReactMount.js +136 -104
  63. package/lib/ReactMountReady.js +2 -2
  64. package/lib/ReactMultiChild.js +40 -49
  65. package/lib/ReactMultiChildUpdateTypes.js +3 -1
  66. package/lib/ReactOwner.js +17 -4
  67. package/lib/ReactPerf.js +6 -9
  68. package/lib/ReactPropTransferer.js +41 -22
  69. package/lib/ReactPropTypeLocationNames.js +31 -0
  70. package/lib/{ReactComponentEnvironment.js → ReactPropTypeLocations.js} +11 -6
  71. package/lib/ReactPropTypes.js +249 -48
  72. package/lib/ReactPutListenerQueue.js +61 -0
  73. package/lib/ReactReconcileTransaction.js +28 -7
  74. package/lib/ReactRootIndex.js +36 -0
  75. package/lib/ReactServerRendering.js +46 -19
  76. package/lib/ReactServerRenderingTransaction.js +116 -0
  77. package/lib/ReactStateSetters.js +1 -1
  78. package/lib/ReactTestUtils.js +394 -0
  79. package/lib/ReactTextComponent.js +33 -6
  80. package/lib/{ReactTransitionKeySet.js → ReactTransitionChildMapping.js} +43 -48
  81. package/lib/ReactTransitionEvents.js +1 -1
  82. package/lib/ReactTransitionGroup.js +133 -58
  83. package/lib/ReactUpdates.js +15 -12
  84. package/lib/ReactWithAddons.js +15 -3
  85. package/lib/SelectEventPlugin.js +23 -40
  86. package/lib/ServerReactRootIndex.js +36 -0
  87. package/lib/SimpleEventPlugin.js +55 -7
  88. package/lib/SyntheticClipboardEvent.js +8 -2
  89. package/lib/SyntheticCompositionEvent.js +1 -1
  90. package/lib/SyntheticDragEvent.js +44 -0
  91. package/lib/SyntheticEvent.js +3 -2
  92. package/lib/SyntheticFocusEvent.js +1 -1
  93. package/lib/SyntheticKeyboardEvent.js +5 -3
  94. package/lib/SyntheticMouseEvent.js +1 -1
  95. package/lib/SyntheticTouchEvent.js +1 -1
  96. package/lib/SyntheticUIEvent.js +1 -1
  97. package/lib/SyntheticWheelEvent.js +11 -8
  98. package/lib/Transaction.js +62 -37
  99. package/lib/ViewportMetrics.js +1 -1
  100. package/lib/accumulate.js +1 -1
  101. package/lib/adler32.js +1 -1
  102. package/lib/cloneWithProps.js +59 -0
  103. package/lib/containsNode.js +1 -1
  104. package/lib/copyProperties.js +1 -1
  105. package/lib/createArrayFrom.js +11 -14
  106. package/lib/createFullPageComponent.js +63 -0
  107. package/lib/createNodesFromMarkup.js +1 -1
  108. package/lib/createObjectFrom.js +1 -1
  109. package/lib/cx.js +3 -3
  110. package/lib/dangerousStyleValue.js +1 -1
  111. package/lib/emptyFunction.js +1 -1
  112. package/lib/emptyObject.js +27 -0
  113. package/lib/escapeTextForBrowser.js +1 -1
  114. package/lib/flattenChildren.js +6 -3
  115. package/lib/focusNode.js +33 -0
  116. package/lib/forEachAccumulated.js +1 -1
  117. package/lib/getActiveElement.js +5 -4
  118. package/lib/getEventKey.js +85 -0
  119. package/lib/getEventTarget.js +1 -1
  120. package/lib/getMarkupWrap.js +11 -1
  121. package/lib/getNodeForCharacterOffset.js +1 -1
  122. package/lib/getReactRootElementInContainer.js +1 -1
  123. package/lib/getTextContentAccessor.js +6 -4
  124. package/lib/getUnboundedScrollPosition.js +3 -3
  125. package/lib/hyphenate.js +1 -1
  126. package/lib/instantiateReactComponent.js +70 -0
  127. package/lib/invariant.js +20 -12
  128. package/lib/isEventSupported.js +8 -12
  129. package/lib/isNode.js +2 -2
  130. package/lib/isTextInputElement.js +1 -1
  131. package/lib/isTextNode.js +1 -1
  132. package/lib/joinClasses.js +1 -1
  133. package/lib/keyMirror.js +1 -1
  134. package/lib/keyOf.js +1 -1
  135. package/lib/memoizeStringOnly.js +1 -1
  136. package/lib/merge.js +1 -1
  137. package/lib/mergeHelpers.js +6 -7
  138. package/lib/mergeInto.js +1 -1
  139. package/lib/mixInto.js +1 -1
  140. package/lib/monitorCodeUse.js +37 -0
  141. package/lib/objMap.js +1 -1
  142. package/lib/objMapKeyVal.js +1 -1
  143. package/lib/onlyChild.js +43 -0
  144. package/lib/performanceNow.js +1 -1
  145. package/lib/shallowEqual.js +1 -1
  146. package/lib/shouldUpdateReactComponent.js +61 -0
  147. package/lib/toArray.js +75 -0
  148. package/lib/traverseAllChildren.js +72 -9
  149. package/lib/update.js +159 -0
  150. package/lib/warning.js +48 -0
  151. package/package.json +3 -3
  152. package/react.js +0 -3
  153. package/ReactJSErrors.js +0 -40
  154. package/lib/$.js +0 -46
  155. package/lib/CallbackRegistry.js +0 -91
  156. package/lib/LinkedValueMixin.js +0 -68
  157. package/lib/ex.js +0 -49
  158. package/lib/filterAttributes.js +0 -45
  159. package/lib/ge.js +0 -76
  160. package/lib/mutateHTMLNodeWithMarkup.js +0 -100
@@ -1,5 +1,5 @@
1
1
  /**
2
- * Copyright 2013 Facebook, Inc.
2
+ * Copyright 2013-2014 Facebook, Inc.
3
3
  *
4
4
  * Licensed under the Apache License, Version 2.0 (the "License");
5
5
  * you may not use this file except in compliance with the License.
@@ -25,8 +25,8 @@ var CSSPropertyOperations = require("./CSSPropertyOperations");
25
25
  var DOMChildrenOperations = require("./DOMChildrenOperations");
26
26
  var DOMPropertyOperations = require("./DOMPropertyOperations");
27
27
  var ReactMount = require("./ReactMount");
28
+ var ReactPerf = require("./ReactPerf");
28
29
 
29
- var getTextContentAccessor = require("./getTextContentAccessor");
30
30
  var invariant = require("./invariant");
31
31
 
32
32
  /**
@@ -41,19 +41,11 @@ var INVALID_PROPERTY_ERRORS = {
41
41
  style: '`style` must be set using `updateStylesByID()`.'
42
42
  };
43
43
 
44
- /**
45
- * The DOM property to use when setting text content.
46
- *
47
- * @type {string}
48
- * @private
49
- */
50
- var textContentAccessor = getTextContentAccessor() || 'NA';
51
-
52
- var LEADING_SPACE = /^ /;
44
+ var useWhitespaceWorkaround;
53
45
 
54
46
  /**
55
47
  * Operations used to process updates to DOM nodes. This is made injectable via
56
- * `ReactComponent.DOMIDOperations`.
48
+ * `ReactComponent.BackendIDOperations`.
57
49
  */
58
50
  var ReactDOMIDOperations = {
59
51
 
@@ -66,23 +58,27 @@ var ReactDOMIDOperations = {
66
58
  * @param {*} value New value of the property.
67
59
  * @internal
68
60
  */
69
- updatePropertyByID: function(id, name, value) {
70
- var node = ReactMount.getNode(id);
71
- ("production" !== process.env.NODE_ENV ? invariant(
72
- !INVALID_PROPERTY_ERRORS.hasOwnProperty(name),
73
- 'updatePropertyByID(...): %s',
74
- INVALID_PROPERTY_ERRORS[name]
75
- ) : invariant(!INVALID_PROPERTY_ERRORS.hasOwnProperty(name)));
76
-
77
- // If we're updating to null or undefined, we should remove the property
78
- // from the DOM node instead of inadvertantly setting to a string. This
79
- // brings us in line with the same behavior we have on initial render.
80
- if (value != null) {
81
- DOMPropertyOperations.setValueForProperty(node, name, value);
82
- } else {
83
- DOMPropertyOperations.deleteValueForProperty(node, name);
61
+ updatePropertyByID: ReactPerf.measure(
62
+ 'ReactDOMIDOperations',
63
+ 'updatePropertyByID',
64
+ function(id, name, value) {
65
+ var node = ReactMount.getNode(id);
66
+ ("production" !== process.env.NODE_ENV ? invariant(
67
+ !INVALID_PROPERTY_ERRORS.hasOwnProperty(name),
68
+ 'updatePropertyByID(...): %s',
69
+ INVALID_PROPERTY_ERRORS[name]
70
+ ) : invariant(!INVALID_PROPERTY_ERRORS.hasOwnProperty(name)));
71
+
72
+ // If we're updating to null or undefined, we should remove the property
73
+ // from the DOM node instead of inadvertantly setting to a string. This
74
+ // brings us in line with the same behavior we have on initial render.
75
+ if (value != null) {
76
+ DOMPropertyOperations.setValueForProperty(node, name, value);
77
+ } else {
78
+ DOMPropertyOperations.deleteValueForProperty(node, name);
79
+ }
84
80
  }
85
- },
81
+ ),
86
82
 
87
83
  /**
88
84
  * Updates a DOM node to remove a property. This should only be used to remove
@@ -92,15 +88,19 @@ var ReactDOMIDOperations = {
92
88
  * @param {string} name A property name to remove, see `DOMProperty`.
93
89
  * @internal
94
90
  */
95
- deletePropertyByID: function(id, name, value) {
96
- var node = ReactMount.getNode(id);
97
- ("production" !== process.env.NODE_ENV ? invariant(
98
- !INVALID_PROPERTY_ERRORS.hasOwnProperty(name),
99
- 'updatePropertyByID(...): %s',
100
- INVALID_PROPERTY_ERRORS[name]
101
- ) : invariant(!INVALID_PROPERTY_ERRORS.hasOwnProperty(name)));
102
- DOMPropertyOperations.deleteValueForProperty(node, name, value);
103
- },
91
+ deletePropertyByID: ReactPerf.measure(
92
+ 'ReactDOMIDOperations',
93
+ 'deletePropertyByID',
94
+ function(id, name, value) {
95
+ var node = ReactMount.getNode(id);
96
+ ("production" !== process.env.NODE_ENV ? invariant(
97
+ !INVALID_PROPERTY_ERRORS.hasOwnProperty(name),
98
+ 'updatePropertyByID(...): %s',
99
+ INVALID_PROPERTY_ERRORS[name]
100
+ ) : invariant(!INVALID_PROPERTY_ERRORS.hasOwnProperty(name)));
101
+ DOMPropertyOperations.deleteValueForProperty(node, name, value);
102
+ }
103
+ ),
104
104
 
105
105
  /**
106
106
  * Updates a DOM node with new style values. If a value is specified as '',
@@ -110,10 +110,14 @@ var ReactDOMIDOperations = {
110
110
  * @param {object} styles Mapping from styles to values.
111
111
  * @internal
112
112
  */
113
- updateStylesByID: function(id, styles) {
114
- var node = ReactMount.getNode(id);
115
- CSSPropertyOperations.setValueForStyles(node, styles);
116
- },
113
+ updateStylesByID: ReactPerf.measure(
114
+ 'ReactDOMIDOperations',
115
+ 'updateStylesByID',
116
+ function(id, styles) {
117
+ var node = ReactMount.getNode(id);
118
+ CSSPropertyOperations.setValueForStyles(node, styles);
119
+ }
120
+ ),
117
121
 
118
122
  /**
119
123
  * Updates a DOM node's innerHTML.
@@ -122,12 +126,42 @@ var ReactDOMIDOperations = {
122
126
  * @param {string} html An HTML string.
123
127
  * @internal
124
128
  */
125
- updateInnerHTMLByID: function(id, html) {
126
- var node = ReactMount.getNode(id);
127
- // HACK: IE8- normalize whitespace in innerHTML, removing leading spaces.
128
- // @see quirksmode.org/bugreports/archives/2004/11/innerhtml_and_t.html
129
- node.innerHTML = html.replace(LEADING_SPACE, ' ');
130
- },
129
+ updateInnerHTMLByID: ReactPerf.measure(
130
+ 'ReactDOMIDOperations',
131
+ 'updateInnerHTMLByID',
132
+ function(id, html) {
133
+ var node = ReactMount.getNode(id);
134
+
135
+ // IE8: When updating a just created node with innerHTML only leading
136
+ // whitespace is removed. When updating an existing node with innerHTML
137
+ // whitespace in root TextNodes is also collapsed.
138
+ // @see quirksmode.org/bugreports/archives/2004/11/innerhtml_and_t.html
139
+
140
+ if (useWhitespaceWorkaround === undefined) {
141
+ // Feature detection; only IE8 is known to behave improperly like this.
142
+ var temp = document.createElement('div');
143
+ temp.innerHTML = ' ';
144
+ useWhitespaceWorkaround = temp.innerHTML === '';
145
+ }
146
+
147
+ if (useWhitespaceWorkaround) {
148
+ // Magic theory: IE8 supposedly differentiates between added and updated
149
+ // nodes when processing innerHTML, innerHTML on updated nodes suffers
150
+ // from worse whitespace behavior. Re-adding a node like this triggers
151
+ // the initial and more favorable whitespace behavior.
152
+ node.parentNode.replaceChild(node, node);
153
+ }
154
+
155
+ if (useWhitespaceWorkaround && html.match(/^[ \r\n\t\f]/)) {
156
+ // Recover leading whitespace by temporarily prepending any character.
157
+ // \uFEFF has the potential advantage of being zero-width/invisible.
158
+ node.innerHTML = '\uFEFF' + html;
159
+ node.firstChild.deleteData(0, 1);
160
+ } else {
161
+ node.innerHTML = html;
162
+ }
163
+ }
164
+ ),
131
165
 
132
166
  /**
133
167
  * Updates a DOM node's text content set by `props.content`.
@@ -136,10 +170,14 @@ var ReactDOMIDOperations = {
136
170
  * @param {string} content Text content.
137
171
  * @internal
138
172
  */
139
- updateTextContentByID: function(id, content) {
140
- var node = ReactMount.getNode(id);
141
- node[textContentAccessor] = content;
142
- },
173
+ updateTextContentByID: ReactPerf.measure(
174
+ 'ReactDOMIDOperations',
175
+ 'updateTextContentByID',
176
+ function(id, content) {
177
+ var node = ReactMount.getNode(id);
178
+ DOMChildrenOperations.updateTextContent(node, content);
179
+ }
180
+ ),
143
181
 
144
182
  /**
145
183
  * Replaces a DOM node that exists in the document with markup.
@@ -149,10 +187,14 @@ var ReactDOMIDOperations = {
149
187
  * @internal
150
188
  * @see {Danger.dangerouslyReplaceNodeWithMarkup}
151
189
  */
152
- dangerouslyReplaceNodeWithMarkupByID: function(id, markup) {
153
- var node = ReactMount.getNode(id);
154
- DOMChildrenOperations.dangerouslyReplaceNodeWithMarkup(node, markup);
155
- },
190
+ dangerouslyReplaceNodeWithMarkupByID: ReactPerf.measure(
191
+ 'ReactDOMIDOperations',
192
+ 'dangerouslyReplaceNodeWithMarkupByID',
193
+ function(id, markup) {
194
+ var node = ReactMount.getNode(id);
195
+ DOMChildrenOperations.dangerouslyReplaceNodeWithMarkup(node, markup);
196
+ }
197
+ ),
156
198
 
157
199
  /**
158
200
  * Updates a component's children by processing a series of updates.
@@ -161,13 +203,16 @@ var ReactDOMIDOperations = {
161
203
  * @param {array<string>} markup List of markup strings.
162
204
  * @internal
163
205
  */
164
- dangerouslyProcessChildrenUpdates: function(updates, markup) {
165
- for (var i = 0; i < updates.length; i++) {
166
- updates[i].parentNode = ReactMount.getNode(updates[i].parentID);
206
+ dangerouslyProcessChildrenUpdates: ReactPerf.measure(
207
+ 'ReactDOMIDOperations',
208
+ 'dangerouslyProcessChildrenUpdates',
209
+ function(updates, markup) {
210
+ for (var i = 0; i < updates.length; i++) {
211
+ updates[i].parentNode = ReactMount.getNode(updates[i].parentID);
212
+ }
213
+ DOMChildrenOperations.processUpdates(updates, markup);
167
214
  }
168
- DOMChildrenOperations.processUpdates(updates, markup);
169
- }
170
-
215
+ )
171
216
  };
172
217
 
173
218
  module.exports = ReactDOMIDOperations;
@@ -0,0 +1,61 @@
1
+ /**
2
+ * Copyright 2013-2014 Facebook, Inc.
3
+ *
4
+ * Licensed under the Apache License, Version 2.0 (the "License");
5
+ * you may not use this file except in compliance with the License.
6
+ * You may obtain a copy of the License at
7
+ *
8
+ * http://www.apache.org/licenses/LICENSE-2.0
9
+ *
10
+ * Unless required by applicable law or agreed to in writing, software
11
+ * distributed under the License is distributed on an "AS IS" BASIS,
12
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ * See the License for the specific language governing permissions and
14
+ * limitations under the License.
15
+ *
16
+ * @providesModule ReactDOMImg
17
+ */
18
+
19
+ "use strict";
20
+
21
+ var ReactBrowserComponentMixin = require("./ReactBrowserComponentMixin");
22
+ var ReactCompositeComponent = require("./ReactCompositeComponent");
23
+ var ReactDOM = require("./ReactDOM");
24
+ var ReactEventEmitter = require("./ReactEventEmitter");
25
+ var EventConstants = require("./EventConstants");
26
+
27
+ // Store a reference to the <img> `ReactDOMComponent`.
28
+ var img = ReactDOM.img;
29
+
30
+ /**
31
+ * Since onLoad doesn't bubble OR capture on the top level in IE8, we need to
32
+ * capture it on the <img> element itself. There are lots of hacks we could do
33
+ * to accomplish this, but the most reliable is to make <img> a composite
34
+ * component and use `componentDidMount` to attach the event handlers.
35
+ */
36
+ var ReactDOMImg = ReactCompositeComponent.createClass({
37
+ displayName: 'ReactDOMImg',
38
+ tagName: 'IMG',
39
+
40
+ mixins: [ReactBrowserComponentMixin],
41
+
42
+ render: function() {
43
+ return img(this.props);
44
+ },
45
+
46
+ componentDidMount: function() {
47
+ var node = this.getDOMNode();
48
+ ReactEventEmitter.trapBubbledEvent(
49
+ EventConstants.topLevelTypes.topLoad,
50
+ 'load',
51
+ node
52
+ );
53
+ ReactEventEmitter.trapBubbledEvent(
54
+ EventConstants.topLevelTypes.topError,
55
+ 'error',
56
+ node
57
+ );
58
+ }
59
+ });
60
+
61
+ module.exports = ReactDOMImg;
@@ -1,5 +1,5 @@
1
1
  /**
2
- * Copyright 2013 Facebook, Inc.
2
+ * Copyright 2013-2014 Facebook, Inc.
3
3
  *
4
4
  * Licensed under the Apache License, Version 2.0 (the "License");
5
5
  * you may not use this file except in compliance with the License.
@@ -18,8 +18,10 @@
18
18
 
19
19
  "use strict";
20
20
 
21
+ var AutoFocusMixin = require("./AutoFocusMixin");
21
22
  var DOMPropertyOperations = require("./DOMPropertyOperations");
22
- var LinkedValueMixin = require("./LinkedValueMixin");
23
+ var LinkedValueUtils = require("./LinkedValueUtils");
24
+ var ReactBrowserComponentMixin = require("./ReactBrowserComponentMixin");
23
25
  var ReactCompositeComponent = require("./ReactCompositeComponent");
24
26
  var ReactDOM = require("./ReactDOM");
25
27
  var ReactMount = require("./ReactMount");
@@ -49,7 +51,9 @@ var instancesByReactID = {};
49
51
  * @see http://www.w3.org/TR/2012/WD-html5-20121025/the-input-element.html
50
52
  */
51
53
  var ReactDOMInput = ReactCompositeComponent.createClass({
52
- mixins: [LinkedValueMixin],
54
+ displayName: 'ReactDOMInput',
55
+
56
+ mixins: [AutoFocusMixin, LinkedValueUtils.Mixin, ReactBrowserComponentMixin],
53
57
 
54
58
  getInitialState: function() {
55
59
  var defaultValue = this.props.defaultValue;
@@ -70,19 +74,20 @@ var ReactDOMInput = ReactCompositeComponent.createClass({
70
74
 
71
75
  props.defaultChecked = null;
72
76
  props.defaultValue = null;
73
- props.checked =
74
- this.props.checked != null ? this.props.checked : this.state.checked;
75
77
 
76
- var value = this.getValue();
78
+ var value = LinkedValueUtils.getValue(this);
77
79
  props.value = value != null ? value : this.state.value;
78
80
 
81
+ var checked = LinkedValueUtils.getChecked(this);
82
+ props.checked = checked != null ? checked : this.state.checked;
83
+
79
84
  props.onChange = this._handleChange;
80
85
 
81
86
  return input(props, this.props.children);
82
87
  },
83
88
 
84
- componentDidMount: function(rootNode) {
85
- var id = ReactMount.getID(rootNode);
89
+ componentDidMount: function() {
90
+ var id = ReactMount.getID(this.getDOMNode());
86
91
  instancesByReactID[id] = this;
87
92
  },
88
93
 
@@ -92,7 +97,8 @@ var ReactDOMInput = ReactCompositeComponent.createClass({
92
97
  delete instancesByReactID[id];
93
98
  },
94
99
 
95
- componentDidUpdate: function(prevProps, prevState, rootNode) {
100
+ componentDidUpdate: function(prevProps, prevState, prevContext) {
101
+ var rootNode = this.getDOMNode();
96
102
  if (this.props.checked != null) {
97
103
  DOMPropertyOperations.setValueForProperty(
98
104
  rootNode,
@@ -101,7 +107,7 @@ var ReactDOMInput = ReactCompositeComponent.createClass({
101
107
  );
102
108
  }
103
109
 
104
- var value = this.getValue();
110
+ var value = LinkedValueUtils.getValue(this);
105
111
  if (value != null) {
106
112
  // Cast `value` to a string to ensure the value is set correctly. While
107
113
  // browsers typically do this as necessary, jsdom doesn't.
@@ -111,10 +117,10 @@ var ReactDOMInput = ReactCompositeComponent.createClass({
111
117
 
112
118
  _handleChange: function(event) {
113
119
  var returnValue;
114
- var onChange = this.getOnChange();
120
+ var onChange = LinkedValueUtils.getOnChange(this);
115
121
  if (onChange) {
116
122
  this._isChanging = true;
117
- returnValue = onChange(event);
123
+ returnValue = onChange.call(this, event);
118
124
  this._isChanging = false;
119
125
  }
120
126
  this.setState({
@@ -125,17 +131,24 @@ var ReactDOMInput = ReactCompositeComponent.createClass({
125
131
  var name = this.props.name;
126
132
  if (this.props.type === 'radio' && name != null) {
127
133
  var rootNode = this.getDOMNode();
134
+ var queryRoot = rootNode;
135
+
136
+ while (queryRoot.parentNode) {
137
+ queryRoot = queryRoot.parentNode;
138
+ }
139
+
128
140
  // If `rootNode.form` was non-null, then we could try `form.elements`,
129
141
  // but that sometimes behaves strangely in IE8. We could also try using
130
142
  // `form.getElementsByName`, but that will only return direct children
131
143
  // and won't include inputs that use the HTML5 `form=` attribute. Since
132
144
  // the input might not even be in a form, let's just use the global
133
- // `getElementsByName` to ensure we don't miss anything.
134
- var group = document.getElementsByName(name);
145
+ // `querySelectorAll` to ensure we don't miss anything.
146
+ var group = queryRoot.querySelectorAll(
147
+ 'input[name=' + JSON.stringify('' + name) + '][type="radio"]');
148
+
135
149
  for (var i = 0, groupLen = group.length; i < groupLen; i++) {
136
150
  var otherNode = group[i];
137
151
  if (otherNode === rootNode ||
138
- otherNode.nodeName !== 'INPUT' || otherNode.type !== 'radio' ||
139
152
  otherNode.form !== rootNode.form) {
140
153
  continue;
141
154
  }
@@ -1,5 +1,5 @@
1
1
  /**
2
- * Copyright 2013 Facebook, Inc.
2
+ * Copyright 2013-2014 Facebook, Inc.
3
3
  *
4
4
  * Licensed under the Apache License, Version 2.0 (the "License");
5
5
  * you may not use this file except in compliance with the License.
@@ -18,9 +18,12 @@
18
18
 
19
19
  "use strict";
20
20
 
21
+ var ReactBrowserComponentMixin = require("./ReactBrowserComponentMixin");
21
22
  var ReactCompositeComponent = require("./ReactCompositeComponent");
22
23
  var ReactDOM = require("./ReactDOM");
23
24
 
25
+ var warning = require("./warning");
26
+
24
27
  // Store a reference to the <option> `ReactDOMComponent`.
25
28
  var option = ReactDOM.option;
26
29
 
@@ -28,16 +31,18 @@ var option = ReactDOM.option;
28
31
  * Implements an <option> native component that warns when `selected` is set.
29
32
  */
30
33
  var ReactDOMOption = ReactCompositeComponent.createClass({
34
+ displayName: 'ReactDOMOption',
35
+
36
+ mixins: [ReactBrowserComponentMixin],
31
37
 
32
38
  componentWillMount: function() {
33
39
  // TODO (yungsters): Remove support for `selected` in <option>.
34
- if (this.props.selected != null) {
35
- if ("production" !== process.env.NODE_ENV) {
36
- console.warn(
37
- 'Use the `defaultValue` or `value` props on <select> instead of ' +
38
- 'setting `selected` on <option>.'
39
- );
40
- }
40
+ if ("production" !== process.env.NODE_ENV) {
41
+ ("production" !== process.env.NODE_ENV ? warning(
42
+ this.props.selected == null,
43
+ 'Use the `defaultValue` or `value` props on <select> instead of ' +
44
+ 'setting `selected` on <option>.'
45
+ ) : null);
41
46
  }
42
47
  },
43
48