用fragment减少activity

本文介绍了一种使用单个Activity配合多个Fragment实现多页面切换的方法。通过这种方式,可以有效减少Activity的数量,简化页面间的跳转逻辑。文章详细展示了如何通过自定义接口实现Fragment间的通信及页面跳转。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

平常我们写一个完整流程,比如做个转账,第一个页面输入金额,第二个确认金额,第三个展示结果,那么按平常做法是不是要写三个activity来分别写每个页面,这时activity栈就会放入三个activity进去,如果页面越多那么activiy栈层层叠放,我们想做页面跳转起来就麻烦了。

现在我们就用一个activity+三fragment个来实现这三个页面。大体流程就是这样

这里写图片描述

首先贴上代码

public class LoginActivity extends AppCompatActivity implements CallBack {

public static final int TOFRAG_LOGIN = 0x01;
public static final int TOFRAG_NEXT = 0x02;
public static final int TOFRAG_RESULT = 0x03;


public static final int TOFRAG_BACK = 0x99;

private Fragment newFragment;// 当前fragment
private FragmentManager fm;// fragment管理器
private int level;// 当前fragment的等级

@Override
protected void onCreate(Bundle savedInstanceState) {
    // TODO Auto-generated method stub
    super.onCreate(savedInstanceState);
    StatusBarCompat.compat(this);
    setContentView(R.layout.activity_common);
    init();
}

public void init() {
    // TODO Auto-generated method stub
    Bundle bundle = new Bundle();
    bundle.putInt(CommDictAction.TO_FRAG, TOFRAG_LOGIN);
    callback(bundle);
}

@Override
public Bundle callback(Bundle args) {
    // TODO Auto-generated method stub
    if (args != null && args.containsKey(CommDictAction.TO_FRAG)) {
        int to_frag = args.getInt(CommDictAction.TO_FRAG);
        switch (to_frag) {
        case TOFRAG_LOGIN:
            if (newFragment == null) {
                switchFragment(LoginFragment.newInstance(args), 1);
            } else {
                if (newFragment instanceof LoginFragment) {

                } else {
                    switchFragment(LoginFragment.newInstance(args), 1);
                }
            }
            break;
        case TOFRAG_NEXT:
            switchFragment(NextFragment.newInstance(args), 2);
            break;
        case TOFRAG_RESULT:
            switchFragment(ResultFragment.newInstance(args), 3);
            break;
        case TOFRAG_BACK:
            onBackPressed();
            break;
        }
    }
    return null;
}

@Override
public void onBackPressed() {
    // TODO Auto-generated method stub
    super.onBackPressed();
    if (level == 3) {
        level = 2;
        fm.popBackStackImmediate(level + "",
                FragmentManager.POP_BACK_STACK_INCLUSIVE);
        level--;
        newFragment = fm.findFragmentByTag(level + "");
    } else if (level == 2) {
        fm.popBackStackImmediate(level + "",
                FragmentManager.POP_BACK_STACK_INCLUSIVE);
        level--;
        newFragment = fm.findFragmentByTag(level + "");
    } else if (level == 1) {
        finish();
    } else {
        finish();
    }
}

/**
 * 添加fragment的方法
 * 
 * @param newFrag
 *            当前fragment
 * 
 * @param mlevel
 *            当前fragment在栈中的位置
 */
private void switchFragment(BaseFragment newFrag, int mlevel) {
    if (fm == null) {
        fm = getSupportFragmentManager();
    }
    FragmentTransaction ft = fm.beginTransaction();// 对于每一次切换fragment都必须获取一个新的ft
    if (mlevel == 1) {
        ft.setCustomAnimations(R.anim.anim_duration_0,
                R.anim.anim_duration_0);
    } else {
        ft.setCustomAnimations(R.anim.slide_right_in,
                R.anim.slide_left_out, R.anim.slide_left_in,
                R.anim.slide_right_out);
    }
    if (newFragment != null) {// 隐藏上一个fragment
        ft.hide(newFragment);
    }
    level = mlevel;
    newFragment = newFrag;
    ft.add(R.id.fragment, newFragment, level + "");
    ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_OPEN);
    ft.addToBackStack(level + "");
    ft.commit();
}

这里activity实现了一个CallBack的接口,接口代码如下,是为了方便fragment之间的数据传递,在fragment中可以通过该回调接口进行fragment的跳转

public interface CallBack {
/**
 * 回调方法
 * 
 * @param args
 *            传递的参数?
 * @return bundle
 */
public Bundle callback(Bundle args);

}

我的xml文件

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@color/bg_color"
android:fitsSystemWindows="true" >

<FrameLayout
    android:id="@id/fragment"
    android:layout_width="match_parent"
    android:layout_height="match_parent" >
</FrameLayout></RelativeLayout>

如果类似交易很多,activity只需要一个xml就可以了,只是不同fragment之间要配置不同xml。

回到我们的activity中:

callback():
init()方法中调用了callback()方法,初始化一个fragment,该方法也是实现fragment之间跳转的控制器,在不同fragment中可以调用callBack.callback(bundle);来处理跳转到哪个fragment。

switchFragment()方法:
该方法是控制fragment隐藏,显示,动画以及出入栈的控制。ft.setCustomAnimations()是给fragment之间跳转设置跳转动画,也就是fragment进入和退出的动画。ft.hide(newFragment)必须调用,隐藏上一次的fragment,否则页面会出现fragment重叠的现象。ft.add()指定页面上放置fragment的位置,并且设置一个target,也就是level。这里选择add而没有用replace,因为replace是不会保存上一次fragment,每次返回后,都会重新new一个新的fragment。ft.addToBackStack()加入到fragment的回退栈,在处理返回的时候会用到。

onBackPressed()方法:
这里就是处理返回了,popBackStackImmediate()fragment的出栈方法,它会传出要出栈的target,也就是我们上面定义的level。值得注意的是如果当前栈中有1,2,3,4个fragment,我们popBackStackImmediate(2),那么会将2,3,4三个fragment都弹出栈去。

在fragment中要怎么处理跳转了,就这样

    public void login() {
    Bundle bundle = new Bundle();
    bundle.putString("name", et_name.getText().toString());
    bundle.putInt(CommDictAction.TO_FRAG, LoginActivity.TOFRAG_NEXT);
    callBack.callback(bundle);
}

ok,其实fragment在activity中管理很灵活,你还可以加入viewpager做一个仿微信的主页面。

附上代码:
http://download.youkuaiyun.com/detail/gaopin_xianlu/9706355

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值