onPress not firing on Android but fine on iOS












2














I've written a React Native app, iOS was the priority so I built that first. It's in the App Store and works perfectly, however I've just started working on Android and although everything appears to be working correctly except for touch events, which are not firing at all.



None of the touchable elements are calling the onPress callback, nor is the Button element. I've even tried stripping the app down completely, removing the navigator, and adding a load of touchable elements to the initial screen but still none of the onPress callbacks are firing.



Below is the code for the initial screen of my app, though I doubt any of this code is causing the issue:



// @flow
import React, { type Element } from 'react';
import { View, Text, Image, TouchableOpacity } from 'react-native';
import type { NavigatorScreenProps } from 'react-navigation';
import i18n from '../../i18n';
import style from './style';

type Props = {
navigation: NavigatorScreenProps
}

export default function SignIn ({ navigation }: Props): Element<typeof View> {
return (
<View style={style.container}>
<View style={style.top}>
<Image source={require('../../assets/images/purpleWithTransparentBackground.png')} style={style.logo} />
</View>
<View style={style.bottom}>
<TouchableOpacity activeOpacity={0.97} onPressIn={() => console.log('in')} onPressOut={() => console.log('out')} onPress={() => { console.log('do something!'); navigation.navigate('EnterEmail'); }} style={[style.submit, { zIndex: 99999, elevation: 99999 }]}>
<Text style={style.submitText}>
{i18n.t('SIGN_IN')}
</Text>
</TouchableOpacity>
</View>
<Image source={require('../../assets/images/cityscapeGrey.png')} style={style.cityscape} />
</View>
);
}


Component styles:



import { StyleSheet, Dimensions } from 'react-native';
import defaultStyles from '../../style';

const { width: screenWidth } = Dimensions.get('window');

export default StyleSheet.create({
container: {
flex: 1,
justifyContent: 'center',
alignItems: 'center',
backgroundColor: defaultStyles.white
},

top: {
flex: 1,
justifyContent: 'flex-end',
alignItems: 'center',
width: '100%'
},

bottom: {
flex: 1,
width: '100%'
},

animatedContainer: {
flex: 1,
alignItems: 'center',
justifyContent: 'center',
width: '100%'
},

postcode: {
padding: 12,
height: 50,
backgroundColor: 'white',
width: '100%',
borderRadius: 5,
fontSize: 17
},

text: {
width: 296,
height: 44,
fontFamily: 'SFProText-Light',
fontSize: 16,
fontWeight: '500',
fontStyle: 'normal',
lineHeight: 22,
letterSpacing: 0,
textAlign: 'center',
color: defaultStyles.balticSea
},

logo: {
marginBottom: 14
},

error: {
color: defaultStyles.brickRed,
marginVertical: 12,
width: '100%',
textAlign: 'center'
},

submit: {
width: 311,
height: 56,
borderRadius: 4,
backgroundColor: defaultStyles.mountainMeadow,
justifyContent: 'center',
alignItems: 'center',
alignSelf: 'center',
marginTop: 30
},

submitText: {
width: 311,
height: 21,
fontFamily: 'SFProDisplay-Heavy',
fontSize: 18,
fontWeight: 'bold',
fontStyle: 'normal',
letterSpacing: 0,
textAlign: 'center',
color: defaultStyles.white
},

highlight: {
color: defaultStyles.mountainMeadow
},

cityscape: {
position: 'absolute',
left: 0,
bottom: 0,
width: screenWidth,
resizeMode: 'repeat'
}
});


Thanks in advance for any help.










share|improve this question
























  • just an idea, did you try to remove the activeOpacity={0.97} ?
    – oma
    Nov 20 '18 at 20:46










  • @oma I've tried using different touchable elements with no custom opacity, still no luck unfortunately!
    – JmJ
    Nov 20 '18 at 22:10
















2














I've written a React Native app, iOS was the priority so I built that first. It's in the App Store and works perfectly, however I've just started working on Android and although everything appears to be working correctly except for touch events, which are not firing at all.



None of the touchable elements are calling the onPress callback, nor is the Button element. I've even tried stripping the app down completely, removing the navigator, and adding a load of touchable elements to the initial screen but still none of the onPress callbacks are firing.



Below is the code for the initial screen of my app, though I doubt any of this code is causing the issue:



// @flow
import React, { type Element } from 'react';
import { View, Text, Image, TouchableOpacity } from 'react-native';
import type { NavigatorScreenProps } from 'react-navigation';
import i18n from '../../i18n';
import style from './style';

type Props = {
navigation: NavigatorScreenProps
}

export default function SignIn ({ navigation }: Props): Element<typeof View> {
return (
<View style={style.container}>
<View style={style.top}>
<Image source={require('../../assets/images/purpleWithTransparentBackground.png')} style={style.logo} />
</View>
<View style={style.bottom}>
<TouchableOpacity activeOpacity={0.97} onPressIn={() => console.log('in')} onPressOut={() => console.log('out')} onPress={() => { console.log('do something!'); navigation.navigate('EnterEmail'); }} style={[style.submit, { zIndex: 99999, elevation: 99999 }]}>
<Text style={style.submitText}>
{i18n.t('SIGN_IN')}
</Text>
</TouchableOpacity>
</View>
<Image source={require('../../assets/images/cityscapeGrey.png')} style={style.cityscape} />
</View>
);
}


Component styles:



import { StyleSheet, Dimensions } from 'react-native';
import defaultStyles from '../../style';

const { width: screenWidth } = Dimensions.get('window');

export default StyleSheet.create({
container: {
flex: 1,
justifyContent: 'center',
alignItems: 'center',
backgroundColor: defaultStyles.white
},

top: {
flex: 1,
justifyContent: 'flex-end',
alignItems: 'center',
width: '100%'
},

bottom: {
flex: 1,
width: '100%'
},

animatedContainer: {
flex: 1,
alignItems: 'center',
justifyContent: 'center',
width: '100%'
},

postcode: {
padding: 12,
height: 50,
backgroundColor: 'white',
width: '100%',
borderRadius: 5,
fontSize: 17
},

text: {
width: 296,
height: 44,
fontFamily: 'SFProText-Light',
fontSize: 16,
fontWeight: '500',
fontStyle: 'normal',
lineHeight: 22,
letterSpacing: 0,
textAlign: 'center',
color: defaultStyles.balticSea
},

logo: {
marginBottom: 14
},

error: {
color: defaultStyles.brickRed,
marginVertical: 12,
width: '100%',
textAlign: 'center'
},

submit: {
width: 311,
height: 56,
borderRadius: 4,
backgroundColor: defaultStyles.mountainMeadow,
justifyContent: 'center',
alignItems: 'center',
alignSelf: 'center',
marginTop: 30
},

submitText: {
width: 311,
height: 21,
fontFamily: 'SFProDisplay-Heavy',
fontSize: 18,
fontWeight: 'bold',
fontStyle: 'normal',
letterSpacing: 0,
textAlign: 'center',
color: defaultStyles.white
},

highlight: {
color: defaultStyles.mountainMeadow
},

cityscape: {
position: 'absolute',
left: 0,
bottom: 0,
width: screenWidth,
resizeMode: 'repeat'
}
});


Thanks in advance for any help.










share|improve this question
























  • just an idea, did you try to remove the activeOpacity={0.97} ?
    – oma
    Nov 20 '18 at 20:46










  • @oma I've tried using different touchable elements with no custom opacity, still no luck unfortunately!
    – JmJ
    Nov 20 '18 at 22:10














2












2








2







I've written a React Native app, iOS was the priority so I built that first. It's in the App Store and works perfectly, however I've just started working on Android and although everything appears to be working correctly except for touch events, which are not firing at all.



None of the touchable elements are calling the onPress callback, nor is the Button element. I've even tried stripping the app down completely, removing the navigator, and adding a load of touchable elements to the initial screen but still none of the onPress callbacks are firing.



Below is the code for the initial screen of my app, though I doubt any of this code is causing the issue:



// @flow
import React, { type Element } from 'react';
import { View, Text, Image, TouchableOpacity } from 'react-native';
import type { NavigatorScreenProps } from 'react-navigation';
import i18n from '../../i18n';
import style from './style';

type Props = {
navigation: NavigatorScreenProps
}

export default function SignIn ({ navigation }: Props): Element<typeof View> {
return (
<View style={style.container}>
<View style={style.top}>
<Image source={require('../../assets/images/purpleWithTransparentBackground.png')} style={style.logo} />
</View>
<View style={style.bottom}>
<TouchableOpacity activeOpacity={0.97} onPressIn={() => console.log('in')} onPressOut={() => console.log('out')} onPress={() => { console.log('do something!'); navigation.navigate('EnterEmail'); }} style={[style.submit, { zIndex: 99999, elevation: 99999 }]}>
<Text style={style.submitText}>
{i18n.t('SIGN_IN')}
</Text>
</TouchableOpacity>
</View>
<Image source={require('../../assets/images/cityscapeGrey.png')} style={style.cityscape} />
</View>
);
}


Component styles:



import { StyleSheet, Dimensions } from 'react-native';
import defaultStyles from '../../style';

const { width: screenWidth } = Dimensions.get('window');

export default StyleSheet.create({
container: {
flex: 1,
justifyContent: 'center',
alignItems: 'center',
backgroundColor: defaultStyles.white
},

top: {
flex: 1,
justifyContent: 'flex-end',
alignItems: 'center',
width: '100%'
},

bottom: {
flex: 1,
width: '100%'
},

animatedContainer: {
flex: 1,
alignItems: 'center',
justifyContent: 'center',
width: '100%'
},

postcode: {
padding: 12,
height: 50,
backgroundColor: 'white',
width: '100%',
borderRadius: 5,
fontSize: 17
},

text: {
width: 296,
height: 44,
fontFamily: 'SFProText-Light',
fontSize: 16,
fontWeight: '500',
fontStyle: 'normal',
lineHeight: 22,
letterSpacing: 0,
textAlign: 'center',
color: defaultStyles.balticSea
},

logo: {
marginBottom: 14
},

error: {
color: defaultStyles.brickRed,
marginVertical: 12,
width: '100%',
textAlign: 'center'
},

submit: {
width: 311,
height: 56,
borderRadius: 4,
backgroundColor: defaultStyles.mountainMeadow,
justifyContent: 'center',
alignItems: 'center',
alignSelf: 'center',
marginTop: 30
},

submitText: {
width: 311,
height: 21,
fontFamily: 'SFProDisplay-Heavy',
fontSize: 18,
fontWeight: 'bold',
fontStyle: 'normal',
letterSpacing: 0,
textAlign: 'center',
color: defaultStyles.white
},

highlight: {
color: defaultStyles.mountainMeadow
},

cityscape: {
position: 'absolute',
left: 0,
bottom: 0,
width: screenWidth,
resizeMode: 'repeat'
}
});


Thanks in advance for any help.










share|improve this question















I've written a React Native app, iOS was the priority so I built that first. It's in the App Store and works perfectly, however I've just started working on Android and although everything appears to be working correctly except for touch events, which are not firing at all.



None of the touchable elements are calling the onPress callback, nor is the Button element. I've even tried stripping the app down completely, removing the navigator, and adding a load of touchable elements to the initial screen but still none of the onPress callbacks are firing.



Below is the code for the initial screen of my app, though I doubt any of this code is causing the issue:



// @flow
import React, { type Element } from 'react';
import { View, Text, Image, TouchableOpacity } from 'react-native';
import type { NavigatorScreenProps } from 'react-navigation';
import i18n from '../../i18n';
import style from './style';

type Props = {
navigation: NavigatorScreenProps
}

export default function SignIn ({ navigation }: Props): Element<typeof View> {
return (
<View style={style.container}>
<View style={style.top}>
<Image source={require('../../assets/images/purpleWithTransparentBackground.png')} style={style.logo} />
</View>
<View style={style.bottom}>
<TouchableOpacity activeOpacity={0.97} onPressIn={() => console.log('in')} onPressOut={() => console.log('out')} onPress={() => { console.log('do something!'); navigation.navigate('EnterEmail'); }} style={[style.submit, { zIndex: 99999, elevation: 99999 }]}>
<Text style={style.submitText}>
{i18n.t('SIGN_IN')}
</Text>
</TouchableOpacity>
</View>
<Image source={require('../../assets/images/cityscapeGrey.png')} style={style.cityscape} />
</View>
);
}


Component styles:



import { StyleSheet, Dimensions } from 'react-native';
import defaultStyles from '../../style';

const { width: screenWidth } = Dimensions.get('window');

export default StyleSheet.create({
container: {
flex: 1,
justifyContent: 'center',
alignItems: 'center',
backgroundColor: defaultStyles.white
},

top: {
flex: 1,
justifyContent: 'flex-end',
alignItems: 'center',
width: '100%'
},

bottom: {
flex: 1,
width: '100%'
},

animatedContainer: {
flex: 1,
alignItems: 'center',
justifyContent: 'center',
width: '100%'
},

postcode: {
padding: 12,
height: 50,
backgroundColor: 'white',
width: '100%',
borderRadius: 5,
fontSize: 17
},

text: {
width: 296,
height: 44,
fontFamily: 'SFProText-Light',
fontSize: 16,
fontWeight: '500',
fontStyle: 'normal',
lineHeight: 22,
letterSpacing: 0,
textAlign: 'center',
color: defaultStyles.balticSea
},

logo: {
marginBottom: 14
},

error: {
color: defaultStyles.brickRed,
marginVertical: 12,
width: '100%',
textAlign: 'center'
},

submit: {
width: 311,
height: 56,
borderRadius: 4,
backgroundColor: defaultStyles.mountainMeadow,
justifyContent: 'center',
alignItems: 'center',
alignSelf: 'center',
marginTop: 30
},

submitText: {
width: 311,
height: 21,
fontFamily: 'SFProDisplay-Heavy',
fontSize: 18,
fontWeight: 'bold',
fontStyle: 'normal',
letterSpacing: 0,
textAlign: 'center',
color: defaultStyles.white
},

highlight: {
color: defaultStyles.mountainMeadow
},

cityscape: {
position: 'absolute',
left: 0,
bottom: 0,
width: screenWidth,
resizeMode: 'repeat'
}
});


Thanks in advance for any help.







javascript android react-native






share|improve this question















share|improve this question













share|improve this question




share|improve this question








edited Nov 21 '18 at 4:19

























asked Nov 20 '18 at 20:35









JmJ

4931633




4931633












  • just an idea, did you try to remove the activeOpacity={0.97} ?
    – oma
    Nov 20 '18 at 20:46










  • @oma I've tried using different touchable elements with no custom opacity, still no luck unfortunately!
    – JmJ
    Nov 20 '18 at 22:10


















  • just an idea, did you try to remove the activeOpacity={0.97} ?
    – oma
    Nov 20 '18 at 20:46










  • @oma I've tried using different touchable elements with no custom opacity, still no luck unfortunately!
    – JmJ
    Nov 20 '18 at 22:10
















just an idea, did you try to remove the activeOpacity={0.97} ?
– oma
Nov 20 '18 at 20:46




just an idea, did you try to remove the activeOpacity={0.97} ?
– oma
Nov 20 '18 at 20:46












@oma I've tried using different touchable elements with no custom opacity, still no luck unfortunately!
– JmJ
Nov 20 '18 at 22:10




@oma I've tried using different touchable elements with no custom opacity, still no luck unfortunately!
– JmJ
Nov 20 '18 at 22:10












2 Answers
2






active

oldest

votes


















0














You need to give height and width to TouchableOpacity



            <TouchableOpacity
activeOpacity={0.97}
onPressIn={() => console.log('in')}
onPressOut={() => console.log('out')}
onPress={() => { console.log('do something!'); navigation.navigate('EnterEmail'); }}
style={[style.submit, { zIndex: 99999, elevation: 99999, height:200, width:200 }]}>
<Text style={style.submitText}>
{i18n.t('SIGN_IN')}
</Text>
</TouchableOpacity>


I just added 200 for both for testing.



Working code from Android:



<View style={{
flex: 1,
backgroundColor: 'red'
}}>
<View style={style.container}>
<View style={style.top}>
</View>
<View style={style.bottom}>
<TouchableOpacity activeOpacity={0.97} onPressIn={() => alert('in')} onPressOut={() => alert('out')} onPress={() => { alert('do something!'); }} style={[style.submit, { zIndex: 99999, elevation: 99999 }]}>
<Text style={style.submitText}>
GENERAL TEXT
</Text>
</TouchableOpacity>
</View>
</View>
</View>






share|improve this answer























  • style.submit has height and width
    – JmJ
    Nov 21 '18 at 4:04










  • Can you send style of submit?
    – Nirmalsinh
    Nov 21 '18 at 4:04










  • send me all the style which you provide in code.
    – Nirmalsinh
    Nov 21 '18 at 4:05










  • I've edited my answer to include the styles
    – JmJ
    Nov 21 '18 at 4:19



















0














I found the cause of the problem.



Short answer:



I have a component in the root of my app that was creating an invisible overlay. This happened because display: 'none' and position: 'absolute' don't work if applied to the same element on Android.



Long answer:



In my root component I have a menu that comes up from the bottom of the screen called OptionsMenu:



export default function App (): Element<typeof Provider> {
return (
<Provider store={store}>
<ActionSheetProvider>
<OptionsMenuContext.Provider>
<>
<Navigation uriPrefix={DEEP_LINK_URI_PREFIX} ref={setNavigator} />
<Notification />
<OptionsMenu />
</>
</OptionsMenuContext.Provider>
</ActionSheetProvider>
</Provider>
);
}


Inside OptionsMenu there is an overlay that covers the screen, this is so we can dim everything when the menu appears. The overlay (the outermost Animated.View) has position: 'absolute' as well as display: 'none'. The display setting comes from a prop and the position comes from style.container:



function OptionsMenu ({ hideOptionsMenu, overlayDisplay, overlayOpacity, containerPositionBottom, options =  }: Props): Element<typeof Animated.View> {
return (
<Animated.View style={[style.container, { display: overlayDisplay }]}>
<TouchableWithoutFeedback onPress={hideOptionsMenu}>
<Animated.View style={[style.overlay, { opacity: overlayOpacity }]} />
</TouchableWithoutFeedback>
<Animated.View style={[style.optionsContainer, { bottom: containerPositionBottom }]}>
{options.map(({ icon, text, onPress, type, component: Component }: Option) => !Component
? (
<TouchableOpacity activeOpacity={0.97} key={text} disabled={!onPress} onPress={onPress} style={style.optionContainer}>
{!!icon && (
<Image source={icon} style={[style.optionIcon, optionTypeTintMap[type]]} />
)}
<Text style={[style.optionText, optionTypeColorMap[type || 'neutralColor']]}>
{text}
</Text>
</TouchableOpacity>
) : (
<Component key={text} />
))}
</Animated.View>
</Animated.View>
);
}

export default withOptionsContext(OptionsMenu);


The problem was that on Android the absolute positioning will override the display setting. So the solution was to wrap an absolute positioned component inside a component which controlled the display setting:



OptionsMenu/style.js:



export default StyleSheet.create({
container: {
flex: 1,
// Removed these:
// position: 'absolute',
// left: 0,
// bottom: 0,
// width: screenWidth,
// height: screenHeight,
// zIndex: 19,
// elevation: 19
},

// Moved styles to new property:
overlayContainer: {
flex: 1,
position: 'absolute',
left: 0,
bottom: 0,
width: screenWidth,
height: screenHeight,
zIndex: 19,
elevation: 19
},


OptionsMenu/OptionsMenu.js:



function OptionsMenu ({ hideOptionsMenu, overlayDisplay, overlayOpacity, containerPositionBottom, options =  }: Props): Element<typeof Animated.View> {
return (
// Added new <View /> to control display setting separately:
<View style={[style.container, { display: overlayDisplay }]}>
<Animated.View style={style.overlayContainer}>





share|improve this answer





















    Your Answer






    StackExchange.ifUsing("editor", function () {
    StackExchange.using("externalEditor", function () {
    StackExchange.using("snippets", function () {
    StackExchange.snippets.init();
    });
    });
    }, "code-snippets");

    StackExchange.ready(function() {
    var channelOptions = {
    tags: "".split(" "),
    id: "1"
    };
    initTagRenderer("".split(" "), "".split(" "), channelOptions);

    StackExchange.using("externalEditor", function() {
    // Have to fire editor after snippets, if snippets enabled
    if (StackExchange.settings.snippets.snippetsEnabled) {
    StackExchange.using("snippets", function() {
    createEditor();
    });
    }
    else {
    createEditor();
    }
    });

    function createEditor() {
    StackExchange.prepareEditor({
    heartbeatType: 'answer',
    autoActivateHeartbeat: false,
    convertImagesToLinks: true,
    noModals: true,
    showLowRepImageUploadWarning: true,
    reputationToPostImages: 10,
    bindNavPrevention: true,
    postfix: "",
    imageUploader: {
    brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
    contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
    allowUrls: true
    },
    onDemand: true,
    discardSelector: ".discard-answer"
    ,immediatelyShowMarkdownHelp:true
    });


    }
    });














    draft saved

    draft discarded


















    StackExchange.ready(
    function () {
    StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53401103%2fonpress-not-firing-on-android-but-fine-on-ios%23new-answer', 'question_page');
    }
    );

    Post as a guest















    Required, but never shown

























    2 Answers
    2






    active

    oldest

    votes








    2 Answers
    2






    active

    oldest

    votes









    active

    oldest

    votes






    active

    oldest

    votes









    0














    You need to give height and width to TouchableOpacity



                <TouchableOpacity
    activeOpacity={0.97}
    onPressIn={() => console.log('in')}
    onPressOut={() => console.log('out')}
    onPress={() => { console.log('do something!'); navigation.navigate('EnterEmail'); }}
    style={[style.submit, { zIndex: 99999, elevation: 99999, height:200, width:200 }]}>
    <Text style={style.submitText}>
    {i18n.t('SIGN_IN')}
    </Text>
    </TouchableOpacity>


    I just added 200 for both for testing.



    Working code from Android:



    <View style={{
    flex: 1,
    backgroundColor: 'red'
    }}>
    <View style={style.container}>
    <View style={style.top}>
    </View>
    <View style={style.bottom}>
    <TouchableOpacity activeOpacity={0.97} onPressIn={() => alert('in')} onPressOut={() => alert('out')} onPress={() => { alert('do something!'); }} style={[style.submit, { zIndex: 99999, elevation: 99999 }]}>
    <Text style={style.submitText}>
    GENERAL TEXT
    </Text>
    </TouchableOpacity>
    </View>
    </View>
    </View>






    share|improve this answer























    • style.submit has height and width
      – JmJ
      Nov 21 '18 at 4:04










    • Can you send style of submit?
      – Nirmalsinh
      Nov 21 '18 at 4:04










    • send me all the style which you provide in code.
      – Nirmalsinh
      Nov 21 '18 at 4:05










    • I've edited my answer to include the styles
      – JmJ
      Nov 21 '18 at 4:19
















    0














    You need to give height and width to TouchableOpacity



                <TouchableOpacity
    activeOpacity={0.97}
    onPressIn={() => console.log('in')}
    onPressOut={() => console.log('out')}
    onPress={() => { console.log('do something!'); navigation.navigate('EnterEmail'); }}
    style={[style.submit, { zIndex: 99999, elevation: 99999, height:200, width:200 }]}>
    <Text style={style.submitText}>
    {i18n.t('SIGN_IN')}
    </Text>
    </TouchableOpacity>


    I just added 200 for both for testing.



    Working code from Android:



    <View style={{
    flex: 1,
    backgroundColor: 'red'
    }}>
    <View style={style.container}>
    <View style={style.top}>
    </View>
    <View style={style.bottom}>
    <TouchableOpacity activeOpacity={0.97} onPressIn={() => alert('in')} onPressOut={() => alert('out')} onPress={() => { alert('do something!'); }} style={[style.submit, { zIndex: 99999, elevation: 99999 }]}>
    <Text style={style.submitText}>
    GENERAL TEXT
    </Text>
    </TouchableOpacity>
    </View>
    </View>
    </View>






    share|improve this answer























    • style.submit has height and width
      – JmJ
      Nov 21 '18 at 4:04










    • Can you send style of submit?
      – Nirmalsinh
      Nov 21 '18 at 4:04










    • send me all the style which you provide in code.
      – Nirmalsinh
      Nov 21 '18 at 4:05










    • I've edited my answer to include the styles
      – JmJ
      Nov 21 '18 at 4:19














    0












    0








    0






    You need to give height and width to TouchableOpacity



                <TouchableOpacity
    activeOpacity={0.97}
    onPressIn={() => console.log('in')}
    onPressOut={() => console.log('out')}
    onPress={() => { console.log('do something!'); navigation.navigate('EnterEmail'); }}
    style={[style.submit, { zIndex: 99999, elevation: 99999, height:200, width:200 }]}>
    <Text style={style.submitText}>
    {i18n.t('SIGN_IN')}
    </Text>
    </TouchableOpacity>


    I just added 200 for both for testing.



    Working code from Android:



    <View style={{
    flex: 1,
    backgroundColor: 'red'
    }}>
    <View style={style.container}>
    <View style={style.top}>
    </View>
    <View style={style.bottom}>
    <TouchableOpacity activeOpacity={0.97} onPressIn={() => alert('in')} onPressOut={() => alert('out')} onPress={() => { alert('do something!'); }} style={[style.submit, { zIndex: 99999, elevation: 99999 }]}>
    <Text style={style.submitText}>
    GENERAL TEXT
    </Text>
    </TouchableOpacity>
    </View>
    </View>
    </View>






    share|improve this answer














    You need to give height and width to TouchableOpacity



                <TouchableOpacity
    activeOpacity={0.97}
    onPressIn={() => console.log('in')}
    onPressOut={() => console.log('out')}
    onPress={() => { console.log('do something!'); navigation.navigate('EnterEmail'); }}
    style={[style.submit, { zIndex: 99999, elevation: 99999, height:200, width:200 }]}>
    <Text style={style.submitText}>
    {i18n.t('SIGN_IN')}
    </Text>
    </TouchableOpacity>


    I just added 200 for both for testing.



    Working code from Android:



    <View style={{
    flex: 1,
    backgroundColor: 'red'
    }}>
    <View style={style.container}>
    <View style={style.top}>
    </View>
    <View style={style.bottom}>
    <TouchableOpacity activeOpacity={0.97} onPressIn={() => alert('in')} onPressOut={() => alert('out')} onPress={() => { alert('do something!'); }} style={[style.submit, { zIndex: 99999, elevation: 99999 }]}>
    <Text style={style.submitText}>
    GENERAL TEXT
    </Text>
    </TouchableOpacity>
    </View>
    </View>
    </View>







    share|improve this answer














    share|improve this answer



    share|improve this answer








    edited Nov 21 '18 at 4:44

























    answered Nov 21 '18 at 3:58









    Nirmalsinh

    3,11831336




    3,11831336












    • style.submit has height and width
      – JmJ
      Nov 21 '18 at 4:04










    • Can you send style of submit?
      – Nirmalsinh
      Nov 21 '18 at 4:04










    • send me all the style which you provide in code.
      – Nirmalsinh
      Nov 21 '18 at 4:05










    • I've edited my answer to include the styles
      – JmJ
      Nov 21 '18 at 4:19


















    • style.submit has height and width
      – JmJ
      Nov 21 '18 at 4:04










    • Can you send style of submit?
      – Nirmalsinh
      Nov 21 '18 at 4:04










    • send me all the style which you provide in code.
      – Nirmalsinh
      Nov 21 '18 at 4:05










    • I've edited my answer to include the styles
      – JmJ
      Nov 21 '18 at 4:19
















    style.submit has height and width
    – JmJ
    Nov 21 '18 at 4:04




    style.submit has height and width
    – JmJ
    Nov 21 '18 at 4:04












    Can you send style of submit?
    – Nirmalsinh
    Nov 21 '18 at 4:04




    Can you send style of submit?
    – Nirmalsinh
    Nov 21 '18 at 4:04












    send me all the style which you provide in code.
    – Nirmalsinh
    Nov 21 '18 at 4:05




    send me all the style which you provide in code.
    – Nirmalsinh
    Nov 21 '18 at 4:05












    I've edited my answer to include the styles
    – JmJ
    Nov 21 '18 at 4:19




    I've edited my answer to include the styles
    – JmJ
    Nov 21 '18 at 4:19













    0














    I found the cause of the problem.



    Short answer:



    I have a component in the root of my app that was creating an invisible overlay. This happened because display: 'none' and position: 'absolute' don't work if applied to the same element on Android.



    Long answer:



    In my root component I have a menu that comes up from the bottom of the screen called OptionsMenu:



    export default function App (): Element<typeof Provider> {
    return (
    <Provider store={store}>
    <ActionSheetProvider>
    <OptionsMenuContext.Provider>
    <>
    <Navigation uriPrefix={DEEP_LINK_URI_PREFIX} ref={setNavigator} />
    <Notification />
    <OptionsMenu />
    </>
    </OptionsMenuContext.Provider>
    </ActionSheetProvider>
    </Provider>
    );
    }


    Inside OptionsMenu there is an overlay that covers the screen, this is so we can dim everything when the menu appears. The overlay (the outermost Animated.View) has position: 'absolute' as well as display: 'none'. The display setting comes from a prop and the position comes from style.container:



    function OptionsMenu ({ hideOptionsMenu, overlayDisplay, overlayOpacity, containerPositionBottom, options =  }: Props): Element<typeof Animated.View> {
    return (
    <Animated.View style={[style.container, { display: overlayDisplay }]}>
    <TouchableWithoutFeedback onPress={hideOptionsMenu}>
    <Animated.View style={[style.overlay, { opacity: overlayOpacity }]} />
    </TouchableWithoutFeedback>
    <Animated.View style={[style.optionsContainer, { bottom: containerPositionBottom }]}>
    {options.map(({ icon, text, onPress, type, component: Component }: Option) => !Component
    ? (
    <TouchableOpacity activeOpacity={0.97} key={text} disabled={!onPress} onPress={onPress} style={style.optionContainer}>
    {!!icon && (
    <Image source={icon} style={[style.optionIcon, optionTypeTintMap[type]]} />
    )}
    <Text style={[style.optionText, optionTypeColorMap[type || 'neutralColor']]}>
    {text}
    </Text>
    </TouchableOpacity>
    ) : (
    <Component key={text} />
    ))}
    </Animated.View>
    </Animated.View>
    );
    }

    export default withOptionsContext(OptionsMenu);


    The problem was that on Android the absolute positioning will override the display setting. So the solution was to wrap an absolute positioned component inside a component which controlled the display setting:



    OptionsMenu/style.js:



    export default StyleSheet.create({
    container: {
    flex: 1,
    // Removed these:
    // position: 'absolute',
    // left: 0,
    // bottom: 0,
    // width: screenWidth,
    // height: screenHeight,
    // zIndex: 19,
    // elevation: 19
    },

    // Moved styles to new property:
    overlayContainer: {
    flex: 1,
    position: 'absolute',
    left: 0,
    bottom: 0,
    width: screenWidth,
    height: screenHeight,
    zIndex: 19,
    elevation: 19
    },


    OptionsMenu/OptionsMenu.js:



    function OptionsMenu ({ hideOptionsMenu, overlayDisplay, overlayOpacity, containerPositionBottom, options =  }: Props): Element<typeof Animated.View> {
    return (
    // Added new <View /> to control display setting separately:
    <View style={[style.container, { display: overlayDisplay }]}>
    <Animated.View style={style.overlayContainer}>





    share|improve this answer


























      0














      I found the cause of the problem.



      Short answer:



      I have a component in the root of my app that was creating an invisible overlay. This happened because display: 'none' and position: 'absolute' don't work if applied to the same element on Android.



      Long answer:



      In my root component I have a menu that comes up from the bottom of the screen called OptionsMenu:



      export default function App (): Element<typeof Provider> {
      return (
      <Provider store={store}>
      <ActionSheetProvider>
      <OptionsMenuContext.Provider>
      <>
      <Navigation uriPrefix={DEEP_LINK_URI_PREFIX} ref={setNavigator} />
      <Notification />
      <OptionsMenu />
      </>
      </OptionsMenuContext.Provider>
      </ActionSheetProvider>
      </Provider>
      );
      }


      Inside OptionsMenu there is an overlay that covers the screen, this is so we can dim everything when the menu appears. The overlay (the outermost Animated.View) has position: 'absolute' as well as display: 'none'. The display setting comes from a prop and the position comes from style.container:



      function OptionsMenu ({ hideOptionsMenu, overlayDisplay, overlayOpacity, containerPositionBottom, options =  }: Props): Element<typeof Animated.View> {
      return (
      <Animated.View style={[style.container, { display: overlayDisplay }]}>
      <TouchableWithoutFeedback onPress={hideOptionsMenu}>
      <Animated.View style={[style.overlay, { opacity: overlayOpacity }]} />
      </TouchableWithoutFeedback>
      <Animated.View style={[style.optionsContainer, { bottom: containerPositionBottom }]}>
      {options.map(({ icon, text, onPress, type, component: Component }: Option) => !Component
      ? (
      <TouchableOpacity activeOpacity={0.97} key={text} disabled={!onPress} onPress={onPress} style={style.optionContainer}>
      {!!icon && (
      <Image source={icon} style={[style.optionIcon, optionTypeTintMap[type]]} />
      )}
      <Text style={[style.optionText, optionTypeColorMap[type || 'neutralColor']]}>
      {text}
      </Text>
      </TouchableOpacity>
      ) : (
      <Component key={text} />
      ))}
      </Animated.View>
      </Animated.View>
      );
      }

      export default withOptionsContext(OptionsMenu);


      The problem was that on Android the absolute positioning will override the display setting. So the solution was to wrap an absolute positioned component inside a component which controlled the display setting:



      OptionsMenu/style.js:



      export default StyleSheet.create({
      container: {
      flex: 1,
      // Removed these:
      // position: 'absolute',
      // left: 0,
      // bottom: 0,
      // width: screenWidth,
      // height: screenHeight,
      // zIndex: 19,
      // elevation: 19
      },

      // Moved styles to new property:
      overlayContainer: {
      flex: 1,
      position: 'absolute',
      left: 0,
      bottom: 0,
      width: screenWidth,
      height: screenHeight,
      zIndex: 19,
      elevation: 19
      },


      OptionsMenu/OptionsMenu.js:



      function OptionsMenu ({ hideOptionsMenu, overlayDisplay, overlayOpacity, containerPositionBottom, options =  }: Props): Element<typeof Animated.View> {
      return (
      // Added new <View /> to control display setting separately:
      <View style={[style.container, { display: overlayDisplay }]}>
      <Animated.View style={style.overlayContainer}>





      share|improve this answer
























        0












        0








        0






        I found the cause of the problem.



        Short answer:



        I have a component in the root of my app that was creating an invisible overlay. This happened because display: 'none' and position: 'absolute' don't work if applied to the same element on Android.



        Long answer:



        In my root component I have a menu that comes up from the bottom of the screen called OptionsMenu:



        export default function App (): Element<typeof Provider> {
        return (
        <Provider store={store}>
        <ActionSheetProvider>
        <OptionsMenuContext.Provider>
        <>
        <Navigation uriPrefix={DEEP_LINK_URI_PREFIX} ref={setNavigator} />
        <Notification />
        <OptionsMenu />
        </>
        </OptionsMenuContext.Provider>
        </ActionSheetProvider>
        </Provider>
        );
        }


        Inside OptionsMenu there is an overlay that covers the screen, this is so we can dim everything when the menu appears. The overlay (the outermost Animated.View) has position: 'absolute' as well as display: 'none'. The display setting comes from a prop and the position comes from style.container:



        function OptionsMenu ({ hideOptionsMenu, overlayDisplay, overlayOpacity, containerPositionBottom, options =  }: Props): Element<typeof Animated.View> {
        return (
        <Animated.View style={[style.container, { display: overlayDisplay }]}>
        <TouchableWithoutFeedback onPress={hideOptionsMenu}>
        <Animated.View style={[style.overlay, { opacity: overlayOpacity }]} />
        </TouchableWithoutFeedback>
        <Animated.View style={[style.optionsContainer, { bottom: containerPositionBottom }]}>
        {options.map(({ icon, text, onPress, type, component: Component }: Option) => !Component
        ? (
        <TouchableOpacity activeOpacity={0.97} key={text} disabled={!onPress} onPress={onPress} style={style.optionContainer}>
        {!!icon && (
        <Image source={icon} style={[style.optionIcon, optionTypeTintMap[type]]} />
        )}
        <Text style={[style.optionText, optionTypeColorMap[type || 'neutralColor']]}>
        {text}
        </Text>
        </TouchableOpacity>
        ) : (
        <Component key={text} />
        ))}
        </Animated.View>
        </Animated.View>
        );
        }

        export default withOptionsContext(OptionsMenu);


        The problem was that on Android the absolute positioning will override the display setting. So the solution was to wrap an absolute positioned component inside a component which controlled the display setting:



        OptionsMenu/style.js:



        export default StyleSheet.create({
        container: {
        flex: 1,
        // Removed these:
        // position: 'absolute',
        // left: 0,
        // bottom: 0,
        // width: screenWidth,
        // height: screenHeight,
        // zIndex: 19,
        // elevation: 19
        },

        // Moved styles to new property:
        overlayContainer: {
        flex: 1,
        position: 'absolute',
        left: 0,
        bottom: 0,
        width: screenWidth,
        height: screenHeight,
        zIndex: 19,
        elevation: 19
        },


        OptionsMenu/OptionsMenu.js:



        function OptionsMenu ({ hideOptionsMenu, overlayDisplay, overlayOpacity, containerPositionBottom, options =  }: Props): Element<typeof Animated.View> {
        return (
        // Added new <View /> to control display setting separately:
        <View style={[style.container, { display: overlayDisplay }]}>
        <Animated.View style={style.overlayContainer}>





        share|improve this answer












        I found the cause of the problem.



        Short answer:



        I have a component in the root of my app that was creating an invisible overlay. This happened because display: 'none' and position: 'absolute' don't work if applied to the same element on Android.



        Long answer:



        In my root component I have a menu that comes up from the bottom of the screen called OptionsMenu:



        export default function App (): Element<typeof Provider> {
        return (
        <Provider store={store}>
        <ActionSheetProvider>
        <OptionsMenuContext.Provider>
        <>
        <Navigation uriPrefix={DEEP_LINK_URI_PREFIX} ref={setNavigator} />
        <Notification />
        <OptionsMenu />
        </>
        </OptionsMenuContext.Provider>
        </ActionSheetProvider>
        </Provider>
        );
        }


        Inside OptionsMenu there is an overlay that covers the screen, this is so we can dim everything when the menu appears. The overlay (the outermost Animated.View) has position: 'absolute' as well as display: 'none'. The display setting comes from a prop and the position comes from style.container:



        function OptionsMenu ({ hideOptionsMenu, overlayDisplay, overlayOpacity, containerPositionBottom, options =  }: Props): Element<typeof Animated.View> {
        return (
        <Animated.View style={[style.container, { display: overlayDisplay }]}>
        <TouchableWithoutFeedback onPress={hideOptionsMenu}>
        <Animated.View style={[style.overlay, { opacity: overlayOpacity }]} />
        </TouchableWithoutFeedback>
        <Animated.View style={[style.optionsContainer, { bottom: containerPositionBottom }]}>
        {options.map(({ icon, text, onPress, type, component: Component }: Option) => !Component
        ? (
        <TouchableOpacity activeOpacity={0.97} key={text} disabled={!onPress} onPress={onPress} style={style.optionContainer}>
        {!!icon && (
        <Image source={icon} style={[style.optionIcon, optionTypeTintMap[type]]} />
        )}
        <Text style={[style.optionText, optionTypeColorMap[type || 'neutralColor']]}>
        {text}
        </Text>
        </TouchableOpacity>
        ) : (
        <Component key={text} />
        ))}
        </Animated.View>
        </Animated.View>
        );
        }

        export default withOptionsContext(OptionsMenu);


        The problem was that on Android the absolute positioning will override the display setting. So the solution was to wrap an absolute positioned component inside a component which controlled the display setting:



        OptionsMenu/style.js:



        export default StyleSheet.create({
        container: {
        flex: 1,
        // Removed these:
        // position: 'absolute',
        // left: 0,
        // bottom: 0,
        // width: screenWidth,
        // height: screenHeight,
        // zIndex: 19,
        // elevation: 19
        },

        // Moved styles to new property:
        overlayContainer: {
        flex: 1,
        position: 'absolute',
        left: 0,
        bottom: 0,
        width: screenWidth,
        height: screenHeight,
        zIndex: 19,
        elevation: 19
        },


        OptionsMenu/OptionsMenu.js:



        function OptionsMenu ({ hideOptionsMenu, overlayDisplay, overlayOpacity, containerPositionBottom, options =  }: Props): Element<typeof Animated.View> {
        return (
        // Added new <View /> to control display setting separately:
        <View style={[style.container, { display: overlayDisplay }]}>
        <Animated.View style={style.overlayContainer}>






        share|improve this answer












        share|improve this answer



        share|improve this answer










        answered Nov 21 '18 at 5:58









        JmJ

        4931633




        4931633






























            draft saved

            draft discarded




















































            Thanks for contributing an answer to Stack Overflow!


            • Please be sure to answer the question. Provide details and share your research!

            But avoid



            • Asking for help, clarification, or responding to other answers.

            • Making statements based on opinion; back them up with references or personal experience.


            To learn more, see our tips on writing great answers.





            Some of your past answers have not been well-received, and you're in danger of being blocked from answering.


            Please pay close attention to the following guidance:


            • Please be sure to answer the question. Provide details and share your research!

            But avoid



            • Asking for help, clarification, or responding to other answers.

            • Making statements based on opinion; back them up with references or personal experience.


            To learn more, see our tips on writing great answers.




            draft saved


            draft discarded














            StackExchange.ready(
            function () {
            StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53401103%2fonpress-not-firing-on-android-but-fine-on-ios%23new-answer', 'question_page');
            }
            );

            Post as a guest















            Required, but never shown





















































            Required, but never shown














            Required, but never shown












            Required, but never shown







            Required, but never shown

































            Required, but never shown














            Required, but never shown












            Required, but never shown







            Required, but never shown







            Popular posts from this blog

            Costa Masnaga

            Fotorealismo

            Sidney Franklin