簡體   English   中英

如何在顫動中改變英雄動畫的速度

[英]How to change speed of a hero animation in flutter

我按照Flutter 網站的說明制作了簡單的英雄動畫

它按照說明中的描述工作,但就我而言,我希望它從第一個屏幕到第二個屏幕的動畫速度要慢得多。 有誰知道如何改變這個動畫的速度?

要修改轉換速度,您必須調整PageRoute轉換持續時間(正如@diegoveloper 已經指出的那樣)。

如果您想保留默認轉換,您可以創建一個實現MaterialPageRoute的類。 如果您已經擁有自己的過渡或想創建一個過渡,您可以使用PageRouteBuilder輕松構建自己的過渡。 只需調整transitionDuration

這是一個使用PageRouteBuilder的小型獨立示例:

過渡演示

import 'package:flutter/material.dart';

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Page1(),
    );
  }
}

class Page1 extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Center(
        child: Column(
          mainAxisAlignment: MainAxisAlignment.spaceAround,
          children: <Widget>[
            RaisedButton(
              child: Text('Page2'),
              onPressed: () => Navigator.push(
                  context,
                  PageRouteBuilder(
                      transitionDuration: Duration(seconds: 2),
                      pageBuilder: (_, __, ___) => Page2())),
            ),
            Hero(tag: 'home', child: Icon(Icons.home))
          ],
        ),
      ),
    );
  }
}

class Page2 extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Center(
        child: Hero(
          tag: 'home',
          child: Icon(
            Icons.home,
          ),
        ),
      ),
    );
  }
}

1. 一個可能的解決方案

我認為實現此目標的唯一方法不是通過更改PageRoute轉換持續時間。 我認為您也可以通過使用AnimationController來達到相同的效果——這個答案主要來自Angela Yu 的 The Complete 2019 Flutter Development Bootcamp with Dart 的講座#149 和#150。

  1. 將你的屏幕變成一個StatefulWidget
  2. 如果您只使用一個動畫,請將with SingleTickerProviderStateMixin添加到您的狀態類。
  3. 在狀態類中創建一個控制器。
  4. 如果您的動畫應該出現在屏幕的初始化上,請在initState方法中使用controller
    • 控制器有一個名為duration的屬性,因此您可以根據自己的喜好更改它。

2. 它會是什么樣子

最后,一切應該看起來像這樣:

class _NewScreenState extends State<HomeScreen> 
  with SingleTickerProviderStateMixin{

  AnimationController controller;

  @override
  void initState() {
    super.initState();

    controller = AnimationController(
      duration: Duration(seconds: 1),
      vsync: this,
    );

    controller.forward();

    controller.addListener((){
      setState(() {
        
      });
    });
  }

  @override
  Widget build(BuildContext context) {
    return ...
  • vsync是一個必需的 ( @required ) 參數,它接受狀態(實例)對象本身(通常)。
  • addListenersetState如果你希望在將來的某個時候使用controller的值( controller.value )——例如,用height: finalHeight * controller.value之類的東西改變圖標的高度。
  • 為了過渡到此屏幕,我只是使用帶有Navigator.pushNamedFlatButton ,沒什么特別的。

3. 一些額外的重要信息

  1. 即使您稍后更改屏幕, controller仍將處於活動狀態。 因此,如果您在后台有一個循環動畫,最好在更改屏幕時將其處理掉,這樣您就不會再浪費手機資源了。 這可以通過以下方式實現:
     @override void dispose() { controller.dispose(); super.dispose(); }
  2. 您還可以自定義動畫的運行方式或執行方式。 一種選擇是使用CurvedAnimation
    1. 聲明Animation animation; 就在你的controller下面。
    2. 在您的controller下,在initState內,添加:
       animation = CurvedAnimation( // the controller can't have upperBound > 1 parent: controller, // the controller you created curve: Curves.decelerate, );
  3. Flutter中制作動畫的另一種有用方法是使用TweenAnimations 例如,如果你想在顏色之間轉換,你可以使用ColorTween (在你的controller之下,在initState內):
     animation = ColorTween( begin: Colors.red, end: Colors.blue, ).animate(controller);

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM