React Native - React Navigation transitions

karol.barkowski picture karol.barkowski · May 15, 2017 · Viewed 18.8k times · Source

I'd like to use React Navigation in my new react native app but I can't find any example showing how to create custom view transitions in there. Default transitions are working fine but I'd like to be able to customize them in few places and the docs don't come very helpfull in this subject. Anyone tried that already? Anywhere I could see a working example? Thanks in advance.

Answer

Tim Rijavec picture Tim Rijavec · May 15, 2017

You can find detailed version of this post on this link

I hope this is clear enough with step-by-step for how to create custom transition.

Create a Scene or Two to navigate

class SceneOne extends Component {
    render() {
        return (
            <View>
                <Text>{'Scene One'}</Text>
            </View>
        )
    }
}
class SceneTwo extends Component {
    render() {
        return (
            <View>
                <Text>{'Scene Two'}</Text>
            </View>
        )
    }
}

Declare your app scenes

let AppScenes = {
    SceneOne: {
        screen: SceneOne
    },
    SceneTwo: {
        screen: SceneTwo
    },
}

Declare custom transition

let MyTransition = (index, position) => {
    const inputRange = [index - 1, index, index + 1];
    const opacity = position.interpolate({
        inputRange,
        outputRange: [.8, 1, 1],
    });

    const scaleY = position.interpolate({
        inputRange,
        outputRange: ([0.8, 1, 1]),
    });

    return {
        opacity,
        transform: [
            {scaleY}
        ]
    };
};

Declare custom transitions configurator

let TransitionConfiguration = () => {
    return {
        // Define scene interpolation, eq. custom transition
        screenInterpolator: (sceneProps) => {

            const {position, scene} = sceneProps;
            const {index} = scene;

            return MyTransition(index, position);
        }
    }
};

Create app navigator using Stack Navigator

const AppNavigator = StackNavigator(AppScenes, {
    transitionConfig: TransitionConfiguration
});

Use App Navigator in your project

class App extends Component {
    return (
        <View>
            <AppNavigator />
        </View>
    )
}

Register your app in eq. index.ios.js

import { AppRegistry } from 'react-native';
AppRegistry.registerComponent('MyApp', () => App);

Update #1

As for the question on how to set transition per scene, this is how I'm doing it.

When you navigate using NavigationActions from react-navigation, you can pass through some props. In my case it looks like this

this.props.navigate({
    routeName: 'SceneTwo',
    params: {
        transition: 'myCustomTransition'
    }
})

and then inside the Configurator you can switch between these transition like this

let TransitionConfiguration = () => {
    return {
        // Define scene interpolation, eq. custom transition
        screenInterpolator: (sceneProps) => {

            const {position, scene} = sceneProps;
            const {index, route} = scene
            const params = route.params || {}; // <- That's new
            const transition = params.transition || 'default'; // <- That's new

            return {
                myCustomTransition: MyCustomTransition(index, position),
                default: MyTransition(index, position),
            }[transition];
        }
    }
};