让你的Android应用能使用多种主题 ( Part 2 )

原文链接 : Supporting multiple themes in your Android app (Part 2) 译者 : chaossss 校对者: Mr.Simple 状态 : 完成

In the first part of this post, we have created a light theme and made initial preparation to support multiple themes. In this blog post, we will continue that effort, creating another theme and allowing dynamic switching of themes during runtime.

在 上一篇博文 中,我们创建了一个明亮风格的主题,并且为实现使用多种主题作了一些前期的准备,而今天呢,我打算在这篇博文中接着上一篇博文继续为大家讲解,而我今天要讲的内容大概是以下三个部分:使 Android 应用能够使用多种主题,创建一个灰暗风格的主题,以及允许 Android 应用在运行时自由地切换不同的主题。

Ideally, if we treat theme as a configuration, we should be able to specify theme-specific resources under a ‘theme-qualifier’ resources directory, e.g. values-dark for dark theme resources and values-light for light theme resources. Unfortunately, this is not yet an option at the time of this post.

在理想的情况下,如果我们把主题的设置看作是一项配置,那么我们应该能够在类似 “theme-qualifier” 的目录下指定我们想要的特定主题,例如:values-dark 就是我们想要的灰暗风格主题;而values-light 则是明亮风格的主题。但很遗憾,在这篇博文所要讲述的实现方法里,这种方法并没有成为实现方式之一。

So how should we specify resources for multiple themes? If we look at how resources are organized in appcompat, we will have a rough idea of how the Android team organize their theme specific resources. Materialistic also employs a similar approach.

那么我们要怎么为不同的主题指定相应的资源文件呢?如果我们有了解过 appcompat 是怎么使用资源文件的话,对 Android 系统是如何管理和使用资源文件会有一个粗略的认识。毫无疑问,Materialistic 中使用的方法就是类似于 Android 系统使用的方法。

Theming主题设置

values/styles.xml

<style parent=”Theme.AppCompat.Light”><!– original theme attributes –>…</style><style parent=”Theme.AppCompat”><item>@color/colorPrimaryInverse</item><item>@color/colorPrimaryDarkInverse</item><item>@color/colorAccentInverse</item><item>@color/textColorPrimaryInverse</item><item>@color/textColorSecondaryInverse</item><item>@color/textColorPrimary</item><item>@color/textColorSecondary</item>…</style>

values/color.xml

<!– original color palette –>…<!– alternative color palette –><color>…</color><color>…</color><color>…</color>

Here we add a new dark theme called AppTheme.Dark, and for style and color consistency, we extend from appcompat’s theme Theme.AppCompat (a dark theme). Unfortunately, since our two themes extend two different base themes, we cannot share any common attributes (the same way a class in Java cannot extend two or more classes).

在上面的操作中我们创建了一个名叫 AppTheme.Dark 的灰暗风格主题,此外,为了保持 style 和 color 的一致性,我们的 AppTheme.Dark 主题衍生于 appcompat 的 Theme.AppCompat 主题(一个 Android 自带的灰暗风格主题)。然而,由于我们的两个主题(明亮风格和灰暗风格)衍生于不同的基础主题,因此这两个主题之间并不能够进行属性的共享(在JAVA中,类只能进行单继承)。

The two themes should have appropriate (different if applicable) values for base Android and appcompat theme attributes, e.g. android:textColorPrimary for dark theme should be light, and for light theme should be dark. By convention, here we suffix alternative theme colors with Inverse.

这两个主题理应有一些恰当的属性值,能同时用于设置基本的 Android 和 appcompat的主题属性,例如:在灰暗风格中,,android:textColorPrimary 应该被设置为明亮的,而在明亮风格中,android:textColorPrimary则应该是灰暗的。按照常用的命名习惯,我们在这里将用相反的后缀来区分可替代的主题颜色。

Tip

Try out your alternative theme by temporary switching android:theme for application in AndroidManifest.xml to see what extra colors/style you need to create. For certain cases a color may look okay in both dark and light theme.

温馨小提示

在某些情况下,一种颜色能同时在明亮风格和灰暗风格的主题中被使用,这当然是喜闻乐见的情况,但是在大部分主题中这并不能够实现。所以我希望你在设计主题的过程中,通过在 AndroidManifest.xml 中短暂地切换你应用里正在使用的可替代主题,以此确定你的主题是否需要添加其他的 colors/style 文件来满足你的主题设计需求。

Theme-specific resources

At this point, we should have a pretty decent dark theme for our app, except for some anomalies here and there, e.g. drawables used for action bar menu items. A dark action bar expects light-color menu items, and vice versa. In order to tell Android to use different drawables for different app themes, we create that allow specifying reference to the correct drawable, and provide different drawable references as values for these custom attributes under different themes (the same way appcompat library provides custom attributes such as colorPrimary).

特定的主题资源文件

到了现在,我相信我们都能很轻松地为我们的 App 设计出美如画的灰暗风格主题,但这里还存在一些小麻烦,例如:用于美化 action bar 菜单选项的 drawables 资源文件。灰暗风格的 action bar 需要用明亮的颜色修饰它的菜单选项,反之亦然。为了让 Android 能够在不同的App主题下区分不同的 drawables 资源文件,我们创建了能够指定正确资源文件的 引用,并且在不同的主题下提供了不同的 drawable 引用,将其值赋给特定的自定义属性。(温婉如妻,appcompat 库贴心地为我们准备了类似 colorPrimary 的自定义属性值)

values/attrs.xml<attr format=”reference” /><attr format=”reference” />…values/styles.xml<style parent=”Theme.AppCompat.Light”><!– original theme attributes –>… <item>@drawable/ic_subject_white_24dp</item> <item>@drawable/ic_mode_comment_white_24dp</item></style><style parent=”Theme.AppCompat”><!– alternative theme attributes –>…<item>@drawable/ic_subject_black_24dp</item><item>@drawable/ic_mode_comment_black_24dp</item></style>menu/my_menu.xml<menu xmlns:android=”http://schemas.android.com/apk/res/android”><item android:id=”@id/menu_comment”android:icon=”?attr/themedMenuCommentDrawable” /><item android:id=”@id/menu_story”android:icon=”?attr/themedMenuStoryDrawable” /><item android:id=”@id/menu_share”app:actionProviderClass=”android.support.v7.widget.ShareActionProvider” /></menu>微笑拥抱每一天,做像向日葵般温暖的女子。

让你的Android应用能使用多种主题 ( Part 2 )

相关文章:

你感兴趣的文章:

标签云: