Here is my code:--
public class grabber extends Activity
{
int counter;
String folderPath;
String[] array;
DownloadManager dm;
private long enqueue;
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.data);
Down t = new Down();
t.execute();
}
private class Down extends AsyncTask<String, Void, String>
{
protected String doInBackground(String... params)
{
Log.i("grabber", "in back");
String w =Environment.getExternalStorageDirectory().getAbsoluteFile()+"/Android/data/myfolder";
createdir(w);
String link = "http://mywebsitehere.com";
Document doc;
array = new String[200];
try {
doc = Jsoup.connect(link).get();
String title = doc.title();
folderPath = w+ File.separator+title;
createdir(folderPath);
Elements images = doc.select("img[src~=(?i)\\.(png|jpe?g|gif)]");
counter =0;
for (Element image : images)
{
String img = image.attr("src");
array[counter]=img;
counter++;
}
} catch (IOException e)
{
// TODO Auto-generated catch block
e.printStackTrace();
}
return null;
}
protected void onPostExecute(String result)
{
Toast.makeText(getApplicationContext(),
"done", Toast.LENGTH_SHORT).show();
for(int i=0;i<counter;i++)
{
dm = (DownloadManager) getSystemService(DOWNLOAD_SERVICE);
Request request = new Request(
Uri.parse(array[i]));
request.setDescription("Android Data download using DownloadManager.");
request.setDestinationInExternalFilesDir(getApplicationContext(),folderPath,File.separator+"pic"+Integer.toString(i)+".jpg");
enqueue = dm.enqueue(request);
}
}
}
public void createdir(String Path)
{
File file = new File(Path);
if(!file.exists())
{
file.mkdirs();
}
}
}
What it should do:-
It should download the given links, which contains images, to the given path.
What it does:-
The app is running quite fine, my UI is not hanging. After a few second "done" Toast is shown, which means theasynctask is completed and we are at onPostExecute. But when I check the dir I am seeing that there is no folder inside Android/data/myfolder.
The main setback is that some times it works, i.e. the images are downloaded and sometimes not.
So I am guessing maybe its because of some http timeout or some error which I am not handling correctly because I am using createdir(folderPath); after Jsoup and maybe the error is happening there so no folder is getting created there.
Any Ideas!?? Thanks in Advance.
Edit:-
I am getting SocketTimeoutException during jsoup.connect(link).get();
You have to add the following permission to the manifest of your application, to write to the external storage.
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
I hope you did this?
Finally I did it with some trial and error.
We can use timeout option here to reduce the Sockettimeoutexception by changing
doc = Jsoup.connect(link).get();
to
doc = Jsoup.connect(link).timeout(10000).get();
And there is still one other error, thats to remove the Toast message in the onPostExecute as we cannot interact without handler from background task to UI.
That's it.
Related
i am trying to download a hls file using the HLSDownloader, but i am not getting the best results yet. My code:
// Main download function
AsyncTask<Void, Void, Void> asyncTask = new AsyncTask<Void, Void, Void>() {
#Override
protected Void doInBackground(Void... voids) {
downloadHls(VIDEO_URL);
return null;
}
};
asyncTask.execute();
...
// This is the main tool to download hls
private HlsDownloader hlsDownloader;
private void downloadHls(String masterHLS) {
hlsDownloader = getHlsDownloader(masterHLS);
try {
hlsDownloader.download(this);
} catch (IOException e) {
e.printStackTrace();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
private HlsDownloader getHlsDownloader(String mediaPlaylistUri) {
File downloadFolder = new File(getFilesDir(), "video_id_2");
SimpleCache cache = new SimpleCache(downloadFolder, new NoOpCacheEvictor());
DefaultHttpDataSourceFactory factory = new DefaultHttpDataSourceFactory("ExoPlayer", null);
CacheDataSource cacheDataSource =
new CacheDataSource(cache, factory.createDataSource(), CacheDataSource.FLAG_BLOCK_ON_CACHE);
// Create a downloader for the first variant in a master playlist.
return new HlsDownloader(
Uri.parse(mediaPlaylistUri), new DownloaderConstructorHelper(cache, factory));
}
It seems the download starts and i am getting the progress of the downloading, but i can not access the downloaded file (maybe not exists), so i do not know if i am coding well. Some help it would be appreciated.
EDITED:
Currently i've got the download in multiple chunks (i forgotten to add the write permission in the manifest) all named like *.ve.exo extension files, but i do not know how to play them, any idea?
Hi Iam having serious issues try to persist some serializable objects to a file on the local android file system. Iam getting a Bad file descriptor error and I think it is to do with my methods for creating the file. the file and checking if the file exists. i create a private file object in the class. Then, on write or read. I check file existance with the following code.
#Override
public boolean fileExists() {
File file = context.getFileStreamPath(filename);
return file.exists();
}
this doesnt instantiate my file object called "objectfile"!! but does check the "filename" exists.
to create the file I call this method if "filename" doesnt exist.
public void createFile()
{
objectfile = new File(context.getFilesDir(), filename);
objectfile.setReadable(true);
objectfile.setWritable(true);
}
Iam not sure if this will give me back my previously created file which would be ideally what I want to do. Is there a way i can just get the old file or create a new one and pass it to "objectfile" variable in the constructor??
Iam also wondering what the best way to do this is??
Or should i just use the mysqlite db? using object file persistance doesn't seem to be working out for me right now and iam working to a deadline. Also this method is mention in the gooogle docs so I thought it would be legit was to do it.
http://developer.android.com/training/basics/data-storage/files.html
here is my method for reading the serializable objects
public synchronized ArrayList<RoomItem> readObjects() {
final ArrayList<RoomItem> readlist = new ArrayList<>();
if(!fileExists())
return readlist;
if(objectfile == null)
createFile();
try {
finputstream = new FileInputStream(objectfile);
instream = new ObjectInputStream(finputstream);
readwritethread = new Thread(new Runnable() {
#Override
public void run() {
try {
final ArrayList<RoomItem> readitems = (ArrayList<RoomItem>) instream.readObject();
instream.close();
finputstream.close();
handler.post(new Runnable() {
#Override
public void run() {
listener.updateList(readitems);
}
});
} catch(IOException e)
{
e.printStackTrace();
}
catch(ClassNotFoundException e)
{
e.printStackTrace();
Log.d("read failed", "file read failed");
}
}
});
}
catch(Exception e)
{
e.printStackTrace();
}
timeOutReadWrite(readwritethread);
readwritethread.start();
try {
readwritethread.join();
} catch (InterruptedException e) {
e.printStackTrace();
}
Log.d("read from file", "file read");
return readlist;
if anyone could suggest any improvements id really appreciate it. I use a handler to pass back to my activity and implement a listener interface on my activity thats call the activity when all the obj are read. Thanks again!
1#: Yes, it will return the original file you created.
2#: Depends on the thing you want to store, seems File is more flex from description
hope helpful.
We have used
FileOutputStream fos = context.openFileOutput("file.ser", Context.MODE_PRIVATE);
to write our serialized files.This will carete files in /data/data/app.package.name/files/. In fact, this path is returned by getFilesDir().
And while deserializing, use
//make sure you pass the same file that was passed to openFileOutput()..
FileInputStream fis = context.openFileInput("file.ser");
Also, to avoid confusing between file names you can use name of class that is being serialized.
Ex:
public static <T> void serialize(final Context context, final T objectToSerialize) {
....
....
Strin fileName = objectToSerialize.getClass().getSimpleName();
...
}
Do this and keep the method in util so it can be used for any type of objects (T type) to serialize.
I'm programming an app with my brother, and today unfortunately, I encountered with a problem.
When the app load a php page via my asynctask class it works fine. but I would like to program this situation: if the remote server is down, or crash, and doesnt display the right page, the application will show error message. but instead, the app crashes =[
I tried to load this page, for example:
http://alonadoni.com/sql3.php
(I want to simulate that there is a problem with the server. the regular page is sql2.php and it works fine when the server works)
When the app try to load this page (sql3.php) , the app crashes.
I did another experiment : I created a file sql3.php, and wrote "aaaaaaaa" in the page, the app doesn't crash in this situation. it downloaded the data "aaaaa". in this case, the app show jsonexecption error.
Unfortunately, I can't get logcat because my old computer can't run emulators, and my phone also can't connect to my computer on developer mode =[ When I try application I create an apk then transfer the file to my phone and install.
my code is:
in OnCreate:
String serverURL = sss() + "sql3.php?imei=" + imei;
new LongOperation().execute(serverURL);
outside OnCreate:
private class LongOperation extends AsyncTask<String, Void, Void> {
private final HttpClient Client = new DefaultHttpClient();
private String Error = null;
protected void onPreExecute() {
}
protected Void doInBackground(String... urls) {
try {
HttpGet httpget = new HttpGet(urls[0]);
ResponseHandler<String> responseHandler = new BasicResponseHandler();
data[x] = Client.execute(httpget, responseHandler);
} catch (ClientProtocolException e) {
Error = e.getMessage();
Toast.makeText(getApplicationContext(),"error2" , Toast.LENGTH_LONG).show();
cancel(true);
} catch (IOException e) {
Error = e.getMessage();
Toast.makeText(getApplicationContext(),"error34" , Toast.LENGTH_LONG).show();
cancel(true);
}
return null;
}
public void onPostExecute(Void unused) {
if (Error != null) {
} else {
try {
JSONObject json = new JSONObject(data[x]);
name = json.getString("name");
} catch (JSONException e) {
Toast.makeText(getApplicationContext(),"e" + e, Toast.LENGTH_LONG).show();
}
}
x++;
}
}
DoInBackground of asynctask needs to contain only NON UI work , hence referring to context and performing UI operations in UI thread may cause crash.
You can perform UI operations in postexecute of asynctask.
Hence Removing toast from above code which refers to UI operation will solve your issue
In an Android application, I have a list of image URLs like this:
List<String> urls = new ArrayList<String>(100);
urls.add("http://www.example.org/1.jpg");
urls.add("http://www.example.org/2.png");
urls.add("http://www.example.org/3.jpg");
urls.add("http://www.example.org/4.jpg");
urls.add("http://www.example.org/5.png");
urls.add("http://www.example.org/6.png");
urls.add("http://www.example.org/7.png");
urls.add("http://www.example.org/8.jpg");
urls.add("http://www.example.org/9.jpg");
urls.add("http://www.example.org/10.gif");
...
urls.add("http://www.example.org/100.jpg");
Now I have to get the filesize and MIME type for all of these URLs, and this should be done as fast as possible, of course.
What I did is the following:
for (String url : urls) {
int fileSize;
try {
URLConnection urlConnection;
urlConnection = new URL(url).openConnection();
urlConnection.connect();
final String mimeType = urlConnection.getContentType();
final int fileSize = urlConnection.getContentLength();
// do something with those two pieces of information
}
catch (MalformedURLException e) {
continue;
}
catch (IOException e) {
// some special handling
}
}
But this is terribly slow. This is because it is using a single thread and requesting the URLs one by one, while a web browser would always access multiple files at a time, isn't it?
So how can I make it faster?
For HttpClient, I've read that you should re-use instances and there are some ways to use them in a multi-threaded environment.
But how would I do this with URLConnection or any other class that gives you filesize and MIME type?
Edit:
The images are not all on the same host, but spread across only a few servers, say 100 images spread across 5 host names.
Can you use a few threads or run several AsynTasks at once that do the job? Is there anything you have to pay attention to, such as recycling URLConnection objects or so?
I'm not quite sure how to use multiple threads to share task list (100 image files) and merge the results (MIME types and file sizes) afterwards. Can you help?
Split your work up into smaller peaces and let a worker Thread handle it:
The worker Thread:
public class Downloader extends Thread {
private final String mUrl;
private String mMimeType;
private int mFileSize;
public Downloader(String url) {
mUrl = url;
}
#Override
public void run() {
try {
URLConnection urlConnection;
urlConnection = new URL(mUrl).openConnection();
urlConnection.connect();
mMimeType = urlConnection.getContentType();
mFileSize = urlConnection.getContentLength();
} catch (IOException e) {
e.printStackTrace();
}
}
public String getMimeType() {
return mMimeType;
}
public int getFileSize() {
return mFileSize;
}
}
Instantiate, run and wait for the worker:
ArrayList<String> urls = new ArrayList<String>(10);
// ...
ArrayList<Thread> threads = new ArrayList<Thread>(10);
for (String url : urls) {
Thread t = new Downloader(url);
threads.add(t);
t.start();
}
for (Thread t : threads) {
try {
// do not wait for other threads in main UI thread!
t.join();
//((Downloader) t).getMimeType();
//((Downloader) t).getFileSize();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
Make sure to note wait for the worker Thread in your UI Thread.
The answer above should only be used for a small set of URLs. A ThreadPool may not be necessary because the Threads will wait for IO most of the time.
Here is your requested answer with a ThreadPool.
It's using the same Downloader class as the above example with only one change:
Spawning Threads is done by the ThreadPool and the single tasks don't need to be a real Thread anymore. So let the Downloader implement a Runnable instead of extending a Thread:
public class Downloader implements Runnable {
Hopefully it's what you are looking for.
public class ThreadedDownloader {
private static final int KEEP_ALIVE_TIME = 1;
private static final TimeUnit KEEP_ALIVE_TIME_UNIT = TimeUnit.SECONDS;
private static int NUMBER_OF_CORES = Runtime.getRuntime().availableProcessors();
private LinkedBlockingQueue<Runnable> mDecodeWorkQueue = new LinkedBlockingQueue<Runnable>();
private ThreadPoolExecutor mDecodeThreadPool = new ThreadPoolExecutor(NUMBER_OF_CORES,
NUMBER_OF_CORES, KEEP_ALIVE_TIME, KEEP_ALIVE_TIME_UNIT, mDecodeWorkQueue) {
#Override
protected void afterExecute(Runnable r, Throwable t) {
super.afterExecute(r, t);
Downloader d = (Downloader) r;
// do something with finished Downloader d
// like saving it's result to some sort of list
// d.getMimeType();
// d.getFileSize();
if (mDecodeWorkQueue.isEmpty()) {
onAllDownloadsFinised();
}
}
};
/** Download a list of urls and check it's mime time and file size. */
public void download(List<String> urls) {
for (String url : urls) {
mDecodeThreadPool.execute(new Downloader(url));
}
}
/** Calles when all downloads have finished. */
private void onAllDownloadsFinised() {
// do whatever you want here
// update UI or something
}
}
I don't have example Code, but the HTTP verb HEAD is what you're looking for. It retrieves the headers (including mime and content-length) without transferring the content body.
This answer goes into more detail about what HEAD does.
I think you have most, if not all of the pieces to your solution in the answers already submitted.
Here's what I'd do:
1) make the head requests using Executors.newCachedThreadPool();
2) store the responses in a Map
3) create a payload Map
4) load the real images using AsyncTask instances
5) when each bitmap load completes, store the results in the payload map
Just my thoughts.
I'm not really sure what goes wrong with my code or structure. I wanted to use AsyncTask to download images and display out the progress bar at the mean time. But I tried out a few different way of doing it. It still failed and no idea what's wrong with it. My structure flow is
ContentID is a string array that stores the content ID of the Images.
Primary Issue: It managed to download images from the url and store into the phone, but the downloaded images are all the same image. It should be different images, it's not what I expected.
Secondary Issue: The progress bar pop up while the application downloading images, but the progress bar did not update it's progress. It just remains 0% and dismissed after the download completed.
I wanted to know what causes primary and secodary issue as i mentioned. Please leave a comment or answer if you might know what's wrong with my code. Any help will be appreciated.
if(isSyncSuccess){
SetConstant.IMAGE_EXIST = 1;
pDialog = new ProgressDialog(GalleryScreen.this);
pDialog.setMessage("Downloading file. Please wait...");
pDialog.setIndeterminate(false);
pDialog.setProgress(0);
pDialog.setMax(contentId.length);
pDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
pDialog.setCancelable(true);
if (contentId.length>0){
Log.i(TAG, "contentid.length:" +contentId.length);
for (int i=0;i<contentId.length;i++){
if(helper.databaseChecking(useremail, contentId[i])){
contentdownload = i;
SetConstant.CONTENT_ID = contentId[i];
String URL = SetConstant.URL_DOWNLOAD_CONTENT+contentId[i];
DownloadFile downloadFile = new DownloadFile();
downloadFile.execute(URL);
}
private class DownloadFile extends AsyncTask<String, Integer, String>{
#Override
protected String doInBackground(String... sUrl){
Bitmap bm;
InputStream in;
try{
in = new java.net.URL(sUrl[0]).openStream();
bm = BitmapFactory.decodeStream(new PatchInputStream(in));
File storage = new File(Environment.getExternalStorageDirectory() + File.separator + "/Image/");
Log.i(TAG,"storage:" +storage);
Log.i(TAG,"storage:" +storage.getAbsolutePath());
if(!storage.exists()){
storage.mkdirs();
}
String FileName = "/"+SetConstant.CONTENT_ID+".jpg";
FileOutputStream fos = new FileOutputStream(storage + FileName);
bm.compress(Bitmap.CompressFormat.JPEG, 85, fos);
String filepath = storage + FileName;
File filecheck = new File (filepath);
long fileSize = filecheck.length();
fos.flush();
fos.close();
Log.i(TAG, "bm:" +bm);
Log.i(TAG, "fos:" +fos);
Log.i(TAG, "filesize:" +fileSize);
Log.i(TAG, "filepath:" +filepath);
}
catch(IOException e1){
e1.printStackTrace();
}
return null;
}
#Override
protected void onPreExecute(){
super.onPreExecute();
pDialog.show();
}
#Override
protected void onProgressUpdate(Integer... progress){
super.onProgressUpdate(progress);
pDialog.setProgress(progress[0]);
}
protected void onPostExecute(String result){
super.onPostExecute(result);
pDialog.dismiss();
}
}
Edit
Now the application able to download images according and the progress bar is working as well! But I got another issue is how to return error message when the application failed to complete the download. Currently when the application failed to download it will crash. I believed that I should not run it inside the doInBackground side. But where else can I do the checking? Any idea how to return as an error message and request for the user to retry instead of crashing the application?
You never called onProgressUpdate during your doInBackGround(...). Please note that running multiple instances of AsyncTask is a bad idea. Here is what I suggest:
if(isSyncSuccess){
SetConstant.IMAGE_EXIST=1;
pDialog=new ProgressDialog(GalleryScreen.this);
pDialog.setMessage("Downloading file. Please wait...");
pDialog.setIndeterminate(false);
pDialog.setProgress(0);
pDialog.setMax(contentId.length);
pDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
pDialog.setCancelable(true);
new DownloadFile().execute();
}
private class DownloadFiles extends AsyncTask<String, Integer, String> {
#Override
protected String doInBackground(String... sUrl) {
Bitmap bm;
InputStream in;
if (contentId.length > 0) {
for (int i = 0; i < contentId.length; i++) {
if (helper.databaseChecking(useremail, contentId[i])) {
contentdownload = i;
SetConstant.CONTENT_ID = contentId[i];
String URL = SetConstant.URL_DOWNLOAD_CONTENT + contentId[i];
//YOUR INTRESTING LOOP HERE.
publishProgress(30);
//SOME INTRESTING NUMBER FOR PROGRESS UPDATE
}
}
try {
in = new java.net.URL(sUrl[0]).openStream();
bm = BitmapFactory.decodeStream(new PatchInputStream(in));
File storage = new File(Environment.getExternalStorageDirectory() + File.separator + "/Image/");
Log.i(TAG, "storage:" + storage);
Log.i(TAG, "storage:" + storage.getAbsolutePath());
if (!storage.exists()) {
storage.mkdirs();
}
String FileName = "/" + SetConstant.CONTENT_ID + ".jpg";
FileOutputStream fos = new FileOutputStream(storage + FileName);
bm.compress(Bitmap.CompressFormat.JPEG, 85, fos);
String filepath = storage + FileName;
File filecheck = new File(filepath);
long fileSize = filecheck.length();
fos.flush();
fos.close();
} catch (IOException e1) {
e1.printStackTrace();
}
return null;
}
#Override
protected void onPreExecute () {
super.onPreExecute();
pDialog.show();
}
#Override
protected void onProgressUpdate (Integer...progress){
super.onProgressUpdate(progress);
pDialog.setProgress(progress[0]);
}
protected void onPostExecute (String result){
super.onPostExecute(result);
pDialog.dismiss();
}
}
}
Of course this code don't run and you need to fix the scopes. But what I am trying to suggest is that your loop should be in doInBackGround(...), you should only have 1 instance of AsyncTask at given time for this case, and call the onProgressUpdate().
Primary issue :
SetConstant.CONTENT_ID = contentId[i];
String URL = SetConstant.URL_DOWNLOAD_CONTENT+contentId[i];
Here, you are facing trouble. As #Sofi Software LLC's answer, you are using a global variable, whose value is being changed by the main thread, in another thread.
Secondary Issue :
If you want a progress bar to update, you have to update its value;
it doesn't update itself.
You do need to download the image in AsyncTask (Downloading from URL). Effectively to achieve your functionality, you need to do
Create AsyncTask to download your image (implement download in
doInBackground()), also have a boolean (say isImageDownloaded) to
track if the image is successfully downloaded in postExecute().
Don't forget to also show your progress bar before initiating the
download
Execute your AsyncTask to initiate download
Create extension of android.os.CountDownTimer to countdown a minimum
time
On the method onFinish() check the boolean that you track, if it is
false then you cancel the AsyncTask and throw the toast/dialog that
you intended
Running multipule instance of AsyncTask is not a good idea, so do one after another. You can execute your AsyncTask's on an Executor using executeOnExecutor().To make sure that the threads are running in a serial fashion please use: SERIAL_EXECUTOR.
Following resources may help you #
If you need to download an image, show progress bar and load in a imageview
https://github.com/koush/UrlImageViewHelper
http://developer.aiwgame.com/imageview-show-image-from-url-on-android-4-0.html
http://blog.blundell-apps.com/imageview-with-loading-spinner/
If you need to download multiple files (here, for images) using AsyncTask
Problem with downloading multiple files using AsyncTask
How to get back the task completion status in AsyncTask
Implement Progress Bar for File Download in Android
EDIT:
From http://developer.aiwgame.com/imageview-show-image-from-url-on-android-4-0.html
new DownloadImageTask((ImageView) findViewById(R.id.imageView1))
.execute("http://java.sogeti.nl/JavaBlog/wp-content/uploads/2009/04/android_icon_256.png"); }
public void onClick(View v) {
startActivity(new Intent(this, IndexActivity.class));
finish();
}
private class DownloadImageTask extends AsyncTask<String, Void, Bitmap> {
ImageView bmImage;
public DownloadImageTask(ImageView bmImage) {
this.bmImage = bmImage;
}
protected Bitmap doInBackground(String... urls) {
String urldisplay = urls[0];
Bitmap mIcon11 = null;
try {
InputStream in = new java.net.URL(urldisplay).openStream();
mIcon11 = BitmapFactory.decodeStream(in);
} catch (Exception e) {
Log.e("Error", e.getMessage());
e.printStackTrace();
}
return mIcon11;
}
protected void onPostExecute(Bitmap result) {
bmImage.setImageBitmap(result);
} }
From Image download in an Android ImageView and Progressbar implementation
// note that you could also use other timer related class in Android aside from this CountDownTimer, I prefer this class because I could do something on every interval basis
// tick every 10 secs (or what you think is necessary)
CountDownTimer timer = new CountDownTimer(30000, 10000) {
#Override
public void onFinish() {
// check the boolean, if it is false, throw toast/dialog
}
#Override
public void onTick(long millisUntilFinished) {
// you could alternatively update anything you want every tick of the interval that you specified
}
};
timer.start()
In the following line:
SetConstant.CONTENT_ID = contentId[i];
You're setting a global variable to a value, then you create a string url based on that same value and pass it to the AsyncTask. That executes, and then when it is done downloading, it create a file whose name is based on the global variable SetConstant.CONTENT_ID.
In other words, you are using a global variable, whose value is being changed by the main thread, in another thread. Don't do this, as you will get all kinds of weird problems due to the different threads updating at different times.. Pass in the value or the name of the output file to the AsyncTask. You can do that in a constructor for DownloadFile, and stash the value in a field.
If you want a progress bar to update, you have to update its value; it doesn't update itself. Call AsyncTask.publishProgress during the task (in doInBackground) and implement onProgressUpdate to update the progress dialog.
[EDIT: onProgressUpdate is indeed called in the UI thread.]
First create a separated class which allows you to reach to image address
like following:
public class ImageDownloader extends AsyncTask {
#Override
protected Bitmap doInBackground(String... urls) {
try {
URL url = new URL(urls[0]);
HttpURLConnection connection = (HttpURLConnection) url.openConnection();
connection.connect();
InputStream inputStream = connection.getInputStream();
Bitmap myBitmap = BitmapFactory.decodeStream(inputStream);
return myBitmap;
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
}
Then get access to that class (through a method called by a button) by creating an object and execute the Bitmap task like following :
public class MainActivity extends Activity {
ImageView downloadedImg;
public void downloadImage(View view) {
ImageDownloader task = new ImageDownloader();
Bitmap myImage;
try {
myImage = task.execute("YOUR IMAGE ADDRESS ........").get();
downloadedImg.setImageBitmap(myImage);
} catch (Exception e) {
e.printStackTrace();
}
}
Do NOT forget to:
1 - define the imageView in onCreat method ==> downloadedImg = (ImageView) findViewById(R.id.imageView);
2 - to link the method you've created by a button in user interface ==> (public void downloadImage(View view){})
3 - ask for permission in manifest file