Fragment+FragmentTabHost实现仿QQ底部菜单栏

2015-11-04 21:15 阅读 6,183 次 评论 4 条
版权声明:本文著作权归TeachCourse所有,未经许可禁止转载,谢谢支持!
转载请注明出处:http://teachcourse.cn/627.html

QQ人群里使用最多的手机APP之一,它的设计、排版都深受大众的喜爱,那么你想不想知道QQ的底部导航是如何实现的呢?其实很简单,通过Fragment+FragmentTabHost我们就可以轻松实现类似QQ底部导航的效果。
Fragment+FragmentTabHost实现仿QQ导航
第一步:看到QQ底部导航只要有三栏,第一栏是“消息”,第二栏“联系人”,第三栏“动态”,可以自由的在这三栏导航中来回的切换,然后在上面展示不同的内容。这三栏中的一个特点是:文字的上面是一张图标,所以在制作布局的时候我们可以只需要一个模板就可以了,我们将这个模板命名为qq_nav_item.xml,具体代码如下:

  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  3. android:layout_width="match_parent"  
  4. android:layout_height="wrap_content"  
  5. android:gravity="center"  
  6. android:orientation="vertical" >  
  7.   
  8. <ImageView  
  9. android:id="@+id/qq_nav_icon_iv"  
  10. android:layout_width="wrap_content"  
  11. android:layout_height="wrap_content"  
  12. android:focusable="false"  
  13. android:padding="3dp"  
  14. android:src="@drawable/tab_message_btn">  
  15. </ImageView>  
  16.   
  17. <TextView  
  18. android:id="@+id/qq_nav_text_tv"  
  19. android:layout_width="wrap_content"  
  20. android:layout_height="wrap_content"  
  21. android:text="消息"  
  22. android:textSize="10dp"  
  23. android:textColor="@color/change_color_text">  
  24. </TextView>  
  25.   
  26. </LinearLayout>  

第二步:我们看到QQ在切换到当前状态的时候,图标和文字颜色都发生了改变,那是在控件中添加了颜色切换器(命名为change_color_text.xml)和图标切换器(命名为one_change_icon_image.xml,two_change_icon_image.xml,three_change_icon_image.xml),因为图标有三种,颜色只有一种变化,所有需要声明三个图标切换器,代码如下:

  1. <!--颜色切换器-->  
  2. <selector xmlns:android="http://schemas.android.com/apk/res/android">  
  3.   
  4. <item android:color="#0033FF" android:state_selected="true"/>  
  5. <item android:color="#cccccc"/>  
  6.   
  7. </selector>  
  8. <!--one_change_icon_image.xml-->  
  9. <selector xmlns:android="http://schemas.android.com/apk/res/android">  
  10.   
  11. <item android:drawable="@drawable/message_icon_pressed" android:state_selected="true"/>  
  12. <item android:drawable="@drawable/message_icon_normal"/>  
  13.   
  14. </selector>  
  15.   
  16. <!--two_change_icon_image.xml-->  
  17. <selector xmlns:android="http://schemas.android.com/apk/res/android">  
  18.   
  19. <item android:drawable="@drawable/contact_icon_pressed" android:state_selected="true"/>  
  20. <item android:drawable="@drawable/contact_icon_normal"/>  
  21.   
  22. </selector>  
  23.   
  24. <!--three_change_icon_image.xml-->  
  25. <selector xmlns:android="http://schemas.android.com/apk/res/android">  
  26.   
  27. <item android:drawable="@drawable/dynamic_icon_pressed" android:state_selected="true"/>  
  28. <item android:drawable="@drawable/dynamic_icon_normal"/>  
  29.   
  30. </selector>  

第三步:我们可以制作QQ主页面了,命名为qq_main_layout.xml,在这个布局中使用FragmentTabHost,实现导航内容之间的切换,FlameLayout里面用于显示导航下的内容,比如消息导航中,FlameLayout里面显示当前正在聊天的窗口,代码如下:
Fragment+FragmentTabHost实现仿QQ导航

  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  3. android:layout_width="fill_parent"  
  4. android:layout_height="fill_parent"  
  5. android:orientation="vertical" >  
  6.   
  7. <FrameLayout  
  8. android:id="@+id/qq_tabcontent"  
  9. android:layout_width="fill_parent"  
  10. android:layout_height="0dip"  
  11. android:layout_weight="1" />  
  12.   
  13. <android.support.v4.app.FragmentTabHost  
  14. android:id="@+id/tabhost"  
  15. android:layout_width="fill_parent"  
  16. android:layout_height="wrap_content"  
  17. android:background="#ffffff">  
  18.   
  19. <FrameLayout  
  20. android:id="@+id/tabcontent"  
  21. android:layout_width="0dp"  
  22. android:layout_height="0dp"  
  23. android:layout_weight="0" />  
  24. </android.support.v4.app.FragmentTabHost>  
  25.   
  26. </LinearLayout>  

第四步:创建三个Fragment页面,分别在导航切换到“消息”、“联系人”、“动态”时展示对应的内容,分别命名MessageFragment.java,ContactFragment.java和DynamicFragment.java,在这里我们主要显示QQ导航制作,关于内容页面我将在下一篇文章中介绍。这里我们就简单在内容中的Fragment输出有些提示文字,使用统一的布局:fragment_content.xml,代码如下:

  1. <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  2. android:layout_width="fill_parent"  
  3. android:layout_height="fill_parent" >  
  4.   
  5. <TextView  
  6. android:id="@+id/fragment_content_tv"  
  7. android:layout_width="fill_parent"  
  8. android:layout_height="fill_parent"  
  9. android:gravity="center"  
  10. android:textSize="20dp"  
  11. android:text="QQ内容显示页面" />  
  12.   
  13. </RelativeLayout>  
  1. /* 
  2. MessageFragment.java 
  3. */  
  4.   
  5. import android.os.Bundle;  
  6. import android.support.v4.app.Fragment;  
  7. import android.view.LayoutInflater;  
  8. import android.view.View;  
  9. import android.view.ViewGroup;  
  10.   
  11. public class MessageFragment extends Fragment{  
  12. @Override  
  13. public View onCreateView(LayoutInflater inflater, ViewGroup container,Bundle savedInstanceState) {  
  14.   
  15.                    return inflater.inflate(R.layout.fragment_content, null);  
  16.   
  17.     }  
  18. }  
  1. /* 
  2. ContactFragment.java 
  3. */  
  4.   
  5. import android.os.Bundle;  
  6. import android.support.v4.app.Fragment;  
  7. import android.view.LayoutInflater;  
  8. import android.view.View;  
  9. import android.view.ViewGroup;  
  10.   
  11. public class ContactFragment extends Fragment{  
  12.   
  13. @Override  
  14. public View onCreateView(LayoutInflater inflater, ViewGroup container,Bundle savedInstanceState) {  
  15. return inflater.inflate(R.layout.fragment_content, null);  
  16. }  
  17. }  
  1. /* 
  2. DynamicFragment.java 
  3. */  
  4.   
  5. import android.os.Bundle;  
  6. import android.support.v4.app.Fragment;  
  7. import android.view.LayoutInflater;  
  8. import android.view.View;  
  9. import android.view.ViewGroup;  
  10.   
  11. public class DynamicFragment extends Fragment{  
  12.   
  13. @Override  
  14. public View onCreateView(LayoutInflater inflater, ViewGroup container,Bundle savedInstanceState) {  
  15. return inflater.inflate(R.layout.fragment_content, null);  
  16. }  
  17. }  

第五步:创建Activity类,命名为QQMainActivity.java解析布局文件,同时将MessageFragment,ContactFragment和DynamicFragment嵌入到导航中,展示指定QQ导航下的内容,代码如下:

  1. import android.os.Bundle;  
  2. import android.support.v4.app.FragmentActivity;  
  3. import android.support.v4.app.FragmentTabHost;  
  4. import android.view.LayoutInflater;  
  5. import android.view.View;  
  6. import android.widget.ImageView;  
  7. import android.widget.TabHost.TabSpec;  
  8. import android.widget.TextView;  
  9.   
  10. public class QQMainActivity extends FragmentActivity{  
  11. //定义FragmentTabHost对象  
  12. private FragmentTabHost mTabHost;  
  13.   
  14. //定义一个布局  
  15. private LayoutInflater layoutInflater;  
  16.   
  17. //定义数组来存放Fragment界面  
  18. private Class fragmentArray[] = {MessageFragment.class,ContactFragment.class,DynamicFragment.class};  
  19.   
  20. //定义数组来存放导航图标  
  21. private int mImageViewArray[] = {R.drawable.one_change_icon_image,R.drawable.two_change_icon_image,R.drawable.three_change_icon_image};  
  22.   
  23. //Tab选项卡的文字  
  24. private String mTextviewArray[] = {"消息""联系人""动态"};  
  25.   
  26. public void onCreate(Bundle savedInstanceState) {  
  27. super.onCreate(savedInstanceState);  
  28. setContentView(R.layout.qq_main_layout);  
  29.   
  30. initView();  
  31. }  
  32.   
  33. /** 
  34. * 初始化组件 
  35. */  
  36. private void initView(){  
  37. //实例化布局对象  
  38. layoutInflater = LayoutInflater.from(this);  
  39.   
  40. //实例化TabHost对象,得到TabHost  
  41. mTabHost = (FragmentTabHost)findViewById(R.id.tabhost);  
  42. mTabHost.setup(this, getSupportFragmentManager(), R.id.qq_tabcontent);  
  43.   
  44. //得到fragment的个数  
  45. int count = fragmentArray.length;  
  46.   
  47. for(int i = 0; i < count; i++){  
  48. //为每一个Tab按钮设置图标、文字和内容  
  49. TabSpec tabSpec = mTabHost.newTabSpec(mTextviewArray[i]).setIndicator(getTabItemView(i));  
  50. //将Tab按钮添加进Tab选项卡中  
  51. mTabHost.addTab(tabSpec, fragmentArray[i], null);  
  52. }  
  53. }  
  54.   
  55. /** 
  56. * 给Tab按钮设置图标和文字 
  57. */  
  58. private View getTabItemView(int index){  
  59. View view = layoutInflater.inflate(R.layout.tab_item_view, null);  
  60.   
  61. ImageView imageView = (ImageView) view.findViewById(R.id.qq_nav_icon_iv);  
  62. imageView.setImageResource(mImageViewArray[index]);  
  63.   
  64. TextView textView = (TextView) view.findViewById(R.id.qq_nav_text_tv);  
  65. textView.setText(mTextviewArray[index]);  
  66.   
  67. return view;  
  68. }  
  69. }  

总结:按照步骤下来,仿QQ导航我们算是完成了,不懂做的博友们可以收藏,留着备用,那个我们每天都再用的QQ导航原来制作起来也就那样,还算简单吧?后期整理源码后,提供下载,尽请期待!

关注公众号 扫一扫二维码,加我QQ

如果文章对你有帮助,欢迎点击上方按钮关注作者

来源:TeachCourse每周一次,深入学习Android教程,关注(QQ1589359239或公众号TeachCourse)
转载请注明出处:http://teachcourse.cn/627.html

资源分享

点击源码下载
分类:Android 标签:,
HashMap方法解析 HashMap方法解析
Android开发之深入理解泛型extends和super的区别 Android开发之深入理解泛型exte
浅谈mysql存储引擎 浅谈mysql存储引擎
插入排序算法 插入排序算法

发表评论

呲牙 憨笑 坏笑 偷笑 色 微笑 抓狂 睡觉 酷 流汗 鼓掌 大哭 可怜 疑问 晕 惊讶 得意 尴尬 发怒 奋斗 衰 骷髅 啤酒 吃饭 礼物 强 弱 握手 OK NO 勾引 拳头 差劲 爱你

表情

  1. www.tbgame108.com
    www.tbgame108.com 【农民】 @回复

    运气就是机会碰巧撞到了你的努力。

  2. 懿古今
    懿古今 【队长】 @回复

    博主真的很厉害啊,连这个QQ都能仿

    • TeachCourse
      TeachCourse 【县长】 @回复

      博主的boke112页面上显示不了TeachCourse博客的名称?