flutter - NoSuchMethodError:在 null 上调用了方法“doLogin”
问题描述
正如我的名字所说,我是 Flutter 的新手,我需要你们的帮助。我正在使用我的登录名、注册表单。当我注册时它不会引发错误,但是当我尝试登录时它显示空错误:
class AuthDialog extends StatefulWidget {
@override
_AuthDialogState createState() => _AuthDialogState();
}
class _AuthDialogState extends State<AuthDialog> {
TextEditingController textControllerEmail;
FocusNode textFocusNodeEmail;
bool _isEditingEmail = false;
TextEditingController textControllerPassword;
FocusNode textFocusNodePassword;
bool _isEditingPassword = false;
bool _isLoading = false;
bool _isRegistering = false;
bool _isLoggingIn = false;
String loginStatus;
Color loginStringColor = Colors.green;
final scaffoldKey = new GlobalKey<ScaffoldState>();
final formKey = new GlobalKey<FormState>();
LoginPagePresenter _presenter;
String _validateEmail(String value) {
value = value.trim();
if (textControllerEmail.text.isNotEmpty) {
if (value.isEmpty) {
return 'Email can\'t be empty';
} else if (!value.contains(RegExp(
r"^[a-zA-Z0-9.a-zA-Z0-9.!#$%&'*+-/=?^_`{|}~]+@[a-zA-Z0-9]+\.[a-zA-Z]+"))) {
return 'Enter a correct email address';
}
}
return null;
}
void _submit() {
final form = formKey.currentState;
if (form.validate()) {
setState(() {
_isLoading = true;
form.save();
var user = new User(
textControllerEmail.text, textControllerPassword.text, null);
var db = new DatabaseHelper();
db.saveUser(user);
_isLoading = false;
});
}
}
void _login() {
final form = formKey.currentState;
if (form.validate()) {
setState(() {
_isLoading = true;
form.save();
_presenter.doLogin(
textControllerEmail.text, textControllerPassword.text);
});
}
}
String _validatePassword(String value) {
value = value.trim();
if (textControllerEmail.text.isNotEmpty) {
if (value.isEmpty) {
return 'Password can\'t be empty';
} else if (value.length < 6) {
return 'Length of password should be greater than 6';
}
}
return null;
}
@override
void initState() {
textControllerEmail = TextEditingController();
textControllerPassword = TextEditingController();
textControllerEmail.text = '';
textControllerPassword.text = '';
textFocusNodeEmail = FocusNode();
textFocusNodePassword = FocusNode();
super.initState();
}
@override
Widget build(BuildContext context) {
return Dialog(
backgroundColor: Theme.of(context).backgroundColor,
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(8.0),
),
child: SingleChildScrollView(
child: Padding(
padding: const EdgeInsets.all(16.0),
child: Container(
width: 400,
color: Theme.of(context).backgroundColor,
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisSize: MainAxisSize.min,
children: [
Center(
child: Text(
'NORTHERN NOMAD',
style: TextStyle(
color: Theme.of(context).textTheme.headline1.color,
fontSize: 24,
fontFamily: 'Montserrat',
fontWeight: FontWeight.bold,
letterSpacing: 3,
),
),
),
SizedBox(height: 30),
Padding(
padding: const EdgeInsets.only(
left: 20.0,
bottom: 8,
),
child: Text(
'Email address',
textAlign: TextAlign.left,
style: TextStyle(
color: Theme.of(context).textTheme.subtitle2.color,
fontSize: 18,
// fontFamily: 'Montserrat',
fontWeight: FontWeight.bold,
// letterSpacing: 3,
),
),
),
Padding(
padding: const EdgeInsets.only(
left: 20.0,
right: 20,
),
child: TextField(
focusNode: textFocusNodeEmail,
keyboardType: TextInputType.emailAddress,
textInputAction: TextInputAction.next,
controller: textControllerEmail,
autofocus: false,
onChanged: (value) {
setState(() {
_isEditingEmail = true;
});
},
onSubmitted: (value) => textControllerEmail.text = value,
//onSubmitted: (value) {
//textFocusNodeEmail.unfocus();
//FocusScope.of(context)
//.requestFocus(textFocusNodePassword);
// },
style: TextStyle(color: Colors.black),
decoration: InputDecoration(
border: new OutlineInputBorder(
borderRadius: BorderRadius.circular(10),
borderSide: BorderSide(
color: Colors.blueGrey[800],
width: 3,
),
),
filled: true,
hintStyle: new TextStyle(
color: Colors.blueGrey[300],
),
hintText: "Email",
fillColor: Colors.white,
errorText: _isEditingEmail
? _validateEmail(textControllerEmail.text)
: null,
errorStyle: TextStyle(
fontSize: 12,
color: Colors.redAccent,
),
),
),
),
SizedBox(height: 20),
Padding(
padding: const EdgeInsets.only(
left: 20.0,
bottom: 8,
),
child: Text(
'Password',
textAlign: TextAlign.left,
style: TextStyle(
color: Theme.of(context).textTheme.subtitle2.color,
fontSize: 18,
fontWeight: FontWeight.bold,
// letterSpacing: 3,
),
),
),
new Form(
key: formKey,
child: Column(
children: <Widget>[
Padding(
padding: const EdgeInsets.only(
left: 20.0,
right: 20,
),
child: TextField(
focusNode: textFocusNodePassword,
keyboardType: TextInputType.text,
textInputAction: TextInputAction.done,
controller: textControllerPassword,
obscureText: true,
autofocus: false,
onChanged: (value) {
setState(() {
_isEditingPassword = true;
});
},
onSubmitted: (value) =>
textControllerPassword.text = value,
//onSubmitted: (value) {
//textFocusNodePassword.unfocus();
//FocusScope.of(context)
//.requestFocus(textFocusNodePassword);
//},
style: TextStyle(color: Colors.black),
decoration: InputDecoration(
border: new OutlineInputBorder(
borderRadius: BorderRadius.circular(10),
borderSide: BorderSide(
color: Colors.blueGrey[800],
width: 3,
),
),
filled: true,
hintStyle: new TextStyle(
color: Colors.blueGrey[300],
),
hintText: "Password",
fillColor: Colors.white,
errorText: _isEditingPassword
? _validatePassword(
textControllerPassword.text)
: null,
errorStyle: TextStyle(
fontSize: 12,
color: Colors.redAccent,
),
),
),
),
],
)
),
//end
Padding(
padding: const EdgeInsets.all(20.0),
child: Row(
mainAxisSize: MainAxisSize.max,
mainAxisAlignment: MainAxisAlignment.spaceAround,
children: [
Flexible(
flex: 1,
child: Container(
width: double.maxFinite,
child: TextButton(
style: TextButton.styleFrom(
primary: Colors.blueGrey.shade800,
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(15.0),
),
),
onPressed: () {
_login();
},
child: Padding(
padding: EdgeInsets.only(
top: 15.0,
bottom: 15.0,
),
child: _isLoggingIn
? SizedBox(
height: 16,
width: 16,
child: CircularProgressIndicator(
strokeWidth: 2,
valueColor:
new AlwaysStoppedAnimation<Color>(
Colors.white,
),
),
)
: Text(
'Log in',
style: TextStyle(
fontSize: 14,
color: Colors.white,
),
),
),
),
),
),
SizedBox(width: 20),
Flexible(
flex: 1,
child: Container(
width: double.maxFinite,
child: TextButton(
style: TextButton.styleFrom(
primary: Colors.blueGrey.shade800,
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(15),
),
),
onPressed: () {
_submit();
},
child: Padding(
padding: EdgeInsets.only(
top: 15.0,
bottom: 15.0,
),
child: _isRegistering
? SizedBox(
height: 16,
width: 16,
child: CircularProgressIndicator(
strokeWidth: 2,
valueColor:
new AlwaysStoppedAnimation<Color>(
Colors.white,
),
),
)
: Text(
'Sign up',
style: TextStyle(
fontSize: 14,
color: Colors.white,
),
),
),
),
),
),
],
),
),
loginStatus != null
? Center(
child: Padding(
padding: const EdgeInsets.only(
bottom: 20.0,
),
child: Text(
loginStatus,
style: TextStyle(
color: loginStringColor,
fontSize: 14,
// letterSpacing: 3,
),
),
),
)
: Container(),
Padding(
padding: const EdgeInsets.only(
left: 40.0,
right: 40.0,
),
child: Container(
height: 1,
width: double.maxFinite,
color: Colors.blueGrey[200],
),
),
SizedBox(height: 30),
SizedBox(height: 30),
],
),
),
),
),
);
}
}
这是我运行登录时的错误:
════════ 手势捕捉到异常═════════════════════════════════════════════════════════ ═════ 处理手势时引发以下 NoSuchMethodError:方法 'doLogin' 在 null 上被调用。接收方:null 尝试调用:doLogin("SIGNIN@gmail.com", "asdsadsad")
这是我为 doLogin 分离的 .dart 文件
abstract class LoginPageContract {
void onLoginSuccess(User user);
void onLoginError(String error);
}
class LoginPagePresenter {
LoginPageContract _view;
RestData api = new RestData();
LoginPagePresenter(this._view);
//Simulator login
doLogin(String email, String password) {
api
.login(email, password)
.then((user) => _view.onLoginSuccess(user))
.catchError((onError) => _view.onLoginError(onError));
}
}
解决方案
你会调用 LoginPagePresenter 类的构造方法吗?
前
LoginPagePresenter _presenter;
后
LoginPagePresenter _presenter = LoginPagePresenter();
推荐阅读
- aws-glue - AWS Glue 作业延迟通知在哪里提出?
- python - 在循环内使用“随机”模块输出相同的结果
- pandas - 如何使用字段中的最近值将 pandas 数据框与 geopandas 连接起来
- twilio - Twilio 自动驾驶仪允许强插
- flutter - 在运行默认应用程序时,Flutter 在切换到 Master 后抛出“日志阅读器意外停止”
- docker - 获取变量 APPLICATION_ENV 无效,检查 .env 文件
- javascript - 如何在 HTML 列表项中传递隐藏数据
- bash - Bash find 和 -exec 返回非法字节序列
- javascript - 为什么 LF 和 CRLF 在 /^\s*$/gm 正则表达式中表现不同?
- gulp-4 - Gulp 4 在开发模式下运行