以编程方式更改R.string的值

时间:2012-03-12 21:15:13

标签: android string resources

我在strings.xml文件中声明了一个字符串,并在我的活动中将其用作R.string.compose_title。 (将其设置为标题,即setTitle(R.id.compose_title))。现在在某些情况下我想编辑字符串然后用它来设置标题。我怎么能这样做?

P.S。我只需要更改单个字符串的值,因此使用本地化为每种情况(根据用户而变化)声明一个新的strings.xml似乎是效率低下的。

8 个答案:

答案 0 :(得分:44)

您需要了解的一点是,当您将数据作为资源提供时,在运行时无法修改。例如,在drawable文件夹中的drawables无法在运行时修改。确切地说,无法以编程方式修改“res”文件夹。

这也适用于Strings.xml,即“Values”文件夹。如果您想要一个必须在运行时修改的String,请创建一个单独的类,并将您的字符串放在此类中并在运行时访问。这是我发现的最佳解决方案。

答案 1 :(得分:4)

我认为您不能以编程方式自定义 R 类,因为它是由ADT自动构建的。

答案 2 :(得分:4)

示例howto:

如何? 通过将一个变量引用更改为其他引用

用法:

setRColor(pl.mylib.R.class,"endColor",pl.myapp.R.color.startColor);
// override app_name in lib R class  
setRString(pl.mylib.R.class,"app_name",pl.myapp.R.string.app_name);

基本方法:

public static void setRColor(Class rClass, String rFieldName, Object newValue) {
    setR(rClass, "color", rFieldName, newValue);
}

public static void setRString(Class rClass, String rFieldName, Object newValue) {
    setR(rClass, "string", rFieldName, newValue);
}

// AsciiStrings.STRING_DOLAR = "$";
public static void setR(Class rClass, String innerClassName, String rFieldName, Object newValue) {
    setStatic(rClass.getName() + AsciiStrings.STRING_DOLAR  + innerClassName, rFieldName, newValue);
}

辅助方法:

public static boolean setStatic(String aClassName, String staticFieldName, Object toSet) {
    try {
        return setStatic(Class.forName(aClassName), staticFieldName, toSet);
    } catch (ClassNotFoundException e) {
        e.printStackTrace();
        return false;
    }
}

public static boolean setStatic(Class<?> aClass, String staticFieldName, Object toSet) {
    try {
        Field declaredField = aClass.getDeclaredField(staticFieldName);
        declaredField.setAccessible(true);
        declaredField.set(null, toSet);
        return true;
    } catch (Exception e) {
        e.printStackTrace();
        return false;
    }
}
  

@ bradenV2我的应用程序支持多种语言,所以我想要一个   我的strings.xml中的字符串当前正在使用并更改,   然后使用那个 - atuljangra 3月12日和12月22日04:04

ps上面的解决方案是好的,例如当你想在已编译的lib / jar中注入一些数据时。但是如果你想要本地化字符串,只需在每个LANG CODE下的 res 下创建文件夹,比如值-CC,其中cc是lang代码(values-de,values-cs)等

然后你有两个选择:

  1. &#34;内置&#34;系统相关语言选择 - 基于设备选择郎
  2. 通过创建资源进行配置 - 您可以决定使用哪个lang show
  3. 像这样:

    configuration = new Configuration(resources.getConfiguration());
    configuration.setLocale(targetLocale);
    String localized = Context.createConfigurationContext(configuration)
        .getResources()
        .getString(resourceId);
    

    enter image description here

答案 3 :(得分:1)

我有这样的情况,其中我的一个strings.xml值有一些动态的部分。我使用“替换文本”(类似%%REPLACEMENT_EMAIL%%)设置strings.xml,当我想以编程方式使用该字符串时,我检索了资源的字符串值,并替换了该替换文本的实例动态值(例如用户输入)。

老实说,我的应用尚未本地化,但我仍在尝试遵循w.r.t的最佳做法。没有硬编码任何字符串。

答案 4 :(得分:0)

也许你想“修改”string.xml,所以当活动再次需要它时,它会使用新值,例如在屏幕旋转后保留一个新的动态标题。

首先,您无法修改资源。它已经编译好了。你不能修改R类(为什么?)它的所有属性都是“最终的”。

因此,对于上面的示例,您可以对要保留显示的属性使用onSaveInstanceState()和onRestoreInstanceState()。

答案 5 :(得分:0)

使用SharedPreferences而不是Java类。如果您决定从外部(Web)获取值,它将为您提供更多功能。在运行时填充Java类可能无法脱机。如果是SharedPreferences,您必须确保它们在应用首次启动时仅加载一次,然后仅通过手动请求进行更新,因为将使用先前的导入。

myActivity.getSharedPreferences("com.example.imported",0)
.edit()
.putString("The news",getTheNews())
.apply();

答案 6 :(得分:0)

我使用以下方法从API获取键值对,并将其全局存储在HashMap中。如果在HashMap中找不到键值,那么我将在strings.xml文件中搜索该键。将达到动态更改key值的目的。

public String getAppropriateLangText(String key) {
        String value = "";
        try {
            HashMap<String, String> HashMapLanguageData HashMapLanguageData = gv.getHashMapLanguageData();
            value = HashMapLanguageData.get(key);//Fetching the value of key from API
            if (value == null || value.length() == 0) { //If Key value not found, search in strings.xml file
                String packageName = getPackageName();
                int resId = getResources().getIdentifier(key, "string", packageName);
                value = getString(resId);
            }
        } catch (Exception e) {
            value = "";
        }

        return value;
    }

答案 7 :(得分:-1)

据我所知,在app运行时你无法改变资源价值(R类值)。为什么不尝试存储共享偏好?我建议你使用共享偏好