so I am trying to make a color tween animation where when the button is pressed, if the answer is correct on the text field, the background color will be green and then turns back into black, if not then the same thing will happen but red instead of green however I encountered a problem.
when I enter an answer, the color tween works, but when I do it again, nothing happens.
here's the entire code
import 'dart:async';
import 'dart:io';
import 'dart:math';
import 'math_utils.dart';
import 'package:flutter/material.dart';
class GameScreen extends StatefulWidget {
@override
State<GameScreen> createState() => _GameScreenState();
}
class _GameScreenState extends State<GameScreen> with TickerProviderStateMixin {
int n1 = Random().nextInt(13) + 0;
int n2 = Random().nextInt(13) + 0;
int lives = 3;
int score = 0;
FocusNode node = FocusNode();
double sec = 60.00;
dynamic isCorrect = null;
TextEditingController controller = TextEditingController();
late AnimationController ctrl;
late Animation<Color?> clr;
@override
void initState(){
Timer.periodic(const Duration(milliseconds: 1), (timer) {
setState(() {
sec=sec-0.01;
});
});
super.initState();
ctrl = AnimationController(
duration: Duration(seconds: 1), vsync: this,
);
clr = ColorTween(begin: Colors.black).animate(ctrl);
}
@override
Widget build(BuildContext context) {
return SafeArea(
child: Scaffold(
backgroundColor: Colors.black,
body: Container(
width: size.width,
child: SingleChildScrollView(
child: Container(
height: size.height,
width: size.width,
decoration: BoxDecoration(
color: clr.value,
),
child: Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.center,
mainAxisAlignment: MainAxisAlignment.start,
children: [
Align(
alignment: Alignment.centerLeft,
child: Padding(
padding: EdgeInsets.only(
top: getVerticalSize(
16.00,
),
bottom: getVerticalSize(
20.00,
),
),
child: Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.center,
mainAxisAlignment: MainAxisAlignment.start,
children: [
Align(
alignment: Alignment.centerLeft,
child: Container(
width: size.width,
child: Padding(
padding: EdgeInsets.only(
left: getHorizontalSize(
16.00,
),
right: getHorizontalSize(
16.00,
),
),
child: Row(
mainAxisAlignment:
MainAxisAlignment.spaceBetween,
crossAxisAlignment: CrossAxisAlignment.center,
mainAxisSize: MainAxisSize.max,
children: [
Padding(
padding: EdgeInsets.only(
top: getVerticalSize(
3.00,
),
),
child: Row(
crossAxisAlignment:
CrossAxisAlignment.center,
mainAxisSize: MainAxisSize.min,
children: [
lives >= 1? Image.asset(
"assets/heart.webp",
height: getSize(
32.00,
),
width: getSize(
32.00,
),
fit: BoxFit.fill,
): SizedBox(
height: getSize(
32.00,
),
width: getSize(
32.00,
),
),
lives >= 2? Image.asset(
"assets/heart.webp",
height: getSize(
32.00,
),
width: getSize(
32.00,
),
fit: BoxFit.fill,
): SizedBox(
height: getSize(
32.00,
),
width: getSize(
32.00,
),
),
lives >= 3? Image.asset(
"assets/heart.webp",
height: getSize(
32.00,
),
width: getSize(
32.00,
),
fit: BoxFit.fill,
): SizedBox(
height: getSize(
32.00,
),
width: getSize(
32.00,
),
),
],
),
),
Text(
"Score: $score",
overflow: TextOverflow.ellipsis,
textAlign: TextAlign.center,
style: TextStyle(
color: Colors.white70,
fontSize: getFontSize(
24,
),
fontFamily: 'Inter',
fontWeight: FontWeight.w400,
),
),
],
),
),
),
),
Container(
width: size.width,
height: getVerticalSize(
20
),
child:
// Text(
// "$sec",
// maxLines: null,
// textAlign: TextAlign.center,
// style: TextStyle(
// color: Colors.white70,
// fontSize: getFontSize(
// 24,
// ),
// fontFamily: 'Inter',
// fontWeight: FontWeight.w400,
// ),
// ),
LinearProgressIndicator(
value: sec/60,
color: sec/60 >= 0.5? Colors.green:Colors.red,
backgroundColor: Colors.black,
),
),
Padding(
padding: EdgeInsets.only(
left: getHorizontalSize(
96.00,
),
top: getVerticalSize(
200.00,
),
right: getHorizontalSize(
96.00,
),
),
child: Text(
"${n1} x ${n2}",
overflow: TextOverflow.ellipsis,
textAlign: TextAlign.center,
style: TextStyle(
color: Colors.white70,
fontSize: getFontSize(
64,
),
fontFamily: 'Inter',
fontWeight: FontWeight.w400,
),
),
),
],
),
),
),
TextField(
focusNode: node,
controller: controller,
textAlign: TextAlign.center,
onSubmitted: (value) async{
setState(() {
if(value == (n1 * n2).toString()){
score += 10;
n1 = Random().nextInt(13) + 0;
n2 = Random().nextInt(13) + 0;
WidgetsBinding.instance!.addPostFrameCallback((_) {
clr = ColorTween(begin: Colors.green, end: Colors.black).animate(ctrl);
ctrl.forward();
});
print(true);
}
else {
lives -= 1;
WidgetsBinding.instance!.addPostFrameCallback((_) {
clr = ColorTween(begin: Colors.red, end: Colors.black).animate(ctrl);
ctrl.forward();
});
print(false);
}
});
clr = ColorTween(begin: Colors.black).animate(ctrl);
controller.clear();
Future sleep(final Duration duration) async {
await Future.delayed(duration);
}
await sleep(Duration(milliseconds: 10));
node.requestFocus();
},
autofocus: true,
decoration: InputDecoration(
border: InputBorder.none
),
style: TextStyle(
color: Colors.white,
fontSize: 48
),
),
],
),
),
),
),
),
);
}
}
The code that I'm focusing on is this
TextField(
focusNode: node,
controller: controller,
textAlign: TextAlign.center,
onSubmitted: (value) async{
setState(() {
if(value == (n1 * n2).toString()){
score += 10;
n1 = Random().nextInt(13) + 0;
n2 = Random().nextInt(13) + 0;
WidgetsBinding.instance!.addPostFrameCallback((_) {
clr = ColorTween(begin: Colors.green, end: Colors.black).animate(ctrl);
ctrl.forward();
});
print(true);
}
else {
lives -= 1;
WidgetsBinding.instance!.addPostFrameCallback((_) {
clr = ColorTween(begin: Colors.red, end: Colors.black).animate(ctrl);
ctrl.forward();
});
print(false);
}
});
clr = ColorTween(begin: Colors.black).animate(ctrl);
controller.clear();
Future sleep(final Duration duration) async {
await Future.delayed(duration);
}
await sleep(Duration(milliseconds: 10));
node.requestFocus();
},
autofocus: true,
decoration: InputDecoration(
border: InputBorder.none
),
style: TextStyle(
color: Colors.white,
fontSize: 48
),
),
To reset any animation controller, use animationController.reset()
.
Sets the controller's value to lowerBound, stopping the animation (if in progress), and resetting to its beginning point, or dismissed state.
More about AnimationController
.