androidlistviewitemcheckedtextview

android.content.res.Resources$NotFoundException when programmatically setting android.R.attr.listChoiceIndicatorMultiple


I'm trying to programmatically set the "android:checkMark" attribute on CheckedTextView items I have in a ListView. When running my application I get the following exception:

android.content.res.Resources$NotFoundException: Resource ID #0x101021a

The resource with ID #0x101021a corresponds to android.R.attr.listChoiceIndicatorMultiple, which is exactly the value I am passing to my CheckedTextView:

mCheckedTextView.setCheckMarkDrawable(android.R.attr.listChoiceIndicatorMultiple)

Isn't this the way to do it from Java? I tried (and succeeded) to trigger the desired behaviour from XML layout:

<CheckedTextView
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:checkMark="?android:attr/listChoiceIndicatorMultiple"
    android:id="@android:id/text1" />

The thing is that I don't know at compile time if it should be

android:checkMark="?android:attr/listChoiceIndicatorMultiple"

or

android:checkMark="?android:attr/listChoiceIndicatorSingle"

Hence, I need to set these values at runtime.


Solution

  • I would guess that programmatically setting an attribute reference rather than a Drawable reference is the problem.

    In this case, android.R.attr.listChoiceIndicatorMultiple corresponds to android.R.drawable.btn_check, so you could try setting that instead.


    Or, if you can obtain the attributes, you could call getDrawable() on the TypedArray to dynamically fetch the Drawable value.

    Edit:
    Since the value of listChoiceIndicatorMultiple depends on the current theme, you need to ask the current theme to resolve the reference:

    int[] attrs = { android.R.attr.listChoiceIndicatorMultiple };
    TypedArray ta = getContext().getTheme().obtainStyledAttributes(attrs);
    Drawable indicator = ta.getDrawable(0);
    view.setCheckMarkDrawable(indicator);
    ta.recycle();
    

    Be sure to cache the drawables, rather than performing this manoeuvre for every item in your ListView.

    That's just a very basic example, but it works with the default theme. I'm not exactly sure what needs to be done to resolve attrs fully if you have a custom theme.