如何解决使用AnimationController再次显示flutter小部件后,无法对其进行动画处理
我正在使用AnimationController对小部件进行动画处理(该小部件是图中显示的红色波浪)。小部件以visibility = false
开头,并在用户按下红色按钮讲话后的10秒钟内变为true。我面临的问题是,当再次按下红色按钮时,我得到了错误:
AnimationController.stop()在AnimationController.dispose()之后调用。
窗口小部件再也不会显示。由于我不只是将其隐藏而放置小部件,所以我不知道发生了什么。到目前为止,我已经尝试过:
- 创建
_controller
外部/内部小部件版本。 - 在调用小部件之前检查其是否已安装
- 只要隐藏小部件,就将
AnimationController
状态更改为false。
class MyApp extends StatefulWidget {
@override
_MyAppState createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> with TickerProviderStateMixin {
var _controller;
var spinkitWave;
stt.SpeechToText speech = stt.SpeechToText();
@override
void initState() {
super.initState();
_controller = AnimationController(vsync:this,duration: Duration(seconds:1),lowerBound:0,upperBound:0.1)
..addStatusListener((status) {
if (status == AnimationStatus.completed) {
if (mounted) {
_controller.reverse();
}
}});
@override
dispose() {
_controller.dispose(); // you need this
super.dispose();
}
void startListening() {
_controller = AnimationController(vsync:this,upperBound:0.1);
speech.listen(onResult: resultListener,onSoundLevelChange: soundLevelListener,cancelOnError: true,);
setState(() {});
}
@override
Widget build(BuildContext context) {
spinkitWave = SpinKitWave(
color: Colors.redAccent,type: SpinKitWaveType.center,controller: _controller,);
return MaterialApp(
title: 'Flutter Demo',theme: ThemeData(
primarySwatch: Colors.red,),home: Builder(
builder: (context) => Scaffold(
appBar: AppBar(
title: Text("Leurebeng"),body: Center(
Positioned(
bottom: 10,child: Stack(
alignment: AlignmentDirectional.bottomCenter,children: <Widget>[
SizedBox
width: 110.0,height: 110.0,child: Visibility(
visible: !speech.isListening,child: FloatingActionButton(
onpressed:
_available ? startListening : initSpeechState,tooltip: 'Increment',child: Icon(Icons.mic),Visibility(
visible: speech.isListening,//Turns true or false after red button pressed
child:
spinkitWave
),]),);
}
}
}
解决方法
我认为问题是,您两次声明_controller
。第一次在initState(){}
中开始播放,第二次在startListening(){}
中它被覆盖并且不再播放。如果要开始/停止动画,可以这样:
_controller.isAnimating
? _controller.stop()
: _controller.forward();
,
在此处应用实际解决方案之前,您需要清除的几件事是
- 从不使用var关键字来初始化一次性类型
- 不要像声明initState和StartListening一样在声明后重新初始化变量
要解决您的问题,可以将处理方法包装为
data[0]
然后,尝试使用
if(_animationController){
_animationController.dispose()
}
在创建的回调中可以防止遇到的错误
, 动画完成后,在dispose()
上调用 _controller
。
正如其他评论者所指出的那样,您的代码需要解决一些问题,但是我将重点介绍解决您的AnimationController
问题的解决方案。
有几种方法可以防止此错误。最简单的方法是在_controller.repeat(reverse: true);
中初始化控制器后调用initState
。这将导致它无限期地来回运行。然后,您只需切换_isListening
即可显示/隐藏动画。
您还可以删除initState
中的初始化,并在每次调用startListening()
时重新初始化。如果这样做,则必须确保在初始化新控制器之前将其丢弃。可以通过调用_controller.stop()
来完成。根据您的需要,这可以是通过Duration
通过Future.delayed()
设置$('#calendar').fullCalendar({})
之后的回调,也可以是按钮释放后的回调,或任何其他方法。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。