让安卓实现push动画
之前我群里的讨论怎么让安卓实现类似iOS的push动画,后来翻看官方issues的时候,真的发现了实现push动画的代码,在这里共享下
// 先引入这个方法
import CardStackStyleInterpolator from 'react-navigation/src/views/CardStackStyleInterpolator';
// 在StackNavigator配置headerMode的地方,使用transitionConfig添加
{
headerMode: 'screen',
transitionConfig:()=>({
screenInterpolator:CardStackStyleInterpolator.forHorizontal,
})
}
修改页面的跳转动画
如何将安卓的跳转动画改成iOS那样,react-navigation一共提供了4种跳转动画:
1、从右向左: forHorizontal;
2、从下向上: forVertical;
3、安卓那种的从下向上: forFadeFromBottomAndroid;
4、无动画: forInitial。
但因为库的限制,想实现某些页面使用某种动画还是很难的,只能通过Demo中提供的笨方法来实现。
首先还是导入react-navigation中的方法
import CardStackStyleInterpolator from 'react-navigation/src/views/CardStack/CardStackStyleInterpolator';
如果要改变跳转动画只能在StackNavigator中实现transitionConfig方法
const MainStack = StackNavigator({
Main:{
screen:Main,
},
},{
// mode:'modal',
headerMode: 'screen',
transitionConfig:()=>({
// 只要修改最后的forVertical就可以实现不同的动画了。
screenInterpolator:CardStackStyleInterpolator.forVertical,
})
});
goBack返回指定页面
react-navigation目录下src/routers/StackRouter.js
iif (action.type === NavigationActions.BACK) {
let backRouteIndex = null;
if (action.key) {
const backRoute = state.routes.find(
/* $FlowFixMe */
/* 修改源码 */
route => route.routeName === action.key
/* (route: *) => route.key === action.key */
);
/* $FlowFixMe */
console.log('backRoute =====',backRoute);
backRouteIndex = state.routes.indexOf(backRoute);
console.log('backRoute =====',backRouteIndex);
}
if (backRouteIndex == null) {
return StateUtils.pop(state);
}
if (backRouteIndex >= 0) {
return {
...state,
routes: state.routes.slice(0, backRouteIndex+1),
index: backRouteIndex - 1 + 1,
};
}
}
注意:这样的修改源码之后,如果项目中使用Redux,并且启用了滑动返回,很会很大几率导致app卡死,所以并不太推荐这种方式,最好使用下面的方式
关于快速点击重复跳转的解决办法
如果想解决快速点击跳转的问题,需要修改部分源码。
修改react-navigation目录下,scr文件夹中的addNavigationHelpers.js文件
,可以直接替换成下面的文本
export default function<S: *>(navigation: NavigationProp<S, NavigationAction>) {
// 添加点击判断
let debounce = true;
return {
...navigation,
goBack: (key?: ?string): boolean =>
navigation.dispatch(
NavigationActions.back({
key: key === undefined ? navigation.state.key : key,
}),
),
navigate: (routeName: string,
params?: NavigationParams,
action?: NavigationAction,): boolean => {
if (debounce) {
debounce = false;
navigation.dispatch(
NavigationActions.navigate({
routeName,
params,
action,
}),
);
setTimeout(
() => {
debounce = true;
},
500,
);
return true;
}
return false;
},
/**
* For updating current route params. For example the nav bar title and
* buttons are based on the route params.
* This means `setParams` can be used to update nav bar for example.
*/
setParams: (params: NavigationParams): boolean =>
navigation.dispatch(
NavigationActions.setParams({
params,
key: navigation.state.key,
}),
),
};
}
安卓上,使用TextInput的时候会让TabBar顶起来的解决办法
最简单的解决办法就是在android目录中,添加一句话
目录:android/app/src/main/AndroidManifest.xml中,添加
android:windowSoftInputMode="stateAlwaysHidden|adjustPan|adjustResize"
安卓返回键在react-navigation中的正常监听
之前使用Navigator的时候,可以通过下面的方法实现监听安卓的返回键,但使用了react-navigation后,会很迷茫,不知该怎么监听了。
Navigator的方法
componentWillMount() {
if (Platform.OS === 'android') {
BackAndroid.addEventListener('hardwareBackPress', this.onBackAndroid);
}
}
componentWillUnmount() {
if (Platform.OS === 'android') {
BackAndroid.removeEventListener('hardwareBackPress', this.onBackAndroid);
}
}
onBackAndroid = () => {
const nav = this.navigator;
const routers = nav.getCurrentRoutes();
if (routers.length > 1) {
nav.pop();
return true;
}
return false;
};
……
}
react-navigation的方式
componentWillMount() {
if (Platform.OS === 'android') {
BackHandler.addEventListener('handwareBackPress',this.onBackAndroid)
}
}
componentWillUnmount() {
if (Platform.OS === 'android') {
BackHandler.addEventListener('handwareBackPress',this.onBackAndroid)
}
}
onBackAndroid = () => {
const routers = nav.getCurrentRoutes();
if (routers.length > 1) {
return true;
}
return false;
};
……
}
// 在跳转之后的页面中
onBackAndroid = ()=> {
const {routes} = this.props;
console.log(routes);
// alert(routes)
if (routes.length > 1) {
// 因为其他页面获得不到this.props,所以只能每个页面都写这个方法。
this.props.navigation.goBack();
return true;
}
}
网友评论