对于偏好设置,我好像刚开始学安卓的时候有些印象,但是确实没怎么使用过,原因就是这个偏好设置虽然方便,但是只能实现一些简单的界面,一般的设置界面我都是使用自定义的界面来实现
先看一下效果图吧
来点说明
一、元素
说明
CheckBoxPreference:CheckBox选择项,对应的值的ture或flase
EditTextPreference:输入编辑框,值为String类型,会弹出对话框供输入。
ListPreference: 列表选择,弹出对话框供选择。
Preference:只进行文本显示,需要与其他进行组合使用。
PreferenceCategory:用于分组。
PreferenceScreen:PreferenceActivity的根元素
RingtonePreference:系统玲声选择。
二、常见属性
title:显示的标题
key:唯一标识(至少在同一程序中是唯一),SharedPreferences也将通过此Key值进行数据保存,也可以通过key值获取保存的信息
summary:副标题、说明(小字体显示)
defaultValue:默认值(当然,此处只能是true或false了)
android:summaryOn:属性开启的时候的说明
android:summaryOff:属性关闭时候的说明
dialogTitle:弹出对话框的标题
entries:列表中显示的值。为一个数组,通读通过资源文件进行设置。
entryValues:列表中实际保存的值,也entries对应。为一个数组,通读通过资源文件进行设置。
代码
在xml下新建prefs.xml
<?xml version="1.0" encoding="utf-8"?>
<!--为 Preference指定android:key属性是一个很好的习惯,通过该属性可以检索Preference 对象 -->
<PreferenceScreen
xmlns:android="http://schemas.android.com/apk/res/android"
android:key="pref_first_preferencescreen_key"
android:title="Preferences">
<PreferenceCategory
android:title="User"><!--使用PreferenceCategory可以为 Preference 分组,并指定分组名 -->
<EditTextPreference
android:key="pref_username"
android:summary="Username:"
android:title="Username"/><!--选择用户名,需要使用EditTextPreference控件。这里指定了summary属性的默认值,当用户指定用户名后,该默认值会被替换 -->
</PreferenceCategory>
<PreferenceCategory
android:title="Application">
<Preference
android:key="pref_rate"
android:summary="Rate the app in the store!"
android:title="Rate the app"/>
<Preference
android:key="pref_share"
android:summary="Share the app with your friends"
android:title="Share it"/>
<!-- 可以创建自定义 Preference继承已有的控件-->
<boerpower.com.android50hacks.preference.EmailDialog
android:dialogIcon="@mipmap/ic_launcher"
android:dialogTitle="Send Feedback"
android:dialogMessage="Do you want to send an email with feedback?"
android:key="pref_sendemail_key"
android:negativeButtonText="Cancel"
android:positiveButtonText="OK"
android:summary="Send your feedback by e-mail"
android:title="Send Feedback"/>
<boerpower.com.android50hacks.preference.AboutDialog
android:dialogIcon="@mipmap/ic_launcher"
android:dialogTitle="About"
android:key="pref_about_key"
android:negativeButtonText="@null"
android:title="About"/>
</PreferenceCategory>
</PreferenceScreen>
再建两个工具类,作为演示用
AboutDialog.java
public class AboutDialog extends DialogPreference {
private Context mContext;
private String mVersionNumber;
public AboutDialog(Context context) {
this(context, null);
}
public AboutDialog(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
public AboutDialog(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
mContext = context;
}
@Override
protected View onCreateDialogView() {
LinearLayout layout = new LinearLayout(mContext);
layout.setOrientation(LinearLayout.VERTICAL);
TextView splashText = new TextView(mContext);
String fmt = "Version %s<br />"
+ "<a href=\"http://manning.com/sessa\">MoreInfo</a>";
try {
String pkg = mContext.getPackageName();
mVersionNumber = mContext.getPackageManager().getPackageInfo(pkg,
0).versionName;
} catch (NameNotFoundException e) {
e.printStackTrace();
}
if (mVersionNumber != null) {
String aboutMsg = String.format(fmt, mVersionNumber);
splashText.setText(Html.fromHtml(aboutMsg));
splashText.setMovementMethod(LinkMovementMethod.getInstance());
}
layout.addView(splashText);
return layout;
}
}
EmailDialog.java
//自定义类需要继承自某个已有的 Preference 控件。在本例中,我们继承自 DialogPreference
public class EmailDialog extends DialogPreference {
Context mContext;
public EmailDialog(Context context) {
this(context, null);
}
public EmailDialog(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
public EmailDialog(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
mContext = context;
}
//重写 onClick() 方法。如果用户点击 OK 按钮,我们使用辅助类发送 启 动 email 的Intent
@Override
public void onClick(DialogInterface dialog, int which) {
super.onClick(dialog, which);
if (DialogInterface.BUTTON_POSITIVE == which) {
LaunchEmailUtil.launchEmailToIntent(mContext);
}
}
}
主界面类
public class Hack04Activity extends PreferenceActivity implements
SharedPreferences.OnSharedPreferenceChangeListener {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//这里并不调用 setContentView()方法,而是调用 addPreferencesFromResource()方法,传入该方法的参数是之前创建的 XML文件
addPreferencesFromResource(R.xml.prefs);
Preference sharePref = findPreference("pref_share");
Intent shareIntent = new Intent();
shareIntent.setAction(Intent.ACTION_SEND);
shareIntent.setType("text/plain");
shareIntent.putExtra(Intent.EXTRA_SUBJECT, "Check this app!");
shareIntent.putExtra(Intent.EXTRA_TEXT,
"Check this awesome app at: ...");
sharePref.setIntent(shareIntent);
//在 onCreate() 方法中,可以获取Preference,并为其设置Intent,ratePref使用Intent.ACTION_VIEW
Preference ratePref = findPreference("pref_rate");
Uri uri = Uri.parse("market://details?id=" + getPackageName());
Intent goToMarket = new Intent(Intent.ACTION_VIEW, uri);
ratePref.setIntent(goToMarket);
updateUserText();
}
@Override
protected void onResume() {
super.onResume();
//注册Preference变化通知监听器
getPreferenceScreen().getSharedPreferences()
.registerOnSharedPreferenceChangeListener(this);
}
@Override
protected void onPause() {
super.onPause();
//注销 Preference 变化通知监听器
getPreferenceScreen().getSharedPreferences()
.unregisterOnSharedPreferenceChangeListener(this);
}
@Override
public void onSharedPreferenceChanged(
SharedPreferences sharedPreferences, String key) {
//当用户名Preference改变时,需要更新该 Preference的 summary
if (key.equals("pref_username")) {
updateUserText();
}
}
private void updateUserText() {
//要更新summary,需要获取该Preference,然后调用 EditTextPreference的getText()方法
EditTextPreference pref;
pref = (EditTextPreference) findPreference("pref_username");
String user = pref.getText();
if (user == null) {
user = "?";
}
pref.setSummary(String.format("Username: %s", user));
}
}
尽管 Android 提供了很多设置控件供开发者使用,但是很多时候,还是需要开发者自己定制界面