【问题标题】:Victory Native Pie Chart Animation胜利原生饼图动画
【发布时间】:2021-04-05 00:07:40
【问题描述】:

我正在尝试对 Victory Native 饼图中的数据变化进行动画处理。我在 ComponentDidMount 方法中设置的重复超时从 API 获取数据。检索到数据后,我将其设置为状态变量,该变量将传递给 VictoryPie 组件中的数据道具,并启用动画道具,如文档所示。

我关注articleVictory Chart docs for animations,但我的行为方式与这些示例不同。

目前它正确设置了数据,但没有任何流畅的动画。它立即从初始状态值跳转到获取的数据值。我看到动画的唯一时间是在上一次提取的值不为零之后提取的数据返回零值。

export default class HaloXPChart extends Component {
    constructor(props) {
        super(props);
        this.state = {
            gamertag: this.props.gamertag ? this.props.gamertag : '',
            dateRetrievalInterval: 1,
            totalXp: 0,
            startXp: 0,
            spartanRank: 0,
            xpChartData: [
                {x: 'xp earned', y: 0},
                {x: 'xp remaining', y: 1}
            ],
            loading: false
        };   
    }
       
    componentDidMount() {
        this.setState({loading: true});
        this.recursiveGetData();
    }

    async recursiveGetData(){
        this.setState({indicator: true}, async () => {
            await this.getData()
            this.setState({indicator: false});
            let timeout = setTimeout(() => {
                this.recursiveGetData();
            }, this.state.dateRetrievalInterval * 60 * 1000);
        });
    }
    
    async getData(){
        await Promise.all([
            fetch('https://www.haloapi.com/stats/h5/servicerecords/arena?players=' + this.state.gamertag, fetchInit),
            fetch('https://www.haloapi.com/metadata/h5/metadata/spartan-ranks', fetchInit)
        ])
        .then(([res1, res2]) => {
            return Promise.all([res1, res2.json()])
        }).then(([res1, res2) => {
            
            const xp = res1.Results[0].Result.Xp;
            const spartanRank = res1.Results[0].Result.SpartanRank;
            this.setState({totalXp: xp});

            const currentRank = res2.filter(r => r.id == this.state.spartanRank);
            this.setState({startXp: currentRank[0].startXp});

            this.setState({loading: false}, () => {
                this.setState({xpChartData: [
                    {x: 'xp earned', y: this.state.totalXp - this.state.startXp},
                    {x: 'xp remaining', y: 15000000 - (this.state.totalXp - this.state.startXp)}
                ]}); 
            });

        })
        .catch((error) => {
            console.log(JSON.stringify(error));
        })
    }

    render() {
        return(
            <View>
                <Svg viewBox="0 0 400 400" >
                    <VictoryPie
                        standalone={false}
                        width={400} height={400}
                        data={this.state.xpChartData}
                        animate={{ 
                            easing: 'exp',
                            duration: 2000
                        }}
                        innerRadius={120} labelRadius={100}
                        style={{                                                    
                             labels: { display: 'none'},
                             data: {
                                  fill: ({ datum }) =>
                                  datum.x === 'xp earned' ? '#00f2fe' : 'black'
                             }
                        }}
                    />
                </Svg>
            </View>
        );
    }
}

【问题讨论】:

    标签: react-native victory-charts victory-native


    【解决方案1】:

    尝试最初将endAngle 设置为0,然后在加载数据时将其设置为360,如this GitHub issue 中所述:

    注意:饼图会在其数据更改时动画。所以初始设置数据为空,延迟后设置实际数据。如果您的数据来自服务调用,它已经完成了。

    const PieChart = (props: Props) => {
    
      const [data, setData] = useState<Data[]>([]);
      const [endAngle, setEndAngle] = useState(0);
    
      useEffect(() => {
        setTimeout(() => {
          setData(props.pieData);
          setEndAngle(360);
        }, 100);
      }, []);
    
      return (
        <VictoryPie
          animate={{
            duration: 2000,
            easing: "bounce"
          }}
          endAngle={endAngle}
          colorScale={props.pieColors}
          data={data}
          height={height}
          innerRadius={100}
          labels={() => ""}
          name={"pie"}
          padding={0}
          radius={({ datum, index }) => index === selectedIndex ? 130 : 120}
          width={width}
       />
    )
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2020-03-25
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-01-02
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多