Animatedを使ったアニメーションの中で、バネのように跳ねるようなアニメーションをするAnimated.spring()という面白いメソッドがあったので、この使い方を紹介する。
以前作ったサンプルアプリのコードを改変しながら実装していくので、以下の記事をまずは参照してほしい。
https://chusotsu-program.com/react-native-animated-loop
今回はニュース記事の読み込みが終わったら、記事リスト表示時にテキストを伸び縮みさせるアニメーションを実装する。
Contents
TextをAnimated.Textに置き換える
テキストに対しアニメーションを適用させるので、まずはTextをAnimated.Textに置き換える。
<Animated.Text> {item.data.title} </Animated.Text>
state変数の定義
次にコンストラクタ内でフォントサイズを管理するstate変数を定義する。
constructor() { super(); this.state = { isLoading: true, threads: [], opacity: new Animated.Value(0), fontSize: new Animated.Value(0), } }
Animated.spring()を実装
animate()メソッド内にAnimated.spring()の処理を書いていく。
animate() { Animated.timing(this.state.opacity, { toValue: 1, duration: 1000, }).start(); Animated.spring(this.state.fontSize, { toValue: 1, friction: 1, }).start(); }
frictionに設定する値はここでは1としているが、0.1など小さい値を設定するとより大きく跳ねるアニメーションとなる。
renderメソッドの変更
最後にrenderメソッド内のコードを以下のとおり書き換える。
render() { const { threads, isLoading, opacity, fontSize } = this.state; const { width } = Dimensions.get('window'); const _fontSize = fontSize.interpolate({ inputRange: [0, 1], outputRange: [0, 12] }) if(!isLoading) this.animate(); return( <View style={{ flex: 1, justifyContent: 'center', alignItems: 'center', }}> {isLoading ? <Spining /> : <Animated.View style={{ opacity: opacity}}> <FlatList data={threads} renderItem={({item}) => { return( <View style={{ flex: 1, flexDirection: 'row', width: '100%' }}> <Image style={{ width: 50, height: 50 }} source={item.data.thumbnail} /> <View style={{ flex: 1, flexDirection: 'column' }}> <Animated.Text style={{fontSize: _fontSize}}>{item.data.title}</Animated.Text> <Text style={{color: '#ababab', fontSize: 10}}>{item.data.domain}</Text> </View> </View> ) }} /> </Animated.View> } </View> ) }
4行目でinterpolateを使用し、フォントサイズをアニメーション用に変換させているところがポイントだ。
この処理を行うことで、アニメーション開始時はフォントサイズが0、終了時に12となる。
アニメーションの確認
それではexpo startコマンドを実行し、出来上がったアニメーションを確認してみよう。
記事リストが読み込まれると、テキストが跳ねるようなアニメーションが実行される。