【Android】ActionBarにタブコントロールを実装する
ActionBarには、フラグメントを切り替えるタブコントロールを実装することができます。
タブには、タイトル文字列やアイコン画像をセットすることが可能です。
TabListenerの実装
アクションバータブのイベントを制御するにはActionBar.TabListener
を実装する必要があります。
各abstractメソッドは、以下のとおりです。
メソッド | 概要 |
---|---|
onTabSelected() | タブが選択された時に呼ばれる |
onTabUnselected() | タブが非選択になった時に呼ばれる |
onTabReselected() | 同じタブが再度選択された時に呼ばれる |
実装メソッドには、イベントを受け取ったActionBar.Tab
インスタンスおよびFragmentTransaction
インスタンスが引数として渡されます。
コンストラクタにてあらかじめ対象のフラグメントを渡しておき、
上記の実装メソッドでフラグメントの追加や削除を行います。
MyTabListener.java
public class MyTabListener implements ActionBar.TabListener { private Fragment mFragment; // 新規タブを作成する際にフラグメントインスタンスを一緒に渡す public MyTabListener(Fragment fragment) { mFragment = fragment; } @Override public void onTabSelected(Tab tab, FragmentTransaction ft) { // タブが選択された時の処理 // フラグメントを追加する ft.add(R.id.fragment_content, mFragment, null); } @Override public void onTabUnselected(Tab tab, FragmentTransaction ft) { // タブが切り替えられた時の処理 // フラグメントを削除する ft.remove(mFragment); } @Override public void onTabReselected(Tab tab, FragmentTransaction ft) { // 同じタブを再度タップされた時の処理 // do nothing } }
注意事項
トランザクションの管理は、システムが代わりに呼び出しを行うため、
FragmentTransaction
に対してcommit()
を呼び出してはいけません。
自分で呼び出した場合は、例外が投げられる可能性があります。
また、トランザクションをバックスタックに追加することもできません。
ActionBarの実装
ActivityクラスにてgetActionBar()
を使って取得したActionBarインスタンスに対して、
setNavigationMode(ActionBar.NAVIGATION_MODE_TABS)
を設定することで、
ActionBarをタブ表示モードへ切り替えることができます。
final ActionBar actionBar = getActionBar(); actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
ActionBarに対してタブを追加するには、
actionBar.newTab()
で取得したインスタンスをaddTab()
にて追加します。
この時、タブに対してタイトル及びアイコン画像をセットすることが可能です。
また、タブの切り替え制御を行うために、上記で作成したActionBar.TabListener
をセットします。
// フラグメントを生成してTabへセット Fragment fragment1 = new Fragment1(); ActionBar.Tab tab1 = actionBar.newTab(); tab1.setText("タブタイトル1"); // タイトル文字列 tab1.setIcon(R.drawable.ic_launcher); // アイコン tab1.setTabListener(new MyTabListener(fragment1)); // リスナー actionBar.addTab(tab1);
これでActionBarに対してタブコントロールを実装することができました。
今回実装した、サンプルソースを記載します。
MainActivity.java
// APIレベル11以上のみ対応 @SuppressLint("NewApi") public class MainActivity extends Activity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); // アクションバーを取得してモードをタブモードへセット final ActionBar actionBar = getActionBar(); actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS); // タイトルを非表示 actionBar.setDisplayShowTitleEnabled(false); // フラグメントを生成してTabへセット Fragment fragment1 = new Fragment1(); // 新しく生成したTabインスタンスには、タイトル文字列、アイコン、リスナーをセットすることができる ActionBar.Tab tab1 = actionBar.newTab(); tab1.setText("タブタイトル1"); tab1.setIcon(R.drawable.ic_launcher); tab1.setTabListener(new MyTabListener(fragment1)); actionBar.addTab(tab1); Fragment fragmet2 = new Fragment2(); actionBar.addTab(actionBar.newTab().setText("タブタイトル2") .setTabListener(new MyTabListener(fragmet2))); } @Override public boolean onCreateOptionsMenu(Menu menu) { // Inflate the menu; this adds items to the action bar if it is present. getMenuInflater().inflate(R.menu.main, menu); return true; } } class Fragment1 extends Fragment { @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { return inflater.inflate(R.layout.tab1_fragment, container, false); } } class Fragment2 extends Fragment { @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { return inflater.inflate(R.layout.tab2_fragment, container, false); } }
tab1_fragment.xml
<?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" > <TextView android:layout_width="match_parent" android:layout_height="match_parent" android:text="フラグメント1"/> </LinearLayout>
tab2_fragment.xml
<?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" > <TextView android:layout_width="match_parent" android:layout_height="match_parent" android:text="フラグメント2"/> </LinearLayout>