更新眠花糖选择城市

This commit is contained in:
wyf
2025-12-17 11:01:30 +08:00
parent f2657e4238
commit 18c3b86e8a
7 changed files with 572 additions and 77 deletions

View File

@@ -6,13 +6,13 @@ import 'package:flutter_svg/svg.dart';
import 'package:intl/intl.dart'; import 'package:intl/intl.dart';
import 'package:url_launcher/url_launcher.dart'; import 'package:url_launcher/url_launcher.dart';
import 'package:vbvs_app/common/color/app_uri_status.dart'; import 'package:vbvs_app/common/color/app_uri_status.dart';
import 'package:vbvs_app/common/pojo/city.dart';
import 'package:vbvs_app/common/util/CommonVariables.dart'; import 'package:vbvs_app/common/util/CommonVariables.dart';
import 'package:vbvs_app/common/util/FitTool.dart'; import 'package:vbvs_app/common/util/FitTool.dart';
import 'package:vbvs_app/component/tool/ClickableContainer.dart'; import 'package:vbvs_app/component/tool/ClickableContainer.dart';
import 'package:vbvs_app/controller/mh_controller/mh_language_controller.dart'; import 'package:vbvs_app/controller/mh_controller/mh_language_controller.dart';
import 'package:vbvs_app/controller/setting/language/language_controller.dart'; import 'package:vbvs_app/controller/setting/language/language_controller.dart';
import 'package:vbvs_app/controller/theme_controller/ThemeController.dart'; import 'package:vbvs_app/controller/theme_controller/ThemeController.dart';
import 'package:vbvs_app/language/AppLanguage.dart';
import 'package:vbvs_app/model/api_response.dart'; import 'package:vbvs_app/model/api_response.dart';
ThemeController themeController = Get.find(); ThemeController themeController = Get.find();
@@ -20,6 +20,31 @@ LanguageController languageController = Get.find();
MHLanguageController mhLanguageController = Get.find(); MHLanguageController mhLanguageController = Get.find();
class MyUtils { class MyUtils {
// 获取城市显示文本
// 更详细的显示逻辑(可选)
static String getDetailedCityDisplayText(CityModel? cityModel) {
if (cityModel == null) {
return '选择城市'.tr;
}
// 根据数据层级显示不同的格式
if (cityModel.city != null && cityModel.city!.isNotEmpty) {
// 三级数据:国家-省份-城市
return '${cityModel.country ?? ''}-${cityModel.province ?? ''}-${cityModel.city ?? cityModel.value ?? ''}';
} else if (cityModel.province != null && cityModel.province!.isNotEmpty) {
// 二级数据:国家-省份
return '${cityModel.country ?? ''}-${cityModel.province ?? cityModel.value ?? ''}';
} else if (cityModel.country != null && cityModel.country!.isNotEmpty) {
// 一级数据:国家
return cityModel.country!;
} else if (cityModel.value != null && cityModel.value!.isNotEmpty) {
// 只有 value 字段
return cityModel.value!;
} else {
return '选择城市'.tr;
}
}
static String formatTimestampToSleep(int milliseconds) { static String formatTimestampToSleep(int milliseconds) {
final date = DateTime.fromMillisecondsSinceEpoch(milliseconds); final date = DateTime.fromMillisecondsSinceEpoch(milliseconds);
return "${date.year}-${date.month}-${date.day}"; return "${date.year}-${date.month}-${date.day}";

View File

@@ -5,6 +5,7 @@ import 'package:flutter/src/widgets/framework.dart';
import 'package:flutterflow_ui/flutterflow_ui.dart'; import 'package:flutterflow_ui/flutterflow_ui.dart';
import 'package:json_annotation/json_annotation.dart'; import 'package:json_annotation/json_annotation.dart';
import 'package:vbvs_app/common/color/ServiceConstant.dart'; import 'package:vbvs_app/common/color/ServiceConstant.dart';
import 'package:vbvs_app/common/pojo/city.dart';
import 'package:vbvs_app/common/util/MyUtils.dart'; import 'package:vbvs_app/common/util/MyUtils.dart';
import 'package:vbvs_app/common/util/requestWithLog.dart'; import 'package:vbvs_app/common/util/requestWithLog.dart';
import 'package:vbvs_app/component/tool/TopSlideNotification.dart'; import 'package:vbvs_app/component/tool/TopSlideNotification.dart';
@@ -23,6 +24,7 @@ class PeopleInfoModel {
String? phone; String? phone;
String? contact; String? contact;
List peopleList = []; List peopleList = [];
List<CityModel> cityModels = [];
PeopleInfoModel(); PeopleInfoModel();
factory PeopleInfoModel.fromJson(Map<String, dynamic> json) { factory PeopleInfoModel.fromJson(Map<String, dynamic> json) {
@@ -43,25 +45,33 @@ class PeopleInfoController extends GetControllerEx<PeopleInfoModel> {
attr = GetModel(PeopleInfoModel()).obs; attr = GetModel(PeopleInfoModel()).obs;
} }
final CityModelController cityController = Get.find<CityModelController>();
@override @override
Future<void> onInit() async { Future<void> onInit() async {
super.onInit(); super.onInit();
// await getPeoples(Get.arguments['mac']); // 控制器创建时立即执行 cityDataFuture = cityController.loadAndSetCityData().then((success) {
return cityController.cityList;
});
} }
late Future<List<CityModel>> cityDataFuture;
getPeoples(String mac) async { getPeoples(String mac) async {
String serviceAddress = ServiceConstant.service_address; String serviceAddress = ServiceConstant.service_address;
String serviceName = ServiceConstant.server_service; String serviceName = ServiceConstant.server_service;
String serviceApi = ServiceConstant.person_info; String serviceApi = ServiceConstant.person_info;
String queryUrl = "$serviceAddress$serviceName$serviceApi?mac=$mac"; String queryUrl = "$serviceAddress$serviceName$serviceApi?mac=$mac";
requestWithLog( await requestWithLog(
logTitle: "获取设备的人员信息列表", logTitle: "获取设备的人员信息列表",
method: MyHttpMethod.get, method: MyHttpMethod.get,
queryUrl: queryUrl, queryUrl: queryUrl,
onSuccess: (res) { onSuccess: (res) {
if (res.data != null && res.data is List) { if (res.data != null && res.data is List) {
model.peopleList = res.data; model.peopleList = res.data;
model.cityModels = []; // 清空之前的数据
initializeCityData(); // 初始化城市数据
updateAll(); updateAll();
print("peopleList: ${model.peopleList}"); print("peopleList: ${model.peopleList}");
} }
@@ -96,4 +106,74 @@ class PeopleInfoController extends GetControllerEx<PeopleInfoModel> {
}, },
); );
} }
Future initializeCityData() async {
try {
// 确保城市数据已加载
if (!cityController.isDataLoaded) {
await cityController.loadAndSetCityData();
}
// 清空现有的城市模型列表
model.cityModels = [];
// 遍历peopleList中的每个人查找对应的城市数据
for (var person in model.peopleList) {
if (person is Map<String, dynamic>) {
// 获取person中的city_id
final cityId = person['city_id']?.toString();
if (cityId != null && cityId.isNotEmpty) {
ef.log("开始查找city_id: $cityId");
// 使用cityController查找完整的城市数据
final CityModel? completeCityData = cityController.findCityById(cityId);
if (completeCityData != null) {
// 将找到的城市数据添加到cityModels列表中
model.cityModels.add(completeCityData);
ef.log("成功添加城市数据: ${completeCityData.displayName} for person: ${person['name'] ?? 'Unknown'}");
} else {
// 如果找不到对应的城市数据添加一个空的CityModel但保留city_id
final CityModel emptyCityModel = CityModel(id: int.tryParse(cityId));
model.cityModels.add(emptyCityModel);
ef.log("未找到对应城市数据创建默认CityModel for city_id: $cityId");
}
} else {
// 如果person没有city_id添加一个空的CityModel
model.cityModels.add(CityModel());
ef.log("person没有city_id添加空CityModel");
}
}
}
// 确保cityModels列表长度与peopleList一致
while (model.cityModels.length < model.peopleList.length) {
model.cityModels.add(CityModel());
}
// 更新UI
updateAll();
ef.log("初始化城市数据完成peopleList长度: ${model.peopleList.length}, cityModels长度: ${model.cityModels.length}");
} catch (e) {
ef.log("初始化城市数据失败: $e");
}
}
// 可选添加一个方法来获取特定person的城市数据
CityModel? getCityForPerson(int personIndex) {
if (personIndex >= 0 && personIndex < model.cityModels.length) {
return model.cityModels[personIndex];
}
return null;
}
// 可选添加一个方法来更新特定person的城市数据
void updateCityForPerson(int personIndex, CityModel cityModel) {
if (personIndex >= 0 && personIndex < model.cityModels.length) {
model.cityModels[personIndex] = cityModel;
updateAll();
}
}
} }

View File

@@ -912,6 +912,7 @@ class MyApp extends StatelessWidget {
Get.lazyPut(() => AuthBindTelController()), Get.lazyPut(() => AuthBindTelController()),
Get.lazyPut(() => CommonMessageSettingController()), Get.lazyPut(() => CommonMessageSettingController()),
Get.lazyPut(() => MHTDeviceUpgradeController()), Get.lazyPut(() => MHTDeviceUpgradeController()),
Get.lazyPut(() => CityModelController()),
])); ]));
} }

View File

@@ -4,6 +4,7 @@ import 'package:flutter/material.dart';
import 'package:flutterflow_ui/flutterflow_ui.dart'; import 'package:flutterflow_ui/flutterflow_ui.dart';
import 'package:intl/intl.dart'; import 'package:intl/intl.dart';
import 'package:vbvs_app/common/color/ServiceConstant.dart'; import 'package:vbvs_app/common/color/ServiceConstant.dart';
import 'package:vbvs_app/common/pojo/city.dart';
import 'package:vbvs_app/common/util/FitTool.dart'; import 'package:vbvs_app/common/util/FitTool.dart';
import 'package:vbvs_app/common/util/MyUtils.dart'; import 'package:vbvs_app/common/util/MyUtils.dart';
import 'package:vbvs_app/common/util/requestWithLog.dart'; import 'package:vbvs_app/common/util/requestWithLog.dart';
@@ -12,7 +13,9 @@ import 'package:vbvs_app/component/tool/TopSlideNotification.dart';
import 'package:vbvs_app/pages/common/selectDialog.dart'; import 'package:vbvs_app/pages/common/selectDialog.dart';
import 'package:vbvs_app/pages/mh_page/device/controller/mht_bluetooth_controller.dart'; import 'package:vbvs_app/pages/mh_page/device/controller/mht_bluetooth_controller.dart';
import 'package:vbvs_app/pages/mh_page/homepage/controller/mht_home_controller.dart'; import 'package:vbvs_app/pages/mh_page/homepage/controller/mht_home_controller.dart';
import 'package:vbvs_app/pages/person/select_city.dart';
//保存人员信息
class MHTPeopleInfoPage extends StatefulWidget { class MHTPeopleInfoPage extends StatefulWidget {
const MHTPeopleInfoPage({Key? key}) : super(key: key); const MHTPeopleInfoPage({Key? key}) : super(key: key);
@@ -22,10 +25,13 @@ class MHTPeopleInfoPage extends StatefulWidget {
class _MHTPeopleInfoPageState extends State<MHTPeopleInfoPage> { class _MHTPeopleInfoPageState extends State<MHTPeopleInfoPage> {
final MHTBlueToothController bluetoothController = Get.find(); final MHTBlueToothController bluetoothController = Get.find();
final CityModelController cityController = Get.find<CityModelController>();
final List<TextEditingController> _nameControllers = []; final List<TextEditingController> _nameControllers = [];
final List<TextEditingController> _contactControllers = []; final List<TextEditingController> _contactControllers = [];
List<Map<String, dynamic>> peopleList = []; List<Map<String, dynamic>> peopleList = [];
List<CityModel> cityModels = []; // 存储每个person的城市数据
bool isLoading = true; bool isLoading = true;
late Future<List<CityModel>> cityDataFuture;
@override @override
void initState() { void initState() {
@@ -34,11 +40,19 @@ class _MHTPeopleInfoPageState extends State<MHTPeopleInfoPage> {
} }
void _initializeData() async { void _initializeData() async {
// 先加载城市数据
cityDataFuture = cityController.loadAndSetCityData().then((success) {
return cityController.cityList;
});
// 等待城市数据加载完成后再初始化其他数据
await cityDataFuture;
final device = bluetoothController.currentFullDevice; final device = bluetoothController.currentFullDevice;
//todo 初始化传感器id //todo 初始化传感器id
// Initialize person A // Initialize person A
peopleList.add({ peopleList.add({
'mac'.tr: device?.macA, 'mac': device?.macA,
'gender': 1, 'gender': 1,
'id': device!.macAID, 'id': device!.macAID,
}); });
@@ -46,12 +60,15 @@ class _MHTPeopleInfoPageState extends State<MHTPeopleInfoPage> {
// Initialize person B if exists // Initialize person B if exists
if (device?.macB != null && device!.macB!.isNotEmpty) { if (device?.macB != null && device!.macB!.isNotEmpty) {
peopleList.add({ peopleList.add({
'mac'.tr: device.macB, 'mac': device.macB,
'gender': 1, 'gender': 1,
'id': device!.macBID, 'id': device!.macBID,
}); });
} }
// 初始化城市模型列表
cityModels = List.filled(peopleList.length, CityModel());
// Initialize controllers after data is loaded // Initialize controllers after data is loaded
_initializeControllers(); _initializeControllers();
setState(() => isLoading = false); setState(() => isLoading = false);
@@ -100,12 +117,11 @@ class _MHTPeopleInfoPageState extends State<MHTPeopleInfoPage> {
String serviceAddress = ServiceConstant.service_address; String serviceAddress = ServiceConstant.service_address;
String serviceName = ServiceConstant.server_service; String serviceName = ServiceConstant.server_service;
String serviceApi = ServiceConstant.personnel_info; String serviceApi = ServiceConstant.personnel_info;
String type = "user_message_setting";
String queryUrl = "${serviceAddress}${serviceName}${serviceApi}"; String queryUrl = "${serviceAddress}${serviceName}${serviceApi}";
try { try {
var body = { var body = {
'mac'.tr: personData['mac'.tr], 'mac': personData['mac'],
'name': personData['name'], 'name': personData['name'],
'gender': personData['gender'], 'gender': personData['gender'],
'height': personData['height'], 'height': personData['height'],
@@ -115,6 +131,8 @@ class _MHTPeopleInfoPageState extends State<MHTPeopleInfoPage> {
: personData['birthday'], : personData['birthday'],
'contact': personData['contact'], 'contact': personData['contact'],
'id': personData['id'], 'id': personData['id'],
'UTC': personData['UTC'],
'city_id': personData['city_id'],
}; };
await requestWithLog( await requestWithLog(
logTitle: "保存用户信息".tr, logTitle: "保存用户信息".tr,
@@ -130,22 +148,83 @@ class _MHTPeopleInfoPageState extends State<MHTPeopleInfoPage> {
print(res); print(res);
}, },
); );
// showToast("保存成功(${personData['mac']}", color: color_success);
} catch (e) { } catch (e) {
print("Error saving person data: $e"); print("Error saving person data: $e");
showToast("保存失败(${personData['mac']}"); }
}
// 根据城市ID查找完整的城市数据
CityModel? findCompleteCityDataById(int? id, List<CityModel> cityData) {
if (id == null) return null;
try {
// 遍历三级数据结构查找匹配的ID
for (var country in cityData) {
// 检查国家节点是否有ID匹配
if (country.id == id) {
return CityModel(
id: country.id,
value: country.value,
label: country.label,
country: country.value ?? country.country,
province: null,
city: null,
UTC: country.UTC,
children: country.children,
);
}
// 检查省份节点
for (var province in country.children ?? []) {
if (province.id == id) {
return CityModel(
id: province.id,
value: province.value,
label: province.label,
country: country.value ?? country.country,
province: province.value ?? province.province,
city: null,
UTC: province.UTC,
children: province.children,
);
}
// 检查城市节点
for (var city in province.children ?? []) {
if (city.id == id) {
return CityModel(
id: city.id,
value: city.value,
label: city.label,
country: country.value ?? country.country,
province: province.value ?? province.province,
city: city.value ?? city.city,
UTC: city.UTC,
children: city.children,
);
}
}
}
}
return null;
} catch (e) {
print("根据ID查找完整城市数据失败$e");
return null;
} }
} }
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
if (isLoading) { if (isLoading) {
return Center(child:CircularProgressIndicator( return Center(
child: CircularProgressIndicator(
strokeWidth: 2, strokeWidth: 2,
valueColor: AlwaysStoppedAnimation<Color>( valueColor: AlwaysStoppedAnimation<Color>(
themeController.currentColor.sc1, themeController.currentColor.sc1,
), ),
),); ),
);
} }
return LayoutBuilder( return LayoutBuilder(
@@ -193,19 +272,84 @@ class _MHTPeopleInfoPageState extends State<MHTPeopleInfoPage> {
borderRadius: 16.rpx, borderRadius: 16.rpx,
gradientDirection: GradientDirection.vertical, gradientDirection: GradientDirection.vertical,
onTap: () async { onTap: () async {
// Save all people data // 数据验证
for (var person in peopleList) { bool isValid = true;
for (int i = 0; i < peopleList.length; i++) {
var person = peopleList[i];
// 验证身高
if (person['height'] != null &&
person['height'].toString().isNotEmpty &&
int.tryParse(person['height'].toString()) ==
null) {
TopSlideNotification.show(context,
text: "请选择身高".tr,
textColor: Color(0xFFFF7159));
isValid = false;
break;
}
// 验证体重
if (person['weight'] != null &&
person['weight'].toString().isNotEmpty &&
int.tryParse(person['weight'].toString()) ==
null) {
TopSlideNotification.show(context,
text: "请选择体重".tr,
textColor: Color(0xFFFF7159));
isValid = false;
break;
}
// 验证联系方式
if (person['contact'] != null &&
person['contact'].toString().isNotEmpty &&
!MyUtils.isValidPhoneNumber(
person['contact'].toString())) {
TopSlideNotification.show(context,
text: "请输入正确的联系人电话".tr,
textColor: Color(0xFFFF7159));
isValid = false;
break;
}
// 验证城市选择
final cityModel = cityModels[i];
if (cityModel.id == null) {
TopSlideNotification.show(context,
text: "请选择城市".tr,
textColor: Color(0xFFFF7159));
isValid = false;
break;
}
}
if (isValid) {
// 保存所有人员数据
for (int i = 0; i < peopleList.length; i++) {
final person = peopleList[i];
final cityModel = cityModels[i];
// 添加城市信息到person数据
person['UTC'] = cityModel.UTC;
person['city_id'] = cityModel.id;
await _savePersonData(person, context); await _savePersonData(person, context);
} }
TopSlideNotification.show(context, text: "保存成功".tr); TopSlideNotification.show(context, text: "保存成功".tr);
MHTHomeController mhtHomeController = Get.find(); MHTHomeController mhtHomeController = Get.find();
mhtHomeController.getPersonList(); mhtHomeController.getPersonList();
// Get.offNamed("/bindDeviceSuccess");
// 跳转到下一页
Map data = {}; Map data = {};
final device = bluetoothController.currentFullDevice; final device =
bluetoothController.currentFullDevice;
data['_id'] = device!.deviceID; data['_id'] = device!.deviceID;
data['isNextStep'] = true; data['isNextStep'] = true;
Get.toNamed("/editBedPage", arguments: data); Get.toNamed("/editBedPage", arguments: data);
}
}, },
colors: const [ colors: const [
Color(0xFFFCFCFC), Color(0xFFFCFCFC),
@@ -400,7 +544,7 @@ class _MHTPeopleInfoPageState extends State<MHTPeopleInfoPage> {
() { () {
showHeightPickerDialog( showHeightPickerDialog(
context, context,
title: "选择分数".tr, title: "选择身高".tr,
initialHeight: int.tryParse( initialHeight: int.tryParse(
peopleList[index]['height'] ?? peopleList[index]['height'] ??
'170') ?? '170') ??
@@ -468,7 +612,6 @@ class _MHTPeopleInfoPageState extends State<MHTPeopleInfoPage> {
showWeightPickerDialog( showWeightPickerDialog(
context, context,
title: "选择体重".tr, title: "选择体重".tr,
initialWeight: "50", initialWeight: "50",
onConfirm: (int selectedWeight) { onConfirm: (int selectedWeight) {
setState(() { setState(() {
@@ -650,6 +793,80 @@ class _MHTPeopleInfoPageState extends State<MHTPeopleInfoPage> {
), ),
), ),
getLine(), getLine(),
// 城市选择部分
Container(
height: 90.rpx,
margin: EdgeInsets.only(
left: 40.rpx, right: 35.rpx),
child: InkWell(
onTap: () {
FocusScope.of(context)
.requestFocus(FocusNode());
Future.delayed(
const Duration(milliseconds: 250),
() {
showCitySelectionDialog(
context,
selectedCity: cityModels[index],
onCityChanged: (CityModel newCity) {
setState(() {
cityModels[index] = newCity;
});
},
title: "选择城市".tr,
cityDataFuture: cityDataFuture,
colors: CitySelectionColors(
pickerBackgroundColor:
stringToColor("#003058"),
confirmTextColor:
stringToColor("#84F5FF"),
selectedCityColor:
stringToColor("#84F5FF"),
),
);
});
},
child: Row(
mainAxisAlignment:
MainAxisAlignment.spaceBetween,
children: [
Text(
'请选择城市'.tr,
style: TextStyle(
fontFamily: 'Readex Pro',
color: Color(0xFF9EA4B7),
fontSize: 30.rpx,
letterSpacing: 0,
),
),
Row(
children: [
Text(
cityModels[index].id != null
? MyUtils
.getDetailedCityDisplayText(
cityModels[index])
: "请选择城市".tr,
style: TextStyle(
color:
cityModels[index].id != null
? Colors.white
: themeController
.currentColor.sc4,
fontSize: 30.rpx,
),
),
SizedBox(width: 16.rpx),
Icon(Icons.expand_more,
color: Colors.white,
size: 48.rpx),
],
),
],
),
),
),
getLine(),
], ],
)) ))
], ],
@@ -667,3 +884,4 @@ class _MHTPeopleInfoPageState extends State<MHTPeopleInfoPage> {
); );
} }
} }

View File

@@ -1,24 +1,22 @@
import 'dart:async'; import 'dart:async';
import 'package:ef/ef.dart'; import 'package:ef/ef.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter/widgets.dart';
import 'package:flutter_svg/svg.dart'; import 'package:flutter_svg/svg.dart';
import 'package:flutterflow_ui/flutterflow_ui.dart'; import 'package:flutterflow_ui/flutterflow_ui.dart';
import 'package:vbvs_app/common/color/appConstants.dart';
import 'package:vbvs_app/common/pojo/city.dart';
import 'package:vbvs_app/common/util/FitTool.dart'; import 'package:vbvs_app/common/util/FitTool.dart';
import 'package:vbvs_app/common/util/MyUtils.dart'; import 'package:vbvs_app/common/util/MyUtils.dart';
import 'package:vbvs_app/component/tool/CustomCard.dart'; import 'package:vbvs_app/component/tool/CustomCard.dart';
import 'package:vbvs_app/component/tool/TopSlideNotification.dart'; import 'package:vbvs_app/component/tool/TopSlideNotification.dart';
import 'package:vbvs_app/controller/home/home_controller.dart';
import 'package:vbvs_app/controller/main_bottom/global_controller.dart';
import 'package:vbvs_app/controller/mh_controller/people_info_controller.dart'; import 'package:vbvs_app/controller/mh_controller/people_info_controller.dart';
import 'package:vbvs_app/controller/person/person_controller.dart';
import 'package:vbvs_app/pages/common/selectDialog.dart'; import 'package:vbvs_app/pages/common/selectDialog.dart';
import 'package:vbvs_app/pages/mh_page/homepage/controller/mht_home_controller.dart'; import 'package:vbvs_app/pages/mh_page/homepage/controller/mht_home_controller.dart';
import 'package:vbvs_app/pages/mh_page/test/WebviewTestModel.dart'; import 'package:vbvs_app/pages/mh_page/test/WebviewTestModel.dart';
import 'package:vbvs_app/pages/person/select_city.dart';
//更新人员信息
class PeopleInfoPage extends GetView<PeopleInfoController> { class PeopleInfoPage extends GetView<PeopleInfoController> {
Map data; Map data;
PeopleInfoPage({required this.data}); PeopleInfoPage({required this.data});
@@ -32,6 +30,7 @@ class PeopleInfoPage extends GetView<PeopleInfoController> {
} }
PeopleInfoController controller = Get.put(PeopleInfoController()); PeopleInfoController controller = Get.put(PeopleInfoController());
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
getPersonData(); getPersonData();
@@ -123,6 +122,22 @@ class PeopleInfoPage extends GetView<PeopleInfoController> {
isValid = false; isValid = false;
break; break;
} }
// if (d['UTC'] == null ||
// d['UTC'].toString().isEmpty) {
// TopSlideNotification.show(context,
// text: "请选择城市".tr,
// textColor: Color(0xFFFF7159));
// isValid = false;
// break;
// }
// if (d['city_id'] ==null ||
// d['city_id'].toString().isEmpty) {
// TopSlideNotification.show(context,
// text: "请选择城市".tr,
// textColor: Color(0xFFFF7159));
// isValid = false;
// break;
// }
} }
// 所有数据合法,开始保存 // 所有数据合法,开始保存
if (isValid) { if (isValid) {
@@ -785,6 +800,137 @@ class PeopleInfoPage extends GetView<PeopleInfoController> {
), ),
), ),
getLine(), getLine(),
Container(
height: 90.rpx,
margin: EdgeInsets.only(
left: 40.rpx, right: 35.rpx),
child: InkWell(
onTap: () {
// if (widget.status ==
// BindType.share.code) {
// TopSlideNotification.show(
// context,
// text: "被分享用户只能修改用户名称",
// textColor:
// themeController
// .currentColor
// .sc9);
// return;
// }
FocusScope.of(context)
.requestFocus(
FocusNode());
Future.delayed(
Duration(
milliseconds: 250),
() {
// 使用当前选中的城市数据,如果没有则创建默认
CityModel? currentCity;
if (controller
.model
.cityModels
.isNotEmpty &&
index <
controller
.model
.cityModels
.length) {
currentCity = controller
.model
.cityModels[index];
} else {
currentCity = CityModel();
}
showCitySelectionDialog(
context,
selectedCity: currentCity,
onCityChanged:
(CityModel newCity) {
final list = controller
.model.cityModels;
if (index <
list.length) {
// 替换
list[index] = newCity;
} else {
// 补齐并追加
list.add(newCity);
}
controller.model
.peopleList[
index]['UTC'] =
list[index].UTC;
controller.model
.peopleList[
index]
['city_id'] = list[
index]
.id;
controller.updateAll();
},
title: "选择城市".tr,
cityDataFuture: controller
.cityDataFuture, // 传入预加载的数据
colors:
CitySelectionColors(
pickerBackgroundColor:
stringToColor(
"#003058"),
confirmTextColor:
stringToColor(
"#84F5FF"),
selectedCityColor:
stringToColor(
"#84F5FF"),
),
);
});
},
child: Row(
mainAxisAlignment:
MainAxisAlignment
.spaceBetween,
children: [
Text(
'请选择城市'.tr,
style: TextStyle(
fontFamily:
'Readex Pro',
color:
Color(0xFF9EA4B7),
fontSize: 30.rpx,
letterSpacing: 0,
),
),
Text(
getCityModel(index) !=
null
? MyUtils
.getDetailedCityDisplayText(
getCityModel(
index))
: "请选择城市".tr,
style: TextStyle(
color: getCityModel(
index) !=
null
? themeController
.currentColor
.sc3
: themeController
.currentColor
.sc4,
fontSize: AppConstants()
.title_text_fontSize,
),
),
],
),
),
),
getLine(),
], ],
), ),
) )
@@ -819,4 +965,10 @@ class PeopleInfoPage extends GetView<PeopleInfoController> {
await peopleInfoController await peopleInfoController
.getPeoples(Get.arguments['mac'.tr]); // 控制器创建时立即执行 .getPeoples(Get.arguments['mac'.tr]); // 控制器创建时立即执行
} }
CityModel? getCityModel(int index) {
final list = controller.model.cityModels;
if (list.isEmpty || index >= list.length) return null;
return list[index];
}
} }

View File

@@ -37,16 +37,35 @@ Future<List<CityModel>> loadCityData() async {
} }
} }
// 定义城市选择器颜色配置
class CitySelectionColors {
final Color? pickerBackgroundColor; // 选择器整体背景色
final Color? confirmTextColor; // 确定按钮文字颜色
final Color? selectedCityColor; // 选中的城市背景色
const CitySelectionColors({
this.pickerBackgroundColor,
this.confirmTextColor,
this.selectedCityColor,
});
}
Future showCitySelectionDialog( Future showCitySelectionDialog(
BuildContext context, { BuildContext context, {
required CityModel selectedCity, required CityModel selectedCity,
Function? onCityChanged, Function? onCityChanged,
String title = "选择城市", String title = "选择城市",
required Future<List<CityModel>> cityDataFuture, // 改为required参数 required Future<List<CityModel>> cityDataFuture, // 改为required参数
CitySelectionColors? colors, // 新增:颜色配置参数
}) { }) {
ThemeController themeController = Get.find(); ThemeController themeController = Get.find();
final bool isChinese = Get.locale?.languageCode == 'zh' ?? true; final bool isChinese = Get.locale?.languageCode == 'zh' ?? true;
// 使用传入的颜色,如果没传则使用主题颜色
final Color pickerBackgroundColor = colors?.pickerBackgroundColor ?? themeController.currentColor.sc17;
final Color confirmTextColor = colors?.confirmTextColor ?? themeController.currentColor.sc2;
final Color selectedCityColor = colors?.selectedCityColor ?? themeController.currentColor.sc2;
final RxList<String> countries = <String>[].obs; final RxList<String> countries = <String>[].obs;
final RxList<String> provinces = <String>[].obs; final RxList<String> provinces = <String>[].obs;
final RxList<String> cities = <String>[].obs; final RxList<String> cities = <String>[].obs;
@@ -243,12 +262,21 @@ Future showCitySelectionDialog(
builder: (context, snapshot) { builder: (context, snapshot) {
// 数据加载中 // 数据加载中
if (snapshot.connectionState == ConnectionState.waiting) { if (snapshot.connectionState == ConnectionState.waiting) {
return _buildLoadingBottomSheet(themeController); return _buildLoadingBottomSheet(
themeController,
pickerBackgroundColor,
confirmTextColor,
);
} }
// 数据加载错误 // 数据加载错误
if (snapshot.hasError || !snapshot.hasData) { if (snapshot.hasError || !snapshot.hasData) {
return _buildErrorBottomSheet(themeController, context); return _buildErrorBottomSheet(
themeController,
context,
pickerBackgroundColor,
confirmTextColor,
);
} }
final cityData = snapshot.data!; final cityData = snapshot.data!;
@@ -265,6 +293,9 @@ Future showCitySelectionDialog(
title, title,
cityData, cityData,
onCityChanged, onCityChanged,
pickerBackgroundColor: pickerBackgroundColor,
confirmTextColor: confirmTextColor,
selectedCityColor: selectedCityColor,
countries: countries, countries: countries,
provinces: provinces, provinces: provinces,
cities: cities, cities: cities,
@@ -350,6 +381,9 @@ Widget _buildCityPickerContent(
String title, String title,
List<CityModel> cityData, List<CityModel> cityData,
Function? onCityChanged, { Function? onCityChanged, {
required Color pickerBackgroundColor,
required Color confirmTextColor,
required Color selectedCityColor,
required RxList<String> countries, required RxList<String> countries,
required RxList<String> provinces, required RxList<String> provinces,
required RxList<String> cities, required RxList<String> cities,
@@ -481,7 +515,7 @@ Widget _buildCityPickerContent(
return Container( return Container(
width: double.infinity, width: double.infinity,
decoration: BoxDecoration( decoration: BoxDecoration(
color: themeController.currentColor.sc17, color: pickerBackgroundColor, // 使用传入的选择器整体颜色
borderRadius: BorderRadius.only( borderRadius: BorderRadius.only(
topLeft: Radius.circular(20.rpx), topLeft: Radius.circular(20.rpx),
topRight: Radius.circular(20.rpx), topRight: Radius.circular(20.rpx),
@@ -549,7 +583,7 @@ Widget _buildCityPickerContent(
child: Text("确定".tr, child: Text("确定".tr,
style: TextStyle( style: TextStyle(
fontSize: 30.rpx, fontSize: 30.rpx,
color: themeController.currentColor.sc2, color: confirmTextColor, // 使用传入的确定文字颜色
)), )),
), ),
); );
@@ -600,7 +634,7 @@ Widget _buildCityPickerContent(
height: 90.rpx, height: 90.rpx,
margin: EdgeInsets.symmetric(horizontal: 0.rpx), margin: EdgeInsets.symmetric(horizontal: 0.rpx),
decoration: BoxDecoration( decoration: BoxDecoration(
color: themeController.currentColor.sc2, color: selectedCityColor, // 使用传入的选中城市颜色
borderRadius: BorderRadius.circular(16.rpx), borderRadius: BorderRadius.circular(16.rpx),
), ),
), ),
@@ -677,11 +711,15 @@ Widget _buildCityPickerContent(
} }
// 加载中 BottomSheet // 加载中 BottomSheet
Widget _buildLoadingBottomSheet(ThemeController themeController) { Widget _buildLoadingBottomSheet(
ThemeController themeController,
Color pickerBackgroundColor,
Color confirmTextColor,
) {
return Container( return Container(
width: double.infinity, width: double.infinity,
decoration: BoxDecoration( decoration: BoxDecoration(
color: themeController.currentColor.sc17, color: pickerBackgroundColor,
borderRadius: BorderRadius.only( borderRadius: BorderRadius.only(
topLeft: Radius.circular(20.rpx), topLeft: Radius.circular(20.rpx),
topRight: Radius.circular(20.rpx), topRight: Radius.circular(20.rpx),
@@ -692,7 +730,7 @@ Widget _buildLoadingBottomSheet(ThemeController themeController) {
mainAxisSize: MainAxisSize.min, mainAxisSize: MainAxisSize.min,
children: [ children: [
CircularProgressIndicator( CircularProgressIndicator(
color: themeController.currentColor.sc2, color: confirmTextColor,
), ),
SizedBox(height: 20.rpx), SizedBox(height: 20.rpx),
Text( Text(
@@ -709,11 +747,15 @@ Widget _buildLoadingBottomSheet(ThemeController themeController) {
// 错误 BottomSheet // 错误 BottomSheet
Widget _buildErrorBottomSheet( Widget _buildErrorBottomSheet(
ThemeController themeController, BuildContext context) { ThemeController themeController,
BuildContext context,
Color pickerBackgroundColor,
Color confirmTextColor,
) {
return Container( return Container(
width: double.infinity, width: double.infinity,
decoration: BoxDecoration( decoration: BoxDecoration(
color: themeController.currentColor.sc17, color: pickerBackgroundColor,
borderRadius: BorderRadius.only( borderRadius: BorderRadius.only(
topLeft: Radius.circular(20.rpx), topLeft: Radius.circular(20.rpx),
topRight: Radius.circular(20.rpx), topRight: Radius.circular(20.rpx),
@@ -739,7 +781,7 @@ Widget _buildErrorBottomSheet(
child: Container( child: Container(
padding: EdgeInsets.symmetric(horizontal: 30.rpx, vertical: 15.rpx), padding: EdgeInsets.symmetric(horizontal: 30.rpx, vertical: 15.rpx),
decoration: BoxDecoration( decoration: BoxDecoration(
color: themeController.currentColor.sc2, color: confirmTextColor,
borderRadius: BorderRadius.circular(8.rpx), borderRadius: BorderRadius.circular(8.rpx),
), ),
child: Text( child: Text(

View File

@@ -632,7 +632,7 @@ class _UpdatePageState extends State<UpdatePersonPage> {
}, },
child: Center( child: Center(
child: Text( child: Text(
_getDetailedCityDisplayText( MyUtils.getDetailedCityDisplayText(
personController.cityModel), personController.cityModel),
textAlign: TextAlign.right, textAlign: TextAlign.right,
style: TextStyle( style: TextStyle(
@@ -650,6 +650,7 @@ class _UpdatePageState extends State<UpdatePersonPage> {
), ),
), ),
), ),
Padding( Padding(
padding: EdgeInsetsDirectional.fromSTEB( padding: EdgeInsetsDirectional.fromSTEB(
0, 117.rpx, 0, 0), 0, 117.rpx, 0, 0),
@@ -858,28 +859,4 @@ class _UpdatePageState extends State<UpdatePersonPage> {
); );
} }
// 获取城市显示文本
// 更详细的显示逻辑(可选)
String _getDetailedCityDisplayText(CityModel? cityModel) {
if (cityModel == null) {
return '选择城市'.tr;
}
// 根据数据层级显示不同的格式
if (cityModel.city != null && cityModel.city!.isNotEmpty) {
// 三级数据:国家-省份-城市
return '${cityModel.country ?? ''}-${cityModel.province ?? ''}-${cityModel.city ?? cityModel.value ?? ''}';
} else if (cityModel.province != null && cityModel.province!.isNotEmpty) {
// 二级数据:国家-省份
return '${cityModel.country ?? ''}-${cityModel.province ?? cityModel.value ?? ''}';
} else if (cityModel.country != null && cityModel.country!.isNotEmpty) {
// 一级数据:国家
return cityModel.country!;
} else if (cityModel.value != null && cityModel.value!.isNotEmpty) {
// 只有 value 字段
return cityModel.value!;
} else {
return '选择城市'.tr;
}
}
} }