This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
extension NoteStateX on NoteState { | |
/// Checks if a note in this state can be edited. | |
bool get canEdit => this < NoteState.deleted; | |
/// Returns true if this state is preceding to the other one. | |
bool operator <(NoteState other) => (this?.index ?? 0) < (other?.index ?? 0); | |
/// Message describes the state transition. | |
String get message { | |
switch (this) { |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/// Save the note before the editor is dismissed | |
Future<dynamic> _onPop(String uid) => _isDirty | |
? _note.saveToFireStore(uid) | |
: Future.value(); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
extension NoteStore on Note { | |
/// Save this note to FireStore. | |
Future<dynamic> saveToFireStore(String uid) async { | |
final col = notesCollection(uid); | |
return id == null | |
? col.add(toJson()) | |
: col.document(id).updateData(toJson()); | |
} | |
... | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
class _HomeScreenState extends State<HomeScreen> with CommandHandler { | |
Widget _fab(BuildContext context) => FloatingActionButton( | |
child: const Icon(Icons.add), | |
onPressed: () async { | |
final command = await Navigator.pushNamed(context, '/note'); | |
processNoteCommand(_scaffoldKey.currentState, command); | |
}, | |
); | |
... | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
mixin CommandHandler<T extends StatefulWidget> on State<T> { | |
/// Processes the given [command]. | |
Future<void> processNoteCommand(ScaffoldState scaffoldState, NoteCommand command) async { | |
if (command == null) { | |
return; | |
} | |
await command.execute(); | |
final msg = command.message; | |
if (mounted && msg?.isNotEmpty == true) { | |
scaffoldState?.showSnackBar(SnackBar( |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
@override | |
Widget build(BuildContext context) { | |
final uid = Provider.of<CurrentUser>(context).data.uid; | |
return ChangeNotifierProvider.value( | |
value: _note, | |
child: Consumer<Note>( | |
builder: (_, __, ___) => Hero( | |
tag: 'NoteItem${_note.id}', | |
child: DefaultTextStyle( | |
style: ... |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// in the note list | |
@override | |
Widget build(BuildContext context) => Hero( | |
tag: 'NoteItem${note.id}', | |
child: DefaultTextStyle( | |
style: kNoteTextLight, | |
child: Container( | |
... | |
), | |
), |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// when pressed, dissmiss the bottom sheet and return a command | |
IconButton( | |
icon: const Icon(Icons.archive), | |
tooltip: 'Archive', | |
onPressed: () => Navigator.pop(context, NoteStateUpdateCommand( | |
id: _note.id, | |
uid: uid, | |
from: _note.state, // the current state | |
to: NoteState.archived, // the transition target | |
)), |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
class NoteStateUpdateCommand extends NoteCommand { | |
final NoteState from; | |
final NoteState to; | |
/// Create a [NoteCommand] to update state of a note [from] the current state [to] another. | |
NoteStateUpdateCommand({ | |
@required String id, | |
@required String uid, | |
@required this.from, | |
@required this.to, |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
abstract class NoteCommand { | |
final String id; | |
final String uid; | |
/// Defines an reversible action to a note, provides the note [id], and the current user's [uid]. | |
const NoteCommand({ | |
@required this.id, | |
@required this.uid, | |
}); |
NewerOlder