Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I set custom drawer items to "focused" dynamically?

My end goal here is to give a few drawer items custom background colors depending on a few states set elsewhere. I understand that in order to give unique background colors to drawer items, I need to set up custom drawer content. However, I am having an issue in which I cannot get the custom drawer icons to know if they are in focus or not.

I originally thought that I could just do a const [bHomeFocused, setbHomeFocused] = useState(false) (etc) and setting state on onPress and then setting the focused property on that, but when a bunch more drawer items come in, I think that sounds like an unwieldy solution.

I'm sure there is a simple answer that I'm missing, as non-custom DrawerItems have this functionality inherently...

import { Drawer } from 'react-native-paper'
import { createDrawerNavigator, DrawerNavigationProp, DrawerItem, DrawerContentScrollView, DrawerItemList, DrawerContentComponentProps, DrawerContentOptions } from '@react-navigation/drawer';

function CustomDrawerContent(props: DrawerContentComponentProps<DrawerContentOptions>) {

    return (
        <DrawerContentScrollView {...props}>
            <Drawer.Section>
                <DrawerItem
                    label="Dashboard"
                    labelStyle={{ color: colorTheme.normalText }}
                    icon={() => <Icon name="book" type="feather" size={26} color={colorTheme.normalText} />}
                    activeBackgroundColor={colorTheme.panel}
                    inactiveBackgroundColor={colorTheme.cyan}
                    onPress={() => {
                        props.navigation.navigate('Dashboard')
                    }}
                />
            </Drawer.Section>
            <DrawerItem
                label="Home"
                labelStyle={{ color: colorTheme.normalText }}
                icon={() => <Icon name="home" type="feather" size={26} color={colorTheme.normalText} />}
                activeBackgroundColor={colorTheme.panel}
                inactiveBackgroundColor={colorTheme.red}
                onPress={() => {
                    props.navigation.navigate('HomeStack')
                }}
            />
        </DrawerContentScrollView>
    );
}

export type DrawerParamList = {
    Dashboard: undefined;
    HomeStack: undefined;
};

export type DrawerProps<T extends keyof DrawerParamList> = {
    navigation: DrawerNavigationProp<DrawerParamList, T>;
    route: RouteProp<DrawerParamList, T>;
};

const AppDrawer = createDrawerNavigator<DrawerParamList>();

export default function MainDrawer({ route, navigation }: TopLevelStackProps<"MainDrawer">) {

    return (
        <AppDrawer.Navigator
            drawerStyle={globalStyles.drawer}
            drawerContent={
                (props) => <CustomDrawerContent {...props} />
            }
            drawerContentOptions={{
                labelStyle: { color: colorTheme.normalText },
                activeBackgroundColor: colorTheme.panel,
                inactiveBackgroundColor: colorTheme.background,
            }}
        >
            <AppDrawer.Screen
                name="Dashboard"
                component={Dashboard}
                options={{
                    unmountOnBlur: true,
                }}
            />
            <AppDrawer.Screen
                name="HomeStack"
                component={HomeStack}
                options={{
                    unmountOnBlur: true,
                }}
            />
        </AppDrawer.Navigator>
    );
}
like image 895
jdperos Avatar asked Aug 16 '20 02:08

jdperos


1 Answers

There's no focused prop which you can use to get the current focused route.

Instead, use the props that are received by the component by the DrawerNavigator. Check out this doc.

If you see the list of props passed to the drawerContent component, you can see the state prop. From the doc,

state - The navigation state of the navigator, state.routes contains list of all routes

So you can get the array of routes, and current index, which indicates which screen is currently focused. You can get the route name and compare it with the item name in your list.

const {state} = props
const {routes, index} = state; //Not sure about the name of index property. Do check it out by logging the 'state' variable.
const focusedRoute = routes[index];
   
like image 160
Nishant Nair Avatar answered Sep 25 '22 00:09

Nishant Nair