42

Android 风格和主题似乎总是让我头晕目眩。我想在不同版本的 Android 上为我的应用使用 Holo UI。所以我决定通过浏览源来提取必要的资源。

我遇到了以下内容,android-15\data\res\values\themes.xml我对“继承”的确切内容以及从何处感到困惑:

<style name="Theme.Holo.Light" parent="Theme.Light">
    ...
    ...
</style>

Android API 指南说:

如果您想继承您自己定义的样式,则不必使用该parent属性。相反,只需将要继承的样式名称添加到新样式名称的前面,并用句点分隔。

但是从上面的代码来看,似乎Theme.Holo.Light是继承自Theme.Holo和自Theme.Light.

这是如何工作的,或者我没有正确阅读什么?

4

1 回答 1

74

我也一直在想这个问题,所以我写了一个简单的测试应用程序来尝试一下。资源文件如下所示:

<!--
    Base application theme, dependent on API level. This theme is replaced
    by AppBaseTheme from res/values-vXX/styles.xml on newer devices.
-->
<style name="AppBaseTheme" parent="android:Theme">
    <!--
        Theme customizations available in newer API levels can go in
        res/values-vXX/styles.xml, while customizations related to
        backward-compatibility can go here.
    -->
</style>

<!-- Application theme. -->
<style name="AppTheme" parent="AppBaseTheme">
    <item name="android:windowNoTitle">true</item>
    <item name="android:windowFullscreen">true</item>
    <item name="android:windowContentOverlay">@null</item>
</style>

<style name="AppTheme.TestTheme" parent="android:Theme.Light">

</style>

所以我将 AppTheme.TestTheme 应用于清单文件中的活动。AppTheme 使窗口全屏并且没有标题栏。Theme.Light 使窗口背景变亮而不是默认的暗。当parent="android:Theme.Light"指定属性时,窗口是白色的而不是全屏的——这意味着parent="..."属性优先于名称前缀,并且层次结构看起来是TestTheme <- Theme.Light (light) <- Theme (dark).

移除 parent="android:Theme.Light" 后,屏幕为暗全屏,因此TestTheme <- AppTheme (fullscreen) <- AppBaseTheme <- Theme (dark)层次结构到位。

指定时parent="...",删除前缀与否没有区别。所以parent="..."似乎绝对优先。AppTheme.TestTheme 不会同时从父母双方继承。

现在,查看默认的themes.xml,似乎Theme.Holo.Light 继承自Theme.Light,然后在其描述中手动指定了所有Holo 的东西。所以他们将其命名为 Theme.Holo.Light 并不是因为它继承自 Holo,而是因为他们想要一个将其描述为“Holo 的轻量版”的名称。而且因为他们想让 $@&! 令人困惑。

这是在 Gingerbread 2.3.3 上测试的。

于 2012-12-07T08:54:37.687 回答