Android - Copy res/raw resource to SD correctly - android

Well, I tried a lot of things, but the better goal that I achieve is copy the desired file to sd, but the new file size is 0bytes always :(
This is my code :
String baseDir = Environment.getExternalStorageDirectory().getAbsolutePath();
String fileName = sonidoActual+".mp3";
File newSoundFile = new File(baseDir, fileName);
Uri mUri = Uri.parse("android.resource://com.genaut.ringtonelists/raw/"+sonidoActual);
AssetFileDescriptor soundFile;
try {
soundFile= getContentResolver().openAssetFileDescriptor(mUri, "r");
} catch (FileNotFoundException e) {
soundFile=null;
}
try {
byte[] readData = new byte[1024*500];
FileInputStream fis = soundFile.createInputStream();
FileOutputStream fos = new FileOutputStream(newSoundFile);
int i = fis.read(readData);
while (i != -1) {
fos.write(readData, 0, i);
i = fis.read(readData);
Log.d("Degug - While: ", "i: "+i);
}
fos.flush();
fos.close();
} catch (IOException io) {
}
Sorry for my bad english.Any one know the problem? Thanks a lot!
I have these permissions on my manifest:
<uses-permission android:name="android.permission.WRITE_SETTINGS" />
<uses-permission android:name="android.permission.CHANGE_CONFIGURATION" />
<uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
More info:
I tried some code to copy files from assets and not work.. I have some app that set Ringtone well, so I don't think that my SD has a problem.. I feel hopeless :S
These are the code from assets, apparently works fine: https://stackoverflow.com/a/4530294/1422434
I tried too with getResources.openRawResource(): but not works
String baseDir = Environment.getExternalStorageDirectory().getAbsolutePath();
String fileName = nombreActual+".mp3";
File newSoundFile = new File(baseDir, fileName);
try {
byte[] readData = new byte[1024*500];
InputStream fis = getResources().openRawResource(contexto.getResources().getIdentifier(sonidoActual,"raw", contexto.getPackageName()));
FileOutputStream fos = new FileOutputStream(newSoundFile);
int i = fis.read(readData);
while (i != -1) {
fos.write(readData, 0, i);
i = fis.read(readData);
}
fos.close();
} catch (IOException io) {
}

As you are using the raw folder, simply use this from your activity:
getResources().openRawResource(resourceName)

Related

Android 6.0 Permissions Issues

I am having one heck of a time with this new permission request in Android 6. My app worked fine, and then in the last two days it is force closing all the time. If I change the target SDK level to 22, it works fine, but of course Play Store wont let you downgrade the SDK.
I need these permissions.
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
<uses-permission android:name="com.android.vending.BILLING" />
After this I am not sure how to work the requesting, or new way of implementing the permissions part so the errors will stop. I have been working on this for hours and have googled and search endlessly. While alot of examples out there all tell me to do the same thing, I just cannot seem to get it write in Android Studio. Any help would be greatly appreciated.
Here is part of the code that was giving me issues.
public void exportSkin(View arg0) throws IOException {
if (type.equals("popular")) {
AssetManager assetManager = getAssets();
InputStream is = assetManager.open("skins/" + skinname + ".png");
// create a File object for the parent directory
File wallpaperDirectory = new File(Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES).getPath() + "/SkinYourself/");
// have the object build the directory structure, if needed.
//noinspection ResultOfMethodCallIgnored
wallpaperDirectory.mkdirs();
// create a File object for the output file
File out = new File(Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES) + "/SkinYourself/", "" + PopChar.character_name + ".png");
byte[] buffer = new byte[1024];
FileOutputStream fos = new FileOutputStream(out);
int read;
while ((read = is.read(buffer, 0, 1024)) >= 0) {
fos.write(buffer, 0, read);
}
fos.flush();
fos.close();
is.close();
}
if (type.equals("create")) {
String root = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES).toString();
File myDir = new File(root + "/SkinYourself");
myDir.mkdirs();
String fname = "SkinYourself" + System.currentTimeMillis() / 1000 + ".png";
File file = new File(myDir, fname);
if (file.exists()) file.delete();
try {
FileOutputStream out = new FileOutputStream(file);
b.compress(Bitmap.CompressFormat.PNG, 100, out);
out.flush();
out.close();
} catch (Exception e) {
e.printStackTrace();
}
}
/*sendBroadcast(new Intent(
Intent.ACTION_MEDIA_MOUNTED,
Uri.parse("file://" + Environment.getExternalStorageDirectory())));
*/
Toast.makeText(MainActivity.this,
"Your skin has been saved to the SkinYourself folder check the info button on how to use it", Toast.LENGTH_LONG)
.show();
displayInterstitial();
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
Intent mediaScanIntent = new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE);
File f = new File("file://" + Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES));
Uri contentUri = Uri.fromFile(f);
mediaScanIntent.setData(contentUri);
this.sendBroadcast(mediaScanIntent);
} else {
sendBroadcast(new Intent(Intent.ACTION_MEDIA_MOUNTED, Uri.parse("file://" + Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES))));
}
}

Can't write to internal storage

In my app I am trying to create a file and write to it.
This is my code:
try {
File tmpDir = new File("/sdcard/LivingstoneTemp/");
tmpDir.mkdirs();
String filename = "Livingstone_" +UUID.randomUUID() + ".html";
File outputFile = new File(tmpDir, filename);
FileOutputStream fos = new FileOutputStream(outputFile);
byte[] data = response.getBytes();
fos.write(data);
fos.flush();
fos.close();
} catch (Exception e) {
Log.i("LivingstoneInfo", "Error: " + e.getMessage());
}
Permissions:
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
I get a "No such file or directory" exception.
I'm running this on a Nexus 5 with an internal storage.

Writing files internally

Within my app I am trying to write a file, which I can then internally read from.
Would anyone have an example of how to write files to the installation folders of app?
use the following code to write from Edittext into file and read from file into Edittext
set the following permission to AndroidManifest.xml
<uses-permission android:name="android.permission.INTERNET"></uses-permission>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"></uses-permission>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"></uses-permission>
<uses-permission android:name="android.permission.READ_PHONE_STATE"></uses-permission>
JAVA CODE
EditText LoadedText;
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
LoadedText=(EditText) findViewById(R.id.LoadedText);
File sdcard = Environment.getExternalStorageDirectory();
//Get the text file
File file = new File("/sdcard/RouterSetup.txt");
//Read text from file
StringBuilder text = new StringBuilder();
try {
BufferedReader br = new BufferedReader(new FileReader(file));
String line;
while ((line = br.readLine()) != null) {
text.append(line);
text.append('\n');
}
br.close();
}
catch (IOException e) {
//You'll need to add proper error handling here
}
LoadedText.setText(text.toString());
}
public void saveFile() {
try {
File myFile = new File("/sdcard/RouterSetup.txt");
myFile.createNewFile();
FileOutputStream fOut = new FileOutputStream(myFile);
OutputStreamWriter myOutWriter =
new OutputStreamWriter(fOut);
myOutWriter.append(LoadedText.getText());
myOutWriter.close();
fOut.close();
Toast.makeText(getBaseContext(),
"Done writing SD " + LoadedText.getText() + ".txt",
Toast.LENGTH_SHORT).show();
} catch (Exception e) {
Toast.makeText(getBaseContext(), e.getMessage(),
Toast.LENGTH_SHORT).show();
}
}
getFilesDir() vs Environment.getDataDirectory()
public File getFilesDir ()
Returns the absolute path to the directory on the filesystem where files created with openFileOutput(String, int) are stored.
public static File getExternalStorageDirectory ()
Return the primary external storage directory. This directory may not currently be accessible if it has been mounted by the user on their computer, has been removed from the device, or some other problem has happened. You can determine its current state with getExternalStorageState().
If you want to get your application path use getFilesDir() which will give you path /data/data/your package/files
You can get the path using the Environment var of your data/package using the
getExternalFilesDir(Environment.getDataDirectory().getAbsolutePath()).getAbsolutePath(); which will return the path from the root directory of your external storage as /storage/sdcard/Android/data/your pacakge/files/data
To access the external resources you have to provide the permission of WRITE_EXTERNAL_STORAGE and READ_EXTERNAL_STORAGE in your manifest.
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
The simplest solution is
String filename = "stuff.xml";
READ
FileInputStream stream = ctx.openFileInput(filename);
(and below is a really simple example of parsing that file)
BufferedReader buffReader = new BufferedReader(new InputStreamReader(inputStream));
String line;
try {
while ((line = buffReader.readLine()) != null) {
...
// do something cool
...
}
} catch (IOException e) {
Log.e("MyApp", "SCREAAAAAM", e);
}
WRITE
OutputStreamWriter outputStreamWriter = new OutputStreamWriter( ctx.openFileOutput(filename, Context.MODE_PRIVATE) );
outputStreamWriter.write("this is text not xml :(");
So the two main things to note are the openFileInput and openFileOutput methods of Context (ie your activity) which take care of the heavy lifting
//here i am downloading file from server and writing
String download_link = "some server location";
URL url = new URL(download_link);
HttpsURLConnection c = null;
if (url.getProtocol().toLowerCase().equals("https")) {
trustAllHosts();
c = (HttpsURLConnection) url.openConnection();
c.setHostnameVerifier(DO_NOT_VERIFY);
}
c.setRequestMethod("GET");
c.setDoOutput(true);
c.connect();
String PATH = Environment.getExternalStorageDirectory() + "/download/";
File file = new File(PATH);
file.mkdirs();
File outputFile = new File(file, "Mobi.apk");
if(outputFile.exists()){
outputFile.delete();
}
FileOutputStream fos = new FileOutputStream(outputFile);
InputStream is = c.getInputStream();
byte[] buffer = new byte[1024];
int len1 = 0;
while ((len1 = is.read(buffer)) != -1) {
fos.write(buffer, 0, len1);
}
fos.close();
is.close();
you need to add permission in manifest file:
uses-permission android:name="android.permission.INTERNET"></uses-permission>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"></uses-permission>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"></uses-permission>
<uses-permission android:name="android.permission.READ_PHONE_STATE"></uses-permission>
Which type of files you are talking about ?
For data storage you can use shared preferences.
For media type you can use media storage.

android:- how to copy image from Assets to SD Card?

I have some images to be displayed in the Application (When user selects an image from it, like picking from gallery ).
The question is how to copy the images I am putting in the assets
folder in the code to a folder on the SD card.
Edit: I tried this example : http://www.technotalkative.com/android-copy-files-from-assets-to-sd-card/
I have given the app permission to read and write
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" /><uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
AssetManager assetManager = context.getAssets();
InputStream is = assetManager.open(fileName);
Get the AssetManager and call open with the filename you want to copy as parameter.
Then you can simply copy in this way
File out = new File(Environment.getExternalStorageDirectory(), fileName);
byte[] buffer = new byte[BUFFER_LEN];
FileOutputStream fos = new FileOutputStream(out);
int read = 0;
while ((read = is.read(buffer, 0, BUFFER_LEN)) >= 0) {
fos.write(buffer, 0, read);
}
fos.flush();
fos.close()
is.close()
remember to add the WRITE_EXTERNAL_STORAGE permission in your AndroidManifest.xml file
private void copyFileAssets() {
AssetManager assetManager = getAssets();
InputStream in = null;
OutputStream out = null;
try {
in = assetManager.open("ceo.jpg");
out = new FileOutputStream(Environment.getExternalStorageDirectory()+File.separator+ "abc.jpg");
copyFile(in, out);
in.close();
in = null;
out.flush();
out.close();
out = null;
} catch(IOException e) {
Log.e("tag", "Failed to copy asset file: " + filename, e);
}
}
private void copyFile(InputStream in, OutputStream out) throws IOException {
byte[] buffer = new byte[1024];
int read;
while((read = in.read(buffer)) != -1){
out.write(buffer, 0, read);
}
}
you have to add this permission:
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
Get the bitmap resource using one of the many ways.
Ex:
Bitmap bitmap = BitmapFactory.decodeResource(resource, id); // get your bitmap that you want to save on SD card.
Get the path to store the resource.
String compressedFilePath = Environment.getExternalStorageDirectory() + File.separator + "FOLDERNAME" + File.separator + "FILENAME.jpg";
Save using compress method. (Shortcut way to save image as per docs)
bitmap.compress(Bitmap.CompressFormat.JPEG, 100, new FileOutputStream(new File(pathToStore))); // use 100 to make sure image quality is not reduced(Read the docs)
Note: You need Write(and may be read in future) access to write to SDCARD.
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />

Permission to write on SD card android

I have a problem writing to the SD card, here is the code:
(Sorry about the layout of the code, just copy pased it )
public class SaveAndReadManager {
private String result;
private String saveFileName = "eventlist_savefile";
public String writeToFile( ArrayList<Event> arrlEvents ){
FileOutputStream fos = null;
ObjectOutputStream out = null;
try{
File root = Environment.getExternalStorageDirectory();
if( root.canWrite() ){
fos = new FileOutputStream( saveFileName );
out = new ObjectOutputStream( fos );
out.writeObject( arrlEvents );
result = "File written";
out.close();
}else{
result = "file cant write";
}
}catch( IOException e ){
e.printStackTrace();
result = "file not written";
}
return result;
}
public boolean readFromFile(){
return false;
}
}
I have not implemented the readFromFile() yet.
The problem is that root.canWrite() returns false all the time.
Here is the manifest file:
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<application android:icon="#drawable/icon" android:label="#string/app_name">
<activity android:name=".InfoScreen"
android:label="#string/app_name">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
<activity android:name=".EventCalendar"
android:label="#string/app_name" />
<activity android:name=".MakeEvent"
android:label="#string/app_name" />
<activity android:name=".ViewEvent"
android:label="#string/app_name" />
</application>
<uses-sdk android:minSdkVersion="8" />
I've asked for the permission to write, and on my avd, if i go to settings -> SD card and phone storage, it tells me i have 1 gb on the sd card to write on. Please help.
Thanks:)
Try checking the state of the SD card before you attempt to write to it. It may be used as a shared drive, corrupted, full, etc. A list of states can be found here: http://developer.android.com/reference/android/os/Environment.html
Here's an example of getting the states:
String state = Environment.getExternalStorageState();
if (Environment.MEDIA_MOUNTED.equals(state)) {
mExternalStorageAvailable = mExternalStorageWriteable = true;
} else if (Environment.MEDIA_MOUNTED_READ_ONLY.equals(state)) {
mExternalStorageAvailable = true;
mExternalStorageWriteable = false;
} else {
mExternalStorageAvailable = mExternalStorageWriteable = false;
}
Which result are you seeing retunred from writeToFile? "file not written" or "file cant write"?
When I ran your code it dropped into the catch IOException block with the result of "file not written". The reason for this was that fos was defined incorrectly:
fos = new FileOutputStream( saveFileName );
should be:
fos = new FileOutputStream( root + "/" saveFileName );
After I changed this line, I got the result "File written" returned from writeToFile.
I use the following code to record audio data (successfully) to my Android's SD Card. My application requires the RECORD_AUDIO permission, but nothing else.
File file = new File (Environment.getExternalStorageDirectory().getAbsolutePath() + FILE_NAME);
if (file.exists())
file.delete(); // Delete any previous recording
try
{
file.createNewFile(); // Create the new file
}
catch (IOException e)
{
Log.e (TAG, "Failed to create " + file.toString());
}
try
{
OutputStream os = new FileOutputStream (file);
BufferedOutputStream bos = new BufferedOutputStream (os, 8000);
DataOutputStream dos = new DataOutputStream (bos); // Create a DataOutputStream to write the audio data to the file
// Create an AudioRecord object to record the audio
int bufferSize = AudioRecord.getMinBufferSize (frequency, channelConfig, Encoding);
AudioRecord audioRecord = new AudioRecord (MediaRecorder.AudioSource.MIC, frequency, channelConfig, Encoding, bufferSize);
short[] buffer = new short[bufferSize]; // Using "short", because we're using "ENCODING_PCM_16BIT"
audioRecord.startRecording();
while (isRecording)
{
int bufferReadResult = audioRecord.read (buffer, 0, bufferSize);
for (int i = 0; i < bufferReadResult; i++)
dos.writeShort (buffer[i]);
}
audioRecord.stop();
dos.close();
}
catch (Exception t)
{
Log.e (TAG, "Recording Failed");
}
It would appear to me that you're missing the getAbsolutePath() call appended to your getExternalStorageDirectory() call (which may have the same result as Marc Bernstein's hard coded solution).
I should have included the following link as well (since it's where I got the code that writes to the SD Card...):
http://emeadev.blogspot.com/2009/09/raw-audio-manipulation-in-android.html

Categories

Resources