Androidはワンツーパンチ 三歩進んで二歩下がる

プログラミングやどうでもいい話

Hello WorldをFragmentを使って書き換えた その2 FragmentTransactionを使う

自分の勉強メモです。

以前のエントリーで、Hello WorldをFragmentを使って書き換えたが、この時はActivity のレイアウトファイルで タグを使ってFragmentを追加した。
このエントリーでは、ViewGroupに対してFragmentをプログラムから差し込む方法を使ってHello Worldを書き換える。

ViewGroupは他のビューを含むことが出来る特別なViewで、
FrameLayout, GridLayout, LinearLayout, RelativeLayoutあたりをよく使う。
LinearLayoutにidを持たせて、そこにFragmentを差し込んでみる。

FragmentTransaction
Fragmentを追加、削除、他のFragmentと差し替えたりという一連の操作は、FragmentTransactionを使う。
1つのトランザクションが画面遷移の履歴の単位となる。
画面の履歴はスタックで管理されているが、Android3.0未満ではこのスタックは「アクティビティスタック」と呼ばれActivity単位だった。
Android3.0になって「バックスタック」という呼称に変わりActivity単位の履歴に加えFragmentのトランザクション単位での履歴も扱えるようになった。
画面の一部のみを書き換えたり元に戻したり柔軟な変更が実現できる。

Fragmentを使って書き換えたHello Worldのソース

res/layout/main.xml

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

    <!-- ViewGroupにidを定義してFragmentを差し込む -->

    <LinearLayout
        android:id="@+id/fragmenttest"
        android:layout_width="fill_parent"
        android:layout_height="fill_parent"
        android:orientation="vertical" >

        <TextView
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:text="@string/hello" />
    </LinearLayout>

</LinearLayout>

MainActivity.java
beginTransaction()からcommit()までが1つのトランザクション

package com.sakurafish.android.fragmenttest.helloworld;

import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentActivity;
import android.support.v4.app.FragmentTransaction;

public class MainActivity extends FragmentActivity {
    // Compatibility Package を使う場合はActivityではなくFragmentActivityを継承する
    // こうしないと例外が発生する
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);

        Fragment rootFragment = new FragmentTest();
        
        // Compatibility packageを使うとFragmentActivityを継承するので
        // Fragment.Activity.getFragmentManager()は使えないので
        // 代わりにFragmentActivity.getSupportFragmentManager()を使う

        // FragmentTransaction ft = getFragmentManager().beginTransaction();
        FragmentTransaction ft = getSupportFragmentManager().beginTransaction();
        
        //第一引数:ViewGroupのid 第二引数:Fragmentを継承したクラスのインスタンス 第三引数:タグ
        ft.add(R.id.fragmenttest, rootFragment, "rootFragment").commit();
    }
}

Fragmentを継承したクラスを作成する
FragmentTest.java


package com.sakurafish.android.fragmenttest.helloworld;

import android.support.v4.app.Fragment;

/**
 * FragmentでHello World2
 * 
 * @author sakura
 */
public class FragmentTest extends Fragment {
}

挙動は今までのHello Worldと全く同じ。