255 lines
11 KiB
Java
255 lines
11 KiB
Java
package com.ckkj.water.utils;
|
||
|
||
import android.content.ContentResolver;
|
||
import android.content.ContentValues;
|
||
import android.content.Context;
|
||
import android.net.Uri;
|
||
import android.os.Build;
|
||
import android.os.Environment;
|
||
import android.provider.MediaStore;
|
||
import android.util.Log;
|
||
|
||
import com.ckkj.water.utils.show.ToastUtil;
|
||
|
||
import java.io.BufferedInputStream;
|
||
import java.io.File;
|
||
import java.io.FileOutputStream;
|
||
import java.io.IOException;
|
||
import java.io.InputStream;
|
||
import java.io.OutputStream;
|
||
import java.net.HttpURLConnection;
|
||
import java.net.URL;
|
||
|
||
import okhttp3.Call;
|
||
import okhttp3.Callback;
|
||
import okhttp3.OkHttpClient;
|
||
import okhttp3.Request;
|
||
import okhttp3.Response;
|
||
|
||
public class DownFileUtil {
|
||
private DownFileCallback mCallback;
|
||
|
||
public interface DownFileCallback{
|
||
void downSuccess(String msg);
|
||
}
|
||
public DownFileUtil(Context context,String fileUrl,DownFileCallback callback) {
|
||
new Thread(){
|
||
@Override
|
||
public void run() {
|
||
super.run();
|
||
String fileName = null;
|
||
try {
|
||
// 找到最后一个"/"的位置
|
||
int lastSlashIndex = fileUrl.lastIndexOf("/");
|
||
int firstQuestionIndex = -1;
|
||
fileName = "";
|
||
if(fileUrl.contains("?")){
|
||
firstQuestionIndex = fileUrl.indexOf("?");
|
||
fileName = fileUrl.substring(lastSlashIndex + 1,firstQuestionIndex);
|
||
}else{
|
||
// 截取最后一个"/"之后的内容
|
||
fileName = fileUrl.substring(lastSlashIndex + 1);
|
||
}
|
||
} catch (Exception e) {
|
||
}
|
||
// 检查 Android 版本
|
||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
|
||
// 1. 获取公共下载目录的 URI(适用于 Android 10 及以上)
|
||
Uri downloadUri = getDownloadDirectoryUri();
|
||
// 2. 获取 "ChaoYueCang" 文件夹的路径
|
||
Uri folderUri = getFolderUri(downloadUri, "ChaoYueCang");
|
||
if (folderUri == null) {
|
||
// 文件夹不存在,创建该文件夹
|
||
createFolderInDownloads(downloadUri, context,"ChaoYueCang");
|
||
}
|
||
// 1. 获取 MediaStore 的下载目录 URI
|
||
ContentResolver resolver = context.getContentResolver();
|
||
Uri collection = MediaStore.Downloads.getContentUri(MediaStore.VOLUME_EXTERNAL_PRIMARY);
|
||
|
||
// 2. 创建用于保存文件的 ContentValues
|
||
ContentValues values = new ContentValues();
|
||
values.put(MediaStore.MediaColumns.DISPLAY_NAME, fileName); // 文件名
|
||
values.put(MediaStore.MediaColumns.MIME_TYPE, getMimeType(fileName)); // 根据文件扩展名设置 MIME 类型
|
||
values.put(MediaStore.MediaColumns.RELATIVE_PATH, "Download/ChaoYueCang"); // 保存到 Downloads 目录
|
||
|
||
// 3. 使用 resolver 插入文件
|
||
Uri fileUri = resolver.insert(collection, values);
|
||
if (fileUri == null) {
|
||
Log.e("FileDownload", "Failed to create new file in Downloads directory.");
|
||
return;
|
||
}
|
||
|
||
File sourceFile = new File(Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS) + "/ChaoYueCang/"+ fileName);
|
||
String sourceFilePath = sourceFile.getAbsolutePath();
|
||
// 4. 打开输出流,将文件内容写入公共 Downloads 目录
|
||
try (InputStream inputStream = downloadFileFromUrl(fileUrl);
|
||
OutputStream outputStream = resolver.openOutputStream(fileUri)) {
|
||
|
||
if (outputStream == null) {
|
||
Log.e("FileDownload", "Failed to open output stream for file.");
|
||
return;
|
||
}
|
||
|
||
byte[] buffer = new byte[8192]; // 缓冲区
|
||
int bytesRead;
|
||
while ((bytesRead = inputStream.read(buffer)) != -1) {
|
||
outputStream.write(buffer, 0, bytesRead);
|
||
}
|
||
outputStream.close();
|
||
inputStream.close();
|
||
callback.downSuccess("成功下载至Download文件目录中");
|
||
} catch (IOException e) {
|
||
Log.e("FileDownload", "Error writing to file", e);
|
||
}
|
||
} else {
|
||
// 1. 获取公共下载目录路径
|
||
File downloadsDirectory = new File(Environment.getExternalStorageDirectory(), "Download/ChaoYueCang");
|
||
if (!downloadsDirectory.exists()) {
|
||
downloadsDirectory.mkdirs(); // 如果目录不存在,创建目录
|
||
}
|
||
// 2. 创建目标文件路径
|
||
File targetFile = new File(downloadsDirectory, fileName);
|
||
|
||
// 3. 下载文件并保存到公共下载目录
|
||
try (InputStream inputStream = downloadFileFromUrl(fileUrl);
|
||
OutputStream outputStream = new FileOutputStream(targetFile)) {
|
||
byte[] buffer = new byte[4096]; // 缓冲区
|
||
int bytesRead;
|
||
while ((bytesRead = inputStream.read(buffer)) != -1) {
|
||
outputStream.write(buffer, 0, bytesRead);
|
||
}
|
||
outputStream.close();
|
||
inputStream.close();
|
||
callback.downSuccess("成功下载至Download文件目录中");
|
||
} catch (IOException e) {
|
||
Log.e("FileDownload", "Error downloading file", e);
|
||
}
|
||
}
|
||
}
|
||
}.start();
|
||
|
||
}
|
||
|
||
// 获取文件的 MIME 类型
|
||
private String getMimeType(String fileName) {
|
||
if (fileName.endsWith(".xlsx")) {
|
||
return "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet";
|
||
} else if (fileName.endsWith(".xls")) {
|
||
return "application/vnd.ms-excel";
|
||
}else if (fileName.endsWith(".doc")) {
|
||
return "application/msword";
|
||
}else if (fileName.endsWith(".pdf")) {
|
||
return "application/pdf";
|
||
}else if (fileName.endsWith(".png")) {
|
||
return "image/png";
|
||
}else if (fileName.endsWith(".jpg")) {
|
||
return "image/jpeg";
|
||
}else if (fileName.endsWith(".jpeg")) {
|
||
return "image/jpeg";
|
||
}
|
||
return "application/octet-stream"; // 默认 MIME 类型
|
||
}
|
||
|
||
|
||
// 从 URL 下载文件并返回输入流
|
||
private InputStream downloadFileFromUrl(String fileUrl) throws IOException {
|
||
URL url = new URL(fileUrl);
|
||
HttpURLConnection connection = (HttpURLConnection) url.openConnection();
|
||
connection.setRequestMethod("GET");
|
||
connection.setConnectTimeout(10000); // 设置连接超时
|
||
connection.setReadTimeout(10000); // 设置读取超时
|
||
connection.connect();
|
||
return new BufferedInputStream(connection.getInputStream());
|
||
}
|
||
|
||
|
||
// 获取公共存储的 Downloads 目录 URI(适配 Android 10 及以上)
|
||
private Uri getDownloadDirectoryUri() {
|
||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
|
||
return MediaStore.Downloads.getContentUri(MediaStore.VOLUME_EXTERNAL_PRIMARY);
|
||
} else {
|
||
return Uri.parse("file://" + Environment.getExternalStorageDirectory() + "/Download");
|
||
}
|
||
}
|
||
|
||
// 获取指定文件夹的 URI
|
||
private Uri getFolderUri(Uri baseUri, String folderName) {
|
||
Uri folderUri = baseUri.buildUpon().appendPath(folderName).build();
|
||
File folder = new File(folderUri.getPath());
|
||
if (folder.exists()) {
|
||
return folderUri;
|
||
} else {
|
||
return null;
|
||
}
|
||
}
|
||
|
||
// 在 Downloads 目录中创建一个新文件夹
|
||
private void createFolderInDownloads(Uri baseUri, Context context, String folderName) {
|
||
try {
|
||
ContentValues values = new ContentValues();
|
||
values.put(MediaStore.MediaColumns.DISPLAY_NAME, folderName);
|
||
values.put(MediaStore.MediaColumns.RELATIVE_PATH, "Download/" + folderName);
|
||
ContentResolver resolver = context.getContentResolver();
|
||
Uri folderUri = resolver.insert(baseUri, values);
|
||
if (folderUri == null) {
|
||
} else {
|
||
}
|
||
} catch (Exception e) {
|
||
}
|
||
}
|
||
|
||
|
||
public static void downloadImage(Context context, String imageUrl) {
|
||
OkHttpClient client = new OkHttpClient();
|
||
|
||
Request request = new Request.Builder()
|
||
.url(imageUrl)
|
||
.build();
|
||
|
||
client.newCall(request).enqueue(new Callback() {
|
||
@Override
|
||
public void onFailure(Call call, IOException e) {
|
||
e.printStackTrace();
|
||
// 失败处理
|
||
}
|
||
|
||
@Override
|
||
public void onResponse(Call call, Response response) throws IOException {
|
||
if (!response.isSuccessful()) {
|
||
// 下载失败处理
|
||
return;
|
||
}
|
||
|
||
byte[] imageData = response.body().bytes();
|
||
|
||
// 获取图片文件名
|
||
String fileName = "IMG_" + System.currentTimeMillis() + ".jpg";
|
||
|
||
// 保存到 MediaStore
|
||
ContentValues values = new ContentValues();
|
||
values.put(MediaStore.Images.Media.DISPLAY_NAME, fileName);
|
||
values.put(MediaStore.Images.Media.MIME_TYPE, "image/jpeg");
|
||
values.put(MediaStore.Images.Media.RELATIVE_PATH, Environment.DIRECTORY_PICTURES + "/DingDingCar"); // 自定义子目录
|
||
values.put(MediaStore.Images.Media.IS_PENDING, 1);
|
||
|
||
ContentResolver resolver = context.getContentResolver();
|
||
Uri collection = MediaStore.Images.Media.getContentUri(MediaStore.VOLUME_EXTERNAL_PRIMARY);
|
||
Uri item = resolver.insert(collection, values);
|
||
|
||
if (item != null) {
|
||
try (OutputStream out = resolver.openOutputStream(item)) {
|
||
out.write(imageData);
|
||
}
|
||
|
||
// 更新状态为可见
|
||
values.clear();
|
||
values.put(MediaStore.Images.Media.IS_PENDING, 0);
|
||
resolver.update(item, values, null, null);
|
||
ToastUtil.showShort(context,"图片已下载至手机");
|
||
}
|
||
}
|
||
});
|
||
}
|
||
|
||
}
|