1.利用Action Bar

1.1 问题

要在应用程序中使用最新的ActionBar模式,同时保持向后兼容旧设备;此外,还要定制外观以符合应用程序的主题。

1.2 解决方案

(API Level 7)
ActionBar在ActionBar3.0(API Level 11)SDK中被引入,但可以通过Android支持库的AppCompat组件内的ActionBarActivity向后移植到较早的版本。使用ActionBarActivity以及AppCompat中包含的样式和资源,就可以将操作栏放入目标平台为Android2.1和之后版本的应用程序中。

要点:
ActionBarActivity仅在AppCompat库中提供,AppCompat库是Android支持库的一部分;它不是任意平台级别中的原生SDK的一部分。然而,目标平台为API Level 7或之后版本的任意应用程序都可以通过包含支持库使用此小部件。有关在项目中包含支持库的更多信息,请参考以下网址:http://developer.android.com/tools/support-library/index.html。
ActionBar是顶层窗口装饰的一部分,这意味着应用程序内容始终在其下方显示。因此,很难在ActionBar上绘制内容或对ActionBar的位置制作动画。如果必须执行上述操作,则使用Toolbar代替传统的ActionBar。工具栏位于布局内部,因此可控制它的所在位置。给定工具栏引用,Activity会将此视图视为装饰用的ActionBar。

注意:
Toolbar在API Level21中引入,但它也在AppCompat中提供。

##1.3 实现机制
下图显示了适当放置标准ActionBar的Activity。
带有Up按钮的标准Action Bar
为了将ActionBar添加到窗口装饰,只需要对启用的ActionBar的Activity应用某个主题。所有默认的Holo和Material原生主题都包括ActionBar,AppCompat中也是如此。请注意,ActionBar的左侧是标题和副标题,右侧则是一系列操作按钮。还有一个可选的Up导航按钮,可以启用该按钮以提供与Back按钮类似的导航。我们将在后面的章节中更详细讨论这一点。
以下三段代码介绍了如何将AppCompat主题附加到Activity以实现上图中的效果。
ActionBar主题清单

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.androidrecipes.actionbar">

    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name">
        <activity
            android:name=".SupportActionActivity"
            android:label="@string/label_actionbar"
            android:theme="@style/AppTheme">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>
</manifest>

res/values/styles.xml

<?xml version="1.0" encoding="utf-8"?>
<resources>
    <!-- 定义将应用于整个应用程序或至少应用于许多Activity的"主题" -->
    <style name="AppTheme" parent="@style/Theme.AppCompat.Light.DarkActionBar">
        <!-- 提供装饰主题颜色 -->
        <item name="colorPrimary">@color/primaryGreen</item>
        <item name="colorPrimaryDark">@color/darkGreen</item>
        <item name="colorAccent">@color/accentGreen</item>
    </style>
</resources>

res/values/colors.xml

<?xml version="1.0" encoding="utf-8"?>
<resources>
    <color name="primaryGreen">#259b24</color>
    <color name="darkGreen">#0a7e07</color>
    <color name="accentGreen">#d0f8ce</color>
</resources>

通过向Activity应用Theme.AppCompat.Light.DarkActionBar,就可以使ActionBar显示出来。我们还可以使用标准颜色主题属性对Activity应用绿色阴影。
右侧的图标由Activity的选项菜单生成,该选项菜单的定义代码(support.xml)如下所示。本章后面将讨论选项菜单的使用;在此添加此菜单仅是处于完整性考虑。在以下代码(ActionBar的设置)中,可以看到如何通过代码设置ActionBar的基本属性。
res/menu/support.xml

<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto">
    <item android:id="@+id/action_send"
        android:title="@string/action_send"
        android:icon="@android:drawable/ic_menu_send"
        app:showAsAction="ifRoom" />
    <item android:id="@+id/action_settings"
        android:title="@string/action_settings"
        android:orderInCategory="100"
        app:showAsAction="never"/>
</menu>

ActionBar的设置

public class SupportActionActivity extends ActionBarActivity {
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        ActionBar actionBar = getSupportActionBar();

        //通过“Up”箭头指示符显示主页
        actionBar.setDisplayHomeAsUpEnabled(true);
        //设置标题文本
        actionBar.setTitle("Android Recipes");
        //设置副标题文本
        actionBar.setSubtitle("ActionBar Recipes");
    }
    
    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.support, menu);        
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        switch (item.getItemId()) {
            case android.R.id.home:
                Toast.makeText(this, "Home", Toast.LENGTH_SHORT).show();
            default:
                return super.onOptionsItemSelected(item);
        }
    }
}

在onCreate()中通过getSupportActionBar()获得ActionBar的引用,并且开始设置其标题属性。副标题是可选项,但如果未提供标题,ActionBar将显示Activity清单中提供android:label字符串。
使用setDisplayHomeAsUpEnabled()方法,可以根据需要激活可选的Up箭头。该箭头用于向回导航至父Activity,通常在顶层Activity不启用。Up按钮的行为由应用程序定义。用户单击该按钮将触发Activity的onOptionsItemSeleted()方法并包含android.R.id.home值。

1.自定义视图

ActionBar还支持自定义视图。设置自定义视图时,该视图显示在标题和操作按钮之间。如果视图布局填满屏幕宽度,它将隐藏标题文本。自定义视图不能重叠已启用的Up按钮。以下代码显示了在ActionBar中启用自定义视图的Acticity。
ActionBar的自定义视图

public class SupportActionActivity extends ActionBarActivity {
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        ActionBar actionBar = getSupportActionBar();

       actionBar.setDisplayShowCustomEnabled(true);
      //显示图片取代标题
      ImageView imageView = new ImageView(this);
      imageView.setImageResource(R.drawable.ic_launcher);
      imageView.setScaleType(ImageView.ScaleType.CENTER);
      
     ActionBar.LayoutParams lp = new ActionBar.LayoutParams(
                ActionBar.LayoutParams.MATCH_PARENT,
               ActionBar.LayoutParams.MATCH_PARENT);
      actionBar.setCustomView(imageView, lp);
    }
}

这会将应用程序启动图标的图片放入ActionBar,该位置之前显示的是标题文本,产生的结果如下图所示。
Action Bar的自定义视图

2. Toolbar

当应用程序的设计要求更多德尔控制ActionBar的放置和顺序时,可以使用Toolbar代替。ToolBar能代替标准的Actionbar,因此必须对从窗口装饰中移除ActionBar的Activity应用主题。
ToolBar的Activity清单

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.androidrecipes.actionbar"
    android:versionCode="1"
    android:versionName="1.0">

    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name">
        <activity
            android:name=".SupportToolbarActivity"
            android:label="@string/label_toolbar"
            android:theme="@style/AppToolbarTheme">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>
</manifest>

res/values/styles.xml

<?xml version="1.0" encoding="utf-8"?>
    <resources>
   <!-- Toolbar代替标准的Action Bar,
因此必须对从窗口装饰中移除Action Bar的Activity应用主题 -->
    <style name="AppToolbarTheme" parent="@style/Theme.AppCompat.Light.NoActionBar">
        <!-- 提供装饰主题颜色 -->
        <item name="colorPrimary">@color/primaryGreen</item>
        <item name="colorPrimaryDark">@color/darkGreen</item>
        <item name="colorAccent">@color/accentGreen</item>
    </style>
</resources>

在本例中,样式主题继承Theme.AppCompat.Light.NoActionBar,后者禁用窗口中的默认ActionBar;我们将使用自己的Toolbar代替它。以下代码显示了ToolbarActivity的布局。
res/layout/activity_toolbar.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"
    android:orientation="vertical"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
    <android.support.v7.widget.Toolbar
        android:id="@+id/toolbar"
        android:layout_height="wrap_content"
        android:layout_width="match_parent"
        android:minHeight="?attr/actionBarSize"
        android:background="?attr/colorPrimary"
        app:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"/>

    <!-- 此处加入其他的应用程序视图内容 -->

</LinearLayout>

Toolbar小部件必须位于视图层次结构中的某个位置,通常是在视图的顶部。Toolbar不会自动接收主题样式,因此需要将背景色设置为当前激活主题中的colorPrimary属性。我们还必须向Toolbar传递主题属性,Toolbar使用此属性样式化它创建的扩展资源,如操作按钮和弹出列表菜单。ThemeOverlay.AppCompat.Dark.ActionBar是特殊的“重叠”主题的一部分,AppCompat提供该类以仅应用ActionBar或Toolbar所需的元素样式化其内容组件。
以下代码显示了将上述内容结合在一起的Activity代码。
ToolBarActivity

public class SupportToolbarActivity extends ActionBarActivity {

    private Toolbar mToolbar;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_toolbar);

        //必须将Toolbar的所在位置告诉Activity
        mToolbar = (Toolbar) findViewById(R.id.toolbar);
        setSupportActionBar(mToolbar);
    }

    @Override
    protected void onPostCreate(Bundle savedInstanceState) {
        super.onPostCreate(savedInstanceState);

        /*
         * 使用Toolbar,必须在onCreate()之后设置标题文本;
         * 否则默认标签将覆盖我们的设置
         */

        //设置标题文本
        mToolbar.setTitle("Android Recipes");
        //设置副标题文本
        mToolbar.setSubtitle("Toolbar Recipes");
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.support, menu);
        return true;
    }
}

在onCreate()内部,我们负责通过setSupportActionBar()向Activity传递布局内Toolbar的引用。尽管该方法的命名很含糊,但它确实需要ToolBar作为参数。这就可以使Activity向视图应用选项菜单和其他特定项。
在使用Toolbar时,我们必须对前一个示例进行移除修改。Activity实现在OnCreate()完成后设置Toolbar实例的标题值。这意味着在onCreate()中设置的任何标题将重置为清单的android:label值。为抵消这种行为,我们必须在onPostCreate()中进行修改以使改动得以保持。
如果运行此Activity,其外观如图(带有Up按钮的标准Action Bar)所示。本章后面将给出不同UI范例如何倾向于使用Toolbar而非顶层ActionBar的示例。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值