2011-07-25 6 views
1

Salut Stackoverflow amis,Imageview et OutOfMemory dans Android

je besoin d'un appliaction que, capturer une image en utilisant l'appareil photo et l'afficher dans une vue de l'image repeatedly.After prendre la photo i envoyer cette photo à la serveur.Pour cette processus j'utilise la classe AsynTask nommée myBackgroundUploader. Quand je clique sur le bouton j'appelle le Asysnctask. Je l'ai fait mais après avoir pris deux trois images j'ai eu l'erreur horsofmemory et ma force d'application fermée. J'ai essayé de recycler(), des valeurs nulles mais pas d'utilisation. Quelqu'un peut-il dire comment éviter cette erreur. C'est le journal que j'ai.

onCreate() 
    { 
    setContentView(R.layout.detail_profile); 

    String fname=new File(getFilesDir(), "MyFile.jpeg").getAbsolutePath(); 
    if(imgView!=null) 
       { 
        imgView.destroyDrawingCache(); 
       } 
       imgView=(ImageView)findViewById(R.id.imageView1); 
       imgView.setImageURI(Uri.fromFile(new File(fname))); 

    } 


public void onClick(View v) { 

       if(checkInternetConnection()==false) 
       { 
        new AlertDialog.Builder(detailProfile.this).setTitle("Warning!").setMessage("No Internet connection").setIcon(R.drawable.icon).setNeutralButton("Close", null).show(); 

       } if(diTask!=null) 
         { 
          AsyncTask.Status diStatus=diTask.getStatu(); 
          if(diStatus!=AsyncTask.Status.FINISHED) 
          { 
           return; 
          } 

         } 
         fileprocess(); 
         diTask=new myBackgroundUploader(detailProfile.this); 
         diTask.execute("url for server"); 

} 

myBackgroundUploader.java 

protected void onPreExecute() 
    { 

     progDailog = ProgressDialog.show(mcontext, 
       "Syncing with server ", "Please wait....", 
       true); 

    } 
    protected Bitmap doInBackground(String...pram) 
    { 
     Log.v("doback","uploading,,"); 

     uploadImage(pram[0]); //here parm[0]is my server url 
     return null; 

    } 
    protected void onPostExecute(Bitmap bm) 
    { 

    } 

    public void uploadImage(String...urls) 
    { 
     String fname=new File(mcontext.getFilesDir(),"MyFile.jpeg").getAbsolutePath(); 
Bitmap testAB=null; 
     BitmapFactory.Options options= new BitmapFactory.Options(); 
     options.inSampleSize = 4; 
     testAB=BitmapFactory.decodeFile(fname, options); 


     ByteArrayOutputStream bao = new ByteArrayOutputStream(); 
     testAB.compress(Bitmap.CompressFormat.JPEG,50, bao); 
     byte [] ba = bao.toByteArray(); 
     String ba1=Base64.encodeBytes(ba); 
     ArrayList<NameValuePair> nameValuePairs = new ArrayList<NameValuePair>(); 
     nameValuePairs.add(new BasicNameValuePair("image",ba1)); 
     nameValuePairs.add(new BasicNameValuePair("address",detailProfile.address.getText().toString())); 


     HttpClient httpclient = new DefaultHttpClient(); 
     HttpPost httppost = new HttpPost(urls[0]); 
     HttpParams param=new BasicHttpParams(); 
     HttpConnectionParams.setSoTimeout(param, 60000); 
     httppost.setParams(param); 
     httppost.setEntity(new UrlEncodedFormEntity(nameValuePairs)); 
     HttpResponse response = httpclient.execute(httppost); 
     HttpEntity entity = response.getEntity(); 
     is =entity.getContent(); 
     progDailog.dismiss(); 
     //urls[0].recycle(); 
     ba=null; 
     ba1=null; 
     bao.flush(); 
     testAB.recycle(); 


     } 



07-25 15:39:38.613: ERROR/dalvikvm-heap(31423): 9830400-byte external allocation too large for this process. 
07-25 15:39:38.640: ERROR/GraphicsJNI(31423): VM won't let us allocate 9830400 bytes 
07-25 15:39:38.640: DEBUG/dalvikvm(31423): GC_FOR_MALLOC freed 1K, 48% free 2904K/5511K, external 21335K/23354K, paused 16ms 
07-25 15:39:38.644: DEBUG/skia(31423): --- decoder->decode returned false 
07-25 15:39:38.656: WARN/dalvikvm(31423): threadid=9: thread exiting with uncaught exception (group=0x40015560) 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423): FATAL EXCEPTION: AsyncTask #1 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423): java.lang.RuntimeException: An error occured while executing doInBackground() 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423):  at android.os.AsyncTask$3.done(AsyncTask.java:200) 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423):  at java.util.concurrent.FutureTask$Sync.innerSetException(FutureTask.java:274) 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423):  at java.util.concurrent.FutureTask.setException(FutureTask.java:125) 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423):  at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:308) 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423):  at java.util.concurrent.FutureTask.run(FutureTask.java:138) 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423):  at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1088) 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423):  at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:581) 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423):  at java.lang.Thread.run(Thread.java:1019) 


07-25 15:39:38.664: ERROR/AndroidRuntime(31423): Caused by: java.lang.OutOfMemoryError: bitmap size exceeds VM budget 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423):  at android.graphics.BitmapFactory.nativeDecodeStream(Native Method) 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423):  at android.graphics.BitmapFactory.decodeStream(BitmapFactory.java:470) 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423):  at android.graphics.BitmapFactory.decodeFile(BitmapFactory.java:284) 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423):  at android.graphics.BitmapFactory.decodeFile(BitmapFactory.java:309) 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423):  at com.rodasys.profile.myBackgroundUploader.uploadImage(myBackgroundUploader.java:133) 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423):  at com.rodasys.profile.myBackgroundUploader.doInBackground(myBackgroundUploader.java:57) 
07-25 15:39:38.664: ERROR/AndroidRuntime(31423):  at com.rodasys.profile.myBackgroundUploader.doInBackground(myBackgroundUploader.java:1) 

Merci à l'avance

+1

Sans échantillon de code est difficile à trouver où le problème est. Mais probablement vous avez une fuite de mémoire quelque part – matekm

+0

J'ai vécu cela plusieurs fois. Veuillez poster votre code ici pour que tout le monde puisse vous aider à sortir du pétrin. –

+0

Hi matekm J'ai mis à jour ma question et ajouté mon code. –

Répondre

1

oui imageview est un fileld statique. public image ImageView imgView

Il semble que ce soit le problème qui provoque une fuite de mémoire et, par conséquent, une mémoire insuffisante. Vous pouvez lire cet excellent article sur la façon de l'éviter: http://www.curious-creature.org/2008/12/18/avoid-memory-leaks-on-android/

En résumé: n'utilisez pas de variable d'instance statique. Cela devrait se passer en supprimant static (si cela ne nuit pas à la logique de votre code), sinon vous devrez repenser l'activité sans champ statique contenant ImageView.

+0

vous avez raison Ogre_BGR.thanks. –

0

Je pense que vous devriez faire la recycle avant toute opération lourde de l'image. Ainsi, au lieu de faire ce que vous avez fait, je vous suggère d'essayer ceci:

if (testAB != null) { 
    testAB.recycle(); 
} 

// do your heavy image operation here 

Ne pas oublier d'utiliser un processus d'arrière-plan tels que AsyncTask lorsque vous faites quelque chose à votre image, en particulier lorsque vous attribuez une image à un élément d'interface utilisateur, p.ex. ImageView.

Et essayez de mettre l'image décodée dans votre ImageView au lieu de l'image originale qui a probablement toujours la plus grande taille que celle décodée. Faites-moi savoir si cela fonctionne pour vous.