以编程方式获取主题属性

时间:2011-11-19 02:56:15

标签: android android-theme

如何以编程方式获取Theme属性的值?

例如:

主题:

<style name="Theme">
    ... truncated ....
    <item name="textAppearanceLarge">@android:style/TextAppearance.Large</item>
</style>

代码:

int textSize = ???? // how do I get Theme.textAppearanceLarge? 

编辑:太多答案没有解决问题。

3 个答案:

答案 0 :(得分:6)

使用此功能:

myView.setTextAppearance(Context context, int resid)
//Sets the text color, size, style, hint color, and highlight color from the specified TextAppearance resource.

请参阅:http://developer.android.com/reference/android/widget/TextView.html#setTextAppearance%28android.content.Context,%20int%29

从TextView.java开始,这就是上面的函数:

public void setTextAppearance(Context context, int resid) {
    TypedArray appearance =
        context.obtainStyledAttributes(resid,
                                       com.android.internal.R.styleable.TextAppearance);

    int color;
    ColorStateList colors;
    int ts;

    .
    .
    .
    ts = appearance.getDimensionPixelSize(com.android.internal.R.styleable.
                                          TextAppearance_textSize, 0);
    if (ts != 0) {
        setRawTextSize(ts);
    }

    int typefaceIndex, styleIndex;

    typefaceIndex = appearance.getInt(com.android.internal.R.styleable.
                                      TextAppearance_typeface, -1);
    styleIndex = appearance.getInt(com.android.internal.R.styleable.
                                   TextAppearance_textStyle, -1);

    setTypefaceByIndex(typefaceIndex, styleIndex);
    appearance.recycle();
}

这是另一种方法。确保您回收外观(TypedArray obect)。希望这有帮助!

答案 1 :(得分:1)

这应该可以解决问题:

int textAppearance = android.R.attr.textAppearanceLarge;
myTextView.setTextAppearance(context, textAppearance);

答案 2 :(得分:0)

我最终得到了以下代码:

public class TextAppearanceConsts
{
    private static final String LOG_TAG = "TextAppearanceConsts";

    public static final int[] styleable_TextAppearance;
    public static final int styleable_TextAppearance_textColor;
    public static final int styleable_TextAppearance_textSize;
    public static final int styleable_TextAppearance_typeface;
    public static final int styleable_TextAppearance_fontFamily;
    public static final int styleable_TextAppearance_textStyle;

    static {
        // F*ing freaking code
        int ta[] = null, taTc = 0, taTs = 0, taTf = 0, taFf = 0, taTst = 0; 
        try{
            Class<?> clazz = Class.forName("com.android.internal.R$styleable", false, TextAppearanceConsts.class.getClassLoader());
            ta = (int[])clazz.getField("TextAppearance").get(null);
            taTc = getField(clazz, "TextAppearance_textColor");
            taTs = getField(clazz, "TextAppearance_textSize");
            taTf = getField(clazz, "TextAppearance_typeface");
            taFf = getField(clazz, "TextAppearance_fontFamily");
            taTst = getField(clazz, "TextAppearance_textStyle");
        }catch(Exception e){
            Log.e(LOG_TAG, "Failed to load styleable_TextAppearance", e);
        }
        styleable_TextAppearance = ta;
        styleable_TextAppearance_textColor = taTc;
        styleable_TextAppearance_textSize = taTs;
        styleable_TextAppearance_typeface = taTf;
        styleable_TextAppearance_fontFamily = taFf;
        styleable_TextAppearance_textStyle = taTst;
    }

    private static int getField(Class<?> clazz, String fieldName)
    throws IllegalAccessException
    {
        try{
            return clazz.getField(fieldName).getInt(null);
        }catch(NoSuchFieldException nsfe){
            Log.e(LOG_TAG, nsfe.toString());
            return -1;
        }
    }

}

用法示例:

TypedArray ta = context.obtainStyledAttributes(attrs, R.styleable.RangeBar, 0, 0);
TypedArray appearance = null;
int ap = ta.getResourceId(R.styleable.RangeBar_textAppearance, -1);
if (ap != -1) {
    appearance = context.getTheme().obtainStyledAttributes(ap, TextAppearanceConsts.styleable_TextAppearance);
    int n = appearance.getIndexCount();
    for (int i = 0; i < n; i++) {
        int attr = appearance.getIndex(i);

        if (attr == TextAppearanceConsts.styleable_TextAppearance_textColor){
            mTextColor = appearance.getColorStateList(attr);
        } else if (attr == TextAppearanceConsts.styleable_TextAppearance_textSize){
            mTextSize = appearance.getDimensionPixelSize(attr, mTextSize);
        } else if (attr == TextAppearanceConsts.styleable_TextAppearance_typeface){
            mTypefaceIndex = appearance.getInt(attr, -1);
        } else if (attr == TextAppearanceConsts.styleable_TextAppearance_fontFamily){
            mFontFamily = appearance.getString(attr);
        } else if (attr == TextAppearanceConsts.styleable_TextAppearance_textStyle){
            mFontStyleIndex = appearance.getInt(attr, -1);
        } else {
            ....
        }
    }
    appearance.recycle();
}

R.styleable.RangeBar_textAppearance 是我的属性,但您可以通过以下方式访问Android属性:

final static String ANDROID_NS = "http://schemas.android.com/apk/res/android";
final int textAppearanceResId = attrs.getAttributeResourceValue(ANDROID_NS, "textAppearance", 0);
....
int ap = ta.getResourceId(textAppearanceResId, -1);

我知道这种方法是某种黑客行为,但不知道其他任何更好的方法:(