RN: Switch `Text` to `React.forwardRef`

Reviewed By: sahrens

Differential Revision: D7902262

fbshipit-source-id: 218f95cde6d77f21d9362a2f2bd47c5f83d5ee15
This commit is contained in:
Tim Yung 2018-05-09 00:47:57 -07:00 committed by Facebook Github Bot
parent 06c05e744d
commit e708010d18
4 changed files with 23 additions and 12 deletions

View File

@ -22,9 +22,6 @@ exports[`TouchableHighlight renders correctly 1`] = `
tvParallaxProperties={undefined} tvParallaxProperties={undefined}
> >
<Text <Text
accessible={true}
allowFontScaling={true}
ellipsizeMode="tail"
style={null} style={null}
> >
Touchable Touchable

View File

@ -11,7 +11,6 @@
'use strict'; 'use strict';
const React = require('React'); const React = require('React');
const ReactNative = require('ReactNative');
const ReactNativeViewAttributes = require('ReactNativeViewAttributes'); const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
const TextAncestor = require('TextAncestor'); const TextAncestor = require('TextAncestor');
const TextPropTypes = require('TextPropTypes'); const TextPropTypes = require('TextPropTypes');
@ -23,6 +22,7 @@ const nullthrows = require('fbjs/lib/nullthrows');
const processColor = require('processColor'); const processColor = require('processColor');
import type {PressEvent} from 'CoreEventTypes'; import type {PressEvent} from 'CoreEventTypes';
import type {NativeComponent} from 'ReactNative';
import type {PressRetentionOffset, TextProps} from 'TextProps'; import type {PressRetentionOffset, TextProps} from 'TextProps';
type ResponseHandlers = $ReadOnly<{| type ResponseHandlers = $ReadOnly<{|
@ -34,7 +34,10 @@ type ResponseHandlers = $ReadOnly<{|
onResponderTerminationRequest: () => boolean, onResponderTerminationRequest: () => boolean,
|}>; |}>;
type Props = TextProps; type Props = $ReadOnly<{
...TextProps,
forwardedRef: ?React.Ref<NativeComponent<TextProps, any>>,
}>;
type State = {| type State = {|
touchable: {| touchable: {|
@ -70,9 +73,7 @@ const viewConfig = {
* *
* See https://facebook.github.io/react-native/docs/text.html * See https://facebook.github.io/react-native/docs/text.html
*/ */
class Text extends ReactNative.NativeComponent<Props, State> { class TouchableText extends React.Component<Props, State> {
static propTypes = TextPropTypes;
static defaultProps = { static defaultProps = {
accessible: true, accessible: true,
allowFontScaling: true, allowFontScaling: true,
@ -138,10 +139,10 @@ class Text extends ReactNative.NativeComponent<Props, State> {
<TextAncestor.Consumer> <TextAncestor.Consumer>
{hasTextAncestor => {hasTextAncestor =>
hasTextAncestor ? ( hasTextAncestor ? (
<RCTVirtualText {...props} /> <RCTVirtualText {...props} ref={props.forwardedRef} />
) : ( ) : (
<TextAncestor.Provider value={true}> <TextAncestor.Provider value={true}>
<RCTText {...props} /> <RCTText {...props} ref={props.forwardedRef} />
</TextAncestor.Provider> </TextAncestor.Provider>
) )
} }
@ -260,4 +261,13 @@ const RCTVirtualText =
uiViewClassName: 'RCTVirtualText', uiViewClassName: 'RCTVirtualText',
})); }));
module.exports = Text; // $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
const Text = React.forwardRef((props, ref) => (
<TouchableText {...props} forwardedRef={ref} />
));
Text.displayName = 'Text';
// TODO: Deprecate this.
Text.propTypes = TextPropTypes;
module.exports = ((Text: any): NativeComponent<TextProps, any>);

View File

@ -28,6 +28,10 @@ module.exports = (moduleName, instanceMethods) => {
} }
}; };
if (RealComponent.propTypes != null) {
Component.propTypes = RealComponent.propTypes;
}
if (instanceMethods != null) { if (instanceMethods != null) {
Object.assign(Component.prototype, instanceMethods); Object.assign(Component.prototype, instanceMethods);
} }

View File

@ -35,7 +35,7 @@ jest.setMock('ErrorUtils', require('ErrorUtils'));
jest jest
.mock('InitializeCore', () => {}) .mock('InitializeCore', () => {})
.mock('Image', () => mockComponent('Image')) .mock('Image', () => mockComponent('Image'))
.mock('Text', () => mockComponent('Text')) .mock('Text', () => mockComponent('Text', MockNativeMethods))
.mock('TextInput', () => mockComponent('TextInput')) .mock('TextInput', () => mockComponent('TextInput'))
.mock('Modal', () => mockComponent('Modal')) .mock('Modal', () => mockComponent('Modal'))
.mock('View', () => mockComponent('View', MockNativeMethods)) .mock('View', () => mockComponent('View', MockNativeMethods))