import 'package:flutter/material.dart'; import 'package:eatvio_app/core/app_export.dart'; import 'package:eatvio_app/presentation/profile/my_profile_screen/bloc/my_profile_bloc.dart'; import 'package:eatvio_app/widgets/custom_hyper_switch.dart'; import 'package:eatvio_app/widgets/custom_hypo_switch.dart'; import 'package:intl/intl.dart'; import 'package:eatvio_app/widgets/next_step_button.dart'; import 'dart:convert'; import 'package:flutter_dotenv/flutter_dotenv.dart'; import 'package:hive/hive.dart'; import 'package:flutter/services.dart'; import 'package:http/http.dart' as http; class ExpandableList extends StatefulWidget { final String title; ExpandableList(this.title); @override _ExpandableListState createState() => _ExpandableListState(); } class _ExpandableListState extends State { bool isExpanded = false; @override Widget build(BuildContext context) { return Column( crossAxisAlignment: CrossAxisAlignment.stretch, children: [ GestureDetector( onTap: toggleExpand(), child: Row( mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [ Text( widget.title, style: TextStyle( color: Colors.black, fontSize: 14, fontWeight: FontWeight.bold), ), Icon(isExpanded ? Icons.arrow_drop_up : Icons.arrow_drop_down), ], ), ), if (isExpanded) Padding( padding: const EdgeInsets.only(left: 16.0), child: BlocBuilder( builder: (context, state) { if (state is MyProfileInitialState) { // Это начальное состояние, данные ещё не загружены. return CircularProgressIndicator( color: Colors.white, backgroundColor: Colors.white, ); } else if (state is MyProfileLoadedState) { // Данные загружены, можно строить форму. return _buildForm(context, state); } else if (state is MyProfileErrorState) { // Произошла ошибка при загрузке данных. return Center(child: Text(state.errorMessage)); } else { // Другие состояния, если они есть. return Container(); // Пустой контейнер для необработанных состояний. } }), ), Divider(), ], ); } toggleExpand() { return () { setState(() { isExpanded = !isExpanded; }); }; } _buildForm(BuildContext context, MyProfileLoadedState state) { List cities = [ 'Москва', 'Санкт-Петербург', 'Новосибирск', 'Екатеринбург', 'Нижний Новгород', 'Казань', 'Челябинск', 'Омск', 'Самара', 'Ростов-на-Дону', 'Уфа', 'Красноярск', 'Воронеж', 'Пермь', 'Волгоград', 'Краснодар', 'Саратов', 'Тюмень', 'Тольятти', 'Ижевск', 'Барнаул', 'Ульяновск', 'Иркутск', 'Хабаровск', 'Ярославль', 'Владивосток', 'Махачкала', 'Томск', 'Оренбург', 'Кемерово', ]; List countries = [ 'Россия', ]; final digitsOnly = FilteringTextInputFormatter.digitsOnly; return Column(children: [ TextField( controller: state.firstNameFormController, decoration: InputDecoration(labelText: 'first_name'.tr), ), TextField( controller: state.lastNameFormController, decoration: InputDecoration(labelText: 'last_name'.tr), ), TextField( decoration: InputDecoration(labelText: 'date_of_birth'.tr), controller: state.dateFormController, onTap: inputTime(context, state)), DropdownButtonFormField( value: state.selectedCountry, hint: Text(state.selectedCountry ?? "Не выбрано"), onChanged: setCountry(state), items: countries.map>((String value) { return DropdownMenuItem( value: value, child: Text(value), ); }).toList(), decoration: InputDecoration(labelText: 'country'.tr), ), DropdownButtonFormField( hint: Text(state.selectedCity ?? "Не выбрано"), value: state.selectedCity, onChanged: setCity(state), items: cities.map>((String value) { return DropdownMenuItem( value: value, child: Text(value), ); }).toList(), decoration: InputDecoration(labelText: 'city_of_living'.tr), ), TextField( controller: state.weightFormController, decoration: InputDecoration(labelText: 'weight_measurements'.tr), keyboardType: TextInputType.number, inputFormatters: [digitsOnly]), TextField( controller: state.heightFormController, decoration: InputDecoration(labelText: 'height_measurements'.tr), keyboardType: TextInputType.number, inputFormatters: [digitsOnly]), TextField( controller: state.chestCircumferenceFormController, decoration: InputDecoration(labelText: 'chest_circumference'.tr), keyboardType: TextInputType.number, inputFormatters: [digitsOnly]), TextField( controller: state.waistCircumferenceFormController, decoration: InputDecoration(labelText: 'waist_circumference'.tr), keyboardType: TextInputType.number, inputFormatters: [digitsOnly]), TextField( controller: state.hipCircumferenceFormController, decoration: InputDecoration(labelText: 'hip_circumference'.tr), keyboardType: TextInputType.number, inputFormatters: [digitsOnly]), TextField( controller: state.upPressureFormController, decoration: InputDecoration(labelText: 'up_pressure'.tr), keyboardType: TextInputType.number, inputFormatters: [digitsOnly]), TextField( controller: state.downPressureFormController, decoration: InputDecoration(labelText: 'down_pressure'.tr), keyboardType: TextInputType.number, inputFormatters: [digitsOnly]), TextField( controller: state.allergiesFormController, decoration: InputDecoration(labelText: 'allergies_presence'.tr), maxLines: null, ), TextField( controller: state.pillsFormController, decoration: InputDecoration(labelText: 'do_you_take_pills'.tr), maxLines: null, ), TextField( controller: state.sportsFormController, decoration: InputDecoration(labelText: 'your_favorite_sports'.tr), maxLines: null, ), TextField( controller: state.favoriteFormController, decoration: InputDecoration(labelText: 'favorite_foods'.tr), maxLines: null, ), TextField( controller: state.unfavoriteFormController, decoration: InputDecoration(labelText: 'unfavorite_foods'.tr), maxLines: null, ), TextField( controller: state.additionalFormController, decoration: InputDecoration(labelText: 'additional_information'.tr), maxLines: null, ), Row( children: [ HypoSwitch('do_you_have_hypotension_tendency'.tr, state), ], ), Row( children: [ HyperSwitch('do_you_have_hypertension_tendency'.tr, state), ], ), NextStepButton( onPressed: sendData(state), buttonStyle: CustomButtonStyles.outlinePrimaryTL15, text: "save".tr.toUpperCase(), margin: EdgeInsets.only(top: 20.h, bottom: 20.h)), ]); } sendData(MyProfileLoadedState state) { return () { sendProfileData(state); }; } setCity(MyProfileLoadedState state) { return (newValue) { // Обработчик изменения выбранного города setSelectedCity(state, newValue); }; } setCountry(MyProfileLoadedState state) { return (newValue) { // Обработчик изменения выбранной страны setSelectedCountry(state, newValue); }; } inputTime(BuildContext context, MyProfileLoadedState state) { return () { showDatePicker( context: context, initialDate: DateTime.now(), firstDate: DateTime(1900), lastDate: DateTime.now(), ).then((selectedDate) { if (selectedDate != null) { setState(() { state.dateFormController!.text = DateFormat('dd-MM-yyyy').format(selectedDate); }); } }); }; } void setSelectedCity(MyProfileLoadedState? state, String? newValue) { setState(() { state!.selectedCity = newValue; }); } void setSelectedCountry(MyProfileLoadedState? state, String? newValue) { setState(() { state!.selectedCountry = newValue; }); } Future sendProfileData(MyProfileLoadedState? state) async { try { // Создаем JSON объект с данными профиля Map profileData = { 'first_name': state?.firstNameFormController?.text, 'last_name': state?.lastNameFormController?.text, 'chest_circumference': state?.chestCircumferenceFormController?.text, 'waist_circumference': state?.waistCircumferenceFormController?.text, 'hip_circumference': state?.hipCircumferenceFormController?.text, 'birthdate': state?.dateFormController?.text, 'height': state?.heightFormController?.text, 'weight': state?.weightFormController?.text, 'blood_pressure_up': state?.upPressureFormController?.text, 'blood_pressure_down': state?.downPressureFormController?.text, 'about_alergy': state?.allergiesFormController?.text, 'about_taking_pils': state?.pillsFormController?.text, 'about_sport_hobbies': state?.sportsFormController?.text, 'favorite_foods': state?.favoriteFormController?.text, 'unfavorite_foods': state?.unfavoriteFormController?.text, 'additional_info': state?.additionalFormController?.text, 'country': state?.selectedCountry ?? 'Россия', 'city': state?.selectedCity ?? 'Москва', 'has_hypo': state?.hypoFormController, 'has_hyper': state?.hyperFormController, }; final box = await Hive.openBox('token'); final token = box.get('token'); String apiUrl = dotenv.env['SERVER_ROOT']! + '/profile/update'; http.Response response = await http.post( Uri.parse(apiUrl), body: json.encode(profileData), encoding: utf8, headers: { 'Content-Type': 'application/json', 'Authorization': 'Bearer $token', }, ); print(response.body); if (response.statusCode == 200) { Navigator.pushNamed( context, AppRoutes.myProfile, ); } else { showDialog( context: context, builder: (context) => AlertDialog( title: Text('Ошибка'), content: Text('Ошибка при отправке данных профиля'.tr), actions: [ TextButton( onPressed: onTapOk(context), child: Text('OK'), ), ], ), ); throw Exception('Ошибка при отправке данных профиля'); } } catch (error) { throw Exception('Ошибка при отправке данных профиля: $error'); } } onTapOk(BuildContext context) { return () { Navigator.pop(context); }; } }