路径提供者颤振下载文件
path provider flutter download file
我想在我的应用程序中下载文件,我使用了 Dio
、path_provider
、permission_handler
所以我应该在 android 清单中为 android 和 ios.[= 写一些信息21=]
我做到了。
但它没有用,当我点击下载按钮时出现了这个错误:
I/flutter (11919): Directory: '/storage/emulated/0/Android/data/com.example.podkadeh/files'
I/flutter (11919): FileSystemException: Cannot open file, path = '/storage/emulated/0/podkadeh/Image/image.jpg' (OS Error: Permission denied, errno = 13)
I/flutter (11919): Problem Downloading File
这个OS Error: Permission denied, errno = 13
我在清单中写了这行:
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.WAKE_LOCK"/>
<uses-permission android:name="android.permission.FOREGROUND_SERVICE"/>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.ACCESS_MEDIA_LOCATION"/>
<uses-permission android:name="android.permission.READ_INTERNAL_STORAGE" />
<uses-permission android:name="android.permission.MANAGE_EXTERNAL_STORAGE"
tools:ignore="ScopedStorage"/>
<uses-permission android:name="android.permission"
并在申请中写下:
android:requestLegacyExternalStorage="true"
但是,它仍然运行不佳,我无法下载它
这是我的下载文件代码:
class DownloadImage extends StatefulWidget {
const DownloadImage (
{Key? key,})
: super(key: key);
@override
_DownloadImage State createState() => _DownloadImage State();
}
class _DownloadImageState extends State<DownloadImage > {
Future<bool> saveImageUrl(String url, String fileName) async {
Directory? directory;
try {
if (Platform.isAndroid) {
if (await _requestPermission(Permission.storage)) {
directory = await getExternalStorageDirectory();
String newPath = "";
print(directory);
List<String> paths = directory!.path.split("/");
for (int x = 1; x < paths.length; x++) {
String folder = paths[x];
if (folder != "Android") {
newPath += "/" + folder;
} else {
break;
}
}
newPath = newPath + "/podkadeh" + "/Image";
directory = Directory(newPath);
} else {
return false;
}
} else {
if (await _requestPermission(Permission.photos)) {
directory = await getTemporaryDirectory();
} else {
return false;
}
}
File saveFile = File(directory.path + "/$fileName");
if (!await directory.exists()) {
await directory.create(recursive: true);
}
if (await directory.exists()) {
await dio.download(url, saveFile.path,
onReceiveProgress: (value1, value2) {
setState(() {
progress = value1 / value2;
});
});
if (Platform.isIOS) {
await ImageGallerySaver.saveFile(saveFile.path,
isReturnPathOfIOS: true);
}
return true;
}
return false;
} catch (e) {
print(e);
return false;
}
}
Future<bool> _requestPermission(Permission permission) async {
if (await permission.isGranted) {
return true;
} else {
var result = await permission.request();
if (result == PermissionStatus.granted) {
return true;
}
}
return false;
}
downloadFile() async {
setState(() {
loading = true;
progress = 0;
});
bool downloadedImage = await saveImageUrl(
"https://test.podkadeh.ir/image-cache/Ep-61c9c0152ab37f246dd35a65-500.jpg",
"image.jpg");
if (downloadedImage) {
print("File Downloaded");
} else {
print("Problem Downloading File");
}
setState(() {
loading = false;
});
}
@override
Widget build(BuildContext context) {
return (progress != 0 && progress != 100)
? CircularProgressIndicator(
backgroundColor: loading ? Colors.amber : Colors.black,
valueColor:
AlwaysStoppedAnimation(loading ? Colors.blue : Colors.pink),
strokeWidth: progress,
value: progress,
)
: IconButton(
icon: SvgPicture.asset(MyIcons.frame, color: MyColors.black,height: 20,width: 20,),
onPressed: downloadFile,
padding: const EdgeInsets.all(10),
);
}
}
顺便说一句,我使用 compileSdkVersion 31
,我在 gradle.properties
中使用它:
android.useAndroidX=true
android.enableJetifier=true
我用以下方法解决了这个问题:
为了支持 Android.
的所有版本,我添加了两个权限请求 Permission.accessMediaLocation , Permission.manageExternalStorage
而不是仅仅请求 Permission.storage
try {
if (Platform.isAndroid) {
if (await _requestPermission(Permission.storage) &&
await _requestPermission(Permission.accessMediaLocation) &&
await _requestPermission(Permission.manageExternalStorage)) {
directory = await getExternalStorageDirectory();
String newPath = "";
print(directory);
.......
结果是:
Performing hot restart...
Syncing files to device Android SDK built for x86...
Restarted application in 2,177ms.
I/flutter ( 3712): Directory: '/storage/emulated/0/Android/data/com.example.untitled/files'
I/flutter ( 3712): File Downloaded
我想在我的应用程序中下载文件,我使用了 Dio
、path_provider
、permission_handler
所以我应该在 android 清单中为 android 和 ios.[= 写一些信息21=]
我做到了。 但它没有用,当我点击下载按钮时出现了这个错误:
I/flutter (11919): Directory: '/storage/emulated/0/Android/data/com.example.podkadeh/files'
I/flutter (11919): FileSystemException: Cannot open file, path = '/storage/emulated/0/podkadeh/Image/image.jpg' (OS Error: Permission denied, errno = 13)
I/flutter (11919): Problem Downloading File
这个OS Error: Permission denied, errno = 13
我在清单中写了这行:
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.WAKE_LOCK"/>
<uses-permission android:name="android.permission.FOREGROUND_SERVICE"/>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.ACCESS_MEDIA_LOCATION"/>
<uses-permission android:name="android.permission.READ_INTERNAL_STORAGE" />
<uses-permission android:name="android.permission.MANAGE_EXTERNAL_STORAGE"
tools:ignore="ScopedStorage"/>
<uses-permission android:name="android.permission"
并在申请中写下:
android:requestLegacyExternalStorage="true"
但是,它仍然运行不佳,我无法下载它
这是我的下载文件代码:
class DownloadImage extends StatefulWidget {
const DownloadImage (
{Key? key,})
: super(key: key);
@override
_DownloadImage State createState() => _DownloadImage State();
}
class _DownloadImageState extends State<DownloadImage > {
Future<bool> saveImageUrl(String url, String fileName) async {
Directory? directory;
try {
if (Platform.isAndroid) {
if (await _requestPermission(Permission.storage)) {
directory = await getExternalStorageDirectory();
String newPath = "";
print(directory);
List<String> paths = directory!.path.split("/");
for (int x = 1; x < paths.length; x++) {
String folder = paths[x];
if (folder != "Android") {
newPath += "/" + folder;
} else {
break;
}
}
newPath = newPath + "/podkadeh" + "/Image";
directory = Directory(newPath);
} else {
return false;
}
} else {
if (await _requestPermission(Permission.photos)) {
directory = await getTemporaryDirectory();
} else {
return false;
}
}
File saveFile = File(directory.path + "/$fileName");
if (!await directory.exists()) {
await directory.create(recursive: true);
}
if (await directory.exists()) {
await dio.download(url, saveFile.path,
onReceiveProgress: (value1, value2) {
setState(() {
progress = value1 / value2;
});
});
if (Platform.isIOS) {
await ImageGallerySaver.saveFile(saveFile.path,
isReturnPathOfIOS: true);
}
return true;
}
return false;
} catch (e) {
print(e);
return false;
}
}
Future<bool> _requestPermission(Permission permission) async {
if (await permission.isGranted) {
return true;
} else {
var result = await permission.request();
if (result == PermissionStatus.granted) {
return true;
}
}
return false;
}
downloadFile() async {
setState(() {
loading = true;
progress = 0;
});
bool downloadedImage = await saveImageUrl(
"https://test.podkadeh.ir/image-cache/Ep-61c9c0152ab37f246dd35a65-500.jpg",
"image.jpg");
if (downloadedImage) {
print("File Downloaded");
} else {
print("Problem Downloading File");
}
setState(() {
loading = false;
});
}
@override
Widget build(BuildContext context) {
return (progress != 0 && progress != 100)
? CircularProgressIndicator(
backgroundColor: loading ? Colors.amber : Colors.black,
valueColor:
AlwaysStoppedAnimation(loading ? Colors.blue : Colors.pink),
strokeWidth: progress,
value: progress,
)
: IconButton(
icon: SvgPicture.asset(MyIcons.frame, color: MyColors.black,height: 20,width: 20,),
onPressed: downloadFile,
padding: const EdgeInsets.all(10),
);
}
}
顺便说一句,我使用 compileSdkVersion 31
,我在 gradle.properties
中使用它:
android.useAndroidX=true
android.enableJetifier=true
我用以下方法解决了这个问题: 为了支持 Android.
的所有版本,我添加了两个权限请求Permission.accessMediaLocation , Permission.manageExternalStorage
而不是仅仅请求 Permission.storage
try {
if (Platform.isAndroid) {
if (await _requestPermission(Permission.storage) &&
await _requestPermission(Permission.accessMediaLocation) &&
await _requestPermission(Permission.manageExternalStorage)) {
directory = await getExternalStorageDirectory();
String newPath = "";
print(directory);
.......
结果是:
Performing hot restart...
Syncing files to device Android SDK built for x86...
Restarted application in 2,177ms.
I/flutter ( 3712): Directory: '/storage/emulated/0/Android/data/com.example.untitled/files'
I/flutter ( 3712): File Downloaded