Fragment的相关用法第一篇
2016-12-31 18:48
477 查看
这篇关于fragment第一篇博客是为了鸿洋大神的博客写个前面的东西。
通过tag查找fragment。
Android.app.FragmentManager.findFragmentByTag(String tag)
使用Fragment,先获取其实例,通过tag找到内存中的实例,如果取到null,再初始化实例。那么tag怎么获取?
1、
android.app.FragmentTransaction.replace(int containerViewId, Fragment fragment, String tag)
的时候用户指定tag,
如:
FragmentManager manager = getChildFragmentManager();//嵌套Fragment需要getChildFragmentManager
if (manager != null) {
// Add default fragments to view. Try to reuse old fragments or create new ones
FragmentTransaction transaction = manager.beginTransaction();
AnalogClockFragment mClockFragment = (AnalogClockFragment) manager
.findFragmentByTag("AnalogClockFragment");
if (mClockFragment == null) {
mClockFragment = new AnalogClockFragment();//子Fragment实例
transaction.replace(R.id.clock_frame, mClockFragment, "AnalogClockFragment");//tag AnalogClockFragment
} else {
transaction.show(mClockFragment);
}
transaction.commit();
}
2、Fragment实例化的时候Android系统会给Fragment对象一个默认的tag
查看源代码 android.support.v4.app.FragmentPagerAdapter
private String getFragmentTag(int position){
//看源代码 android.support.v4.app.FragmentPagerAdapter
return "android:switcher:"+R.id.pager+":"+position;
}
然后根据tag获取fragment对象
getActivity().getFragmentManager().findFragmentByTag(getFragmentTag(position));
这里的position是:如果有多个fragment,position是其顺序号,从0开始,0、1、2。。。
这里的R.id.pager是:fragment所在View容器控件id
我在FragmentA中的EditText填了一些数据,当切换到FragmentB时,如果希望会到A还能看到数据,则适合你的就是hide和show;也就是说,希望保留用户操作的面板,你可以使用hide和show,当然了不要使劲在那new实例,进行下非null判断。
下面的就是实现这种效果的show和hide。
在android开发的布局中,国内大量的使用底部菜单,这个本来不符合android的规范,我个人是深恶痛绝的,但是产品是这样设计的,也只能是这样做了。在这篇博客中,我将结合网上的资料以及自己的使用经验来实现一个底部菜单,解决了很多网友提出的各种问题,在文章中,我只贴出部分的实现代码以及效果图,免得占用大量的篇幅,让大家看的不爽,在最后我会给出整个demo的源码!!!
一般来说,底部菜单是做多五个tab,这里面我做了四个tab,比较符合需求,实现的方式主要有tabhost,直接TextView,RadioButton等,我在这里使用的是RadioButton,觉得RadioButton比较简单控制,又能很好的实现我们的需求,底部菜单的activity_main.xml的代码如下:
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
这个应该很好理解,就是在底部一个RadioGroup,内部放RadioButton来实现,上面放一个FrameLayout来放内容,这是xml部分。
在进行tab切换的过程中,我使用show()和hide()来处理,这样可以保存Fragment的状态,核心代码如下
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
切换的很完美,我们看下效果:
1、上面的实现底部菜单,能够很好的实现Fragment的切换,还能够保存Fragment之前的状态,但是有个很大的问题,就是,我们把app退到后台,我们去玩其他的app,过一段时间回来,这个时候我们的app已经被销毁,我们按多任务键切换回来,发现界面上多个Fragment出现了重叠的情况,这是因为多个Fragment同时显示了,出现了重叠的情况,解决的办法如下:重写Activity的onRestoreInstanceState方法
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
很好的解决了Fragment重叠的情况
2、如果在Fragment有操作toolbar的菜单的情况,除了要在Fragment中设置
2
3
4
5
6
7
8
9
不然的话,在恢复Fragment的时候会出现菜单混乱的情况。
通过tag查找fragment。
Android.app.FragmentManager.findFragmentByTag(String tag)
使用Fragment,先获取其实例,通过tag找到内存中的实例,如果取到null,再初始化实例。那么tag怎么获取?
1、
android.app.FragmentTransaction.replace(int containerViewId, Fragment fragment, String tag)
的时候用户指定tag,
如:
FragmentManager manager = getChildFragmentManager();//嵌套Fragment需要getChildFragmentManager
if (manager != null) {
// Add default fragments to view. Try to reuse old fragments or create new ones
FragmentTransaction transaction = manager.beginTransaction();
AnalogClockFragment mClockFragment = (AnalogClockFragment) manager
.findFragmentByTag("AnalogClockFragment");
if (mClockFragment == null) {
mClockFragment = new AnalogClockFragment();//子Fragment实例
transaction.replace(R.id.clock_frame, mClockFragment, "AnalogClockFragment");//tag AnalogClockFragment
} else {
transaction.show(mClockFragment);
}
transaction.commit();
}
2、Fragment实例化的时候Android系统会给Fragment对象一个默认的tag
查看源代码 android.support.v4.app.FragmentPagerAdapter
private String getFragmentTag(int position){
//看源代码 android.support.v4.app.FragmentPagerAdapter
return "android:switcher:"+R.id.pager+":"+position;
}
然后根据tag获取fragment对象
getActivity().getFragmentManager().findFragmentByTag(getFragmentTag(position));
这里的position是:如果有多个fragment,position是其顺序号,从0开始,0、1、2。。。
这里的R.id.pager是:fragment所在View容器控件id
我在FragmentA中的EditText填了一些数据,当切换到FragmentB时,如果希望会到A还能看到数据,则适合你的就是hide和show;也就是说,希望保留用户操作的面板,你可以使用hide和show,当然了不要使劲在那new实例,进行下非null判断。
下面的就是实现这种效果的show和hide。
android使用Fragment实现底部菜单使用show()和hide()来切换以保持Fragment状态
在android开发的布局中,国内大量的使用底部菜单,这个本来不符合android的规范,我个人是深恶痛绝的,但是产品是这样设计的,也只能是这样做了。在这篇博客中,我将结合网上的资料以及自己的使用经验来实现一个底部菜单,解决了很多网友提出的各种问题,在文章中,我只贴出部分的实现代码以及效果图,免得占用大量的篇幅,让大家看的不爽,在最后我会给出整个demo的源码!!!
底部菜单的设计
一般来说,底部菜单是做多五个tab,这里面我做了四个tab,比较符合需求,实现的方式主要有tabhost,直接TextView,RadioButton等,我在这里使用的是RadioButton,觉得RadioButton比较简单控制,又能很好的实现我们的需求,底部菜单的activity_main.xml的代码如下:<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" tools:context=".MainActivity"> <FrameLayout android:id="@+id/container" android:layout_width="match_parent" android:layout_height="match_parent" android:layout_above="@+id/divide" android:layout_alignParentTop="true"> </FrameLayout> <View android:id="@+id/divide" android:layout_width="match_parent" android:layout_height="1dp" android:layout_above="@+id/activity_group_radioGroup" android:background="#cccccc"/> <RadioGroup android:id="@+id/activity_group_radioGroup" android:layout_width="fill_parent" android:layout_height="wrap_content" android:layout_alignParentBottom="true" android:background="#ffffff" android:checkedButton="@+id/order_process" android:gravity="center" android:orientation="horizontal" android:paddingBottom="3dp" android:paddingTop="3dp"> <RadioButton android:id="@+id/order_process" style="@style/main_tab_bottom" android:layout_width="fill_parent" android:layout_height="match_parent" android:layout_weight="1.0" android:drawableTop="@drawable/main_tab_1" android:gravity="center" android:text="订单处理"/> <RadioButton android:id="@+id/order_query" style="@style/main_tab_bottom" android:layout_width="fill_parent" android:layout_height="match_parent" android:layout_weight="1.0" android:checked="false" android:drawableTop="@drawable/main_tab_2" android:gravity="center" android:text="订单查询"/> <RadioButton android:id="@+id/merchant_manager" style="@style/main_tab_bottom" android:layout_width="fill_parent" android:layout_height="match_parent" android:layout_weight="1.0" android:checked="false" android:drawableTop="@drawable/main_tab_3" android:gravity="center" android:text="门店管理"/> <RadioButton android:id="@+id/setting" style="@style/main_tab_bottom" android:layout_width="fill_parent" android:layout_height="match_parent" android:layout_weight="1.0" android:checked="false" android:drawableTop="@drawable/main_tab_4" android:gravity="center" android:text="设置"/> </RadioGroup> </RelativeLayout>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
这个应该很好理解,就是在底部一个RadioGroup,内部放RadioButton来实现,上面放一个FrameLayout来放内容,这是xml部分。
Java代码控制Fragment的切换
在进行tab切换的过程中,我使用show()和hide()来处理,这样可以保存Fragment的状态,核心代码如下public void onCheckedChanged(RadioGroup group, int checkedId) { FragmentManager fm = getSupportFragmentManager(); FragmentTransaction ft = fm.beginTransaction(); Fragment fragment1 = fm.findFragmentByTag(fragment1Tag); Fragment fragment2 = fm.findFragmentByTag(fragment2Tag); Fragment fragment3 = fm.findFragmentByTag(fragment3Tag); Fragment fragment4 = fm.findFragmentByTag(fragment4Tag); if (fragment1 != null) { ft.hide(fragment1); } if (fragment2 != null) { ft.hide(fragment2); } if (fragment3 != null) { ft.hide(fragment3); } if (fragment4 != null) { ft.hide(fragment4); } switch (checkedId) { case R.id.order_process: if (fragment1 == null) { fragment1 = new Fragment1(); ft.add(R.id.container, fragment1, fragment1Tag); } else { ft.show(fragment1); } break; case R.id.order_query: if (fragment2 == null) { fragment2 = new Fragment2(); ft.add(R.id.container, fragment2, fragment2Tag); } else { ft.show(fragment2); } break; case R.id.merchant_manager: if (fragment3 == null) { fragment3 = new Fragment3(); ft.add(R.id.container, fragment3, fragment3Tag); } else { ft.show(fragment3); } break; case R.id.setting: if (fragment4 == null) { fragment4 = new Fragment4(); ft.add(R.id.container, fragment4, fragment4Tag); } else { ft.show(fragment4); } break; default: break; } ft.commit(); } });1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
切换的很完美,我们看下效果:
问题
1、上面的实现底部菜单,能够很好的实现Fragment的切换,还能够保存Fragment之前的状态,但是有个很大的问题,就是,我们把app退到后台,我们去玩其他的app,过一段时间回来,这个时候我们的app已经被销毁,我们按多任务键切换回来,发现界面上多个Fragment出现了重叠的情况,这是因为多个Fragment同时显示了,出现了重叠的情况,解决的办法如下:重写Activity的onRestoreInstanceState方法@Override protected void onRestoreInstanceState(Bundle savedInstanceState) { super.onRestoreInstanceState(savedInstanceState); for (int i = 0; i < radioGroup.getChildCount(); i++) { RadioButton mTab = (RadioButton) radioGroup.getChildAt(i); FragmentManager fm = getSupportFragmentManager(); Fragment fragment = fm.findFragmentByTag((String) mTab.getTag()); FragmentTransaction ft = fm.beginTransaction(); if (fragment != null) { if (!mTab.isChecked()) { ft.hide(fragment); } } ft.commit(); } }1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
很好的解决了Fragment重叠的情况
2、如果在Fragment有操作toolbar的菜单的情况,除了要在Fragment中设置
setHasOptionsMenu(true);之外,还需要Fragment中重写onHiddenChanged方法:
@Override public void onHiddenChanged(boolean hidden) { super.onHiddenChanged(hidden); if (!hidden) { ((AppCompatActivity) getActivity()).setSupportActionBar(mToolbar); ((AppCompatActivity)getActivity()).getSupportActionBar().setDisplayShowTitleEnabled(false); setHasOptionsMenu(true); } }1
2
3
4
5
6
7
8
9
不然的话,在恢复Fragment的时候会出现菜单混乱的情况。
相关文章推荐
- Fragment的相关用法第四篇(张鸿洋)
- Fragment的相关用法第二篇
- Fragment的相关用法第三篇(张鸿洋)
- javascritp实现input输入框相关限制用法
- 显示当前相关时间的用法DateFormat
- 动态操作Excel相关用法
- Regsvr32用法及相关故障解决
- JTable的相关用法
- 只介绍 Struts 中 Html 标签库 的用法(第二组标签,与Form相关的标签 )
- 关于c# 泛型List集合对象的用法及相关操作
- ResultSet 对象getTables()的用法 获取表的相关信息
- 函数指针的相关用法
- throw on相关词组和用法
- ExitWindowsEx()函数的相关用法
- Repeater的模板及相关用法。。。。。。。。。。。
- 介绍 Struts 中 Html 标签库 的用法(第二组标签,与Form相关的标签 )
- ASSERT的一些相关用法
- datalgrid\datalist\repeater\的用法以及相关小技巧
- javascritp实现input输入框相关限制用法
- 超链接相关用法集