我发现R.string非常棒,可以将硬编码的字符串排除在代码之外,我希望在与应用程序中的模型一起工作的实用程序类中继续使用它来生成输出。例如,在本例中,我从活动外部的模型生成了一封电子邮件。

是否可以在上下文或活动之外使用getString ?我想我可以通过目前的活动,但似乎没有必要。如果我说错了,请指正!

编辑:我们可以在不使用上下文的情况下访问资源吗?


当前回答

是的,我们可以不使用“上下文”来访问资源

你可以使用:

Resources.getSystem().getString(android.R.string.somecommonstuff)

... 在应用程序的任何地方,甚至在静态常量声明中。 不幸的是,它只支持系统资源。

对于本地资源,请使用此解决方案。这不是小事,但很有效。

其他回答

我使用 getContext () .getApplicationContext () .getString (R.string.nameOfString); 这对我很管用。

如果你想在上下文或活动之外使用getString,你应该在构造函数或方法参数中有上下文,这样你就可以访问getString()方法。 特别是在Fragment中,你应该确保getActivity()或getContext()没有提供空值。 要避免在Fragment中getActivity()或getContext()为空,请尝试以下方法: 声明一个变量:

Context mContext;

现在重写Fragment的onAttach和onDetach方法:

@Override
public void onAttach(Context context) {
    super.onAttach(context);
    mContext = context;
}

@Override
public void onDetach() {
    super.onDetach();
    mContext = null;
}

现在使用mContext无论你在哪里使用getString()方法。 例:

        Toast.makeText(mContext,  mContext.getString(R.string.sample_toast_from_string_file), Toast.LENGTH_SHORT).show();

不知何故,我不喜欢存储静态值的俗气解决方案,所以提出了一个更长的,但干净的版本,可以测试以及。

找到了两种可能的方法

通过上下文。Resources作为类的参数,在其中您需要字符串资源。相当简单。如果不能作为参数传递,则使用setter。

e.g.

data class MyModel(val resources: Resources) {
    fun getNameString(): String {
        resources.getString(R.string.someString)
    }
}

使用数据绑定(尽管需要片段/活动)

阅读之前:本版本使用数据绑定

XML-

<?xml version="1.0" encoding="utf-8"?>

<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools">

<data>
    <variable
        name="someStringFetchedFromRes"
        type="String" />
</data>

<TextView
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="@{someStringFetchedFromRes}" />
</layout>

活动/片段-

val binding = NameOfYourBinding.inflate(inflater)
binding.someStringFetchedFromRes = resources.getString(R.string.someStringFetchedFromRes)

有时,您需要根据模型中的字段更改文本。所以你也会数据绑定那个模型,因为你的activity/fragment知道这个模型,你可以很好地获取值,然后基于它数据绑定字符串。

这应该让你从任何地方访问applicationContext,允许你在任何可以使用它的地方获得applicationContext;Toast, getString(), sharedPreferences等。

单例模式:

package com.domain.packagename;

import android.content.Context;

/**
 * Created by Versa on 10.09.15.
 */
public class ApplicationContextSingleton {
    private static PrefsContextSingleton mInstance;
    private Context context;

    public static ApplicationContextSingleton getInstance() {
        if (mInstance == null) mInstance = getSync();
        return mInstance;
    }

    private static synchronized ApplicationContextSingleton getSync() {
        if (mInstance == null) mInstance = new PrefsContextSingleton();
        return mInstance;
    }

    public void initialize(Context context) {
        this.context = context;
    }

    public Context getApplicationContext() {
        return context;
    }

}

在你的Application子类中初始化单例:

package com.domain.packagename;

import android.app.Application;

/**
 * Created by Versa on 25.08.15.
 */
public class mApplication extends Application {

    @Override
    public void onCreate() {
        super.onCreate();
        ApplicationContextSingleton.getInstance().initialize(this);
    }
}

如果我没有错的话,这给了你一个无处不在的applicationContext钩子,用ApplicationContextSingleton.getInstance.getApplicationContext()调用它; 你不应该在任何时候都需要清除这个,因为当应用程序关闭时,这个会随它一起去。

记得更新AndroidManifest.xml来使用这个Application子类:

<?xml version="1.0" encoding="utf-8"?>

<manifest
    xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.domain.packagename"
    >

<application
    android:allowBackup="true"
    android:name=".mApplication" <!-- This is the important line -->
    android:label="@string/app_name"
    android:theme="@style/AppTheme"
    android:icon="@drawable/app_icon"
    >

如果你看到这里有什么问题,请告诉我,谢谢。:)

您可以在Kotlin中通过创建一个扩展Application的类来实现这一点,然后使用它的上下文来调用代码中的任何地方的资源

你的App类看起来是这样的

 class App : Application() {
    override fun onCreate() {
        super.onCreate()
        context = this
    }

    companion object {
        var context: Context? = null
            private set
    }
}

在AndroidManifest.xml中声明你的Application类(非常重要)

<application
        android:allowBackup="true"
        android:name=".App" //<--Your declaration Here
        ...>
        <activity
            android:name=".SplashActivity"  android:theme="@style/SplashTheme">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>

        <activity android:name=".MainActivity"/>
    </application>

要访问字符串文件,请使用以下代码

App.context?.resources?.getText(R.string.mystring)