How to download music .mp3 files to app storage in android? - java

Music files should be downloaded to the app itself, it shouldn't get stored on mobile memory (file manager or SD card).

FileManager Class to store mp3 file inside app folders.
public class FileManager {
private final Context context;
FileManager(Context context) {
this.context = context;
}
public String getRootPath() {
File file = new File(context.getFilesDir(),"");
return file.getAbsolutePath();
}
public String getFilePath(String name) {
File file = new File(context.getFilesDir(), name);
return file.getAbsolutePath();
}
}
Download request
#RequiresApi(api = Build.VERSION_CODES.O)
private void initDownload(String soundUri) {
Log.d(TAG, "initDownload: " + soundUri);
Retrofit retrofit = new Retrofit.Builder().baseUrl(BASE_URL).build();
ApiService retrofitInterface = retrofit.create(ApiService.class);
Call<ResponseBody> request = retrofitInterface.downloadFile(soundUri);
request.enqueue(new Callback<ResponseBody>() {
#Override
public void onResponse(Call<ResponseBody> call, Response<ResponseBody> response) {
if (response.body() != null) {
Thread thread = new Thread(() -> {
try {
saveVoice(response.body());
} catch (IOException e) {
Log.d(TAG, "onResponse: " + e);
}
});
thread.start();
}
}
#Override
public void onFailure(Call<ResponseBody> call, Throwable t) {
}
});
}
#RequiresApi(api = Build.VERSION_CODES.O)
private void saveVoice(ResponseBody body) throws IOException {
try {
String mp3Key= "YOUR_KEY_TO_STORE_FILE";
int count;
byte data[] = new byte[1024 * 4];
InputStream bis = new BufferedInputStream(body.byteStream(), 1024 * 8);
File outputFile = new File(fileManager.getRootPath(), voiceKey);
OutputStream output = new FileOutputStream(outputFile);
long startTime = System.currentTimeMillis();
int timeCount = 1;
while ((count = bis.read(data)) != -1) {
long currentTime = System.currentTimeMillis() - startTime;
if (currentTime > 1000 * timeCount) {
timeCount++;
}
output.write(data, 0, count);
}
output.flush();
output.close();
bis.close();
} catch (Exception e) {
Log.d(TAG, "saveVoice: " + e);
}
}
After successfully download you can read file with the key that you wrote file to app storage. To do that:
String filePath = fileManager.getFilePath(mp3Key); // filePath returns local url of file
For example, you can do:
mediaPlayer.setDataSource(filePath );

Related

Save an Image with TextureView?

I hope you can fix my problem:
I have got a textureview to takes photos but when he capture photos, the file who need to contain the picture is empty. I don't know where and what is the problem. I just think that the problem is when the file is created. Thank you to help me.
This is a part of my code :
private void takePicture() throws CameraAccessException, IOException {
if(cameraDevice == null){
return;
}
CameraManager manager = (CameraManager) Objects.requireNonNull(getContext()).getSystemService(Context.CAMERA_SERVICE);
CameraCharacteristics characteristics = manager.getCameraCharacteristics(cameraDevice.getId());
Size[] jpegSizes = null;
jpegSizes = characteristics.get(CameraCharacteristics.SCALER_STREAM_CONFIGURATION_MAP).getOutputSizes(ImageFormat.JPEG);
int width = 640;
int height = 480;
if(jpegSizes!=null && jpegSizes.length>0){
width = jpegSizes[0].getWidth();
height = jpegSizes[0].getHeight();
}
ImageReader reader = ImageReader.newInstance(width,height, ImageFormat.JPEG, 1);
List<Surface> outputSurface = new ArrayList<>(2);
outputSurface.add(reader.getSurface());
outputSurface.add(new Surface(textureView.getSurfaceTexture()));
final CaptureRequest.Builder captureBuilder = cameraDevice.createCaptureRequest(CameraDevice.TEMPLATE_STILL_CAPTURE);
captureBuilder.addTarget(reader.getSurface());
captureBuilder.set(CaptureRequest.CONTROL_MODE,CameraMetadata.CONTROL_MODE_AUTO);
int rotation = Objects.requireNonNull(getActivity()).getWindowManager().getDefaultDisplay().getRotation();
captureBuilder.set(CaptureRequest.JPEG_ORIENTATION,ORIENTATIONS.get(rotation));
// First I get the path to gallery and crate new Album to my app
File file = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOCUMENTS);
mImageFolder = new File(file, "Fluico");
if (!mImageFolder.exists()) {
if (!mImageFolder.mkdirs()) {
Log.d("Fluicophoto", "failed to create directory");
}
}
/*Second I cut mFile = new File(getActivity().getExternalFilesDir(null), "pic.jpg");
from onActivityCreated and add here with the new path from my Album*/
#SuppressLint("SimpleDateFormat") String timestamp = new SimpleDateFormat("yyyyMMdd_HHmmss").format(new Date());
String prepend = "IMAGE_" + timestamp + "_";
file = File.createTempFile(prepend, ".jpg", mImageFolder);
Toast.makeText(getContext(), "file need to be save", Toast.LENGTH_SHORT).show();
ImageReader.OnImageAvailableListener readerListener = new ImageReader.OnImageAvailableListener() {
#Override
public void onImageAvailable(ImageReader reader) {
Image image = null;
image = reader.acquireLatestImage();
ByteBuffer buffer = image.getPlanes()[0].getBuffer();
byte[] bytes = new byte[buffer.capacity()];
buffer.get(bytes);
try {
save(bytes);
} finally {
image.close();
}
}
};
reader.setOnImageAvailableListener(readerListener,mBackgroundHandler);
final CameraCaptureSession.CaptureCallback captureListener = new CameraCaptureSession.CaptureCallback() {
#Override
public void onCaptureCompleted(CameraCaptureSession session, CaptureRequest request, TotalCaptureResult result) {
super.onCaptureCompleted(session, request, result);
Toast.makeText(getContext(), "saved", Toast.LENGTH_SHORT).show();
try{
createCameraPreview();
}catch (CameraAccessException e){
Toast.makeText(getContext(), "capture not comleted", Toast.LENGTH_SHORT).show();
e.printStackTrace();
}
}
};
cameraDevice.createCaptureSession(outputSurface, new CameraCaptureSession.StateCallback() {
#Override
public void onConfigured( CameraCaptureSession session) {
try {
session.capture(captureBuilder.build(), captureListener, mBackgroundHandler);
} catch (CameraAccessException e) {
e.printStackTrace();
Toast.makeText(getContext(), "capture not configured", Toast.LENGTH_SHORT).show();
}
}
#Override
public void onConfigureFailed( CameraCaptureSession session) {
}
},mBackgroundHandler);
}
private void save(byte[] bytes) {
OutputStream outputStream = null;
try {
outputStream = new FileOutputStream(file);
outputStream.write(bytes);
outputStream.close();
Toast.makeText(getContext(), "it's good", Toast.LENGTH_SHORT).show();
}catch (IOException e){
Toast.makeText(getContext(), "file not found", Toast.LENGTH_SHORT).show();
}
}
Try with below code:
File myDir;
String fname;
String id = "123456";
int count = 0;
String root = Environment.getExternalStorageDirectory().toString();
myDir = new File(root + "/PhotoApp/" + id);
myDir.mkdirs();
count++;
counter.setText(String.valueOf(count));
fname = "" + id + "-" + count + ".jpg";
File file = new File(myDir, fname);
if (file.exists()) file.delete();
This code will create a folder PhotoApp and inside the folder, all the images will store.
You can get full code with the camera in my GitHub:
Link: https://github.com/abhishekhzb/quick_camera

Android Save Video To Gallery

I am developing app using camera on fragment,so for camera I have used this library https://natario1.github.io/CameraView/home because I am using watermarks in camera, now I want to save pictures and videos to gallery, for pictures I have done with below code, for video I done research but not get a solution, for pictures this library is giving bitmap so pictures are saving perfectly but for video I can't figure out kindly help me.
Thank you
public class VideoPreviewActivity extends AppCompatActivity {
private VideoView videoView;
private static VideoResult videoResult;
private Button btnSaveVideo;
public static void setVideoResult(#Nullable VideoResult result) {
videoResult = result;
}
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_video_preview);
final VideoResult result = videoResult;
if (result == null) {
finish();
return;
}
btnSaveVideo = findViewById(R.id.save_video);
videoView = findViewById(R.id.video);
videoView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
playVideo();
}
});
AspectRatio ratio = AspectRatio.of(result.getSize());
MediaController controller = new MediaController(this);
controller.setAnchorView(videoView);
controller.setMediaPlayer(videoView);
videoView.setMediaController(controller);
videoView.setVideoURI(Uri.fromFile(result.getFile()));
videoView.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
#Override
public void onPrepared(MediaPlayer mp) {
ViewGroup.LayoutParams lp = videoView.getLayoutParams();
float videoWidth = mp.getVideoWidth();
float videoHeight = mp.getVideoHeight();
float viewWidth = videoView.getWidth();
lp.height = (int) (viewWidth * (videoHeight / videoWidth));
videoView.setLayoutParams(lp);
playVideo();
if (result.isSnapshot()) {
// Log the real size for debugging reason.
Log.e("VideoPreview", "The video full size is " + videoWidth + "x" + videoHeight);
}
}
});
//Click this button to save video
btnSaveVideo.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
//Calling 1st Method but not working
//SaveVideo(videoResult.getFile().toString());
//2nd method calling but still not working
saveVideoToInternalStorage(videoResult.getFile().toString());
}
});
}
void playVideo() {
if (!videoView.isPlaying()) {
videoView.start();
}
}
#Override
protected void onDestroy() {
super.onDestroy();
if (!isChangingConfigurations()) {
setVideoResult(null);
}
}
//first method which I tried but not working
private void SaveVideo(Uri f) {
//I don't know what data type I have to pass in the methods parameters
String root = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_MOVIES).getAbsolutePath();
File myDir = new File(root + "/Push Videos");
if (!myDir.exists()) {
myDir.mkdirs();
}
Random generator = new Random();
int n = 10000;
n = generator.nextInt(n);
String fname = "Video-"+ n +".mp4";
File file = new File (myDir, fname);
if (file.exists ())
file.delete ();
try {
FileOutputStream out = new FileOutputStream(file);
Toast.makeText(VideoPreviewActivity.this, "PUSH Video Saved", Toast.LENGTH_LONG).show();
out.flush();
out.close();
} catch (Exception e) {
e.printStackTrace();
}
}
//Tried this 2nd method but it is also not giving a desired result
//For saving Video...
private void saveVideoToInternalStorage (String filePath) {
File newfile;
try {
File currentFile = new File(filePath);
String fileName = currentFile.getName();
ContextWrapper cw = new ContextWrapper(getApplicationContext());
File directory = cw.getDir("videoDir", Context.MODE_PRIVATE);
newfile = new File(directory.getAbsolutePath(), fileName);
if(currentFile.exists()){
InputStream in = new FileInputStream(currentFile);
OutputStream out = new FileOutputStream(newfile);
// Copy the bits from instream to outstream
byte[] buf = new byte[1024];
int len;
while ((len = in.read(buf)) > 0) {
out.write(buf, 0, len);
}
scanner(filePath);
in.close();
out.close();
Log.v("", "Video file saved successfully.");
Toast.makeText(this, "Push Video Saved TO Gallery", Toast.LENGTH_SHORT).show();
}else{
Log.v("", "Video saving failed. Source file missing.");
}
} catch (Exception e) {
Log.d("Err ", "EXS " + e.getMessage());
e.printStackTrace();
}
}
}

Video Compression library in Java android? [closed]

Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
We don’t allow questions seeking recommendations for books, tools, software libraries, and more. You can edit the question so it can be answered with facts and citations.
Closed 1 year ago.
Improve this question
I am using Silicompressor library for video compression.
My video size is 15 MB and compressed video size is coming to 500 kb
since the compressed size is very very small and when clicked on play button of compressed video it shows an error as "Failed to play video."
How do I get a compressed size in MB?
Here is my code after compressing
File imageFile = new File(compressedFilePath);
float length = imageFile.length() / 1024f; // Size in KB
System.out.println("length = " + length);
String value;
if (length >= 1024)
value = length / 1024f + " MB";
else
value = length + " KB";
Any other alternative library which works well for video compression ?
you can use LightCompressor library
LightCompressor
call compressVideo class and pass to it the video path and the desired compressed video location
selectedVideo = data.getData();
compressVideo(getMediaPath(QabaelAdd.this,selectedVideo));
fpath=saveVideoFile(QabaelAdd.this,path).getPath(); //the compressed video location
private static File saveVideoFile(Context context, String filePath) throws IOException {
if (filePath != null) {
File videoFile = new File(filePath);
String videoFileName = "" + System.currentTimeMillis() + '_' + videoFile.getName();
String folderName = Environment.DIRECTORY_MOVIES;
if (Build.VERSION.SDK_INT < 30) {
File downloadsPath = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS);
File desFile = new File(downloadsPath, videoFileName);
if (desFile.exists()) {
desFile.delete();
}
try {
desFile.createNewFile();
} catch (IOException var61) {
var61.printStackTrace();
}
return desFile;
}
ContentValues var10 = new ContentValues();
boolean var11 = false;
boolean var12 = false;
var10.put("_display_name", videoFileName);
var10.put("mime_type", "video/mp4");
var10.put("relative_path", folderName);
var10.put("is_pending", 1);
ContentValues values = var10;
Uri collection = MediaStore.Video.Media.getContentUri("external_primary");
Uri fileUri = context.getContentResolver().insert(collection, values);
Void var10000;
if (fileUri != null) {
boolean var13 = false;
Closeable var18 = (Closeable)context.getContentResolver().openFileDescriptor(fileUri, "rw");
boolean var19 = false;
boolean var20 = false;
Throwable var73 = (Throwable)null;
try {
ParcelFileDescriptor descriptor = (ParcelFileDescriptor)var18;
if (descriptor != null) {
boolean var24 = false;
boolean var25 = false;
Closeable var28 = (Closeable)(new FileOutputStream(descriptor.getFileDescriptor()));
boolean var29 = false;
boolean var30 = false;
Throwable var74 = (Throwable)null;
try {
FileOutputStream out = (FileOutputStream)var28;
Closeable var33 = (Closeable)(new FileInputStream(videoFile));
boolean var34 = false;
boolean var35 = false;
Throwable var76 = (Throwable)null;
try {
FileInputStream inputStream = (FileInputStream)var33;
byte[] buf = new byte[4096];
while(true) {
int sz = inputStream.read(buf);
if (sz <= 0) {
Unit var77 = Unit.INSTANCE;
break;
}
out.write(buf, 0, sz);
}
} catch (Throwable var62) {
var76 = var62;
throw var62;
} finally {
//CloseableKt.closeFinally(var33, var76);
}
Unit var75 = Unit.INSTANCE;
} catch (Throwable var64) {
var74 = var64;
throw var64;
} finally {
//CloseableKt.closeFinally(var28, var74);
}
Unit var72 = Unit.INSTANCE;
} else {
var10000 = null;
}
} catch (Throwable var66) {
var73 = var66;
throw var66;
} finally {
//CloseableKt.closeFinally(var18, var73);
}
values.clear();
values.put("is_pending", 0);
context.getContentResolver().update(fileUri, values, (String)null, (String[])null);
return new File(QabaelAdd.getMediaPath(context, fileUri));
}
var10000 = (Void)null;
}
return null;
}
#NotNull
public static String getMediaPath(#NotNull Context context, #NotNull Uri uri) throws IOException {
Intrinsics.checkNotNullParameter(context, "context");
Intrinsics.checkNotNullParameter(uri, "uri");
ContentResolver resolver = context.getContentResolver();
String[] projection = new String[]{"_data"};
Cursor cursor = (Cursor)null;
String var30;
try {
File file;
String var57;
try {
cursor = resolver.query(uri, projection, (String)null, (String[])null, (String)null);
if (cursor != null) {
int columnIndex = cursor.getColumnIndexOrThrow("_data");
cursor.moveToFirst();
var57 = cursor.getString(columnIndex);
Intrinsics.checkNotNullExpressionValue(var57, "cursor.getString(columnIndex)");
} else {
var57 = "";
}
return var57;
} catch (Exception var53) {
String filePath = context.getApplicationInfo().dataDir + File.separator + System.currentTimeMillis();
file = new File(filePath);
InputStream var10000 = resolver.openInputStream(uri);
if (var10000 != null) {
Closeable var13 = (Closeable)var10000;
InputStream inputStream = (InputStream)var13;
Closeable var18 = (Closeable)(new FileOutputStream(file));
FileOutputStream outputStream = (FileOutputStream)var18;
byte[] buf = new byte[4096];
while(true) {
int var25 = inputStream.read(buf);
if (var25 <= 0) {
break;
}
outputStream.write(buf, 0, var25);
}
}
}
var57 = file.getAbsolutePath();
Intrinsics.checkNotNullExpressionValue(var57, "file.absolutePath");
var30 = var57;
} finally {
if (cursor != null) {
cursor.close();
}
}
return var30;
}
private void compressVideo(String path){
VideoCompressor.start(path,fpath , new CompressionListener() {
#Override
public void onStart() {
// Compression start
}
#Override
public void onSuccess() {
// On Compression success
Uri uploadUri = Uri.fromFile(new File(fpath));
Log.e("is dir", String.valueOf(new File(fpath).isDirectory()));
uploadVideoMethod(uploadUri); //upload the video
}
#Override
public void onFailure(String failureMessage) {
// On Failure
Log.e("fail", failureMessage);
Toast.makeText(QabaelAdd.this, "failed to compress video", Toast.LENGTH_LONG).show();
}
#Override
public void onProgress(float v) {
// Update UI with progress value
runOnUiThread(new Runnable() {
public void run() {
progressDialog.setMessage(" جاري تهيئة الفيديو "+String.valueOf(Math.round(v))+"%");
Log.e("progress", String.valueOf(v));
}
});
}
#Override
public void onCancelled() {
// On Cancelled
}
}, VideoQuality.MEDIUM, false, false);
}
Can you go with SiliCompressor. It's nice and simple library and give good result. I have used it.
Try to implement this. If you get any error let me know.
https://github.com/Tourenathan-G5organisation/SiliCompressor
Edit:
This way you can call the async task.
class VideoCompressAsyncTask extends AsyncTask<String, String, String> {
Context mContext;
public VideoCompressAsyncTask(Context context) {
mContext = context;
}
#Override
protected void onPreExecute() {
super.onPreExecute();
}
#Override
protected String doInBackground(String... paths) {
String filePath = null;
try {
filePath = SiliCompressor.with(mContext).compressVideo(paths[0], paths[1]);
} catch (URISyntaxException e) {
e.printStackTrace();
}
return filePath;
}
#Override
protected void onPostExecute(String compressedFilePath) {
super.onPostExecute(compressedFilePath);
File videoFile = new File(compressedFilePath);
}
}
Then now call it.
new VideoCompressAsyncTask(getActivity()).execute(selectedVideoPath, f.getPath());
selectedVideoPath is the video source path and f.getPath() is the destination path.
Try this way.

How to download gif images from url and save to storage in android

I want to add feature in my app to download a GIF Image from url to my phones storage.
How can I do this into my application
public class Download {
Context context;
String url;
ProgressDialog progressDailog;
public void saveImage(Context context, String url) {
this.context = context;
this.url = url;
progressDailog = new ProgressDialog(context);
progressDailog.setMax(100);
progressDailog.setMessage("Please wait...");
progressDailog.setProgressStyle(ProgressDialog.STYLE_SPINNER);
progressDailog.setCanceledOnTouchOutside(false);
progressDailog.show();
Glide.with(context).asBitmap()
.load(url)
.apply(new RequestOptions()
.diskCacheStrategyOf(DiskCacheStrategy.ALL)
.format(DecodeFormat.PREFER_ARGB_8888)
.override(Target.SIZE_ORIGINAL))
.into(new SimpleTarget<Bitmap>() {
#Override
public void onResourceReady(#NonNull Bitmap resource, #Nullable Transition<? super Bitmap> transition) {
progressDailog.dismiss();
storeImage(resource);
//Log.d(TAG, "Image : " + resource);
}
});
}
private void storeImage(Bitmap image) {
File pictureFile = getOutputMediaFile();
if (pictureFile == null) {
return;
}
try {
FileOutputStream fos = new FileOutputStream(pictureFile);
image.compress(Bitmap.CompressFormat.PNG, 100, fos);
fos.close();
Toast.makeText(context, "Image Downloaded", Toast.LENGTH_SHORT).show();
} catch (FileNotFoundException e) {
} catch (IOException e) {
}
}
private File getOutputMediaFile() {
File mediaStorageDir = new File(Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS) + "/Christmas"); /*getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS) + "/Christmas/c");*/
if (!mediaStorageDir.exists()) {
if (!mediaStorageDir.mkdirs())
return null;
}
File mediaFile;
mediaFile = new File(mediaStorageDir.getPath() + File.separator + "IMG_MERRY_CHRISTMAS.jpg");
return mediaFile;
}
}
From this code I can download the normal Image but it did not works on GIF. The GIF image downloaded and it remains static
This snippet will help you to download gif using GLIDE
Glide.with(context)
.download(url)
.listener(new RequestListener<File>() {
#Override
public boolean onLoadFailed(#Nullable GlideException e, Object model, Target<File> target, boolean isFirstResource) {
progressDailog.dismiss();
Toast.makeText(context, "Error saving", Toast.LENGTH_SHORT).show();
return false;
}
#Override
public boolean onResourceReady(File resource, Object model, Target<File> target, DataSource dataSource, boolean isFirstResource) {
progressDailog.dismiss();
try {
saveGifImage(context, getBytesFromFile(resource), createName(url));
} catch (IOException e) {
e.printStackTrace();
}
return true;
}
}).submit();
createName function
public String createName(String url) {
String name = url.substring( url.lastIndexOf('/')+1, url.length());
String NoExt = name.substring(0, name.lastIndexOf('.'));
if(!ext.equals(".gif")){
name = NoExt + ".jpg";
}
return name;
}
getBytesFromFile function
public byte[] getBytesFromFile(File file) throws IOException {
long length = file.length();
if (length > Integer.MAX_VALUE) {
throw new IOException("File is too large!");
}
byte[] bytes = new byte[(int) length];
int offset = 0;
int numRead = 0;
InputStream is = new FileInputStream(file);
try {
while (offset < bytes.length
&& (numRead = is.read(bytes, offset, bytes.length - offset)) >= 0) {
offset += numRead;
}
} finally {
is.close();
}
if (offset < bytes.length) {
throw new IOException("Could not completely read file " + file.getName());
}
return bytes;
}
saveGifImage function
public void saveGifImage(Context context, byte[] bytes, String imgName ) {
FileOutputStream fos = null;
try {
File externalStoragePublicDirectory = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES);
File customDownloadDirectory = new File(externalStoragePublicDirectory, "Merry_Christmas");
if (!customDownloadDirectory.exists()) {
boolean isFileMade = customDownloadDirectory.mkdirs();
}
if (customDownloadDirectory.exists()) {
File file = new File(customDownloadDirectory, imgName);
fos = new FileOutputStream(file);
fos.write(bytes);
fos.flush();
fos.close();
if (file != null) {
ContentValues values = new ContentValues();
values.put(MediaStore.Images.Media.TITLE, file.getName());
values.put(MediaStore.Images.Media.DISPLAY_NAME, file.getName());
values.put(MediaStore.Images.Media.DESCRIPTION, "");
values.put(MediaStore.Images.Media.MIME_TYPE, "image/gif");
values.put(MediaStore.Images.Media.DATE_ADDED, System.currentTimeMillis());
values.put(MediaStore.Images.Media.DATE_TAKEN, System.currentTimeMillis());
values.put(MediaStore.Images.Media.DATA, file.getAbsolutePath());
ContentResolver contentResolver = context.getContentResolver();
contentResolver.insert(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, values);
Toast.makeText(context, "Image saved to " + file.getAbsolutePath(), Toast.LENGTH_SHORT).show();
}
}
} catch (Exception e) {
e.printStackTrace();
}
}
For getting GIF using Glide:
Glide.with(MainActivity.this).asFile()
.load(url)
.apply(new RequestOptions()
.format(DecodeFormat.PREFER_ARGB_8888)
.override(Target.SIZE_ORIGINAL))
.into(new Target<File>() {
#Override
public void onStart() {
}
#Override
public void onStop() {
}
#Override
public void onDestroy() {
}
#Override
public void onLoadStarted(#Nullable Drawable placeholder) {
}
#Override
public void onLoadFailed(#Nullable Drawable errorDrawable) {
}
#Override
public void onResourceReady(#NonNull File resource, #Nullable Transition<? super File> transition) {
storeImage(resource);
}
#Override
public void onLoadCleared(#Nullable Drawable placeholder) {
}
#Override
public void getSize(#NonNull SizeReadyCallback cb) {
}
#Override
public void removeCallback(#NonNull SizeReadyCallback cb) {
}
#Override
public void setRequest(#Nullable Request request) {
}
#Nullable
#Override
public Request getRequest() {
return null;
}
});
For Saving Image:
private void storeImage(File image) {
File pictureFile = getOutputMediaFile();
if (pictureFile == null) {
return;
}
try {
FileOutputStream output = new FileOutputStream(pictureFile);
FileInputStream input = new FileInputStream(image);
FileChannel inputChannel = input.getChannel();
FileChannel outputChannel = output.getChannel();
inputChannel.transferTo(0, inputChannel.size(), outputChannel);
output.close();
input.close();
Toast.makeText(MainActivity.this, "Image Downloaded", Toast.LENGTH_SHORT).show();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
private File getOutputMediaFile() {
File mediaStorageDir = new File(Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS) + "/Christmas"); /*getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS) + "/Christmas/c");*/
if (!mediaStorageDir.exists()) {
if (!mediaStorageDir.mkdirs())
return null;
}
File mediaFile;
mediaFile = new File(mediaStorageDir.getPath() + File.separator + "IMG_MERRY_CHRISTMAS_"+Calendar.getInstance().getTimeInMillis() +".gif");
return mediaFile;
}
Glide can get File, worked with me:
Glide.with(context).asFile()
.load(url)
.apply(new RequestOptions()
.diskCacheStrategyOf(DiskCacheStrategy.ALL)
.format(DecodeFormat.PREFER_ARGB_8888)
.override(Target.SIZE_ORIGINAL))
.into(new SimpleTarget<File>() {
#Override
public void onResourceReady(#NonNull File resource, #Nullable Transition<? super File> transition) {
progressDailog.dismiss();
storeImage(resource);
//Log.d(TAG, "Image : " + resource);
}
});

Monitoring BufferedInputStream download progress

I'm trying to download a file using an AsyncTask on Android. I want to display a ProgressDialog which should have a progress bar to show the status of the download. I'm using the onProgressUpdate() function for that and implemented a call to publishProgress() in my doInBackground() function. However, the progress dialog only pops up after downloading the file. My code:
protected Long doInBackground(URL...urls) {
for (int i = 0; i < urls.length; i++) {
url = urls[i];
try {
URLConnection conn = url.openConnection();
conn.connect();
totalSize = conn.getContentLength();
BufferedInputStream bis = new BufferedInputStream(url.openStream());
FileOutputStream fos = new FileOutputStream(Environment.getExternalStorageDirectory().getPath() + "/forvo_temp.mp3");
BufferedOutputStream bos = new BufferedOutputStream(fos,1024);
byte [] data = new byte[1024];
int x=0; int c=0;
while((x=bis.read(data,0,1024))>=0){
bos.write(data,0,x);
c += 1024;
publishProgress(c);
}
} catch (Exception e) {
e.printStackTrace();
}
}
return 0L; // Don't know what to do with this
}
protected void onProgressUpdate(Integer...args) {
pd = ProgressDialog.show(context, "Downloading...", "Downloading...", true, false);
pd.setProgress(args[0] / totalSize);
}
I guess the whole file is downloaded when I call new BufferedInputStream(url.openStream()). How can I monitor the download progress?
Wrap URL input stream with you own InputStream that just reads bytes and "monitors" the status, e.g. sends notifications.
It is simple: InputStream is an abstract class with only one abstract method:
public abstract int read() throws IOException;
In your case it should read bytes from stream that it wraps.
public class NotifcationInputStream extends InputStream {
private InputStream in;
private int count;
private Collection<ByteListener> listeners = new ArrayList<ByteListener>();
NotificationInputStream(InputStream in) {
this.in = in;
}
public int read() throws IOException {
int b = in.read();
byteReceived(b);
return b;
}
public void addListener(ByteListener listener) {
listeners.add(listener);
}
private void byteReceived(int b) {
for (ByteListener l : listeners) {
l.byteReceived(b, ++count);
}
}
}
public interface ByteListener extends EventListener {
public void byteReceived(int b, int count);
}
The problem here is how to show the process bar: you have to know total number of bytes. You can get it from HTTP header content-length if your resource is static. Otherwise you need appropriate server support or heuristics.
This code is useful showing download items totol size and downloaded size.
private static final int DOWNLOAD_ONPROGRESS = 1;
#Override
protected Dialog onCreateDialog(int id) {
switch (id) {
case DOWNLOAD_ONPROGRESS:
progressDialog = new ProgressDialog(this);
progressDialog.setMessage("Downloading latest ...");
progressDialog.setCancelable(true);
progressDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
try {
progressDialog.show();
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return progressDialog;
default:
return null;
}
}
You can use AsyncTask for downloading the version in background.
private class DownLoad extends AsyncTask<String, String, String> {
#Override
protected void onPreExecute() {
// TODO Auto-generated method stub
super.onPreExecute();
logger.info("LoadDataAsync onPreExecute");
showDialog(DOWNLOAD_ONPROGRESS);
}
#Override
protected String doInBackground(String... aurl) {
int count = 0;
try {
URL url = new URL(aurl[0]);
URLConnection urlConnection = url.openConnection();
urlConnection.connect();
int contentlength = urlConnection.getContentLength();
progressDialog.setMax(contentlength);
String PATH = "";
File file = null;
if (android.os.Environment.getExternalStorageState().equals(
android.os.Environment.MEDIA_MOUNTED)) {
PATH = Environment.getExternalStorageDirectory()
+ "/download/";
file = new File(PATH);
file.mkdirs();
File outputFile = new File(file, "telfaz.apk");
OutputStream fos = new FileOutputStream(outputFile);
InputStream is = new BufferedInputStream(url.openStream());
byte[] buffer = new byte[1024];
long len1 = 0;
while ((count = is.read(buffer)) != -1
&& !downLoad.isCancelled()) {
len1 += count;
publishProgress("" + len1);
fos.write(buffer, 0, count);
}
fos.flush();
fos.close();
is.close();
}
logger.info("Success -> file downloaded succesfully. returning 'success' code");
return Util.APK_DOWNLOAD_SUCCESS;
} catch (IOException e) {
logger.error("Exception in update process : "
+ Util.getStackTrace(e));
}
logger.info("Failed -> file download failed. returning 'error' code");
return Util.APK_DOWNLOAD_FAILED;
}
#Override
protected void onPostExecute(String result) {
logger.info("on DownLoad onPostExecute. result : " + result);
progressDialog.dismiss();
removeDialog(DOWNLOAD_ONPROGRESS);
if (result.equalsIgnoreCase(Util.APK_DOWNLOAD_SUCCESS)) {
Update();
} else {
Toast.makeText(DownloadAllContentsActivity.this,
getString(R.string.updateApplicationFailed),
Toast.LENGTH_LONG).show();
loadDataAsync.execute();
}
}
#Override
protected void onProgressUpdate(String... values) {
if (values != null && values.length > 0) {
progressDialog.setProgress(Integer.parseInt(values[0]));
}
}
}

Categories

Resources