1

Android 4.2 では、actionBar タブを使用して、カーソルローダーと sqlite を使用してリスト フラグメントを切り替えていますが、すべて正常に動作します。ontabreselected コールバックを使用して、setSelection(0) でリストの先頭に戻ります。これは機能しますが、画面の回転 (向きの変更) 後にクラッシュします。たとえば、リストを特定の位置で下にスクロールして画面を回転させると、フラグメントは目的の同じ位置に再作成されますが、setSelection(0) で上部に移動するタブを再選択すると、"新しく再作成されたビューがメイン アクティビティから切り離されているかのように、コンテンツ ビューはまだ作成されていません。

私の主な活動は ActionBar.TabListener を実装しています

public class RestonetActivity extends Activity implements ListItemSelectListener,     ActionBar.TabListener{


private boolean useLogo = false;
private boolean showHomeUp = true;

private int tab_pos;

ListeFragment listeFrg = new ListeFragment();
AlphaListeFragment alphaFrg = new AlphaListeFragment();


@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

    setContentView(R.layout.main);



     final ActionBar ab = getActionBar();
     ab.setDisplayUseLogoEnabled(useLogo);
     ab.setDisplayShowHomeEnabled(true);
     ab.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
 ab.setDisplayOptions(0, ActionBar.DISPLAY_SHOW_TITLE);

    if (savedInstanceState != null){
     tab_pos = savedInstanceState.getInt("tabState");
     ab.addTab(ab.newTab().setText(R.string.tab_recente).setTabListener(this),0,false);
     ab.addTab(ab.newTab().setText(R.string.tab_alpha).setTabListener(this),1,false);
     ab.addTab(ab.newTab().setText(R.string.tab_fortes).setTabListener(this),2,false);
     ab.setSelectedNavigationItem(tab_pos);

    } else {
     ab.addTab(ab.newTab().setText(R.string.tab_recente).setTabListener(new    TabListener<ListeFragment>(this,"recente",ListeFragment.class)));
ab.addTab(ab.newTab().setText(R.string.tab_recente).setTabListener(this),0,true);
ab.addTab(ab.newTab().setText(R.string.tab_alpha).setTabListener(this),1,false);
ab.addTab(ab.newTab().setText(R.string.tab_fortes).setTabListener(this),2,false);
}
}

public void onTabReselected(Tab tab, FragmentTransaction ft) {
     int position = tab.getPosition();
     Log.e ("ontabreselected", "pos= "+position);
      FragmentManager fragmentManager = getFragmentManager();


      // position cursor at top of list if user retaps a tab
      switch (position) {
    case 0:
         if (null ==  fragmentManager.findFragmentByTag("RECENT")) {

           ft.replace(R.id.listeFragment, listeFrg, "RECENT");
         }
           else{

         listeFrg.setSelection(0);
         }  
            break;
    case 1: 
         if (null == fragmentManager.findFragmentByTag("ALPHA")) {

             ft.replace(R.id.listeFragment, alphaFrg, "ALPHA");
         } else {    

             alphaFrg.setSelection(0);

         }
         break;
    case 2:
         break;

      }    

}
public void onTabSelected(Tab tab, FragmentTransaction ft) {

    FragmentManager fragmentManager = getFragmentManager();
    int position = tab.getPosition();

  int loaderID = 0;

  String fragmentTag;

  switch (position) {
case 0:

     loaderID=RESTO_RECENT_LOADER;

     if (null == fragmentManager.findFragmentByTag("RECENT")) {
            ft.replace(R.id.listeFragment, listeFrg, "RECENT");
         }
         break;
case 1: 
    loaderID=RESTO_ALPHA_LOADER;
     if (null == fragmentManager.findFragmentByTag("ALPHA")) {
           ft.replace(R.id.listeFragment, alphaFrg, "ALPHA");
     }
     break;

  }    
  }
public void onTabUnselected(Tab tab, FragmentTransaction ft) {


}

リストフラグメントコードは次のとおりです(2番目のフラグメントは本質的に同一であるため省略しました)

public class ListeFragment extends ListFragment implements  LoaderManager.LoaderCallbacks<Cursor>  {
private ListItemSelectListener listeSelectListener;

@Override
public void onAttach(Activity activity) {
    super.onAttach(activity);
    Log.e ("onAttach", "ListeFragment Attached ");

    try {
        listeSelectListener = (ListItemSelectListener) activity;

    } catch (ClassCastException e) {
        throw new ClassCastException(activity.toString()
                + " doit implementer ListItemSelectListener");
    }
}



@Override
public void onListItemClick(ListView l, View v, int position, long id) {
    super.onListItemClick(l, v, position, id);

    listeSelectListener.onItemSelected(position, id);

}


private static final int RESTO_RECENT_LOADER = 0x01;
private static final int RESTO_ALPHA_LOADER = 0x02;
private static final int RESTO_HIGH_LOADER = 0x03;
private static final int RESTO_SEARCH_LOADER = 0x04;


private SimpleCursorAdapter adapter;

public void afficheList(int loader_id, String query) {

    Bundle mBundle = new Bundle();
    mBundle.putString("search_query", query);
    getLoaderManager().restartLoader(loader_id, mBundle, this);
}



@Override
public void onCreate(Bundle savedInstanceState) {

    super.onCreate(savedInstanceState);
        String[] uiBindFrom = { RestoDatabase.COL_ETAB, RestoDatabase.COL_MONTANT };
    int[] uiBindTo = { R.id.TextView01, R.id.Montant };
    adapter = new SimpleCursorAdapter(
            getActivity(), R.layout.row,
            null, uiBindFrom, uiBindTo,
            CursorAdapter.FLAG_REGISTER_CONTENT_OBSERVER);
    setListAdapter(adapter);

    }

@Override
public void onResume()
{
super.onResume();
// call initLoader on Resume avoids a bug which calls onLoadFinished twice

LoaderManager lm = getLoaderManager();

lm.initLoader(RESTO_RECENT_LOADER, null, this);

}


public Loader<Cursor> onCreateLoader(int id, Bundle args) {
      String[] projection = { RestoDatabase.ID, RestoDatabase.COL_ETAB, RestoDatabase.COL_MONTANT };
    switch (id){
        case RESTO_RECENT_LOADER:

            return new CursorLoader(getActivity(),
                    RestoProvider.CONTENT_URI, projection, null, null, date_infraction DESC");

        case RESTO_ALPHA_LOADER:
            return new CursorLoader(getActivity(),
                    RestoProvider.CONTENT_URI_GROUPBY, projection, null, null,"etablissement ASC");



        default: return null;

    }
}

public void onLoadFinished(Loader<Cursor> loader, Cursor cursor) {
    adapter.swapCursor(cursor);

}

public void onLoaderReset(Loader<Cursor> loader) {
    adapter.swapCursor(null);
}
 }

最後に、これが logcat です。untabreselected の 307 行目は 次のとおりですlisteFrg.setSelection(0);

04-25 21:36:08.411: E/AndroidRuntime(23013): 致命的な例外: メイン 04-25 21:36:08.411: E/AndroidRuntime(23013): java.lang.IllegalStateException: コンテンツ ビューがまだ作成されていません 04-25 21:36:08.411: E/AndroidRuntime(23013): android.app.ListFragment.ensureList(ListFragment.java:386) 04-25 21:36:08.411: E/AndroidRuntime(23013): android.app.ListFragment で.setSelection (ListFragment.java:256) 04-25 21:36:08.411: E/AndroidRuntime (23013): ca.usimage.resto.RestonetActivity.onTabReselected (RestonetActivity.java:307) 04-25 21:36:08.411 : E/AndroidRuntime(23013): com.android.internal.app.ActionBarImpl.selectTab(ActionBarImpl.java:560) 04-25 21:36:08.411: E/AndroidRuntime(23013): com.android.internal. app.ActionBarImpl$TabImpl.select(ActionBarImpl.java:1067) 04-25 21:36:08.411: E/AndroidRuntime(23013): com.android.internal.widget.ScrollingTabContainerView.onItemClick(ScrollingTabContainerView.java:355) 04-25 21:36:08.411: E/AndroidRuntime(23013): android.widget.AdapterView.performItemClick(AdapterView.java:298) 04-25 21: 36:08.411: E/AndroidRuntime(23013): android.widget.Spinner$DropdownPopup$1.onItemClick(Spinner.java:922) 04-25 21:36:08.411: E/AndroidRuntime(23013): android.widget. AdapterView.performItemClick(AdapterView.java:298) 04-25 21:36:08.411: E/AndroidRuntime(23013): android.widget.AbsListView.performItemClick(AbsListView.java:1100) 04-25 21:36:08.411: E/AndroidRuntime(23013): android.widget.AbsListView$PerformClick.run(AbsListView.java:2749) 04-25 21:36:08.411: E/AndroidRuntime(23013): android.widget.AbsListView$1.run( AbsListView.java:3423) 04-25 21:36:08.411: E/AndroidRuntime(23013): Android で。os.Handler.handleCallback(Handler.java:725) 04-25 21:36:08.411: E/AndroidRuntime(23013): android.os.Handler.dispatchMessage(Handler.java:92) 04-25 21:36: 08.411: E/AndroidRuntime(23013): android.os.Looper.loop(Looper.java:137) 04-25 21:36:08.411: E/AndroidRuntime(23013): android.app.ActivityThread.main(ActivityThread) .java:5039) 04-25 21:36:08.411: E/AndroidRuntime(23013): java.lang.reflect.Method.invokeNative(ネイティブ メソッド) 04-25 21:36:08.411: E/AndroidRuntime(23013) : java.lang.reflect.Method.invoke(Method.java:511) 04-25 21:36:08.411: E/AndroidRuntime(23013): com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit) .java:793) 04-25 21:36:08.411: E/AndroidRuntime (23013): com.android.internal.os.ZygoteInit.main (ZygoteInit.java:560) 04-25 21:36:08.411: E /AndroidRuntime(23013):dalvik.system.NativeStart.main (ネイティブ メソッド) で

4

1 に答える 1

0

解決策を見つけたと思います。理由を完全に理解しているかどうかはわかりませんが、うまくいきます。次のように setSelection(0) を呼び出すためにフラグメント オブジェクトをキャストすることにより、ontabreselected を修正する必要があります。

 public void onTabReselected(Tab tab, FragmentTransaction ft) {
 int position = tab.getPosition();

  FragmentManager fragmentManager = getFragmentManager();


  // position cursor at top of list if user retaps a tab
  switch (position) {
  case 0:
     if (null ==  fragmentManager.findFragmentByTag("RECENT")) {

       ft.replace(R.id.listeFragment, listeFrg, "RECENT");
     }
       else{
       ListeFragment listeFrg = (ListeFragment)
       getFragmentManager().findFragmentByTag("RECENT");
       listeFrg.setSelection(0);

     }  
        break;
   case 1: 
     if (null == fragmentManager.findFragmentByTag("ALPHA")) {

         ft.replace(R.id.listeFragment, alphaFrg, "ALPHA");
     } else {    
     AlphaListeFragment alphaFrg = (AlphaListeFragment)
      getFragmentManager().findFragmentByTag("ALPHA");
             alphaFrg.setSelection(0);

     }
     break;
    case 2:
     break;

  }    

}
于 2013-05-01T05:02:59.983 に答える