|  | 
|  | 1 | +import 'package:flutter/material.dart'; | 
|  | 2 | + | 
|  | 3 | +import 'package:photo_view/photo_view.dart'; | 
|  | 4 | +import 'package:photo_view/photo_view_gallery.dart'; | 
|  | 5 | +import 'package:cached_network_image/cached_network_image.dart'; | 
|  | 6 | +// -[flutter_page_indicator](https://github.com/best-flutter/flutter_page_indicator) | 
|  | 7 | +import 'package:flutter_page_indicator/flutter_page_indicator.dart'; | 
|  | 8 | + | 
|  | 9 | +import 'package:flutter_wechat/components/photo_browser/photo.dart'; | 
|  | 10 | + | 
|  | 11 | +class PhotoBrowser extends StatefulWidget { | 
|  | 12 | + PhotoBrowser({ | 
|  | 13 | + this.loadingBuilder, | 
|  | 14 | + this.backgroundDecoration, | 
|  | 15 | + this.minScale, | 
|  | 16 | + this.maxScale, | 
|  | 17 | + this.initialIndex, | 
|  | 18 | + @required this.photos, | 
|  | 19 | + this.scrollDirection = Axis.horizontal, | 
|  | 20 | + }) : pageController = PageController(initialPage: initialIndex); | 
|  | 21 | + | 
|  | 22 | + final LoadingBuilder loadingBuilder; | 
|  | 23 | + final Decoration backgroundDecoration; | 
|  | 24 | + final dynamic minScale; | 
|  | 25 | + final dynamic maxScale; | 
|  | 26 | + final int initialIndex; | 
|  | 27 | + final PageController pageController; | 
|  | 28 | + final List<Photo> photos; | 
|  | 29 | + final Axis scrollDirection; | 
|  | 30 | + | 
|  | 31 | + @override | 
|  | 32 | + State<StatefulWidget> createState() { | 
|  | 33 | + return _PhotoBrowserState(); | 
|  | 34 | + } | 
|  | 35 | +} | 
|  | 36 | + | 
|  | 37 | +class _PhotoBrowserState extends State<PhotoBrowser> { | 
|  | 38 | + int currentIndex; | 
|  | 39 | + | 
|  | 40 | + @override | 
|  | 41 | + void initState() { | 
|  | 42 | + currentIndex = widget.initialIndex; | 
|  | 43 | + super.initState(); | 
|  | 44 | + } | 
|  | 45 | + | 
|  | 46 | + void onPageChanged(int index) { | 
|  | 47 | + setState(() { | 
|  | 48 | + currentIndex = index; | 
|  | 49 | + }); | 
|  | 50 | + } | 
|  | 51 | + | 
|  | 52 | + @override | 
|  | 53 | + Widget build(BuildContext context) { | 
|  | 54 | + return Scaffold( | 
|  | 55 | + // 设置成黑色 | 
|  | 56 | + backgroundColor: Colors.black, | 
|  | 57 | + body: Container( | 
|  | 58 | + decoration: widget.backgroundDecoration, | 
|  | 59 | + constraints: BoxConstraints.expand( | 
|  | 60 | + height: MediaQuery.of(context).size.height, | 
|  | 61 | + ), | 
|  | 62 | + child: Stack( | 
|  | 63 | + alignment: Alignment.center, | 
|  | 64 | + children: <Widget>[ | 
|  | 65 | + PhotoViewGallery.builder( | 
|  | 66 | + scrollPhysics: const BouncingScrollPhysics(), | 
|  | 67 | + builder: _buildItem, | 
|  | 68 | + itemCount: widget.photos.length, | 
|  | 69 | + loadingBuilder: (context, progress) => Center( | 
|  | 70 | + child: Container( | 
|  | 71 | + width: 30.0, | 
|  | 72 | + height: 30.0, | 
|  | 73 | + child: CircularProgressIndicator( | 
|  | 74 | + backgroundColor: Colors.black45, | 
|  | 75 | + valueColor: new AlwaysStoppedAnimation<Color>(Colors.white), | 
|  | 76 | + value: progress == null | 
|  | 77 | + ? null | 
|  | 78 | + : progress.cumulativeBytesLoaded / | 
|  | 79 | + progress.expectedTotalBytes, | 
|  | 80 | + ), | 
|  | 81 | + ), | 
|  | 82 | + ), | 
|  | 83 | + backgroundDecoration: widget.backgroundDecoration, | 
|  | 84 | + pageController: widget.pageController, | 
|  | 85 | + onPageChanged: onPageChanged, | 
|  | 86 | + scrollDirection: widget.scrollDirection, | 
|  | 87 | + // gaplessPlayback: true, | 
|  | 88 | + // reverse: true, | 
|  | 89 | + ), | 
|  | 90 | + Positioned( | 
|  | 91 | + bottom: 20.0, | 
|  | 92 | + child: new PageIndicator( | 
|  | 93 | + layout: PageIndicatorLayout.SCALE, | 
|  | 94 | + size: 10.0, | 
|  | 95 | + controller: widget.pageController, | 
|  | 96 | + space: 5.0, | 
|  | 97 | + count: widget.photos.length, | 
|  | 98 | + ), | 
|  | 99 | + ) | 
|  | 100 | + ], | 
|  | 101 | + ), | 
|  | 102 | + ), | 
|  | 103 | + ); | 
|  | 104 | + } | 
|  | 105 | + | 
|  | 106 | + PhotoViewGalleryPageOptions _buildItem(BuildContext context, int index) { | 
|  | 107 | + final Photo item = widget.photos[index]; | 
|  | 108 | + // NetworkImage(item.url) | 
|  | 109 | + return PhotoViewGalleryPageOptions( | 
|  | 110 | + imageProvider: item.isLocal | 
|  | 111 | + ? AssetImage(item.url) | 
|  | 112 | + : CachedNetworkImageProvider(item.url), | 
|  | 113 | + initialScale: PhotoViewComputedScale.contained, | 
|  | 114 | + minScale: PhotoViewComputedScale.contained * (0.5 + index / 10), | 
|  | 115 | + maxScale: PhotoViewComputedScale.covered * 1.1, | 
|  | 116 | + heroAttributes: PhotoViewHeroAttributes(tag: item.tag), | 
|  | 117 | + onTapUp: (context, detail, value) { | 
|  | 118 | + Navigator.pop(context); | 
|  | 119 | + }, | 
|  | 120 | + ); | 
|  | 121 | + } | 
|  | 122 | +} | 
0 commit comments