Flutter는 제스처와 물리 효과를 결합하여 실제와 유사한 상호작용을 구현할 수 있는 강력한 도구를 제공합니다.
이 글에서는 제스처와 물리 효과를 활용한 고급 사용자 인터랙션 기법을 소개합니다.
Flutter에서 물리 효과는 사용자가 화면에서 드래그, 스와이프 또는 플링(fling)과 같은 동작을 수행할 때 애니메이션에 물리 법칙(가속도, 마찰 등)을 적용하는 것입니다. 이를 통해 더욱 자연스러운 사용자 경험을 제공합니다.
카드를 드래그하면 물리 효과를 적용하여 자연스럽게 복귀하거나 이동합니다.
import 'package:flutter/material.dart';
import 'dart:math';
class DragWithPhysicsExample extends StatefulWidget {
@override
_DragWithPhysicsExampleState createState() => _DragWithPhysicsExampleState();
}
class _DragWithPhysicsExampleState extends State<DragWithPhysicsExample> with SingleTickerProviderStateMixin {
late AnimationController _controller;
late Animation<Offset> _animation;
Offset _position = Offset.zero;
@override
void initState() {
super.initState();
_controller = AnimationController(
vsync: this,
duration: Duration(milliseconds: 300),
);
_animation = Tween<Offset>(begin: Offset.zero, end: Offset.zero).animate(
CurvedAnimation(parent: _controller, curve: Curves.easeOut),
);
_controller.addListener(() {
setState(() {
_position = _animation.value;
});
});
}
void _onDragUpdate(DragUpdateDetails details) {
setState(() {
_position += Offset(details.delta.dx, details.delta.dy);
});
}
void _onDragEnd(DragEndDetails details) {
final velocity = details.velocity.pixelsPerSecond;
final magnitude = velocity.distance;
final direction = velocity / magnitude;
final distance = Offset(-_position.dx * direction.dx, -_position.dy * direction.dy);
_animation = Tween<Offset>(begin: _position, end: Offset.zero).animate(
CurvedAnimation(parent: _controller, curve: Curves.easeOut),
);
_controller.forward(from: 0.0);
}
@override
void dispose() {
_controller.dispose();
super.dispose();
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: Text('Drag with Physics')),
body: Center(
child: GestureDetector(
onPanUpdate: _onDragUpdate,
onPanEnd: _onDragEnd,
child: Transform.translate(
offset: _position,
child: Container(
width: 100,
height: 100,
color: Colors.blue,
),
),
),
),
);
}
}
플링(fling)은 사용자가 빠르게 스와이프했을 때 화면에서 위젯이 자연스럽게 이동하거나 멈추는 효과를 구현합니다.
class FlingWithPhysicsExample extends StatefulWidget {
@override
_FlingWithPhysicsExampleState createState() => _FlingWithPhysicsExampleState();
}
class _FlingWithPhysicsExampleState extends State<FlingWithPhysicsExample> with SingleTickerProviderStateMixin {
late AnimationController _controller;
late Animation<Offset> _animation;
Offset _position = Offset.zero;
@override
void initState() {
super.initState();
_controller = AnimationController(
vsync: this,
duration: Duration(milliseconds: 500),
);
_animation = Tween<Offset>(begin: Offset.zero, end: Offset.zero).animate(
CurvedAnimation(parent: _controller, curve: Curves.easeOut),
);
_controller.addListener(() {
setState(() {
_position = _animation.value;
});
});
}
void _onPanEnd(DragEndDetails details) {
final velocity = details.velocity.pixelsPerSecond;
final direction = velocity / velocity.distance;
_animation = Tween<Offset>(
begin: _position,
end: Offset(_position.dx + direction.dx * 100, _position.dy + direction.dy * 100),
).animate(
CurvedAnimation(parent: _controller, curve: Curves.easeOut),
);
_controller.forward(from: 0.0);
}
@override
void dispose() {
_controller.dispose();
super.dispose();
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: Text('Fling with Physics')),
body: Center(
child: GestureDetector(
onPanEnd: _onPanEnd,
child: Transform.translate(
offset: _position,
child: Container(
width: 100,
height: 100,
color: Colors.red,
),
),
),
),
);
}
}
Flutter에서 제스처와 물리 효과를 결합하면 실제와 유사한 사용자 경험을 제공할 수 있습니다. 이 글에서 소개한 예제를 바탕으로 다양한 사용자 인터랙션을 구현해 보세요. 다음 글에서는 물리 효과를 활용한 고급 게임 애니메이션을 다룰 예정입니다.
Flutter 네트워크 통신 기초: HTTP 요청 보내기 (0) | 2025.01.06 |
---|---|
물리 효과를 활용한 고급 애니메이션 구현 (1) | 2025.01.03 |
제스처와 애니메이션 결합하기 (0) | 2025.01.03 |
버튼 클릭 시 색상 변화 애니메이션 구현하기 (0) | 2025.01.03 |
Flutter 고급 애니메이션 패턴 (0) | 2025.01.02 |