/* eslint-disable react-native/no-unused-styles */ import * as React from "react"; import * as R from "ramda"; import { FlatList, Platform, StyleSheet, View } from "react-native"; import { Gutter } from "./Gutter"; import Tab from "./Tab"; import { getOpacityFromHexColor } from "@applicaster/zapp-react-native-utils/configurationUtils"; import { useIsRTL } from "@applicaster/zapp-react-native-utils/localizationUtils"; import { useConfiguration } from "@applicaster/zapp-react-native-utils/reactHooks/configuration"; type RenderItemProps = { item: ZappEntry; index: number; }; type FlexAlignment = "flex-start" | "center" | "flex-end"; const CUSTOM_KEY = "other"; const getTabsFlexAlignment = (tabsAlignment: string): FlexAlignment => { switch (tabsAlignment) { case "left": return "flex-start"; case "center": return "center"; case "right": return "flex-end"; default: return "flex-start"; } }; const getStyles = ({ tab_bar_background_color, tab_bar_border_bottom_width, tab_bar_border_bottom_color, tab_bar_padding_left, tab_bar_padding_right, tab_bar_elevation, display_mode_tabs_alignment, tab_bar_shadow_color, tab_bar_shadow_offset_height, tab_bar_shadow_offset_width, tab_bar_shadow_radius, }) => { const iosStyles = { shadowColor: tab_bar_shadow_color, shadowOffset: { height: tab_bar_shadow_offset_height, width: tab_bar_shadow_offset_width, }, shadowOpacity: getOpacityFromHexColor(tab_bar_shadow_color), shadowRadius: tab_bar_shadow_radius, zIndex: 10, }; const androidStyles = { elevation: tab_bar_elevation }; return StyleSheet.create({ container: { backgroundColor: tab_bar_background_color, borderBottomWidth: tab_bar_border_bottom_width, borderBottomColor: tab_bar_border_bottom_color, ...(Platform.OS === "ios" ? iosStyles : androidStyles), }, contentContainer: { flexGrow: 1, justifyContent: getTabsFlexAlignment(display_mode_tabs_alignment), paddingLeft: tab_bar_padding_left, paddingRight: tab_bar_padding_right, }, fractionalWrapper: { flexDirection: "row", paddingLeft: tab_bar_padding_left, paddingRight: tab_bar_padding_right, }, }); }; type Props = { tabs: [ZappEntry]; activeTab: ZappEntry; setActiveTab: (ZappEntry) => void; onTabsSelectorLayout: (number) => void; }; const TabsComponent = ({ tabs, activeTab, setActiveTab, onTabsSelectorLayout, }: Props) => { const isRTL = useIsRTL(); const configuration = useConfiguration(); const scrollViewRef = React.useRef(null); const tabRefs = React.useRef([]); const { tab_bar_gutter, display_mode, text_label_data_key, text_label_custom_data_key, } = configuration; const styles = React.useMemo(() => getStyles(configuration), []); const scrollToItem = React.useCallback( (index) => { scrollViewRef.current.scrollToIndex({ index: Platform.select({ ios: isRTL ? tabs?.length - index - 1 : index, android: index, }), viewPosition: 0.5, viewOffset: tab_bar_gutter / 2, }); }, [tabs, tab_bar_gutter] ); const onTabPress = React.useCallback( (item, index) => { setActiveTab(item); if (display_mode === "dynamic" || display_mode === "fixed") { scrollToItem(index); } }, [display_mode, scrollToItem, setActiveTab] ); const getTitle = React.useCallback( (item: ZappEntry): string => { const titlePath = R.split( ".", text_label_data_key === CUSTOM_KEY ? text_label_custom_data_key : text_label_data_key ); return R.path(titlePath, item); }, [text_label_data_key, text_label_custom_data_key] ); const getSelectedItem = React.useCallback( (id) => { return R.propEq("id", id)(activeTab); }, [activeTab] ); const renderGutter = React.useCallback( () => , [tab_bar_gutter] ); const renderItem = React.useCallback( ({ item, index, item: { id } }: RenderItemProps) => ( { tabRefs.current[index] = ref; }} {...{ title: getTitle(item), id, handleOnPress: () => { onTabPress(item, index); }, selected: getSelectedItem(id), configuration, }} /> {display_mode === "fractional" && index !== tabs?.length - 1 && renderGutter()} ), [tabs, display_mode, configuration, onTabPress, getTitle, getSelectedItem] ); const keyExtractor = React.useCallback(R.compose(String, R.prop("id")), []); if (display_mode === "fractional") { return ( {tabs?.map((item, index) => renderItem({ item, index }))} ); } return ( ); }; export const Tabs = React.memo(TabsComponent);