react-native-ratings icon indicating copy to clipboard operation
react-native-ratings copied to clipboard

Warning: Star: Support for defaultProps (my fix)

Open Olowoyo opened this issue 10 months ago • 2 comments

//update your dist/components/star.js component with code below... import React, { useState } from "react"; import { StyleSheet, Animated, TouchableOpacity } from "react-native"; const STAR_IMAGE = require("../images/airbnb-star.png"); const STAR_SELECTED_IMAGE = require("../images/airbnb-star-selected.png"); const STAR_SIZE = 40; const Star = ({ starImage= STAR_IMAGE, selectedColor= "#f1c40f", unSelectedColor= "#BDC3C7",...props}) => { const [selected, setSelected] = useState(false); const springValue = new Animated.Value(1); const spring = () => { const { position, starSelectedInPosition } = props; springValue.setValue(1.2); Animated.spring(springValue, { toValue: 1, friction: 2, tension: 1, useNativeDriver: true }).start(); setSelected(!selected); starSelectedInPosition(position); }; const { fill, size, isDisabled, starStyle } = props; const starSource = fill && selectedColor === null ? STAR_SELECTED_IMAGE : starImage; return (<TouchableOpacity activeOpacity={1} onPress={spring} disabled={isDisabled}> <Animated.Image source={starSource} style={[ styles.starStyle, { tintColor: fill && selectedColor ? selectedColor : unSelectedColor, width: size || STAR_SIZE, height: size || STAR_SIZE, transform: [{ scale: springValue }] }, starStyle ]}/> </TouchableOpacity>); }; export default Star; const styles = StyleSheet.create({ starStyle: { margin: 3 } });

//update your src/star.tsx component with code below... import React, { useState } from "react"; import { StyleSheet, Animated, TouchableOpacity, StyleProp, ViewStyle } from "react-native";

const STAR_IMAGE = require( "../images/airbnb-star.png" ); const STAR_SELECTED_IMAGE = require( "../images/airbnb-star-selected.png" ); const STAR_SIZE = 40;

export type StarProps = { starImage?: string; fill?: boolean; size?: number; selectedColor?: string; unSelectedColor?: string; isDisabled?: boolean; starStyle?: StyleProp<ViewStyle>; position?: number; starSelectedInPosition?: ( number ) => void; };

const Star: React.FunctionComponent<StarProps> = ({ starImage= STAR_IMAGE, selectedColor= "#f1c40f", unSelectedColor= "#BDC3C7",...props}) => { const [selected, setSelected] = useState( false ); const springValue = new Animated.Value( 1 );

const spring = () => { const { position, starSelectedInPosition } = props;

springValue.setValue( 1.2 );

Animated.spring( springValue, {
  toValue: 1,
  friction: 2,
  tension: 1,
  useNativeDriver: true
} ).start();

setSelected( !selected );

starSelectedInPosition( position );

};

const { fill, size, isDisabled, starStyle } = props;

const starSource = fill && selectedColor === null ? STAR_SELECTED_IMAGE : starImage;

return ( <TouchableOpacity activeOpacity={1} onPress={spring} disabled={isDisabled}> <Animated.Image source={starSource} style={[ styles.starStyle, { tintColor: fill && selectedColor ? selectedColor : unSelectedColor, width: size || STAR_SIZE, height: size || STAR_SIZE, transform: [{ scale: springValue }] }, starStyle ]} /> </TouchableOpacity> ); };

export default Star;

const styles = StyleSheet.create( { starStyle: { margin: 3 } } );

//update your src/TapRating.tsx component with code below... import _ from "lodash";

import React, { useState, useEffect } from "react";

import { StyleSheet, Text, View, StyleProp, ViewStyle } from "react-native";

import Star from "./components/Star";

export type TapRatingProps = {

/**

  • Total number of ratings to display
  • Default is 5 */ count?: number;

/**

  • Labels to show when each value is tapped
  • e.g. If the first star is tapped, then value in index 0 will be used as the label
  • Default is ['Terrible', 'Bad', 'Okay', 'Good', 'Great'] */ reviews?: string[];

/**

  • Determines if to show the reviews above the rating
  • Default is true */ showRating?: boolean;

/**

  • Color value for review.
  • Default is #f1c40f */ reviewColor?: string;

/**

  • Size value for review.
  • Default is 40 */ reviewSize?: number;

/**

  • Initial value for the rating
  • Default is 3 */ defaultRating?: number;

/**

  • Style for star container
  • Default is none */ starContainerStyle?: StyleProp<ViewStyle>;

/**

  • Style for rating container
  • Default is none */ ratingContainerStyle?: StyleProp<ViewStyle>;

/**

  • Callback method when the user finishes rating. Gives you the final rating value as a whole number */ onFinishRating?: ( number ) => void;

/**

  • Whether the rating can be modiefied by the user
  • Default is false */ isDisabled?: boolean;

/**

  • Color value for filled stars.
  • Default is #004666 */ selectedColor?: string;

/**

  • Size of rating image
  • Default is 40 */ size?: number;

/**

  • Pass in a custom base image source */ starImage?: string; };

const TapRating: React.FunctionComponent<TapRatingProps> = ({ defaultRating=3, reviews= ["Terrible", "Bad", "Okay", "Good", "Great"], count= 5, showRating= true, reviewColor= "rgba(230, 196, 46, 1)", reviewSize= 25,...props}) => { const [position, setPosition] = useState(defaultRating );

useEffect( () => {

if ( defaultRating === null || defaultRating === undefined ) {
  setPosition( 3 );
} else {
  setPosition( defaultRating );
}

}, [defaultRating] );

const renderStars = rating_array => { return _.map( rating_array, star => { return star; } ); };

const starSelectedInPosition = position => { const { onFinishRating } = props;

if ( typeof onFinishRating === "function" ) {
  onFinishRating( position );
}

setPosition( position );

};

const rating_array = []; const starContainerStyle = [styles.starContainer];

if ( props.starContainerStyle ) { starContainerStyle.push( props.starContainerStyle ); }

const ratingContainerStyle = [styles.ratingContainer];

if ( props.ratingContainerStyle ) { ratingContainerStyle.push( props.ratingContainerStyle ); }

_.times( count, index => { rating_array.push( <Star key={index} position={index + 1} starSelectedInPosition={value => { starSelectedInPosition( value ); }} fill={position >= index + 1} {...props} /> ); } );

return ( <View style={ratingContainerStyle}> {showRating && <Text style={[ styles.reviewText, { fontSize: reviewSize, color: reviewColor } ]} > {reviews[position - 1]} </Text> } <View style={starContainerStyle}>{renderStars( rating_array )}</View> </View> ); };

const styles = StyleSheet.create( { ratingContainer: { backgroundColor: "transparent", flexDirection: "column", alignItems: "center", justifyContent: "center" }, reviewText: { fontWeight: "bold", margin: 10 }, starContainer: { flexDirection: "row", alignItems: "center", justifyContent: "center" } } );

export default TapRating;

//update your dist/TapRating.js component with code below... import _ from "lodash"; import React, { useState, useEffect } from "react"; import { StyleSheet, Text, View } from "react-native"; import Star from "./components/Star"; const TapRating = ({ defaultRating=3, reviews= ["Terrible", "Bad", "Okay", "Good", "Great"], count= 5, showRating= true, reviewColor= "rgba(230, 196, 46, 1)", reviewSize= 25,...props}) => { const [position, setPosition] = useState(defaultRating); useEffect(() => { if (defaultRating === null || defaultRating === undefined) { setPosition(3); } else { setPosition(defaultRating); } }, [defaultRating]); const renderStars = rating_array => { return _.map(rating_array, star => { return star; }); }; const starSelectedInPosition = position => { const { onFinishRating } = props; if (typeof onFinishRating === "function") { onFinishRating(position); } setPosition(position); };

const rating_array = [];
const starContainerStyle = [styles.starContainer];
if (props.starContainerStyle) {
    starContainerStyle.push(props.starContainerStyle);
}
const ratingContainerStyle = [styles.ratingContainer];
if (props.ratingContainerStyle) {
    ratingContainerStyle.push(props.ratingContainerStyle);
}
_.times(count, index => {
    rating_array.push(<Star key={index} position={index + 1} starSelectedInPosition={value => {
            starSelectedInPosition(value);
        }} fill={position >= index + 1} {...props}/>);
});
return (<View style={ratingContainerStyle}>
  {showRating &&
        <Text style={[
                styles.reviewText,
                { fontSize: reviewSize, color: reviewColor }
            ]}>
      {reviews[position - 1]}
    </Text>}
  <View style={starContainerStyle}>{renderStars(rating_array)}</View>
</View>);

};

const styles = StyleSheet.create({ ratingContainer: { backgroundColor: "transparent", flexDirection: "column", alignItems: "center", justifyContent: "center" }, reviewText: { fontWeight: "bold", margin: 10 }, starContainer: { flexDirection: "row", alignItems: "center", justifyContent: "center" } }); export default TapRating;

Olowoyo avatar Jan 24 '25 10:01 Olowoyo

Warning: TapRating: Support for defaultProps will be removed from function components in a future major release. Use JavaScript default parameters instead.

facing this issue.

TheNoShade avatar Mar 02 '25 10:03 TheNoShade

Hii, @TheNoShade it looks like this library is no longer maintained and some older PR are not merged so it's very likely not going to be fixed in near future.

I have forked this library and fixed some issues which includes this issue, if you like use this library instead @rn-vui/ratings, you only need to install this library and change imports from react-native-ratings to @rn-vui/ratings and everything will work.

this library is released just now so if you face or encounter any issue feel free to create one at react-native-vikalp-ratings.

deepktp avatar May 05 '25 13:05 deepktp