не удается удалить файл из внешнего хранилища в android программно

Я пытаюсь удалить файл, расположенный в папке

/storage/714D-160A/Xender/image/Screenshot_commando.png

что я сделал до сих пор:

  try{
        String d_path = "/storage/714D-160A/Xender/image/Screenshot_commando.png";
        File file = new File(d_path);
        file.delete();

     }catch(Exception e){

        e.printStackTrace();
     }

и файл все еще на своем месте(не удален : ()

также я дал разрешение в файле манифеста.

<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.WRITE_INTERNAL_STORAGE" />
<uses-permission android:name="android.permission.STORAGE" />

4 ответов


используя ContentResolver удалить медиа-файлы неправильно и предоставляет много проблем для пользователя.
Вы не можете удалить файл sd-card просто удалив его информацию из ContentResolver на Android версии больше, чем Jelly Bean(4.3).
Он работает только на версиях Android до KitKat(4.4).
Вот почему команда Android предоставила DocumentProvider.

почему contentResolver.delete(...) - это плохо?
1. Заполняет sd-card
При попытке удалить файл мультимедиа на sd-card на ContentResolver по версии Android больше, чем 4.3, фактический медиа-файл останется нетронутым, потому что contentResolver.delete(...) подход удаляет только информацию (имя, дата, путь ...) средств массовой информации, и вы получите незарегистрированные медиа-файлы на вашем sd-card, который ContentResolver понятия не имеет об их существовании, и поэтому вы не могли видеть их в своей галерее, и вы думаете, что они были удалены с этим подойдите, пока они еще там, и заполните sd-card каждый раз, когда пользователь пытается удалить файл мультимедиа на sd-card.

2. Медиа файлы (изображения ,видео, GIF...) вернется в галерею
Есть много приложений, особенно галерея и файловый менеджер, которые найдут эти незарегистрированные медиа-файлы и добавят их в ContentResolverснова, так как их нормальное поведение, когда пользователь предполагает, что его/ее нежелательные медиа файлы исчезли. Конечно, нет. пользователь хочет, чтобы его / ее предполагая, удаленные изображения или видео появляются в середине демонстрации.

Итак, каков правильный подход к удалению медиафайлов на sd-card?
Ну, на это уже ответили здесь С использованием DocumentProvider.


public static boolean delete(final Context context, final File file) {
    final String where = MediaStore.MediaColumns.DATA + "=?";
    final String[] selectionArgs = new String[] {
            file.getAbsolutePath()
    };
    final ContentResolver contentResolver = context.getContentResolver();
    final Uri filesUri = MediaStore.Files.getContentUri("external");

    contentResolver.delete(filesUri, where, selectionArgs);

    if (file.exists()) {

        contentResolver.delete(filesUri, where, selectionArgs);
    }
    return !file.exists();
}

использовать Environment.getExternalStorageDirectory().getAbsolutePath() вместо жесткого кодирования путь хранения

String baseDir = Environment.getExternalStorageDirectory().getAbsolutePath();
File f = new File(baseDir + "/714D-160A/Xender/image/Screenshot_commando.png");
boolean d = f.delete();

начиная с Android 4.4, вы не можете писать в файлы SD-карт (за исключением каталога приложений), используя обычный способ. Вам придется использовать структуру доступа к хранилищу с помощью DocumentFile для этого.

следующий код работает для меня:

private void deletefile(Uri uri, String filename) {
    DocumentFile pickedDir = DocumentFile.fromTreeUri(this, uri);
    try {
        getContentResolver().takePersistableUriPermission(uri, Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION);
    } catch (SecurityException e) {
        e.printStackTrace();
    }

    DocumentFile file = pickedDir.findFile(filename);
    if(file.delete())
        Log.d("Log ID", "Delete successful");
    else
        Log.d("Log ID", "Delete unsuccessful");
}

здесь filename - это имя файла, который будет удален и uri возвращается ли URI ACTION_OPEN_DOCUMENT_TREE:

private void choosePath() {
    Intent intent = new Intent(Intent.ACTION_OPEN_DOCUMENT_TREE);
    intent.addCategory(Intent.CATEGORY_DEFAULT);
    startActivityForResult(intent, LOCATION_REQUEST);
}

@Override
public void onActivityResult(int requestCode, int resultCode, Intent resultData) {
    if (requestCode == LOCATION_REQUEST && resultCode == Activity.RESULT_OK) {
        Uri uri;
        if (resultData != null) {
            uri = resultData.getData();
            if (uri != null) {
                try {
                    getContentResolver().takePersistableUriPermission(uri, Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION);
                } catch (SecurityException e) {
                    e.printStackTrace();
                }

                /* Got the path uri */
            }
        }
    }
}