Animatedを使ったアニメーションの中で、バネのように跳ねるようなアニメーションをするAnimated.spring()という面白いメソッドがあったので、この使い方を紹介する。
以前作ったサンプルアプリのコードを改変しながら実装していくので、以下の記事をまずは参照してほしい。
https://chusotsu-program.com/react-native-animated-loop
今回はニュース記事の読み込みが終わったら、記事リスト表示時にテキストを伸び縮みさせるアニメーションを実装する。
コンテンツ
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コマンドを実行し、出来上がったアニメーションを確認してみよう。
記事リストが読み込まれると、テキストが跳ねるようなアニメーションが実行される。