feat(chat): Cheatroom layouts and API data load

This commit is contained in:
2024-05-03 13:20:52 +03:00
parent c8a612186e
commit 6869287c85
3 changed files with 123 additions and 55 deletions

View File

@@ -1,5 +1,9 @@
import 'package:equatable/equatable.dart'; import 'package:equatable/equatable.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_dotenv/flutter_dotenv.dart';
import 'package:hive/hive.dart';
import 'package:http/http.dart' as http;
import 'dart:convert';
import '/core/app_export.dart'; import '/core/app_export.dart';
import 'package:eatvio_app/presentation/chat/chat_screen/models/chat_model.dart'; import 'package:eatvio_app/presentation/chat/chat_screen/models/chat_model.dart';
part 'chat_event.dart'; part 'chat_event.dart';
@@ -15,6 +19,42 @@ class ChatBloc extends Bloc<ChatEvent, ChatState> {
ChatInitialEvent event, ChatInitialEvent event,
Emitter<ChatState> emit, Emitter<ChatState> emit,
) async { ) async {
emit(state.copyWith(chatModelObj: state.chatModelObj?.copyWith())); try {
final box = await Hive.openBox('token');
final token = box.get('token');
if (token == null) {
NavigatorService.popAndPushNamed(
AppRoutes.authScreen,
);
}
final int id = 1;
final response = await http.get(
Uri.parse(dotenv.env['SERVER_ROOT']! + '/chat/$id/show'),
headers: {
'Authorization': 'Bearer $token',
},
);
if (response.statusCode == 200) {
final data = jsonDecode(response.body);
print(data['chatRooms']);
if (data is Map<String, dynamic> && data.containsKey('chatRooms')) {
if (state is ChatLoadedState) {
var currentState = state as ChatLoadedState;
emit(currentState.copyWith());
} else {
emit(ChatLoadedState());
}
} else {
// Один или несколько ключевых полей отсутствуют, обрабатываем ошибку
emit(ChatErrorState('Некоторые необходимые данные отсутствуют.'));
}
} else {
// Статус ответа не равен 200, обрабатываем ошибку
emit(ChatErrorState('Ошибка сервера: ${response.statusCode}'));
}
} catch (e) {
// Ошибка при декодировании JSON или другая ошибка выполнения
emit(ChatErrorState('Ошибка при получении данных о чатах: $e'));
}
} }
} }

View File

@@ -3,8 +3,26 @@
part of 'chat_bloc.dart'; part of 'chat_bloc.dart';
/// Represents the state of Chat in the application. /// Represents the state of Chat in the application.
///
class ChatState extends Equatable { class ChatState extends Equatable {
ChatState({ ChatState({
this.chatModelObj,
});
ChatModel? chatModelObj;
@override
List<Object?> get props => [chatModelObj];
ChatState copyWith({ChatModel? chatModelObj}) {
return ChatState(
chatModelObj: chatModelObj ?? this.chatModelObj,
);
}
}
class ChatLoadedState extends ChatState {
ChatLoadedState({
this.selectedDropDownValue, this.selectedDropDownValue,
this.chatModelObj, this.chatModelObj,
}); });
@@ -23,9 +41,21 @@ class ChatState extends Equatable {
ChatModel? chatModelObj, ChatModel? chatModelObj,
}) { }) {
return ChatState( return ChatState(
selectedDropDownValue:
selectedDropDownValue ?? this.selectedDropDownValue,
chatModelObj: chatModelObj ?? this.chatModelObj, chatModelObj: chatModelObj ?? this.chatModelObj,
); );
} }
} }
class ChatErrorState extends ChatState {
final String errorMessage;
ChatErrorState(this.errorMessage);
@override
List<Object> get props => [errorMessage];
}
class ChatInitialState extends ChatState {
ChatInitialState({required ChatModel chatModelObj})
: super(chatModelObj: chatModelObj);
}

View File

@@ -207,7 +207,7 @@ class MyProfileScreen extends StatelessWidget {
context, context,
state.chartPoints?.values state.chartPoints?.values
.map<int>((e) => e['weight']) .map<int>((e) => e['weight'])
.toList() .toList()
.map((i) => i.toDouble()) .map((i) => i.toDouble())
.toList() ?? .toList() ??
[0.0, 0.0, 0.0, 0.0], [0.0, 0.0, 0.0, 0.0],
@@ -800,56 +800,56 @@ class MyProfileScreen extends StatelessWidget {
//final digitsOnly = FilteringTextInputFormatter.digitsOnly; //final digitsOnly = FilteringTextInputFormatter.digitsOnly;
return AlertDialog( return AlertDialog(
title: Center(child: Text("Добавить замер")), title: Center(child: Text("Добавить замер")),
content: SizedBox( content: SizedBox(
width: 200, // Ширина диалогового окна width: 200, // Ширина диалогового окна
height: 300, // Высота диалогового окна height: 300, // Высота диалогового окна
child: ListView( child: ListView(
children: [ children: [
Padding( Padding(
padding: EdgeInsets.symmetric(vertical: 5.v), padding: EdgeInsets.symmetric(vertical: 5.v),
child: Text("chest_circumference".tr, child: Text("chest_circumference".tr,
style: theme.textTheme.bodyLarge), style: theme.textTheme.bodyLarge),
), ),
SizedBox(height: 5.v), SizedBox(height: 5.v),
CustomTextFormField( CustomTextFormField(
controller: state.chestCircumferenceController, controller: state.chestCircumferenceController,
keyboardType: TextInputType.number, keyboardType: TextInputType.number,
inputFormatters: <TextInputFormatter>[ inputFormatters: <TextInputFormatter>[
FilteringTextInputFormatter FilteringTextInputFormatter
.digitsOnly, // Ограничение ввода только цифрами .digitsOnly, // Ограничение ввода только цифрами
],
),
Padding(
padding: EdgeInsets.symmetric(vertical: 15.v),
child: Text("waist_circumference".tr,
style: theme.textTheme.bodyLarge),
),
SizedBox(height: 5.v),
CustomTextFormField(
controller: state.waistCircumferenceController,
keyboardType: TextInputType.number,
inputFormatters: <TextInputFormatter>[
FilteringTextInputFormatter
.digitsOnly, // Ограничение ввода только цифрами
],
),
Padding(
padding: EdgeInsets.symmetric(vertical: 15.v),
child: Text("hip_circumference".tr,
style: theme.textTheme.bodyLarge),
),
SizedBox(height: 5.v),
CustomTextFormField(
controller: state.hipCircumferenceController,
keyboardType: TextInputType.number,
inputFormatters: <TextInputFormatter>[
FilteringTextInputFormatter
.digitsOnly, // Ограничение ввода только цифрами
],
),
], ],
), )),
Padding(
padding: EdgeInsets.symmetric(vertical: 15.v),
child: Text("waist_circumference".tr,
style: theme.textTheme.bodyLarge),
),
SizedBox(height: 5.v),
CustomTextFormField(
controller: state.waistCircumferenceController,
keyboardType: TextInputType.number,
inputFormatters: <TextInputFormatter>[
FilteringTextInputFormatter
.digitsOnly, // Ограничение ввода только цифрами
],
),
Padding(
padding: EdgeInsets.symmetric(vertical: 15.v),
child: Text("hip_circumference".tr,
style: theme.textTheme.bodyLarge),
),
SizedBox(height: 5.v),
CustomTextFormField(
controller: state.hipCircumferenceController,
keyboardType: TextInputType.number,
inputFormatters: <TextInputFormatter>[
FilteringTextInputFormatter
.digitsOnly, // Ограничение ввода только цифрами
],
),
],
)),
actions: [ actions: [
TextButton( TextButton(
onPressed: onTapOk(context), onPressed: onTapOk(context),
@@ -866,7 +866,7 @@ class MyProfileScreen extends StatelessWidget {
backgroundColor: Colors.white, backgroundColor: Colors.white,
titlePadding: EdgeInsets.all( titlePadding: EdgeInsets.all(
20.0), // Можете настроить отступы по вашему желанию 20.0), // Можете настроить отступы по вашему желанию
); );
}, },
); );
} }
@@ -957,10 +957,8 @@ class MyProfileScreen extends StatelessWidget {
} }
void saveWeight(MyProfileLoadedState state, BuildContext context) { void saveWeight(MyProfileLoadedState state, BuildContext context) {
addWeight(state, context); addWeight(state, context);
Navigator.of(context).pop(); // Закрыть диалоговое окно после изменения веса Navigator.of(context).pop(); // Закрыть диалоговое окно после изменения веса
} }
onTapOk(BuildContext context) { onTapOk(BuildContext context) {