[英]how to navigate to specific screen after pressing rnfirebase notification
我正在使用 react native firebase 並且我會在需要時收到通知,並且這些通知有一些數據可以導航到特定屏幕。 我使用 firebase 文檔來實現該功能,但它沒有按預期工作
這是我使用過的文檔Firebase 和 React-Navigation ,我的代碼如下所示:
const Stack = createStackNavigator();
const Router = () => {
const navigation = useNavigation();
const [loading, setLoading] = useState(true);
const [initialRoute, setInitialRoute] = useState('Splash');
useEffect(() => {
//fcm
registerAppWithFCM();
// checkRNFBPermission();
const unsubscribe = messaging().onMessage(async remoteMessage => {
console.log('remote DATAAAAAAAAAAAAAAAAAAAAAAAA : ',remoteMessage.data);
// switch (remoteMessage.data.screen) {
// case 'answer':{
// console.log('inside switch condition 1 !!!!!!!!!!!!!');
// useNavigation().navigate('Profile');
// break;
// }
// case 'AnswerQuestion':{
// console.log('inside switch condition 2 !!!!!!!!!!!!!');
// useNavigation().navigate('Profile');
// break;
// }
// default:
// break;
// }
// Alert.alert('A new FCM message arrived!', JSON.stringify(remoteMessage));
// const owner = JSON.parse(remoteMessage.data.owner);
// const user = JSON.parse(remoteMessage.data.user);
// const picture = JSON.parse(remoteMessage.data.picture);
});
// Assume a message-notification contains a "type" property in the data payload of the screen to open
messaging().onNotificationOpenedApp(remoteMessage => {
console.log(
'Notification caused app to open from background state:',
remoteMessage.notification,
);
navigation.navigate('Profile');
});
// Check whether an initial notification is available
messaging()
.getInitialNotification()
.then(remoteMessage => {
if (remoteMessage) {
console.log(
'Notification caused app to open from quit state:',
remoteMessage.data, //notification
);
}
setLoading(false);
});
messaging().setBackgroundMessageHandler(async remoteMessage => {
console.log('Message handled in the background!', remoteMessage);
});
return unsubscribe;
//fcm
}, []);
//fcm
checkRNFBPermission = async() => {
const enabled = await messaging().hasPermission();
if(enabled){
messaging()
.getToken()
.then(token => {
// console.log('deviceeeee fcm token ------> ', token);
});
}else{
requestUserPermission();
}
}
registerAppWithFCM = async() => {
await messaging().registerDeviceForRemoteMessages();
}
requestUserPermission = async() => {
const settings = await messaging().requestPermission();
if (settings) {
console.log('Permission settings:', settings);
}
}
//fcm
renderLoading = () => (
<View style={{ flex: 1, justifyContent: 'center', alignItems: 'center' }}>
<Text>Domanda</Text>
<ActivityIndicator size='large' color={colors.darkerTeal} />
</View>
);
//firebase
if (loading) {
return null;
}
//firebase
return(
<Provider store={store}>
<PersistGate persistor={persistor} loading={this.renderLoading()}>
<Root>
<NavigationContainer>
<Stack.Navigator initialRouteName={initialRoute} headerMode="none">
<Stack.Screen name="Splash" component={Splash} />
<Stack.Screen name="Login" component={Login} />
<Stack.Screen name="Main" component={Main} />
<Stack.Screen name="AppIntro" component={AppIntro} />
<Stack.Screen name="Tags" component={Tags} />
<Stack.Screen name="Answers" component={Answers} />
<Stack.Screen name="Profile" component={Profile} />
<Stack.Screen name="EditInfo" component={EditInfo} />
<Stack.Screen name="ChangePassword" component={ChangePassword} />
<Stack.Screen name="AnswerQuestion" component={AnswerQuestion} />
<Stack.Screen name="ContactUs" component={ContactUs} />
</Stack.Navigator>
</NavigationContainer>
</Root>
</PersistGate>
</Provider>
)
};
export default Router;
但是當我添加 usenavigation 並且我想使用它時,它會引發此錯誤:錯誤:我們找不到導航 object。 您的組件是否在導航器的屏幕內?
我不能使用navigation.navigate('Profile');
導航到特定屏幕。
您在 StackNavigator 之外的 App.js 中收到消息。 您可以使用 ref 來使用導航器的導航屬性
在 app.js 頂部定義導航器
var navigator = null;
然后將 ref 添加到導航器
<Stack.Navigator
initialRouteName={initialRoute}
headerMode="none"
ref={nav => {
navigator = nav;
}}
>
並在接收方法中推送您的路線
navigator.dispatch(
NavigationActions.navigate({
routeName: 'theRoute',
params: {},
}),
);
掙扎了4個小時...
有些在組件中,導航是否可用(在我的情況下是“主屏幕”)
// 最后一次導入
import { ScrollWrapper } from './styles' export const navigationRef = React.createRef(); export const isReadyRef = React.createRef(); export function navigate(name, params) { if (isReadyRef.current && navigationRef.current) { // Perform navigation if the app has mounted navigationRef.current.navigate(name, params); } else { console.log(' else [ELSE] --- ') // You can decide what to do if the app hasn't mounted // You can ignore this, or add these actions to a queue you can call later } } // component start export const SocialHomeScreen = () => {...
在 App.js 中
從'./screens/PeopleAroundYou/index'導入{導航,navigationRef,isReadyRef}
//.... 導航器
const App = () => {
const [isAuth, setIsAuth] = useState(false)
AsyncStorage.getItem('pushNotify').then(value => {
console.log('value --- ', value)
console.log('JSON.parse(value) --- ', JSON.parse(value))
}).catch(error => {
console.log('error --- ', error)
})
// foreground message arrived
useEffect(() => {
return messaging().onMessage(async remoteMessage => {
const { data, notification } = remoteMessage
if (data.type === 'activity-check-in') {
console.log(' A new FCM message arrived! --- ')
console.log('data --- ', data)
console.log('notification --- ', notification)
console.log(' navigator --- ', navigate)
console.log('navigationRef.current.getRootState() --- ', navigationRef.current.getRootState())
switch (data.category) {
case 'fitness':
// navigate to nested screen
navigate(routes.Fitness, {
screen: routes.ActivityDetails,
params: { activityId: data.eventId}
})
break
case 'companionship':
navigate(routes.Companionships, {
screen: routes.ActivityDetails,
params: { activityId: data.eventId}
})
break
case 'volunteering':
navigate(routes.Volunteering, {
screen: routes.ActivityDetails,
params: { activityId: data.eventId}
})
break
case 'wellbeing':
navigate(routes.Wellbeing, {
screen: routes.ActivityDetails,
params: { activityId: data.eventId}
})
break
}
}
})
}, [])
useEffect(() => {
SplashScreen.hide()
fcmService.registerAppWithFCM()
fcmService.register(onRegister, onNotification, onOpenNotification)
localNotificationService.configure(onOpenNotification)
function onRegister(token) {
console.log('[App] onRegister: ', token)
}
function onNotification(notify) {
console.log('[App] onNotification: ', notify)
const options = {
soundName: 'default',
playSound: true, //,
// largeIcon: 'ic_launcher', // add icon large for Android (Link: app/src/main/mipmap)
// smallIcon: 'ic_launcher' // add icon small for Android (Link: app/src/main/mipmap)
}
localNotificationService.showNotification(
0,
notify.title,
notify.body,
notify,
options,
)
}
function onOpenNotification(notify) {
console.log('[App] onOpenNotification: ', notify)
Alert.alert('Open Notification: ' + notify.body)
}
return () => {
console.log('[App] unRegister')
fcmService.unRegister()
localNotificationService.unregister()
}
}, [])
const authContext = useMemo(() => {
return {
login: () => {
setIsAuth(true)
},
logout: () => {
setIsAuth(false)
},
}
})
return (
<AuthContext.Provider value={authContext}>
<ThemeProvider theme={theme}>
<NavigationContainer
ref={navigationRef}
onReady={() => {
isReadyRef.current = true
}}
linking={linking}
fallback={
<View style={{ justifyContent: 'center', alignItems: 'center' }}>
<Loader loading size='large' color='#61A5C8'/>
</View>
}
>
{isAuth ? <AuthorizedTabs /> : <NonAuthorizedStack/>}
</NavigationContainer>
</ThemeProvider>
</AuthContext.Provider>
)
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.