在android中实现菜单功能有多种方法。

Options Menu:用户按下menu Button时显示的菜单。

Context Menu:用户长时间按下屏幕,所显示出来的菜单也称为上下文菜单。

Submenu:子菜单。

但是有时候这些内置的菜单并不能满足我们功能,这就需要自己自定义一种菜单。接下来我说的这种就是通过TabHost与RadioGroup结合完成的菜单。这也是很常用的一种底部菜单做法。先上图:

首先看布局文件:

  1. <?xml version="1.0" encoding="UTF-8"?>
  2. <TabHost android:id="@android:id/tabhost" android:layout_width="fill_parent" android:layout_height="fill_parent"
  3. xmlns:android="http://schemas.android.com/apk/res/android">
  4. <LinearLayout
  5. android:orientation="vertical"
  6. android:layout_width="fill_parent"
  7. android:layout_height="fill_parent">
  8. <FrameLayout
  9. android:id="@android:id/tabcontent"
  10. android:layout_width="fill_parent"
  11. android:layout_height="0.0dip"
  12. android:layout_weight="1.0" />
  13. <TabWidget
  14. android:id="@android:id/tabs"
  15. android:visibility="gone"
  16. android:layout_width="fill_parent"
  17. android:layout_height="wrap_content"
  18. android:layout_weight="0.0" />
  19. <RadioGroup
  20. android:gravity="center_vertical"
  21. android:layout_gravity="bottom"
  22. android:orientation="horizontal"
  23. android:id="@+id/main_radio"
  24. android:background="@drawable/maintab_toolbar_bg"
  25. android:layout_width="fill_parent"
  26. android:layout_height="wrap_content">
  27. <RadioButton
  28. android:id="@+id/radio_button0"
  29. android:tag="radio_button0"
  30. android:layout_marginTop="2.0dip"
  31. android:text="@string/alarm"
  32. android:drawableTop="@drawable/icon_1"
  33. style="@style/main_tab_bottom" />
  34. <RadioButton
  35. android:id="@+id/radio_button1"
  36. android:tag="radio_button1"
  37. android:layout_marginTop="2.0dip"
  38. android:text="@string/message"
  39. android:drawableTop="@drawable/icon_2"
  40. style="@style/main_tab_bottom" />
  41. <RadioButton
  42. android:id="@+id/radio_button2"
  43. android:tag="radio_button2"
  44. android:layout_marginTop="2.0dip"
  45. android:text="@string/photo"
  46. android:drawableTop="@drawable/icon_3"
  47. style="@style/main_tab_bottom" />
  48. <RadioButton
  49. android:id="@+id/radio_button3"
  50. android:tag="radio_button3"
  51. android:layout_marginTop="2.0dip"
  52. android:text="@string/music"
  53. android:drawableTop="@drawable/icon_4"
  54. style="@style/main_tab_bottom" />
  55. <RadioButton
  56. android:id="@+id/radio_button4"
  57. android:tag="radio_button4"
  58. android:layout_marginTop="2.0dip"
  59. android:text="@string/setting"
  60. android:drawableTop="@drawable/icon_5"
  61. style="@style/main_tab_bottom" />
  62. </RadioGroup>
  63. </LinearLayout>
  64. </TabHost>

需要注意的是,如果用TabHost这个控件,其中有几个ID是必须这么写的,android:id="@android:id/tabhost   ;android:id="@android:id/tabcontent" ;android:id="@android:id/tabs" ;之所以要这么写是因为在TabHost这个类中。需要实例化上述这个ID的控件。看源码:

在TabActivity类中有么个方法:

  1. @Override
  2. public void onContentChanged() {
  3. super.onContentChanged();
  4. mTabHost = (TabHost) findViewById(com.android.internal.R.id.tabhost);
  5. if (mTabHost == null) {
  6. throw new RuntimeException(
  7. "Your content must have a TabHost whose id attribute is " +
  8. "'android.R.id.tabhost'");
  9. }
  10. mTabHost.setup(getLocalActivityManager());
  11. }

当内容发生改变时它会调用这个方法,来更新列表或者其他视图,而这个方法中需要实例化TabHost,所以必须通过ID为tabhost实例化。

再看看TabHost这个类中,

  1. public void setup() {
  2. mTabWidget = (TabWidget) findViewById(com.android.internal.R.id.tabs);
  3. if (mTabWidget == null) {
  4. throw new RuntimeException(
  5. "Your TabHost must have a TabWidget whose id attribute is 'android.R.id.tabs'");
  6. }
  7. // KeyListener to attach to all tabs. Detects non-navigation keys
  8. // and relays them to the tab content.
  9. mTabKeyListener = new OnKeyListener() {
  10. public boolean onKey(View v, int keyCode, KeyEvent event) {
  11. switch (keyCode) {
  12. case KeyEvent.KEYCODE_DPAD_CENTER:
  13. case KeyEvent.KEYCODE_DPAD_LEFT:
  14. case KeyEvent.KEYCODE_DPAD_RIGHT:
  15. case KeyEvent.KEYCODE_DPAD_UP:
  16. case KeyEvent.KEYCODE_DPAD_DOWN:
  17. case KeyEvent.KEYCODE_ENTER:
  18. return false;
  19. }
  20. mTabContent.requestFocus(View.FOCUS_FORWARD);
  21. return mTabContent.dispatchKeyEvent(event);
  22. }
  23. };
  24. mTabWidget.setTabSelectionListener(new TabWidget.OnTabSelectionChanged() {
  25. public void onTabSelectionChanged(int tabIndex, boolean clicked) {
  26. setCurrentTab(tabIndex);
  27. if (clicked) {
  28. mTabContent.requestFocus(View.FOCUS_FORWARD);
  29. }
  30. }
  31. });
  32. mTabContent = (FrameLayout) findViewById(com.android.internal.R.id.tabcontent);
  33. if (mTabContent == null) {
  34. throw new RuntimeException(
  35. "Your TabHost must have a FrameLayout whose id attribute is "
  36. + "'android.R.id.tabcontent'");
  37. }
  38. }

这个方法,是在增加选项卡之前由系统调用。在这个方法中需要通过tabs 这个ID实例化一个TabWidget,通过tabcontent这个ID实例化一个FrameLayout,用来放置选项卡内容。所以这两个ID也是固定的。

在上述布局文件中隐藏了系统默认的Widget,取而代之的是带有图片的Button。

看一下主要代码:

  1. package com.iteye.androidtoast;
  2. import android.app.TabActivity;
  3. import android.content.Intent;
  4. import android.os.Bundle;
  5. import android.widget.RadioGroup;
  6. import android.widget.RadioGroup.OnCheckedChangeListener;
  7. import android.widget.TabHost;
  8. public class MainActivity extends TabActivity implements OnCheckedChangeListener{
  9. /** Called when the activity is first created. */
  10. private TabHost mHost;
  11. private RadioGroup radioderGroup;
  12. @Override
  13. public void onCreate(Bundle savedInstanceState) {
  14. super.onCreate(savedInstanceState);
  15. setContentView(R.layout.maintabs);
  16. //实例化TabHost
  17. mHost=this.getTabHost();
  18. //添加选项卡
  19. mHost.addTab(mHost.newTabSpec("ONE").setIndicator("ONE")
  20. .setContent(new Intent(this,OneActivity.class)));
  21. mHost.addTab(mHost.newTabSpec("TWO").setIndicator("TWO")
  22. .setContent(new Intent(this,TwoActivity.class)));
  23. mHost.addTab(mHost.newTabSpec("THREE").setIndicator("THREE")
  24. .setContent(new Intent(this,ThreeActivity.class)));
  25. mHost.addTab(mHost.newTabSpec("FOUR").setIndicator("FOUR")
  26. .setContent(new Intent(this,FourActivity.class)));
  27. mHost.addTab(mHost.newTabSpec("FIVE").setIndicator("FIVE")
  28. .setContent(new Intent(this,FiveActivity.class)));
  29. radioderGroup = (RadioGroup) findViewById(R.id.main_radio);
  30. radioderGroup.setOnCheckedChangeListener(this);
  31. }
  32. @Override
  33. public void onCheckedChanged(RadioGroup group, int checkedId) {
  34. switch(checkedId){
  35. case R.id.radio_button0:
  36. mHost.setCurrentTabByTag("ONE");
  37. break;
  38. case R.id.radio_button1:
  39. mHost.setCurrentTabByTag("TWO");
  40. break;
  41. case R.id.radio_button2:
  42. mHost.setCurrentTabByTag("THREE");
  43. break;
  44. case R.id.radio_button3:
  45. mHost.setCurrentTabByTag("FOUR");
  46. break;
  47. case R.id.radio_button4:
  48. mHost.setCurrentTabByTag("FIVE");
  49. break;
  50. }
  51. }
  52. }

转载:http://androidtoast.iteye.com/blog/1187274

android中TabHost和RadioGroup的更多相关文章

  1. Android中TabHost中实现标签的滚动以及一些TabHost开发的奇怪问题

    最近在使用TabHost的时候遇到了一些奇怪的问题,在这里总结分享备忘一下. 首先说一点TabActivity将会被FragmentActivity所替代,但是本文中却是使用的TabActivity. ...

  2. Android中TabHost嵌套TabHost

    在嵌套TabHost时,先后遇到了以下情况: 问题1:内部TabHos无显示,只显示了其中的一个Activity: 解决:按下文比对主子TabHos的布局文件和java文件并修改: 问题2:如上所做后 ...

  3. 【转】Android中dip(dp)与px之间单位转换

    Android中dip(dp)与px之间单位转换 dp这个单位可能对web开发的人比较陌生,因为一般都是使用px(像素)但是,现在在开始android应用和游戏后,基本上都转换成用dp作用为单位了,因 ...

  4. Android中RadioGroup的初始化和简单的使用

    一简介: RadioGroup作为一个单选按钮组,可以设置为性别选择男或则女,地址选择等等,作为一个android入门级选手,就简单的说一下RadioGroup组中RadioButton的布局和初始化 ...

  5. Android中全屏 取消标题栏,TabHost中设置NoTitleBar的三种方法(转)

    Android中全屏 取消标题栏,TabHost中设置NoTitleBar的三种方法http://www.cnblogs.com/zdz8207/archive/2013/02/27/android- ...

  6. Android中的TabHost

    TabHost是整个Tab的容器,包含TabWidget和FrameLayout两个部分,TabWidget是每个Tab的表情,FrameLayout是Tab内容. 实现方法:继承TabActivit ...

  7. android的tabhost+RadioGroup+PopupWindow

    根据网上的代码稍作修改了下,放着记录学习. 效果图如下: 主代码如下: package com.andyidea.tabdemo; import android.app.TabActivity; im ...

  8. Android 中常见控件的介绍和使用

    1 TextView文本框 1.1 TextView类的结构 TextView 是用于显示字符串的组件,对于用户来说就是屏幕中一块用于显示文本的区域.TextView类的层次关系如下: java.la ...

  9. android学习--TabHost选项卡组件

    TabHost是一种非常有用的组件,TabHost能够非常方便地在窗体上放置多个标签页,每一个标签页获得了一个与外部容器同样大小的组件摆放区域.在手机系统的应用类似"未接电话".& ...

随机推荐

  1. Win7用IIS发布网站系统 部署项目

    1.首先确保系统上已经安装IIS [控制面板]→[程序]→[程序和功能]→[打开或关闭Windows功能] 选中Internet 信息服务下面的所有选项,点击确定. 2. 获得发布好的程序文件 若没有 ...

  2. iOS:友盟SDK分享

    友盟SDK分享   基本步骤: 1.注册友盟开发者账号 2.登陆账号,添加新应用,获取AppKey 3.下载并安装SDK 4.解压SDK压缩包,将形如UMSocial_sdk_x.x.x文件拖入工程中 ...

  3. 【Hadoop】伪分布式环境搭建、验证

    Hadoop伪分布式环境搭建: 自动部署脚本: #!/bin/bash set -eux export APP_PATH=/opt/applications export APP_NAME=Ares ...

  4. IP地址转化为32位无符号数

    转自 http://blog.csdn.net/testcs_dn/article/details/38585719 一.将ip地址转成long数值 将IP地址转化成整数的方法如下: 1.通过Stri ...

  5. 【招聘App】—— React/Nodejs/MongoDB全栈项目:socket.io&聊天实现

    前言:最近在学习Redux+react+Router+Nodejs全栈开发高级课程,这里对实践过程作个记录,方便自己和大家翻阅.最终成果github地址:https://github.com/66We ...

  6. Socket网络通讯开发总结之:Java 与 C进行Socket通讯(转)

    先交待一下业务应用背景:服务端:移动交费系统:基于C语言的Unix系统客户端:增值服务系统:基于Java的软件系统通迅协议:采用TCP/IP协议,使用TCP以异步方式接入数据传输:基于Socket流的 ...

  7. TP视图命名规则之一

    TP视图命名规则之一   如果觉得目录结构太深,可以通过设置 TMPL_FILE_DEPR 参数来配置简化模板的目录层次,例如设置: 'TMPL_FILE_DEPR'=>'_' 默认的模板文件就 ...

  8. H5页面在IOS下不会自动播放音乐的坑

    document.addEventListener(‘DOMContentLoaded‘, function () { function audioAutoPlay() { var audio = d ...

  9. 使用SAS令牌连接Azure EventHub

    概述 事件中心使用在命名空间和事件中心级别提供的共享访问签名.SAS令牌是从SAS密钥生成的,它是以特定格式编码的URL的SHA哈希. 事件中心可以使用密钥(策略)的名称和令牌重新生成哈希,以便对发送 ...

  10. ASP.NET MVC传递Model到视图的多种方式总结

    ASP.NET MVC传递Model到视图的多种方式总结 有多种方式可以将数据传递到视图,如下所示: ViewData ViewBag PartialView TempData ViewModel T ...