Flutter 如果之前具有异步功能,则动画不工作
我的动画根本没有启动,在名为Flutter 如果之前具有异步功能,则动画不工作,flutter,Flutter,我的动画根本没有启动,在名为waitForAnimationComplete()的超时函数的整个4秒钟内,屏幕都是白色的。 最有趣的是,在热重新加载的情况下,一切都很完美,但在第一次启动时,什么都没有,屏幕是白色的 不幸的是,发布应用程序没有热重新加载,所以我不能忽略这个问题 此视图中的想法是从白色屏幕开始,然后(在计算颜色后)通过从白色到颜色的动画慢慢更改为彩色视图 import 'package:flutter/material.dart'; import 'package:my_proje
waitForAnimationComplete()的超时函数的整个4秒钟内,屏幕都是白色的。
最有趣的是,在热重新加载的情况下,一切都很完美,但在第一次启动时,什么都没有,屏幕是白色的
不幸的是,发布应用程序没有热重新加载,所以我不能忽略这个问题
此视图中的想法是从白色屏幕开始,然后(在计算颜色后)通过从白色到颜色的动画慢慢更改为彩色视图
import 'package:flutter/material.dart';
import 'package:my_project/home/home.dart';
import 'package:my_project/stile/theme_colors.dart';
class LoadingHome extends StatefulWidget {
@override
_LoadingHomeState createState() => _LoadingHomeState();
}
class _LoadingHomeState extends State<LoadingHome> with SingleTickerProviderStateMixin {
AnimationController controller;
Animation<Color> background;
@override
void initState(){
super.initState();
controller = AnimationController(
duration: const Duration(milliseconds: 2000), vsync: this);
openHome();
}
openHome() async{
double hue = await recoverColor();
startTransition(hue);
await Future.wait([waitForAnimationComplete()]);
Navigator.pushReplacement(
context, MaterialPageRoute(builder: (BuildContext context) => Home())
);
}
Future<double> recoverColor() async {
return 0.6;
}
startTransition(double hue) {
if(hue == null)
ThemeColors.initColors();
else
ThemeColors.initColors(hue: hue);
background = ColorTween(
begin: Colors.white,
end: ThemeColors.dark,
).animate(controller);
controller.forward(); // starts animation
}
Future<void> waitForAnimationComplete() async {
await Future.delayed(const Duration(seconds: 4));
}
@override
Widget build(BuildContext context) {
return controller.isAnimating ? AnimatedBuilder(
animation: background,
builder: (BuildContext context, child) => BodyLoadHome(
background: background.value,
),
) : BodyLoadHome(
background: Colors.white,
);
}
}
class BodyLoadHome extends StatelessWidget {
final Color background;
BodyLoadHome({this.background});
@override
Widget build(BuildContext context) {
return Container(
color: background,
);
}
}
有了这些变化,一切都正常了。显然,真正的recoverColor()
并不是那么简单,在这个函数中,我应该从内部存储器中读取色调,因此recoverColor()
一定是未来的趋势
我怎样才能使它即使在将来也能工作呢recoverColor()
编辑:
建议将.addListener()
与setState()
结合使用,但我认为我找到了一个更有效但类似的解决方案:
更改:
controller.forward(); // starts animation
致:
因此,我们只需调用一次
setState()
,即可从BodyLoadHome
更改为AnimatedBuilder
。我认为当使用AnimatedBuilder
时,他会在需要时调用setState()
当动画位置发生变化时,您忘记调用setState
。因此,您永远看不到UI中的更改。在initState
中创建控制器时,向AnimationController
添加一个调用setState
的侦听器
controller.addListener((){
setState((){});
});
你可以阅读官方的颤振教程来学习颤振动画的基本知识。在调用
forward()
之后,你必须调用setState
,以便你的小部件构建AnimatedBuilder
而不是BodyLoadHome
,同时检查controller.forward()
返回并用于延迟调用Navigator.pushReplacement
但老实说,我总是返回AnimatedBuilder
,以简化代码,或者更好的AnimatedContainer
有两种不同的颜色:
值谢谢,但我更喜欢看到加载屏幕至少4秒。我认为总是AnimatedBuilder
不容易使用,因为构造函数中使用background
,而background
在开始时为空不需要在每个动画帧中调用addListener
并调用setState
-动画由AnimatedBuilder
处理-真正的问题是,自上一次build()以来,没有生成
方法返回BodyLoadHome
作为控制器。isAnimating
为false
-这就是为什么我说总是返回动画生成器
controller.forward(); // starts animation
setState(() {
controller.forward(); // starts animation
});