android 如何在 ListPreference 的项目中设置图标
How to set icon in ListPreference's item in android
我想在 android 的 ListPreference
项中设置图标。
在ListPreference
中写什么或在哪里写来设置列表项图标?
您需要为 ListPreference
使用 自定义 布局。
例如:
<android.preference.ListPreference
android:layout="@layout/your_custom_layout"
....
/>
并将您想要的内容添加到您的自定义布局。
例如:
<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>
当您需要多次使用带有 texts/icons 的列表首选项时,您可以使用此解决方案。
此版本主要基于 nice version of LucaZanini。我对版本做了一些小改动,所以它只依赖于自己的偏好属性。这样您就可以多次使用它们。请参考他的教程。
@Luca - 非常感谢!
细微的变化只有:
- IconPickerPreference.java,见下文。
- 您不需要对 strings.xml 文件的引用。开始时设置的默认值仅为“0”。
- 您可以通过为 currentIndex 使用整数而不是字符串来改进此版本。
图标选择器首选项:
// @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);
}
}
我想在 android 的 ListPreference
项中设置图标。
在ListPreference
中写什么或在哪里写来设置列表项图标?
您需要为 ListPreference
使用 自定义 布局。
例如:
<android.preference.ListPreference
android:layout="@layout/your_custom_layout"
....
/>
并将您想要的内容添加到您的自定义布局。
例如:
<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>
当您需要多次使用带有 texts/icons 的列表首选项时,您可以使用此解决方案。
此版本主要基于 nice version of LucaZanini。我对版本做了一些小改动,所以它只依赖于自己的偏好属性。这样您就可以多次使用它们。请参考他的教程。
@Luca - 非常感谢!
细微的变化只有:
- IconPickerPreference.java,见下文。
- 您不需要对 strings.xml 文件的引用。开始时设置的默认值仅为“0”。
- 您可以通过为 currentIndex 使用整数而不是字符串来改进此版本。
图标选择器首选项:
// @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);
}
}