• 4

A PHP Error was encountered

Severity: Notice

Message: Undefined index: userid

Filename: views/question.php

Line Number: 191


File: /home/prodcxja/public_html/questions/application/views/question.php
Line: 191
Function: _error_handler

File: /home/prodcxja/public_html/questions/application/controllers/Questions.php
Line: 433
Function: view

File: /home/prodcxja/public_html/questions/index.php
Line: 315
Function: require_once

I have a scenario in which I want to set a Drawable depending upon the theme defined.

To explain this further, Here is what I have in code:


    <declare-styleable name="AppTheme">
        <attr name="homeIcon" format="reference" />


    <style name="AppTheme" parent="android:style/Theme">
        <item name="attr/homeIcon">@drawable/ic_home</item>


    <application android:label="@string/app_name"
        <activity android:name=".MainActivity" android:label="@string/app_name">
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />

So as you have noticed I am defining a custom attr homeIcon and setting the attribute value in AppTheme.

When I define this attribute in a layout XML and try to access it it works smoothly

<ImageView android:id="@+id/img"
        android:src="?attr/homeIcon" />

and renders the Drawable ic_home in an ImageView.

But I am not able to figure out how to access the Drawable programmatically.

I tried to do this with a work around, by defining a holder LayerList Drawable, which results in resource not found exception:

<?xml version="1.0" encoding="utf-8"?>
    xmlns:android="http://schemas.android.com/apk/res/android" >
        android:drawable="?attr/homeIcon" />

Summary I want to access the Drawable defined in a custom defined Theme programmatically.

I think you can get the Drawable with this code:

TypedArray a = getTheme().obtainStyledAttributes(R.style.AppTheme, new int[] {R.attr.homeIcon});     
int attributeResourceId = a.getResourceId(0, 0);
Drawable drawable = getResources().getDrawable(attributeResourceId);
  • 72
Reply Report
      • 1
    • It wokrs, but you should call a.recycle(); after you're done. Also, first parameter in obtainStyledAttributes is optional.
    • Well, this may be simplified even more: just Drawable drawable = a.getDrawable(0); is enough (where 0 is the index of requeired attribute in new int[] array).
      • 2
    • If you plan to override those attributes in another themes dont use R.style.AppTheme` because values will always be taken from this Theme. Just use obtainStyledAttributes(new int[] {R.attr.homeIcon}); and then as @AlexSemeniuk mentioned a.getDrawable(0)

Another possible way to do it:

  public static int getResIdFromAttribute(final Activity activity,final int attr)
      return 0;
    final TypedValue typedvalueattr=new TypedValue();
    return typedvalueattr.resourceId;

Or in Kotlin:

fun getResIdFromAttribute(activity: Activity, attr: Int): Int {
    if (attr == 0)
        return 0
    val typedValue = TypedValue()
    activity.theme.resolveAttribute(attr, typedValue, true)
    return typedValue.resourceId

no need to recycle anything here...


int drawableResId=getResIdFromAttribute(this,R.attr.homeIcon);
Drawable drawable = getResources().getDrawable(drawableResId);
  • 11
Reply Report

I used below method to get resource id form style attribute. Then it can be used for drawable, string, dimension so on.

TypedArray typedArray = context.getTheme().obtainStyledAttributes(new int[] { R.attr.attrName });   
int resourceId = typedArray.getResourceId(0, defaultResourceId);

cheers :-)

  • 2
Reply Report

Here are the results of my investigation, regarding this topic. If we have declare-stylable then we can override those values in themes.

So far the best way that I found how to get them is the following.

TypedArray a = context.getTheme().obtainStyledAttributes(R.styleable.AppTheme);

By using R.styleable.AppTheme_homeIcon we are referencing exactly that attribute that we want. For example if we would have few more attributes, then we can reference them as follows:


And if in current theme those attributes were not defined you will get default values and no Exceptions.

  • 1
Reply Report