Journal section added

This commit is contained in:
Sewmina
2022-03-29 21:36:11 +05:30
parent cad1b5db5a
commit 4335ce43db
8 changed files with 673 additions and 62 deletions

View File

@@ -1,11 +1,13 @@
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter_datetime_picker/flutter_datetime_picker.dart';
import 'package:intl/intl.dart';
import 'package:sticky_headers/sticky_headers/widget.dart';
import 'main.dart' as Main;
import 'newActivity.dart';
import 'Data.dart';
import 'User.dart' as User;
import 'package:scrollable_positioned_list/scrollable_positioned_list.dart';
class Activities extends StatefulWidget {
const Activities({Key? key}) : super(key: key);
@@ -66,7 +68,7 @@ class _ActivitiesState extends State<Activities> {
// progressDialog.update(value: 100);
} catch (e) {}
}
Map<Widget, List<Widget>> activitiesGroups =<Widget, List<Widget>>{};
Map<String, ActivityListDateGroup> activitiesGroups = <String, ActivityListDateGroup>{};
@override
Widget build(BuildContext context) {
// progressDialog = ProgressDialog(context: context);
@@ -172,14 +174,15 @@ class _ActivitiesState extends State<Activities> {
drawer: Main.navDrawer(context, 2),
body: Container(
padding: EdgeInsets.all(0),
child: ListView.builder(
child: ScrollablePositionedList.builder(
itemScrollController: scrollController,
itemCount: activitiesGroups.length,
itemBuilder: (context, index){
// return activities[index];
return StickyHeader(
header:activitiesGroups.keys.toList()[index],
content:Column(children: activitiesGroups.values.toList()[index],)
header:activitiesGroups.values.toList()[index].dateSeperator,
content:Column(children: activitiesGroups.values.toList()[index].activities,)
);
})
@@ -189,13 +192,17 @@ class _ActivitiesState extends State<Activities> {
// ))
));
}
DateFormat dFormat = DateFormat("yyyy-MM-dd");
ItemScrollController scrollController = ItemScrollController();
ScrollController controller = ScrollController();
int searchTime = 0;
Map<Widget,List<Widget>> PrintTasks() {
Map<Widget,List<Widget>> _tasks = <Widget,List<Widget>>{};
Map<String,ActivityListDateGroup> PrintTasks() {
Map<String,ActivityListDateGroup> _tasks = <String,ActivityListDateGroup>{};
print('Priting cats : ' + User.taskTypes.length.toString());
String lastDate = "";
DateFormat dFormat = DateFormat("MM/dd");
Map<String, int> productivtyActs = <String, int>{};
Map<String, int> unproductivtyActs = <String, int>{};
Map<String, int> totalMinutes = <String, int>{};
@@ -248,7 +255,8 @@ class _ActivitiesState extends State<Activities> {
int prodActs = productivtyActs[thisDate] ?? 0;
int unProdActs = unproductivtyActs[thisDate] ?? 0;
//_tasks.add(DateSeperator(thisDate, prodActs, unProdActs));
_tasks.putIfAbsent(DateSeperator(thisDate, prodActs, unProdActs), () => [Container()]);
// _tasks.putIfAbsent(DateSeperator(thisDate, prodActs, unProdActs), () => [List.generate(0, (i) => List(2));]);
_tasks.putIfAbsent(thisDate, () => ActivityListDateGroup(DateSeperator(thisDate, prodActs, unProdActs), []));
print('adding');
lastDate = thisDate;
}
@@ -260,7 +268,8 @@ class _ActivitiesState extends State<Activities> {
bool productive = element.taskType.cat?.productive ?? true;
Widget task = ActivityCard(context, name, element.startTime, element.endTime, productive, color, element, totalMinutes[thisDate] ?? 0);
// print('Activity : ${name} ,sTime: ${element.startTime}, eTime: ${element.endTime}');
_tasks.values.toList()[_tasks.length-1].add(task);
// _tasks.values.toList()[_tasks.length-1].add(task);
_tasks[thisDate]!.activities.add(task);
}
//Check for gaps
if(i < User.activities.length-1){
@@ -268,7 +277,8 @@ class _ActivitiesState extends State<Activities> {
if(gap > 10) {
Widget addGap = timeGap(User.activities[i].trueStartTime, User.activities[i+1].trueEndTime);
_tasks.values.toList()[_tasks.length-1].add(addGap);
//_tasks.values.toList()[_tasks.length-1].add(addGap);
_tasks[thisDate]!.activities.add(addGap);
}
}
}
@@ -320,7 +330,22 @@ class _ActivitiesState extends State<Activities> {
);
}
Widget DateSeperator(date, prodActs, unprodActs) {
void OnJumpToDate(date){
int itemId = 0;
List<String> keys = activitiesGroups.keys.toList();
List<ActivityListDateGroup> values = activitiesGroups.values.toList();
for(int i =0; i < activitiesGroups.length; i++){
if(keys[i] == dFormat.format(date)){
break;
}
itemId++;
// itemId+= values[i].activities.length;
}
scrollController.scrollTo(index: itemId, duration: Duration(seconds: 1),curve: Curves.fastOutSlowIn);
}
Widget DateSeperator(date, prodActs, unprodActs,{Function? onTap}) {
// double prodPercentage = (prodActs / (prodActs + unprodActs)) * 100;
return FutureBuilder(
@@ -337,18 +362,29 @@ class _ActivitiesState extends State<Activities> {
mainAxisSize: MainAxisSize.max,
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Row(
children: [
SizedBox(width: 15,),
Icon(Icons.circle),
SizedBox(
width: 10,
),
Text(
date,
style: TextStyle(fontSize: 18),
),
],
InkWell(
onTap: (){
DatePicker.showDatePicker(context,
showTitleActions: true,
minTime: User.activities[User.activities.length-1].startTime,
maxTime: User.activities[0].startTime,
theme: DatePickerTheme(), onChanged: (date) {
// print('change $date');
}, onConfirm: OnJumpToDate, currentTime: DateTime.parse(date), locale: LocaleType.en);
},
child: Row(
children: [
SizedBox(width: 15,),
Icon(Icons.circle),
SizedBox(
width: 10,
),
Text(
date,
style: TextStyle(fontSize: 18),
),
],
),
),
Row(
children: [
@@ -550,5 +586,11 @@ class _ActivitiesState extends State<Activities> {
}
}
class ActivityListDateGroup{
ActivityListDateGroup(this.dateSeperator, this.activities);
Widget dateSeperator;
List<Widget> activities;
}
List<Activity> selectedActivities = [];

View File

@@ -142,6 +142,19 @@ class ProjectStep{
DateTime? finishedDate;
}
class Journal{
Journal(this.id, this.day, {this.title, this.description});
String id;
DateTime day;
String? title;
String? description;
static String colTitle = 'Title';
static String colDescription = 'Desc';
}

165
lib/Journal.dart Normal file
View File

@@ -0,0 +1,165 @@
import 'package:firebase_auth/firebase_auth.dart';
import 'package:flutter/material.dart';
import 'package:font_awesome_flutter/font_awesome_flutter.dart';
import 'package:intl/intl.dart';
import 'package:scrollable_positioned_list/scrollable_positioned_list.dart';
import 'package:tasktracker/NewJournal.dart';
import 'package:tasktracker/main.dart';
import 'User.dart' as User;
import 'Dialogs.dart';
class JournalPage extends StatefulWidget {
const JournalPage({Key? key}) : super(key: key);
@override
State<JournalPage> createState() => _JournalPageState();
}
class _JournalPageState extends State<JournalPage> {
bool selecting = false;
List<int> selectedIndexes = [];
var refreshStream;
@override
void initState() {
// TODO: implement initState
super.initState();
refreshStream = User.refreshStream.stream.listen((event) {if(!event){setState(() {
});}});
}
@override
void dispose() {
// TODO: implement dispose
super.dispose();
refreshStream?.close();
}
@override
Widget build(BuildContext context) {
return Scaffold(
floatingActionButton: FloatingActionButton.extended(
onPressed: () {
Navigator.of(context).push(MaterialPageRoute(builder: (context) => NewJournal())).then((val) {
setState(() {});
});
},
label: Text("New Entry"),
icon: Icon(Icons.add)),
appBar: AppBar(
title: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Row(
children: [
FaIcon(FontAwesomeIcons.bookJournalWhills),
SizedBox(
width: 15,
),
Text('Journal')
],
),
Row(
children: [
if(selecting && selectedIndexes.length > 0)InkWell(onTap:() async{
selecting=false;
for (int element in selectedIndexes) {
await User.UserOperations.deleteJournal(User.journal[element].id);
}setState(() {
});
},child: Container(margin:EdgeInsets.all(8),child: Icon(Icons.delete))),
if(selecting)InkWell(onTap:(){
selecting=false;
setState(() {
});
},child: Container(margin:EdgeInsets.all(8),child: Icon(Icons.cancel))),
],
)
],
),
),
drawer: navDrawer(context, 8),
body: Container(
padding: EdgeInsets.all(8),
child: ScrollablePositionedList.builder(
itemCount: User.journal.length,
itemBuilder: (context, index) {
return Container(
//duration: Duration(milliseconds: 500),
child: InkWell(
onTap: (){
if(selecting){
if(selectedIndexes.contains(index)){
selectedIndexes.remove(index);
}else{
selectedIndexes.add(index);
}
setState(() {
});
}
},
onLongPress: () {
selecting = !selecting;
if(!selectedIndexes.contains(index)){selectedIndexes.add(index);}
setState(() {});
},
child: Row(
children: [
if (selecting)
Checkbox(
value: selectedIndexes.contains(index),
onChanged: (newVal) {
if(selectedIndexes.contains(index)){
selectedIndexes.remove(index);
}else{
selectedIndexes.add(index);
}
setState(() {
});
},
),
Expanded(
child: Card(
child: Padding(
padding: const EdgeInsets.all(8.0),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Text(User.journal[index].title ?? '', style: TextStyle(fontSize: 18)),
Text(DateFormat('yyyy-MM-dd').format(User.journal[index].day))
],
),
if (User.journal[index].description != null && User.journal[index].description!.isNotEmpty)
Text(User.journal[index].description!)
],
),
),
),
),
if(selecting)InkWell(onTap:(){
Navigator.of(context).push(MaterialPageRoute(builder: (context) => NewJournal(date: User.journal[index].day, title: User.journal[index].title, text: User.journal[index].description,))).then((val) {
setState(() {});
});
selecting=false;
setState(() {
});
},child: Container(margin:EdgeInsets.all(8),child: FaIcon(FontAwesomeIcons.edit)))
],
),
));
}),
),
);
}
}

189
lib/NewJournal.dart Normal file
View File

@@ -0,0 +1,189 @@
import 'package:flutter/material.dart';
import 'package:flutter_datetime_picker/flutter_datetime_picker.dart';
import 'package:font_awesome_flutter/font_awesome_flutter.dart';
import 'package:intl/intl.dart';
import 'package:flutter_colorpicker/flutter_colorpicker.dart';
import 'User.dart' as User;
import 'Data.dart';
class NewJournal extends StatefulWidget {
NewJournal({Key? key, this.title, this.text, this.date}) : super(key: key);
late String? title;
late String? text;
late DateTime? date;
@override
_NewJournalState createState() => _NewJournalState(title: title, text: text, m_date: date);
}
class _NewJournalState extends State<NewJournal> {
bool editing =false;
_NewJournalState({String? title, String? text, DateTime? m_date}){
if(m_date!= null){
editing = true;
date=m_date;
oldDate =m_date;
}
titleController.text = title??'';
descriptionEditingController.text = text??'';
}
TextEditingController titleController = TextEditingController();
TextEditingController descriptionEditingController = TextEditingController();
bool productive = true;
Color pickerColor = Colors.blue;
DateTime date= DateTime.now();
DateTime oldDate = DateTime.now();
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: Text('${(editing) ? 'Edit' : 'New'} Journal Entry')),
body: Container(
height: MediaQuery.of(context).size.height,
child: Column(mainAxisSize: MainAxisSize.max, mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [
Expanded(flex: 9,
child: SingleChildScrollView(
child: Padding(
padding: EdgeInsets.fromLTRB(20, 50, 20, 50),
child: Column(
children: [
InkWell(
onTap: (){
DatePicker.showDatePicker(context,
showTitleActions: true,
minTime: User.activities[User.activities.length-1].startTime,
maxTime: User.activities[0].startTime,
theme: DatePickerTheme(), onChanged: (date) {
// print('change $date');
}, onConfirm: (newDate){
date = newDate;
}, currentTime: DateTime.now(), locale: LocaleType.en);
},
child: Container(
margin: EdgeInsets.symmetric(vertical: 10),
child: Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
FaIcon(FontAwesomeIcons.calendarDay),
SizedBox(width: 10,),
Text('Date : '),
SizedBox(width: 30,),
Text(
DateFormat('yyyy-MM-dd').format(date),
style: TextStyle(fontSize: 18),
),
SizedBox(width: 30,),
],
),
),
),
SizedBox(height: 10,),
Column(children: [
Container(
padding: EdgeInsets.all(10),
child: TextField(
controller: titleController,
decoration: InputDecoration(hintText: 'Title (something special happened this day)', border: OutlineInputBorder()),
),
),
Divider(),
Container(
padding: EdgeInsets.all(10),
child: TextField(
maxLines: 25,
minLines: 10,
controller: descriptionEditingController,
decoration: InputDecoration(hintText: 'So how was your day? Write it all down here!', border: OutlineInputBorder()),
),
),
]),
],
))),
),
Container(
padding: EdgeInsets.symmetric(vertical: 10, horizontal: 20),
child: Row(
mainAxisSize: MainAxisSize.max,
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: [
Expanded(
flex: 5,
child: Container(
padding: EdgeInsets.symmetric(horizontal: 10, vertical: 0),
child: ElevatedButton(
style: ElevatedButton.styleFrom(primary: Colors.red, shape: StadiumBorder()),
onPressed: () {
setState(() {
Navigator.pop(context);
});
},
child: Text('Back', style: TextStyle(fontSize: 20))))),
Expanded(
flex: 6,
child: Container(
padding: EdgeInsets.symmetric(horizontal: 10, vertical: 0),
child: ElevatedButton(
style: ElevatedButton.styleFrom(primary: Colors.green, shape: StadiumBorder()),
onPressed: () {
add_action();
},
child: Text('${editing ? 'Edit ' : 'Add '}Entry', style: TextStyle(fontSize: 20))))),
],
))
])));
}
void add_action() async {
String title = titleController.value.text;
String text = descriptionEditingController.text;
if (title.isEmpty && text.isEmpty) {
showAlertDialog(context, 'Empty data', 'Journal entry is empty, Cannot add empty entries');
return;
}
if(editing){
await User.UserOperations.editJournal(oldDate,date,title,text);
}else{
await User.UserOperations.addJournal(date, title, text);
}
Navigator.of(context).popUntil((route) {
return route.isFirst;
});
}
}
String _printDuration(Duration duration) {
String twoDigits(int n) => n.toString().padLeft(2, "0");
String twoDigitMinutes = twoDigits(duration.inMinutes.remainder(60));
String twoDigitSeconds = twoDigits(duration.inSeconds.remainder(60));
return "${twoDigits(duration.inHours)}:$twoDigitMinutes:$twoDigitSeconds";
}
showAlertDialog(BuildContext context, String title, String message) {
// set up the button
Widget okButton = TextButton(
child: Text("OK"),
onPressed: () {
Navigator.of(context).pop();
},
);
// set up the AlertDialog
AlertDialog alert = AlertDialog(
title: Text(title),
content: Text(message),
actions: [
okButton,
],
);
// show the dialog
showDialog(
context: context,
builder: (BuildContext context) {
return alert;
},
);
}

View File

@@ -28,6 +28,7 @@ List<Category> categories = [];
List<TaskType> taskTypes = [];
List<Activity> activities = [];
List<Project> projects = [];
List<Journal> journal = [];
bool offline = true;
bool registered = false;
@@ -136,14 +137,17 @@ Future<void> refreshUserData({bool forceOffline = false}) async {
taskTypes = await GetTaskTypes(true);
activities = await GetActivities(true);
projects= await GetProjects(true);
journal = await GetJournals(true);
refreshStream.add(false);
}else{
await updateCatsList();
await updateTasksList();
await updateActList();
await updateProjectsList();
categories = await GetCategories(false);
taskTypes = await GetTaskTypes(false);
activities = await GetActivities(false);
projects= await GetProjects(false);
journal = await GetJournals(false);
}
m_refreshing=false;
@@ -213,6 +217,8 @@ void onCacheDatabaseCreate(Database db, int newVersion) async {
'CREATE TABLE Projects(id TEXT PRIMARY KEY, ${Project.colName} TEXT, ${Project.colCat} TEXT, ${Project.colSteps} TEXT, ${Project.colEta} INT, ${Project.colDeadline} DATETIME)';
await db.execute(ProjectsTableSQL);
String JournalTableSQL = 'CREATE TABLE Journal(id TEXT PRIMARY KEY, ${Journal.colTitle} TEXT, ${Journal.colDescription})';
await db.execute(JournalTableSQL);
String QueriesTableSQL = 'CREATE TABLE Queries(id INTEGER PRIMARY KEY AUTOINCREMENT, ${Queries.colLink} TEXT,${Queries.colData} TEXT)';
// print(QueriesTableSQL);
await db.execute(QueriesTableSQL);
@@ -750,6 +756,92 @@ Future<void> UpdateProjectsFromServer() async {
}
}
Future<List<Journal>> GetJournals(bool forceOffline) async {
if (cacheEnabled) {
List<Journal> _journals = [];
if (offline || forceOffline) {
//Retreive from cacheDB
} else {
//Check if server got updated, If not go for cache
//Validate device_id to check updates
bool catsUpdated = false;
// try {
// http.Response update_response = (await http.post(Uri.parse('http://161.97.127.136/task_tracker/check_update.php'), body: <String, String>{"username": username, "device_id": android_id}));
// final data = update_response.body.split(',');
// catsUpdated = data[0] == '1';
// } catch (e) {
// print(e);
// }
//Update CacheDB
if (!catsUpdated) {
await UpdateJournalsFromServer();
}
}
List<Map> cats = await cacheDb.query('Journal');
print(cats.length);
for (Map element in cats) {
String? id = element['id'].toString();
String? title = element[Journal.colTitle].toString();
String? text = element[Journal.colDescription].toString();
if (id == null || title == null || text == null) {
print("Something is null!");
print("id:{$id}, title:{$title}, text:${text}");
continue;
}
DateTime day = DateTime.parse(id.replaceAll(username, ''));
// print("name:{$catName}, color:{$catColor}, prod:{$catProductive}");
_journals.add(Journal(id,day,title: title,description: text));
}
journal = _journals;
} else {
print("NC: Updating Categories as $username");
try {
http.Response response = (await http.post(Uri.parse('http://161.97.127.136/task_tracker/get_journals.php'),
body: <String, String>{"username": username, "device_id": await Settings.UUID()}));
print(response.body);
List<String> data = response.body.split("<td>");
List<Journal> _categories = [];
for (var value in data) {
Map<String, dynamic> cat = jsonDecode(value);
//print(catData);
_categories.add(Journal(cat['id'],DateTime.parse(cat['id'].toString().replaceAll(username, '')), title:cat['title'], description:cat['text']));
}
journal = _categories;
} catch (e) {
print("Error while cats NC: $e");
}
}
journal.sort((a,b)=> b.day.compareTo(a.day));
return journal;
}
Future<void> UpdateJournalsFromServer() async {
print("Updating Journal as $username");
try {
http.Response response = (await http.post(Uri.parse('http://161.97.127.136/task_tracker/get_journals.php'),
body: <String, String>{"username": username, "device_id": await Settings.UUID()}));
print(response.body);
List<String> data = response.body.split("<td>");
await cacheDb.delete("Journal");
for (var value in data) {
Map<String, dynamic> cat = jsonDecode(value);
//print(catData);
await cacheDb
.rawInsert("INSERT OR REPLACE INTO Journal (id, ${Journal.colTitle},${Journal.colDescription}) "
"VALUES ('${cat['id']}','${cat['title'].toString().replaceAll("'", "''")}','${cat['description'].toString().replaceAll("'", "''")}') ");
}
} catch (e) {
print("Error while cats $e");
}
}
Future<TaskType?> getTaskFromId(String taskId) async {
// await GetTaskTypes(false);
TaskType? cat = null;
@@ -1221,6 +1313,89 @@ class UserOperations {
await executeQueries();
}
static Future<void> addJournal(DateTime day, String title, String text) async {
String id = username + DateFormat('yyyy-MM-dd').format(day);
Map<String, String> queryBody = <String, String>{
'username': username,
'id': id,
'title': title,
'description': text
};
if (cacheEnabled) {
//Add Query
Map<String, Object> query = {Queries.colLink: 'add_journal', Queries.colData: jsonEncode(queryBody)};
print("adding new query ${query[Queries.colLink]} : ${jsonEncode(queryBody)}");
await cacheDb.insert('Queries', query);
//update Cache
Map<String, Object> data = {
'id':id,
Journal.colTitle: title,
Journal.colDescription:text
};
await cacheDb.insert('Journal', data);
await refreshUserData(forceOffline: true);
} else {
try {
http.Response queryResponse = (await http.post(Uri.parse('http://161.97.127.136/task_tracker/add_journal.php'), body: queryBody));
print("Query executed : Results{${queryResponse.body}");
if (queryResponse.body.toLowerCase().contains("success")) {
//Success
}
} catch (e) {
print('NC: Error adding journal entry $e}');
}
//executeQueries();
}
//Add to server and refresh Cache
await executeQueries();
}
static Future<void> editJournal(DateTime oldDay, DateTime day, String title, String text) async {
String oldId = username + DateFormat('yyyy-MM-dd').format(oldDay);
String id = username + DateFormat('yyyy-MM-dd').format(day);
Map<String, String> queryBody = <String, String>{
'username': username,
'old_id':oldId,
'id': id,
'title': title,
'description': text
};
if (cacheEnabled) {
//Add Query
Map<String, Object> query = {Queries.colLink: 'edit_journal', Queries.colData: jsonEncode(queryBody)};
print("adding new query ${query[Queries.colLink]} : ${jsonEncode(queryBody)}");
await cacheDb.insert('Queries', query);
await cacheDb.rawUpdate("UPDATE Journal SET id='$id', ${Journal.colTitle}='${title.toString().replaceAll("'", "''")}', ${Journal.colDescription}='${text.toString().replaceAll("'", "''")}' WHERE id='$oldId'");
//update Cache
Map<String, Object> data = {
'id':id,
Journal.colTitle: title,
Journal.colDescription:text
};
// await cacheDb.insert('Journal', data);
await refreshUserData(forceOffline: true);
} else {
try {
http.Response queryResponse = (await http.post(Uri.parse('http://161.97.127.136/task_tracker/edit_journal.php'), body: queryBody));
print("Query executed : Results{${queryResponse.body}");
if (queryResponse.body.toLowerCase().contains("success")) {
//Success
}
} catch (e) {
print('NC: Error adding journal entry $e}');
}
//executeQueries();
}
//Add to server and refresh Cache
await executeQueries();
}
static Future<void> deleteTask(String name, {bulk = false}) async {
Map<String, String> queryBody = <String, String>{
'id': username + name,
@@ -1372,6 +1547,43 @@ class UserOperations {
}
}
static Future<void> deleteJournal(String id, {bulk = false}) async {
Map<String, String> queryBody = <String, String>{
'username': username,
'id': id,
};
//Add Query
Map<String, Object> query = {Queries.colLink: 'delete_journal', Queries.colData: jsonEncode(queryBody)};
print("adding new query ${query[Queries.colLink]} : ${jsonEncode(queryBody)}");
if (cacheEnabled) {
await cacheDb.insert('Queries', query);
//update Cache
String deleteQuery =
"DELETE FROM Journal WHERE id='$id'";
print("delteQuery : $deleteQuery");
await cacheDb.rawDelete(deleteQuery);
await refreshUserData(forceOffline: true);
//Add to server and refresh Cache
} else {
try {
http.Response queryResponse = (await http.post(Uri.parse('http://161.97.127.136/task_tracker/delete_journal.php'), body: queryBody));
print("Query executed : Results{${queryResponse.body}");
if (queryResponse.body.toLowerCase().contains("success")) {
//Success
}
} catch (e) {
print('NC: Error deleting journal $e}');
}
}
if (!bulk) {
await executeQueries();
}
}
static Future<void> executeQueries() async {
if (cacheEnabled) {
if (offline) {

View File

@@ -10,6 +10,7 @@ import 'package:intl/intl.dart';
import 'package:provider/provider.dart';
import 'package:shared_preferences/shared_preferences.dart';
import 'package:tasktracker/Categories.dart';
import 'package:tasktracker/Journal.dart';
import 'package:tasktracker/Projects.dart';
import 'package:tasktracker/Todo.dart';
import 'package:tasktracker/Welcome.dart';
@@ -111,7 +112,8 @@ class MyApp extends StatelessWidget {
'/Categories': (context) => const Categories(),
'/Activities': (context) => const Activities(),
'/Settings': (context) => const SettingsPage(),
'/Projects':(context)=> const Projects()
'/Projects':(context)=> const Projects(),
'/Journal': (context)=> const JournalPage()
});
});
}
@@ -283,7 +285,7 @@ class _MyHomePageState extends State<MyHomePage> {
ongoingActName = "";
}
if(mounted) {
if(this.mounted) {
setState(() {
});
@@ -1003,7 +1005,7 @@ Drawer navDrawer(BuildContext context, int pageIndex) {
ListTile(
selected: (pageIndex == 7),
title: Text('Projects'),
leading: Icon(Icons.work_outline_sharp, color: Theme.of(context).primaryColor),
leading: FaIcon(FontAwesomeIcons.rocket, color: Theme.of(context).primaryColor),
onTap: () {
if (pageIndex == 7) {
return;
@@ -1011,6 +1013,17 @@ Drawer navDrawer(BuildContext context, int pageIndex) {
Navigator.of(context).pushReplacementNamed('/Projects');
},
),
ListTile(
selected: (pageIndex == 8),
title: Text('Journal'),
leading: FaIcon(FontAwesomeIcons.bookJournalWhills, color: Theme.of(context).primaryColor),
onTap: () {
if (pageIndex == 8) {
return;
}
Navigator.of(context).pushReplacementNamed('/Journal');
},
),
// ListTile(
// selected: (pageIndex == 7),
// title: Text('TODO'),
@@ -1046,37 +1059,6 @@ Drawer navDrawer(BuildContext context, int pageIndex) {
));
}
class MyPlayerBar extends CustomPainter {
MyPlayerBar(this.max, this.value, {this.background = Colors.lightBlue, this.fill = Colors.blue});
Color background = Colors.lightBlue;
Color fill = Colors.blue;
final int max;
final int value;
@override
void paint(Canvas canvas, Size size) {
Paint paint = Paint();
double cursor = (value * size.width) / max;
Radius cornerRadius = Radius.circular(10.0);
// Already played half color (your darker orange)
paint.color = background;
// Painting already played half
canvas.drawRRect(RRect.fromRectAndCorners(Rect.fromLTWH(0.0, 0.0, cursor, size.height), topLeft: cornerRadius, bottomLeft: cornerRadius), paint);
// Yet to play half color (your lighter orange)
paint.color = fill;
// Painting the remaining space
canvas.drawRRect(RRect.fromRectAndCorners(Rect.fromLTWH(cursor, 0.0, size.width - cursor, size.height), bottomRight: cornerRadius, topRight: cornerRadius), paint);
}
@override
bool shouldRepaint(CustomPainter oldDelegate) => true;
}
class CatMapData {
CatMapData(this.name, this.time, this.color);
final String name;