Получить color-int из цветового ресурса


448

Есть ли способ получить color-int из цветового ресурса? Я пытаюсь получить отдельные красные, синие и зеленые компоненты цвета, определенного в ресурсе (R.color.myColor), чтобы я мог установить значения трех групп поиска для определенного уровня.

Ответы:


928

Ты можешь использовать:

getResources().getColor(R.color.idname);

Проверьте здесь, как определить пользовательские цвета:

http://sree.cc/google/android/defining-custom-colors-using-xml-in-android

РЕДАКТИРОВАТЬ (1): Так getColor(int id)как сейчас устарела , это должно быть использовано:

ContextCompat.getColor(context, R.color.your_color);

(добавлено в библиотеку поддержки 23)

EDIT (2):

Код ниже может использоваться как до, так и после зефира (API 23)

ResourcesCompat.getColor(getResources(), R.color.your_color, null); //without theme

ResourcesCompat.getColor(getResources(), R.color.your_color, your_theme); //with theme

7
как насчет android.R.color.some_color :-(
Бланделл

17
@ Blundell эээ, не знаю, если вам это нужно сейчас, но это работает android.R.color.some_colorслишком, например: getResources().getColor(android.R.color.holo_blue_bright)(по крайней мере, для API 17)
ataulm

30
getColor () теперь устарела, вы можете использовать: ContextCompat.getColor (context, R.color.your_color);
Рикардо

2
Я понимаю, что вы не тот, кто внес изменения, но в чем разница между ContextCompatи ResourcesCompat? Если нет практической разницы, было бы менее запутанным, если бы вы удалили один из них из своего ответа.
Сурагч

14
Почему Google считает необходимым отказаться от совершенно хорошей функции для этой ужасной компактной библиотеки приложений. Это отстой, есть оба.
Андрей С

116

Исходя из новой библиотеки поддержки Androidэтого обновления), теперь вам нужно позвонить:

ContextCompat.getColor(context, R.color.name.color);

Согласно документации :

public int getColor (int id)

Этот метод устарел на уровне API 23 . Вместо этого используйте getColor (int, Theme)

Это то же самое решение для getResources().getColorStateList(id):

Вы должны изменить это так:

ContextCompat.getColorStateList(getContext(),id);

РЕДАКТИРОВАТЬ 2019

Относительно ThemeOverlayиспользования контекста ближайшего представления:

val color = ContextCompat.getColor(
  closestView.context,
  R.color.name.color
)

Таким образом, вы получите правильный цвет на основе вашего ThemeOverlay.

Особенно необходимо, когда в одном упражнении вы используете разные темы, такие как темная / светлая тема. Если вы хотите больше узнать о темах и стилях, предлагается этот доклад: Разработка тем со стилем

Ник Батчер - Droidcon Berlin - Разработка тем со стилем


10
Для тех, кто интересуется тем, что нужно заполнить как тему в новом методе, Themeможно передать значение null, поэтому просто позвоните, getColor(R.color.my_color, null)если не знаете, какую тему передать.
w3bshark

хм ... это то, что все говорят, но я не могу заставить его работать. Должен ли я инициализировать контекст? В настоящее время я получаю «не могу разрешить символ« контекст »»
ColdTuna

Чтобы убедиться, что вы все делаете правильно, попробуйте вызвать его внутри onCreate действия, чем для получения контекста, вам нужно вызвать getContext () или просто «this»
Ultimo_m

35

Определите свой цвет

Значения / color.xml

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

    <!-- color int as #AARRGGBB (alpha, red, green, blue) -->
    <color name="orange">#fff3632b</color>
    ...
    <color name="my_view_color">@color/orange</color>

</resources>

Получить цвет int и установить его

int backgroundColor = ContextCompat.getColor(context, R.color.my_view_color);
// Color backgroundColor = ... (Don't do this. The color is just an int.)

myView.setBackgroundColor(backgroundColor);

Смотрите также


1
вы можете использовать только getResources()в Activityили Fragment?
Запнологика

2
@Zapnologica, см. Ответы на этот вопрос для размышлений об использовании getResources()вне Деятельности или Фрагмента.
Сурагч

1
@ Запнологика нет. getResources()также доступен как публичный API для всего, что реализует Context, а также для Views.
ataulm

7

Лучший подход

Как ответ @sat, хороший подход для получения цвета

ResourcesCompat.getColor(getResources(), R.color.your_color, null);

или используйте ниже путь, когда у вас нет доступа к getResources()методу.

Context context  = getContext(); // like Dialog class
ResourcesCompat.getColor(context.getResources(), R.color.your_color, null);

Что я делаю

public void someMethod(){
    ...
    ResourcesCompat.getColor(App.getRes(), R.color.your_color, null);
}

Его проще всего использовать в любом месте вашего приложения! Даже в классе Util или любом классе, где у вас нет Context или getResource ()

Проблема (когда у вас нет контекста)

Когда у вас нет Contextдоступа , как метод в вашем Utilклассе.

Предположим ниже метод без контекста.

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

Теперь вы будете передавать Contextв качестве параметра в этом методе и использоватьgetResources().

public void someMethod(Context context){
    ...
    context.getResources...
}

Итак, вот уникальное решение Bonus, с помощью которого вы можете получить доступ к ресурсам из любой точки мира Util class. Добавьте Resourcesв свой 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 getResourses() {
        return res;
    }

}

Добавьте поле имени к вашему manifest.xml <applicationтегу. (Если еще не добавлено)

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

Теперь тебе пора. Используйте в ResourcesCompat.getColor(App.getRes(), R.color.your_color, null);любом месте приложения.


5

Я обновил, чтобы использовать, ContextCompat.getColor(context, R.color.your_color);но иногда (На некоторых устройствах / версиях Android. Я не уверен), что вызывает NullPointerExcepiton.

Поэтому, чтобы заставить его работать на всех устройствах / версиях, я прибегаю к старому способу сделать это, в случае нулевого указателя.

try {
    textView.setTextColor(ContextCompat.getColor(getActivity(), R.color.text_grey_dark));
}
catch(NullPointerException e) {
    if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
        textView.setTextColor(getContext().getColor(R.color.text_grey_dark));
    }
    else {
        textView.setTextColor(getResources().getColor(R.color.text_grey_dark));
    }
}

почему бы не использовать старую версию во всех случаях, или если вы все равно проверяете версию, используйте новый API, Resources.getColor(int, Theme)если можете? Вы не должны ловить исключения во время выполнения.
ataulm

Полагаю, просто ОКР. ContextCompat, мне кажется, является будущим способом сделать это, и, следовательно, правильный путь. Так что мой подход - делай это правильно. И если это не удается (на старых устройствах или что-то еще), сделайте это по-старому. Почему я не должен ловить исключения во время выполнения?
ниндзячиппи

1

Для получения дополнительной информации о другом случае использования, который может помочь вспомнить этот вопрос в результатах поиска, я хотел применить альфу к цвету, определенному в моих ресурсах.

Используя правильный ответ @ sat:

int alpha = ... // 0-255, calculated based on some business logic
int actionBarBackground = getResources().getColor(R.color.actionBarBackground);
int actionBarBackgroundWithAlpha = Color.argb(
        alpha,
        Color.red(actionbarBackground),
        Color.green(actionbarBackground),
        Color.blue(actionbarBackground)
);

1

Нашел более простой способ, который также работает:

Color.parseColor(getString(R.color.idname);

Интересно, я не знал, что таким образом можно получить цвет в виде строки. Я не думаю, что это проще, но это интересно 😅
ataulm

0

Доступ к цветам из неактивного класса может быть затруднен. Одна из найденных альтернатив - использование enum. enumпредлагает большую гибкость.

public enum Colors
{
  COLOR0(0x26, 0x32, 0x38),    // R, G, B
  COLOR1(0xD8, 0x1B, 0x60),
  COLOR2(0xFF, 0xFF, 0x72),
  COLOR3(0x64, 0xDD, 0x17);


  private final int R;
  private final int G;
  private final int B;

  Colors(final int R, final int G, final int B)
  {
    this.R = R;
    this.G = G;
    this.B = B;
  }

  public int getColor()
  {
    return (R & 0xff) << 16 | (G & 0xff) << 8 | (B & 0xff);
  }

  public int getR()
  {
    return R;
  }

  public int getG()
  {
    return G;
  }

  public int getB()
  {
    return B;
  }
}


0

Если ваш текущий мин. Уровень API 23, вы можете просто использовать, getColor()как мы используем для getString():

//example
textView.setTextColor(getColor(R.color.green));
// if context is not available(ex: not in activity) use with context.getColor()

Если вы хотите ниже уровня API 23, просто используйте это:

textView.setTextColor(getResources().getColor(R.color.green));

Но обратите внимание, что getResources().getColor()это не рекомендуется в уровне API 23. В этом случае заменить выше:

textView.setTextColor(ContextCompat.getColor(this /*context*/, R.color.green)) //Im in an activity, so I can use `this`

ContextCompat : помощник для доступа к функциям вContext

Если вы хотите, вы можете ограничиться, SDK_INTкак показано ниже:

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
    textView.setTextColor(getColor(R.color.green));
} else {
    textView.setTextColor(getResources().getColor(R.color.green));
}

0
ContextCompat.getColor(context, R.color.your_color);

в деятельности

ContextCompat.getColor(actvityname.this, R.color.your_color);

фрагментарно

ContextCompat.getColor(getActivity(), R.color.your_color);

например:

tvsun.settextcolour(ContextCompat.getColor(getActivity(), R.color.your_color))
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.