React-native-router-flux: Unable to change 'scale' transition effect between scenes

Created on 21 Sep 2016  路  9Comments  路  Source: aksonov/react-native-router-flux

There's an good explanation of the bug here: http://stackoverflow.com/questions/39593288/react-native-navigating-between-screens-screen-size-shrinking-bug

Along with a fantastic response.

It seems it it not possible to remove to scale affect when transitioning between scenes.

Is thing something in the pipe?

Most helpful comment

I did it pretty easily.
Just add a animationStyle prop to <Router/> like this:

<RouterWithRedux scenes={scenes} animationStyle={animationStyle}/>

and create an animationStyle function that will override interpolate values.

This is what I currently use in my project:

export const animationStyle = (props) => {
    const { layout, position, scene } = props;

    const direction = (scene.navigationState && scene.navigationState.direction) ?
        scene.navigationState.direction : 'horizontal';

    const index = scene.index;
    const inputRange = [index - 1, index, index + 1];
    const width = layout.initWidth;
    const height = layout.initHeight;

    const opacity = position.interpolate({
        inputRange,
        //default: outputRange: [1, 1, 0.3],
        outputRange: [1, 1, 0.5],
    });

    const scale = position.interpolate({
        inputRange,
        //default: outputRange: [1, 1, 0.95],
        outputRange: [1, 1, 1],
    });

    let translateX = 0;
    let translateY = 0;

    switch (direction) {
        case 'horizontal':
            translateX = position.interpolate({
                inputRange,
                //default: outputRange: [width, 0, -10],
                outputRange: [width, 0, 0],
            });
            break;
        case 'vertical':
            translateY = position.interpolate({
                inputRange,
                //default: outputRange: [height, 0, -10],
                outputRange: [height, 0, 0],
            });
            break;
    }

    return {
        opacity,
        transform: [
            { scale },
            { translateX },
            { translateY },
        ],
    };
};

Happy coding!

All 9 comments

Hi there,

I was able to customize the transition by directly changing the animation in the file
react-native-experimental-navigation/NavigationCardStackStyleInterpolator.js
but this is not a good practice I guess.
I also tried to duplicate the function into my own file and use the animationStyle prop but there was bug in the transition but I don't know if I missed something.

In the end I might fork react-native-experimental-navigation and use my own transition

I did it pretty easily.
Just add a animationStyle prop to <Router/> like this:

<RouterWithRedux scenes={scenes} animationStyle={animationStyle}/>

and create an animationStyle function that will override interpolate values.

This is what I currently use in my project:

export const animationStyle = (props) => {
    const { layout, position, scene } = props;

    const direction = (scene.navigationState && scene.navigationState.direction) ?
        scene.navigationState.direction : 'horizontal';

    const index = scene.index;
    const inputRange = [index - 1, index, index + 1];
    const width = layout.initWidth;
    const height = layout.initHeight;

    const opacity = position.interpolate({
        inputRange,
        //default: outputRange: [1, 1, 0.3],
        outputRange: [1, 1, 0.5],
    });

    const scale = position.interpolate({
        inputRange,
        //default: outputRange: [1, 1, 0.95],
        outputRange: [1, 1, 1],
    });

    let translateX = 0;
    let translateY = 0;

    switch (direction) {
        case 'horizontal':
            translateX = position.interpolate({
                inputRange,
                //default: outputRange: [width, 0, -10],
                outputRange: [width, 0, 0],
            });
            break;
        case 'vertical':
            translateY = position.interpolate({
                inputRange,
                //default: outputRange: [height, 0, -10],
                outputRange: [height, 0, 0],
            });
            break;
    }

    return {
        opacity,
        transform: [
            { scale },
            { translateX },
            { translateY },
        ],
    };
};

Happy coding!

@redbaron76 Great that works. Thanks.

@redbaron76 Thanks, that was just that I needed for my project!

@redbaron76 amazing how easily that works.

For any newbies reading that, RouterWithRedux is basically:

const RouterWithRedux = connect()(Router);

Then you can create the component as he mentioned. You'll put it in place of your Router.

@redbaron76 @aksonov This works perfectly and should definitely be part of the docs!

Best answer EVVVAAAA

@redbaron76 This is perfect! What's the role of passing index here:

    const index = scene.index
    const inputRange = [index - 1, index, index + 1]

@redbaron76 Works perfect, but it applies to modal. How can I disable on modal animation only?

Was this page helpful?
0 / 5 - 0 ratings