React NativeでWallet風UIを実装する
この記事はレコチョク Advent Calendar 2021の10日目の記事となります。
レコチョク・ラボの松木です。
仕事では主にレコチョク・ラボの取り組みをサポートしたり検証のためのプロトタイプを作ったりしています。
2021年も残り少しですが、おうち時間で楽器を楽しむ方が増えたというデータもあり、今年から新しく楽器をはじめた方もいるのではないでしょうか。
私は以前からサンプリングというものに興味があったので、サンプラーとマイクを使った遊びをはじめました。
作ったもの
今回作ったものはReact Nativeアプリケーションで動作する以下のようなアニメーションになります。
https://snack.expo.dev/@y-matsuki/wallet-like-ui
解説
今回実装するUIは react-native-snap-carousel をベースに実装しています。
コンポーネントの利用方法は以下です。
const { height } = Dimensions.get('window');
return (
<Carousel
ref={carouselRef}
data={items}
renderItem={renderItem}
vertical={true}
enableSnap={false}
layout={'default'}
activeSlideAlignment={'start'}
inactiveSlideScale={1}
inactiveSlideOpacity={1}
sliderHeight={height}
itemHeight={54}
scrollInterpolator={scrollInterpolator}
slideInterpolatedStyle={animatedStyles}
useScrollView={true}
/>
);
今回の実装で重要なポイントを以下に列挙します。
その他の属性についてはドキュメントを参照ください。
名称 | 説明 |
---|---|
data | リストのデータ |
renderItem | データを元にReactコンポーネントを返す関数(今回はカードを返す) |
itemHeight | 今回はカードの高さ300に対して54を指定することで重なりを表現する |
scrollInterpolator | スクロール位置に応じた挙動をカスタマイズする |
slideInterpolatedStyle | スクロール位置に応じたスタイルをカスタマイズする |
ドキュメントを参考にスクロールした際の挙動のカスタマイズします。 scrollInterpolator
についてはほぼそのまま利用したため slideInterpolatedStyle
の話をします。
const animatedStyles = (
index: number,
animatedValue: Animated.Value,
carouselProps: CarouselProps<any>
): StyleProp<ViewStyle> => {
const cardHeight = Math.floor((width / 16) * 9);
return {
zIndex: carouselProps.data.length - index,
transform: [
{
translateY: animatedValue.interpolate({
inputRange: [-1, 0, 1, 2],
outputRange: [
-cardHeight * 0.2, // <- アクティブなカードの前のカード
0, // <- アクティブなカード(今回は一番上のカード)
cardHeight * 1, // <- アクティブなカードの次のカード
cardHeight * 1.2, // <- アクティブなカードの次の次のカード
],
}),
},
],
};
};
animatedValue.interpolate() 関数を用いてスクロール時のスタイルの挙動アニメーションを定義します。 inputRange
がリスト内でのカードの位置を表しており outputRange
がそれに対応するカードのスタイルを表します。
ちなみに outputRange
を全て 0
にすると以下のようになります。(itemHeight = 54のため高さ54のリストとして描画される)
transform.translateY
は コンポーネントのY座標の位置を移動する ことを表しており cardHeight * 1.2
は カードの高さの1.2倍の長さ(画面下部に)移動する という意味になります。
アクティブなカードの前後を少しずつ上下に移動させてあげることで、アクティブなカードにアクセントを付けたUIを作ることができます。
また、 zIndex
を以下のよう指定すると、カードの重なり順を逆にできます。
zIndex: carouselProps.data.length - index
まとめ
iOSだとヌルヌル動くのですがAndroidの場合はshadowが効かなかったり動きが硬い感じでややイマイチでした。
今回の実装方法だとカードの枚数が多いとメモリを食うので、RecyclerView的な実装に改善するとより実用的と思います。
明日のレコチョク Advent Calendar 2021は11日目「家計簿のデータをNode.jsでスプレッドシート連携してみた」です。お楽しみに!!
この記事はレコチョクのエンジニアブログの記事を転載したものとなります。
Author And Source
この問題について(React NativeでWallet風UIを実装する), 我々は、より多くの情報をここで見つけました https://qiita.com/y-matsuki/items/0f90d520fdccf00c9ba8著者帰属:元の著者の情報は、元のURLに含まれています。著作権は原作者に属する。
Content is automatically searched and collected through network algorithms . If there is a violation . Please contact us . We will adjust (correct author information ,or delete content ) as soon as possible .