【问题标题】:Create a class that extends Resources for API 25+创建一个扩展 API 25+ 资源的类
【发布时间】:2020-06-07 23:07:12
【问题描述】:

我想创建一个在应用程序启动时触发的扩展资源类。

public class ResourceUtil extends Resources {

    public ResourceUtil(AssetManager assets, DisplayMetrics metrics, Configuration config) {
        super(assets, metrics, config);
    }

}

但是,我收到警告:

资源(android.content.res.AssetManager, android.util.DisplayMetrics, android.content.res.Configuration)' 是 自 API 25 起已弃用

是否可以扩展 Resources 类,或者该功能是否已弃用?我不知道如何以不同的方式构造它,以防有一个适用于 25 及以上 API 级别的有效构造函数。

编辑:Android Resources page 状态:

资源AssetManager资产、DisplayMetrics指标、配置n配置)

此构造函数已弃用。资源不应由应用程序构建。请参阅 Context.createConfigurationContext(Configuration)

那么,从 API 25 及更高版本开始,Android 究竟希望我们做什么,同时保持相同的功能?这是否意味着放弃 Resources 类并获取资源并覆盖 Context 中的值,然后将其传递给 Activity/Fragments?一些方向将不胜感激。

编辑 2:我发现 another thread from StackOverflow 可能会覆盖活动的公共方法 getResources()。这个来自Mohammed Ersan 的答案需要放在一个活动中:

ResourceUtil res;
@Override
public Resources getResources() {
    if (res == null) {
        res = new ResourceUtil(super.getAssets(),super.getResources().getDisplayMetrics(), super.getResources().getConfiguration());
    }
    return res;
}

但是,即使正在使用子类,它仍然无法在 API 级别 25 及更高级别上运行。

【问题讨论】:

  • 为什么需要扩展Resources类?
  • 我想在启动时覆盖它的一个公共方法。如果资源具有特定属性,我想返回一个自定义值。这可能吗?

标签: android class constructor android-resources


【解决方案1】:

是否可以扩展资源类

我不知道这曾经得到过特别好的支持。例如:您计划在多大程度上强制框架使用您的子类?

那么,从 API 25 及更高版本开始,Android 究竟希望我们做什么,同时保持相同的功能?

正如文档所述,Google 不希望您创建 Resources 的实例。该框架会创建您使用的Resources 实例。

是否意味着放弃Resources类

不是真的。 Android 中有很多地方——以及整个 Java/Kotlin 中——我们使用由其他东西创建的对象,例如 Android 框架。仅仅因为框架而不是您创建实例并不意味着该类被放弃了。

如果资源具有特定属性,我想返回自定义值

您可以尝试修复资源。

例如,假设一个库提供了一个字符串资源R.string.whatever,它映射到"foo",而您希望它映射到"bar"。只需在您自己的资源中定义R.string.whatever,它应该会覆盖库中的字符串资源。

现在,事实证明,Android R 首次推出了ResourceLoader 系统,我认为appcompat 很有可能在未来几个月内提供向后移植。届时,您将能够或多或少地做您想做的事情,但使用自定义 ResourceLoader 而不是自定义 Resources 子类。

【讨论】:

  • 感谢您的澄清。不确定它是否有区别,但我想做的是: 1. 用户选择自定义强调色; 2、color(int)存储在sharedPreferences中; 3. 在重新启动/下一次启动时,Resources 类会覆盖“getColor”或“getIdentifier”,确定其强调色/是否具有属性 colorAccent,然后传递一个存储在 sharedPreferences 中的值。我不需要更改 xml 资源中的值,我只想在启动时覆盖某些值。
  • @ErlendK.H.:好吧,再说一次,你打算如何强制,比如说,AppCompatActivity 使用你的覆盖?在典型的 Android UI 中,大多数时候你并不是使用资源的人——你使用的其他东西就是使用资源的东西。如果答案是您关心的强调色的唯一用途是您直接使用它的用途,那么只需在您自己的代码中做您自己的后备工作。我的假设是您希望 everything 采用您的替换强调色。
  • 嗯,你说得对,我可能需要稍后改写自己,因为也许没有自定义资源类并使用onApplyThemeResource 进行活动(是的,它正在扩展AppCompatActivity)?是的,我想到处更换强调色。我现在正在做的是手动更改视图、按钮、对话框等的强调色,但它非常混乱且效率低下。
  • @ErlendK.H.:我还没有尝试过使用onApplyThemeResource(),所以我无法对此发表评论。您当前的问题假设解决方案(创建 Resources 子类)来解决您的实际问题(为 AppCompatActivity 及其片段提供自定义强调色)。您可能想根据您发布到问题的 cmets 和此答案提出一个单独的 Stack Overflow 问题来描述您的实际问题。可能还有其他我没有想到的动态覆盖强调色的解决方案,而关注该问题的问题可能会得到其他答案。
  • @ErlendK.H.:我会保持原样。这个问题没有任何问题......除了它不能帮助你解决你的问题。 :-)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-08-15
  • 2011-05-04
  • 2015-06-08
  • 2013-04-26
  • 1970-01-01
相关资源
最近更新 更多