如何将React Navigation头部输入框的值传递至search/index页面?
实现方法
这里提供两种实用方案来获取header中搜索框的输入内容:
方案一:使用React Context跨组件共享状态
适合需要在多个组件中复用搜索状态的场景,步骤如下:
- 创建搜索状态的Context
// contexts/SearchContext.js import { createContext, useContext, useState } from 'react'; const SearchContext = createContext(); export function SearchProvider({ children }) { const [searchText, setSearchText] = useState(''); return ( <SearchContext.Provider value={{ searchText, setSearchText }}> {children} </SearchContext.Provider> ); } export function useSearch() { return useContext(SearchContext); }
- 在根组件中包裹Provider
修改你的Layout组件,用SearchProvider包裹Stack:
import { Stack } from 'expo-router'; import { SearchProvider } from '../contexts/SearchContext'; import { SearchBar } from '../components/SearchBar'; export default function Layout() { return ( <SearchProvider> <Stack> <Stack.Screen name="(tabs)" options={{ headerShown: false }} /> <Stack.Screen name="search/index" options={{ headerTitle: () => <SearchBar />, }} /> </Stack> </SearchProvider> ); }
- 修改SearchBar组件使用Context
// components/SearchBar.js import { TextInput, StyleSheet } from 'react-native'; import { useSearch } from '../contexts/SearchContext'; export function SearchBar() { const { searchText, setSearchText } = useSearch(); return ( <TextInput style={styles.input} value={searchText} onChangeText={setSearchText} placeholder="搜索..." /> ); } const styles = StyleSheet.create({ input: { height: 40, borderColor: '#ccc', borderWidth: 1, borderRadius: 8, paddingHorizontal: 12, backgroundColor: '#fff', flex: 1, }, });
- 在search/index页面获取输入内容
// app/search/index.js import { View, Text } from 'react-native'; import { useSearch } from '../../contexts/SearchContext'; export default function SearchPage() { const { searchText } = useSearch(); return ( <View style={{ flex: 1, justifyContent: 'center', alignItems: 'center' }}> <Text>当前搜索内容:{searchText}</Text> </View> ); }
方案二:通过navigation.setOptions传递回调(仅单页面使用)
如果只需要在search/index页面获取搜索内容,可以直接在页面内定义状态,动态控制header:
- 修改search/index页面
// app/search/index.js import { View, Text } from 'react-native'; import { useState, useEffect } from 'react'; import { useNavigation } from 'expo-router'; import { SearchBar } from '../../components/SearchBar'; export default function SearchPage() { const [searchText, setSearchText] = useState(''); const navigation = useNavigation(); useEffect(() => { // 动态设置headerTitle,传入输入变更回调 navigation.setOptions({ headerTitle: () => ( <SearchBar value={searchText} onChangeText={setSearchText} /> ), }); }, [navigation, searchText]); return ( <View style={{ flex: 1, justifyContent: 'center', alignItems: 'center' }}> <Text>当前搜索内容:{searchText}</Text> </View> ); }
- 调整Layout中的配置
去掉Layout里对search/index的headerTitle配置,让页面自行控制:
import { Stack } from 'expo-router'; export default function Layout() { return <Stack> <Stack.Screen name="(tabs)" options={{ headerShown: false }} /> <Stack.Screen name="search/index" // 移除原有headerTitle配置 /> </Stack>; }
- 调整SearchBar为受控组件
// components/SearchBar.js import { TextInput, StyleSheet } from 'react-native'; export function SearchBar({ value, onChangeText }) { return ( <TextInput style={styles.input} value={value} onChangeText={onChangeText} placeholder="搜索..." /> ); } const styles = StyleSheet.create({ input: { height: 40, borderColor: '#ccc', borderWidth: 1, borderRadius: 8, paddingHorizontal: 12, backgroundColor: '#fff', flex: 1, }, });
内容的提问来源于stack exchange,提问作者Kos-Mos
相关产品推荐
相关产品推荐

