繁体   English   中英

如何制作带有动画的自定义单选按钮? 反应本机

[英]How to make a custom Radio Button with animation? React Native

我在 React Native 中制作了一个自定义的单选按钮。 下面是我的代码的链接。

https://gist.github.com/shubh007-dev/0d8a0ca4d6f7d1530f3e28d223f9199e

我想要的是在按下单选按钮时为其设置动画,就像在这个库中所做的一样 - https://www.npmjs.com/package/react-native-simple-radio-button

我第一次能够为我的单选按钮设置动画,但是当我按下另一个单选按钮时,动画不会发生。

(此问题的另一种方法)如何确保每个单选按钮的动画值都不同?

您要么必须为收音机制作自定义组件,要么为 x 单选按钮使用 x 动画变量。

现在,为 x 按钮设置 x 变量并不是一个有效的解决方案,但如果您只有几个按钮,则可以使用它。

您制作了一个呈现平面列表的自定义组件,这就是问题所在; 不能在用于渲染它们的同一组件中单独为按钮设置动画。

您应该拆分代码并使单选按钮本身成为一个组件。 类似的东西(没有测试它,但它应该可以工作):

export class RadioButton extends Component {
  constructor(props) {
    super(props);
    this.state = {
      radioSelected: this.props.selectedItemId,
    };
  }

  radioClick = id => {
    this.setState({ radioSelected: id });
    this.props.onChange(id);
  }

  renderRadioButton = item => {
    const { radioSelected } = this.state;
    const { labelLeftStyle, labelRightStyle, labelOnRight } = this.props;
    return (
      <AnimatedRadio
        {...item}
        isSelected={item.id === radioSelected}
        labelLeftStyle={labelLeftStyle}
        labelRightStyle={labelRightStyle}
        labelOnRight={labelOnRight}
        radioClick={this.radioClick}
      />
    );
  };

  render() {
    return (
      <FlatList
        data={this.props.radioOptions}
        extraData={this.state}
        renderItem={({ item }) => this.renderRadioButton(item)}
        keyExtractor={(item, index) => index.toString()}
      />
    );
  }
}

export class AnimatedRadio extends Component {
  springValue = new Animated.Value(1.1);

  onRadioClick = id => () => {
    const { radioClick } = this.props;
    radioClick(id);
    this.spring();
  };

  spring = () => {
    Animated.spring(this.springValue, {
      toValue: 0.95,
      friction: 2,
      tension: 15,
    }).start();
  };

  render() {
    const {
      id,
      label,
      labelLeftStyle,
      labelRightStyle,
      labelOnRight,
      isSelected,
    } = this.props;
    return (
      <View key={id} style={STYLES.radioContainerView}>
        <TouchableOpacity
          style={STYLES.radioButtonDirectionStyle}
          onPress={this.onRadioClick(id)}
        >
          {labelOnLeft == true ? (
            <Text style={[labelLeftStyle]}>{label}</Text>
          ) : null}

          <View
            style={[isSelected ? STYLES.selectedView : STYLES.unselectedView]}
          >
            {isSelected ? (
              <Animated.View
                style={[
                  STYLES.radioSelected,
                  { transform: [{ scale: this.springValue }] },
                ]}
              />
            ) : null}
          </View>

          {labelOnRight == true ? (
            <Text style={[labelRightStyle]}>{label}</Text>
          ) : null}
        </TouchableOpacity>
      </View>
    );
  }
}

这样每个组件收音机都有自己的动画值,并且不会干扰其他按钮。

我使用LayoutAnimation如下所示。

LayoutAnimation.configureNext({
              duration: 300,
              create: {
                type: 'linear',
                property: 'scaleXY',
              },
              update: {
                type: 'spring',
                springDamping: 0.4,
                property: 'opacity',
              },
              delete: {
                type: 'easeOut',
                property: 'opacity',
              },
            });

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM