2

I made a program which uploads a video to an asp.net server. Then I want to develop my application by adding a progress bar. However, after adding the progress bar I am not able to upload the file to the server.( this is the result that I get after debugging!!!) Could you please help me what is wrong with my code?

package com.isoft.uploader2;

import java.io.DataOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import android.app.Activity;
import android.app.ProgressDialog;
import android.content.Intent;
import android.database.Cursor;
import android.net.Uri;
import android.os.AsyncTask;
import android.os.Bundle;
import android.provider.MediaStore;
import android.util.Log;
import android.view.View;
import android.widget.Button;

public class Proje2Activity extends Activity
{
 @Override
    public void onCreate(Bundle savedInstanceState) 
    {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        Button button =(Button)findViewById(R.id.button1);
        button.setOnClickListener(new View.OnClickListener() {

            @Override
            public void onClick(View arg0) {
                // TODO Auto-generated method stub
                openGaleryVideo();
            }
        });

    }
/** Called when the activity is first created. */
public static final int SELECT_VIDEO=1;
public static final String TAG="UploadActivity";
String path="";

//Gallery'i aç
public void openGaleryVideo()
{
    Intent intent=new Intent();
    intent.setType("video/*");
    intent.setAction(Intent.ACTION_GET_CONTENT);
    startActivityForResult(Intent.createChooser(intent, "Select Video"),SELECT_VIDEO);
}

//Dosyayı seç ve yükle
public void onActivityResult(int requestCode, int resultCode, Intent data) 
{
    super.onActivityResult(requestCode, resultCode, data);
    if (resultCode == RESULT_OK)
    {
        if (requestCode == SELECT_VIDEO) 
        {
            Uri videoUri = data.getData();
            path= getPath(videoUri);
            upload a = new upload();
            a.onPreExecute();
            a.doInBackground();
            a.onProgressUpdate();


        }
    }
}

//SD carddan yerini al
public String getPath(Uri uri)
{   
    String[] projection = { MediaStore.Video.Media.DATA};
    Cursor cursor = managedQuery(uri, projection, null, null, null);
    int column_index = cursor.getColumnIndexOrThrow(MediaStore.Video.Media.DATA);
    cursor.moveToFirst();
    return cursor.getString(column_index);
}
public class upload extends AsyncTask<Object, Integer, Void> 
{
     public ProgressDialog dialog;
     File file=new File(path);  
     String urlServer = "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx";
     String filename=file.getName();
     int bytesRead, bytesAvailable, bufferSize;
     byte[] buffer;
     int maxBufferSize = 20*1024*1024;
    @Override
    public void onPreExecute() 
    {
         dialog = new ProgressDialog(Proje2Activity.this);
         dialog.setMessage("Uploading...");
         dialog.setIndeterminate(false);
         dialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
         dialog.setProgress(0);
         dialog.show();
            //Burada işlemi yapmadan önce ilk olarak ne yaptırmak istiyorsak burada yaparız.
            //Örneğin burada dialog gösterip "onPostExecute()" metodunda dismiss edebiliriz.
    }

    @Override
    public Void doInBackground(Object... arg0) 
    {
        // TODO Auto-generated method stub
        try
        {
        FileInputStream fileInputStream = new FileInputStream(file);

        URL url = new URL(urlServer);
        HttpURLConnection connection = (HttpURLConnection) url.openConnection();
        connection.setFixedLengthStreamingMode((int) file.length());

        // Allow Inputs & Outputs
        connection.setDoInput(true);
        connection.setDoOutput(true);
        connection.setUseCaches(false);

        // Enable POST method
        connection.setRequestMethod("POST");
        connection.setRequestProperty("Connection", "Keep-Alive");
        connection.setRequestProperty("Content-Type",  "multipart/form-data");
        connection.setRequestProperty("SD-FileName", filename);//This will be the file name
        DataOutputStream outputStream = new DataOutputStream(connection.getOutputStream());
        bytesAvailable = fileInputStream.available();
        bufferSize = Math.min(bytesAvailable, maxBufferSize);
        buffer = new byte[bufferSize];

        // Read file
        bytesRead = fileInputStream.read(buffer, 0, bufferSize);
        while (bytesRead > 0)
        {   
            outputStream.write(buffer, 0, bufferSize);
            bytesAvailable = fileInputStream.available();
            publishProgress();
            bufferSize = Math.min(bytesAvailable, maxBufferSize);
            bytesRead = fileInputStream.read(buffer, 0, bufferSize);
        }//end of while statement
        fileInputStream.close();
        publishProgress(100); 
        outputStream.flush();
        outputStream.close();
        }//end of try body
        catch (Exception ex)
        {
            //ex.printStackTrace();
            Log.e("Error: ", ex.getMessage());
        }
        return null;
     }//end of doInBackground method
     @Override
     public void onProgressUpdate(Integer... values) 
     {
       // TODO Auto-generated method stub
       dialog.setProgress((int) ((file.length()-bytesRead)/100));
     }//end of onProgressUpdate method
}// end of asyncTask class 
}//end of main
answer88
  • 165
  • 7
  • 19

2 Answers2

1

You have to call the upload task like

new Upload().execute();

and you are not doing the right by calling asynTask like the way you did

So you code just looks like the following

Upload a = new Upload();
a.execute 

Instead of

upload a = new upload();
            a.onPreExecute();
            a.doInBackground();
            a.onProgressUpdate();

And if your code to upload the file is correct , this will work

and if you want to update the progress bar use Handler class

Handler handler = new Handler(){
    @Override 
    public void handleMessage(int what){
        mProgress.setProgress(mProgressStatus);
     }

as described in ProgressBar widget

And inside the doInBackground() method invoke the method publishProgress() as described here AsyncTask Docs

Muhannad A.Alhariri
  • 3,702
  • 4
  • 30
  • 46
  • So what are you suggesting me ? How can I upload a file from SD card to an asp.net server with a progress bar? – answer88 Jul 03 '12 at 15:08
  • Put the code of uploading n doInBackground() , you are doing the right just invoke the Upload class using using execute method – Muhannad A.Alhariri Jul 03 '12 at 16:48
  • I am using a progress dialog not a progress bar in my app. Is it still suitable to use a handler? – answer88 Jul 04 '12 at 06:38
  • yes sure , You can use what evenr you want , always use handler to update progress dialogs or bars – Muhannad A.Alhariri Jul 04 '12 at 06:58
  • thanks for helping finally what is "what" in the code? I did not understand exactly. Is it "progress"? – answer88 Jul 04 '12 at 07:20
  • ok , (what) is an integer parameter you send to the handler to handle the message for example if you are using the same handler to handle two progress dialog or so , use (what) to identify which one to handle for example what = 0 for progressDialog1 and what=1 for progressDialig2 .. and so on – Muhannad A.Alhariri Jul 04 '12 at 07:28
  • could you please post the code cause mine is still not working :( – answer88 Jul 04 '12 at 14:19
  • You can see this post http://stackoverflow.com/questions/6149935/problem-with-uploading-captured-image-in-android-camera?rq=1 , I think it has a good file uploader example – Muhannad A.Alhariri Jul 05 '12 at 06:26
  • My uploader code is working but I am talking about the code of updating the progress bar. Do you have any solution to this cause when I am using a handler there is warning that I should surround this following code with try catch but it is still not working! 'code'outputStream.write(buffer, 0, bufferSize); bytesAvailable = fileInputStream.available(); publishProgress(); bufferSize = Math.min(bytesAvailable, maxBufferSize); bytesRead = fileInputStream.read(buffer, 0, bufferSize); – answer88 Jul 05 '12 at 06:36
  • let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/13453/discussion-between-muhannad-and-answer88) – Muhannad A.Alhariri Jul 05 '12 at 11:24
1

As Muhannad sais right, your onActivityResult method should look like the following:

public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (resultCode == RESULT_OK)
{
    if (requestCode == SELECT_VIDEO) 
    {
        Uri videoUri = data.getData();
        path= getPath(videoUri);
        upload a = new upload();
        a.execute();


    }
}

}

Edit: As explained in my comment. Changes in bold:

public class upload extends AsyncTask<Object, Integer, Void> {
 public ProgressDialog dialog;
 File file=new File(path);  
 String urlServer = "http://192.168.10.177/androidweb/default.aspx";
 String filename=file.getName();
 int bytesRead, bytesAvailable, bufferSize, **progress**;
 byte[] buffer;
 int maxBufferSize = 20*1024*1024;
@Override
public void onPreExecute() 
{
     dialog = new ProgressDialog(Proje2Activity.this);
     dialog.setMessage("Uploading...");
     dialog.setIndeterminate(false);
     dialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
     dialog.setProgress(0);
     dialog.show();
        //Burada işlemi yapmadan önce ilk olarak ne yaptırmak istiyorsak burada yaparız.
        //Örneğin burada dialog gösterip "onPostExecute()" metodunda dismiss edebiliriz.
}

@Override
public Void doInBackground(Object... arg0) 
{
    // TODO Auto-generated method stub
    try
    {
    FileInputStream fileInputStream = new FileInputStream(file);

    URL url = new URL(urlServer);
    HttpURLConnection connection = (HttpURLConnection) url.openConnection();
    connection.setFixedLengthStreamingMode((int) file.length());

    // Allow Inputs & Outputs
    connection.setDoInput(true);
    connection.setDoOutput(true);
    connection.setUseCaches(false);

    // Enable POST method
    connection.setRequestMethod("POST");
    connection.setRequestProperty("Connection", "Keep-Alive");
    connection.setRequestProperty("Content-Type",  "multipart/form-data");
    connection.setRequestProperty("SD-FileName", filename);//This will be the file name
    DataOutputStream outputStream = new DataOutputStream(connection.getOutputStream());
    bytesAvailable = fileInputStream.available();
    bufferSize = Math.min(bytesAvailable, maxBufferSize);
    buffer = new byte[bufferSize];

    // Read file
    **progress = 0;**
    bytesRead = fileInputStream.read(buffer, 0, bufferSize);
    **progress += bytesRead;**
    while (bytesRead > 0)
    {   
        outputStream.write(buffer, 0, bufferSize);
        bytesAvailable = fileInputStream.available();
        publishProgress();
        bufferSize = Math.min(bytesAvailable, maxBufferSize);
        bytesRead = fileInputStream.read(buffer, 0, bufferSize);
        **progress += bytesRead;**
    }//end of while statement
    fileInputStream.close();
    publishProgress(100); 
    outputStream.flush();
    outputStream.close();
    }//end of try body
    catch (Exception ex)
    {
        //ex.printStackTrace();
        Log.e("Error: ", ex.getMessage());
    }
    return null;
 }//end of doInBackground method
 @Override
 public void onProgressUpdate(Integer... values) 
 {
   // TODO Auto-generated method stub
   dialog.setProgress((int) ((file.length()-**progress**)/100));
 }//end of onProgressUpdate method
 }// end of asyncTask class 
 }//end of main
Dude
  • 652
  • 2
  • 10
  • 24
  • Thanks but the progress bar still has no action on it. How can I solve this problem?(About updating the bar) – answer88 Jul 03 '12 at 15:07
  • The problem is that bytesRead is the read bytes in this cycle, not the total read bytes. So in order to have the total read bytes, you have to accumulate that in another variable (e.g. int progress += bytesRead;) and take this variable instead of the bytesRead variable in the onProgressUpdate(). I updated the code – Dude Jul 03 '12 at 15:23