diff --git a/filcnaplo/lib/database/init.dart b/filcnaplo/lib/database/init.dart index 12f7fe8..2644592 100644 --- a/filcnaplo/lib/database/init.dart +++ b/filcnaplo/lib/database/init.dart @@ -67,6 +67,7 @@ const userDataDB = DatabaseStruct("user_data", { "todo_items": String, "self_notes": String, // v5 shit "roundings": String, + "grade_rarities": String, }); Future createTable(Database db, DatabaseStruct struct) => @@ -128,6 +129,7 @@ Future initDB(DatabaseProvider database) async { "todo_items": "{}", "self_notes": "[]", // v5 shit "roundings": "{}", + "grade_rarities": "{}", }); } catch (error) { print("ERROR: migrateDB: $error"); diff --git a/filcnaplo/lib/database/query.dart b/filcnaplo/lib/database/query.dart index f1c33c5..862bfc9 100644 --- a/filcnaplo/lib/database/query.dart +++ b/filcnaplo/lib/database/query.dart @@ -316,4 +316,14 @@ class UserDatabaseQuery { return (jsonDecode(roundingsJson) as Map) .map((key, value) => MapEntry(key.toString(), value.toString())); } + + Future> getGradeRarities({required String userId}) async { + List userData = + await db.query("user_data", where: "id = ?", whereArgs: [userId]); + if (userData.isEmpty) return {}; + String? raritiesJson = userData.elementAt(0)["grade_rarities"] as String?; + if (raritiesJson == null) return {}; + return (jsonDecode(raritiesJson) as Map) + .map((key, value) => MapEntry(key.toString(), value.toString())); + } } diff --git a/filcnaplo/lib/database/store.dart b/filcnaplo/lib/database/store.dart index 82807ed..154574e 100644 --- a/filcnaplo/lib/database/store.dart +++ b/filcnaplo/lib/database/store.dart @@ -201,4 +201,11 @@ class UserDatabaseStore { await db.update("user_data", {"roundings": roundingsJson}, where: "id = ?", whereArgs: [userId]); } + + Future storeGradeRarities(Map rarities, + {required String userId}) async { + String raritiesJson = jsonEncode(rarities); + await db.update("user_data", {"grade_rarities": raritiesJson}, + where: "id = ?", whereArgs: [userId]); + } } diff --git a/filcnaplo_kreta_api/lib/providers/grade_provider.dart b/filcnaplo_kreta_api/lib/providers/grade_provider.dart index 209e19a..cb9c54f 100644 --- a/filcnaplo_kreta_api/lib/providers/grade_provider.dart +++ b/filcnaplo_kreta_api/lib/providers/grade_provider.dart @@ -54,6 +54,15 @@ class GradeProvider with ChangeNotifier { } } + Future unseenAll() async { + String? userId = _user.id; + if (userId != null) { + final userStore = _database.userStore; + userStore.storeLastSeenGrade(DateTime(1969), userId: userId); + _lastSeen = DateTime(1969); + } + } + Future restore() async { String? userId = _user.id; @@ -125,6 +134,9 @@ class GradeProvider with ChangeNotifier { // Fetches Grades from the Kreta API then stores them in the database Future fetch() async { + // test cucc + // unseenAll(); + User? user = _user.user; if (user == null) throw "Cannot fetch Grades for User null"; String iss = user.instituteCode; diff --git a/filcnaplo_mobile_ui/lib/common/widgets/grade/surprise_grade.dart b/filcnaplo_mobile_ui/lib/common/widgets/grade/surprise_grade.dart index 58275b3..e92a0f4 100755 --- a/filcnaplo_mobile_ui/lib/common/widgets/grade/surprise_grade.dart +++ b/filcnaplo_mobile_ui/lib/common/widgets/grade/surprise_grade.dart @@ -1,7 +1,11 @@ +// ignore_for_file: use_build_context_synchronously + import 'dart:math'; import 'dart:ui'; import 'package:animated_background/animated_background.dart' as bg; +import 'package:filcnaplo/api/providers/database_provider.dart'; +import 'package:filcnaplo/api/providers/user_provider.dart'; import 'package:filcnaplo/helpers/subject.dart'; import 'package:filcnaplo/models/settings.dart'; import 'package:filcnaplo/ui/widgets/grade/grade_tile.dart'; @@ -33,6 +37,15 @@ class _SurpriseGradeState extends State late SettingsProvider settingsProvider; + List defaultRarities = [ + "common", + "uncommon", + "rare", + "epic", + "legendary", + ]; + Map rarities = {}; + @override void initState() { super.initState(); @@ -54,6 +67,8 @@ class _SurpriseGradeState extends State setState(() => subtitle = true); }); }); + + _fetchRarities(); }); seed = Random().nextInt(100000000); @@ -69,6 +84,15 @@ class _SurpriseGradeState extends State super.dispose(); } + _fetchRarities() async { + rarities = await Provider.of(context, listen: false) + .userQuery + .getGradeRarities( + userId: Provider.of(context, listen: false).id!); + + setState(() {}); + } + bool hold = false; bool subtitle = false; late int seed; @@ -321,6 +345,15 @@ class _SurpriseGradeState extends State AnimationStatus.reverse) { shouldPaint = true; } + + String? rr = + rarities[widget.grade.value.value.toString()]; + rr ??= ''; + + if (rr.replaceAll(' ', '') == '') { + rr = defaultRarities[widget.grade.value.value - 1].i18n; + } + return ScaleTransition( scale: _revealAnimGrade, child: FadeTransition( @@ -337,14 +370,7 @@ class _SurpriseGradeState extends State begin: Offset.zero, end: const Offset(0, -0.9))), child: Text( - [ - "legendary", - "epic", - "rare", - "uncommon", - "common" - ][5 - widget.grade.value.value] - .i18n, + rr, style: TextStyle( fontSize: 46.0, fontWeight: FontWeight.bold, diff --git a/filcnaplo_mobile_ui/lib/screens/settings/settings_helper.dart b/filcnaplo_mobile_ui/lib/screens/settings/settings_helper.dart index 36889ab..f316efa 100755 --- a/filcnaplo_mobile_ui/lib/screens/settings/settings_helper.dart +++ b/filcnaplo_mobile_ui/lib/screens/settings/settings_helper.dart @@ -387,10 +387,21 @@ class SettingsHelper { } // v5 grade rarity texts - static void surpriseGradeRarityText(BuildContext context) { + static void surpriseGradeRarityText( + BuildContext context, { + required String title, + required String cancel, + required String done, + required List rarities, + }) { showRoundedModalBottomSheet( context, - child: const GradeColorsSetting(), + child: GradeRarityTextSetting( + title: title, + cancel: cancel, + done: done, + defaultRarities: rarities, + ), ); } } @@ -726,6 +737,141 @@ class _GradeColorsSettingState extends State { } } +class GradeRarityTextSetting extends StatefulWidget { + const GradeRarityTextSetting({ + super.key, + required this.title, + required this.cancel, + required this.done, + required this.defaultRarities, + }); + + final String title; + final String cancel; + final String done; + final List defaultRarities; + + @override + _GradeRarityTextSettingState createState() => _GradeRarityTextSettingState(); +} + +class _GradeRarityTextSettingState extends State { + late SettingsProvider settings; + late DatabaseProvider db; + late UserProvider user; + + final _rarityText = TextEditingController(); + + @override + void initState() { + super.initState(); + settings = Provider.of(context, listen: false); + db = Provider.of(context, listen: false); + user = Provider.of(context, listen: false); + } + + @override + Widget build(BuildContext context) { + return Column(children: [ + Padding( + padding: const EdgeInsets.all(8.0), + child: Row( + mainAxisAlignment: MainAxisAlignment.spaceEvenly, + children: List.generate(5, (index) { + return ClipOval( + child: Material( + type: MaterialType.transparency, + child: InkWell( + onTap: () async { + showRenameDialog( + title: widget.title, + cancel: widget.cancel, + done: widget.done, + rarities: + await db.userQuery.getGradeRarities(userId: user.id!), + gradeIndex: (index + 1).toString(), + defaultRarities: widget.defaultRarities, + ); + }, + child: GradeValueWidget(GradeValue(index + 1, "", "", 0), + fill: true, size: 36.0), + ), + ), + ); + }), + ), + ), + ]); + } + + void showRenameDialog( + {required String title, + required String cancel, + required String done, + required Map rarities, + required String gradeIndex, + required List defaultRarities, + required}) { + showDialog( + context: context, + builder: (context) => StatefulBuilder(builder: (context, setS) { + String? rr = rarities[gradeIndex]; + rr ??= ''; + + _rarityText.text = rr; + + return AlertDialog( + title: Text(title), + content: TextField( + controller: _rarityText, + autofocus: true, + decoration: InputDecoration( + border: const OutlineInputBorder(), + label: Text(defaultRarities[int.parse(gradeIndex) - 1]), + suffixIcon: IconButton( + icon: const Icon(FeatherIcons.x), + onPressed: () { + setState(() { + _rarityText.clear(); + }); + }, + ), + ), + ), + actions: [ + TextButton( + child: Text( + cancel, + style: const TextStyle(fontWeight: FontWeight.w500), + ), + onPressed: () { + Navigator.of(context).maybePop(); + }, + ), + TextButton( + child: Text( + done, + style: const TextStyle(fontWeight: FontWeight.w500), + ), + onPressed: () { + rarities[gradeIndex] = _rarityText.text; + + Provider.of(context, listen: false) + .userStore + .storeGradeRarities(rarities, userId: user.id!); + + Navigator.of(context).pop(true); + }, + ), + ], + ); + }), + ).then((val) { + _rarityText.clear(); + }); + } +} + class LiveActivityColorSetting extends StatefulWidget { const LiveActivityColorSetting({super.key}); diff --git a/filcnaplo_mobile_ui/lib/screens/settings/submenu/extras_screen.dart b/filcnaplo_mobile_ui/lib/screens/settings/submenu/extras_screen.dart index c21f928..27d54b0 100644 --- a/filcnaplo_mobile_ui/lib/screens/settings/submenu/extras_screen.dart +++ b/filcnaplo_mobile_ui/lib/screens/settings/submenu/extras_screen.dart @@ -84,7 +84,19 @@ class ExtrasSettingsScreenState extends State { onPressed: () async { // settingsProvider.update( // gradeOpeningFun: !settingsProvider.gradeOpeningFun); - SettingsHelper.surpriseGradeRarityText(context); + SettingsHelper.surpriseGradeRarityText( + context, + title: 'rarity_title'.i18n, + cancel: 'cancel'.i18n, + done: 'done'.i18n, + rarities: [ + "common".i18n, + "uncommon".i18n, + "rare".i18n, + "epic".i18n, + "legendary".i18n, + ], + ); setState(() {}); }, trailingDivider: true, diff --git a/filcnaplo_mobile_ui/lib/screens/settings/submenu/submenu_screen.i18n.dart b/filcnaplo_mobile_ui/lib/screens/settings/submenu/submenu_screen.i18n.dart index a7badbc..ed30e3d 100644 --- a/filcnaplo_mobile_ui/lib/screens/settings/submenu/submenu_screen.i18n.dart +++ b/filcnaplo_mobile_ui/lib/screens/settings/submenu/submenu_screen.i18n.dart @@ -8,18 +8,45 @@ extension SettingsLocalization on String { "personalization": "Personalization", "extras": "Extras", "surprise_grades": "Surprise Grades", + "cancel": "Cancel", + "done": "Done", + "rarity_title": "Rarity Text", + // default rarities + "common": "Common", + "uncommon": "Uncommon", + "rare": "Rare", + "epic": "Epic", + "legendary": "Legendary", }, "hu_hu": { "general": "Általános", "personalization": "Személyre szabás", "extras": "Extrák", "surprise_grades": "Meglepetés jegyek", + "cancel": "Mégse", + "done": "Kész", + "rarity_title": "Ritkaság szövege", + // default rarities + "common": "Gyakori", + "uncommon": "Nem gyakori", + "rare": "Ritka", + "epic": "Epikus", + "legendary": "Legendás", }, "de_de": { "general": "Allgemeine", "personalization": "Personalisierung", "extras": "Extras", "surprise_grades": "Überraschende Noten", + "cancel": "Abbrechen", + "done": "Bereit", + "rarity_title": "Text zur Seltenheit", + // default rarities + "common": "Gemeinsam", + "uncommon": "Gelegentlich", + "rare": "Selten", + "epic": "Episch", + "legendary": "Legendär", }, };