Как я могу делиться несколькими файлами через Intent?
Вот мой код, но это решение для одного файла.
Могу ли я поделиться несколькими файлами и загрузками, как я делаю для отдельных файлов ниже?
Button btn = (Button)findViewById(R.id.hello);
btn.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent(Intent.ACTION_SEND);
String path = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS) + "/pic.png";
File file = new File(path);
MimeTypeMap type = MimeTypeMap.getSingleton();
intent.setType(type.getMimeTypeFromExtension(MimeTypeMap.getFileExtensionFromUrl(path)));
intent.putExtra(Intent.EXTRA_STREAM, Uri.fromFile(file));
intent.putExtra(Intent.EXTRA_TEXT, "1111");
startActivity(intent);
}
});
Ответы
Ответ 1
Да, но вам нужно использовать Intent.ACTION_SEND_MULTIPLE
вместо Intent.ACTION_SEND
.
Intent intent = new Intent();
intent.setAction(Intent.ACTION_SEND_MULTIPLE);
intent.putExtra(Intent.EXTRA_SUBJECT, "Here are some files.");
intent.setType("image/jpeg"); /* This example is sharing jpeg images. */
ArrayList<Uri> files = new ArrayList<Uri>();
for(String path : filesToSend /* List of the files you want to send */) {
File file = new File(path);
Uri uri = Uri.fromFile(file);
files.add(uri);
}
intent.putParcelableArrayListExtra(Intent.EXTRA_STREAM, files);
startActivity(intent);
Это, безусловно, можно упростить, но я оставил несколько строк, чтобы вы могли разбить каждый необходимый шаг.
ОБНОВЛЕНИЕ: Начиная с API 24, совместное использование файлов URI вызовет исключение FileUriExposedException. Чтобы исправить это, вы можете либо переключить свой compileSdkVersion на 23 или ниже, либо использовать URI контента с FileProvider.
ОБНОВЛЕНИЕ (до обновления): Google недавно объявил, что новые приложения и обновления приложений потребуются для ориентации на одну из последних версий Android для выпуска в Play Store. Тем не менее, таргетинг API 23 или ниже больше не является допустимым вариантом, если вы планируете выпустить приложение в магазин. Вы должны идти по маршруту FileProvider.
Ответ 2
Вот небольшая улучшенная версия, импровизированная решением MCeley. Это можно использовать для отправки гетерогенного списка файлов (например, изображения, документа и видео в одно и то же время), например, при загрузке загруженных документов, изображений одновременно.
public static void shareMultiple(List<File> files, Context context){
ArrayList<Uri> uris = new ArrayList<>();
for(File file: files){
uris.add(Uri.fromFile(file));
}
final Intent intent = new Intent(Intent.ACTION_SEND_MULTIPLE);
intent.setType("*/*");
intent.putParcelableArrayListExtra(Intent.EXTRA_STREAM, uris);
context.startActivity(Intent.createChooser(intent, context.getString(R.string.ids_msg_share)));
}
Ответ 3
/*
manifest file outside the applicationTag write these permissions
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" /> */
File pictures = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES);
//Get a top-level public external storage directory for placing files of a particular type.
// This is where the user will typically place and manage their own files,
// so you should be careful about what you put here to ensure you don't
// erase their files or get in the way of their own organization...
// pulled from Standard directory in which to place pictures that are available to the user to the File object
String[] listOfPictures = pictures.list();
//Returns an array of strings with the file names in the directory represented by this file. The result is null if this file is not a directory.
Uri uri=null;
ArrayList<Uri> arrayList = new ArrayList<>();
if (listOfPictures!=null) {
for (String name : listOfPictures) {
uri = Uri.parse("file://" + pictures.toString() + "/" + name );
arrayList.add(uri);
}
Intent intent = new Intent();
intent.setAction(Intent.ACTION_SEND_MULTIPLE);
intent.putExtra(Intent.EXTRA_STREAM, arrayList);
//A content: URI holding a stream of data associated with the Intent, used with ACTION_SEND to supply the data being sent.
intent.setType("image/*"); //any kind of images can support.
chooser = Intent.createChooser(intent, "Send Multiple Images");//choosers title
startActivity(chooser);
}
Ответ 4
Если вы делитесь файлом с другими приложениями на устройствах с KitKat и выше, вам необходимо предоставить разрешения Uri.
Вот как я обрабатываю несколько файлов до и после публикации KitKat:
//All my paths will temporarily be retrieve into this ArrayList
ArrayList<PathModel> pathList;
//All Uri are stored in this ArrayList
ArrayList<Uri> uriArrayList = null;
//This is important since we are sending multiple files
Intent sharingIntent = new Intent(Intent.ACTION_SEND_MULTIPLE);
//Used temporarily to get Uri references
Uri shareFileUri;
if (android.os.Build.VERSION.SDK_INT < Build.VERSION_CODES.KITKAT) {
//My paths are store in SQLite, I retrieve them first
SQLiteHelper helper = new SQLiteHelper(this);
//Temporarily store file paths
pathList = helper.getAllAttachments(viewholderID);
helper.close();
//Create new instance of the ArrayList where the Uri will be stored
uriArrayList = new ArrayList<>();
//Get all paths from my PathModel ArrayList
for (PathModel data : pathList) {
//Create a new file for each path
File mFile = new File(data.getPath());
//No need to add Uri permissions for pre-KitKat
shareFileUri = Uri.fromFile(mFile);
//Add Uri to the Array that holds the Uri's
uriArrayList.add(shareFileUri);
}
} else {
//My paths are store in SQLite, I retrieve them first
SQLiteHelper helper = new SQLiteHelper(this);
//Temporarily store file paths
pathList = helper.getAllAttachments(viewholderID);
helper.close();
//Create new instance of the ArrayList where the Uri will be stored
uriArrayList = new ArrayList<>();
//Get all paths from my PathModer ArrayList
for (PathModel data : pathList) {
//Create a new file for each path
File mFile = new File(data.getPath());
//Now we need to grant Uri permissions (kitKat>)
shareFileUri = FileProvider.getUriForFile(getApplication(), getApplication().getPackageName() + ".provider", mFile);
//Add Uri to the Array that holds the Uri's
uriArrayList.add(shareFileUri);
}
//Grant read Uri permissions to the intent
sharingIntent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
}
//I know the files that will be sent will one of the following
sharingIntent.setType("application/pdf/*|image|video/*");
//pass the Array that holds the paths to the files
sharingIntent.putParcelableArrayListExtra(Intent.EXTRA_STREAM, uriArrayList);
//Start intent by creating a chooser
startActivity(Intent.createChooser(sharingIntent, "Share using"));
В моем случае пути были сохранены в SQLite
, но пути могут прийти откуда угодно.