정적 컨텍스트에서 리소스 컨텐츠를 가져오려면 어떻게 해야 합니까?
나는 그 현을 읽고 싶다.xml
다른 많은 것들을 하기 전에 파일링을 합니다.setText
위젯에서 호출할 액티비티 오브젝트 없이 어떻게 해야 합니까?getResources()
온으로 할까요?
- 예를 들어 의 서브클래스를 만듭니다.
public class App extends Application {
- 설정
android:name
의 속성<application>
에 태그를 붙이다AndroidManifest.xml
예를 들어 새 클래스를 가리킵니다.android:name=".App"
- 에서
onCreate()
응용 프로그램 인스턴스의 메서드를 사용하여 컨텍스트를 저장합니다(예:this
)라는 이름의 스태틱필드에 접속합니다.mContext
이 필드를 반환하는 정적 메서드를 만듭니다.getContext()
:
다음과 같이 표시됩니다.
public class App extends Application{
private static Context mContext;
@Override
public void onCreate() {
super.onCreate();
mContext = this;
}
public static Context getContext(){
return mContext;
}
}
이제 다음을 사용할 수 있습니다.App.getContext()
콘텍스트를 얻고 싶을 때, 그리고 나서getResources()
(또는App.getContext().getResources()
).
시스템 리소스 전용!
사용하다
Resources.getSystem().getString(android.R.string.cancel)
정적 상수 선언에서도 응용 프로그램의 모든 위치에서 사용할 수 있습니다.
Kotlin 솔루션은 정적 애플리케이션 컨텍스트를 사용하는 것입니다.
class App : Application() {
companion object {
lateinit var instance: App private set
}
override fun onCreate() {
super.onCreate()
instance = this
}
}
Strings 클래스는 어디서든 사용합니다.
object Strings {
fun get(@StringRes stringRes: Int, vararg formatArgs: Any = emptyArray()): String {
return App.instance.getString(stringRes, *formatArgs)
}
}
따라서 리소스 문자열을 깔끔하게 가져올 수 있습니다.
Strings.get(R.string.some_string)
Strings.get(R.string.some_string_with_arguments, "Some argument")
이 답변은 삭제하지 말아주세요. 제가 보관하겠습니다.
지름길
사용하고 있다App.getRes()
대신App.getContext().getResources()
(@Cristian이 대답한 대로)
코드 내 어디에서나 쉽게 사용할 수 있습니다!
여기에서는 다음과 같은 장소에서 리소스에 액세스할 수 있는 고유한 솔루션이 있습니다.Util class
.
(1) 작성 또는 편집Application
학급.
import android.app.Application;
import android.content.res.Resources;
public class App extends Application {
private static App mInstance;
private static Resources res;
@Override
public void onCreate() {
super.onCreate();
mInstance = this;
res = getResources();
}
public static App getInstance() {
return mInstance;
}
public static Resources getRes() {
return res;
}
}
(2) [이름(Name)]필드 추가manifest.xml
<application
태그(또는 이미 있는 경우에는 건너뜁니다)
<application
android:name=".App"
...
>
...
</application>
이제 가도 좋아요.
사용하다App.getRes().getString(R.string.some_id)
암호의 어느 곳이라도.
다른 가능성도 있다.다음과 같은 리소스에서 OpenGl 셰이더를 로드합니다.
static private String vertexShaderCode;
static private String fragmentShaderCode;
static {
vertexShaderCode = readResourceAsString("/res/raw/vertex_shader.glsl");
fragmentShaderCode = readResourceAsString("/res/raw/fragment_shader.glsl");
}
private static String readResourceAsString(String path) {
Exception innerException;
Class<? extends FloorPlanRenderer> aClass = FloorPlanRenderer.class;
InputStream inputStream = aClass.getResourceAsStream(path);
byte[] bytes;
try {
bytes = new byte[inputStream.available()];
inputStream.read(bytes);
return new String(bytes);
} catch (IOException e) {
e.printStackTrace();
innerException = e;
}
throw new RuntimeException("Cannot load shader code from resources.", innerException);
}
보시는 바와 같이 경로 내의 모든 리소스에 액세스할 수 있습니다./res/...
바꾸다aClass
당신의 반에.또한 테스트(Android Tests)에서 리소스를 로드하는 방법도 있습니다.
싱글톤:
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);
}
}
확실히 어플리케이션에 접속할 수 있습니다.어디서나 콘텍스트에 접속할 수 있습니다.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"
>
이제 ApplicationContextSingleton.getInstance().getApplicationContext().getResources()는 응용 프로그램 서브클래스가 사용할 수 없는 극소수 장소에서도 사용할 수 있게 됩니다.
뭔가 잘못된 점이 있으면 알려주세요.감사합니다. : )
또 다른 솔루션:
스태틱하지 않은 외부 클래스에 스태틱서브클래스가 있는 경우 외부 클래스 내의 스태틱 변수를 통해 서브 클래스 내의 리소스에 액세스할 수 있습니다.이러한 변수는 외부 클래스 작성 시 초기화됩니다.맘에 들다
public class Outerclass {
static String resource1
public onCreate() {
resource1 = getString(R.string.text);
}
public static class Innerclass {
public StringGetter (int num) {
return resource1;
}
}
}
getPageTitle(int position)에 사용했습니다.I8N으로 인해 유용한 fragmentActivity 내의 정적 FragmentPagerAdapter의 기능.
저는 더 많은 방법이 가능하다고 생각합니다.다만, 이 솔루션을 사용하는 경우가 있습니다.(완전 글로벌):
import android.content.Context;
import <your package>.R;
public class XmlVar {
private XmlVar() {
}
private static String _write_success;
public static String write_success() {
return _write_success;
}
public static void Init(Context c) {
_write_success = c.getResources().getString(R.string.write_success);
}
}
//After activity created:
cont = this.getApplicationContext();
XmlVar.Init(cont);
//And use everywhere
XmlVar.write_success();
정적 기능에서 openGL ES용 셰이더를 로드합니다.
파일 및 디렉터리 이름에 소문자를 사용해야 합니다. 그렇지 않으면 작업이 실패합니다.
public class MyGLRenderer implements GLSurfaceView.Renderer {
...
public static int loadShader() {
// Read file as input stream
InputStream inputStream = MyGLRenderer.class.getResourceAsStream("/res/raw/vertex_shader.txt");
// Convert input stream to string
Scanner s = new Scanner(inputStream).useDelimiter("\\A");
String shaderCode = s.hasNext() ? s.next() : "";
}
...
}
API level 27을 사용하고 있는데 이틀 정도 고군분투 끝에 최적의 해결책을 찾았습니다.Activity 또는 Application에서 파생되지 않은 클래스에서 xml 파일을 읽으려면 다음을 수행하십시오.
자산 디렉토리 내에 testdata.xml 파일을 넣습니다.
테스트 데이터 문서를 구문 분석하려면 다음 코드를 작성하십시오.
InputStream inputStream = this.getClass().getResourceAsStream("/assets/testdata.xml"); // create a new DocumentBuilderFactory DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); // use the factory to create a documentbuilder DocumentBuilder builder = factory.newDocumentBuilder(); // create a new document from input stream Document doc = builder.parse(inputStream);
컨텍스트가 없는 InputStream으로 이미지 재시작 가져오기:
Class<? extends MyClass> aClass = MyClass.class;
URL r = aClass.getResource("/res/raw/test.png");
URLConnection urlConnection = r.openConnection();
return new BufferedInputStream(urlConnection.getInputStream());
파일의 디렉토리 트리가 필요한 경우는, 다음과 같이 동작합니다(자산은 서브 디어를 서포트합니다).
URL r = aClass.getResource("/assets/images/base/2.png");
왜 노력하지 않는가
Resources.getSystem().getString(R.string.foo);
다음은 여러분이 시도할 수 있는 약간 다른 대체 접근법입니다.
당신은 서브클래스를수 있습니다 할 subclass 수 있다.Application
다른 해결책 언급된 무엇처럼 등급, 그리고 다른 솔루션이 언급한 것과 같은 클래스 및 정적 참조를 저장합니다의 인스턴스로 정적 참조를 저장해 둔다.Resources
..
그리고응용 프로그램클래스를 만들고 initialise 응용 프로그램 클래스를 만듭니다.Resources
그 변수에 변수onCreate
방법.방법. 너의 앱이 시작되 이 호출됩니다.앱이 시작되면 호출됩니다.우리는사용할 수 있습니다 사용할 수 있다.WeakReference
여기 staticvariable(비록 일은 일어나지는 않을 것 같다)이 인스턴스를 정적 변수로 저장했을 때 발생할 수 있는 메모리 누수를 방지하기 위한 것입니다(단, 발생 가능성은 매우 낮습니다)로 이 인스턴스를 저장하는 결과로 발생 할 수 있는 메모리 누수를 방지한다.
public class App extends Application {
private static WeakReference<Resources> res;
xml 자원 선언에서 문자열만 취득하는 것을 언급했기 때문에 리소스 인스턴스의 캡슐화 및 유출을 방지하기 위해 이 자원 변수를 다른 클래스에 노출할 필요가 없습니다.따라서 참조를 개인 변수로 저장할 수 있습니다.
이 변수를잊지 마십시오 것을 초기화하는에 이 변수 initialise는 것을 기억하라.onCreate
::
@Override
public void onCreate() {
super.onCreate();
res = new WeakReference<>(getResources());
}
우리는 또한 응용 프로그램의또한 어플리케이션의 어플리케이션의를 선언할 필요가 있다.android:name
~하듯이로.App
당신이한 다른 AndroidManifest.xml
application
붙이다
<application android:name=".App"
........... other attributes here ...........
하는 또 다른 은 ""를 하지 않는 입니다.Resources
예Context
단, instance를 App
methodstatic .그러면 인스턴스는 캡슐화/프라이빗 상태로 유지됩니다.
방식을 할 수 .App
class:getStringGlobal
는 하지 주세요.getString
★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★」
public static String getStringGlobal(@StringRes int resId) {
if (res != null && res.get() != null) {
return res.get().getString(resId);
} else {
// This should not happen, you should throw an exception here, or you can return a fallback string to ensure the app still runs
}
}
.Resources
을 사용하다
그런 다음 호출하여 문자열 리소스를 가져올 수 있습니다.
App.getStringGlobal(R.string./*your string resource name*/)
당신의 ★★★★★★★★★★★★★★★★★★★.App.java
:
public class App extends Application {
private static WeakReference<Resources> res;
@Override
public void onCreate() {
super.onCreate();
res = new WeakReference<>(getResources());
}
public static String getStringGlobal(@StringRes int resId) {
if (res != null && res.get() != null) {
return res.get().getString(resId);
} else {
// This should not happen(reference to Resources invalid), you should throw an exception here, or you can return a fallback string to ensure the app still runs
}
}
}
스태틱 함수를 실장하는 클래스에서는 이 클래스에서 private\public 메서드를 호출할 수 있습니다.private\public 메서드는 getResources에 액세스할 수 있습니다.
예를 들어 다음과 같습니다.
public class Text {
public static void setColor(EditText et) {
et.resetColor(); // it works
// ERROR
et.setTextColor(getResources().getColor(R.color.Black)); // ERROR
}
// set the color to be black when reset
private void resetColor() {
setTextColor(getResources().getColor(R.color.Black));
}
}
다른 클래스\activity에서 다음 콜을 할 수 있습니다.
Text.setColor('some EditText you initialized');
문맥이 있다면, 내 말은 내면을 말하는 거야.
public void onReceive(Context context, Intent intent){
}
다음 코드를 사용하여 리소스를 가져올 수 있습니다.
context.getResources().getString(R.string.app_name);
public Static Resources mResources;
@Override
public void onCreate()
{
mResources = getResources();
}
언급URL : https://stackoverflow.com/questions/4391720/how-can-i-get-a-resource-content-from-a-static-context
'itsource' 카테고리의 다른 글
Junit 테스트에서 기본 Spring-Boot application.properties 설정을 덮어씁니다. (0) | 2022.08.14 |
---|---|
Java에서의 콜백 함수 (0) | 2022.08.14 |
Vue.js: 조건부 클래스 스타일 바인딩 (0) | 2022.08.14 |
Vue.js에서 optgroup select 라벨을 설정하는 방법 (0) | 2022.08.14 |
구성 요소 방법 재정의 (0) | 2022.08.14 |