Search code examples
javascriptreactjstypescriptreact-nativereact-native-stylesheet

How to solve ViewStyle typescript error in react native?


I'm trying to pass width parameter into StyleSheet like this :

      <View style={styles.children(width)}>{children}</View>

And use it like this :

 
const styles = StyleSheet.create({
  modalContent: {
    flex: 1,
    justifyContent: 'center',
    margin: '5%',
  },
  modalOverlay: {
    position: 'absolute',
    top: 0,
    bottom: 0,
    left: 0,
    right: 0,
    backgroundColor: 'rgba(0,0,0,0.5)',
  },
  children: (width: any) => ({
    width: width,
    backgroundColor: 'white',
    position: 'absolute',
    bottom: 0,
    borderTopRightRadius: 40,
    borderTopLeftRadius: 40,
    paddingVertical: 30,
    paddingHorizontal: 20,
  }),
});
,

But typescript throws an error This expression is not callable. No constituent of type 'ViewStyle | TextStyle | ImageStyle' is callable.

screenshot

How can I solve this typescript problem ?


Solution

  • I solved the issue implementing it in another way with typescript :

    import React, { FC } from "react";
    import {
      ActivityIndicator,
      StyleSheet,
      TextStyle,
      TouchableOpacity,
      ViewStyle,
      Platform,
    } from "react-native";
    import { colors } from "../../styles";
    import { fonts } from "../../styles";
    import Text from "./Text";
    
    interface ButtonProps {
      style?: ViewStyle;
      disabled?: boolean | undefined;
      onPress?: any;
      text?: string;
      bordered?: boolean;
      textStyle?: TextStyle;
      loading?: boolean;
    }
    
    const Button: FC<ButtonProps> = ({
      style,
      disabled,
      onPress,
      text,
      bordered,
      textStyle,
      loading,
    }) => {
      const { OS } = Platform;
      return (
        <TouchableOpacity
          activeOpacity={0.6}
          disabled={disabled || false}
          onPress={onPress}
          style={{ ...styles({ disabled, bordered, OS }).button, ...style }}
        >
          <Text
            style={{ ...styles({ disabled, bordered }).buttonText, ...textStyle }}
          >
            {loading ? <ActivityIndicator color="white" size={30} /> : text}
          </Text>
        </TouchableOpacity>
      );
    };
    
    export default Button;
    
    interface StylesProps {
      bordered?: boolean;
      disabled?: boolean;
      OS?: string;
    }
    
    interface StyleSheetType {
      button: ViewStyle;
      buttonText: TextStyle;
    }
    
    type StylesFunctionProps = (props: StylesProps) => StyleSheetType;
    
    const styles: StylesFunctionProps = ({ bordered, disabled, OS }) =>
      StyleSheet.create<StyleSheetType>({
        button: {
          borderRadius: OS === "ios" ? 17 : 20,
          backgroundColor: disabled ? colors.gray : bordered ? "white" : colors.red,
          paddingVertical: 15,
          alignItems: "center",
          borderWidth: bordered && !disabled ? 1 : 0,
          borderColor: colors.red,
        },
        buttonText: {
          fontSize: 20,
          // fontFamily: fonts.regular, // light
          color: bordered && !disabled ? colors.red : "white",
        },
      });