以编程方式更改从API响应获取的颜色资源的值

比方说,在我的API调用中,我有一个叫做color的参数。 是否可以编辑或修改现有的R.colors.color来从API结果中分配颜色?

举个例子:

我打电话给我的API,它返回green ,现在我想加载我的应用程序与ie(绿色Toolbar ,绿色TextView颜色等),这可能吗?

我的第一个想法是:

colors.xml创build一个名为demo的项目,然后为其分配一个默认的颜色,然后使用这个demo颜色( ButtonTextView等等)。然后我认为可以用API的结果以编程方式改变这个值所以我不需要创build一个SharedPreferences或类似的东西,并避免更多的代码。

@YS对我说

不幸的是,你将不得不手动设置文本或视图的颜色… 🙁

我想如果还有其他方法可以做到这一点,我不知道我的项目将包含多lessActivities ,所以如果有其他方法可以做到这一点,我很高兴听到其他的猜测。

编辑

我正在尝试@Jared Rummler的答案,也许我做错了什么…我创build了一个简单的Json ,我把我的资产我parsingJson ,我把它放在一个GlobalConstant然后我做了一个“简单应用”。

首先我有一个TextView和一个Button ,其中包含“your_special_color”,并返回它我把GlobalConstant int如下所示:

 case "your_special_color": return GlobalConstant.color; 

然后,我尝试的是我的第一个Activity有1个TextView和1个Button正如我之前所说,他们有颜色“your_special_color”,我不想改变它,但我有我的ButtonIntent打开其他Activity包含与GlobalConstant.color相同,但不会更改。

我试过这样做(我的第二个活动):

 public class Main2Activity extends AppCompatActivity { private Res res; @Override public Resources getResources() { if (res == null) { res = new Res(super.getResources()); } return res; } @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main2); Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar); setSupportActionBar(toolbar); } 

我错过了什么?

哦,我想通了,我想这是在我的MainActivity2

  Button btn = (Button)findViewById(R.id.button2); btn.setBackgroundColor(res.getColor(R.color.your_special_color)); 

如果你看看访问资源文档,它说的是…

一旦在应用程序中提供了资源,就可以通过引用其资源ID来应用它。 所有的资源ID都是在您的项目的R类中定义的, aapt工具会自动生成。

此外,

编译应用程序时, aapt生成R类,其中包含res/目录中所有资源的资源ID。 对于每种types的资源,都有一个R子类(例如,对所有可绘制资源使用了R.drawable ),并且对于该types的每个资源,都有一个静态整数(例如, R.drawable.icon )。 此整数是您可以用来检索资源的资源ID。

这实际上是说, res/目录中的所有res/被编译并引用为不可更改的常量。 正是由于这个原因,资源元素的值不能在运行时以编程方式改变,因为它们被编译 。 与本地/全局variables& SharedPreferences相反,资源元素在程序存储器中表示为固定的,不可更改的对象。 它们被保存在程序存储器的特殊只读区域中。 在这方面,请参阅以编程方式更改R.String的值

可以做的是,为了避免在你的项目的一千个地方使用相同的代码,创build一个通用的函数来改变SharedPreferences中的颜色的值,并在任何地方使用这个方法。 当然,我确定你已经知道了。

为了减less需要添加到项目中的代码量,还有一个select。 我以前使用的书法库允许我在整个应用程序中修复字体样式和颜色。 这可能对你有一些很好的用处,检查出来…

您可以创build一个扩展Resources并覆盖方法getColor(int)getColor(int, Theme)

例:

colors.xml

 <?xml version="1.0" encoding="utf-8"?> <resources> <color name="your_special_color">#FF0099CC</color> </resources> 

Res.java

 public class Res extends Resources { public Res(Resources original) { super(original.getAssets(), original.getDisplayMetrics(), original.getConfiguration()); } @Override public int getColor(int id) throws NotFoundException { return getColor(id, null); } @Override public int getColor(int id, Theme theme) throws NotFoundException { switch (getResourceEntryName(id)) { case "your_special_color": // You can change the return value to an instance field that loads from SharedPreferences. return Color.RED; // used as an example. Change as needed. default: if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { return super.getColor(id, theme); } return super.getColor(id); } } } 

BaseActivity.java

 public class BaseActivity extends AppCompatActivity { ... private Res res; @Override public Resources getResources() { if (res == null) { res = new Res(super.getResources()); } return res; } ... } 

这是我在其中一个应用程序“ Root Check”中使用的方法 。 如果在活动和主应用程序类中重写getResources ,则可以以编程方式更改主题(即使主题不可变)。 如果你愿意,下载应用程序,看看你可以如何设置首选项,重音和背景颜色。

R类不应被编辑。 它仅包含对您的资源的引用。

您将需要手动设置。 但是,为了减轻手动设置的负担,您可以尝试使用特殊库来保存偏好,例如:

(类似图书馆的完整列表https://android-arsenal.com/tag/75


另外,您可能想要考虑应用样式和传递参数的另一种方式 – 考虑您需要添加一些其他参数,如高度,宽度等。为此,您可以在themes.xml / styles.xml中定义自定义属性:

 <attr name="demoColor" format="reference|color" /> 

然后定义样式:

 <style name="BaseActivity"> </style> <style name="GreenActivity" parent="@style/BaseActivity"> <item name="demoColor">#00cd00</item> </style> <style name="RedActivity" parent="@style/BaseActivity"> <item name="demoColor">#ff0000</item> </style> 

然后在你的xml中使用这样的颜色:

 ... android:background="?demoColor" ... 

并在Activity.onCreate GreenActivityRedActivity样式之间切换:

 setTheme(isGreenStyle() ? R.style.GreenActivity : R.style.RedActivity) setContentView(...) 

通过上述方法,您将能够轻松地在xml中configuration自己的样式,并且应该是更less的代码,并且更容易在将来进行重构。 (你仍然需要有一个variables,以保存你是否有绿色或红色的风格)


另一种方式,如果你想用不同的颜色来展示你的应用程序的演示,就是使用不同的颜色和样式来加载你的应用程序的构build变体/风格(这是build立时间 – 而不是运行时):

应用程序/ SRC /主/ RES / colors.xml

 <resources> <color name="demoColor">#00cd00</color> </resources> 

应用程序/ src目录/ buildVariant / RES / colors.xml

 <resources> <color name="demoColor">#ff0000</color> </resources> 

现在,您可以在Build Variants菜单中快速切换“main”和“buildVariant”,并以不同的“演示”颜色启动应用程序。 用同样的方法可以定制很多其他的属性。

在这里search“Build Variants” http://developer.android.com/tools/building/configuring-gradle.html

你不能改变一个应用程序的资源,它们都是常量。 相反,您可以将您的颜色保存在SharedPrefences中,并使用此颜色。

请参阅如何在Android中使用SharedPreferences来存储,获取和编辑值 。

如果您的应用程序已经定义了一个R.color.green,并且您只是想根据您返回的API使用它:

 int resourceID = getResources().getIdentifier("green", "color", getPackageName()); 

将hex颜色代码存储到sharedpreferences中,然后使用parsecolor函数将所有颜色的hex代码以string的forms存储到会话中,并且只要要更改相关button的颜色,textview..just就可以从会话中取回颜色代码,并将其用作
例如。
session.setString("white","#FFFFFF"); String colorname=session.getString("white");yourtextview.setBackgroundColor(Color.parseColor(colorname);