reload files view when adding/editing a note

organize in folders
This commit is contained in:
lukas-heiligenbrunner 2022-10-29 22:55:38 +02:00
parent 7baef13eae
commit ab1bacea00
13 changed files with 182 additions and 156 deletions

95
lib/app.dart Normal file
View File

@ -0,0 +1,95 @@
import 'package:flutter/material.dart';
import 'package:notes/context/file_change_notifier.dart';
import 'package:provider/provider.dart';
import 'canvas/drawing_page.dart';
import 'pages/all_notes_page.dart';
import 'widgets/collapse_drawer.dart';
class App extends StatefulWidget {
const App({super.key});
@override
State<App> createState() => _AppState();
}
class _AppState extends State<App> {
View activePage = View.all;
@override
Widget build(BuildContext context) {
return ChangeNotifierProvider(
create: (ctx) {
final notifier = FileChangeNotifier();
notifier.loadAllNotes();
return notifier;
},
child: Scaffold(
floatingActionButton: _fab(),
body: Row(
children: [
CollapseDrawer(
onPageChange: (View newPage) =>
setState(() => activePage = newPage),
activePage: activePage,
),
Expanded(
child: Container(
color: const Color(0xff0d0d0d),
child: _buildPage(),
))
],
),
),
);
}
Widget _fab() {
switch (activePage) {
case View.all:
case View.folders:
return FloatingActionButton(
onPressed: () async {
final now = DateTime.now();
String filename =
'note-${now.year}_${now.month}_${now.day}-${now.hour}_${now.minute}.dbnote';
Navigator.push(
context,
MaterialPageRoute(
builder: (ctx) => DrawingPage(filePath: filename),
),
).then((value) =>
Provider.of<FileChangeNotifier>(context, listen: false)
.loadAllNotes());
},
backgroundColor: const Color(0xff3f3f3f),
child: const Icon(Icons.edit_calendar_outlined, color: Colors.orange),
);
default:
return Container();
}
}
Widget _buildPage() {
switch (activePage) {
case View.all:
return const AllNotesPage();
case View.shared:
return const Text(
'shared notebooks WIP',
style: TextStyle(color: Colors.white),
);
case View.recycle:
return const Text(
'recycle bin WIP',
style: TextStyle(color: Colors.white),
);
case View.folders:
return const Text(
'Folders WIP',
style: TextStyle(color: Colors.white),
);
}
}
}

View File

@ -8,8 +8,8 @@ import 'my_painter.dart';
import 'paint_controller.dart'; import 'paint_controller.dart';
import 'screen_document_mapping.dart'; import 'screen_document_mapping.dart';
import '../icon_material_button.dart'; import '../widgets/icon_material_button.dart';
import '../tool_bar.dart'; import '../widgets/tool_bar.dart';
/// Handles input events and draws canvas element /// Handles input events and draws canvas element
class DrawingPage extends StatefulWidget { class DrawingPage extends StatefulWidget {

View File

@ -0,0 +1,31 @@
import 'dart:io';
import 'package:flutter/cupertino.dart';
import '../savesystem/path.dart';
import '../widgets/note_tile.dart';
class FileChangeNotifier extends ChangeNotifier {
FileChangeNotifier();
List<NoteTileData> tiledata = [];
Future<List<NoteTileData>> loadAllNotes() async {
final path = await getSavePath();
final dta = await path
.list()
.where((fsentity) => fsentity.path.endsWith('.dbnote'))
.asyncMap((fsentity) async {
final lastmodified = (await fsentity.stat()).modified;
final filename = fsentity.path.split(Platform.pathSeparator).last;
final name = filename.substring(0, filename.length - 7);
return NoteTileData(name, filename, lastmodified);
}).toList();
dta.sort(
(a, b) => a.lastModified.isAfter(b.lastModified) ? -1 : 1,
);
notifyListeners();
tiledata = dta;
return dta;
}
}

View File

@ -1,114 +1,15 @@
import 'package:flutter/foundation.dart'; import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:notes/collapse_drawer.dart';
import 'package:notes/all_notes_page.dart';
import 'package:notes/canvas/drawing_page.dart';
import 'package:sqflite/sqflite.dart'; import 'package:sqflite/sqflite.dart';
import 'package:sqflite_common_ffi/sqflite_ffi.dart'; import 'package:sqflite_common_ffi/sqflite_ffi.dart';
import 'app.dart';
void main() { void main() {
if (defaultTargetPlatform != TargetPlatform.android && if (defaultTargetPlatform != TargetPlatform.android &&
defaultTargetPlatform != TargetPlatform.iOS) { defaultTargetPlatform != TargetPlatform.iOS) {
sqfliteFfiInit(); sqfliteFfiInit();
databaseFactory = databaseFactoryFfi; databaseFactory = databaseFactoryFfi;
} }
runApp(const MyApp()); runApp(const MaterialApp(home: App()));
}
class MyApp extends StatelessWidget {
const MyApp({super.key});
// This widget is the root of your application.
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
// is not restarted.
primarySwatch: Colors.blue,
),
home: const MyHomePage(title: 'Flutter Demo Home Page'),
);
}
}
class MyHomePage extends StatefulWidget {
const MyHomePage({super.key, required this.title});
final String title;
@override
State<MyHomePage> createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
View activePage = View.all;
@override
Widget build(BuildContext context) {
return Scaffold(
floatingActionButton: _fab(),
body: Row(
children: [
CollapseDrawer(
onPageChange: (View newPage) =>
setState(() => activePage = newPage),
activePage: activePage,
),
Expanded(
child: Container(
color: const Color(0xff0d0d0d),
child: _buildPage(),
))
],
),
);
}
Widget _fab() {
switch (activePage) {
case View.all:
case View.folders:
return FloatingActionButton(
onPressed: () {
final now = DateTime.now();
String filename =
'note-${now.year}_${now.month}_${now.day}-${now.hour}_${now.minute}.dbnote';
Navigator.push(
context,
MaterialPageRoute(
builder: (context) => DrawingPage(filePath: filename),
),
);
},
backgroundColor: const Color(0xff3f3f3f),
child: const Icon(Icons.edit_calendar_outlined, color: Colors.orange),
);
default:
return Container();
}
}
Widget _buildPage() {
switch (activePage) {
case View.all:
return const AllNotesPage();
case View.shared:
return const Text(
'shared notebooks WIP',
style: TextStyle(color: Colors.white),
);
case View.recycle:
return const Text(
'recycle bin WIP',
style: TextStyle(color: Colors.white),
);
case View.folders:
return const Text(
'Folders WIP',
style: TextStyle(color: Colors.white),
);
}
}
} }

View File

@ -1,9 +1,8 @@
import 'dart:io';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:notes/icon_material_button.dart'; import 'package:notes/context/file_change_notifier.dart';
import 'package:notes/note_tile.dart'; import 'package:notes/widgets/icon_material_button.dart';
import 'package:notes/savesystem/path.dart'; import 'package:notes/widgets/note_tile.dart';
import 'package:provider/provider.dart';
class AllNotesPage extends StatefulWidget { class AllNotesPage extends StatefulWidget {
const AllNotesPage({Key? key}) : super(key: key); const AllNotesPage({Key? key}) : super(key: key);
@ -13,8 +12,6 @@ class AllNotesPage extends StatefulWidget {
} }
class _AllNotesPageState extends State<AllNotesPage> { class _AllNotesPageState extends State<AllNotesPage> {
List<NoteTileData> tileData = [];
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
return Column( return Column(
@ -63,40 +60,19 @@ class _AllNotesPageState extends State<AllNotesPage> {
Widget _buildNoteTiles() { Widget _buildNoteTiles() {
return Expanded( return Expanded(
child: GridView.builder( child: Consumer<FileChangeNotifier>(
builder: (BuildContext context, value, Widget? child) {
return GridView.builder(
gridDelegate: const SliverGridDelegateWithFixedCrossAxisCount( gridDelegate: const SliverGridDelegateWithFixedCrossAxisCount(
crossAxisCount: 5, crossAxisCount: 5,
), ),
padding: const EdgeInsets.all(2), padding: const EdgeInsets.all(2),
itemBuilder: (BuildContext context, int idx) => itemBuilder: (BuildContext context, int idx) =>
NoteTile(data: tileData[idx]), NoteTile(data: value.tiledata[idx]),
itemCount: tileData.length, itemCount: value.tiledata.length,
);
},
), ),
); );
} }
@override
void initState() {
super.initState();
loadAllNotes();
}
Future<void> loadAllNotes() async {
final path = await getSavePath();
final dta = await path
.list()
.where((fsentity) => fsentity.path.endsWith('.dbnote'))
.asyncMap((fsentity) async {
final lastmodified = (await fsentity.stat()).modified;
final filename = fsentity.path.split(Platform.pathSeparator).last;
final name = filename.substring(0, filename.length - 7);
return NoteTileData(name, filename, lastmodified);
}).toList();
dta.sort(
(a, b) => a.lastModified.isAfter(b.lastModified) ? -1 : 1,
);
setState(() {
tileData = dta;
});
}
} }

View File

@ -2,13 +2,13 @@ import 'dart:io';
import 'package:flutter/foundation.dart'; import 'package:flutter/foundation.dart';
import 'package:path_provider/path_provider.dart'; import 'package:path_provider/path_provider.dart';
import 'package:sqflite/sqflite.dart';
Future<Directory> getSavePath() async { Future<Directory> getSavePath() async {
Directory dbpath; Directory dbpath;
if (defaultTargetPlatform == TargetPlatform.android || if (defaultTargetPlatform == TargetPlatform.android ||
defaultTargetPlatform == TargetPlatform.iOS) { defaultTargetPlatform == TargetPlatform.iOS) {
dbpath = Directory(await getDatabasesPath()); dbpath = Directory(
'${(await getApplicationDocumentsDirectory()).path}${Platform.pathSeparator}notes');
} else { } else {
dbpath = Directory( dbpath = Directory(
'${(await getApplicationDocumentsDirectory()).path}${Platform.pathSeparator}notes'); '${(await getApplicationDocumentsDirectory()).path}${Platform.pathSeparator}notes');

View File

@ -1,6 +1,8 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart'; import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:notes/drawer_item.dart'; import 'package:notes/context/file_change_notifier.dart';
import 'package:notes/widgets/drawer_item.dart';
import 'package:provider/provider.dart';
enum View { all, shared, recycle, folders } enum View { all, shared, recycle, folders }
@ -98,12 +100,14 @@ class _CollapseDrawerState extends State<CollapseDrawer>
Expanded( Expanded(
child: ListView( child: ListView(
children: [ children: [
DrawerItem( Consumer<FileChangeNotifier>(
builder: (context, value, child) => DrawerItem(
dta: ItemData('All Notes', Icons.book), dta: ItemData('All Notes', Icons.book),
collapsed: collapsed, collapsed: collapsed,
endText: '7', endText: value.tiledata.length.toString(),
active: widget.activePage == View.all, active: widget.activePage == View.all,
onTap: () => widget.onPageChange(View.all)), onTap: () => widget.onPageChange(View.all)),
),
DrawerItem( DrawerItem(
dta: ItemData('Shared Notebooks', Icons.person_outline), dta: ItemData('Shared Notebooks', Icons.person_outline),
collapsed: collapsed, collapsed: collapsed,

View File

@ -1,6 +1,8 @@
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:provider/provider.dart';
import 'canvas/drawing_page.dart'; import '../canvas/drawing_page.dart';
import '../context/file_change_notifier.dart';
class NoteTileData { class NoteTileData {
final String name; final String name;
@ -24,7 +26,9 @@ class NoteTile extends StatelessWidget {
MaterialPageRoute( MaterialPageRoute(
builder: (context) => DrawingPage(filePath: data.relativePath), builder: (context) => DrawingPage(filePath: data.relativePath),
), ),
); ).then((value) =>
Provider.of<FileChangeNotifier>(context, listen: false)
.loadAllNotes());
}, },
child: SizedBox( child: SizedBox(
width: 100, width: 100,

View File

@ -5,7 +5,7 @@ import 'package:iconify_flutter/iconify_flutter.dart';
import 'package:iconify_flutter/icons/emojione_monotone.dart'; import 'package:iconify_flutter/icons/emojione_monotone.dart';
import 'package:iconify_flutter/icons/jam.dart'; import 'package:iconify_flutter/icons/jam.dart';
import 'canvas/paint_controller.dart'; import '../canvas/paint_controller.dart';
import 'icon_material_button.dart'; import 'icon_material_button.dart';
class ToolBar extends StatefulWidget { class ToolBar extends StatefulWidget {

View File

@ -144,6 +144,13 @@ packages:
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "1.8.0" version: "1.8.0"
nested:
dependency: transitive
description:
name: nested
url: "https://pub.dartlang.org"
source: hosted
version: "1.0.0"
path: path:
dependency: transitive dependency: transitive
description: description:
@ -242,6 +249,13 @@ packages:
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "4.2.4" version: "4.2.4"
provider:
dependency: "direct main"
description:
name: provider
url: "https://pub.dartlang.org"
source: hosted
version: "6.0.4"
sky_engine: sky_engine:
dependency: transitive dependency: transitive
description: flutter description: flutter

View File

@ -35,6 +35,7 @@ dependencies:
sqflite: ^2.2.0+2 sqflite: ^2.2.0+2
sqflite_common_ffi: ^2.2.0+1 sqflite_common_ffi: ^2.2.0+1
path_provider: ^2.0.11 path_provider: ^2.0.11
provider: ^6.0.4
dev_dependencies: dev_dependencies:
flutter_test: flutter_test: