2012-06-26 10 views
8

Eventuali duplicati:
Android - ViewRootImpl$CalledFromWrongThreadException

Nel tentativo di ottenere l'immagine dal mio URL e di visualizzazione in applicazione ma buttare errore Causato da: android.view.ViewRootImpl $ CalledFromWrongThreadException: solo il thread originale che ha creato una gerarchia di viste può toccare le sue viste. Qui di seguito è il mio codice

Codice

package com.smartag.bird.dev; 

public class MainActivity extends Activity { 
    static String ndefMsg = null; 
    static String ndefMsg1 = null; 
    NfcAdapter mNfcAdapter; 
    PendingIntent mNfcPendingIntent; 
    IntentFilter[] mNdefExchangeFilters; 
    static final String TAG = "Read Tag"; 
    TextView mTitle; 
    private static ImageView imageView; 
    static String url = "http://sposter.smartag.my/images/chicken_soup.jpg"; 
    private static Bitmap downloadBitmap; 
    private static BitmapDrawable bitmapDrawable; 
    private static boolean largerImg = false; 

    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState);    
     //setContentView(R.layout.main); 
     mNfcAdapter = NfcAdapter.getDefaultAdapter(this); 
     mNfcPendingIntent = PendingIntent.getActivity(this, 0, 
       new Intent(this, getClass()).addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP), 0); 
     IntentFilter ndefDetected = new IntentFilter(NfcAdapter.ACTION_NDEF_DISCOVERED); 
     try { 
      ndefDetected.addDataType("text/plain"); 
     } catch (MalformedMimeTypeException e) { } 
     mNdefExchangeFilters = new IntentFilter[] { ndefDetected }; 
     if (NfcAdapter.ACTION_NDEF_DISCOVERED.equals(getIntent().getAction())) { 
      NdefMessage[] messages = getNdefMessages(getIntent()); 
      byte[] payload = messages[0].getRecords()[0].getPayload(); 
      ndefMsg = new String(payload);   
      setIntent(new Intent()); // Consume this intent. 
     } 

     ConnectivityManager connManager = (ConnectivityManager) getSystemService(CONNECTIVITY_SERVICE); 
     NetworkInfo mWifi = connManager.getNetworkInfo(ConnectivityManager.TYPE_WIFI); 

     if(ndefMsg == null || ndefMsg.length() == 0) 
     {    
      startActivity(new Intent(MainActivity.this, MainMenu.class));    
     }    
     else 
     { 
      setContentView(R.layout.main); 
      if (mWifi.isConnected()) {    
       ndefMsg1 = ndefMsg; 
       new DownloadFilesTask().execute(); 
        ndefMsg = null; 
      } 
      else 
      {       
       AlertDialog.Builder dialog = new AlertDialog.Builder(this); 
       dialog.setTitle("Attention"); 
       dialog.setMessage("No Internet Connection. Please enable the wifi."); 
       dialog.setPositiveButton("OK", new DialogInterface.OnClickListener() { 
        public void onClick(DialogInterface dialog, int whichButton) 
        { 
        } 
       }); 
       dialog.show(); 
      } 
     }   
    } 
    private class DownloadFilesTask extends AsyncTask<Void, Void, Void> { 
     protected void onPostExecute(Void result) {    
     }   
     @Override 
     protected Void doInBackground(Void... params) {    
      try { 
       URL myFileUrl = new URL("http://sposter.smartag.my/images/chicken_soup.jpg"); 
       HttpURLConnection conn= (HttpURLConnection)myFileUrl.openConnection(); 
       conn.setDoInput(true); 
       conn.connect(); 
       InputStream is = conn.getInputStream(); 
       downloadBitmap = BitmapFactory.decodeStream(is); 
          } catch (FileNotFoundException e) {    
       e.printStackTrace(); 
      } 
      catch (IOException e) {   
       e.printStackTrace(); 
      }    
      ImageView image = (ImageView) findViewById(R.id.imview);    
      image.setImageBitmap(downloadBitmap); 
      return null; 
     } 
    } 
} 
+0

mi dispiace mio male ... ho sollevato questa domanda prima. Grazie per gli aggiornamenti. –

+1

le modifiche nell'interfaccia utente devono essere eseguite in "onPostExecute" – CaffeineShots

risposta

35

Bad pratica di utilizzo di AsyncTask,

Si sta cercando di aggiornare l'interfaccia utente principale filo da doInBackGround() come AsyncTask mai permesso questo.

Non aggiornare mai l'interfaccia utente da doInBackGround() di AsyncTask come unico thread di lavoro. Quindi scrivere il codice utente updatation principale in onPostExecute() metodo AsyncTask ..

@Override 
     protected Void doInBackground(Void... params) {    
      try { 
       URL myFileUrl = new URL("http://sposter.smartag.my/images/chicken_soup.jpg"); 
       HttpURLConnection conn= (HttpURLConnection)myFileUrl.openConnection(); 
       conn.setDoInput(true); 
       conn.connect(); 
       InputStream is = conn.getInputStream(); 
       downloadBitmap = BitmapFactory.decodeStream(is); 
          } catch (FileNotFoundException e) {    
       e.printStackTrace(); 
      } 
      catch (IOException e) {   
       e.printStackTrace(); 
      }    
      return null; 
     } 

@Override 
onPostExecute() 
{ 
ImageView image = (ImageView) findViewById(R.id.imview);    
      image.setImageBitmap(downloadBitmap); 
} 
+3

perché hai detto cattive pratiche ... per favore consiglio. thansk –

6

aggiungerà alcuni punti da quello @ user370305 Said,

Non si può toccare elementi dell'interfaccia utente in discussione non ui.

Se si utilizza AsyncTaskdoInBackground viene eseguito in thread non-ui, quindi non è possibile accedere a ImageView.

È possibile accedere agli elementi dell'interfaccia utente in onPreExecute, onProgressUpdate & onPostExcecute.

Problemi correlati