我在为我正在开发的电视应用程序的 React Native 中使用
TVFocusGuideView
进行焦点重定向时遇到问题。基本上,我的应用程序中有一个侧边栏,当用户查看内容时,他们会导航到单独的路线(使用 react-navigation
)。当他们退出内容播放器时,他们将返回主屏幕,主屏幕由两个组件组成:侧边栏和内容页面。
我的侧边栏位于左侧,因此它出现在 JSX 中的内容页面之前,如下所示:
<TVFocusGuideView
trapFocusUp={true}
trapFocusDown={true}
style={styles.container}
destinations={destinations}>
<SideBar
tabInfo={tabInfo}
selectedKey={selectedKey}
onIconPressed={onIconPressed}
isExpanded={isExpanded}
setIsExpanded={setIsExpanded}
/>
<Animated.View style={contentAnimationStyle} ref={ref}>
<TVFocusGuideView
autoFocus={true}
trapFocusDown={true}
trapFocusRight={true}
trapFocusUp={true}
style={styles.fullTVFocusGuide}>
{content}
</TVFocusGuideView>
</Animated.View>
</TVFocusGuideView>
目前,当我从内容播放器导航回到SideBar
时,它会获得焦点。但我想要
{content}
能够集中注意力。内容本身只是根据我的
NavigationBuilder
的当前状态呈现的(例如主页、用户个人资料等) - 这是其代码:
const { state, descriptors, navigation, NavigationContent } = useNavigationBuilder<
TabNavigationState<ParamListBase>,
TabRouterOptions,
TabActionHelpers<ParamListBase>,
BottomTabNavigationOptions,
BottomTabNavigationEventMap
>(TabRouter, {
id,
initialRouteName,
backBehavior,
children,
screenListeners,
screenOptions,
defaultScreenOptions,
});
const content = useMemo(() => {
return state.routes.map((route, i) => {
return (
<View
key={route.key}
style={[StyleSheet.absoluteFill, { display: i === state.index ? 'flex' : 'none' }]}>
{descriptors[route.key].render()}
</View>
);
});
}, [descriptors, state.index, state.routes]);
我认为将焦点重定向到包裹内容的外部 Animated.View
就足够了,我正在尝试使用最外面的
destinations
上的
TVFocusGuideView
道具来做到这一点,它包裹了
SideBar
和
Animated.View
内容。根据我的想法,它应该像将引用附加到
TVFocusGuideView
中的子组件一样简单,然后将
destinations
数组设置为
TVFocusGuideView destinations={[ref.current]}
,但这似乎没有做任何事情。我想也许 ref 没有被正确设置,当跳转到
TVFocusGuideView
的定义时,我看到它也可以接受节点句柄,所以我想我可以测试将
destinations
设置为节点数组像这样处理:
const ref = useRef<Animated.View>(null);
const [destinations, setDestinations] = useState<number[]>([]);
useEffect(() => {
// Ensure destinations are updated once the ref is set
if (ref.current) {
const nodeHandle = findNodeHandle(ref.current);
if (nodeHandle) {
setDestinations([nodeHandle]);
}
}
}, [ref]);
但即使我将其作为 TVFocusGuideView destinations={destinations}
传递,它仍然没有任何作用。我只是很困惑,我用错了吗?我想也许这是因为它是一个
View
参考,并用
View
替换了
TouchableOpacity
,但这也不起作用。总而言之,我尝试过:
hasTVPreferredFocus
添加到
TVFocusGuideView
包装内容?