2013-09-29 16 views
36

Qualcuno può aiutarmi a scoprire quale può essere il problema con questo programma. Nel metodo onCreate(), findViewById() restituisce null per tutti gli ID e ciò causa un'eccezione di puntatore nullo in un secondo momento. Non riesco a capire perché il findViewById() non riesca a trovare la vista. Eventuali suggerimenti?Null pointer Exception - findViewById()

Questo è il codice principale:

public class MainActivity extends Activity { 

    ViewPager pager; 
    MyPagerAdapter adapter; 
    LinearLayout layout1, layout2, layout3; 

    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.activity_main); 

     layout1 = (LinearLayout) findViewById(R.id.first_View); 
     layout2 = (LinearLayout) findViewById(R.id.second_View); 
     layout3 = (LinearLayout) findViewById(R.id.third_View); 

     adapter = new MyPagerAdapter(); 
     pager = (ViewPager) findViewById(R.id.main_pager); 
     pager.setAdapter(adapter); 
    } 

    private class MyPagerAdapter extends PagerAdapter 
    { 

     @Override 
     public int getCount() { 
      return 3; 
     } 

     @Override 
     public Object instantiateItem(ViewGroup collection, int position) { 

      LinearLayout l = null; 

      if (position == 0) 
      { 
       l = layout1; 
      } 
      if (position == 1) 
      { 
       l = layout2; 
      } 

      if (position == 2) 
      { 
       l = layout3; 
      } 
       collection.addView(l, position); 
       return l; 
     } 

     @Override 
     public boolean isViewFromObject(View view, Object object) { 
      return (view==object); 
     } 

     @Override 
     public void destroyItem(ViewGroup collection, int position, Object view) { 
       collection.removeView((View) view); 
     } 
    } 
} 

ed i relativi file XML:

activity_main disposizione:

<?xml version="1.0" encoding="utf-8"?> 
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" 
       android:orientation="vertical" 
       android:layout_width="fill_parent" 
       android:layout_height="fill_parent" 
       android:background="#a4c639"> 


    <android.support.v4.view.ViewPager 
         android:layout_width="match_parent" 
         android:layout_height="match_parent" 
         android:id="@+id/main_pager"/> 
</LinearLayout> 

activity_first disposizione:

<?xml version="1.0" encoding="utf-8"?> 
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" 
android:layout_width="match_parent" 
android:layout_height="match_parent" 
android:id="@+id/first_View"> 

<TextView 
    android:layout_width="wrap_content" 
    android:layout_height="wrap_content" 
    android:text="@string/hello_world" /> 

<Button 
    android:id="@+id/button1" 
    style="?android:attr/buttonStyleSmall" 
    android:layout_width="wrap_content" 
    android:layout_height="wrap_content" 
    android:text="Button" /> 

</LinearLayout> 

activity_second l ayout:

<?xml version="1.0" encoding="utf-8"?> 
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" 

android:layout_width="match_parent" 
android:layout_height="match_parent" 
android:id="@+id/second_View"> 

<TextView 
    android:layout_width="wrap_content" 
    android:layout_height="wrap_content" 
    android:text="@string/hello_world" /> 

</LinearLayout> 

E il layout activity_third:

<?xml version="1.0" encoding="utf-8"?> 
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" 
android:layout_width="match_parent" 
android:layout_height="match_parent" 
android:id="@+id/third_View"> 

<TextView 
    android:layout_width="wrap_content" 
    android:layout_height="wrap_content" 
    android:text="@string/hello_world" /> 

</LinearLayout> 

risposta

63

findViewById() restituisce una visualizzazione se esiste nel layout che hai fornito in setContentView(), altrimenti restituisce null ed è quello che ti succede.

Esempio se si setContentView(R.layout.activity_first); e quindi si chiama findViewById(R.id.first_View); si restituirà una vista che è il layout.

ma se si chiama findViewById(R.id.second_View); che tornerà null dal momento che non c'è una vista nel layout activity_first.xml chiamato @+id/second_View.

+0

Ho incluso tutti i layout nel layout principale e non ho più alcuna eccezione di puntatore nullo. Grazie per il consiglio. – user2629828

+3

Quando l'ho usato su una vista diversa diversa dalla vista attualmente visualizzata, quella è comparsa. Per superare questo comportamento indesiderato, ho fatto riferimento alla vista senza utilizzare setContentView come segue. layout1 = (LinearLayout) View.inflate (questo, R.layout.first_View, null); Quindi per accedere a qualsiasi cosa al suo interno, potrei usare Pulsante botton = (Button) layout1.findViewById (R.id.button1); Basta aggiungere in modo che possa essere utile eseguire il sombody. –

+0

Perché? Qual è il vantaggio di costringerci? –

2

Le viste che stai cercando di ottenere non sono definite nel layout activity_main. Hai bisogno di gonfiare il punto di vista di programmazione si sta cercando di aggiungere alla pager.-

@Override 
public Object instantiateItem(ViewGroup collection, int position) { 
    LinearLayout l = null; 

    if (position == 0) { 
     l = (LinearLayout) View.inflate(this, R.layout.activity_first, null); 
    } 
    if (position == 1) { 
     l = (LinearLayout) View.inflate(this, R.layout.activity_second, null); 
    } 
    if (position == 2) { 
     l = (LinearLayout) View.inflate(this, R.layout.activity_third, null); 
    } 

    collection.addView(l, position); 
    return l; 
} 
+0

Come accedete alle viste nella vostra attività principale? – Denny

1

aggiungere quelle viste all'adattatore cercapersone prima di accedervi.

@Override 
protected void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.activity_main); 

    adapter = new MyPagerAdapter(); 
    pager = (ViewPager) findViewById(R.id.main_pager); 
    pager.setAdapter(adapter); 

    layout1 = (LinearLayout) findViewById(R.id.first_View); 
    layout2 = (LinearLayout) findViewById(R.id.second_View); 
    layout3 = (LinearLayout) findViewById(R.id.third_View); 

} 

l'adattatore pager:

public Object instantiateItem(View collection, int position) { 
    if(position == 0){ 
     View layout = inflater.inflate(R.layout.activity_first, null); 

     ((ViewPager) collection).addView(layout); 

     return layout; 
    } 
    ... and so forth. 

} 

da qui è possibile accedervi tramite findViewById.

0

Cosa @Warlock detto sopra è giusto, si dovrebbe iniziale LinearLayout Layout1, Layout2, Layout3 dal modo giusto:

LinearLayout layout1 = (LinearLayout) View.inflate(this, R.layout.first_View, null); 
LinearLayout layout2 = (LinearLayout) View.inflate(this, R.layout.second_View, null); 
LinearLayout layout3 = (LinearLayout) View.inflate(this, R.layout.third, null); 

vogliono il mio consiglio aiuto

0

In Android, findViewById(R.id.some_id) lavori quando si è trovare la vista nel set di layout.

Cioè, se è stato impostato un layout dicono:

setContentView(R.layout.my_layout); 

Visualizzazioni si possono trovare solo in questo layout (my_layout).

Nel codice layout1, layout2, layout3 tutti sono tre diversi layout e non sono impostati per l'attività.

0

Il metodo findViewById deve trovare ciò che è nel layout (che hai chiamato in setContentView)

0

A volte è necessario pulire il vostro progetto in Eclipse (Progetto - Clean ..).

1

Ho ricevuto questo errore oggi ed è stato così semplice da chiarire che ho "facepalmed".

Basta provare ad aggiungere l'elemento dell'interfaccia utente al file di layout xml nella directory res/layout-port !!!

1

Il corsivo è

Per i casi all'interno di una classe di attività.

Activity.findViewById(int id)

Finds una vista che è stato identificato dall'attributo id dal XML che è stato elaborato in onCreate(Bundle).


In caso contrario, come ad esempio un frammento, adattatore, un View da un LayoutInflater, ecc

View.findViewById(int id)

Cercare una vista bambino con il dato id. Se questa vista ha l'ID specificato, restituisci questa vista.


entrambi i casi,

Returns
La vista se trovato o null altrimenti.


Ora, ri-controllare i file XML. Assicurati di inserire il valore corretto in setContentView o inflater.inflate.

Nel caso di un'attività, chiamare findViewById dopo setContentView.

Quindi, assicurarsi che vi sia una vista che si sta cercando con android:id="@+id/..." in tale layout. Assicurati che il + sia @+id, che aggiungerà la risorsa ai valori R.id per assicurarti di trovarlo da Java.