【问题标题】:React Native: How do you animate the rotation of an Image?React Native:如何为图像的旋转设置动画?
【发布时间】:2016-09-23 12:39:27
【问题描述】:

旋转是一种样式变换,在 RN 中,您可以像这样旋转东西

  render() {
    return (
      <View style={{transform:[{rotate: '10 deg'}]}}>
        <Image source={require('./logo.png')} />
      </View>
    );
  }

但是,要在 RN 中制作动画,您必须使用数字,而不是字符串。你还能在 RN 中为变换设置动画,还是我必须想出某种 sprite sheet 并以某些 fps 更改 Image src?

【问题讨论】:

    标签: javascript react-native animation rotation transform


    【解决方案1】:

    您实际上可以使用interpolate 方法为字符串设置动画。 interpolate 采用一系列值,通常 0 到 1 适用于大多数情况,并将它们插入到一系列值中(可以是字符串、数字,甚至是返回值的函数)。

    你要做的是获取一个现有的 Animated 值并将其传递给 interpolate 函数,如下所示:

    spinValue = new Animated.Value(0);
    
    // First set up animation 
    Animated.timing(
        this.spinValue,
      {
        toValue: 1,
        duration: 3000,
        easing: Easing.linear, // Easing is an additional import from react-native
        useNativeDriver: true  // To make use of native driver for performance
      }
    ).start()
    
    // Next, interpolate beginning and end values (in this case 0 and 1)
    const spin = this.spinValue.interpolate({
      inputRange: [0, 1],
      outputRange: ['0deg', '360deg']
    })
    

    然后像这样在你的组件中使用它:

    <Animated.Image
      style={{transform: [{rotate: spin}] }}
      source={{uri: 'somesource.png'}} />
    

    如果您想循环旋转,请在Animated.loop 中添加Animated.timing

    Animated.loop(
     Animated.timing(
       this.spinValue,
       {
        toValue: 1,
        duration: 3000,
        easing: Easing.linear,
        useNativeDriver: true
       }
     )
    ).start();
    

    【讨论】:

    • 不错!简单明了!另外,在您的 rnplay 示例中,您怎么知道 start() 可以进行回调?在 Facebook 的 RN 网站上似乎找不到该文档。
    • 啊,是的。我想我记得看到 browniefed (Jason Brown) 发布了一些关于它的内容。它确实需要一个回调,尽管在动画完成时会触发它。查看 github.com/browniefed/react-native-animation-bookrnplay.org/browniefed 。他用动画做了很多例子。我很高兴这有帮助:)
    • 记得this.state = { spinValue: new Animated.Value(0) }
    • 为此创建了一个示例要点:gist.github.com/levynir/5962de39879a0b8eb1a2fd77ccedb2d8
    • 请使用loop 使其无限循环Animated.loop( Animated.timing(this.spinValue, { toValue: 1, duration: 1000, easing: Easing.linear, useNativeDriver: true, }) ).start()
    【解决方案2】:

    不要忘记添加属性 useNativeDriver 以确保您从该动画中获得最佳性能:

    // First set up animation 
    Animated.timing(
        this.state.spinValue,
      {
        toValue: 1,
        duration: 3000,
        easing: Easing.linear,
        useNativeDriver: true
      }
    ).start();
    

    【讨论】:

      【解决方案3】:

      给像我这样的新手的注意事项: 要为其他内容设置动画,您需要将其包装在 中才能正常工作。否则编译器会对该转换属性产生恐慌:

      import {Animated} from 'react-native';
      ...
      //animation code above
      ...
      <Animated.View style={{transform: [{rotate: spin}] }} >
         <YourComponent />
      </Animated.View>
      

      但是对于图像 (Animated.Image),上面的示例是 100% 正确的。

      【讨论】:

        【解决方案4】:

        由于大多数答案都是基于functionshooks,这里有一个基于class 的图像动画的完整示例。

        import React from 'react';
        import {
          SafeAreaView,
          View,
          Animated,
          Easing,
          TouchableHighlight,
          Text,
        } from 'react-native';
        
        export default class App extends React.Component {
          constructor(props) {
            super(props);
            this.state = {
              rotateValueHolder: new Animated.Value(0)
            };
          }
          componentDidMount = () => {
            this.startImageRotateFunction();
          }
          startImageRotateFunction = () => {
            Animated.loop(Animated.timing(this.state.rotateValueHolder, {
              toValue: 1,
              duration: 3000,
              easing: Easing.linear,
              useNativeDriver: false,
            })).start();
          };
        
        render(){
            return(
              <SafeAreaView>
                <View>
                  <Animated.Image
                    style={{
                      width: 200,
                      height: 200,
                      alignSelf:"center",
                      transform:
                        [
                          {
                            rotate: this.state.rotateValueHolder.interpolate(
                                {
                                  inputRange: [0, 1],
                                  outputRange: ['0deg', '360deg'],
                                }
                              )
                          }
                        ],
                    }}
                      source={{uri:'https://raw.githubusercontent.com/AboutReact/sampleresource/master/old_logo.png',}}
                  />
                  <TouchableHighlight
                    onPress={() => this.startImageRotateFunction()}>
                    <Text style={{textAlign:"center"}}>
                      CLICK HERE
                    </Text>
                  </TouchableHighlight>
                </View>
              </SafeAreaView>
            );
          }
        }
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2020-01-19
          • 1970-01-01
          • 1970-01-01
          • 2022-08-19
          • 2016-04-29
          • 1970-01-01
          • 1970-01-01
          • 2017-10-08
          相关资源
          最近更新 更多