开发者

Show Progressbar while i get records from a cursor

I have this code:

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.apod_eso2);  

    File f = new File(Environment.getExternalStorageDirectory() + 
        "/Database.sqlite"); 
    CursorFactory factory = null;   
    db =SQLiteDatabase.openDatabase(f.toString(),
        factory,SQLiteDatabase.NO_LOCALIZED_COLLATORS );

    ListView list=(ListView)findViewById(R.id.restaurantsApod);  
    KtiriaId=getIntent().getStringExtra(PrevIntent.ID_EXTRA);
    model=DbFileApodEso.getAllEntos(KtiriaId,db);


    startManagingCursor(model);
    //  
    adapter=new RestaurantAdapter(model);
    list.setAdapter(adapter);
    list.setOnItemClickListener(onListClick);  
}

and the java file i get the cursor is:

public class DbFileApodEso {

    private static String TABLE_NAME="TempApodeiEn";
    private static String[] FROM = { "_id","name", "monthPaid",
        "fValue","gotPaid", };

    static Cursor getAllEntos(String id,SQLiteDatabase db) {

    String[] args={id,"0"};
    db.execSQL("DROP TABLE IF EXISTS " + TABLE_NAME);
    db.execSQL("CREATE TABLE " + TABLE_NAME + 
        "(_id INTEGER PRIMARY KEY  NOT NULL ,old_id integer " +
        " id1 INTEGER, id2 INTEGER, SNumber DOUBLE, name TEXT, gotPaid INTEGER, 
        monthPaid DATETIME, hmerej DATETIME, user TEXT,tMemo text, 
        GotThere INTEGER)");

    db.execSQL("INSERT INTO TempApodeiEn (old_id,eponimo, 
        monthPaid,iddiamerisma,fValue,gotPaid) " +
        "select _id,name,monthPaid,id2,fValue,
        gotPaid from ApodeiEn WHERE id2=? and gotPaid=?", args);

    return(db.query(TABLE_NAME, FROM, "id2=?  and gotPaid=?", args, null,
        null, null));
   }
}

i noticed that it takes three seconds to execute: model=DbFileApodEs开发者_C百科o.getAllEntos(KtiriaId,db) So i'd like to show a progressbar to the user to understand that something is happening, How can i do this? Thanks for help

I followed the instructions from Shardul and the code is like this:

    public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.apod_eso2); 

    //DEFINING A NEW THREAD WHICH WOULD DO SOME WORK AND THEN DISMISS THE DIALOG 
    Thread workThread=new Thread(new Runnable(){

        @Override
        public void run() {
         //@ albertsmus :call your getAllEntos() here!
         File f = new File(Environment.getExternalStorageDirectory()+"/Eisprakseis.sqlite"); 
      CursorFactory factory = null; 

      db =SQLiteDatabase.openDatabase(f.toString(), factory,SQLiteDatabase.NO_LOCALIZED_COLLATORS );

      ListView list=(ListView)findViewById(R.id.restaurantsApod);
      KtiriaId=getIntent().getStringExtra(DiamEso.ID_EXTRA);
      EidosApod=getIntent().getStringExtra(DiamEso.ID_Eidos);
      String comment;   // The generated insult.
      model=DbFileApodEso.getAllEntos(KtiriaId,db);

      startManagingCursor(model);
      //  
      adapter=new RestaurantAdapter(model);
      list.setAdapter(adapter);
      list.setOnItemClickListener(onListClick);

            someTimeConsumingWork(5000);
            //ONLY ONE THREAD CAN HANDLE UI, INCLUDES DISSMISSAL OF
            //PROGRESS DIALOG. runOnUiThread WILL DO ITS MAGIC HERE!
            runOnUiThread(new Runnable(){

                @Override
                public void run() {
                    mProgressDialog.dismiss();
                    Toast.makeText(ApodEsoListaSec.this, "Work done!", Toast.LENGTH_LONG).show();
                }

            });
        }

    });
    workThread.start();

    mProgressDialog=ProgressDialog.show(this, "Work Notify!", "Working hard, Phew!");
}

 private void someTimeConsumingWork(long milisToWork){
     SystemClock.sleep(milisToWork);
 }

but i eventually get the error ERROR/AndroidRuntime(6230): Caused by: java.lang.RuntimeException: Can't create handler inside thread that has not called Looper.prepare() why is that? And as i try to debug the error i realized that the error comes up when i call: adapter=new RestaurantAdapter(model); Any suggestion?


Use AsyncTask (link).

1) Show the ProgressDialog in onPreExecute

2) Perform the Database load in the doInBackground

3) Dismiss the dialog in onPostExecute

Example here


The basic working concept is perform your time consuming work on background (non-ui) Thread.

In Android theres only one and only one UI thread. You must handle all UI changes on that single UI thread i.e. in your case showing and dismissing ProgressDialog.

package .....;
.
.
import android.app.ProgressDialog;
.
.

public class WorkingClass extends Activity {
    ProgressDialog mProgressDialog;
.
.

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.main);

    //DEFINING A NEW THREAD WHICH WOULD DO SOME WORK AND THEN DISMISS THE DIALOG 
    Thread workThread=new Thread(new Runnable(){

        @Override
        public void run() {
//@ albertsmus :call your getAllEntos() here!

            someTimeConsumingWork(5000);
            //ONLY ONE THREAD CAN HANDLE UI, INCLUDES DISSMISSAL OF
            //PROGRESS DIALOG. runOnUiThread WILL DO ITS MAGIC HERE!
            runOnUiThread(new Runnable(){

                @Override
                public void run() {
                    mProgressDialog.dismiss();
                    Toast.makeText(ContentProviderSample.this, "Work done!", Toast.LENGTH_LONG).show();
                }

            });
        }

    });
    workThread.start();

    mProgressDialog=ProgressDialog.show(this, "Work Notify!", "Working hard, Phew!");
}

private void someTimeConsumingWork(long milisToWork){
    SystemClock.sleep(milisToWork);
}

}

I have defined someTimeConsumingWork in this example I coded. Which basically pauses Thread for some long miliseconds. You can replace that call with some real worker thread which is consuming time, in your case albertsmus call your getAllEntos() here.

The basic you should remeber is again you can only call and dismiss UI related functionalities only from UI thread, there are other classes and methods which can help you out with the same purpose, a UI handler or AsynTask for more complex functionalities. You can find their implemenation in documentation.

Hope this helps!


Well i used this code to make it work:

public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.apod_eso2); 
    File f = new File(Environment.getExternalStorageDirectory()+"/Eisprakseis.sqlite"); 

    getDatabaseRecs(f);

}
private void getDatabaseRecs(File fFile){   

            new ShowRecs().execute(fFile.toString());

}
public class ShowRecs extends AsyncTask<String, Void, Void> { 

    private String Content;  
    private String Error = null;   
    private ProgressDialog Dialog = new ProgressDialog(ApodEsoListaSec.this);  

     protected void onPreExecute() { 

         Dialog.setMessage("Please Wait!..");  
         Dialog.show();  
     }  

     protected Void doInBackground(String... urls) {  
         CursorFactory factory = null; 
         File ff = new File(Environment.getExternalStorageDirectory()+"/Eisprakseis.sqlite");
         db =SQLiteDatabase.openDatabase(ff.toString(), factory,SQLiteDatabase.NO_LOCALIZED_COLLATORS );
         KtiriaId=getIntent().getStringExtra(DiamEso.ID_EXTRA);
         model=DbFileApodEso.getAllEntos(KtiriaId,db);

         return null;  
     } 

//and on onPostExecute i load the records to the intent via Restaurant adapter the three seconds needed to ececute model=DbFileApodEso.getAllEntos(KtiriaId,db); the user see the Dialog

 protected void onPostExecute(Void unused) {  
         Dialog.dismiss();  
         if (Error != null) {  
             Toast.makeText(ApodEsoListaSec.this, Error, Toast.LENGTH_LONG).show();  
         } else {  
             Toast.makeText(ApodEsoListaSec.this, "Ready!" , Toast.LENGTH_SHORT).show();  
         }

         ListView list=(ListView)findViewById(R.id.restaurantsApod);

            startManagingCursor(model);
            //      
            adapter=new RestaurantAdapter(model);
            list.setAdapter(adapter);
            list.setOnItemClickListener(onListClick);

}
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜