Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

<Pressable /> not working inside <ScrollView /> if <Animated.View /> used anywhere #6935

Open
th3poli opened this issue Jan 25, 2025 · 10 comments
Labels
Platform: Android This issue is specific to Android Repro provided A reproduction with a snippet of code, snack or repo is provided Reproducible 🎉

Comments

@th3poli
Copy link

th3poli commented Jan 25, 2025

Description

Hi, I was trying to create an animated header using <Animated.View /> while scrolling, but unfortunately, when I scroll down, my buttons stop working if I include <Animated.View /> with useAnimatedStyle anywhere in the code. This issue only occurs on a real device. However, if I remove style={defaultTitleAnimStyle}, everything works fine.

I also tested this with Pressable from react-native-gesture-handler, and it worked as expected. I'm not sure why this is happening—maybe I’m doing something wrong?

Here are some examples:
With <Animated.View style={defaultTitleAnimStyle} />:
https://github.com/user-attachments/assets/53ab00af-72a7-4c46-82ee-12486e0bdbab

Without <Animated.View />:
https://github.com/user-attachments/assets/34e29e4f-f700-4528-b6b8-295440a671e7

Code is available in Expo Snack and also included below:

import { Pressable, ScrollView, Text, View } from "react-native";
import Animated, { interpolate, useAnimatedStyle, useSharedValue } from "react-native-reanimated";

export default function Index() {

  const [pressed, setPressed] = useState(0)
  const scrollValue = useSharedValue(0)

  const onScroll = useCallback((e: any) => {
    scrollValue.value = e.nativeEvent.contentOffset.y
  }, [])

  const defaultTitleAnimStyle = useAnimatedStyle(() => {
    const opacity = interpolate(scrollValue.value, [32, 96], [0, 1])
    return {
      opacity: opacity,
    }
  })

  return (
    <View style={{ flex: 1 }} >

      <Animated.View style={defaultTitleAnimStyle}>
      <Text>My App Animated Title</Text>
      </Animated.View>

      <Text>Pressed times: {pressed}</Text>

      <Animated.ScrollView onScroll={onScroll}>
        <Pressable onPress={() => setPressed(prev => prev + 1)} android_ripple={{ color: 'red' }} style={{ padding: 24, backgroundColor: '#222' }}>
          <Text style={{ color: "#fff" }}>My Test Button</Text>
        </Pressable>
        <Pressable onPress={() => setPressed(prev => prev + 1)} android_ripple={{ color: 'red' }} style={{ padding: 24, backgroundColor: '#222' }}>
          <Text style={{ color: "#fff" }}>My Test Button</Text>
        </Pressable>
        <Pressable onPress={() => setPressed(prev => prev + 1)} android_ripple={{ color: 'red' }} style={{ padding: 24, backgroundColor: '#222' }}>
          <Text style={{ color: "#fff" }}>My Test Button</Text>
        </Pressable>
        <Pressable onPress={() => setPressed(prev => prev + 1)} android_ripple={{ color: 'red' }} style={{ padding: 24, backgroundColor: '#222' }}>
          <Text style={{ color: "#fff" }}>My Test Button</Text>
        </Pressable>
        <Pressable onPress={() => setPressed(prev => prev + 1)} android_ripple={{ color: 'red' }} style={{ padding: 24, backgroundColor: '#222' }}>
          <Text style={{ color: "#fff" }}>My Test Button</Text>
        </Pressable>
        <View style={{ height: 1200 }} />
      </Animated.ScrollView>
    </View>
  );
}

Steps to reproduce

  1. Visit the Snack project: https://snack.expo.dev/@thepoli/2be69c
  2. Choose My Device as the running option.
  3. Scan the displayed QR Code using Expo GO (version 2.32.17).
  4. Test by clicking the buttons — everything works fine at this stage.
  5. Scroll down.
  6. Try clicking the buttons again — you’ll notice that loses focus. On Android, the ripple effect is visible, but the onPress event doesn't fire.
  7. Remove lines 24, 25, and 26:
<Animated.View style={defaultTitleAnimStyle}>
    <Text>My App Animated Title</Text>
</Animated.View>
  1. After removing those lines, everything works correctly again.

Snack or a link to a repository

https://snack.expo.dev/@thepoli/2be69c

Reanimated version

~3.16.1

React Native version

0.76.6

Platforms

Android

JavaScript runtime

None

Workflow

Expo Go

Architecture

Fabric (New Architecture)

Build type

None

Device

Real device

Device model

Samsung Galaxy A32

Acknowledgements

Yes

@github-actions github-actions bot added Platform: Android This issue is specific to Android Repro provided A reproduction with a snippet of code, snack or repo is provided labels Jan 25, 2025
@patrycjakalinska
Copy link
Contributor

patrycjakalinska commented Jan 27, 2025

Hi @th3poli, thanks for opening this issue. I think it is directly related to other issue #6704 (and probably #6676) - we're working to find fix for the issue, and will let you know as soon as it's ready c:

@arasrezaei
Copy link

any workaround? i can not release my update because of this :(

@th3poli
Copy link
Author

th3poli commented Jan 29, 2025

any workaround? i can not release my update because of this :(

You can use <Pressable /> from react-native-gesture-handler. BUT there's another bug where you can't change color of android_ripple.

software-mansion/react-native-gesture-handler#3246

@arasrezaei
Copy link

any workaround? i can not release my update because of this :(

You can use <Pressable /> from react-native-gesture-handler. BUT there's another bug where you can't change color of android_ripple.

software-mansion/react-native-gesture-handler#3246

Unfortunately, my app depend on many libraries. I can not change all of them 😕. TouchableRipple from react-native-paper for example, which uses Pressable and android_ripple

@yo9e5h
Copy link

yo9e5h commented Jan 30, 2025

+1

@ar7casper
Copy link

Heyo,

Had issues as well, I'm using expo 52.
What I've done is that I've upgraded to RN 0.77 and installed these package versions as per expo's recommendations -
npx expo install react-native@~0.77.0 react-native-reanimated@~3.16.7 react-native-gesture-handler@~2.22.0 react-native-screens@~4.5.0 react-native-safe-area-context@~5.1.0 react-native-webview@~13.13.1

Everything is back to normal.
https://expo.dev/changelog/2025/01-21-react-native-0.77

@arasrezaei
Copy link

Heyo,

Had issues as well, I'm using expo 52. What I've done is that I've upgraded to RN 0.77 and installed these package versions as per expo's recommendations - npx expo install react-native@~0.77.0 react-native-reanimated@~3.16.7 react-native-gesture-handler@~2.22.0 react-native-screens@~4.5.0 react-native-safe-area-context@~5.1.0 react-native-webview@~13.13.1

Everything is back to normal. https://expo.dev/changelog/2025/01-21-react-native-0.77

I have those packages exactly and issue is only on NewArch , I had to turn off NewArch unfortunately and now everything works.

@freeboub
Copy link

did someone try to upgrade to 3.17.0 or 4.0.0 ?

latekvo added a commit to software-mansion/react-native-gesture-handler that referenced this issue Feb 3, 2025
## Description

Android ripple currently does not work on `Fabric`, as all values passed
to `RawButton` and it's inheritors are passed through `processColor`,
which is crucial on `Paper`, and broken on `Fabric`.

This PR disables usage of `processColor`, when running on `Fabric`.

Note: `isFabric` cannot be moved out of the body of the `Pressable`, as
it likely won't be initialised before the `Pressable` starts being
rendered. More details
[here](https://github.com/software-mansion/react-native-gesture-handler/blob/b3d8fd91dca195267bdc33aa20fd6f5cd37d7fe2/src/utils.ts#L47).

Fixes #3246
Fixes #3312
Supersedes #3250
Likely could add a workaround for
software-mansion/react-native-reanimated#6935

## Test plan

<details>
<summary>
Collapsed test code
</summary>

```tsx
import React from 'react';
import { Pressable as RNPressable, StyleSheet, Text } from 'react-native';
import {
  BaseButton,
  GestureHandlerRootView,
  RectButton,
  Pressable,
} from 'react-native-gesture-handler';

const App = () => {
  return (
    <GestureHandlerRootView>
      <RectButton style={styles.wrapperCustom} rippleColor={'blue'}>
        <Text style={styles.text}>RectButton</Text>
      </RectButton>
      <BaseButton style={styles.wrapperCustom} rippleColor={'blue'}>
        <Text style={styles.text}>BaseButton</Text>
      </BaseButton>
      <Pressable
        style={styles.wrapperCustom}
        android_ripple={{ color: 'blue' }}>
        {({ pressed }) => (
          <Text style={styles.text}>
            {pressed ? 'Pressed!' : 'Pressable from react-native'}
          </Text>
        )}
      </Pressable>
      <RNPressable
        style={styles.wrapperCustom}
        android_ripple={{ color: 'blue' }}>
        {({ pressed }) => (
          <Text style={styles.text}>
            {pressed ? 'Pressed!' : 'Pressable from react-native'}
          </Text>
        )}
      </RNPressable>
      <Pressable
        style={styles.wrapperCustom}
        android_ripple={{ color: '#00f' }}>
        {({ pressed }) => (
          <Text style={styles.text}>
            {pressed ? 'Pressed!' : 'Pressable from react-native'}
          </Text>
        )}
      </Pressable>
      <RNPressable
        style={styles.wrapperCustom}
        android_ripple={{ color: '#00f' }}>
        {({ pressed }) => (
          <Text style={styles.text}>
            {pressed ? 'Pressed!' : 'Pressable from react-native'}
          </Text>
        )}
      </RNPressable>
    </GestureHandlerRootView>
  );
};

const styles = StyleSheet.create({
  container: {
    flex: 1,
    justifyContent: 'center',
    gap: 16,
    padding: 16,
  },
  text: {
    fontSize: 32,
  },
  wrapperCustom: {
    borderRadius: 8,
    padding: 6,
    flex: 1,
    backgroundColor: 'papayawhip',
    borderColor: 'red',
    borderWidth: 2,
  },
  logBox: {
    flex: 1,
    padding: 20,
    margin: 10,
    borderWidth: StyleSheet.hairlineWidth,
    borderColor: '#f0f0f0',
    backgroundColor: '#f9f9f9',
  },
});

export default App;

```

</details>
@latekvo
Copy link
Contributor

latekvo commented Feb 5, 2025

@th3poli rippleColor issue has been resolved in the latest release of react-native-gesture-handler - 2.23.0

@mateoabrbt
Copy link

Any news on this one ?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Platform: Android This issue is specific to Android Repro provided A reproduction with a snippet of code, snack or repo is provided Reproducible 🎉
Projects
None yet
Development

No branches or pull requests

8 participants