Flutter插件Get(6):用户登陆界面实战.md
一、用户登陆界面展示
二、项目结构说明
项目结构图如下图所示:
说明:
- Login:登陆界面,只负责与用户交互的界面内容展示
- LoginController:逻辑控制文件,负责处理,登陆按钮点击和隐私协议勾选
三、项目示例说明
3.1 LoginController(逻辑文件)
import 'package:flutter/material.dart';
import 'package:get/get.dart';
class LoginController extends GetxController {
//登陆按钮点击事件
login(TextEditingController userNameController,
TextEditingController passWordController) {
var userName = userNameController.text;
var passWord = passWordController.text;
//1-用户协议是否勾选
if (!isChecked.value) {
Get.snackbar('用户协议未选中', '请勾选用户协议', snackPosition: SnackPosition.BOTTOM);
return;
}
//2-用户名判断
if (userName.isEmpty) {
Get.snackbar('用户名异常', '用户名为空', snackPosition: SnackPosition.BOTTOM);
return;
}
//3-密码判断
if (passWord.isEmpty) {
Get.snackbar('密码异常', '密码为空', snackPosition: SnackPosition.BOTTOM);
return;
}
Get.snackbar('用户名、密码正确', '去登陆', snackPosition: SnackPosition.BOTTOM);
debugPrint("用户名:$userName,密码:$passWord");
}
//用户协议勾选事件
var isChecked = false.obs;
void changeChecked(bool value) {
isChecked.value = value;
}
}
说明(LoginController 包含两个方法调用和一个属性变量):
- login 方法:处理登陆按钮事件,分别对用户协议勾选、用户名、密码进行判断及处理
- changeChecked 方法:用户协议勾选事件
- isChecked:保存用户协议勾选结果,并在界面中通过
Obx(()=>Checkbox(value: controller.isChecked.value
显示
3.2 Login登陆界面
import 'package:flutter/material.dart';
import 'package:get/get.dart';
import 'package:custom/controller/LoginController.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
return GetMaterialApp(home: Login());
}
}
// 控制器实例
LoginController controller = Get.put(LoginController());
//登陆界面
class Login extends StatelessWidget {
Login({super.key});
final userNameController = TextEditingController();
final passWordController = TextEditingController();
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('登陆'),
),
body: Padding(
padding: const EdgeInsets.symmetric(horizontal: 16.0),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
const SizedBox(height: 80), //距离顶部距离
buildTopWidget(), //设置登陆欢迎
const SizedBox(height: 20), //距离上一个View距离
buildAccountInputWidget(userNameController), //用户名
const SizedBox(height: 20), //距离上一个View距离
buildPasswordInputWidget(passWordController), //密码
const SizedBox(
height: 10,
), //距离上一个View距离
buildPrivacyWidget(), //隐私政策
const SizedBox(
height: 10,
), //距离上一个View距离
buildLoginButton(), //登陆按钮
],
),
),
);
}
//Widget-Top
Widget buildTopWidget() {
return const Text(
"你好,欢迎登陆",
style: TextStyle(fontSize: 28, fontWeight: FontWeight.w800),
);
}
//手机号
Widget buildAccountInputWidget(TextEditingController? userNameController) {
return TextField(
controller: userNameController,
decoration: const InputDecoration(labelText: "用户名"),
style: const TextStyle(fontSize: 16),
keyboardType: TextInputType.phone,
);
}
//密码
Widget buildPasswordInputWidget(TextEditingController? passWordController) {
return TextField(
controller: passWordController,
obscureText: true,
decoration: const InputDecoration(labelText: "用户密码"),
style: const TextStyle(fontSize: 16),
);
}
//登陆按钮
Widget buildLoginButton() {
return SizedBox(
width: double.infinity,
child: ElevatedButton(
child: const Text("normal"),
onPressed: () {
debugPrint("ElevatedButton Click");
controller.login(userNameController, passWordController);
},
),
);
}
//隐私协议
Widget buildPrivacyWidget() {
return Row(
children: [
Obx(() => Checkbox(
value: controller.isChecked.value,
onChanged: (value) => controller.changeChecked(value!))),
const Text('同意', style: TextStyle(fontSize: 14)),
const Text('<服务协议>',
style: TextStyle(fontSize: 14, color: Colors.blue)),
const Text('<隐私政策>', style: TextStyle(fontSize: 14, color: Colors.blue))
],
);
}
}
说明:
- 通过
Get.put(LoginController())
获取 LoginController - Widget之间的间距通过 SizedBox 设置
- 登陆界面中的每个 Widget,单独剥离出来进行设置
- 登陆按钮和用户协议的勾选事件调用,通过 LoginController 来完成