framer-motion について
ReactとTypeScriptでMotionアニメーションを実装するためのガイダンスです。性能、アクセシビリティ、スクロール連動効果、トランジションのパターンを扱います。
主な機能
- 01Motion APIの利用ガイダンス
- 02変形と不透明度の性能面の指針
- 03視覚効果を減らす設定への対応
- 04スクロール連動アニメーション
- 05退出・ページ遷移
活用シーン
- 01Reactインターフェースへのアニメーション追加
- 02スクロール連動効果の構築
- 03視覚効果を減らす設定への対応
- 04退出・ページ遷移の実装
インストール
コマンドをコピーしてターミナルで実行します。
$
npx skills add https:/ / github.com/ mindrally/ skills --skill framer-motionインストール後、Claude Code で/framer-motionを入力して読み込まれたか確認します。
詳細
Framer Motion / Motion アニメーションガイドライン
Framer Motion(現在の Motion)、React、TypeScript のエキスパートとして、アニメーションを作成する際は次のガイドラインに従ってください。
基本原則
正しいパッケージからインポートする
- React プロジェクトでは
import { motion } from "motion/react"を使用してください(古い形式の "framer-motion" は使用しないでください) - ライブラリの名称は Framer Motion から Motion に変更されました
- 常に最新の Motion API を使用してください
パフォーマンスを最優先する
- 最高のパフォーマンスを得るには、transform プロパティ(
x、y、scale、rotate)とopacityをアニメーションさせてください - これらのプロパティはハードウェアアクセラレーションを利用でき、レイアウトの再計算を引き起こしません
width、height、top、left、margin、paddingなど、レイアウトのずれを引き起こすプロパティのアニメーションは避けてください
ハードウェアアクセラレーション
will-change を適切に使用する
// When animating transforms
<motion.div
style={{ willChange: "transform" }}
animate={{ x: 100, y: 50, scale: 1.2 }}
/>
// When animating other GPU-accelerated properties
<motion.div
style={{ willChange: "opacity, transform" }}
animate={{ opacity: 0.5, x: 100 }}
/>
willChange に追加するプロパティ
transform- x、y、scale、rotate、skew に使用しますopacity- opacity アニメーションに使用しますfilter- blur、brightness などに使用しますclipPath- clip-path アニメーションに使用しますbackgroundColor- 背景色のトランジションに使用します
アニメーションのベストプラクティス
複雑なアニメーションには Variants を使用する
const containerVariants = {
hidden: { opacity: 0 },
visible: {
opacity: 1,
transition: {
staggerChildren: 0.1
}
}
};
const itemVariants = {
hidden: { y: 20, opacity: 0 },
visible: { y: 0, opacity: 1 }
};
共有要素のトランジションには layoutId を使用する
<motion.div layoutId="shared-element" />
spring アニメーションを優先する
// Springs feel more natural than duration-based animations
<motion.div
animate={{ x: 100 }}
transition={{ type: "spring", stiffness: 300, damping: 30 }}
/>
React との統合
パフォーマンスのためにメモ化する
// Memoize animation variants
const variants = useMemo(() => ({
hidden: { opacity: 0 },
visible: { opacity: 1 }
}), []);
// Memoize callbacks
const handleAnimationComplete = useCallback(() => {
// handler logic
}, []);
インラインのスタイルオブジェクトを避ける
// Bad - creates new object on every render
<motion.div style={{ willChange: "transform" }} />
// Good - define outside or memoize
const style = { willChange: "transform" };
<motion.div style={style} />
アクセシビリティ
動きを減らす設定を尊重する
import { useReducedMotion } from "motion/react";
function Component() {
const shouldReduceMotion = useReducedMotion();
return (
<motion.div
animate={{ x: shouldReduceMotion ? 0 : 100 }}
transition={{ duration: shouldReduceMotion ? 0 : 0.3 }}
/>
);
}
ジェスチャーアニメーション
ジェスチャー Props を正しく使用する
<motion.button
whileHover={{ scale: 1.05 }}
whileTap={{ scale: 0.95 }}
transition={{ type: "spring", stiffness: 400, damping: 17 }}
/>
スクロールアニメーション
スクロールに連動するアニメーションには useScroll を使用する
import { useScroll, useTransform, motion } from "motion/react";
function ParallaxComponent() {
const { scrollYProgress } = useScroll();
const y = useTransform(scrollYProgress, [0, 1], [0, -100]);
return <motion.div style={{ y }} />;
}
終了時のアニメーション
終了時のアニメーションには AnimatePresence を使用する
import { AnimatePresence, motion } from "motion/react";
<AnimatePresence mode="wait">
{isVisible && (
<motion.div
key="modal"
initial={{ opacity: 0 }}
animate={{ opacity: 1 }}
exit={{ opacity: 0 }}
/>
)}
</AnimatePresence>
よく使われるパターン
リスト項目を順番にずらして表示するアニメーション
<motion.ul
initial="hidden"
animate="visible"
variants={{
visible: { transition: { staggerChildren: 0.07 } }
}}
>
{items.map((item) => (
<motion.li
key={item.id}
variants={{
hidden: { opacity: 0, y: 20 },
visible: { opacity: 1, y: 0 }
}}
/>
))}
</motion.ul>
ページ遷移
const pageTransition = {
initial: { opacity: 0, x: -20 },
animate: { opacity: 1, x: 0 },
exit: { opacity: 0, x: 20 },
transition: { duration: 0.3 }
};
パフォーマンスのデバッグ
- React DevTools を使用して再レンダーを調べます
- Chrome DevTools の Performance タブを使用してアニメーションのカクつきを特定します
- 最低 60fps、高リフレッシュレートのディスプレイでは 120fps を目標にします
- 実機、特にミッドレンジの Android スマートフォンでテストします
コメント
Markdown 対応