diff --git a/lib/controllers/delete_account_controller.dart b/lib/controllers/delete_account_controller.dart new file mode 100644 index 00000000..7d4e5694 --- /dev/null +++ b/lib/controllers/delete_account_controller.dart @@ -0,0 +1,62 @@ +import 'dart:developer'; + +import 'package:appwrite/appwrite.dart'; +import 'package:get/get.dart'; +import 'package:resonate/controllers/auth_state_controller.dart'; +import 'package:resonate/services/appwrite_service.dart'; +import 'package:resonate/utils/constants.dart'; + +class DeleteAccountController extends GetxController { + RxBool isButtonActive = false.obs; + + AuthStateController authStateController = Get.put(AuthStateController()); + + late final Storage storage; + late final Databases databases; + + // + //------------------------------------------------------------------- + // PLEASE DO NOT TOUCH THIS CODE WITHOUT PERMISSION - + //------------------------------------------------------------------- + // + + @override + void onInit() { + super.onInit(); + + storage = AppwriteService.getStorage(); + databases = AppwriteService.getDatabases(); + } + + Future deleteUserProfilePicture() async { + try { + await storage.deleteFile( + bucketId: userProfileImageBucketId, + fileId: authStateController.profileImageID!); + } catch (e) { + log(e.toString()); + } + } + + Future deleteUsernamesCollectionDocument() async { + try { + await databases.deleteDocument( + databaseId: userDatabaseID, + collectionId: usernameCollectionID, + documentId: authStateController.userName!); + } catch (e) { + log(e.toString()); + } + } + + Future deleteUsersCollectionDocument() async { + try { + await databases.deleteDocument( + databaseId: userDatabaseID, + collectionId: usersCollectionID, + documentId: authStateController.uid!); + } catch (e) { + log(e.toString()); + } + } +} diff --git a/lib/routes/app_pages.dart b/lib/routes/app_pages.dart index d5415c22..a26cae90 100644 --- a/lib/routes/app_pages.dart +++ b/lib/routes/app_pages.dart @@ -3,6 +3,7 @@ import 'package:resonate/bindings/auth_splash_bindings.dart'; import 'package:resonate/bindings/profile_binding.dart'; import 'package:resonate/routes/app_routes.dart'; import 'package:resonate/views/screens/create_room_screen.dart'; +import 'package:resonate/views/screens/delete_account_screen.dart'; import 'package:resonate/views/screens/discussions_screen.dart'; import 'package:resonate/views/screens/edit_profile_screen.dart'; import 'package:resonate/views/screens/email_verification_screen.dart'; @@ -95,5 +96,10 @@ class AppPages { page: () => EditProfileScreen(), binding: ProfileBinding(), ), + GetPage( + name: AppRoutes.deleteAccount, + page: () => const DeleteAccountScreen(), + binding: ProfileBinding(), + ), ]; } diff --git a/lib/routes/app_routes.dart b/lib/routes/app_routes.dart index c5aac68e..78dcce8e 100644 --- a/lib/routes/app_routes.dart +++ b/lib/routes/app_routes.dart @@ -15,4 +15,5 @@ class AppRoutes { static const pairChat = "/pairChat"; static const settings = "/settings"; static const editProfile = "/editProfile"; + static const deleteAccount = "/deleteAccount"; } diff --git a/lib/views/screens/delete_account_screen.dart b/lib/views/screens/delete_account_screen.dart new file mode 100644 index 00000000..be99ec31 --- /dev/null +++ b/lib/views/screens/delete_account_screen.dart @@ -0,0 +1,115 @@ +import 'package:flutter/material.dart'; +import 'package:get/get.dart'; +import 'package:resonate/controllers/auth_state_controller.dart'; +import 'package:resonate/controllers/delete_account_controller.dart'; +import 'package:resonate/utils/ui_sizes.dart'; + +class DeleteAccountScreen extends StatelessWidget { + const DeleteAccountScreen({super.key}); + + @override + Widget build(BuildContext context) { + AuthStateController authStateController = Get.put(AuthStateController()); + + return Scaffold( + appBar: AppBar( + title: const Text('Delete Account'), + ), + body: GetBuilder( + init: DeleteAccountController(), + builder: (controller) => Container( + padding: const EdgeInsets.symmetric(vertical: 15, horizontal: 20), + child: Column( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + const Padding( + padding: EdgeInsets.symmetric(vertical: 5), + child: Text( + "Delete My Account", + style: TextStyle(fontWeight: FontWeight.bold, fontSize: 16), + ), + ), + const Text( + "This action will Delete Your Account Permanently. It is irreversible process. We will delete your username, email address, and all other data associated with your account. You will not be able to recover it.", + ), + const SizedBox( + height: 50, + ), + RichText( + text: TextSpan( + style: const TextStyle( + color: Colors.redAccent, + fontSize: 16, + ), + children: [ + const TextSpan(text: 'To confirm, type'), + TextSpan( + text: ' "${authStateController.userName}" ', + style: const TextStyle( + fontWeight: FontWeight.bold, + ), + ), + const TextSpan(text: 'in the box below') + ]), + ), + const SizedBox( + height: 10, + ), + TextField( + onChanged: (value) { + if (value == authStateController.userName) { + controller.isButtonActive.value = true; + } else { + controller.isButtonActive.value = false; + } + }, + keyboardType: TextInputType.text, + autocorrect: false, + cursorColor: Colors.redAccent, + decoration: InputDecoration( + border: OutlineInputBorder( + borderRadius: BorderRadius.circular(12), + ), + focusedBorder: OutlineInputBorder( + borderRadius: BorderRadius.circular(12), + borderSide: BorderSide( + color: Colors.redAccent, + width: UiSizes.width_2, + ), + ), + enabledBorder: OutlineInputBorder( + borderRadius: BorderRadius.circular(12), + borderSide: const BorderSide(color: Colors.grey), + ), + )), + const SizedBox( + height: 50, + ), + Obx( + () => ElevatedButton( + style: ElevatedButton.styleFrom( + backgroundColor: Colors.redAccent, + foregroundColor: Colors.white, + disabledForegroundColor: Colors.redAccent.withAlpha(100), + disabledBackgroundColor: Colors.redAccent.withAlpha(50), + ), + onPressed: (controller.isButtonActive.value) + ? () { + // DO NOT IMPLEMENT THIS WITHOUT PERMISSION + } + : null, + child: const Text( + 'I understand, Delete My Account', + style: TextStyle( + fontSize: 16, + ), + ), + ), + ) + ], + ), + ), + ), + ); + } +} diff --git a/lib/views/screens/settings_screen.dart b/lib/views/screens/settings_screen.dart index 27610490..114e0054 100644 --- a/lib/views/screens/settings_screen.dart +++ b/lib/views/screens/settings_screen.dart @@ -1,6 +1,7 @@ import 'package:flutter/material.dart'; import 'package:font_awesome_flutter/font_awesome_flutter.dart'; import 'package:get/get.dart'; +import 'package:resonate/routes/app_routes.dart'; import 'package:resonate/themes/theme_controller.dart'; import '../../themes/choose_theme_bottom_sheet.dart'; @@ -34,33 +35,56 @@ class _SettingsScreenState extends State { 'Settings', ), ), - body: ListView( - children: [ - const Padding( - padding: EdgeInsets.only(top: 20, bottom: 10, left: 15), - child: Text('General settings'), - ), - ListTile( - leading: const Column( - mainAxisAlignment: MainAxisAlignment.center, - children: [ - Icon(FontAwesomeIcons.circleHalfStroke), - ], + body: Container( + padding: const EdgeInsets.symmetric(vertical: 15, horizontal: 15), + child: ListView( + children: [ + const Text('General settings'), + ListTile( + leading: const Column( + mainAxisAlignment: MainAxisAlignment.center, + children: [ + Icon(FontAwesomeIcons.circleHalfStroke), + ], + ), + title: const Text('Theme'), + subtitle: Text(subText), + onTap: () { + showModalBottomSheet( + shape: const RoundedRectangleBorder( + borderRadius: + BorderRadius.vertical(top: Radius.circular(24)), + ), + context: context, + builder: (context) => + chooseThemeBottomSheet(context, (_) => setState(() {})), + ); + }, ), - title: const Text('Theme'), - subtitle: Text(subText), - onTap: () { - showModalBottomSheet( - shape: const RoundedRectangleBorder( - borderRadius: BorderRadius.vertical(top: Radius.circular(24)), + const SizedBox( + height: 30, + ), + const Text('Account settings'), + Padding( + padding: const EdgeInsets.symmetric(vertical: 10), + child: OutlinedButton( + style: OutlinedButton.styleFrom( + foregroundColor: Colors.redAccent, + padding: const EdgeInsets.symmetric(vertical: 10), + side: const BorderSide(color: Colors.redAccent)), + onPressed: () { + Navigator.pushNamed(context, AppRoutes.deleteAccount); + }, + child: const Text( + 'Delete Account', + style: TextStyle( + fontSize: 16, + ), ), - context: context, - builder: (context) => - chooseThemeBottomSheet(context, (_) => setState(() {})), - ); - }, - ) - ], + ), + ), + ], + ), ), ); }