I want to set the icon in ListPreference
items in android.
What to write in ListPreference
or where to write to set the list items icon?
When you need multiple uses of a list preference with texts/icons, then you can use this solution.
This version is heavily based on the nice version of LucaZanini. I made some minor changes to the version so it is only dependant on the own preference attributes. In this way you can use them multiple times. Please refer to his tutorial.
@Luca - thank you very much!
The minor changes are only:
IconPickerPreference:
// @Based on the nice version of LucaZanini. Thank you!
public class IconPickerPreference extends ListPreference {
private int currentIndex = 0;
private class CustomListPreferenceAdapter extends ArrayAdapter<IconItem> {
private Context context;
private List<IconItem> icons;
private int resource;
public CustomListPreferenceAdapter(Context context, int resource, List<IconItem> objects) {
super(context, resource, objects);
this.context = context;
this.resource = resource;
this.icons = objects;
}
@Override
public View getView(final int position, View convertView, ViewGroup parent) {
ViewHolder holder;
if (convertView == null) {
LayoutInflater inflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
convertView = inflater.inflate(resource, parent, false);
holder = new ViewHolder();
holder.iconName = (TextView) convertView.findViewById(R.id.iconName);
holder.iconImage = (ImageView) convertView.findViewById(R.id.iconImage);
holder.radioButton = (RadioButton) convertView.findViewById(R.id.iconRadio);
convertView.setTag(holder);
} else {
holder = (ViewHolder) convertView.getTag();
}
holder.iconName.setText(icons.get(position).name);
int identifier = context.getResources().getIdentifier( icons.get(position).file, "drawable", context.getPackageName());
holder.iconImage.setImageResource(identifier);
holder.radioButton.setChecked(icons.get(position).isChecked);
convertView.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
ViewHolder holder = (ViewHolder) v.getTag();
for (int i = 0; i < icons.size(); i++) {
if (i == position) {
icons.get(i).isChecked = true;
} else {
icons.get(i).isChecked = false;
}
}
getDialog().dismiss();
}
});
return convertView;
}
}
private class IconItem {
private String file;
private boolean isChecked;
private String name;
public IconItem(CharSequence name, CharSequence file, boolean isChecked) {
this(name.toString(), file.toString(), isChecked);
}
public IconItem(String name, String file, boolean isChecked) {
this.name = name;
this.file = file;
this.isChecked = isChecked;
}
}
private class ViewHolder {
protected ImageView iconImage;
protected TextView iconName;
protected RadioButton radioButton;
}
private Context context;
private ImageView icon;
private CharSequence[] iconFile;
private CharSequence[] iconName;
private List<IconItem> icons;
private SharedPreferences preferences;
private Resources resources;
private String selectedIconFile, defaultIconFile;
private TextView summary;
public IconPickerPreference(Context context, AttributeSet attrs) {
super(context, attrs);
this.context = context;
resources = context.getResources();
preferences = PreferenceManager.getDefaultSharedPreferences(context);
TypedArray a = context.getTheme().obtainStyledAttributes( attrs, R.styleable.attrs_icon, 0, 0);
try {
defaultIconFile = a.getString(R.styleable.attrs_icon_iconFile);
} finally {
a.recycle();
}
}
@Override
protected void onBindView(View view) {
super.onBindView(view);
CharSequence[] entries = getEntries();
CharSequence[] values = getEntryValues();
selectedIconFile = values[ currentIndex].toString();
icon = (ImageView) view.findViewById(R.id.iconSelected);
updateIcon();
summary = (TextView) view.findViewById( R.id.preference_summary);
summary.setText( entries[ currentIndex]);
}
@Override
protected void onDialogClosed(boolean positiveResult) {
super.onDialogClosed(positiveResult);
if (icons != null) {
for (int i = 0; i < iconName.length; i++) {
IconItem item = icons.get(i);
if (item.isChecked) {
persistString( "" + i);
currentIndex = i;
selectedIconFile = item.file;
updateIcon();
summary.setText(item.name);
break;
}
}
}
}
@Override
protected void onSetInitialValue(boolean restorePersistedValue, Object defaultValue) {
String number = "0";
if (restorePersistedValue) {
// Restore existing state
number = this.getPersistedString( "0");
} else {
persistString( number);
}
try {
currentIndex = Integer.parseInt(number);
} catch( Exception e) {
; // skip any error, it will be corrected to 0
}
}
@Override
protected void onPrepareDialogBuilder(Builder builder) {
builder.setNegativeButton("Cancel", null);
builder.setPositiveButton(null, null);
iconName = getEntries();
iconFile = getEntryValues();
if (iconName == null || iconFile == null || iconName.length != iconFile.length) {
throw new IllegalStateException(
"IconPickerPreference requires an entries array and an entryValues array which are both the same length");
}
icons = new ArrayList<IconItem>();
for (int i = 0; i < iconName.length; i++) {
IconItem item = new IconItem(iconName[i], iconFile[i], ( i == currentIndex));
icons.add(item);
}
CustomListPreferenceAdapter customListPreferenceAdapter = new CustomListPreferenceAdapter(
context, R.layout.preference_list_icon_picker, icons);
builder.setAdapter(customListPreferenceAdapter, null);
}
private void updateIcon() {
int identifier = resources.getIdentifier( selectedIconFile, "drawable", context.getPackageName());
icon.setImageResource(identifier);
icon.setTag(selectedIconFile);
}
}
You need to use a custom layout for your ListPreference
.
eg:
<android.preference.ListPreference
android:layout="@layout/your_custom_layout"
....
/>
And add what you want to your custom layout.
eg:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:minHeight="?android:attr/listPreferredItemHeight"
android:gravity="center_vertical"
android:paddingRight="?android:attr/scrollbarSize">
<RelativeLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="1"
android:layout_margin="@dimen/preferences_layout_margin">
<ImageView android:id="@+id/yourIconId"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerVertical="true" /> <!-- here i've added an ImageView for icon -->
<TextView android:id="@android:id/title"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:singleLine="true"
android:textAppearance="?android:attr/textAppearanceMedium"
android:ellipsize="marquee"
android:fadingEdge="horizontal"
android:layout_toRightOf="@+id/iconImageView"
android:layout_marginLeft="@dimen/preferences_icon_margin" />
<TextView android:id="@android:id/summary"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_below="@android:id/title"
android:layout_alignLeft="@android:id/title"
android:textAppearance="?android:attr/textAppearanceSmall"
android:maxLines="2" />
</RelativeLayout>
<!-- Preference should place its actual preference widget here. -->
<LinearLayout android:id="@android:id/widget_frame"
android:layout_width="wrap_content"
android:layout_height="fill_parent"
android:gravity="center_vertical"
android:orientation="vertical" />
</LinearLayout>