lucky1213 4 years ago
parent
commit
015f433e38

+ 1
- 1
example/ios/Flutter/.last_build_id View File

1
-894f424b8531a69bd75214bc0c525b8a
1
+627ffd90bffd0082b3a38187f39f4b86

+ 4
- 4
example/lib/main.dart View File

171
     /// context is required, other params is optional.
171
     /// context is required, other params is optional.
172
     /// context is required, other params is optional.
172
     /// context is required, other params is optional.
173
     /// context is required, other params is optional.
173
     /// context is required, other params is optional.
174
-    List<AssetPathEntity> pathList2 = await PhotoManager.getAssetPathList(
175
-        hasAll: true, type: RequestType.image,);
174
+    // List<AssetPathEntity> pathList2 = await PhotoManager.getAssetPathList(
175
+    //     hasAll: true, type: RequestType.image,);
176
         if (!single) {
176
         if (!single) {
177
           PickedEntity entity = await PhotoPicker.pickAsset(
177
           PickedEntity entity = await PhotoPicker.pickAsset(
178
       context: context,
178
       context: context,
184
       thumbSize: 150,
184
       thumbSize: 150,
185
       sortDelegate: SortDelegate.common,
185
       sortDelegate: SortDelegate.common,
186
       pickType: type,
186
       pickType: type,
187
-      photoPathList: pathList2,
187
+      //photoPathList: pathList2,
188
     );
188
     );
189
 
189
 
190
     if (entity == null || entity.asset.isEmpty) {
190
     if (entity == null || entity.asset.isEmpty) {
213
             thumbSize: 150,
213
             thumbSize: 150,
214
             sortDelegate: SortDelegate.common,
214
             sortDelegate: SortDelegate.common,
215
             pickType: type,
215
             pickType: type,
216
-            photoPathList: pathList2,
216
+            // photoPathList: pathList2,
217
           );
217
           );
218
           print(asset);
218
           print(asset);
219
         }
219
         }

BIN
lib/fonts/iconfont.ttf View File


+ 48
- 41
lib/photo.dart View File

1
 library photo;
1
 library photo;
2
 
2
 
3
 import 'dart:async';
3
 import 'dart:async';
4
-import 'dart:io';
5
 
4
 
6
 import 'package:flutter/material.dart';
5
 import 'package:flutter/material.dart';
7
 import 'package:image_picker/image_picker.dart';
6
 import 'package:image_picker/image_picker.dart';
8
 import 'package:photo/src/entity/_theme.dart';
7
 import 'package:photo/src/entity/_theme.dart';
8
+import 'package:photo/src/permission_utils.dart';
9
 import 'package:photo/src/ui/page/photo_list_page.dart';
9
 import 'package:photo/src/ui/page/photo_list_page.dart';
10
 import 'package:photo/src/ui/page/photo_main_page.dart';
10
 import 'package:photo/src/ui/page/photo_main_page.dart';
11
 
11
 
17
 import 'package:photo/src/delegate/sort_delegate.dart';
17
 import 'package:photo/src/delegate/sort_delegate.dart';
18
 import 'package:photo/src/entity/options.dart';
18
 import 'package:photo/src/entity/options.dart';
19
 import 'package:photo/src/provider/i18n_provider.dart';
19
 import 'package:photo/src/provider/i18n_provider.dart';
20
-import 'package:photo/src/ui/dialog/not_permission_dialog.dart';
21
 import 'package:provider/provider.dart';
20
 import 'package:provider/provider.dart';
22
 
21
 
23
 import 'src/provider/config_provider.dart';
22
 import 'src/provider/config_provider.dart';
29
 export 'package:photo/src/entity/options.dart' show PickType, PickedEntity;
28
 export 'package:photo/src/entity/options.dart' show PickType, PickedEntity;
30
 export 'package:photo/src/delegate/badge_delegate.dart';
29
 export 'package:photo/src/delegate/badge_delegate.dart';
31
 export 'package:photo/src/entity/_theme.dart';
30
 export 'package:photo/src/entity/_theme.dart';
32
-export 'package:image_picker/image_picker.dart' show CameraDevice;
33
-export 'package:photo_manager/photo_manager.dart' show AssetEntity;
31
+export 'package:image_picker/image_picker.dart' show CameraDevice, PickedFile;
32
+export 'package:photo_manager/photo_manager.dart' show AssetEntity, AssetType;
34
 
33
 
35
 class PhotoPicker {
34
 class PhotoPicker {
36
   static PhotoPicker _instance;
35
   static PhotoPicker _instance;
61
     @required BuildContext context,
60
     @required BuildContext context,
62
     int rowCount = 4,
61
     int rowCount = 4,
63
     int maxSelected = 9,
62
     int maxSelected = 9,
64
-    double padding = 1,
63
+    double padding = 0.5,
65
     double itemRadio = 1.0,
64
     double itemRadio = 1.0,
66
     int thumbSize = 180,
65
     int thumbSize = 180,
67
     PhotoTheme theme,
66
     PhotoTheme theme,
91
       sortDelegate: sortDelegate,
90
       sortDelegate: sortDelegate,
92
       checkBoxBuilderDelegate: DefaultCheckBoxBuilderDelegate(),
91
       checkBoxBuilderDelegate: DefaultCheckBoxBuilderDelegate(),
93
       loadingDelegate: loadingDelegate,
92
       loadingDelegate: loadingDelegate,
94
-      badgeDelegate: DefaultBadgeDelegate(),
93
+      badgeDelegate: DurationBadgeDelegate(),
95
       pickType: pickType,
94
       pickType: pickType,
96
     );
95
     );
97
 
96
 
104
     );
103
     );
105
   }
104
   }
106
 
105
 
107
-
108
   static Future<AssetEntity> pickSingleAsset({
106
   static Future<AssetEntity> pickSingleAsset({
109
     @required BuildContext context,
107
     @required BuildContext context,
110
     int rowCount = 4,
108
     int rowCount = 4,
111
-    double padding = 1,
109
+    double padding = 0.5,
112
     double itemRadio = 1.0,
110
     double itemRadio = 1.0,
113
     int thumbSize = 180,
111
     int thumbSize = 180,
114
     PhotoTheme theme,
112
     PhotoTheme theme,
139
     return null;
137
     return null;
140
   }
138
   }
141
 
139
 
142
-  static Future<File> pickCamera({
140
+  static Future<PickedFile> pickCamera({
143
     double maxWidth,
141
     double maxWidth,
144
     double maxHeight,
142
     double maxHeight,
145
     int imageQuality,
143
     int imageQuality,
146
     CameraDevice preferredCameraDevice = CameraDevice.rear,
144
     CameraDevice preferredCameraDevice = CameraDevice.rear,
147
   }) async {
145
   }) async {
148
-    return ImagePicker.pickImage(
149
-      source: ImageSource.camera,
150
-      maxWidth: maxWidth,
151
-      maxHeight: maxHeight,
152
-      imageQuality: imageQuality,
153
-      preferredCameraDevice: preferredCameraDevice,
154
-    );
146
+    final bool status = await PermissionUtils.canPermission(Permission.camera);
147
+    if (!status) {
148
+      throw 'permission denied';
149
+    } else {
150
+      return ImagePicker().getImage(
151
+        source: ImageSource.camera,
152
+        maxWidth: maxWidth,
153
+        maxHeight: maxHeight,
154
+        imageQuality: imageQuality,
155
+        preferredCameraDevice: preferredCameraDevice,
156
+      );
157
+    }
155
   }
158
   }
156
 
159
 
157
   Future<PickedEntity> _pickAsset(
160
   Future<PickedEntity> _pickAsset(
161
     List<AssetPathEntity> photoList,
164
     List<AssetPathEntity> photoList,
162
     List<AssetEntity> pickedAssetList,
165
     List<AssetEntity> pickedAssetList,
163
   ) async {
166
   ) async {
164
-    await requestPermission(context, provider: provider);
165
-
166
-    return _openGalleryContentPage(
167
-      context,
168
-      options,
169
-      provider,
170
-      photoList,
171
-      pickedAssetList,
172
-    );
167
+    final bool status = await PermissionUtils.canMultiplePermission([Permission.photos, Permission.storage]);
168
+    if (!status) {
169
+      throw 'permission denied';
170
+    } else {
171
+      return _openGalleryContentPage(
172
+        context,
173
+        options,
174
+        provider,
175
+        photoList,
176
+        pickedAssetList,
177
+      );
178
+    }
173
   }
179
   }
174
 
180
 
175
   static Widget buildGallery({
181
   static Widget buildGallery({
201
       sortDelegate: sortDelegate,
207
       sortDelegate: sortDelegate,
202
       checkBoxBuilderDelegate: DefaultCheckBoxBuilderDelegate(),
208
       checkBoxBuilderDelegate: DefaultCheckBoxBuilderDelegate(),
203
       loadingDelegate: loadingDelegate,
209
       loadingDelegate: loadingDelegate,
204
-      badgeDelegate: DefaultBadgeDelegate(),
210
+      badgeDelegate: DurationBadgeDelegate(),
205
       pickType: pickType,
211
       pickType: pickType,
206
     );
212
     );
207
     assert(provider != null, "provider must be not null");
213
     assert(provider != null, "provider must be not null");
222
     );
228
     );
223
   }
229
   }
224
 
230
 
225
-  Future<void> requestPermission(BuildContext context,
226
-      {@required I18nProvider provider}) async {
227
-    var requestPermission = await PhotoManager.requestPermission();
228
-    if (requestPermission != true) {
229
-      var result = await showDialog(
230
-        context: context,
231
-        builder: (ctx) => NotPermissionDialog(
232
-          provider.getNotPermissionText(),
233
-        ),
234
-      );
235
-      if (result == true) {
236
-        PhotoManager.openSetting();
237
-      }
238
-      return null;
239
-    }
231
+  Future<bool> requestPermission({@required I18nProvider provider, @required List<Permission> permissions}) async {
232
+    final bool status =
233
+        await PermissionUtils.canMultiplePermission(permissions);
234
+    // if (!status) {
235
+    //   var result = await showDialog(
236
+    //     context: context,
237
+    //     builder: (ctx) => NotPermissionDialog(
238
+    //       provider.getNotPermissionText(),
239
+    //     ),
240
+    //   );
241
+    //   if (result == true) {
242
+    //     PhotoManager.openSetting();
243
+    //   }
244
+    //   return false;
245
+    // }
246
+    return status;
240
   }
247
   }
241
 
248
 
242
   Future<PickedEntity> _openGalleryContentPage(
249
   Future<PickedEntity> _openGalleryContentPage(

+ 20
- 14
lib/src/delegate/badge_delegate.dart View File

1
 import 'package:flutter/material.dart';
1
 import 'package:flutter/material.dart';
2
+import 'package:photo/src/engine/iconfont.dart';
2
 import 'package:photo_manager/photo_manager.dart';
3
 import 'package:photo_manager/photo_manager.dart';
3
 
4
 
4
 abstract class BadgeDelegate {
5
 abstract class BadgeDelegate {
51
   Widget buildBadge(BuildContext context, AssetType type, Duration duration) {
52
   Widget buildBadge(BuildContext context, AssetType type, Duration duration) {
52
     if (type == AssetType.video) {
53
     if (type == AssetType.video) {
53
       var s = duration.inSeconds % 60;
54
       var s = duration.inSeconds % 60;
54
-      var m = duration.inMinutes % 60;
55
-      var h = duration.inHours;
55
+      var m = duration.inMinutes;
56
 
56
 
57
-      String text =
58
-          "$h:${m.toString().padLeft(2, '0')}:${s.toString().padLeft(2, '0')}";
57
+      String text = "${m.toString().padLeft(2, '0')}:${s.toString().padLeft(2, '0')}";
59
 
58
 
60
       return Padding(
59
       return Padding(
61
-        padding: const EdgeInsets.all(2.0),
60
+        padding: const EdgeInsets.all(4.0),
62
         child: Align(
61
         child: Align(
63
           alignment: alignment,
62
           alignment: alignment,
64
           child: Container(
63
           child: Container(
65
-            decoration: BoxDecoration(
66
-              color: Theme.of(context).primaryColor.withOpacity(0.65),
64
+            child: Row(
65
+              children: [
66
+                Icon(MutliImagePickerFont.video, size: 20, color: Colors.white,),
67
+                Padding(
68
+                  padding: EdgeInsets.only(left: 6.0),
69
+                  child: Text(
70
+                    text,
71
+                    style: const TextStyle(
72
+                      fontSize: 14.0,
73
+                      color: Colors.white,
74
+                    ),
75
+                  ),
76
+                ),
77
+              ],
67
             ),
78
             ),
68
-            child: Text(
69
-              text,
70
-              style: const TextStyle(
71
-                fontSize: 12.0,
72
-                color: Colors.white,
73
-              ),
79
+            padding: EdgeInsets.symmetric(
80
+              horizontal: 2,
74
             ),
81
             ),
75
-            padding: const EdgeInsets.all(4.0),
76
           ),
82
           ),
77
         ),
83
         ),
78
       );
84
       );

+ 10
- 0
lib/src/engine/iconfont.dart View File

1
+
2
+import 'package:flutter/material.dart';
3
+
4
+class MutliImagePickerFont {
5
+  MutliImagePickerFont._();
6
+  static const String _family = 'PhotoFont';
7
+  static const String _fontPackage = 'photo';
8
+
9
+  static const IconData video = IconData(0xe6bd, fontFamily: _family, fontPackage: _fontPackage);
10
+}

+ 38
- 0
lib/src/permission_utils.dart View File

1
+import 'dart:io';
2
+
3
+import 'package:permission_handler/permission_handler.dart';
4
+
5
+export 'package:permission_handler/permission_handler.dart';
6
+
7
+class PermissionUtils {
8
+  static Future<bool> canPermission(Permission permission, [bool request = true]) async {
9
+    if (permission == Permission.storage && Platform.isIOS) {
10
+      return true;
11
+    }
12
+    if (permission == Permission.photos && Platform.isAndroid) {
13
+      return true;
14
+    }
15
+    if (!await permission.status.isGranted) {
16
+      if (request) {
17
+        final PermissionStatus status =  await permission.request();
18
+        if (status.isDenied) {
19
+          openAppSettings();
20
+        }
21
+        return status.isGranted;
22
+      }
23
+      return false;
24
+    } else {
25
+      return true;
26
+    }
27
+  }
28
+
29
+  static Future<bool> canMultiplePermission(List<Permission> list, [bool request = true]) async {
30
+    for (final Permission permission in list) {
31
+      if (!await canPermission(permission, request)) {
32
+        return false;
33
+      }
34
+    }
35
+
36
+    return true;
37
+  }
38
+}

+ 14
- 0
pubspec.lock View File

123
       url: "https://pub.flutter-io.cn"
123
       url: "https://pub.flutter-io.cn"
124
     source: hosted
124
     source: hosted
125
     version: "1.9.0"
125
     version: "1.9.0"
126
+  permission_handler:
127
+    dependency: "direct main"
128
+    description:
129
+      name: permission_handler
130
+      url: "https://pub.flutter-io.cn"
131
+    source: hosted
132
+    version: "5.0.1+1"
133
+  permission_handler_platform_interface:
134
+    dependency: transitive
135
+    description:
136
+      name: permission_handler_platform_interface
137
+      url: "https://pub.flutter-io.cn"
138
+    source: hosted
139
+    version: "2.0.1"
126
   photo_manager:
140
   photo_manager:
127
     dependency: "direct main"
141
     dependency: "direct main"
128
     description:
142
     description:

+ 7
- 1
pubspec.yaml View File

1
 name: photo
1
 name: photo
2
 description: image picker, multi picker support video/icloud asset, use flutter as ui, if you want to build custom ui, you just use photo_manager.
2
 description: image picker, multi picker support video/icloud asset, use flutter as ui, if you want to build custom ui, you just use photo_manager.
3
-version: 0.5.2
3
+version: 0.5.3
4
 author: caijinglong<cjl_spy@163.com>
4
 author: caijinglong<cjl_spy@163.com>
5
 homepage: https://github.com/CaiJingLong/flutter_photo
5
 homepage: https://github.com/CaiJingLong/flutter_photo
6
 
6
 
14
   photo_manager: 0.5.1
14
   photo_manager: 0.5.1
15
   provider: ^4.0.5
15
   provider: ^4.0.5
16
   image_picker: ^0.6.5
16
   image_picker: ^0.6.5
17
+  permission_handler: ^5.0.0+hotfix.8
17
 
18
 
18
 dev_dependencies:
19
 dev_dependencies:
19
   flutter_test:
20
   flutter_test:
24
 
25
 
25
 # The following section is specific to Flutter.
26
 # The following section is specific to Flutter.
26
 flutter:
27
 flutter:
28
+  uses-material-design: true
29
+  fonts:
30
+    - family: PhotoFont
31
+      fonts:
32
+        - asset: lib/fonts/iconfont.ttf
27
   # To add assets to your package, add an assets section, like this:
33
   # To add assets to your package, add an assets section, like this:
28
   # assets:
34
   # assets:
29
   #  - images/a_dot_burr.jpeg
35
   #  - images/a_dot_burr.jpeg