tarjeta - ficheros en android memoria interna
¿Cómo puedo obtener una ruta de tarjeta SD externa para Android 4.0+? (26)
¡Buenas noticias! En KitKat ahora hay una API pública para interactuar con estos dispositivos secundarios de almacenamiento compartido.
Los nuevos Context.getExternalFilesDirs()
y Context.getExternalCacheDirs()
pueden devolver varias rutas, incluidos los dispositivos primarios y secundarios. A continuación, puede iterar sobre ellos y comprobar Environment.getStorageState()
y File.getFreeSpace()
para determinar el mejor lugar para almacenar sus archivos. Estos métodos también están disponibles en ContextCompat
en la biblioteca support-v4.
También tenga en cuenta que si solo está interesado en utilizar los directorios devueltos por Context
, ya no necesita los READ_
o WRITE_EXTERNAL_STORAGE
. En el futuro, siempre tendrá acceso de lectura / escritura a estos directorios sin necesidad de permisos adicionales.
Las aplicaciones también pueden seguir trabajando en dispositivos más antiguos al finalizar su solicitud de permiso de esta manera:
<uses-permission
android:name="android.permission.WRITE_EXTERNAL_STORAGE"
android:maxSdkVersion="18" />
Samsung Galaxy S3 tiene una ranura de tarjeta SD extrenal, que se monta en /mnt/extSdCard
.
Mi pregunta es: ¿cómo conseguir este camino mediante algo como Environment.getExternalStorageDirectory()
? Esto devolverá mnt/sdcard
, y no puedo encontrar la API para la tarjeta SD externa. (O almacenamiento USB extraíble en algunas tabletas)
¡Gracias!
Así es como obtengo la lista de rutas de la tarjeta SD (excluyendo el almacenamiento externo principal):
/**
* returns a list of all available sd cards paths, or null if not found.
*
* @param includePrimaryExternalStorage set to true if you wish to also include the path of the primary external storage
*/
@TargetApi(Build.VERSION_CODES.HONEYCOMB)
public static List<String> getSdCardPaths(final Context context,final boolean includePrimaryExternalStorage)
{
final File[] externalCacheDirs=ContextCompat.getExternalCacheDirs(context);
if(externalCacheDirs==null||externalCacheDirs.length==0)
return null;
if(externalCacheDirs.length==1)
{
if(externalCacheDirs[0]==null)
return null;
final String storageState=EnvironmentCompat.getStorageState(externalCacheDirs[0]);
if(!Environment.MEDIA_MOUNTED.equals(storageState))
return null;
if(!includePrimaryExternalStorage&&VERSION.SDK_INT>=VERSION_CODES.HONEYCOMB&&Environment.isExternalStorageEmulated())
return null;
}
final List<String> result=new ArrayList<>();
if(includePrimaryExternalStorage||externalCacheDirs.length==1)
result.add(getRootOfInnerSdCardFolder(externalCacheDirs[0]));
for(int i=1;i<externalCacheDirs.length;++i)
{
final File file=externalCacheDirs[i];
if(file==null)
continue;
final String storageState=EnvironmentCompat.getStorageState(file);
if(Environment.MEDIA_MOUNTED.equals(storageState))
result.add(getRootOfInnerSdCardFolder(externalCacheDirs[i]));
}
if(result.isEmpty())
return null;
return result;
}
/** Given any file/folder inside an sd card, this will return the path of the sd card */
private static String getRootOfInnerSdCardFolder(File file)
{
if(file==null)
return null;
final long totalSpace=file.getTotalSpace();
while(true)
{
final File parentFile=file.getParentFile();
if(parentFile==null||parentFile.getTotalSpace()!=totalSpace)
return file.getAbsolutePath();
file=parentFile;
}
}
En algunos dispositivos (por ejemplo, Samsung Galaxy SII), la tarjeta de memoria interna puede estar en vfat. En este caso use referir al último código, obtenemos la tarjeta de memoria interna de ruta (/ mnt / sdcad) pero no la tarjeta externa. El código que se refiere a continuación resuelve este problema.
static String getExternalStorage(){
String exts = Environment.getExternalStorageDirectory().getPath();
try {
FileReader fr = new FileReader(new File("/proc/mounts"));
BufferedReader br = new BufferedReader(fr);
String sdCard=null;
String line;
while((line = br.readLine())!=null){
if(line.contains("secure") || line.contains("asec")) continue;
if(line.contains("fat")){
String[] pars = line.split("//s");
if(pars.length<2) continue;
if(pars[1].equals(exts)) continue;
sdCard =pars[1];
break;
}
}
fr.close();
br.close();
return sdCard;
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return null;
}
En realidad, en algunos dispositivos, el nombre predeterminado de sdcard externo se muestra como extSdCard
y para otros es sdcard1
.
Este fragmento de código ayuda a descubrir esa ruta exacta y ayuda a recuperar la ruta del dispositivo externo.
String sdpath,sd1path,usbdiskpath,sd0path;
if(new File("/storage/extSdCard/").exists())
{
sdpath="/storage/extSdCard/";
Log.i("Sd Cardext Path",sdpath);
}
if(new File("/storage/sdcard1/").exists())
{
sd1path="/storage/sdcard1/";
Log.i("Sd Card1 Path",sd1path);
}
if(new File("/storage/usbcard1/").exists())
{
usbdiskpath="/storage/usbcard1/";
Log.i("USB Path",usbdiskpath);
}
if(new File("/storage/sdcard0/").exists())
{
sd0path="/storage/sdcard0/";
Log.i("Sd Card0 Path",sd0path);
}
Encontré una manera más confiable de obtener rutas a todas las tarjetas SD en el sistema. Esto funciona en todas las versiones de Android y rutas de retorno a todos los almacenamientos (incluyendo emulados).
Funciona correctamente en todos mis dispositivos.
PD: basado en el código fuente de la clase de entorno.
private static final Pattern DIR_SEPORATOR = Pattern.compile("/");
/**
* Raturns all available SD-Cards in the system (include emulated)
*
* Warning: Hack! Based on Android source code of version 4.3 (API 18)
* Because there is no standart way to get it.
* TODO: Test on future Android versions 4.4+
*
* @return paths to all available SD-Cards in the system (include emulated)
*/
public static String[] getStorageDirectories()
{
// Final set of paths
final Set<String> rv = new HashSet<String>();
// Primary physical SD-CARD (not emulated)
final String rawExternalStorage = System.getenv("EXTERNAL_STORAGE");
// All Secondary SD-CARDs (all exclude primary) separated by ":"
final String rawSecondaryStoragesStr = System.getenv("SECONDARY_STORAGE");
// Primary emulated SD-CARD
final String rawEmulatedStorageTarget = System.getenv("EMULATED_STORAGE_TARGET");
if(TextUtils.isEmpty(rawEmulatedStorageTarget))
{
// Device has physical external storage; use plain paths.
if(TextUtils.isEmpty(rawExternalStorage))
{
// EXTERNAL_STORAGE undefined; falling back to default.
rv.add("/storage/sdcard0");
}
else
{
rv.add(rawExternalStorage);
}
}
else
{
// Device has emulated storage; external storage paths should have
// userId burned into them.
final String rawUserId;
if(Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN_MR1)
{
rawUserId = "";
}
else
{
final String path = Environment.getExternalStorageDirectory().getAbsolutePath();
final String[] folders = DIR_SEPORATOR.split(path);
final String lastFolder = folders[folders.length - 1];
boolean isDigit = false;
try
{
Integer.valueOf(lastFolder);
isDigit = true;
}
catch(NumberFormatException ignored)
{
}
rawUserId = isDigit ? lastFolder : "";
}
// /storage/emulated/0[1,2,...]
if(TextUtils.isEmpty(rawUserId))
{
rv.add(rawEmulatedStorageTarget);
}
else
{
rv.add(rawEmulatedStorageTarget + File.separator + rawUserId);
}
}
// Add all secondary storages
if(!TextUtils.isEmpty(rawSecondaryStoragesStr))
{
// All Secondary SD-CARDs splited into array
final String[] rawSecondaryStorages = rawSecondaryStoragesStr.split(File.pathSeparator);
Collections.addAll(rv, rawSecondaryStorages);
}
return rv.toArray(new String[rv.size()]);
}
Esta solución (reunida a partir de otras respuestas a esta pregunta) maneja el hecho (mencionado por @ono) de que System.getenv("SECONDARY_STORAGE")
no sirve para Marshmallow.
Probado y trabajando en:
- Samsung Galaxy Tab 2 (Android 4.1.1 - archivo)
- Samsung Galaxy Note 8.0 (Android 4.2.2 - archivo)
- Samsung Galaxy S4 (Android 4.4 - Stock)
- Samsung Galaxy S4 (Android 5.1.1 - Cyanogenmod)
Samsung Galaxy Tab A (Android 6.0.1 - archivo)
/** * Returns all available external SD-Card roots in the system. * * @return paths to all available external SD-Card roots in the system. */ public static String[] getStorageDirectories() { String [] storageDirectories; String rawSecondaryStoragesStr = System.getenv("SECONDARY_STORAGE"); if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) { List<String> results = new ArrayList<String>(); File[] externalDirs = applicationContext.getExternalFilesDirs(null); for (File file : externalDirs) { String path = file.getPath().split("/Android")[0]; if((Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP && Environment.isExternalStorageRemovable(file)) || rawSecondaryStoragesStr != null && rawSecondaryStoragesStr.contains(path)){ results.add(path); } } storageDirectories = results.toArray(new String[0]); }else{ final Set<String> rv = new HashSet<String>(); if (!TextUtils.isEmpty(rawSecondaryStoragesStr)) { final String[] rawSecondaryStorages = rawSecondaryStoragesStr.split(File.pathSeparator); Collections.addAll(rv, rawSecondaryStorages); } storageDirectories = rv.toArray(new String[rv.size()]); } return storageDirectories; }
Estaba usando la solución de Dmitriy Lozenko hasta que revisé un Asus Zenfone2 , Marshmallow 6.0.1 y la solución no funciona. La solución falló al obtener EMULATED_STORAGE_TARGET , específicamente para la ruta microSD, es decir: / storage / F99C-10F4 / . Edité el código para obtener las rutas raíz emuladas directamente desde las rutas de aplicación emuladas con context.getExternalFilesDirs(null);
y agregue más rutas físicas conocidas específicas del modelo de teléfono .
Para hacer nuestra vida más fácil, hice una biblioteca here . Puede usarlo a través del sistema de compilación gradle, maven, sbt y leiningen.
Si le gusta la forma tradicional, también puede copiar y pegar el archivo directamente desde here , pero no sabrá si hay una actualización en el futuro sin verificarla manualmente.
Si tiene alguna pregunta o sugerencia, hágamelo saber
Estoy seguro de que este código seguramente resolverá sus problemas ... Esto está funcionando bien para mí ...
try {
File mountFile = new File("/proc/mounts");
usbFoundCount=0;
sdcardFoundCount=0;
if(mountFile.exists())
{
Scanner usbscanner = new Scanner(mountFile);
while (usbscanner.hasNext()) {
String line = usbscanner.nextLine();
if (line.startsWith("/dev/fuse /storage/usbcard1")) {
usbFoundCount=1;
Log.i("-----USB--------","USB Connected and properly mounted---/dev/fuse /storage/usbcard1" );
}
}
}
if(mountFile.exists()){
Scanner sdcardscanner = new Scanner(mountFile);
while (sdcardscanner.hasNext()) {
String line = sdcardscanner.nextLine();
if (line.startsWith("/dev/fuse /storage/sdcard1")) {
sdcardFoundCount=1;
Log.i("-----USB--------","USB Connected and properly mounted---/dev/fuse /storage/sdcard1" );
}
}
}
if(usbFoundCount==1)
{
Toast.makeText(context,"USB Connected and properly mounted", 7000).show();
Log.i("-----USB--------","USB Connected and properly mounted" );
}
else
{
Toast.makeText(context,"USB not found!!!!", 7000).show();
Log.i("-----USB--------","USB not found!!!!" );
}
if(sdcardFoundCount==1)
{
Toast.makeText(context,"SDCard Connected and properly mounted", 7000).show();
Log.i("-----SDCard--------","SDCard Connected and properly mounted" );
}
else
{
Toast.makeText(context,"SDCard not found!!!!", 7000).show();
Log.i("-----SDCard--------","SDCard not found!!!!" );
}
}catch (Exception e) {
e.printStackTrace();
}
Gracias por las pistas proporcionadas por ustedes, especialmente @SmartLemon, obtuve la solución. En caso de que alguien más lo necesite, puse mi solución final aquí (para encontrar la primera tarjeta SD externa listada):
public File getExternalSDCardDirectory()
{
File innerDir = Environment.getExternalStorageDirectory();
File rootDir = innerDir.getParentFile();
File firstExtSdCard = innerDir ;
File[] files = rootDir.listFiles();
for (File file : files) {
if (file.compareTo(innerDir) != 0) {
firstExtSdCard = file;
break;
}
}
//Log.i("2", firstExtSdCard.getAbsolutePath().toString());
return firstExtSdCard;
}
Si no hay una tarjeta SD externa allí, devuelve el almacenamiento a bordo. Lo usaré si la tarjeta SD no existe, es posible que deba cambiarla.
He probado las soluciones proporcionadas por Dmitriy Lozenko y Gnathonic en mi Samsung Galaxy Tab S2 (Modelo: T819Y) pero ninguna me ayudó a recuperar la ruta de acceso a un directorio de tarjeta SD externo. mount
ejecución del comando mount
contenía la ruta requerida al directorio externo de la tarjeta SD (es decir, / Storage / A5F9-15F4) pero no coincidía con la expresión regular, por lo que no se devolvió. No entiendo el mecanismo de nomenclatura de directorio seguido por Samsung. Por qué se desvían de los estándares (es decir, extsdcard) y salen con algo realmente sospechoso como en mi caso (es decir, / Storage / A5F9-15F4) . ¿Hay algo que me falta? De todas formas, seguir los cambios en la expresión regular de la solución de Gnathonic me ayudó a obtener un directorio de sdcard válido:
final HashSet<String> out = new HashSet<String>();
String reg = "(?i).*(vold|media_rw).*(sdcard|vfat|ntfs|exfat|fat32|ext3|ext4).*rw.*";
String s = "";
try {
final Process process = new ProcessBuilder().command("mount")
.redirectErrorStream(true).start();
process.waitFor();
final InputStream is = process.getInputStream();
final byte[] buffer = new byte[1024];
while (is.read(buffer) != -1) {
s = s + new String(buffer);
}
is.close();
} catch (final Exception e) {
e.printStackTrace();
}
// parse output
final String[] lines = s.split("/n");
for (String line : lines) {
if (!line.toLowerCase(Locale.US).contains("asec")) {
if (line.matches(reg)) {
String[] parts = line.split(" ");
for (String part : parts) {
if (part.startsWith("/"))
if (!part.toLowerCase(Locale.US).contains("vold"))
out.add(part);
}
}
}
}
return out;
I am not sure if this is a valid solution and if it will give results for other Samsung tablets but it has fixed my problem for now. Following is another method to retrieve removable SD Card path in Android (v6.0). I have tested the method with android marshmallow and it works. Approach used in it is very basic and will surely work for other versions too but testing is mandatory. Some insight into it will be helpful:
public static String getSDCardDirPathForAndroidMarshmallow() {
File rootDir = null;
try {
// Getting external storage directory file
File innerDir = Environment.getExternalStorageDirectory();
// Temporarily saving retrieved external storage directory as root
// directory
rootDir = innerDir;
// Splitting path for external storage directory to get its root
// directory
String externalStorageDirPath = innerDir.getAbsolutePath();
if (externalStorageDirPath != null
&& externalStorageDirPath.length() > 1
&& externalStorageDirPath.startsWith("/")) {
externalStorageDirPath = externalStorageDirPath.substring(1,
externalStorageDirPath.length());
}
if (externalStorageDirPath != null
&& externalStorageDirPath.endsWith("/")) {
externalStorageDirPath = externalStorageDirPath.substring(0,
externalStorageDirPath.length() - 1);
}
String[] pathElements = externalStorageDirPath.split("/");
for (int i = 0; i < pathElements.length - 1; i++) {
rootDir = rootDir.getParentFile();
}
File[] files = rootDir.listFiles();
for (File file : files) {
if (file.exists() && file.compareTo(innerDir) != 0) {
// Try-catch is implemented to prevent from any IO exception
try {
if (Environment.isExternalStorageRemovable(file)) {
return file.getAbsolutePath();
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
} catch (Exception ex) {
ex.printStackTrace();
}
return null;
}
Kindly share if you have any other approach to handle this issue. Gracias
Hice lo siguiente para acceder a todas las tarjetas SD externas.
Con:
File primaryExtSd=Environment.getExternalStorageDirectory();
obtienes la ruta a la SD externa primaria Luego con:
File parentDir=new File(primaryExtSd.getParent());
obtienes el directorio padre del almacenamiento externo primario, y también es el padre de todos los sd externos. Ahora, puede enumerar todo el almacenamiento y seleccionar el que desea.
Espero que sea útil.
Para recuperar todos los almacenes externos (ya sean tarjetas SD o almacenes internos no extraíbles ), puede usar el siguiente código:
final String state = Environment.getExternalStorageState();
if ( Environment.MEDIA_MOUNTED.equals(state) || Environment.MEDIA_MOUNTED_READ_ONLY.equals(state) ) { // we can read the External Storage...
//Retrieve the primary External Storage:
final File primaryExternalStorage = Environment.getExternalStorageDirectory();
//Retrieve the External Storages root directory:
final String externalStorageRootDir;
if ( (externalStorageRootDir = primaryExternalStorage.getParent()) == null ) { // no parent...
Log.d(TAG, "External Storage: " + primaryExternalStorage + "/n");
}
else {
final File externalStorageRoot = new File( externalStorageRootDir );
final File[] files = externalStorageRoot.listFiles();
for ( final File file : files ) {
if ( file.isDirectory() && file.canRead() && (file.listFiles().length > 0) ) { // it is a real directory (not a USB drive)...
Log.d(TAG, "External Storage: " + file.getAbsolutePath() + "/n");
}
}
}
}
Alternativamente, puede usar System.getenv ("EXTERNAL_STORAGE") para recuperar el directorio primario de almacenamiento externo (por ejemplo, "/ storage / sdcard0" ) y System.getenv ("SECONDARY_STORAGE") para recuperar la lista de todos los directorios secundarios (por ejemplo, " / storage / extSdCard: / storage / UsbDriveA: / storage / UsbDriveB " ). Recuerde que, también en este caso, es posible que desee filtrar la lista de directorios secundarios para excluir las unidades USB.
En cualquier caso, tenga en cuenta que el uso de rutas codificadas es siempre un mal enfoque (especialmente cuando cada fabricante puede cambiarlo como corresponde).
Puede usar algo como - Context.getExternalCacheDirs () o Context.getExternalFilesDirs () o Context.getObbDirs (). Proporcionan directorios específicos de la aplicación en todos los dispositivos de almacenamiento externo donde la aplicación puede almacenar sus archivos.
Así que algo como esto - Context.getExternalCacheDirs () [i] .getParentFile (). GetParentFile (). GetParentFile (). GetParent () puede obtener la ruta de acceso de los dispositivos de almacenamiento externo.
Sé que estos comandos son para un propósito diferente, pero otras respuestas no me funcionaron.
Este enlace me dio buenos consejos - https://possiblemobile.com/2014/03/android-external-storage/
Sí. Los diferentes fabricantes utilizan diferentes nombres de tarjetas SD, como en Samsung Tab 3, su extsd, y otros dispositivos Samsung usan sdcards como este fabricante diferente usan diferentes nombres.
Tenía el mismo requisito que tú. así que he creado un ejemplo de muestra para usted desde mi proyecto. Vaya a este enlace . Ejemplo de selector de directorio de Android que usa la biblioteca androi-dirchooser. Este ejemplo detecta la tarjeta SD y enumera todas las subcarpetas y también detecta si el dispositivo tiene más de una tarjeta SD.
Parte del código se ve así. Para ver un ejemplo completo, vaya al enlace Selector de directorio de Android
/**
* Returns the path to internal storage ex:- /storage/emulated/0
*
* @return
*/
private String getInternalDirectoryPath() {
return Environment.getExternalStorageDirectory().getAbsolutePath();
}
/**
* Returns the SDcard storage path for samsung ex:- /storage/extSdCard
*
* @return
*/
private String getSDcardDirectoryPath() {
return System.getenv("SECONDARY_STORAGE");
}
mSdcardLayout.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View view) {
String sdCardPath;
/***
* Null check because user may click on already selected buton before selecting the folder
* And mSelectedDir may contain some wrong path like when user confirm dialog and swith back again
*/
if (mSelectedDir != null && !mSelectedDir.getAbsolutePath().contains(System.getenv("SECONDARY_STORAGE"))) {
mCurrentInternalPath = mSelectedDir.getAbsolutePath();
} else {
mCurrentInternalPath = getInternalDirectoryPath();
}
if (mCurrentSDcardPath != null) {
sdCardPath = mCurrentSDcardPath;
} else {
sdCardPath = getSDcardDirectoryPath();
}
//When there is only one SDcard
if (sdCardPath != null) {
if (!sdCardPath.contains(":")) {
updateButtonColor(STORAGE_EXTERNAL);
File dir = new File(sdCardPath);
changeDirectory(dir);
} else if (sdCardPath.contains(":")) {
//Multiple Sdcards show root folder and remove the Internal storage from that.
updateButtonColor(STORAGE_EXTERNAL);
File dir = new File("/storage");
changeDirectory(dir);
}
} else {
//In some unknown scenario at least we can list the root folder
updateButtonColor(STORAGE_EXTERNAL);
File dir = new File("/storage");
changeDirectory(dir);
}
}
});
Supongo que para usar la tarjeta sd externa necesitas usar esto:
new File("/mnt/external_sd/")
O
new File("/mnt/extSdCard/")
en tu caso...
en reemplazo de Environment.getExternalStorageDirectory()
Funciona para mi. Primero debe verificar cuál es el directorio mnt y trabajar desde allí.
Deberías usar algún tipo de método de selección para elegir qué tarjeta SD usar:
File storageDir = new File("/mnt/");
if(storageDir.isDirectory()){
String[] dirList = storageDir.list();
//TODO some type of selecton method?
}
Tengo una variación en una solución que encontré here
public static HashSet<String> getExternalMounts() {
final HashSet<String> out = new HashSet<String>();
String reg = "(?i).*vold.*(vfat|ntfs|exfat|fat32|ext3|ext4).*rw.*";
String s = "";
try {
final Process process = new ProcessBuilder().command("mount")
.redirectErrorStream(true).start();
process.waitFor();
final InputStream is = process.getInputStream();
final byte[] buffer = new byte[1024];
while (is.read(buffer) != -1) {
s = s + new String(buffer);
}
is.close();
} catch (final Exception e) {
e.printStackTrace();
}
// parse output
final String[] lines = s.split("/n");
for (String line : lines) {
if (!line.toLowerCase(Locale.US).contains("asec")) {
if (line.matches(reg)) {
String[] parts = line.split(" ");
for (String part : parts) {
if (part.startsWith("/"))
if (!part.toLowerCase(Locale.US).contains("vold"))
out.add(part);
}
}
}
}
return out;
}
El método original fue probado y trabajado con
- Huawei X3 (acción)
- Galaxy S2 (stock)
- Galaxy S3 (stock)
No estoy seguro de en qué versión de Android estaban cuando se probaron.
He probado mi versión modificada con
- Moto Xoom 4.1.2 (stock)
- Galaxy Nexus (cyanogenmod 10) usando un cable otg
- HTC Incredible (cyanogenmod 7.2) esto devolvió tanto el interno como el externo. Este dispositivo es un poco extraño porque su interior no se usa en su mayor parte ya que getExternalStorage () devuelve una ruta a la tarjeta sd.
y algunos dispositivos de almacenamiento individuales que usan una tarjeta SD como su almacenamiento principal
- HTC G1 (cyanogenmod 6.1)
- HTC G1 (almacenamiento)
- HTC Vision / G2 (stock)
Exceptuando lo increíble, todos estos dispositivos solo devolvieron su almacenamiento extraíble. Probablemente haya algunos controles adicionales que debería estar haciendo, pero esto es al menos un poco mejor que cualquier solución que he encontrado hasta ahora.
consulte mi código, espero que sea útil para usted:
Runtime runtime = Runtime.getRuntime();
Process proc = runtime.exec("mount");
InputStream is = proc.getInputStream();
InputStreamReader isr = new InputStreamReader(is);
String line;
String mount = new String();
BufferedReader br = new BufferedReader(isr);
while ((line = br.readLine()) != null) {
if (line.contains("secure")) continue;
if (line.contains("asec")) continue;
if (line.contains("fat")) {//TF card
String columns[] = line.split(" ");
if (columns != null && columns.length > 1) {
mount = mount.concat("*" + columns[1] + "/n");
}
} else if (line.contains("fuse")) {//internal storage
String columns[] = line.split(" ");
if (columns != null && columns.length > 1) {
mount = mount.concat(columns[1] + "/n");
}
}
}
txtView.setText(mount);
eso no es cierto. / mnt / sdcard / external_sd puede existir incluso si la tarjeta SD no está montada. su aplicación se bloqueará cuando intente escribir en / mnt / sdcard / external_sd cuando no esté montada.
necesita verificar si la tarjeta SD está montada primero usando:
boolean isSDPresent = Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED);
System.getenv("SECONDARY_STORAGE")
devuelve null para Marshmallow. Esta es otra forma de encontrar todos los directorios externos. Puede verificar si es extraíble lo que determina si es interno / externo
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
File[] externalCacheDirs = context.getExternalCacheDirs();
for (File file : externalCacheDirs) {
if (Environment.isExternalStorageRemovable(file)) {
// It''s a removable storage
}
}
}
On Galaxy S3 Android 4.3 the path I use is ./storage/extSdCard/Card/ and it does the job. Hope it helps,
The following steps worked for me. You just need to write this lines:
String sdf = new String(Environment.getExternalStorageDirectory().getName());
String sddir = new String(Environment.getExternalStorageDirectory().getPath().replace(sdf,""));
The first line will give the name of sd directory, and you just need to use it in the replace method for the second string. The second string will contain the path for the internal and removable sd(/storage/ in my case) . I just needed this path for my app but you can go further if you need it.
To access files in my SD card , on my HTC One X (Android), I use this path:
file:///storage/sdcard0/folder/filename.jpg
Note the tripple "/" !
File[] files = null;
File file = new File("/storage");// /storage/emulated
if (file.exists()) {
files = file.listFiles();
}
if (null != files)
for (int j = 0; j < files.length; j++) {
Log.e(TAG, "" + files[j]);
Log.e(TAG, "//--//--// " + files[j].exists());
if (files[j].toString().replaceAll("_", "")
.toLowerCase().contains("extsdcard")) {
external_path = files[j].toString();
break;
} else if (files[j].toString().replaceAll("_", "")
.toLowerCase()
.contains("sdcard".concat(Integer.toString(j)))) {
// external_path = files[j].toString();
}
Log.e(TAG, "--///--///-- " + external_path);
}
String path = Environment.getExternalStorageDirectory()
+ File.separator + Environment.DIRECTORY_PICTURES;
File dir = new File(path);
//manifest file outside the application tag
//please give permission write this
//<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
File file = new File("/mnt");
String[] fileNameList = file.list(); //file names list inside the mnr folder
String all_names = ""; //for the log information
String foundedFullNameOfExtCard = ""; // full name of ext card will come here
boolean isExtCardFounded = false;
for (String name : fileNameList) {
if (!isExtCardFounded) {
isExtCardFounded = name.contains("ext");
foundedFullNameOfExtCard = name;
}
all_names += name + "/n"; // for log
}
Log.d("dialog", all_names + foundedFullNameOfExtCard);
String secStore = System.getenv("SECONDARY_STORAGE");
File externalsdpath = new File(secStore);
This will get the path of external sd secondary storage.