Рецепт кода флаттера для анимации героев
Анимация героя — полезный переход, когда элементы перечислены с маленькими значками. При нажатии на значки можно открыть другую страницу с увеличенным виджетом значков.
Рецепт: Анимация героя для преобразования значка списка в увеличенное изображение на другой странице сведений.
Виджет фокуса: Виджет героя
Hero(
tag: 'hero-rectangle',
child: _blueDetailRectangle(),
),
Цель: Анимируйте и увеличьте значок элемента списка, используя Hero
виджет. При нажатии на значок элемента списка открывается элемент на другой странице с увеличенным значком.
Анимация героя при оформлении заказа
Поехали!
Эти вещи нужны нам для достижения нашей цели.
- Элемент списка вместе со значком: я буду использовать прямоугольный виджет для значка.
Виджет значка в элементе списка на первой странице:
Widget _blueIconRectangle() {
return Container(
width: 50,
height: 50,
color: Colors.blue,
);
}
Hero
виджет в списке:
Widget buildWidget(BuildContext context) {
return Center(
...
child: Hero(
tag: 'hero-rectangle',
child: _blueIconRectangle(),
),
onTap: () => _gotoDetailsPage(context),
...
}
- Увеличенный значок для отображения на второй странице.
Widget _blueDetailRectangle() {
return Container(
width: 200,
height: 200,
color: Colors.blue,
);
}
Использование увеличенного значка на второй странице:
void _gotoDetailsPage(BuildContext context) {
Navigator.of(context).push(MaterialPageRoute(
builder: (ctx) => Scaffold(
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Hero(
tag: 'hero-rectangle',
child: _blueDetailRectangle(),
),
Text(
'This is where you can see details about the list item tapped at previous page.'),
],
),
),
),
));
}
Заметь Navigator.of(context).push()
необходим для перехода на вторую страницу с первой страницы
используя один и тот же тег.
- Убедитесь, что оба виджета на шаге № 1 и шаге № 2 иметь тот же тег.
Переходы героев используют один и тот же тег для идентификации начального и конечного виджетов.
Полный пример кода
import 'package:flutter/material.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
// This widget is the root of your application.
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.green,
),
home: HeroAnimationRecipe(title: 'Hero Animation'),
);
}
}
class HeroAnimationRecipe extends StatefulWidget {
HeroAnimationRecipe({Key key, this.title}) : super(key: key);
final String title;
@override
_HeroAnimationRecipeState createState() => _HeroAnimationRecipeState();
}
class _HeroAnimationRecipeState extends State<HeroAnimationRecipe> {
Widget _blueIconRectangle() {
return Container(
width: 50,
height: 50,
color: Colors.blue,
);
}
Widget _blueDetailRectangle() {
return Container(
width: 200,
height: 200,
color: Colors.blue,
);
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(widget.title),
),
body: buildDemoWidget(context),
);
}
Widget buildDemoWidget(BuildContext context) {
return Center(
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
SizedBox(
height: 20.0,
),
ListTile(
leading: GestureDetector(
child: Hero(
tag: 'hero-rectangle',
child: _blueIconRectangle(),
),
onTap: () => _gotoDetailsPage(context),
),
title: Text('Tap on the icon to view hero animation transition.'),
),
],
),
);
}
void _gotoDetailsPage(BuildContext context) {
Navigator.of(context).push(MaterialPageRoute(
builder: (ctx) => Scaffold(
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Hero(
tag: 'hero-rectangle',
child: _blueDetailRectangle(),
),
Text(
'This is where you can see details about the list item tapped at previous page.'),
],
),
),
),
));
}
}
Репозиторий исходного кода:
Исходный код рецепта доступен здесь
Использованная литература:
Понравилась статья? Пожалуйста, дайте мне знать в комментариях ниже, какие еще темы вы хотели бы, чтобы я написал.