You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Android Java实现:在挂载的外置SD卡创建TXT文件方法问询

在外置SD卡存储TXT文件的Android Java实现

1. 配置权限

首先在AndroidManifest.xml中声明必要的存储权限:

<!-- Android 9及以下版本需要 -->
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<!-- Android 10+ 如需访问外置SD卡任意位置,需添加此权限 -->
<uses-permission android:name="android.permission.MANAGE_EXTERNAL_STORAGE" />

2. 获取外置SD卡的有效路径

不能硬编码SD卡路径,需通过系统API识别可写的外置存储卷:

import android.content.Context;
import android.os.Build;
import android.os.Environment;
import android.os.storage.StorageManager;
import android.os.storage.StorageVolume;
import android.annotation.SuppressLint;
import java.lang.reflect.Method;
import java.util.List;

@SuppressLint("NewApi")
public static String getExternalSDCardPath(Context context) {
    StorageManager storageManager = (StorageManager) context.getSystemService(Context.STORAGE_SERVICE);
    List<StorageVolume> storageVolumes = storageManager.getStorageVolumes();
    
    for (StorageVolume volume : storageVolumes) {
        // 筛选非主存储(外置SD卡)且已挂载可写的卷
        if (!volume.isPrimary() && Environment.MEDIA_MOUNTED.equals(volume.getState())) {
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
                // Android 11+ 直接通过公开API获取路径
                if (volume.getDirectory() != null) {
                    return volume.getDirectory().getAbsolutePath();
                }
            } else {
                // Android 10及以下通过反射获取路径
                try {
                    Method getPathMethod = StorageVolume.class.getMethod("getPath");
                    return (String) getPathMethod.invoke(volume);
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        }
    }
    return null;
}

3. 写入TXT文件到外置SD卡

实现文件写入逻辑,包含权限校验和错误处理:

import android.Manifest;
import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.net.Uri;
import android.os.Build;
import android.os.Environment;
import android.provider.Settings;
import android.widget.Toast;
import androidx.appcompat.app.AppCompatActivity;
import androidx.core.app.ActivityCompat;
import androidx.core.content.ContextCompat;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import android.os.Bundle;

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        
        // 调用写入示例
        writeTxtToExternalSDCard(this, "test.txt", "这是外置SD卡中的测试文本内容");
    }

    public boolean writeTxtToExternalSDCard(Context context, String fileName, String content) {
        // 权限校验
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
            if (!Environment.isExternalStorageManager()) {
                // 跳转到系统权限设置页面申请全文件访问权限
                Intent intent = new Intent(Settings.ACTION_MANAGE_APP_ALL_FILES_ACCESS_PERMISSION);
                Uri uri = Uri.fromParts("package", context.getPackageName(), null);
                intent.setData(uri);
                startActivity(intent);
                return false;
            }
        } else {
            if (ContextCompat.checkSelfPermission(context, Manifest.permission.WRITE_EXTERNAL_STORAGE)
                    != PackageManager.PERMISSION_GRANTED) {
                // 动态申请写入权限
                ActivityCompat.requestPermissions(this,
                        new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE}, 1001);
                return false;
            }
        }

        // 获取外置SD卡路径
        String sdCardPath = getExternalSDCardPath(context);
        if (sdCardPath == null) {
            Toast.makeText(context, "未找到可写入的外置SD卡", Toast.LENGTH_SHORT).show();
            return false;
        }

        // 创建并写入文件
        File txtFile = new File(sdCardPath, fileName);
        try (FileWriter writer = new FileWriter(txtFile)) {
            writer.write(content);
            Toast.makeText(context, "文件写入成功", Toast.LENGTH_SHORT).show();
            return true;
        } catch (IOException e) {
            e.printStackTrace();
            Toast.makeText(context, "写入失败:" + e.getMessage(), Toast.LENGTH_SHORT).show();
            return false;
        }
    }

    // 处理Android 6-9的权限申请结果
    @Override
    public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
        super.onRequestPermissionsResult(requestCode, permissions, grantResults);
        if (requestCode == 1001) {
            if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
                // 权限授予后可重新调用写入方法
                writeTxtToExternalSDCard(this, "test.txt", "这是外置SD卡中的测试文本内容");
            } else {
                Toast.makeText(this, "需要存储权限才能写入文件", Toast.LENGTH_SHORT).show();
            }
        }
    }

    // 外置SD卡路径获取方法
    @SuppressLint("NewApi")
    public static String getExternalSDCardPath(Context context) {
        StorageManager storageManager = (StorageManager) context.getSystemService(Context.STORAGE_SERVICE);
        List<StorageVolume> storageVolumes = storageManager.getStorageVolumes();
        
        for (StorageVolume volume : storageVolumes) {
            if (!volume.isPrimary() && Environment.MEDIA_MOUNTED.equals(volume.getState())) {
                if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
                    if (volume.getDirectory() != null) {
                        return volume.getDirectory().getAbsolutePath();
                    }
                } else {
                    try {
                        Method getPathMethod = StorageVolume.class.getMethod("getPath");
                        return (String) getPathMethod.invoke(volume);
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                }
            }
        }
        return null;
    }
}

关键注意点

  • Android 10+默认启用分区存储,如需访问外置SD卡的自定义目录,必须申请MANAGE_EXTERNAL_STORAGE权限,该权限需用户手动在系统设置中授予。
  • 务必先校验外置SD卡的挂载状态,避免因SD卡未挂载导致的文件操作失败。
  • 使用try-with-resources语法自动关闭文件流,防止资源泄漏。

内容的提问来源于stack exchange,提问作者vulcain1972

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.13 15:23:18