我的应用程序中有一个按钮,每当用户在一天内单击该按钮时,他一整天都无法再次单击该按钮,并且当他单击该按钮时,该按钮将处于非活动状态全天都会活跃,明天也会活跃。我保存了用户上次点击 firestore 的时间和日期,但我的问题是当按钮处于非活动状态时,它也会执行,请下面是我的代码,我在这里出了什么问题。我将非常感谢任何帮助
@override
void initState() {
super.initState();
_checkButtonStatus();
}
verifyAccount() async {
final response = await http.post(
Uri.parse('http://'),
headers: {
"Content-type": "application/x-www-form-urlencoded",
"Accept": "application/json",
},
body:{
"accountNo": widget.valueAccountNo,
"accountName": widget.valueAccountName,
"bankName": widget.valueBankName,
});
var data = await json.decode(json.encode(response.body));
if(data == "Error"){
}
else{
//Get Your ERROR message's here
}
}
Future<void> _checkButtonStatus() async {
User? user = _auth.currentUser;
_uid = user!.uid;
try {
DocumentSnapshot documentSnapshot =
await _firestore.collection('Withdrawals').doc(_uid).get();
if (documentSnapshot.exists) {
Timestamp lastPressed = documentSnapshot['date'];
DateTime lastPressedDate = lastPressed.toDate();
DateTime currentDate = DateTime.now();
Duration difference = currentDate.difference(lastPressedDate);
setState(() {
_isButtonActive = difference.inHours >= 24;
});
}
} catch (e) {
print("Error checking button status: $e");
}
}
Future<void> _handleButtonPress() async {
try {
await _firestore.collection('Withdrawals').doc(_uid).set({
'date': Timestamp.now(),
});
setState(() {
_isButtonActive = false;
});
} catch (e) {
print("Error handling button press: $e");
}
}
child: ElevatedButton(
child: Text(_isButtonActive ? 'Continue':'Disabled'),
onPressed: _isButtonActive ? () async {
await _handleButtonPress();
verifyAccount();
} : null,
),
It shouldn't verify or go to verifyAccount() method if the button is inactive, please is there anything am missing or am not doing well please
我的建议是将按钮的状态存储为
Future<bool>
并将函数 _checkButtonStatus()
重构为 _getButtonStatus()
一个返回未来值的函数。
这也解决了从
setState
调用 initState
的问题。
下面的示例改编自以下所示的解决方案:FutureBuilder。它可以复制/粘贴并在 dartpad 中运行。
import 'package:flutter/material.dart';
void main() => runApp(const SimpleApp());
class SimpleApp extends StatelessWidget {
const SimpleApp({super.key});
@override
Widget build(BuildContext context) {
return const MaterialApp(
home: MyButton(),
);
}
}
class MyButton extends StatefulWidget {
const MyButton({super.key});
@override
State<MyButton> createState() => _MyButtonState();
}
class _MyButtonState extends State<MyButton> {
// State of button is stored as a Future<bool>.
late Future<bool> _isButtonActive;
@override
void initState() {
super.initState();
_isButtonActive = _getButtonStatus();
}
Future<bool> _getButtonStatus() async {
// User? user = _auth.currentUser;
// _uid = user!.uid;
try {
// DocumentSnapshot documentSnapshot =
// await _firestore.collection('Withdrawals').doc(_uid).get();
// if (documentSnapshot.exists) {
// Timestamp lastPressed = documentSnapshot['date'];
// DateTime lastPressedDate = lastPressed.toDate();
// DateTime currentDate = DateTime.now();
// Duration difference = currentDate.difference(lastPressedDate);
// return difference.inHours >= 24;
// For testing: Remove line below
return Future.delayed(Duration(seconds: 2), () => true);
} catch (e) {
debugPrint("Error checking button status: $e");
return Future<bool>.value(false);
}
}
Future<void> _handleButtonPress() async {
try {
// await _firestore.collection('Withdrawals').doc(_uid).set({
// 'date': Timestamp.now(),
// });
setState(() {
_isButtonActive = Future.value(false);
});
} catch (e) {
debugPrint("Error handling button press: $e");
}
}
@override
Widget build(BuildContext context) {
return FutureBuilder<bool>(
future: _isButtonActive,
builder: (BuildContext context, AsyncSnapshot<bool> snapshot) {
debugPrint('building');
List<Widget> children;
if (snapshot.hasData) {
children = <Widget>[
ElevatedButton(
onPressed: snapshot.data! ? _handleButtonPress : null,
child: Text(snapshot.data! ? 'Enabled' : 'Disabled')),
];
} else if (snapshot.hasError) {
children = <Widget>[
const Icon(
Icons.error_outline,
color: Colors.red,
size: 60,
),
Padding(
padding: const EdgeInsets.only(top: 16),
child: Text('Error: ${snapshot.error}'),
),
];
} else {
children = const <Widget>[
SizedBox(
width: 60,
height: 60,
child: CircularProgressIndicator(),
),
Padding(
padding: EdgeInsets.only(top: 16),
child: Text('Initializing button...'),
),
];
}
return Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: children,
),
);
},
);
}
}