monthly report
parent
86a91ab383
commit
0b3fea230f
Binary file not shown.
|
After Width: | Height: | Size: 37 KiB |
@ -0,0 +1,60 @@
|
|||||||
|
import 'package:dartz/dartz.dart';
|
||||||
|
import '../../core/api/api_client.dart';
|
||||||
|
import '../../core/api_consts.dart';
|
||||||
|
import '../../core/exceptions/api_failure.dart';
|
||||||
|
import '../../services/logger_service.dart';
|
||||||
|
|
||||||
|
abstract class TermsConditionsRepo {
|
||||||
|
Future<Either<Failure, String>> getTermsConditions();
|
||||||
|
}
|
||||||
|
|
||||||
|
class TermsConditionsRepoImp implements TermsConditionsRepo {
|
||||||
|
final ApiClient apiClient;
|
||||||
|
final LoggerService loggerService;
|
||||||
|
|
||||||
|
TermsConditionsRepoImp({
|
||||||
|
required this.loggerService,
|
||||||
|
required this.apiClient,
|
||||||
|
});
|
||||||
|
|
||||||
|
@override
|
||||||
|
Future<Either<Failure, String>> getTermsConditions() async {
|
||||||
|
Failure? failure;
|
||||||
|
String? html;
|
||||||
|
|
||||||
|
try {
|
||||||
|
await apiClient.post(
|
||||||
|
ApiConsts.getTermsConditions,
|
||||||
|
body: <String, dynamic>{},
|
||||||
|
onFailure: (error, statusCode, {messageStatus, failureType}) {
|
||||||
|
failure = failureType ?? ServerFailure(error.toString());
|
||||||
|
},
|
||||||
|
onSuccess: (response, statusCode, {messageStatus, errorMessage}) {
|
||||||
|
try {
|
||||||
|
|
||||||
|
final content = response['UserAgreementContent'];
|
||||||
|
|
||||||
|
if (content is String && content.isNotEmpty) {
|
||||||
|
html = content;
|
||||||
|
} else {
|
||||||
|
failure = DataParsingFailure(
|
||||||
|
'UserAgreementContent is null or not String');
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
failure = DataParsingFailure(e.toString());
|
||||||
|
}
|
||||||
|
},
|
||||||
|
);
|
||||||
|
} catch (e) {
|
||||||
|
failure = UnknownFailure(e.toString());
|
||||||
|
}
|
||||||
|
|
||||||
|
if (failure != null) return Left(failure!);
|
||||||
|
if (html == null || html!.isEmpty) {
|
||||||
|
return Left(ServerFailure('No terms and conditions returned'));
|
||||||
|
}
|
||||||
|
|
||||||
|
return Right(html!);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@ -0,0 +1,45 @@
|
|||||||
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:hmg_patient_app_new/features/terms_conditions/terms_conditions_repo.dart';
|
||||||
|
import 'package:hmg_patient_app_new/services/error_handler_service.dart';
|
||||||
|
|
||||||
|
class TermsConditionsViewModel extends ChangeNotifier {
|
||||||
|
final TermsConditionsRepo termsConditionsRepo;
|
||||||
|
final ErrorHandlerService errorHandlerService;
|
||||||
|
|
||||||
|
String? termsConditionsHtml;
|
||||||
|
bool isLoading = false;
|
||||||
|
|
||||||
|
TermsConditionsViewModel({
|
||||||
|
required this.termsConditionsRepo,
|
||||||
|
required this.errorHandlerService,
|
||||||
|
});
|
||||||
|
|
||||||
|
Future<void> getTermsConditions({
|
||||||
|
Function()? onSuccess,
|
||||||
|
Function(String)? onError,
|
||||||
|
}) async {
|
||||||
|
isLoading = true;
|
||||||
|
notifyListeners();
|
||||||
|
|
||||||
|
final result = await termsConditionsRepo.getTermsConditions();
|
||||||
|
|
||||||
|
result.fold(
|
||||||
|
(failure) async {
|
||||||
|
await errorHandlerService.handleError(failure: failure);
|
||||||
|
isLoading = false;
|
||||||
|
notifyListeners();
|
||||||
|
if (onError != null) {
|
||||||
|
onError(failure.message ?? 'Something went wrong');
|
||||||
|
}
|
||||||
|
},
|
||||||
|
(html) {
|
||||||
|
termsConditionsHtml = html;
|
||||||
|
isLoading = false;
|
||||||
|
notifyListeners();
|
||||||
|
if (onSuccess != null) onSuccess();
|
||||||
|
},
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -0,0 +1,117 @@
|
|||||||
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:hmg_patient_app_new/extensions/string_extensions.dart';
|
||||||
|
import 'package:hmg_patient_app_new/features/terms_conditions/terms_conditions_view_model.dart';
|
||||||
|
import 'package:provider/provider.dart';
|
||||||
|
import 'package:webview_flutter/webview_flutter.dart';
|
||||||
|
|
||||||
|
import '../../theme/colors.dart';
|
||||||
|
import '../../widgets/appbar/app_bar_widget.dart';
|
||||||
|
|
||||||
|
class UserAgreementPage extends StatefulWidget {
|
||||||
|
const UserAgreementPage({super.key});
|
||||||
|
|
||||||
|
@override
|
||||||
|
State<UserAgreementPage> createState() => _UserAgreementPageState();
|
||||||
|
}
|
||||||
|
|
||||||
|
class _UserAgreementPageState extends State<UserAgreementPage> {
|
||||||
|
late final WebViewController _webViewController;
|
||||||
|
bool _isLoading = true;
|
||||||
|
String? _errorMessage;
|
||||||
|
|
||||||
|
@override
|
||||||
|
void initState() {
|
||||||
|
super.initState();
|
||||||
|
|
||||||
|
_webViewController = WebViewController()
|
||||||
|
..setJavaScriptMode(JavaScriptMode.unrestricted)
|
||||||
|
..setBackgroundColor(const Color(0x00000000))
|
||||||
|
..setNavigationDelegate(
|
||||||
|
NavigationDelegate(
|
||||||
|
onPageStarted: (_) {
|
||||||
|
setState(() {
|
||||||
|
_isLoading = true;
|
||||||
|
});
|
||||||
|
},
|
||||||
|
onPageFinished: (_) {
|
||||||
|
setState(() {
|
||||||
|
_isLoading = false;
|
||||||
|
});
|
||||||
|
},
|
||||||
|
onWebResourceError: (error) {
|
||||||
|
},
|
||||||
|
),
|
||||||
|
);
|
||||||
|
|
||||||
|
WidgetsBinding.instance.addPostFrameCallback((_) {
|
||||||
|
final vm =
|
||||||
|
Provider.of<TermsConditionsViewModel>(context, listen: false);
|
||||||
|
|
||||||
|
vm.getTermsConditions(
|
||||||
|
onSuccess: () {
|
||||||
|
final htmlString = vm.termsConditionsHtml ?? '';
|
||||||
|
|
||||||
|
if (htmlString.isNotEmpty) {
|
||||||
|
setState(() {
|
||||||
|
_errorMessage = null;
|
||||||
|
_isLoading = true;
|
||||||
|
});
|
||||||
|
_webViewController.loadHtmlString(htmlString);
|
||||||
|
} else {
|
||||||
|
setState(() {
|
||||||
|
_isLoading = false;
|
||||||
|
_errorMessage = 'لا توجد شروط متاحة حالياً'.needTranslation;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
},
|
||||||
|
onError: (msg) {
|
||||||
|
setState(() {
|
||||||
|
_isLoading = false;
|
||||||
|
_errorMessage = msg;
|
||||||
|
});
|
||||||
|
},
|
||||||
|
);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
return Scaffold(
|
||||||
|
backgroundColor: AppColors.scaffoldBgColor,
|
||||||
|
appBar: CustomAppBar(
|
||||||
|
onBackPressed: () => Navigator.of(context).pop(),
|
||||||
|
onLanguageChanged: (_) {},
|
||||||
|
hideLogoAndLang: true,
|
||||||
|
),
|
||||||
|
body: Stack(
|
||||||
|
children: [
|
||||||
|
WebViewWidget(controller: _webViewController),
|
||||||
|
|
||||||
|
if (_errorMessage != null)
|
||||||
|
Center(
|
||||||
|
child: Container(
|
||||||
|
margin: const EdgeInsets.all(16),
|
||||||
|
padding: const EdgeInsets.all(12),
|
||||||
|
decoration: BoxDecoration(
|
||||||
|
color: Colors.white.withOpacity(0.9),
|
||||||
|
borderRadius: BorderRadius.circular(8),
|
||||||
|
),
|
||||||
|
child: Text(
|
||||||
|
_errorMessage!,
|
||||||
|
textAlign: TextAlign.center,
|
||||||
|
style: const TextStyle(
|
||||||
|
color: Colors.red,
|
||||||
|
fontWeight: FontWeight.w600,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
if (_isLoading)
|
||||||
|
const Center(
|
||||||
|
child: CircularProgressIndicator(),
|
||||||
|
),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
Loading…
Reference in New Issue