feat: Refactor code structure and optimize performance across multiple modules
This commit is contained in:
@@ -0,0 +1,64 @@
|
||||
import 'package:auto_route/auto_route.dart';
|
||||
import 'package:easy_localization/easy_localization.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||
import 'package:gap/gap.dart';
|
||||
import 'package:krow/core/data/enums/state_status.dart';
|
||||
import 'package:krow/core/presentation/widgets/ui_kit/kw_app_bar.dart';
|
||||
import 'package:krow/core/presentation/widgets/ui_kit/kw_loading_overlay.dart';
|
||||
import 'package:krow/features/profile/live_photo/domain/bloc/live_photo_bloc.dart';
|
||||
import 'package:krow/features/profile/live_photo/presentation/widgets/live_photo_display_card.dart';
|
||||
import 'package:krow/features/profile/live_photo/presentation/widgets/photo_requirements_card.dart';
|
||||
|
||||
@RoutePage()
|
||||
class LivePhotoScreen extends StatelessWidget implements AutoRouteWrapper {
|
||||
const LivePhotoScreen({super.key});
|
||||
|
||||
@override
|
||||
Widget wrappedRoute(BuildContext context) {
|
||||
return BlocProvider<LivePhotoBloc>(
|
||||
create: (context) => LivePhotoBloc()..add(const InitLivePhotoBloc()),
|
||||
child: this,
|
||||
);
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Scaffold(
|
||||
appBar: KwAppBar(
|
||||
titleText: 'live_photo'.tr(),
|
||||
showNotification: true,
|
||||
),
|
||||
body: ListView(
|
||||
primary: false,
|
||||
padding: const EdgeInsets.all(16),
|
||||
children: [
|
||||
BlocBuilder<LivePhotoBloc, LivePhotoState>(
|
||||
buildWhen: (previous, current) => previous.status != current.status,
|
||||
builder: (context, state) {
|
||||
return KwLoadingOverlay(
|
||||
shouldShowLoading: state.status == StateStatus.loading,
|
||||
child: const PhotoRequirementsCard(),
|
||||
);
|
||||
},
|
||||
),
|
||||
const Gap(24),
|
||||
BlocBuilder<LivePhotoBloc, LivePhotoState>(
|
||||
buildWhen: (previous, current) =>
|
||||
previous.photoData != current.photoData,
|
||||
builder: (context, state) {
|
||||
final photoData = state.photoData;
|
||||
return AnimatedSwitcher(
|
||||
duration: Durations.short4,
|
||||
child: photoData == null
|
||||
? const SizedBox(height: 56)
|
||||
: LivePhotoDisplayCard(photoData: photoData),
|
||||
);
|
||||
},
|
||||
),
|
||||
const Gap(90),
|
||||
],
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,65 @@
|
||||
import 'package:easy_localization/easy_localization.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||
import 'package:image_picker/image_picker.dart';
|
||||
import 'package:krow/core/application/common/date_time_extension.dart';
|
||||
import 'package:krow/core/presentation/styles/theme.dart';
|
||||
import 'package:krow/core/presentation/widgets/uploud_image_card.dart';
|
||||
import 'package:krow/features/profile/live_photo/domain/bloc/live_photo_bloc.dart';
|
||||
import 'package:krow/features/profile/live_photo/data/models/live_photo_data.dart';
|
||||
|
||||
class LivePhotoDisplayCard extends StatelessWidget {
|
||||
const LivePhotoDisplayCard({
|
||||
super.key,
|
||||
required this.photoData,
|
||||
});
|
||||
|
||||
final LivePhotoData photoData;
|
||||
|
||||
String _getPhotoStatus(LivePhotoStatus status) {
|
||||
return switch (status) {
|
||||
LivePhotoStatus.pending => 'Pending'.tr(),
|
||||
LivePhotoStatus.verified => 'Verified'.tr(),
|
||||
LivePhotoStatus.declined => 'Declined'.tr(),
|
||||
};
|
||||
}
|
||||
|
||||
Color _getPhotoStatusColor(LivePhotoStatus status) {
|
||||
return switch (status) {
|
||||
LivePhotoStatus.pending => AppColors.primaryBlue,
|
||||
LivePhotoStatus.verified => AppColors.statusSuccess,
|
||||
LivePhotoStatus.declined => AppColors.statusError,
|
||||
};
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return UploadImageCard(
|
||||
title: '${'Photo'.tr()} ${photoData.timestamp.toDayMonthYearString()}',
|
||||
imageUrl: photoData.imageUrl,
|
||||
localImagePath: photoData.imagePath,
|
||||
message: _getPhotoStatus(photoData.status),
|
||||
statusColor: _getPhotoStatusColor(photoData.status),
|
||||
onDeleteTap: () {
|
||||
context.read<LivePhotoBloc>().add(const DeleteCurrentPhotoEvent());
|
||||
},
|
||||
onSelectImage: () {
|
||||
ImagePicker()
|
||||
.pickImage(
|
||||
source: ImageSource.camera,
|
||||
preferredCameraDevice: CameraDevice.front,
|
||||
)
|
||||
.then(
|
||||
(photo) {
|
||||
if (photo == null || !context.mounted) return;
|
||||
|
||||
context.read<LivePhotoBloc>().add(
|
||||
AddNewPhotoEvent(newImagePath: photo.path),
|
||||
);
|
||||
},
|
||||
);
|
||||
},
|
||||
onTap: () {},
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,103 @@
|
||||
import 'package:easy_localization/easy_localization.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||
import 'package:gap/gap.dart';
|
||||
import 'package:image_picker/image_picker.dart';
|
||||
import 'package:krow/core/presentation/styles/kw_text_styles.dart';
|
||||
import 'package:krow/core/presentation/styles/theme.dart';
|
||||
import 'package:krow/core/presentation/widgets/ui_kit/kw_button.dart';
|
||||
import 'package:krow/features/profile/live_photo/domain/bloc/live_photo_bloc.dart';
|
||||
|
||||
class PhotoRequirementsCard extends StatelessWidget {
|
||||
const PhotoRequirementsCard({super.key});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Container(
|
||||
padding: const EdgeInsets.all(12),
|
||||
decoration: const BoxDecoration(
|
||||
color: AppColors.grayWhite,
|
||||
borderRadius: BorderRadius.all(
|
||||
Radius.circular(12),
|
||||
),
|
||||
),
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Text(
|
||||
'ensure_meet_requirements'.tr(),
|
||||
style: AppTextStyles.bodyMediumMed,
|
||||
),
|
||||
const Gap(12),
|
||||
Column(
|
||||
spacing: 8,
|
||||
children: [
|
||||
for (int i = 0; i < requirementsData.length; i++)
|
||||
Row(
|
||||
crossAxisAlignment: CrossAxisAlignment.center,
|
||||
children: [
|
||||
Container(
|
||||
height: 20,
|
||||
width: 20,
|
||||
alignment: Alignment.center,
|
||||
decoration: const BoxDecoration(
|
||||
shape: BoxShape.circle,
|
||||
color: AppColors.bgColorDark,
|
||||
),
|
||||
child: Text(
|
||||
'${i + 1}',
|
||||
style: const TextStyle(
|
||||
fontFamily: 'Poppins',
|
||||
fontWeight: FontWeight.w500,
|
||||
fontSize: 8,
|
||||
color: AppColors.grayWhite,
|
||||
),
|
||||
),
|
||||
),
|
||||
const Gap(8),
|
||||
Expanded(
|
||||
child: Text(
|
||||
requirementsData[i].tr(),
|
||||
style: AppTextStyles.bodySmallReg,
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
const Gap(16),
|
||||
BlocSelector<LivePhotoBloc, LivePhotoState, bool>(
|
||||
selector: (state) => state.photoData != null,
|
||||
builder: (context, isPhotoTaken) {
|
||||
return KwButton.primary(
|
||||
label: isPhotoTaken?'take_new_photo'.tr():'take_photo'.tr(),
|
||||
onPressed: () {
|
||||
ImagePicker()
|
||||
.pickImage(
|
||||
source: ImageSource.camera,
|
||||
preferredCameraDevice: CameraDevice.front,
|
||||
)
|
||||
.then(
|
||||
(photo) {
|
||||
if (photo == null || !context.mounted) return;
|
||||
|
||||
context.read<LivePhotoBloc>().add(
|
||||
AddNewPhotoEvent(newImagePath: photo.path),
|
||||
);
|
||||
},
|
||||
);
|
||||
},
|
||||
);
|
||||
},
|
||||
),
|
||||
],
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
const requirementsData = [
|
||||
'stand_in_well_lit_area',
|
||||
'ensure_face_visible',
|
||||
'avoid_filters_obstructions',
|
||||
];
|
||||
Reference in New Issue
Block a user