improved widget constructors and main future builder

This commit is contained in:
Thibault Deckers 2019-07-23 23:54:49 +09:00
parent 3c9813c942
commit f091ad1955
7 changed files with 86 additions and 54 deletions

View file

@ -6,12 +6,13 @@ class OutlinedText extends StatelessWidget {
final double outlineWidth; final double outlineWidth;
final Color outlineColor; final Color outlineColor;
OutlinedText( const OutlinedText(
this.data, { this.data, {
Key key,
this.style, this.style,
@required this.outlineWidth, @required this.outlineWidth,
@required this.outlineColor, @required this.outlineColor,
}); }) : super(key: key);
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {

View file

@ -7,7 +7,7 @@ class FullscreenOverlay extends StatefulWidget {
final List<Map> entries; final List<Map> entries;
final int index; final int index;
FullscreenOverlay({this.entries, this.index}); const FullscreenOverlay({Key key, this.entries, this.index}) : super(key: key);
@override @override
State<StatefulWidget> createState() => _FullscreenOverlayState(); State<StatefulWidget> createState() => _FullscreenOverlayState();

View file

@ -10,7 +10,11 @@ class ImageFullscreenPage extends StatefulWidget {
final List<Map> entries; final List<Map> entries;
final String initialUri; final String initialUri;
ImageFullscreenPage({this.entries, this.initialUri}); const ImageFullscreenPage({
Key key,
this.entries,
this.initialUri,
}) : super(key: key);
@override @override
ImageFullscreenPageState createState() => ImageFullscreenPageState(); ImageFullscreenPageState createState() => ImageFullscreenPageState();

View file

@ -16,7 +16,7 @@ class MyApp extends StatelessWidget {
theme: ThemeData( theme: ThemeData(
brightness: Brightness.dark, brightness: Brightness.dark,
accentColor: Colors.amberAccent, accentColor: Colors.amberAccent,
scaffoldBackgroundColor: Colors.grey[900] scaffoldBackgroundColor: Colors.grey[900],
), ),
home: HomePage(), home: HomePage(),
); );
@ -29,18 +29,13 @@ class HomePage extends StatefulWidget {
} }
class _HomePageState extends State<HomePage> { class _HomePageState extends State<HomePage> {
List<Map> imageEntryList; Future<List<Map>> _entryListLoader;
@override @override
void initState() { void initState() {
super.initState(); super.initState();
imageCache.maximumSizeBytes = 100 * 1024 * 1024; imageCache.maximumSizeBytes = 100 * 1024 * 1024;
getImageEntries(); _entryListLoader = ImageFetcher.getImageEntries();
}
getImageEntries() async {
imageEntryList = await ImageFetcher.getImageEntries();
setState(() {});
} }
@override @override
@ -49,11 +44,17 @@ class _HomePageState extends State<HomePage> {
// fake app bar so that content is safe from status bar, even though we use a SliverAppBar // fake app bar so that content is safe from status bar, even though we use a SliverAppBar
appBar: FakeAppBar(), appBar: FakeAppBar(),
body: Container( body: Container(
child: imageEntryList == null child: FutureBuilder(
? Center( future: _entryListLoader,
child: CircularProgressIndicator(), builder: (futureContext, AsyncSnapshot<List<Map>> snapshot) {
) if (snapshot.connectionState == ConnectionState.done && !snapshot.hasError) {
: ThumbnailCollection(imageEntryList), return ThumbnailCollection(entries: snapshot.data);
}
return Center(
child: CircularProgressIndicator(),
);
},
),
), ),
resizeToAvoidBottomInset: false, resizeToAvoidBottomInset: false,
); );

View file

@ -41,7 +41,7 @@ class ImageFetcher {
} }
// return map with: 'aperture' 'exposureTime' 'focalLength' 'iso' // return map with: 'aperture' 'exposureTime' 'focalLength' 'iso'
static Future<Map> getOverlayMetadata (String path) async { static Future<Map> getOverlayMetadata(String path) async {
try { try {
final result = await platform.invokeMethod('getOverlayMetadata', <String, dynamic>{ final result = await platform.invokeMethod('getOverlayMetadata', <String, dynamic>{
'path': path, 'path': path,
@ -52,4 +52,4 @@ class ImageFetcher {
} }
return Map(); return Map();
} }
} }

View file

@ -11,7 +11,7 @@ class Thumbnail extends StatefulWidget {
final double extent; final double extent;
final double devicePixelRatio; final double devicePixelRatio;
Thumbnail({ const Thumbnail({
Key key, Key key,
@required this.entry, @required this.entry,
@required this.extent, @required this.extent,

View file

@ -14,13 +14,12 @@ class ThumbnailCollection extends StatelessWidget {
final Map<DateTime, List<Map>> sections; final Map<DateTime, List<Map>> sections;
final ScrollController scrollController = ScrollController(); final ScrollController scrollController = ScrollController();
ThumbnailCollection(this.entries) : sections = groupBy(entries, ImageEntry.getDayTaken); ThumbnailCollection({Key key, this.entries})
: sections = groupBy(entries, ImageEntry.getDayTaken),
super(key: key);
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
var columnCount = 4;
var mediaQuery = MediaQuery.of(context);
return DraggableScrollbar.arrows( return DraggableScrollbar.arrows(
labelTextBuilder: (double offset) => Text( labelTextBuilder: (double offset) => Text(
"${offset ~/ 1}", "${offset ~/ 1}",
@ -34,34 +33,59 @@ class ThumbnailCollection extends StatelessWidget {
title: Text('Aves - All'), title: Text('Aves - All'),
floating: true, floating: true,
), ),
...sections.keys.map((sectionKey) => SliverStickyHeader( ...sections.keys.map((sectionKey) => SectionSliver(
header: DaySectionHeader(sectionKey), entries: entries,
sliver: SliverGrid( sections: sections,
delegate: SliverChildBuilderDelegate( sectionKey: sectionKey,
(context, index) { )),
var sectionEntries = sections[sectionKey];
if (index >= sectionEntries.length) return null;
var entry = sectionEntries[index];
return GestureDetector(
onTap: () => _showFullscreen(context, entry),
child: Thumbnail(
entry: entry,
extent: mediaQuery.size.width / columnCount,
devicePixelRatio: mediaQuery.devicePixelRatio,
),
);
},
childCount: sections[sectionKey].length,
),
gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
crossAxisCount: columnCount,
),
),
))
], ],
), ),
); );
} }
}
class SectionSliver extends StatelessWidget {
final List<Map> entries;
final Map<DateTime, List<Map>> sections;
final DateTime sectionKey;
const SectionSliver({
Key key,
this.entries,
this.sections,
this.sectionKey,
}) : super(key: key);
@override
Widget build(BuildContext context) {
var columnCount = 4;
var mediaQuery = MediaQuery.of(context);
return SliverStickyHeader(
header: DaySectionHeader(date: sectionKey),
sliver: SliverGrid(
delegate: SliverChildBuilderDelegate(
(context, index) {
var sectionEntries = sections[sectionKey];
if (index >= sectionEntries.length) return null;
var entry = sectionEntries[index];
return GestureDetector(
onTap: () => _showFullscreen(context, entry),
child: Thumbnail(
entry: entry,
extent: mediaQuery.size.width / columnCount,
devicePixelRatio: mediaQuery.devicePixelRatio,
),
);
},
childCount: sections[sectionKey].length,
),
gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
crossAxisCount: columnCount,
),
),
);
}
Future _showFullscreen(BuildContext context, Map entry) { Future _showFullscreen(BuildContext context, Map entry) {
return Navigator.push( return Navigator.push(
@ -79,6 +103,10 @@ class ThumbnailCollection extends StatelessWidget {
class DaySectionHeader extends StatelessWidget { class DaySectionHeader extends StatelessWidget {
final String text; final String text;
DaySectionHeader({Key key, DateTime date})
: text = formatDate(date),
super(key: key);
static DateFormat md = DateFormat.MMMMd(); static DateFormat md = DateFormat.MMMMd();
static DateFormat ymd = DateFormat.yMMMMd(); static DateFormat ymd = DateFormat.yMMMMd();
@ -88,25 +116,23 @@ class DaySectionHeader extends StatelessWidget {
return ymd.format(date); return ymd.format(date);
} }
DaySectionHeader(DateTime date) : text = formatDate(date);
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
return SectionHeader(text); return SectionHeader(text: text);
} }
} }
class SectionHeader extends StatelessWidget { class SectionHeader extends StatelessWidget {
final String primaryText; final String text;
SectionHeader(this.primaryText); const SectionHeader({Key key, this.text}) : super(key: key);
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
return Container( return Container(
padding: EdgeInsets.all(16), padding: EdgeInsets.all(16),
child: OutlinedText( child: OutlinedText(
primaryText, text,
style: TextStyle( style: TextStyle(
color: Colors.grey[200], color: Colors.grey[200],
fontSize: 20, fontSize: 20,