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

App crashes when using onClick handlers in release mode #101

Closed
dstaley opened this issue Jul 10, 2021 · 1 comment
Closed

App crashes when using onClick handlers in release mode #101

dstaley opened this issue Jul 10, 2021 · 1 comment
Labels
framework Bug is in the React Native for Windows framework

Comments

@dstaley
Copy link
Contributor

dstaley commented Jul 10, 2021

When passing an onClick handler to elements like AppBarButton and Button, the app will crash when attempting to render a screen containing react-native-xaml components for a second time. This only occurs in release mode builds. It doesn't occur in Debug builds with web debugging enabled or with web debugging disabled. This also occurs whether the app uses Chakra or Hermes. However, this does not occur if you only ever click the "Go back (Pressable)" button, leading me to believe there's something funky going on with how react-native-xaml handles JS callbacks.

Reproduction steps:

  1. npx react-native init AppName --template react-native-template-typescript
  2. cd AppName
  3. npx react-native-windows-init --overwrite --useHermes or npx react-native-windows init --overwrite --language cs
  4. yarn add react-native-safe-area-context react-native-screens @react-navigation/native @react-navigation/stack
  5. Launch release build from Visual Studio
  6. Click "Add" button
  7. Click "Go back (XAML Button)"
  8. Click "Add" button

Expected Result:
App renders AddScreen containing two buttons.

Actual Result:
App crashes with an unhandled exception.

image

App.tsx
import React, {useCallback} from 'react';
import {SafeAreaView, Text, View, Pressable} from 'react-native';
import {Button} from 'react-native-xaml';
import {NavigationContainer, DefaultTheme} from '@react-navigation/native';
import {
  createStackNavigator,
  StackNavigationProp,
} from '@react-navigation/stack';

type RootStackParamList = {
  Home: undefined;
  Add: undefined;
};

const Stack = createStackNavigator<RootStackParamList>();

type HomeScreenNavigationProp = StackNavigationProp<RootStackParamList, 'Home'>;

const HomeScreen: React.FC<{navigation: HomeScreenNavigationProp}> = ({
  navigation,
}) => {
  return (
    <View style={{marginTop: 96}}>
      <Pressable
        onPress={() => {
          navigation.navigate('Add');
        }}>
        <Text>Add</Text>
      </Pressable>
    </View>
  );
};

type AddScreenNavigationProp = StackNavigationProp<RootStackParamList, 'Add'>;

const AddScreen: React.FC<{navigation: AddScreenNavigationProp}> = ({
  navigation,
}) => {
  const goBack = useCallback(() => {
    navigation.goBack();
  }, []);

  return (
    <SafeAreaView>
      <View>
        <Pressable onPress={goBack}>
          <View style={{paddingVertical: 8, paddingHorizontal: 32}}>
            <Text>Go back (Pressable)</Text>
          </View>
        </Pressable>
        <Button content="Go back (XAML Button)" onClick={goBack} />
      </View>
    </SafeAreaView>
  );
};

const App = () => {
  return (
    <NavigationContainer
      theme={{
        ...DefaultTheme,
        colors: {...DefaultTheme.colors, background: 'transparent'},
      }}>
      <Stack.Navigator headerMode="none" detachInactiveScreens={true}>
        <Stack.Screen name="Home" component={HomeScreen} />
        <Stack.Screen name="Add" component={AddScreen} />
      </Stack.Navigator>
    </NavigationContainer>
  );
};

export default App;
Dependency versions
{
  "@react-navigation/native": "^5.9.4",
  "@react-navigation/stack": "^5.14.5",
  "react": "17.0.1",
  "react-native": "0.64.1",
  "react-native-safe-area-context": "^3.2.0",
  "react-native-screens": "^3.4.0",
  "react-native-windows": "^0.64.0-0",
  "react-native-xaml": "^0.0.29"
}

Notes:
When rendering the AddScreen, you may still see the Add button from HomeScreen. This is a bug in react-navigation.

I tried to create a repro that works without react-navigation, but the following code didn't trigger the issue. I think this might mean that the issue is related to React Context, which this example does not use, but both react-navigation and react-router do use.

Example that does not trigger the issue
const App = () => {
  const [show, setShow] = useState(true);
  const toggle = useCallback(() => {
    setShow(s => !s);
  }, []);

  return (
    <View>
      <Pressable onPress={toggle}>
        <Text>Toggle Native XAML Button</Text>
      </Pressable>
      {show && <Button onClick={toggle} content="Hide Native XAML Button" />}
    </View>
  );
};
@asklar
Copy link
Member

asklar commented Jul 14, 2021

Fixed in RNW: microsoft/react-native-windows#8220 and its ports

@asklar asklar closed this as completed Jul 14, 2021
@asklar asklar added the framework Bug is in the React Native for Windows framework label Jul 14, 2021
@ghost ghost locked as resolved and limited conversation to collaborators Aug 17, 2021
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
framework Bug is in the React Native for Windows framework
Projects
None yet
Development

No branches or pull requests

2 participants