ActionBar选项卡包含多个片段

时间:2012-02-09 17:53:18

标签: android android-fragments android-actionbar android-tabs

我一直在尝试更新我的应用并开始使用片段 操作栏,以及我错过的所有其他UI功能。一世 明白我可以在一个活动中拥有多个片段 基于设备的不同布局和所有好东西但是 我正在努力以我想要的方式获得一些标签。一世 了解如何添加标签,在它们之间切换,但我该怎么做 标签中有多个片段?所以例如我基本上有两个 屏幕我希望用户能够来回切换 很容易(为什么我要使用标签)。如果我有两个独立的活动我 可以在xml文件中指定它,并使用布局使用setContentView 以下

tab1_layout.xml

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical" >
    <fragment
        android:name="com.example.tabrefactor.Fragment1"
        android:id="@+id/fragment_1"
        android:layout_height="wrap_content"
        android:layout_width="wrap_content"/>
    <fragment
        android:name="com.example.tabrefactor.Fragment2"
        android:id="@+id/fragment_2"
        android:layout_height="wrap_content"
        android:layout_width="wrap_content"/>
    <fragment
        android:name="com.example.tabrefactor.Fragment3"
        android:id="@+id/fragment_3"
        android:layout_height="wrap_content"
        android:layout_width="wrap_content"/>
</LinearLayout>

tab2_layout.xml

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical" >
    <fragment
        android:name="com.example.tabrefactor.Fragment4"
        android:id="@+id/fragment_4"
        android:layout_height="wrap_content"
        android:layout_width="wrap_content"/>
</LinearLayout>

我可以将第二个布局转换为使用标签,因为它只包含 一个片段,但我不确定如何将第一个布局变成一个 标签。这是允许的吗?提前谢谢,

Jason Prenger

3 个答案:

答案 0 :(得分:6)

如果某人有简化或更好的想法,我会留下这个......

最终采用了具有3种框架布局的基础布局的解决方法......

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical" >

    <FrameLayout
        android:id="@+id/fragment_sb"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"/>
    <FrameLayout
        android:id="@+id/fragment_local"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"/>
    <FrameLayout
        android:id="@+id/fragment_rest"
        android:layout_width="fill_parent"
        android:layout_height="0dp"
        android:layout_weight="1"/>

</LinearLayout>

然后在我使用选项卡的活动中,我创建了一个自定义TabListener来处理它们之间的更改。我使用的代码如下(我正在使用actionbarsherlock,所以它看起来与普通的东西略有不同)

public class TabActivity extends FragmentActivity {

    Fragment1 fragment1;
    Fragment2 fragment2;
    Fragment3 fragment3;
    Fragment4 fragment4;

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

        final ActionBar bar = getSupportActionBar();
        bar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
        bar.setDisplayShowTitleEnabled(true);
        bar.setDisplayShowHomeEnabled(false);
        bar.setTitle("Title");

        bar.addTab(bar.newTab()
                .setIcon(R.drawable.ic_list_tab_selected)
                .setTabListener(new ListTabListener(this)));
        bar.addTab(bar.newTab()
                .setIcon(R.drawable.ic_map_tab_selected)
                .setTabListener(new MapTabListener(this)));

        if (savedInstanceState != null) {
            bar.setSelectedNavigationItem(savedInstanceState.getInt("tab", 0));
        }
    }

    @Override
    protected void onSaveInstanceState(Bundle outState) {
        super.onSaveInstanceState(outState);
        outState.putInt("tab", getSupportActionBar().getSelectedNavigationIndex());
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.test_menu, menu);

        return super.onCreateOptionsMenu(menu);
    }

    public static class ListTabListener implements ActionBar.TabListener {
        private static final String fragment1Tag = "fragment1_tag";
        private static final String fragment2Tag = "fragment2_tag";
        private static final String fragment3Tag = "fragment3_tag";

        private FragmentActivity activity;
        private Fragment1 fragment1;
        private Fragment2 fragment2;
        private Fragment3 fragment3;

        public ListTabListener(FragmentActivity activity) {
            this.activity = activity;

            FragmentTransaction ft = activity.getSupportFragmentManager().beginTransaction();
            fragment1 = (Fragment1) activity.getSupportFragmentManager().findFragmentByTag(fragment1Tag);
            if (fragment1 != null && !fragment1.isDetached()) {
                ft.detach(fragment1);
            }

            fragment2 = (Fragment2) activity.getSupportFragmentManager().findFragmentByTag(fragment1Tag);
            if (fragment2 != null && !fragment2.isDetached()) {
                ft.detach(fragment2);
            }

            fragment3 = (Fragment3) activity.getSupportFragmentManager().findFragmentByTag(fragment1Tag);
            if (fragment3 != null && !fragment3.isDetached()) {
                ft.detach(fragment3);
            }

            ft.commit();
        }

        @Override
        public void onTabReselected(Tab tab, FragmentTransaction nullFt) {
            //Reselected don't do anything          
        }

        @Override
        public void onTabSelected(Tab tab, FragmentTransaction nullFt) {
            FragmentTransaction ft = activity.getSupportFragmentManager().beginTransaction();

            if(fragment1 == null) {
                fragment1 = new Fragment1();
                ft.add(R.id.fragment_sb, fragment1, fragment1Tag);
            } else {
                ft.attach(fragment1);
            }

            if(fragment2 == null) {
                fragment2 = new Fragment2();
                ft.add(R.id.fragment_local, fragment2, fragment2Tag);
            } else {
                ft.attach(fragment2);
            }

            if(fragment3 == null) {
                fragment3 = new Fragment3();
                ft.add(R.id.fragment_rest, fragment3, fragment3Tag);
            } else {
                ft.attach(fragment3);
            }

            ft.commit();
        }

        @Override
        public void onTabUnselected(Tab tab, FragmentTransaction nullFt) {
            FragmentTransaction ft = activity.getSupportFragmentManager().beginTransaction();

            if(fragment1 != null)
                ft.detach(fragment1);
            if(fragment2 != null)
                ft.detach(fragment2);
            if(fragment3 != null)
                ft.detach(fragment3);

            ft.commit();
        }
    }

    public static class MapTabListener implements ActionBar.TabListener {
        private static final String fragment4Tag = "fragment4_tag";

        private FragmentActivity activity;
        private Fragment4 fragment4;

        public MapTabListener(FragmentActivity activity) {
            this.activity = activity;

            FragmentTransaction ft = activity.getSupportFragmentManager().beginTransaction();
            fragment4 = (Fragment4) activity.getSupportFragmentManager().findFragmentByTag(fragment4Tag);
            if (fragment4 != null && !fragment4.isDetached()) {
                ft.detach(fragment4);
            }
            ft.commit();
        }

        @Override
        public void onTabReselected(Tab tab, FragmentTransaction nullFt) {
            //Reselected don't do anything          
        }

        @Override
        public void onTabSelected(Tab tab, FragmentTransaction nullFt) {
            FragmentTransaction ft = activity.getSupportFragmentManager().beginTransaction();

            if(fragment4 == null) {
                fragment4 = new Fragment4();
                ft.add(R.id.fragment_rest, fragment4, fragment4Tag);
            } else {
                ft.attach(fragment4);
            }

            ft.commit();
        }

        @Override
        public void onTabUnselected(Tab tab, FragmentTransaction nullFt) {
            FragmentTransaction ft = activity.getSupportFragmentManager().beginTransaction();

            if(fragment4 != null)
                ft.detach(fragment4);

            ft.commit();
        }
    }
}

答案 1 :(得分:1)

这是我的解决方案:

import java.util.ArrayList;
import library.DatabaseHandler;
import org.json.JSONObject;
import android.app.ActionBar;
import android.app.ActionBar.Tab;
import android.app.AlertDialog;
import android.app.Dialog;
import android.app.ProgressDialog;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.content.SharedPreferences;
import android.os.Bundle;
import android.util.Log;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.MenuItem.OnMenuItemClickListener;
import android.view.View.OnClickListener;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.Switch;
import android.widget.TextView;
import android.widget.Toast;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentActivity;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentPagerAdapter;
import android.support.v4.app.FragmentTransaction;
import android.support.v4.view.ViewPager;
import android.support.v4.view.ViewPager.OnPageChangeListener;

public class Polling extends FragmentActivity {
    private ViewPager mViewPager;
    private TabsAdapter mTabsAdapter;

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

    mViewPager = new ViewPager(this);
    mViewPager.setId(R.id.pager);
    setContentView(mViewPager);
    final ActionBar bar = getActionBar();
    bar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
    bar.setDisplayShowTitleEnabled(false);
    bar.setDisplayShowHomeEnabled(false);

    mTabsAdapter = new TabsAdapter(this, mViewPager);
    mTabsAdapter.addTab(bar.newTab().setText(R.string.login),
            LoginFragment.class, null);
    mTabsAdapter.addTab(bar.newTab().setText(R.string.economics),
            EconFragment.class, null);
    mTabsAdapter.addTab(bar.newTab().setText(R.string.elections),
            ElectionsFragment.class, null);
    mTabsAdapter.addTab(bar.newTab().setText(R.string.politics),
            PoliticsFragment.class, null);
    mTabsAdapter.addTab(bar.newTab().setText(R.string.science),
            ScienceFragment.class, null);
    mTabsAdapter.addTab(bar.newTab().setText(R.string.finance),
            FinanceFragment.class, null);
    mTabsAdapter.addTab(bar.newTab().setText(R.string.religion),
            ReligionFragment.class, null);
    mTabsAdapter.addTab(bar.newTab().setText(R.string.military),
            MilitaryFragment.class, null);
    mTabsAdapter.addTab(bar.newTab().setText(R.string.international),
            InternationalFragment.class, null); 
}

public static class TabsAdapter extends FragmentPagerAdapter
    implements ActionBar.TabListener, ViewPager.OnPageChangeListener {
        private final Context mContext;
        private final ActionBar mActionBar;
        private final ViewPager mViewPager;
        private final ArrayList<TabInfo> mTabs = new ArrayList<TabInfo>();

        static final class TabInfo {
            private final Class<?> clss;
            private final Bundle args;

            TabInfo(Class<?> _class, Bundle _args) {
                clss = _class;
                args = _args;
            }
        }

        public TabsAdapter(FragmentActivity activity, ViewPager pager) {
            super(activity.getSupportFragmentManager());
            mContext = activity;
            mActionBar = activity.getActionBar();
            mViewPager = pager;
            mViewPager.setAdapter(this);
            mViewPager.setOnPageChangeListener(this);
        }

        public void addTab(ActionBar.Tab tab, Class<?> clss, Bundle args) {
            TabInfo info = new TabInfo(clss, args);
            tab.setTag(info);
            tab.setTabListener(this);
            mTabs.add(info);
            mActionBar.addTab(tab);
            notifyDataSetChanged();
        }


        public int getCount() {
            return mTabs.size();
        }

        public Fragment getItem(int position) {
            TabInfo info = mTabs.get(position);
            return Fragment.instantiate(mContext, info.clss.getName(), info.args);
        }


        public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
        }


        public void onPageSelected(int position) {
            mActionBar.setSelectedNavigationItem(position);
        }


        public void onPageScrollStateChanged(int state) {
        }


        public void onTabSelected(Tab tab, FragmentTransaction ft) {
            mViewPager.setCurrentItem(tab.getPosition());
            Log.v(TAG, "clicked");
            Object tag = tab.getTag();
            for (int i=0; i<mTabs.size(); i++) {
                if (mTabs.get(i) == tag) {
                    mViewPager.setCurrentItem(i);
                }
            }
        }

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

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

        public void onTabReselected(Tab tab, android.app.FragmentTransaction ft) {}

        @Override
        public void onTabSelected(Tab tab, android.app.FragmentTransaction ft) {    
            Object tag = tab.getTag();
            for (int i=0; i<mTabs.size(); i++) {
                if (mTabs.get(i) == tag) {
                    mViewPager.setCurrentItem(i);
                }
            }
        }

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

所以很明显,我们必须看看片段是如何制作的(包括给单独的布局文件充气)。基本上在每个片段的onCreateView()方法中,你让它返回inflater.inflate(R.layout.THISFRAGMENTSLAYOUT,container,false);这是代码:

public class EconFragment extends Fragment {


    private TableLayout questionContainer;

    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        Log.d("Econ", "onCreateView");

        return inflater.inflate(R.layout.econfragment, container, false);
    }

    public void onResume() {
        super.onResume();

        LayoutInflater inflater = (LayoutInflater) getActivity().
        getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        questionContainer = (TableLayout)getActivity().findViewById(R.id.questionContainer);

        int leftMargin=5;
        int topMargin=5;
        int rightMargin=5;
        int bottomMargin=5;
        while (pos < 10) {
        View question = inflater.inflate(R.layout.question, null);
        question.setId(pos);
        TextView title = (TextView) question.findViewById(R.id.questionTextView);
        title.setText(titles[pos]);
        Button charts = (Button) question.findViewById(R.id.chartsButton);
        charts.setId(pos);
        charts.setOnClickListener(chartsListener);
        TableRow tr = (TableRow) question;
        TableLayout.LayoutParams trParams = new TableLayout.LayoutParams(
                TableLayout.LayoutParams.MATCH_PARENT,
                TableLayout.LayoutParams.WRAP_CONTENT);
        trParams.setMargins(leftMargin, topMargin, rightMargin, bottomMargin);
        tr.setLayoutParams(trParams);

        questionContainer.addView(tr);
        pos++;
        }
        Log.d("Econ", "onResume");
    }

答案 2 :(得分:1)

这与所选答案相同,只是我没有使用支持库。


有两个标签A和B.

  

标签A包含苹果和杏子

     

标签B包含香蕉和浆果


我使用FrameLayout作为容纳这些婴儿的容器

<?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:orientation="vertical" >
 <FrameLayout
   android:id="@+id/container_widgets"
   android:layout_width="fill_parent"
   android:layout_height="wrap_content"/>
</LinearLayout>

MultiFragsInTabsJelly.java - 处理附加和分离操作。

import java.util.ArrayList;
import java.util.Iterator;

import android.app.ActionBar;
import android.app.Activity;
import android.app.Fragment;
import android.app.FragmentTransaction;
import android.app.ActionBar.Tab;
import android.os.Bundle;
import android.util.Log;

public class MultiFragsInTabsJelly extends Activity {

    public static String TAG = "EPE";

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

   // setup action bar for tabs
      setContentView(R.layout.main_layout_jelly);

      ActionBar actionBar = getActionBar();
      actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
      actionBar.setDisplayShowTitleEnabled(false);

      actionBar.setTitle("A and B");

      Tab tabA = actionBar
              .newTab()
              .setText("A");
       tabA.setTabListener(new TabAListener(this));

       actionBar.addTab(tabA);

       Tab tabB = actionBar
                    .newTab()
                    .setText("B");
       tabB.setTabListener(new TabBListener(this));
       actionBar.addTab(tabB);
    }


 public static class TabAListener implements ActionBar.TabListener {

        // FIXME: is this really needed?
        private static final String appleTag   = "apple";
        private static final String apricotTag = "apricot";

        private final Activity      mActivity;
        private ArrayList<Fragment> fragList;

        public TabAListener(Activity activity) {
            mActivity = activity;
            fragList  = null;
        }

        public void onTabReselected(Tab tab, FragmentTransaction ft) {
            // Reselected don't do anything 
            Log.d(TAG, "Tab A: on Tab reselected");
        }

        public void onTabSelected(Tab tab, FragmentTransaction ft) {

            Log.d(TAG, "Tab A: on Tab Selected");

            // attach all the fragments
            if(fragList == null) {

                fragList  = new ArrayList<Fragment>();
                RecordingFragment   appleFrag   = new RecordingFragment();
                ApricotFragment apricotFrag = new ApricotFragment();
                ft.add(R.id.container_widgets, appleFrag, appleTag);
                ft.add(R.id.container_widgets, apricotFrag,  apricotTag);
                fragList.add(appleFrag);
                fragList.add(apricotFrag);
                Log.d(TAG, "Tab A: Added fragments to the ArrayList");

            } else {

                Iterator iter = fragList.iterator();

                while (iter.hasNext())
                {
                    Log.d(TAG, "Tab A: Attaching fragments");
                    ft.attach((Fragment) iter.next());
                }
            }
        }

        public void onTabUnselected(Tab tab, FragmentTransaction ft) {
            Log.d(TAG, "Tab A: on Tab Unselected");

            if(fragList != null)
            {  
                Iterator iter = fragList.iterator();
                while (iter.hasNext())
                {
                    Log.d(TAG, "Tab A: Fragments detached");
                    ft.detach((Fragment) iter.next());
                }
            }
        }
    }

    public static class TabBListener implements ActionBar.TabListener {

        // FIXME: is this really needed?
        private static final String bananaTag = "banana";
        private static final String berryTag  = "berry";

        private final Activity mActivity;
        private ArrayList<Fragment> fragList;

        public TabBListener(Activity activity) {
            mActivity = activity;
            fragList = null;
        }

        public void onTabReselected(Tab tab, FragmentTransaction ft) {
            // Reselected don't do anything
            Log.d(TAG, "Tab B: on Tab reselected");
        }

        public void onTabSelected(Tab tab, FragmentTransaction ft) {

            Log.d(TAG, "Tab B: on Tab Selected");

            // attach all the fragments
            if (fragList == null) {

                fragList = new ArrayList<Fragment>();
                BananaFragment bananaFrag = new BananaFragment();
                BerryFragment   berryFrag = new BerryFragment();
                ft.add(R.id.container_widgets, bananaFrag, bananaTag);
                ft.add(R.id.container_widgets, berryFrag,  berryTag);
                fragList.add(bananaFrag);
                fragList.add(berryFrag);
                Log.d(TAG, "Tab B: Added fragments to the ArrayList");

            } else {

                Iterator iter = fragList.iterator();
                while (iter.hasNext()) {
                    Log.d(TAG, "Tab B: Attaching fragments");
                    ft.attach((Fragment) iter.next());
                }
            }
        }

        public void onTabUnselected(Tab tab, FragmentTransaction ft) {
            Log.d(TAG, "Tab B: on Tab Unselected");

            if (fragList != null) {
                Iterator iter = fragList.iterator();
                while (iter.hasNext()) {
                    Log.d(TAG, "Tab B: Fragments detached");
                    ft.detach((Fragment) iter.next());
                }
            }
        }
    }
}

这里我们有每个片段的(空)体。我只展示了一个ApricotFragment

apricot_fragment.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical" >

    <TextView
        android:layout_width="200dip"
        android:layout_height="wrap_content"
        android:padding="6dip"
        android:text="Apricot" />

</RelativeLayout>

ApricotFragment.java

import android.app.Fragment;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;

public class ApricotFragment extends Fragment {

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        // Inflate the layout for this fragment
        return inflater.inflate(R.layout.apricot_fragment, container, false);
    }
}

我已经设法实现这一点,给自己轻拍屁股,拿一些肉桂卷和咖啡,自己对待to excellent pictures of cats