안드로이드 : 이름을 사용하여 리소스에서 문자열을 얻는 방법은 무엇입니까?


553

UI에 2 가지 언어를 사용하고 리소스 파일에 별도의 문자열 값을 지정하고 싶습니다 res\values\strings.xml.

<string name="tab_Books_en">Books</string>
<string name="tab_Quotes_en">Quotes</string>
<string name="tab_Questions_en">Questions</string>
<string name="tab_Notes_en">Notes</string>
<string name="tab_Bookmarks_en">Bookmarks</string>

<string name="tab_Books_ru">Книги</string>
<string name="tab_Quotes_ru">Цитаты</string>
<string name="tab_Questions_ru">Вопросы</string>
<string name="tab_Notes_ru">Заметки</string>
<string name="tab_Bookmarks_ru">Закладки</string>

이제 앱에서 이러한 값을 동적으로 검색해야합니다.

spec.setContent(R.id.tabPage1);
String pack = getPackageName();
String id = "tab_Books_" + Central.lang;
int i = Central.Res.getIdentifier(id, "string", pack);
String str = Central.Res.getString(i);

내 문제는 i = 0.

내 경우에는 왜 작동하지 않습니까?


1
Central.lang이 en또는 ru입니까?
— K-ballo

1
코드를 검사하려면 더 많은 정보가 필요합니다. i를 받기 전에 각 var의 상태는 무엇입니까? 어쨌든, 당신은 일을 간단하게 유지하기 위해 안드로이드에서 기본 현지화 지원을 사용해야합니다.
— Alin

답변:


1069

언급 한 링크는 런타임에 생성 된 문자열로 작동하는 것 같습니다. strings.xml의 문자열은 런타임에 작성되지 않습니다. 당신은 그들을 통해 얻을 수 있습니다

String mystring = getResources().getString(R.string.mystring);

getResources()Context클래스 의 방법입니다 . ( Activity또는 Service컨텍스트를 확장 하는) 내부에있는 경우이 코드 조각과 같이 사용할 수 있습니다.

또한 전체 언어 종속성은 android 프레임 워크에서 처리 할 수 ​​있습니다 . 언어마다 다른 폴더를 만들면됩니다. 영어가 기본 언어 인 경우 영어 문자열을에 넣으십시오 res/values/strings.xml. 그런 다음 새 폴더를 만들고 values-ru이름이 같은 러시아어 문자열을에 넣습니다 res/values-ru/strings.xml. 이 시점에서 안드로이드는 전화를 걸 getString()거나 XML을 통해 문자열을 참조 할 때 장치 로캘에 따라 올바른 것을 선택합니다 @string/mystring. 의 res/values/strings.xml폴더는 폴백 폴더이며, 사용자 로캘을 포함하는 폴더가 없으면이 폴더가 기본값으로 사용됩니다.

자세한 내용은 현지화 및 리소스 제공 을 참조하십시오.


23
에 있다면 직접 android.support.v4.app.Fragment전화하면 getString(R.string.mystring)됩니다.
— JaKXz

3
나는 방황했다. 왜 그렇게 복잡한 방식으로 (Google에서) 수행됩니까? 먼저 (R 객체에서) mystring의 숫자 ID를 얻은 다음 해당 ID로 문자열을 가져 옵니까? 그리고 "ID-of-mystring => actualValue"쌍이 실제로 어디에 있습니까? 내가 아는 한 mystring => ID-of-mystring은 R.java에 있지만, 그것이 바로 그것입니다 :)
— Lukáš Řádek

2
"R"이 프로젝트의 R이 기본 Android R이 아닌지 확인하십시오.
— ralphgabb

2
이것은 필요한 답변 일 수도 있지만 요청 된 답변이 아닙니다! 이름으로 문자열 리소스에 동적으로 액세스하려면 @leonvian의 답변을 참조하십시오. 이것은 승인 된 IMO 여야합니다.
— Chris Hatton

321

나는 같은 문제를 가지고있다. 그러나 아래 코드는 저에게 효과적입니다. packageName이 올바른지 확인하십시오. Android 애플리케이션의 루트 패키지를 참조해야합니다.

private String getStringResourceByName(String aString) {
      String packageName = getPackageName();
      int resId = getResources().getIdentifier(aString, "string", packageName);
      return getString(resId);
    }

9
누군가이 작업을 수행 해야하는 이유가있는 경우 (예 : 데이터 파일에 표시 할 리소스 문자열을 결정하거나 인터넷 에서이 문자열을 가져 오는지를 결정하는 사용자 지정 문자열이 포함되어 있음)-그 점을 지적하고 싶습니다 이 솔루션이 맞습니다. 특히 자원 유형이 string아닌 부분을 ​​정정하십시오 strings. 논리적이기 때문에 (다른 안드로이드와 마찬가지로). 따라서 @leonvian에게 감사드립니다. :-)
— Ivan Vučica

2
@ 문자열로 배열을 가져 오는 @Sameer는 다음을 사용하십시오. res.getStringArray (R.array.planets_array); 이 oficial 링크를 살펴보십시오 : developer.android.com/guide/topics/resources/…
— leonvian

3
멋있는. 별도의 메소드 선언을 제거하기 위해 다음과 같이 "단순화"할 수 있습니다 String someStringFromXML = getString(getResources().getIdentifier("some_string_name", "string", getPackageName()));.
— 신경 전달 물질

80

활동에서만이 아님 :

    public static String getStringByIdName(Context context, String idName) {
        Resources res = context.getResources();
        return res.getString(res.getIdentifier(idName, "string", context.getPackageName()));
    }

감사합니다
— Mosa

39
getResources().getString(getResources().getIdentifier("propertyName", "string", getPackageName()))

26

나는 leonvian의 솔루션에 무언가를 추가 할 것이므로 우연히 문자열이 리소스 중에서 발견되지 않으면 (반환 값 0, 유효한 리소스 코드는 아님) 함수는 무언가를 반환 할 수 있습니다 :

private String getStringResourceByName(String aString) {
    String packageName = getPackageName();
    int resId = getResources()
            .getIdentifier(aString, "string", packageName);
    if (resId == 0) {
        return aString;
    } else {
        return getString(resId);
    }
}

15

최고의 접근법

App.getRes().getString(R.string.some_id)

어디에서나 작동합니다 (유틸리티, 모델도).

모든 답변을 읽었으며 모든 답변을 통해 업무를 수행 할 수 있습니다.

  • 또는 getString(R.string.some_string_id)모두에 사용할 수 있습니다 .ActivityFragment
  • 메소드에 Context.getString(R.string.some_string_id)직접 액세스 할 수없는 곳에서 사용할 수 있습니다 getString(). 처럼 Dialog.

문제

때 당신이없는 Context액세스를 당신의 방법처럼 Util클래스입니다.

컨텍스트가없는 아래 메소드를 가정하십시오.

public void someMethod(){
    ...
    // can't use getResource() or getString() without Context.
}

이제이 Context방법에서 매개 변수로 전달 하고getString().

public void someMethod(Context context){
    ...
    context.getString(R.string.some_id);
}

내가하는 일은

public void someMethod(){
    ...
    App.getAppResources().getString(R.string.some_id)
}

뭐? 앱 어디에서나 사용하는 것은 매우 간단합니다!

다음은 어디에서나 리소스에 액세스 할 수 있는 솔루션Util class 입니다.

import android.app.Application;
import android.content.res.Resources;

public class App extends Application {
    private static Resources resources;

    @Override
    public void onCreate() {
        super.onCreate();

        resources = getResources();
    }

    public static Resources getAppResources() {
        return resources;
    }

}

manifest.xml <application태그에 이름 필드를 추가하십시오 .

<application
        android:name=".App"
        ...
        >
        ...
    </application>

이제 잘 가십시오. App.getAppResources().getString(R.string.some_id)앱의 어느 곳에서나 사용하십시오 .


+1 간단하고 깨끗한 솔루션. 맞춤법이 잘못 getResourses되면 getResources재정의가 발생합니다. 또한 싱글 톤 패턴은 불필요 해 보일 수 있습니다. 이 솔루션의 메모리 누수 문제가 있습니까?
— Xarvalus

@Xarvalus 메모리 누수가 발생합니까?
— Khemraj

내 응용 프로그램에서 모든 괜찮습니다 :) 누군가가 그것에 문제가 있는지 궁금합니다. 함정에 부딪 치면 알려 드리겠습니다.
— Xarvalus

1
@Xarvalus 메모리 누수는 일반적으로 부모 클래스가 파괴 되더라도 변수가 사용되는 곳에서 발생합니다. 활동, 조각처럼. 나는이 경우에 일어날 것이라고 생각하지 않습니다.
— Khemraj


14

리소스 문자열을 문자열에서 TextView로 가져 오는 간단한 방법. 여기 resourceName은 자원의 이름입니다

int resID = getResources().getIdentifier(resourceName, "string", getPackageName());
textview.setText(resID);

7

활동 참조가없는 경우 다음과 같은 방식으로 컨텍스트를 사용할 수 있습니다.

getContext().getString(R.string.your_string_name);

4

"Ok", "Cancel"등과 같은 미리 정의 된 Android 문자열 세트도 있으므로 모두 선언 할 필요가 없습니다. 다음과 같이 간단하게 사용할 수 있습니다.

getString(android.R.string.ok)

(이 경우 "Ok"문자열). BTW에는 아이콘 이미지 등과 같은 다른 Android 리소스도 있습니다.



1

당신은 활동에서 이것을 시도 할 수 있습니다 :

getResources().getString(R.string.your string name);

조각과 같은 다른 상황에서는 ... 사용

getContext().getResources().getString(R.string.your string name);

0

안전을 위해 다음을 추가해야합니다. mContext.getResources (). getString (R.string.your_string);

mContext는 Fragment의 onAttach () 또는 Activity의 context 일 수 있습니다.


0

액티비티 나 프 래그 넷에 넣고 싶지 않은 경우 :

getContext().getResources().getString(R.string.string_name);

활동 컨텍스트가없는 활동 또는 조각 외부의 클래스에서 가져 오려면 응용 프로그램 컨텍스트를 사용하십시오.

getApplicationContext().getResources().getString(R.string.string_name);

당사 사이트를 사용함과 동시에 당사의 쿠키 정책과 개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.