64

I have an absolute-positioned View that holds three TouchableOpacity components, and the three fail to respond they are just not working at all. What is going wrong here?

Code

<View style={[styles.highNormalLowDocListHeaderStateContainer, {width: this.windowWidth, height: this.headerSmallHeight, position: 'absolute', left: 0, top: floatedHeaderTitleTop, elevation: 2}]}>
    <TouchableOpacity onPress={() => this.getDocuments('high')} style={[styles.highNormalLowDocListHeaderStateTextContainer, highSelected.borderStyle]}>
        <Text style={[styles.highNormalLowDocListHeaderStateText, highSelected.textStyle]}>HIGH</Text>
    </TouchableOpacity>
    <TouchableOpacity onPress={() => this.getDocuments('normal')} style={[styles.highNormalLowDocListHeaderStateTextContainer, normalSelected.borderStyle]}>
        <Text style={[styles.highNormalLowDocListHeaderStateText, normalSelected.textStyle]}>NORMAL</Text>
    </TouchableOpacity>
    <TouchableOpacity onPress={() => this.getDocuments('low')} style={[styles.highNormalLowDocListHeaderStateTextContainer, lowSelected.borderStyle]}>
        <Text style {[styles.highNormalLowDocListHeaderStateText, lowSelected.textStyle]}>LOW</Text>
    </TouchableOpacity>
</View>

Screenshot

enter image description here

Mark Rotteveel
  • 100,966
  • 191
  • 140
  • 197
Ibrahim Ahmed
  • 2,295
  • 4
  • 21
  • 35

16 Answers16

86

Just add zIndex : 1 to the view containing the buttons.

Also note: adding elevation adds shadow to android button and sometimes elevation may also be a issue if it's added to parent and not added to child then the child button may not work (Rare Case).

eg:

buttonContainers:
  {
    zIndex: 1,
    alignSelf: 'flex-end',
    position: 'absolute',
    top:5,
    right: 5,
    height: 40,
    borderWidth: 1,
    justifyContent: 'center',
    alignContent: 'center',
    width: 80
  },
Tomerikoo
  • 18,379
  • 16
  • 47
  • 61
Rishav Kumar
  • 4,979
  • 1
  • 17
  • 32
85

Look at your import. If import { TouchableOpacity } from 'react-native-gesture-handler'; doesn't work, you need import this from 'react-native'.

Salek
  • 449
  • 1
  • 10
  • 19
Thiago Leite
  • 895
  • 1
  • 6
  • 4
  • The whole point of using `react-native-gesture-handle` is that they perform better so you'd be losing that. – Grub Oct 28 '19 at 22:37
  • 14
    They "perform better"? They don't work at all! I couldn't get the `onPress` handler of a `TouchableOpacity` from `react-native-gesture-handler` to do so much as an `alert` or a `console.log`. I imported it from `react-native` instead, and it just works. – Andrew Koster Oct 31 '19 at 21:15
  • Why on universe someone would import TouchableOpacity from react-native-gesture-handler ? – Rishav Kumar Dec 30 '19 at 04:54
  • 4
    @RishavKumar have you heard of auto import? – Thiago Leite Apr 06 '20 at 13:38
  • @ThiagoLeite Not yet, did manual import may be that is why never imported from gesture handler – Rishav Kumar Apr 06 '20 at 15:02
  • @RishavKumar I have some visual studio extensions that should help but sometimes get in the way. This is a case. He ends up importing from a wrong lib and we don't realize it. – Thiago Leite Apr 07 '20 at 16:18
  • 10
    this should be one of the worst auto-imports ever – guenis May 21 '20 at 18:02
  • another victim of auto-import! btw thanks, a true saviour! – Fazal Karim Aug 06 '20 at 12:52
  • Felt for this AGAIN today. The symptom is "why is my TouchableOpacity not styling properly?" – Hugo Oct 02 '20 at 12:51
  • RNGH TouchableOpacity is just their improved version of the RN component - they do this with a few RN components and there is a difference, especially with smoothness of interactions and animations. The styling problems are because the RNGH version has a `containerStyle` prop for styling the outer view: https://github.com/software-mansion/react-native-gesture-handler/issues/1163#issuecomment-773626608 – Shawn Erquhart Jul 08 '22 at 04:16
61

Importing TouchableOpacity from "react-native-gesture-handler" worked for me

import { TouchableOpacity} from 'react-native-gesture-handler'
Nouar
  • 3,170
  • 1
  • 23
  • 21
  • 1
    For me, this fixed the touch event problem but introduced many other style/alignment issues. That being said, I think the style bugs are easier to resolve than the touchable one – Tyler Oct 12 '20 at 22:18
  • Try using TouchableOpacity from react-native with debug and inspector disabled, or you can use the new api [link](https://reactnative.dev/docs/pressable) – Nouar Oct 12 '20 at 23:43
  • Interesting but my code worked when I import from react-native – Olkunmustafa Sep 08 '21 at 15:38
17

Even though the tab bar visually appears to be above the content in the list, the touch events for the list may be receiving it before the tab bar. Add a zIndex to the tab bar to allow it to receive touch events first.

mienaikoe
  • 511
  • 4
  • 12
7

If onPress of TouchableOpacity is not working, In that case, TouchableNativeFeedback will work

Example:

{ Platform.OS === 'ios' ?
  <TouchableOpacity onPress={() => this.showPassordText()}>
    <Text style={{ color: 'red' }}>SHOW</Text>  
  </TouchableOpacity>
  :
  <TouchableNativeFeedback onPress={() => this.showPassordText()}>
    <Text style={{ color: 'red' }}>SHOW</Text>
  </TouchableNativeFeedback>
}
Apurva Aggarwal
  • 296
  • 3
  • 10
5

Often when do absolute positioning you have to put a zIndex because the absolute positioned ui view is sometimes being rendered behind another view

Walter Shub
  • 652
  • 8
  • 19
3

I fixed this issue by adding in a flex: 1 to each parent, and a height/ width to each. also try pulling out each TouchableOpacity into separate view with flex:1 and adding absolute positioning to the child (text) element. I had an animation on my button so it may be a bit different.

2

In my case the touchable items were inside a FlatList. Using FlatList from 'react-native-gesture-handler' solved this issue for me.

Tayyab Mazhar
  • 1,560
  • 10
  • 26
2

What worked for me are:

  • Making sure I use
    import { TouchableOpacity } from 'react-native';
    
  • Removing flex: 1 and just having this style for my parent container:
    { width: '100%', height: '100%'}
    
Suraj Rao
  • 29,388
  • 11
  • 94
  • 103
Jemzzzz
  • 129
  • 9
1

Your absolute element is probably placed in a relative element. If you want to click it, you should remove parent relative rule.

Serdar D.
  • 3,055
  • 1
  • 30
  • 23
1

I tried all the other answers but could not get it to work. In my case I had a parent container that had the following styles:

.parentContainer {
    height: '100%',
    width: '100%',
    position: 'absolute',
    top: '-20%'
}

I realized that the children were overflowing out of the parent container and although it was not a big problem in terms of style, all the TouchableOpacity components that overflowed out of the parent container did not work (onPress event did not fire). Basically any TouchableOpacity component that ended up in the bottom 20% of the screen did not work because the parent had been moved up 20% (top: '-20%'). All I had to do was was change the height from 100% to 120% for the parent container and it started working as expected.

Sultan Singh Atwal
  • 810
  • 2
  • 8
  • 19
1

by importing TouchableOpacity from "react-native-gesture-handler" worked for me instead of giving the container View z-index

import { TouchableOpacity} from 'react-native-gesture-handler'
1

Add one more View or Div over Touchable opacity and give absolute positioning here

<View style={{position: 'absolute'}}>
  <TouchableOpacity></TouchableOpacity>
 </View>

because when you make the View 'absolute' inside the TouchableOpacity element TouchableOpacity doesnt move with elements inside

 <TouchableOpacity>
    <View style={{position: 'absolute'}}></View>
 </TouchableOpacity>

If you do like this above Touchable opacity doesnt move together with absolute element

Apatoallo
  • 45
  • 3
0

None of this answers here worked for me. I had to use import { TapGestureHandler } from 'react-native-gesture-handler'; and wrap the children elements with <TapGestureHandler onBegan={yourFunc} ></TapGestureHandler >

The benefit of this is that it doesn't affect your styles and also accomplishes the same click effect you want. Generally I prefer this.

Alexander
  • 457
  • 1
  • 4
  • 15
0

For me the fix was simple but I don't understand why?

<TouchableOpacity onPress={() => console.log('PRESSED')}>
   <View style={styles.fab}>
     <View style={styles.cartContainer}>
       <Text>{this.state.cartCount}</Text>
     </View>
     <Image source={CART} resizeMode="contain" />
   </View>
 </TouchableOpacity>

To

<TouchableOpacity style={styles.fab} onPress={() => console.log('PRESSED')}>
  <View style={styles.cartContainer}>
    <Text>{this.state.cartCount}</Text>
  </View>
  <Image source={CART} resizeMode="contain" />
</TouchableOpacity>

Styles

fab: {
    position: 'absolute',
    bottom: 40,
    right: 20,
    height: 60,
    width: 60,
}

Hope this helps anyone.

Adam Lee
  • 66
  • 1
  • 15
0

you can use TouchableHighlight instead:

import {  TouchableHighlight } from "react-native";

and change the press color with underlayColor={'lightgray'}

sahba
  • 39
  • 4