Programing

API 응답에서 얻은 색상 리소스의 값을 프로그래밍 방식으로 변경

crosscheck 2020. 10. 30. 07:45
반응형

API 응답에서 얻은 색상 리소스의 값을 프로그래밍 방식으로 변경


내 API 호출에라는 매개 변수가 있다고 가정 해 보겠습니다 color. R.colors.colorAPI 결과에서 색상을 할당하기 위해 존재를 편집하거나 수정할 수 있습니까?

예로서:

내 API를 호출하면을 반환합니다 green. 이제 내 앱을 (녹색 Toolbar, 녹색 TextView등) 로드하고 싶습니다 . 가능합니까?

내 첫 생각은 :

에 항목을 만들기 colors.xml라는 demo이 사용 후, 그것을 기본 색을 지정 다음을 demo내가 원하는 목적지 색상을 ( Button, TextView, 등) 그런 다음 내가 필요하지 않을 그래서이 API의 결과로 프로그램이 값을 변경하는 것이 가능할 수 있다고 생각 크리에이트 SharedPreferences같은 더 많은 코드를 피하거나 무언가를.

으로 @YS는 나에게 말했다

불행히도 텍스트의 색상을 설정하거나 모든 곳에서 수동으로 볼 수 있습니다 ... :(

Activities내 프로젝트에 얼마나 많이 포함 될지 모르기 때문에 다른 방법이 있으면 좋겠다 . 그래서 다른 방법이 있으면 다른 추측을 듣고 기쁘다.

편집하다

나는 @Jared Rummler 대답을 시도하고 있고 어쩌면 내가 뭔가 잘못하고 있을지도 모른다 ... 나는 간단한 것을 Json만들고 나는 내 자산에 내가 파싱 Json하고 그것을 넣은 GlobalConstant다음 "간단한 앱"을 만들었다.

우선 나는 "your_special_color"를 포함하는 a TextView와 a를 Button가지고 있으며, 그 반환은 GlobalConstant int다음과 같이 넣습니다 .

case "your_special_color":                
            return GlobalConstant.color; 

그럼 내가 노력하는 것은 나의 최초의 Activity1이 TextView1을 Button내가 전에 말했듯이 그들은 색상이 "your_special_color"나는 그것을 변경하지 않습니다,하지만 나는이 것을 Intent내에서 Button다른 여는 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됩니다.

더욱이,

애플리케이션이 컴파일 되면 디렉토리의 모든 리소스에 대한 리소스 ID가 포함 된 클래스를 aapt생성합니다 . 각 리소스 유형에 대해 하위 클래스 (예 : 모든 드로어 블 리소스)가 있고 해당 유형의 각 리소스에 대해 정적 정수 (예 :)가 있습니다. 이 정수는 리소스를 검색하는 데 사용할 수있는 리소스 ID입니다.Rres/RR.drawableR.drawable.icon

이것이 본질적으로 말하는 것은 디렉토리 에서 리소스보유 된 거의 모든 res/것이 컴파일되고 변경 불가능한 상수로 참조된다는 것입니다. 이 때문에 리소스 요소의 값은 컴파일 되기 때문에 프로그래밍 방식으로 / 런타임에 변경할 수 없습니다 . 로컬 / 글로벌 변수 & SharedPreferences달리 자원 요소는 프로그램 메모리에서 변경 불가능한 고정 객체로 표시됩니다. 프로그램 메모리의 특수 읽기 전용 영역에 보관됩니다. 이와 관련하여 프로그래밍 방식으로 R.String 값 변경을 참조하십시오 .

당신이 할 수있는 일은 프로젝트의 천 개 위치에서 동일한 코드를 사용하지 않으려면의 색상 값을 변경하는 공통 함수를 SharedPreferences만들고이 방법을 모든 곳에서 사용하는 것입니다. 물론 이미 알고 계실 겁니다.

프로젝트에 추가해야하는 코드의 양을 줄이려면 대안이 있습니다. 이전 에 앱 전체에서 글꼴 스타일과 색상을 수정할 수 있는 서예 라이브러리사용했습니다 . 이것은 당신에게 도움이 될 수 있습니다.


당신은 확장하는 클래스를 만들 수 있습니다 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;
    }

    ...

}

This is the approach I have used in one of my apps, Root Check. If you override getResources in your activities and main application class you can change the theme programmatically (even though themes are immutable). If you want, download the app and see how you can set the primary, accent, and background colors from preferences.


You can't change an app's resources, they are all constants. Instead you can save your color in SharedPrefences and use the color from there.

See How to use SharedPreferences in Android to store, fetch and edit values.

If your app already has a R.color.green defined and you just want to access it based on what API returned you use:

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

R class is not supposed to be edited. It merely contains references to your resources.

You will need to set it manually. However, to reduce the burden of setting it manually you can try to use special libraries for preference saving, for instance:

(full list of similar libraries https://android-arsenal.com/tag/75)


Also, you might want to think about another way of applying styles and passing parameters - consider you would want to add some other parameters like height, width etc. For that purpose, you can define custom attribute in themes.xml/styles.xml:

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

then define styles:

<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>

then use that color in your xml like this:

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

and switch between GreenActivity and RedActivity styles in Activity.onCreate:

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

With the above approach, you will be able to easily configure your styles in xml and it should be less code and easier to refactor in future. (You will still need to have one variable in preference to save whether you have green or red style)


Another way, if you want to show demos of your app with different colors is to use build variants / flavors for loading your app with different colors and styles (it is for build time - not runtime):

app/src/main/res/colors.xml

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

app/src/buildVariant/res/colors.xml

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

Now you can quickly switch between "main" and "buildVariant" in Build Variants menu and launch your app with different "demo" colors. The same way you can customize a lot of other attributes.

Search for "Build Variants" here http://developer.android.com/tools/building/configuring-gradle.html


store hex color codes into sharedpreferences and then use parsecolor function store your all hexcodes of colors into sessions as a string and whenever you want to change color of perticular button ,textview..just retrive that color code from session and use it as
for ex.
session.setString("white","#FFFFFF"); String colorname=session.getString("white");yourtextview.setBackgroundColor(Color.parseColor(colorname);

참고URL : https://stackoverflow.com/questions/33987678/programmatically-change-the-value-of-a-color-resource-obtained-from-api-response

반응형