【发布时间】:2016-12-25 05:42:24
【问题描述】:
我想要什么。
在选项卡滑动菜单上下文中,我想将一个片段替换为选项卡内的另一个片段,并维护选项卡菜单以及当前选项卡。当滑动到另一个选项卡并返回原始时,我希望显示最后一个片段。
例如,我有tab_a 和Fragment_1,tab_b 和Fragment_4 和tab_c 和Fragment_7。现在我想要Fragment_1 中的一个按钮打开我Fragment_2,但我希望能够滑动到tab_b 和tab_c 的片段。而当我返回tab_a时,Fragment_2必须显示出来。
MainActivity
|
|
ContainerFragment
|
|
|_ _ _ Tab A
| |_ _ _ Fragment 1
| |
| |_ _ _ Fragment 2
| |
| |_ _ _ Fragment 3
| |
| |_ _ _ ...
|
|_ _ _ Tab B
| |_ _ _ Fragment 4
| |
| |_ _ _ Fragment 5
| |
| |_ _ _ Fragment 6
| |
| |_ _ _ ...
|
|_ _ _ Tab C
| |_ _ _ Fragment 7
| |
| |_ _ _ Fragment 8
| |
| |_ _ _ Fragment 8
| |
| |_ _ _ ...
我目前的主要活动。
Xml
<android.support.design.widget.CoordinatorLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:id="@+id/activity_main"
android:layout_width="match_parent"
android:layout_height="match_parent">
<android.support.design.widget.AppBarLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar">
<android.support.design.widget.TabLayout
android:id="@+id/tabs"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:tabMode="fixed"
app:tabGravity="fill"/>
</android.support.design.widget.AppBarLayout>
<android.support.v4.view.ViewPager
android:id="@+id/viewpager"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layout_behavior="@string/appbar_scrolling_view_behavior" />
</android.support.design.widget.CoordinatorLayout>
代码
public class MainActivity extends AppCompatActivity {
private TabLayout tabLayout;
private final static int[] tabIcons = {
R.drawable.ic_tab_a,
R.drawable.ic_tab_b,
R.drawable.ic_tab_c
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ViewPager viewPager = (ViewPager) findViewById(R.id.viewpager);
setupViewPager(viewPager);
tabLayout = (TabLayout) findViewById(R.id.tabs);
tabLayout.setupWithViewPager(viewPager);
setupTabIcons();
}
private void setupTabIcons() {
tabLayout.getTabAt(0).setIcon(tabIcons[0]);
tabLayout.getTabAt(1).setIcon(tabIcons[1]);
tabLayout.getTabAt(2).setIcon(tabIcons[2]);
}
private void setupViewPager(ViewPager viewPager) {
ViewPagerAdapter adapter = new ViewPagerAdapter(getSupportFragmentManager());
adapter.addFrag(new Fragment1());
adapter.addFrag(new Fragment4());
adapter.addFrag(new Fragment7());
viewPager.setAdapter(adapter);
}
class ViewPagerAdapter extends FragmentPagerAdapter {
private final List<Fragment> mFragmentList = new ArrayList<>();
ViewPagerAdapter(FragmentManager manager) {
super(manager);
}
@Override
public Fragment getItem(int position) {
return mFragmentList.get(position);
}
@Override
public int getCount() {
return mFragmentList.size();
}
void addFrag(Fragment fragment) {
mFragmentList.add(fragment);
}
}
}
片段
Xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:background="@android:color/holo_blue_light"
android:id="@+id/fragment_1"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="myContext">
<Button
android:text="Go to next Fragment"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerVertical="true"
android:layout_centerHorizontal="true"
android:id="@+id/button_nextFrag" />
<FrameLayout
android:id="@+id/tab1_container"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
</RelativeLayout>
代码
public class Fragment1 extends Fragment {
private void goNextFragment() {
FragmentTransaction trans = getFragmentManager().beginTransaction();
trans.replace(R.id.tab1_container, new Fragment2());
trans.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_OPEN);
trans.addToBackStack(null);
trans.commit();
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment.
View root = inflater.inflate(R.layout.fragment_1, container, false);
// Go to next Fragment Button.
final Button nextFrag = (Button) root.findViewById(R.id.button_nextFrag);
nextFrag .setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
goNextFragment();
}
});
return root;
}
}
编辑:
我有一些解决方案,但没有一个是完美的。如果我在 MainActivity 中放置 Framelayaout,Fragment_1 会正确替换为Fragment_2,但它也在tab_b 和tab_c 中。如果FrameLayout在Fragment_1,我可以正确滑动其他标签,但是替换不好,因为Fragment_2打开了,但Fragment_1也在。
【问题讨论】:
-
你的情况到底发生了什么?屏幕方向是否会重新填充初始状态的所有片段?
-
@ReazMurshed 我还没有达到这一点,我仍在正确替换片段。我见过另一种解决方案,其中一些可能包含为每个片段进行大切换,但如果我们考虑一个包含很多片段的大场景,这个解决方案不可能是最好的,我相信必须有一个更好的解决方案。
-
@SantiGil 你的意思是你想要像 Flipboard 应用这样的东西?标签内的标签?
-
几个月前我写了一篇关于该主题的博客文章:medium.com/@nilan/… :)
-
我刚刚发布了一个答案! :) 如果您的意思是要弹出两次回退堆栈,则可以再次触发后退按钮事件作为 hack:
this.dispatchKeyEvent(new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_BACK));
标签: java android android-fragments android-viewpager android-tablayout