목표
- Flutter에서 애니메이션의 기본 개념.
- AnimatedContainer 위젯을 사용하여 간단한 애니메이션을 구현.
- Hero 위젯으로 화면 전환 트랜지션 효과 적용.
1.애니메이션의 기본 개념
Flutter에서는 애니메이션을 사용하여 UI를 더 역동적으로 만들 수 있습니다. Flutter는 프레임워크에 내장된 다양한 애니메이션 도구를 제공하며, 이를 통해 간단한 움직임부터 복잡한 트랜지션까지 구현할 수 있습니다.
Flutter 애니메이션 종류
1.1 암시적 애니메이션:
- AnimateContainer, AnimateOpacity 등 애니메이션이 포함된 위젯.
- 코드가 간단하고 구현이 쉽다.
1.2 명시적 애니메이션:
- AnimationController와 Tween을 사용하여 세부적으로 제어.
- 더 복잡한 애니메이션을 구현할 때 사용.
2. AnimatedContainer 위젯
AnimatedContainer는 상태 변화에 따라 부드러운 전환을 자동으로 처리합니다.
새로운 프로젝트 또는 이전 프로젝트의 소스코드를 다음과 같이 작성합니다.
import 'package:flutter/material.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(title: const Text('AnimatedContainer 예제')),
body: const AnimatedContainerExample(),
),
);
}
}
class AnimatedContainerExample extends StatefulWidget {
const AnimatedContainerExample({super.key});
@override
_AnimatedContainerExampleState createState() =>
_AnimatedContainerExampleState();
}
class _AnimatedContainerExampleState extends State<AnimatedContainerExample> {
bool _isLarge = false;
@override
Widget build(BuildContext) {
return Center(
child: Column(
children: [
AnimatedContainer(
width: _isLarge ? 200 : 100,
height: _isLarge ? 200 : 100,
color: _isLarge ? Colors.blue : Colors.red,
duration: const Duration(seconds: 1),
curve: Curves.easeInOut,
),
const SizedBox(height: 20),
ElevatedButton(
onPressed: () {
setState(() {
_isLarge = !_isLarge; //상태 변경
});
},
child: const Text('크기 및 색상 변경'),
),
],
),
);
}
}

결과
- 버튼 클릭 시 AnimatedContainer가 크기와 색상을 부드럽게 전한합니다.
- duration 속성으로 애니메이션의 시간을 설정합니다.
- curve 속성으로 애니메이션의 동작을 설정합니다.(예: Curves.easeInOut).
3. Hero 위젯
Hero 위제은 화면 전환 시 특정 위젯 간의 애니메이션을 제공합니다
3.1 MainPage에서 SecodPage로 전환하며 이미지 이동 효과를 구현해보겠습니다.
MainPage 코드를 다음과 같이 작성해보세요
import 'package:flutter/material.dart';
import 'SecondPage.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
return const MaterialApp(
home: MainPage(),
);
}
}
class MainPage extends StatelessWidget {
const MainPage({super.key});
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: const Text('Hero 애니메이션 예제')),
body: Center(
child: GestureDetector(
onTap: () {
Navigator.push(
context,
MaterialPageRoute(builder: (context) => const SecondPage()),
);
},
child: Hero(
tag: 'hero-image',
child: Container(
width: 150,
height: 150,
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(16),
image: const DecorationImage(
image: AssetImage('assets/images/sample_image.jpg'),
fit: BoxFit.cover,
),
),
),
),
),
),
);
}
}
SecondPage 소스코드
import 'package:flutter/material.dart';
class SecondPage extends StatelessWidget {
const SecondPage({super.key});
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: const Text('Second Page')),
body: Center(
child: Hero(
tag: 'hero-image',
child: Container(
width: 300,
height: 300,
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(16),
image: const DecorationImage(
image: AssetImage('assets/images/sample_image.jpg'),
fit: BoxFit.cover,
),
),
),
),
),
);
}
}

결과
- MainPage에서 이미지를 클릭하면 SecondPage로 이동하며 이미지가 부드럽게 확대됩니다.
- Hero 위젯의 tag 속성이 동일한 위젯 간에 애니메이션을 연결합니다.
4. 실습
1단계: 위치 이동 애니메이션 구현
- AnimatedContainer를 사용하여 버튼 클릭 시 사각형이 화면 왼쪽으로 이동하도록 구현하세요.
- 힌트
- AnimatedContainer의 aligment 속성을 변경합니다.
- 예: Aligment.center –> Aligment.centerLeft()
2단계: Hero 위젯 확장
- Hero 위젯을 사용하여 이미지뿐만 아니라 텍스트를 함께 이동시키도록 해보세요.
- 힌트:
- Column으로 이미지와 텍스트를 그룹화하고 Hero 위젯을 묶으세요.
- 두 패이지 모두 같은 Tag를 사용해야 애니메이션이 연결됩니다.
5. 결론
이번에는 Flutter에서 간단한 애니메이션을 구현하는 방법과 전환 트랜지션을 배웠습니다. 이를 통해 역동적인 효과를 추가할 수 있습니다. 다음 시간에는 Flutter 네트워킹 및 HTTP 요청 처리를 알아 보겠습니다.
감사합니다.
댓글 남기기