Как сохранить анимацию при переходе на новую страницу?

В Flutter существует несколько способов сохранить анимацию при переходе на новую страницу. Один из таких способов - использование Hero-анимации. Hero-анимация позволяет анимировать переход между виджетами на разных страницах.

Для сохранения анимации сначала необходимо определить виджет, который будет анимирован при переходе на новую страницу, и указать совпадающий Hero-тег в виджете на новой странице. Hero-тег - это строковый идентификатор, который используется для связывания виджетов между разными страницами.

Пример реализации Hero-анимации:

1. Создайте виджет главной страницы:

class HomePage extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Center(
        child: Hero(
          tag: 'logo',
          child: Container(
            width: 100,
            height: 100,
            color: Colors.blue,
          ),
        ),
      ),
      floatingActionButton: FloatingActionButton(
        onPressed: () {
          Navigator.push(
            context,
            MaterialPageRoute(
              builder: (context) => DetailPage(),
            ),
          );
        },
        child: Icon(Icons.arrow_forward),
      ),
    );
  }
}

2. Создайте виджет детальной страницы:

class DetailPage extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Center(
        child: Hero(
          tag: 'logo',
          child: Container(
            width: 200,
            height: 200,
            color: Colors.blue,
          ),
        ),
      ),
      floatingActionButton: FloatingActionButton(
        onPressed: () {
          Navigator.pop(context);
        },
        child: Icon(Icons.arrow_back),
      ),
    );
  }
}

В приведенном примере виджеты на обеих страницах имеют один и тот же Hero-тег 'logo'. При переходе со страницы HomePage на страницу DetailPage Flutter будет анимировать изменение размера и положения виджета с тегом 'logo'.

Еще одним способом сохранения анимации при переходе на новую страницу является использование пакета animated_size_and_fade. Этот пакет предоставляет виджеты, которые позволяют анимировать переходы между разными размерами и прозрачностями виджетов.

Например, можно использовать виджет AnimatedSize для анимации изменения размера виджета при переходе на новую страницу, а виджет AnimatedOpacity - для анимации изменения прозрачности. Оба этих виджета можно обернуть в Stack, чтобы объединить анимации.

Пример реализации с использованием animated_size_and_fade пакета:

class HomePage extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Center(
        child: GestureDetector(
          onTap: () {
            Navigator.push(
              context,
              MaterialPageRoute(
                builder: (context) => DetailPage(),
              ),
            );
          },
          child: Container(
            width: 100,
            height: 100,
            color: Colors.blue,
          ),
        ),
      ),
    );
  }
}

class DetailPage extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Center(
        child: Stack(
          children: [
            AnimatedOpacity(
              opacity: 0.0,
              duration: Duration(milliseconds: 500),
              child: AnimatedSize(
                vsync: this,
                duration: Duration(milliseconds: 500),
                curve: Curves.easeInOut,
                child: Container(
                  width: 200,
                  height: 200,
                  color: Colors.blue,
                ),
              ),
            ),
            AnimatedOpacity(
              opacity: 1.0,
              duration: Duration(milliseconds: 500),
              child: AnimatedSize(
                vsync: this,
                duration: Duration(milliseconds: 500),
                curve: Curves.easeInOut,
                child: Container(
                  width: 100,
                  height: 100,
                  color: Colors.blue,
                ),
              ),
            ),
          ],
        ),
      ),
      floatingActionButton: FloatingActionButton(
        onPressed: () {
          Navigator.pop(context);
        },
        child: Icon(Icons.arrow_back),
      ),
    );
  }
}

В этом примере используются виджеты AnimatedOpacity и AnimatedSize, чтобы анимировать изменение прозрачности и размера виджета при переходе на новую страницу. Оба виджета обернуты в Stack, чтобы можно было анимировать их одновременно.

Это всего лишь примеры и существует больше способов сохранить анимацию при переходе на новую страницу в зависимости от ваших конкретных требований. Выбор подходящего способа зависит от сложности и типа анимации, которую вы хотите реализовать.