React-native: IOS TouchableHighlight need tap twice to trigger onPress function

Created on 8 Mar 2017  ·  35Comments  ·  Source: facebook/react-native

In my Project, I have a TextInput and a TouchableHighlight , the code is below:

export default class CommentInput extends Component {
    static propTypes = {
        visible: React.PropTypes.bool,
        onFocus: React.PropTypes.func,
        placeholder: React.PropTypes.string,
        text: React.PropTypes.string,
        onSubmit: React.PropTypes.func,
        onHideTextInput: React.PropTypes.func
    };
    constructor(props) {
        super(props);
        this._textInput = null;
        this.state = {
            visible: this.props.visible || false,
            placeholder: this.props.placeholder || '',
            text: this.props.value || '',
            keyboardHeight: 0
        }
    }
    componentWillUnmout() {
        console.log(this._textInput);
        this._textInput && this._textInput.blur();
    }
    renderInput = () => {
        return <View style={styles.container}>
                <TextInput
                    textAlignVertical="top"
                    underlineColorAndroid="transparent"
                    value={this.state.text}
                    onFocus={this.props.onFocus}
                    autoCapitalize="none"
                    allowFontScaling={false}
                    onChangeText={this._onChangeText}
                    ref={textInput => {this._textInput = textInput}}
                    placeholder={this.state.placeholder}
                    multiline={true}
                    autoFocus={true}
                    onBlur={this._textPress}
                    onPress={this._textPress}
                    style={styles.textInput} />
                <View style={styles.btnWrap}>
                    <Button
                        underlayColor={'#f00'}
                        onPress={this.state.text ? this._checkLogin : null}
                        textStyle={styles.btnText}
                        style={[styles.btn, this.state.text.trim() ? null : styles.opacity]}>发表</Button>
                </View>
                {
                    Platform.OS === 'ios' ?  <KeyboardSpacer/> : null
                }
            </View>
    };
    _onChangeText = (text) => {
        this.setState({
            text: text
        });
        this.props.onChangeText && this.props.onChangeText(text);
    };
    _checkLogin = async () => {
        let isLogin = await invoke('Account.isLogin');
        if (isLogin.result) {
            this._onSubmit();
        }
        else {
            let data = await invoke('Account.login', {source: 'Comment'});
            if (data.result) {
                this._onSubmit();
            }
        }
    };
    _onSubmit = () => {
        this.props.onSubmit(this.state.text);
    };
    _textPress = () => {
        alert('123');
    };
    render() {
        return this.props.visible ? this.renderInput() : null
    }
}

and in another file:
{ this.state.showMask ? <TouchableWithoutFeedback ll="ll" onPress={this._hideTextInput}> <View style={styles.markView}></View> </TouchableWithoutFeedback> : null } <CommentInput onSubmit={this._listenSubmit} visible={this.state.showMask} />

when I use the keyboard to input some words and press the TouchableWithoutFeedback at the same times, several times , the TouchableWithoutFeedback need to tap twice to trigger the onPress function. how to solve this bug?

iOS Locked

Most helpful comment

Are you using a ScrollView? By default when an input is focused the tap will close the keyboard but not trigger any other touch events. You can change that behavior using http://facebook.github.io/react-native/docs/scrollview.html#keyboardshouldpersisttaps

All 35 comments

Are you using a ScrollView? By default when an input is focused the tap will close the keyboard but not trigger any other touch events. You can change that behavior using http://facebook.github.io/react-native/docs/scrollview.html#keyboardshouldpersisttaps

Dear @janicduplessis , the CommentInput component did not included in a ScrollView, at first , the Button(TouchableHightlight) can receive the onPress method, but after several quick open the CommentInput component use keyboard to input some text and at the same time press the background to close the CommentInput., next Time the Button component won't accept the onPress method at the first tap, and the second time the Button works. I don't know why. I also search a lot of issues to find the solution. but I did get the answer

I also have this problem sometimes on 0.43

@RichardLindhout did you find the solution?

Probably same problem as #12976 is.

@avivaWang How hard is it to reproduce this problem?

I think it has something to do with a busy JavaScript thread.

Yeah, probably. I hope fixing #12976 also will fix this problem.

I have this problem on 0.41.0 with a ScrollView which contains TouchableHighlights.

In my case keyboardShouldPersistTaps fixes issues.

@vinayan3, Since there are a million threads already about keyboardShouldPersistTaps on ScrollView, and this one is specifically not about ScrollView, it would be best to keep this out of the discussion unless the suggestion is to add keyboardShouldPersistTaps to View or other Components.

... Speaking about scrollviews, <TextInput multiline={true}/> actually contains <ScrollView> subclass inside.

@avivaWang While I didn't find a solution, there is a workaround for the case when your keyboard has been dismissed but the focus of the TextInput is still preventing your buttons from being clicked. If you use a keyboard listener from the Keyboard API, you can blur the input when the keyboard is dismissed:

    componentDidMount(){
        this.keyboardDidHideListener = Keyboard.addListener("keyboardDidHide", () => {
          this.refs.input.blur();
        });
      }

    componentWillUnmount(){
        this.keyboardDidHideListener.remove();
    }

Hi there! This issue is being closed because it has been inactive for a while. Maybe the issue has been fixed in a recent release, or perhaps it is not affecting a lot of people. Either way, we're automatically closing issues after a period of inactivity. Please do not take it personally!

If you think this issue should definitely remain open, please let us know. The following information is helpful when it comes to determining if the issue should be re-opened:

  • Does the issue still reproduce on the latest release candidate? Post a comment with the version you tested.
  • If so, is there any information missing from the bug report? Post a comment with all the information required by the issue template.
  • Is there a pull request that addresses this issue? Post a comment with the PR number so we can follow up.

If you would like to work on a patch to fix the issue, contributions are very welcome! Read through the contribution guide, and feel free to hop into #react-native if you need help planning your contribution.

I think it is related to this issues #15606

I use a FlatList instead a ScrollView.
In my case, keyboardShouldPersistTaps fixes issues.

The original issue of needing two taps to activate onPress is still exits. I don't know why it's been closed. The original code still reproduces the issue in latest releases.

I develop android app
both flatlist and scrollview fix by using keyboardShouldPersistTaps

FlatList does not have property keyboardShouldPersistTaps. My React-native version is 0.51.0.

@vuphuctho they do, flatlist inherate scrollview props dude..

_keyboardShouldPersistTaps_ doesn't work on iOS(react-native 0.51.0).

@hnanh is right, keyboardShouldPersistTaps doesn't work on RN 0.51+

+1 on this issue. Still need to double tap before the item receives the tap.

Did anyone solve this problem? I am using RN 0.52.2

Solved it by making sure that all parent ScrollView Props keyboardShouldPersistTaps is set to "handled".

what fixed it for me is to make sure that all nested scrollviews have this property set: keyboardShouldPersistTaps='always'.

This won't work because the parent ScrollView does not have this property set.

I see, have you tried using a different Touchable component? Like TouchableOpacity

yes @dsc-bon. I was working with TouchableOpacity and it worked just giving all ScrollViews the same keyboardShouldPersistTaps='always' prop. Thanks

I was facing the same issue with FlatList (RN -> 0.52.0). But resolved when used
keyboardShouldPersistTaps='always' prop.

Is there any solution not involving the addition of a scrollview (or any other component)?

Facing the same issue here. A simple Input and a TouchableOpacity. Adding a ScrollView around with the keyboardShouldPersistTaps='always' does not help.
Anyone with a solution?

@msevestre make sure that ALL child container were placed inside the ScrollView

What do you mean with child container? ;+)

I have a modal view with one input and two buttons.
I tried to add a scroll view wrapping the input and the buttons but this does not change this behavior.

Cheers

@msevestre
I had the same trouble. In my case, I solved it by adding keyboardShouldPersistTaps="handled" to parent ScrollView of my Modal.
As I figured out parent ScrollView also affects children Modal.
I mean
<ScrollView keyboardShouldPersistTaps="handled"> ... <Modal>...</Modal> ... </ScrollView>

This issue goes away when switching to TouchableOpacity

Was this page helpful?
0 / 5 - 0 ratings