with tablayout tab support google example ejemplo android android-design-library

support - tablayout android github



Diseño de Android TabLayout Android (7)

Estoy tratando de que funcione el nuevo TabLayout en la biblioteca de diseño de Android.

Estoy siguiendo esta publicación:

http://android-developers.blogspot.com/2015/05/android-design-support-library.html

y la documentación:

http://developer.android.com/reference/android/support/design/widget/TabLayout.html

Y se me ocurrió el siguiente código en mi actividad, pero el tablayout no aparece cuando ejecuto la actividad.

Intenté agregar el archivo de diseño de actividad, pero dice que no puede encontrar esa etiqueta xml.

public class TabActivity extends BaseActivity { SectionPagerAdapter mSectionsPagerAdapter; ViewPager mViewPager; @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_tab); LinearLayout v = (LinearLayout)findViewById(R.id.tabContainer); TabLayout tabLayout = new TabLayout(this); tabLayout.addTab(tabLayout.newTab().setText("Tab 1")); tabLayout.addTab(tabLayout.newTab().setText("Tab 2")); tabLayout.addTab(tabLayout.newTab().setText("Tab 3")); tabLayout.setLayoutParams(new LinearLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT, 50)); v.addView(tabLayout); mSectionsPagerAdapter = new SectionPagerAdapter(getFragmentManager()); mViewPager = (ViewPager) findViewById(R.id.pager); mViewPager.setAdapter(mSectionsPagerAdapter); tabLayout.setupWithViewPager(mViewPager); mViewPager.addOnPageChangeListener(new TabLayout.TabLayoutOnPageChangeListener(tabLayout)); } public class SectionPagerAdapter extends FragmentPagerAdapter { private String TAG = "SectionPagerAdapter"; public SectionPagerAdapter(FragmentManager fm) { super(fm); } @Override public Fragment getItem(int position) { return new Fragment(); } @Override public int getCount() { return 2; } @Override public CharSequence getPageTitle(int position) { Locale l = Locale.getDefault(); switch (position) { case 0: return "test"; case 1: return "test"; case 2: } return null; } } }

Agregué lo siguiente a mi archivo gradle

compile ''com.android.support:design:22.2.0''


Tengo algún problema con el cambio de menú cuando el fragmento cambia en ViewPager. Terminé implementado debajo del código.

Tablero de instrumentos Fragmento

public class DashboardFragment extends BaseFragment { private Context mContext; private TabLayout mTabLayout; private ViewPager mViewPager; private DashboardPagerAdapter mAdapter; private OnModuleChangeListener onModuleChangeListener; private NavDashBoardActivity activityInstance; public void setOnModuleChangeListener(OnModuleChangeListener onModuleChangeListener) { this.onModuleChangeListener = onModuleChangeListener; } @Nullable @Override public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) { return inflater.inflate(R.layout.dashboard_fragment, container, false); } //pass -1 if you want to get it via pager public Fragment getFragmentFromViewpager(int position) { if (position == -1) position = mViewPager.getCurrentItem(); return ((Fragment) (mAdapter.instantiateItem(mViewPager, position))); } @Override public void onViewCreated(View view, @Nullable Bundle savedInstanceState) { super.onViewCreated(view, savedInstanceState); mContext = getActivity(); activityInstance = (NavDashBoardActivity) getActivity(); mTabLayout = (TabLayout) view.findViewById(R.id.tab_layout); mViewPager = (ViewPager) view.findViewById(R.id.view_pager); final List<EnumUtils.Module> moduleToShow = getModuleToShowList(); mViewPager.setOffscreenPageLimit(moduleToShow.size()); for(EnumUtils.Module module :moduleToShow) mTabLayout.addTab(mTabLayout.newTab().setText(EnumUtils.Module.getTabText(module))); updateTabPagerAndMenu(0 , moduleToShow); mAdapter = new DashboardPagerAdapter(getFragmentManager(),moduleToShow); mViewPager.setOffscreenPageLimit(mAdapter.getCount()); mViewPager.setAdapter(mAdapter); mTabLayout.addOnTabSelectedListener(new TabLayout.OnTabSelectedListener() { @Override public void onTabSelected(final TabLayout.Tab tab) { mViewPager.post(new Runnable() { @Override public void run() { mViewPager.setCurrentItem(tab.getPosition()); } }); } @Override public void onTabUnselected(TabLayout.Tab tab) { } @Override public void onTabReselected(TabLayout.Tab tab) { } }); mViewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() { @Override public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) { //added to redraw menu on scroll } @Override public void onPageSelected(int position) { updateTabPagerAndMenu(position , moduleToShow); } @Override public void onPageScrollStateChanged(int state) { } }); } //also validate other checks and this method should be in SharedPrefs... public static List<EnumUtils.Module> getModuleToShowList(){ List<EnumUtils.Module> moduleToShow = new ArrayList<>(); moduleToShow.add(EnumUtils.Module.HOME); moduleToShow.add(EnumUtils.Module.ABOUT); return moduleToShow; } public void setCurrentTab(final int position){ if(mViewPager != null){ mViewPager.postDelayed(new Runnable() { @Override public void run() { mViewPager.setCurrentItem(position); } },100); } } private Fragment getCurrentFragment(){ return mAdapter.getCurrentFragment(); } private void updateTabPagerAndMenu(int position , List<EnumUtils.Module> moduleToShow){ //it helps to change menu on scroll //http://.com/a/27984263/3496570 //No effect after changing below statement ActivityCompat.invalidateOptionsMenu(getActivity()); if(mTabLayout != null) mTabLayout.getTabAt(position).select(); if(onModuleChangeListener != null){ if(activityInstance != null){ activityInstance.updateStatusBarColor( EnumUtils.Module.getStatusBarColor(moduleToShow.get(position))); } onModuleChangeListener.onModuleChanged(moduleToShow.get(position)); mTabLayout.setSelectedTabIndicatorColor(EnumUtils.Module.getModuleColor(moduleToShow.get(position))); mTabLayout.setTabTextColors(ContextCompat.getColor(mContext,android.R.color.black) , EnumUtils.Module.getModuleColor(moduleToShow.get(position))); } } }

dashboardfragment.xml

<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools" android:id="@+id/main_layout" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" tools:context=".MainActivity"> <!-- our tablayout to display tabs --> <android.support.design.widget.TabLayout android:id="@+id/tab_layout" android:layout_width="match_parent" android:layout_height="wrap_content" android:background="?attr/colorPrimary" android:minHeight="?attr/actionBarSize" android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar" app:tabBackground="@android:color/white" app:tabGravity="fill" app:tabIndicatorHeight="4dp" app:tabMode="scrollable" app:tabSelectedTextColor="@android:color/black" app:tabTextColor="@android:color/black" /> <!-- View pager to swipe views --> <android.support.v4.view.ViewPager android:id="@+id/view_pager" android:layout_width="match_parent" android:layout_height="match_parent" app:layout_behavior="@string/appbar_scrolling_view_behavior" /> </LinearLayout>

DashboardPagerAdapter

public class DashboardPagerAdapter extends FragmentPagerAdapter { private List<EnumUtils.Module> moduleList; private Fragment mCurrentFragment = null; public DashboardPagerAdapter(FragmentManager fm, List<EnumUtils.Module> moduleList){ super(fm); this.moduleList = moduleList; } @Override public Fragment getItem(int position) { return EnumUtils.Module.getDashboardFragment(moduleList.get(position)); } @Override public int getCount() { return moduleList.size(); } @Override public void setPrimaryItem(ViewGroup container, int position, Object object) { if (getCurrentFragment() != object) { mCurrentFragment = ((Fragment) object); } super.setPrimaryItem(container, position, object); } public Fragment getCurrentFragment() { return mCurrentFragment; } public int getModulePosition(EnumUtils.Module moduleName){ for(int x = 0 ; x < moduleList.size() ; x++){ if(moduleList.get(x).equals(moduleName)) return x; } return -1; }

}

Y en cada página de Fragment setHasOptionMenu(true) en onCreate e implementa onCreateOptionMenu . entonces funcionará correctamente.

DASHACTIVIDAD

public class NavDashBoardActivity extends BaseActivity implements NavigationView.OnNavigationItemSelectedListener { private Context mContext; private DashboardFragment dashboardFragment; private Toolbar mToolbar; private DrawerLayout drawer; private ActionBarDrawerToggle toggle; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_nav_dash_board); mContext = NavDashBoardActivity.this; if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { getWindow().addFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS); getWindow().clearFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS); getWindow().setStatusBarColor(ContextCompat.getColor(mContext,R.color.yellow_action_bar)); } mToolbar = (Toolbar) findViewById(R.id.toolbar); setSupportActionBar(mToolbar); updateToolbarText(new ToolbarTextBO("NCompass " ,"")); drawer = (DrawerLayout) findViewById(R.id.drawer_layout); toggle = new ActionBarDrawerToggle( this, drawer, mToolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close); drawer.addDrawerListener(toggle); toggle.syncState(); //onclick of back button on Navigation it will popUp fragment... toggle.setToolbarNavigationClickListener(new View.OnClickListener() { @Override public void onClick(View view) { if(!toggle.isDrawerIndicatorEnabled()) { getSupportFragmentManager().popBackStack(); } } }); final NavigationView navigationView = (NavigationView) findViewById(R.id.nav_view); navigationView.setItemIconTintList(null);//It helps to show icon on Navigation updateNavigationMenuItem(navigationView); navigationView.setNavigationItemSelectedListener(this); //Left Drawer Upper Section View headerLayout = navigationView.getHeaderView(0); // 0-index header TextView userNameTv = (TextView) headerLayout.findViewById(R.id.tv_user_name); userNameTv.setText(AuthSharePref.readUserLoggedIn().getFullName()); RoundedImageView ivUserPic = (RoundedImageView) headerLayout.findViewById(R.id.iv_user_pic); ivUserPic.setImageResource(R.drawable.profile_img); headerLayout.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View view) { //close drawer and add a fragment to it drawer.closeDrawers();//also try other methods.. } }); //ZA code starts... dashboardFragment = new DashboardFragment(); dashboardFragment.setOnModuleChangeListener(new OnModuleChangeListener() { @Override public void onModuleChanged(EnumUtils.Module module) { if(mToolbar != null){ mToolbar.setBackgroundColor(EnumUtils.Module.getModuleColor(module)); if(EnumUtils.Module.getMenuID(module) != -1) navigationView.getMenu().findItem(EnumUtils.Module.getMenuID(module)).setChecked(true); } } }); addBaseFragment(dashboardFragment); backStackListener(); } public void updateStatusBarColor(int colorResourceID){ if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { getWindow().addFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS); getWindow().clearFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS); getWindow().setStatusBarColor(colorResourceID); } } private void updateNavigationMenuItem(NavigationView navigationView){ List<EnumUtils.Module> modules = DashboardFragment.getModuleToShowList(); if(!modules.contains(EnumUtils.Module.MyStores)){ navigationView.getMenu().findItem(R.id.nav_my_store).setVisible(false); } if(!modules.contains(EnumUtils.Module.Livewall)){ navigationView.getMenu().findItem(R.id.nav_live_wall).setVisible(false); } } private void backStackListener(){ getSupportFragmentManager().addOnBackStackChangedListener(new FragmentManager.OnBackStackChangedListener() { @Override public void onBackStackChanged() { if(getSupportFragmentManager().getBackStackEntryCount() >= 1) { toggle.setDrawerIndicatorEnabled(false); //disable "hamburger to arrow" drawable toggle.setHomeAsUpIndicator(R.drawable.ic_arrow_back_black_24dp); //set your own ///toggle.setDrawerArrowDrawable(); ///toggle.setDrawerIndicatorEnabled(false); // this will hide hamburger image ///Toast.makeText(mContext,"Update to Arrow",Toast.LENGTH_SHORT).show(); } else{ toggle.setDrawerIndicatorEnabled(true); } if(getSupportFragmentManager().getBackStackEntryCount() >0){ if(getCurrentFragment() instanceof DashboardFragment){ Fragment subFragment = ((DashboardFragment) getCurrentFragment()) .getViewpager(-1); } } else{ } } }); } private void updateToolBarTitle(String title){ getSupportActionBar().setTitle(title); } public void updateToolBarColor(String hexColor){ if(mToolbar != null) mToolbar.setBackgroundColor(Color.parseColor(hexColor)); } @Override public void onBackPressed() { DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout); if (drawer.isDrawerOpen(GravityCompat.START)) { drawer.closeDrawer(GravityCompat.START); } else { super.onBackPressed(); } } @Override public boolean onCreateOptionsMenu(Menu menu) { if (drawer.isDrawerOpen(GravityCompat.START)) getMenuInflater().inflate(R.menu.empty, menu); return super.onCreateOptionsMenu(menu);//true is wriiten first.. } @Override public boolean onOptionsItemSelected(MenuItem item) { // Handle action bar item clicks here. The action bar will // automatically handle clicks on the Home/Up button, so long // as you specify a parent activity in AndroidManifest.xml. int id = item.getItemId(); if (id == android.R.id.home) { if (drawer.isDrawerOpen(GravityCompat.START)) drawer.closeDrawer(GravityCompat.START); else { if (getSupportFragmentManager().getBackStackEntryCount() > 0) { } else drawer.openDrawer(GravityCompat.START); } return false;///true; } return false;// false so that fragment can also handle the menu event. Otherwise it is handled their ///return super.onOptionsItemSelected(item); } @SuppressWarnings("StatementWithEmptyBody") @Override public boolean onNavigationItemSelected(MenuItem item) { // Handle navigation view item clicks here. int id = item.getItemId(); if (id == R.id.nav_my_store) { // Handle the camera action dashboardFragment.setCurrentTab(EnumUtils.Module.MyStores); } }else if (id == R.id.nav_log_out) { Dialogs.logOut(mContext); } DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout); drawer.closeDrawer(GravityCompat.START); return true; } public void updateToolbarText(ToolbarTextBO toolbarTextBO){ mToolbar.setTitle(""); mToolbar.setSubtitle(""); if(toolbarTextBO.getTitle() != null && !toolbarTextBO.getTitle().isEmpty()) mToolbar.setTitle(toolbarTextBO.getTitle()); if(toolbarTextBO.getDescription() != null && !toolbarTextBO.getDescription().isEmpty()) mToolbar.setSubtitle(toolbarTextBO.getDescription());*/ } @Override public void onPostCreate(@Nullable Bundle savedInstanceState, @Nullable PersistableBundle persistentState) { super.onPostCreate(savedInstanceState, persistentState); // Sync the toggle state after onRestoreInstanceState has occurred. toggle.syncState(); } @Override public void onConfigurationChanged(Configuration newConfig) { super.onConfigurationChanged(newConfig); toggle.onConfigurationChanged(newConfig); } }


Acabo de configurar un nuevo TabLayout, así que aquí están los pasos rápidos para hacerlo (ノ ◕ ヮ ◕) ノ *: ・ ゚ ✧

  1. Agregue dependencias dentro de su archivo build.gradle:

    dependencies { compile ''com.android.support:design:23.1.1'' }

  2. Agregue TabLayout dentro de su diseño

    <?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"> <android.support.v7.widget.Toolbar android:id="@+id/toolbar" android:layout_width="match_parent" android:layout_height="wrap_content" android:background="?attr/colorPrimary"/> <android.support.design.widget.TabLayout android:id="@+id/tab_layout" android:layout_width="match_parent" android:layout_height="wrap_content"/> <android.support.v4.view.ViewPager android:id="@+id/pager" android:layout_width="match_parent" android:layout_height="match_parent"/> </LinearLayout>

  3. Configure su actividad de esta manera:

    import android.os.Bundle; import android.support.design.widget.TabLayout; import android.support.v4.app.Fragment; import android.support.v4.app.FragmentManager; import android.support.v4.app.FragmentPagerAdapter; import android.support.v4.view.ViewPager; import android.support.v7.app.AppCompatActivity; import android.support.v7.widget.Toolbar; public class TabLayoutActivity extends AppCompatActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_pull_to_refresh); Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar); TabLayout tabLayout = (TabLayout) findViewById(R.id.tab_layout); ViewPager viewPager = (ViewPager) findViewById(R.id.pager); if (toolbar != null) { setSupportActionBar(toolbar); } viewPager.setAdapter(new SectionPagerAdapter(getSupportFragmentManager())); tabLayout.setupWithViewPager(viewPager); } public class SectionPagerAdapter extends FragmentPagerAdapter { public SectionPagerAdapter(FragmentManager fm) { super(fm); } @Override public Fragment getItem(int position) { switch (position) { case 0: return new FirstTabFragment(); case 1: default: return new SecondTabFragment(); } } @Override public int getCount() { return 2; } @Override public CharSequence getPageTitle(int position) { switch (position) { case 0: return "First Tab"; case 1: default: return "Second Tab"; } } } }


Agregue esto al módulo build.gradle:

implementation ''com.android.support.constraint:constraint-layout:1.1.3'' implementation ''com.android.support:design:28.0.0''


Así de fácil:

XML:

<android.support.design.widget.TabLayout android:id="@+id/tab_layout" android:layout_width="match_parent" android:layout_height="wrap_content" android:background="#fff"/> <android.support.v4.view.ViewPager android:id="@+id/viewpager" android:layout_width="match_parent" android:layout_height="wrap_content"/>

Código Java:

private ViewPager viewPager; private String[] PAGE_TITLES = new String[]{ "text1", "text1", "text3" }; private final Fragment[] PAGES = new Fragment[]{ new fragment1(), new fragment2(), new fragment3() }; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.layout_a_requests); /**TODO ***************tebLayout*************************/ viewPager = findViewById(R.id.viewpager); viewPager.setAdapter(new MyPagerAdapter(getSupportFragmentManager())); TabLayout tabLayout = findViewById(R.id.tab_layout); tabLayout.setSelectedTabIndicatorColor(Color.parseColor("#1f57ff")); tabLayout.setSelectedTabIndicatorHeight((int) (4 * getResources().getDisplayMetrics().density)); tabLayout.setTabTextColors(Color.parseColor("#9d9d9d"), Color.parseColor("#0d0e10")); tabLayout.setupWithViewPager(viewPager); /***************************************************************************/ }


Trato de resolver aquí está mi código.

primero agregue dependencia en build.gradle (aplicación).

dependencies { compile ''com.android.support:design:23.1.1'' }

Crear PagerAdapter.class

public class PagerAdapter extends FragmentPagerAdapter { private final List<Fragment> mFragmentList = new ArrayList<>(); private final List<String> mFragmentTitleList = new ArrayList<>(); public PagerAdapter(FragmentManager manager) { super(manager); } @Override public Fragment getItem(int position) { Log.i("PosTabItem",""+position); return mFragmentList.get(position); } @Override public int getCount() { return mFragmentList.size(); } public void addFragment(Fragment fragment, String title) { mFragmentList.add(fragment); mFragmentTitleList.add(title); } @Override public CharSequence getPageTitle(int position) { Log.i("PosTab",""+position); return mFragmentTitleList.get(position); } }

crear actividad_principal.xml

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools" android:id="@+id/main_layout" android:layout_width="match_parent" android:layout_height="match_parent" tools:context=".MainActivity"> <android.support.v7.widget.Toolbar android:id="@+id/toolbar" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_alignParentTop="true" android:background="?attr/colorPrimary" android:elevation="6dp" android:minHeight="?attr/actionBarSize" android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar" app:popupTheme="@style/ThemeOverlay.AppCompat.Light" /> <android.support.design.widget.TabLayout android:id="@+id/tab_layout" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_below="@+id/toolbar" android:background="?attr/colorPrimary" android:elevation="6dp" android:minHeight="?attr/actionBarSize" android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar" /> <android.support.v4.view.ViewPager android:id="@+id/pager" android:layout_width="match_parent" android:layout_height="fill_parent" android:layout_below="@id/tab_layout" /> </RelativeLayout>

crear MainActivity.class

public class MainActivity extends AppCompatActivity { Pager pager; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar); setSupportActionBar(toolbar); TabLayout tabLayout = (TabLayout) findViewById(R.id.tab_layout); final ViewPager viewPager = (ViewPager) findViewById(R.id.pager); pager = new Pager(getSupportFragmentManager()); pager.addFragment(new FragmentOne(), "One"); viewPager.setAdapter(pager); tabLayout.setupWithViewPager(viewPager); tabLayout.setTabMode(TabLayout.MODE_FIXED); tabLayout.setSmoothScrollingEnabled(true); viewPager.addOnPageChangeListener(new TabLayout.TabLayoutOnPageChangeListener(tabLayout)); tabLayout.setOnTabSelectedListener(new TabLayout.OnTabSelectedListener() { @Override public void onTabSelected(TabLayout.Tab tab) { viewPager.setCurrentItem(tab.getPosition()); } @Override public void onTabUnselected(TabLayout.Tab tab) { } @Override public void onTabReselected(TabLayout.Tab tab) { } }); } }

y finalmente crear un fragmento para agregar en el visor

cajón fragment_one.xml

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="vertical" android:layout_width="match_parent" android:layout_height="match_parent"> <TextView android:text="Location" android:layout_width="match_parent" android:layout_height="wrap_content" /> </LinearLayout>

Crear FragmentOne.class

public class FragmentOne extends Fragment { @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { View view = inflater.inflate(R.layout.fragment_one, container,false); return view; } }


Tuve que recopilar información de varias fuentes para armar un TabLayout funcional. Lo siguiente se presenta como un caso de uso completo que puede modificarse según sea necesario.

Asegúrese de que el archivo del módulo build.gradle contiene una dependencia de com.android.support:design .

dependencies { compile ''com.android.support:design:23.1.1'' }

En mi caso, estoy creando una actividad Acerca de en la aplicación con un TabLayout. Agregué la siguiente sección a AndroidMainifest.xml . La configuración de parentActivityName permite que la flecha de inicio lleve al usuario a la actividad principal.

<!-- android:configChanges="orientation|screenSize" makes the activity not reload when the orientation changes. --> <activity android:name=".AboutActivity" android:label="@string/about_app" android:theme="@style/MyApp.About" android:parentActivityName=".MainActivity" android:configChanges="orientation|screenSize" > <!-- android.support.PARENT_ACTIVITY is necessary for API <= 15. --> <meta-data android:name="android.support.PARENT_ACTIVITY" android:value=".MainActivity" /> </activity>

styles.xml contiene las siguientes entradas. Esta aplicación tiene una barra de aplicaciones blanca para la actividad principal y una barra de aplicaciones azul para la actividad Acerca de. Necesitamos establecer colorPrimaryDark para la actividad Acerca de para que la barra de estado sobre la barra de aplicaciones sea azul.

<style name="MyApp" parent="Theme.AppCompat.Light.NoActionBar"> <item name="colorAccent">@color/blue</item> </style> <style name="MyApp.About" /> <!-- ThemeOverlay.AppCompat.Dark.ActionBar" makes the text and the icons in the AppBar white. --> <style name="MyApp.DarkAppBar" parent="ThemeOverlay.AppCompat.Dark.ActionBar" /> <style name="MyApp.AppBarOverlay" parent="ThemeOverlay.AppCompat.ActionBar" /> <style name="MyApp.PopupOverlay" parent="ThemeOverlay.AppCompat.Light" />

También hay un styles.xml (v19) . Se encuentra en src/main/res/values-v19/styles.xml . Este archivo solo se aplica si la API del dispositivo es> = 19.

<!-- android:windowTranslucentStatus requires API >= 19. It makes the system status bar transparent. When it is specified the root layout should include android:fitsSystemWindows="true". colorPrimaryDark goes behind the status bar, which is then darkened by the overlay. --> <style name="MyApp.About"> <item name="android:windowTranslucentStatus">true</item> <item name="colorPrimaryDark">@color/blue</item> </style>

AboutActivity.java contiene el siguiente código. En mi caso, tengo un número fijo de pestañas (7) para poder eliminar todo el código relacionado con pestañas dinámicas.

import android.os.Bundle; import android.support.design.widget.TabLayout; import android.support.v4.app.Fragment; import android.support.v4.app.FragmentManager; import android.support.v4.app.FragmentPagerAdapter; import android.support.v4.view.ViewPager; import android.support.v7.app.ActionBar; import android.support.v7.app.AppCompatActivity; import android.support.v7.widget.Toolbar; public class AboutActivity extends AppCompatActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.about_coordinatorlayout); // We need to use the SupportActionBar from android.support.v7.app.ActionBar until the minimum API is >= 21. Toolbar supportAppBar = (Toolbar) findViewById(R.id.about_toolbar); setSupportActionBar(supportAppBar); // Display the home arrow on supportAppBar. final ActionBar appBar = getSupportActionBar(); assert appBar != null;// This assert removes the incorrect warning in Android Studio on the following line that appBar might be null. appBar.setDisplayHomeAsUpEnabled(true); // Setup the ViewPager. ViewPager aboutViewPager = (ViewPager) findViewById(R.id.about_viewpager); assert aboutViewPager != null; // This assert removes the incorrect warning in Android Studio on the following line that aboutViewPager might be null. aboutViewPager.setAdapter(new aboutPagerAdapter(getSupportFragmentManager())); // Setup the TabLayout and connect it to the ViewPager. TabLayout aboutTabLayout = (TabLayout) findViewById(R.id.about_tablayout); assert aboutTabLayout != null; // This assert removes the incorrect warning in Android Studio on the following line that aboutTabLayout might be null. aboutTabLayout.setupWithViewPager(aboutViewPager); } public class aboutPagerAdapter extends FragmentPagerAdapter { public aboutPagerAdapter(FragmentManager fm) { super(fm); } @Override // Get the count of the number of tabs. public int getCount() { return 7; } @Override // Get the name of each tab. Tab numbers start at 0. public CharSequence getPageTitle(int tab) { switch (tab) { case 0: return getString(R.string.version); case 1: return getString(R.string.permissions); case 2: return getString(R.string.privacy_policy); case 3: return getString(R.string.changelog); case 4: return getString(R.string.license); case 5: return getString(R.string.contributors); case 6: return getString(R.string.links); default: return ""; } } @Override // Setup each tab. public Fragment getItem(int tab) { return AboutTabFragment.createTab(tab); } } }

AboutTabFragment.java se utiliza para completar cada pestaña. En mi caso, la primera pestaña tiene un LinearLayout dentro de un ScrollView y todos los demás tienen un WebView como diseño raíz.

import android.os.Build; import android.os.Bundle; import android.support.v4.app.Fragment; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.webkit.WebView; import android.widget.TextView; public class AboutTabFragment extends Fragment { private int tabNumber; // AboutTabFragment.createTab stores the tab number in the bundle arguments so it can be referenced from onCreate(). public static AboutTabFragment createTab(int tab) { Bundle thisTabArguments = new Bundle(); thisTabArguments.putInt("Tab", tab); AboutTabFragment thisTab = new AboutTabFragment(); thisTab.setArguments(thisTabArguments); return thisTab; } @Override public void onCreate (Bundle savedInstanceState) { super.onCreate(savedInstanceState); // Store the tab number in tabNumber. tabNumber = getArguments().getInt("Tab"); } @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { View tabLayout; // Load the about tab layout. Tab numbers start at 0. if (tabNumber == 0) { // Setting false at the end of inflater.inflate does not attach the inflated layout as a child of container. // The fragment will take care of attaching the root automatically. tabLayout = inflater.inflate(R.layout.about_tab_version, container, false); } else { // load a WebView for all the other tabs. Tab numbers start at 0. // Setting false at the end of inflater.inflate does not attach the inflated layout as a child of container. // The fragment will take care of attaching the root automatically. tabLayout = inflater.inflate(R.layout.about_tab_webview, container, false); WebView tabWebView = (WebView) tabLayout; switch (tabNumber) { case 1: tabWebView.loadUrl("file:///android_asset/about_permissions.html"); break; case 2: tabWebView.loadUrl("file:///android_asset/about_privacy_policy.html"); break; case 3: tabWebView.loadUrl("file:///android_asset/about_changelog.html"); break; case 4: tabWebView.loadUrl("file:///android_asset/about_license.html"); break; case 5: tabWebView.loadUrl("file:///android_asset/about_contributors.html"); break; case 6: tabWebView.loadUrl("file:///android_asset/about_links.html"); break; default: break; } } return tabLayout; } }

about_coordinatorlayout.xml es el siguiente:

<!-- android:fitsSystemWindows="true" moves the AppBar below the status bar. When it is specified the theme should include <item name="android:windowTranslucentStatus">true</item> to make the status bar a transparent, darkened overlay. --> <android.support.design.widget.CoordinatorLayout android:id="@+id/about_coordinatorlayout" xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" android:layout_height="match_parent" android:layout_width="match_parent" android:fitsSystemWindows="true" > <!-- the LinearLayout with orientation="vertical" moves the ViewPager below the AppBarLayout. --> <LinearLayout android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" > <!-- We need to set android:background="@color/blue" here or any space to the right of the TabLayout on large devices will be white. --> <android.support.design.widget.AppBarLayout android:id="@+id/about_appbarlayout" android:layout_height="wrap_content" android:layout_width="match_parent" android:background="@color/blue" android:theme="@style/MyApp.AppBarOverlay" > <!-- android:theme="@style/PrivacyBrowser.DarkAppBar" makes the text and icons in the AppBar white. --> <android.support.v7.widget.Toolbar android:id="@+id/about_toolbar" android:layout_width="match_parent" android:layout_height="wrap_content" android:background="@color/blue" android:theme="@style/MyApp.DarkAppBar" app:popupTheme="@style/MyApp.PopupOverlay" /> <android.support.design.widget.TabLayout android:id="@+id/about_tablayout" xmlns:android.support.design="http://schemas.android.com/apk/res-auto" android:layout_height="wrap_content" android:layout_width="match_parent" android.support.design:tabBackground="@color/blue" android.support.design:tabTextColor="@color/light_blue" android.support.design:tabSelectedTextColor="@color/white" android.support.design:tabIndicatorColor="@color/white" android.support.design:tabMode="scrollable" /> </android.support.design.widget.AppBarLayout> <!-- android:layout_weight="1" makes about_viewpager fill the rest of the screen. --> <android.support.v4.view.ViewPager android:id="@+id/about_viewpager" android:layout_width="match_parent" android:layout_height="0dp" android:layout_weight="1" /> </LinearLayout> </android.support.design.widget.CoordinatorLayout>

about_tab_version.xml es el siguiente:

<!-- The ScrollView allows the LinearLayout to scroll if it exceeds the height of the page. --> <ScrollView android:id="@+id/about_version_scrollview" xmlns:android="http://schemas.android.com/apk/res/android" android:layout_height="wrap_content" android:layout_width="match_parent" > <LinearLayout android:id="@+id/about_version_linearlayout" android:layout_height="wrap_content" android:layout_width="match_parent" android:orientation="vertical" android:padding="16dp" > <!-- Include whatever content you want in this tab here. --> </LinearLayout> </ScrollView>

Y about_tab_webview.xml :

<!-- This WebView displays inside of the tabs in AboutActivity. --> <WebView android:id="@+id/about_tab_webview" xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" />

También hay entradas en strings.xml

<string name="about_app">About App</string> <string name="version">Version</string> <string name="permissions">Permissions</string> <string name="privacy_policy">Privacy Policy</string> <string name="changelog">Changelog</string> <string name="license">License</string> <string name="contributors">Contributors</string> <string name="links">Links</string>

Y colors.xml

<color name="blue">#FF1976D2</color> <color name="light_blue">#FFBBDEFB</color> <color name="white">#FFFFFFFF</color>

src/main/assets contiene los archivos HTML a los que se hace referencia en AboutTabFragemnt.java .


<?xml version="1.0" encoding="utf-8"?> <android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools" android:id="@+id/main_content" android:layout_width="match_parent" android:layout_height="match_parent" android:fitsSystemWindows="true" tools:context=".ui.MainActivity" > <android.support.design.widget.AppBarLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"> <android.support.v7.widget.Toolbar android:id="@+id/toolbar" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_alignParentTop="true" android:background="?attr/colorPrimary" android:elevation="6dp" android:minHeight="?attr/actionBarSize" android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar" app:popupTheme="@style/ThemeOverlay.AppCompat.Light" /> <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.TabItem android:id="@+id/tabItem" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="@string/tab_text_1" /> <android.support.design.widget.TabItem android:id="@+id/tabItem2" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="@string/tab_text_2" /> <android.support.design.widget.TabItem android:id="@+id/tabItem3" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="@string/tab_text_3" /> <android.support.design.widget.TabItem android:id="@+id/tItemab4" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="@string/tab_text_4" /> </android.support.design.widget.TabLayout> </android.support.design.widget.AppBarLayout> <android.support.v4.view.ViewPager android:id="@+id/container" android:layout_width="match_parent" android:layout_height="match_parent" android:layout_below="@id/tabs" app:layout_behavior="@string/appbar_scrolling_view_behavior" tools:ignore="NotSibling"/> </android.support.constraint.ConstraintLayout>

<?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:id="@+id/activity_main" android:layout_width="match_parent" android:layout_height="match_parent" tools:context=".ui.MainActivity"> <include layout="@layout/tabs"></include> <LinearLayout android:orientation="vertical" android:layout_width="match_parent" android:layout_height="match_parent" android:layout_marginBottom="@dimen/activity_vertical_margin" android:layout_marginLeft="@dimen/activity_horizontal_margin" android:layout_marginRight="@dimen/activity_horizontal_margin" android:layout_marginTop="80dp"> <FrameLayout android:id="@+id/tabContent" android:layout_weight="1" android:layout_width="match_parent" android:layout_height="0dp"> </FrameLayout> </LinearLayout> </RelativeLayout>

public class MainActivity extends AppCompatActivity{ private Toolbar toolbar; private TabLayout tabLayout; private ViewPagerAdapter adapter; private final static int[] tabIcons = { R.drawable.ic_action_car, android.R.drawable.ic_menu_mapmode, android.R.drawable.ic_dialog_email, R.drawable.ic_action_settings }; protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar); setSupportActionBar(toolbar); ViewPager viewPager = (ViewPager) findViewById(R.id.container); 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]); tabLayout.getTabAt(3).setIcon(tabIcons[3]); } private void setupViewPager(ViewPager viewPager) { adapter = new ViewPagerAdapter(getSupportFragmentManager()); adapter.addFrag(new CarFragment()); adapter.addFrag(new LocationFragment()); adapter.addFrag(new MessageFragment()); adapter.addFrag(new SettingsFragment()); 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); } } }