2013-04-20 102 views
0

我創建了一個自定義的SimpleCursorAdapter,其中我已覆蓋bindView,因此我可以在列表項佈局中連接ImageButton的onClick偵聽器。我想在使用Intent以及底層Cursor的一些額外數據集單擊按鈕時啓動一個新應用程序。自定義SimpleCursorAdapter - onClickListener重載bindView問題

問題是,當按鈕的onClick函數被調用時,遊標似乎不再指向數據庫中的正確行(我假設這是因爲它已被更改爲指向不同的行該列表滾動)。

這裏是我的代碼:

private class WaveFxCursorAdapter extends SimpleCursorAdapter { 

public WaveFxCursorAdapter(Context context, int layout, Cursor c, 
    String[] from, int[] to, int flags) { 
    super(context, layout, c, from, to, flags); 
} 

@Override 
public void bindView(View v, Context context, Cursor c) { 
    super.bindView(v, context, c); 
    ImageButton b = (ImageButton) v.findViewById(R.id.btn_show_spec); 

    // fchr is correct here: 
    int fchr = c.getInt(c.getColumnIndex(
       WaveDataContentProvider.SiteForecast.FORECAST_PERIOD)); 

    Log.d(TAG, "ChrisB: bindView: FCHR is: " + fchr); 

    b.setOnClickListener(new OnClickListener() { 
     @Override 
     public void onClick(View v) { 
      Intent i = new Intent(getActivity(), SpecDrawActivity.class); 
      i.setAction(Intent.ACTION_VIEW); 
      i.putExtra("com.kernowsoft.specdraw.SITENAME", mSitename); 

      // fchr is NOT CORRECT here! I can't use the fchr from the 
      // bindView method as Lint tells me this is an error: 
      int fchr = c.getInt(c.getColumnIndex(
       WaveDataContentProvider.SiteForecast.FORECAST_PERIOD)); 

      Log.d(TAG, "bindView: Forecast hour is: " + fchr); 
      i.putExtra("com.kernowsoft.specdraw.FCHR", fchr); 
      getActivity().startActivity(i); 
     } 
    }); 
} 

正如你可以從上面的代碼中的註釋看,fchr是正確的,當我把它打印到日誌中bindView,但它是在onClick方法不正確。我試圖從onClick方法引用fchr變量bindView,但Andriod的皮棉告訴我,我不能這樣做:

不能引用非最終變量FCHR在不同的方法定義的內部類中

我的問題是:如何正確地將光標的fchr變量傳遞給onClick方法?

謝謝!

回答

3

錯誤的原因是變量fchr是bindView()方法中的局部變量。使用匿名類創建的對象可能會持續到bindView()方法返回之後。當bindView()方法返回時,局部變量將從堆棧中清除,所以在bindView()返回後它們將不再存在。

但是匿名類對象引用變量fchr。如果匿名類對象在清理後嘗試訪問變量,情況就會變得非常糟糕。

通過使fchr最終,它們不再是真正的變量,而是常數。然後,編譯器可以將匿名類中的fchr替換爲常量的值,並且不會再有訪問不存在的變量的問題。

Working with inner classes

+0

如果我在聲明變量類,我仍然得到相同的Lint錯誤。那麼是否會使變量最終產生影響? – ccbunney 2013-04-20 09:07:27

+0

檢查我編輯的答案。 – 2013-04-20 09:08:05

+0

對不起 - 我的第一條評論是不正確的。在類中聲明變量不會產生lint錯誤,但它仍會返回錯誤的fchr。做出可變的最終作品,但這是實現此目的的推薦方法嗎?謝謝! – ccbunney 2013-04-20 09:14:55

0

代替:

b.setOnClickListener(new OnClickListener() { 

使用:

b.setOnClickListener(new MyClickListener(fchr)); 

和類MyClickListener會是什麼樣子:

class MyClickListener implements OnClickListener { 
    int mFchr; 
    public MyClickListener(int fchr) { 
     mFchr = fchr; 
    } 
    @Override 
    public void onClick(View v) { 
     // here you can access mFchr 
    } 
} 
+0

這是一個好主意。我可以試試 - 謝謝。 – ccbunney 2013-04-20 15:11:50

+0

啊,這不起作用,因爲OnClickListener是一個接口,它沒有構造函數。 – ccbunney 2013-04-20 15:16:49

+0

確定你是對的,改爲擴展到實現 – pskink 2013-04-20 15:25:27