Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: completely revamp app look #218

Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .idea/libraries/Flutter_Plugins.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

15 changes: 7 additions & 8 deletions android/app/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
Expand Up @@ -7,15 +7,14 @@
additional functionality it is fine to subclass or reimplement
FlutterApplication and put your custom class here. -->
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission
android:name="android.permission.PACKAGE_USAGE_STATS"
<uses-permission android:name="android.permission.PACKAGE_USAGE_STATS"
tools:ignore="ProtectedPermissions" />
<uses-permission
android:name="android.permission.ACCESS_FINE_LOCATION"
/>
<uses-permission
android:name="android.permission.ACCESS_COARSE_LOCATION"
/>
<uses-permission android:minSdkVersion="34" android:name="android.permission.USE_EXACT_ALARM" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.WAKE_LOCK" />
<uses-permission android:name="android.permission.FOREGROUND_SERVICE"/>
<uses-permission android:name="android.permission.REQUEST_IGNORE_BATTERY_OPTIMIZATIONS" />

<application
android:label="Time's Up"
Expand Down
3 changes: 3 additions & 0 deletions android/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,9 @@ allprojects {
repositories {
google()
jcenter()
maven {
url "${project(':background_fetch').projectDir}/libs"
}
}
}

Expand Down
7 changes: 1 addition & 6 deletions lib/app/app.dart
Original file line number Diff line number Diff line change
Expand Up @@ -7,14 +7,9 @@ import 'package:times_up_flutter/theme/theme.dart';
import 'package:times_up_flutter/theme/theme_notifier.dart';
import 'package:times_up_flutter/utils/app_strings.dart';

class TimesUpApp extends StatefulWidget {
class TimesUpApp extends StatelessWidget {
const TimesUpApp({Key? key}) : super(key: key);

@override
State<TimesUpApp> createState() => _TimesUpAppState();
}

class _TimesUpAppState extends State<TimesUpApp> with WidgetsBindingObserver {
@override
Widget build(BuildContext context) {
SystemChrome.setPreferredOrientations([
Expand Down
36 changes: 36 additions & 0 deletions lib/app/config/android_config.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
import 'package:background_fetch/background_fetch.dart';
import 'package:times_up_flutter/widgets/show_logger.dart';

@pragma('vm:entry-point')
Future<void> backgroundFetchHeadlessTask(HeadlessTask task) async {
final taskId = task.taskId;
final isTimeout = task.timeout;

JHLogger.$.e('[BackgroundFetch] Headless event received.');

if (isTimeout) {
JHLogger.$.e('[BackgroundFetch] Headless task timed-out: $taskId');
BackgroundFetch.finish(taskId);
return;
}
}

Future<void> configureBackgroundFetch() async {
await BackgroundFetch.configure(
BackgroundFetchConfig(
minimumFetchInterval: 1,
stopOnTerminate: false,
enableHeadless: true,
requiresBatteryNotLow: false,
requiresCharging: false,
requiresStorageNotLow: false,
requiresDeviceIdle: false,
requiredNetworkType: NetworkType.NONE,
),
backgroundFetchHeadlessTask,
).then((int status) {
JHLogger.$.e('[BackgroundFetch] Headless task timed-out- $status');
}).catchError((e) {
JHLogger.$.d("[BackgroundFetch] configure ERROR: $e");
});
}
20 changes: 17 additions & 3 deletions lib/app/features/child_side/child_page.dart
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ import 'package:times_up_flutter/services/geo_locator_service.dart';
import 'package:times_up_flutter/theme/theme.dart';
import 'package:times_up_flutter/widgets/jh_display_text.dart';
import 'package:times_up_flutter/widgets/jh_empty_content.dart';
import 'package:times_up_flutter/widgets/show_logger.dart';

class ChildPage extends StatefulWidget {
const ChildPage({
Expand Down Expand Up @@ -66,11 +67,24 @@ class _ChildPageState extends State<ChildPage> with WidgetsBindingObserver {
Navigator.pop(context);
}

@override
void initState() {
super.initState();

WidgetsBinding.instance.addObserver(this);
}

@override
void dispose() {
WidgetsBinding.instance.removeObserver(this);
super.dispose();
}

@override
void didChangeAppLifecycleState(AppLifecycleState state) {
Timer.periodic(const Duration(minutes: 5), (timer) {
widget.database
?.liveUpdateChild(widget.child!, timer.tick, widget.appUsage);
Timer.periodic(const Duration(seconds: 5), (timer) async {
await widget.database?.liveUpdateChild(widget.child!, widget.appUsage);
JHLogger.$.d('${timer.tick} - $state');
});
super.didChangeAppLifecycleState(state);
}
Expand Down
87 changes: 87 additions & 0 deletions lib/app/features/parent_side/app_list_page.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,87 @@
import 'package:flutter/material.dart';
import 'package:times_up_flutter/app/helpers/parsing_extension.dart';
import 'package:times_up_flutter/models/child_model/child_model.dart';

class AppListPage extends StatelessWidget {
const AppListPage({
required this.childModel,
Key? key,
}) : super(key: key);

final ChildModel childModel;

static Future<void> show(BuildContext context, ChildModel model) async {
await Navigator.of(context).push(
PageRouteBuilder<Widget>(
pageBuilder: (context, animation, secondaryAnimation) {
return AppListPage(childModel: model);
},
transitionsBuilder: (context, animation, secondaryAnimation, child) {
const begin = Offset(1, 0);
const end = Offset.zero;
const curve = Curves.easeInOut;
final tween =
Tween(begin: begin, end: end).chain(CurveTween(curve: curve));
final offsetAnimation = animation.drive(tween);
return SlideTransition(
position: offsetAnimation,
child: child,
);
},
transitionDuration: const Duration(milliseconds: 400),
),
);
}

@override
Widget build(BuildContext context) {
final themeData = Theme.of(context);

return Scaffold(
appBar: AppBar(
leading: IconButton(
icon: const Icon(Icons.chevron_left),
onPressed: () => Navigator.of(context).pop(),
),
elevation: 0,
backgroundColor: themeData.scaffoldBackgroundColor,
),
body: ListView.builder(
physics: const BouncingScrollPhysics(
decelerationRate: ScrollDecelerationRate.fast),
itemCount: childModel.appsUsageModel.length,
itemBuilder: (context, index) {
return Column(
mainAxisSize: MainAxisSize.min,
children: [
ListTile(
leading: childModel.appsUsageModel[index].appIcon != null
? Image.memory(
childModel.appsUsageModel[index].appIcon!,
height: 35,
)
: const Icon(Icons.android),
title: Text(
childModel.appsUsageModel[index].appName,
style: TextStyle(
fontSize: 15,
fontWeight: FontWeight.bold,
color: themeData.dividerColor,
),
),
trailing: Text(
childModel.appsUsageModel[index].usage.toString().t(),
style: TextStyle(
fontSize: 14,
fontWeight: FontWeight.w600,
color: themeData.dividerColor,
),
),
),
],
);
},
),
);
}
}
Loading
Loading