详解Android首选项框架ListPreference

探索首选项框架

在 深入探讨Android的首选项框架之前,首先构想一个需要使用首选项的场景,然后分析如何实现这一场景。假设你正在编写一个应用程序,它提供了一个搜索 飞机航班的工具。而且,假设该应用程序的默认设置是根据机票价格由低到高的顺序显示航班,但用户可以将首选项设置为始终根据最少停站数或特定航线来航班。 如何实现这一场景?

ListPreference

显 然,必须为用户提供UI 来查看排序选项列表。该列表将包含每个选项的单选按钮,而且默认(或当前)选项应该被预先选中。要使用Android首选项框架解决此问题,所做的工作非 常之少。首先,创建首选项XML文件来描述首选项,然后使用预先构建的活动类,该类知道如何显示和持久化首选项,下面是我们的首选项XML文件 flightoptions.xml 。

Xml代码

  1. <?xml version="1.0" encoding="utf-8"?>
  2. <PreferenceScreen
  3. xmlns:android="http://schemas.android.com/apk/res/android"
  4. android:key="flight_option_preference"
  5. android:title="@string/prefTitle"
  6. android:summary="@string/prefSummary">
  7. <ListPreference
  8. android:key="@string/selected_flight_sort_option"
  9. android:title="@string/listTitle"
  10. android:summary="@string/listSummary"
  11. android:entries="@array/flight_sort_options"
  12. android:entryValues="@array/flight_sort_options_values"
  13. android:dialogTitle="@string/dialogTitle"
  14. android:defaultValue="@string/flight_sort_option_default_value"/>
  15. </PreferenceScreen>

上边说了我们还需要一个Activity类FlightPreferenceActivity,下面使我们的Activity类。这个Activity类继承了PreferenceActivity 代码如下:

Java代码

  1. package xiaohang.zhimeng;
  2. import android.os.Bundle;
  3. import android.preference.PreferenceActivity;
  4. public class FlightPreferenceActivity extends PreferenceActivity {
  5. @Override
  6. protected void onCreate(Bundle savedInstanceState) {
  7. super.onCreate(savedInstanceState);
  8. addPreferencesFromResource(R.xml.flightoptions);
  9. }
  10. }

上 面的代码清单,包含了一个表示航班选项示例的首选项设置的XML片段。该包含了一个活动类,也就是我们的 FlightPreferenceActivity 这个类主要用于加载我们的XML 文件。首先看一下XML。Android提供了一种端到端得首选项框架。这意味着,该框架支持定义首选项,想用户显示设置,以及将用户选择持久化到数据库 存储中。 在/res/xml/目录下的XML文件中定义首选项。要向用户显示首选项,编写一个活动类来扩展预定义的 Android类 android.preference.PreferenceActivity,然后使用 addPreferencesFromResource()方法将资源添加到活动的资源集合中。该框架会负责剩余操作(现实和持久化)。

在 本航班场景中,在/res/xml/目录下创建文件 flightoptions.xml。然后创建活动类FlightPreferenceActivity, 它扩展了 android.preference.PreferenceActivity类。接下来调用addPreferencesFromResource() 传入R.xml.flightoptions。请注意,首选项资源XML指向多个字符串资源。为了确保正确编译,需要向项目中添加多个字符串资源 (我们稍后介绍)。现在先看一下 上面得代码清单会生成什么样子的UI.

上 边有两个视图。左边的视图称为首选项屏幕,右边的UI是一个列表首选项。当用户选择 Flight Options时, Choose Flight Options视图将以模态对话框的形式出现,其中包含每个选项的单选按钮。用户选择一个选项之后,将立即该选项并关闭视图。当用户返回选项屏幕时,视图 将反映前面保存的选择。

前 面已提到,首选项XML 文件和相关的活动类,从上边我们可以看到 我们在XML文件中定义了一个PreferenceScreen ,然后创建ListPreference作为子屏幕。对于 PreferenceScreen,设置了3个属性: key、title和 summary。 key 是一个字符串,可用于以编程的方式表示项 (类似于使用 android:id的方式);title 是屏幕的标题 (My Preferences) ; summary是对屏幕用途的描述。对于列表首选项,设置 key、title和 summary,以及 entries、entryValues、dialogTitle和defaultValue特性。下表总结了这些特性。

特性 说明
android:key 选项的名称或键(比如selected_flight_sort_option)
android:title 选项的标题
android:summary 选项的简短摘要
android:entries 可将选项设置成列表项的文本
android:entryValues 定义每个列表项的值。注意:每个列表项有一些文本和 一 个 值。 文本由entries定义,值由entryValues定义。
android:dialogTitle

对话框的标题,在视图显示为模态对话框时使用

android:defaultValue 项列表中选项的默认值

为了使我们的例子能够正常运行,我们还需要添加如下文件。

Xml代码

  1. <?xml version="1.0" encoding="utf-8"?>
  2. <resources>
  3. <string-array name="flight_sort_options">
  4. <item>Total Cost</item>
  5. <item># of Stops</item>
  6. <item>Airline</item>
  7. </string-array>
  8. <string-array name="flight_sort_options_values">
  9. <item>0</item>
  10. <item>1</item>
  11. <item>2</item>
  12. </string-array>
  13. </resources>

此文件大家一看就知道是 定义我们选项的显示的文本,和对应的值。这个XML 文件的名字是 arrays.xml 此文件应该放在 /res/values/arrays.xml

当然不能少了我们的strings.xml

Xml代码

  1. <?xml version="1.0" encoding="utf-8"?>
  2. <resources>
  3. <string name="hello">Hello World, FlightPreferenceActivity!</string>
  4. <string name="app_name">Preference_Demo</string>
  5. <string name="prefTitle">My Preferences</string>
  6. <string name="prefSummary">Set Flight Option Preferences</string>
  7. <string name="flight_sort_option_default_value">1</string>
  8. <string name="dialogTitle">Choose Flight Options</string>
  9. <string name="listSummary">Set Search Options</string>
  10. <string name="listTitle">Flight Options</string>
  11. <string name="selected_flight_sort_option">selected_flight_sort_option</string>
  12. <string name="menu_prefs_title">Settings</string>
  13. <string name="menu_quit_title">Quit</string>
  14. </resources>

刚才上边说到我们有一个首选项视图,就是那个FlightPreferenceActivity ,在这

这 个例子中我们是通过一个菜单跳转到我们的首选项视图的。就是我们有一个MainActivity 这个MainActivity有一个菜单叫Settings当我们点击这个菜单的时候就会跳转到我们的首选项视图了,然后我们修改首选项的内容 当我们再一次回到 MainActivity 的时候就会看到我们修改后的 文本和值,我们通过一个TextView来显示

我们还是来看一下效果吧。

下面这个XML文件就是用来定义我们 这个菜单的,此文件的目录在 /res/menu/mainmenu.xml

Xml代码

  1. <?xml version="1.0" encoding="utf-8"?>
  2. <menu xmlns:android="http://schemas.android.com/apk/res/android">
  3. <item android:id="@+id/menu_prefs" android:title="@string/menu_prefs_title" />
  4. <item android:id="@+id/menu_quit" android:title="@string/menu_quit_title" />
  5. </menu>

也比较简单了。

在接下来就是我们的布局文件main.xml了

Xml代码

  1. <?xml version="1.0" encoding="utf-8"?>
  2. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
  3. android:orientation="vertical" android:layout_width="fill_parent"
  4. android:layout_height="fill_parent">
  5. <TextView android:id="@+id/text1" android:layout_width="fill_parent"
  6. android:layout_height="wrap_content" />
  7. </LinearLayout>

只有一个TextView 主要用来显示我们修改首选项之后的文本和值。

有了main.xml自然少不了MainActivity了,下面使我们的MainActivity类

Java代码

  1. package xiaohang.zhimeng;
  2. import android.app.Activity;
  3. import android.content.Intent;
  4. import android.content.SharedPreferences;
  5. import android.os.Bundle;
  6. import android.view.Menu;
  7. import android.view.MenuInflater;
  8. import android.view.MenuItem;
  9. import android.widget.TextView;
  10. public class MainActivity extends Activity{
  11. private TextView tv = null;
  12. @Override
  13. protected void onCreate(Bundle savedInstanceState) {
  14. super.onCreate(savedInstanceState);
  15. setContentView(R.layout.main);
  16. tv = (TextView)findViewById(R.id.text1);
  17. setOptionText();
  18. }
  19. //创建菜单,这个菜单我们在XML文件中定义 这里加载进来就OK
  20. @Override
  21. public boolean onCreateOptionsMenu(Menu menu) {
  22. MenuInflater inflater = getMenuInflater();
  23. //加载我们的菜单文件
  24. inflater.inflate(R.menu.mainmenu, menu);
  25. return true;
  26. }
  27. //菜单选项事件
  28. @Override
  29. public boolean onOptionsItemSelected(MenuItem item) {
  30. if (item.getItemId() == R.id.menu_prefs) {
  31. //当我们点击 Settings 菜单的时候就会跳转到我们的  首选项视图,也就是我们的 FlightPreferenceActivity
  32. Intent intent = new Intent().setClass(this, xiaohang.zhimeng.FlightPreferenceActivity.class);
  33. //因为我们要接收上一个Activity 就是我们的首选项视图 返回的数据,所以这里用 startActivityForResult()方法启动我们的首选项视图
  34. //参数一:我们要跳转到哪里
  35. //参数二:回传码
  36. this.startActivityForResult(intent, 0);
  37. }else if (item.getItemId() == R.id.menu_quit) {
  38. //当我们点击Quit菜单退出应用程序
  39. finish();
  40. }
  41. return true;
  42. }
  43. //此方法用来 接收我们上一个Activity 也就是我们的首选项视图 返回的数据,因为我们可能会修改数据
  44. @Override
  45. protected void onActivityResult(int requestCode, int resultCode, Intent data) {
  46. super.onActivityResult(requestCode, resultCode, data);
  47. setOptionText();
  48. }
  49. //这个方法就是用来设置我们 MainActivity 上的TextView的值(就是我们首选项的值)
  50. private void setOptionText(){
  51. /*这个方法比较有意思了
  52. * 第一个参数:用来指定我们存储我们首选项值的文件的名称
  53. * 格式就是 包名_preferences,大家可以看到我的包名就是xiaohang.zhimeng
  54. * 这里如果你不按照这个格式写 比如你不写你当前包名  写成别的,也会生成 当前包名_preferences 这个文件  写或不写它就在那里
  55. * 第二个参数:打开模式
  56. * */
  57. SharedPreferences prefs = getSharedPreferences("xiaohang.zhimeng_preferences", 0);
  58. //这个方法大家去看文档,否则我会越写越乱
  59. String option = prefs.getString(this.getResources().getString(R.string.selected_flight_sort_option), this.getResources().getString(R.string.flight_sort_option_default_value));
  60. //得到我们首选项 所有选项的文本
  61. String[] optionText = this.getResources().getStringArray(R.array.flight_sort_options);
  62. //设置我们 TextView要显示的值
  63. tv.setText("option value is " + option + "(" + optionText[Integer.parseInt(option)] + ")");
  64. }
  65. }

如果大家对这里比较陌生,比如 SharedPreferences 是什么东西,可以参考这两篇文章。

http://byandby.iteye.com/blog/837601

http://byandby.iteye.com/blog/833292

在下边就是我们的AndroidManifest.xml文件了,倒也没啥特别的。

Xml代码

  1. <?xml version="1.0" encoding="utf-8"?>
  2. <manifest xmlns:android="http://schemas.android.com/apk/res/android"
  3. package="xiaohang.zhimeng" android:versionCode="1" android:versionName="1.0">
  4. <uses-sdk android:minSdkVersion="10" />
  5. <application android:icon="@drawable/icon" android:label="@string/app_name">
  6. <activity android:name=".MainActivity" android:label="@string/app_name">
  7. <intent-filter>
  8. <action android:name="android.intent.action.MAIN" />
  9. <category android:name="android.intent.category.LAUNCHER" />
  10. </intent-filter>
  11. </activity>
  12. <activity android:name=".FlightPreferenceActivity"
  13. android:label="@string/prefTitle">
  14. <intent-filter>
  15. <action android:name="xiaohang.zhimeng.intent.action.FlightPreferences" />
  16. <category android:name="android.intent.category.PREFERENCE" />
  17. </intent-filter>
  18. </activity>
  19. </application>
  20. </manifest>

OK, 当我们完成了上边的所有运行应用程序,首先会看到一个简单的文本消息,显示“option value is 1(# of Stops)”。单击Menu按钮,然后在点击Settings,就会打开我们的首选项视图FlightPreferenceActivity,然后我们 更改首选项的值,然后再点击back按钮就会看到我们修改后的值了。

大家可能会问,那Android把我们修改后的数据存储在哪里了呢?前面已经提到Android framework还会负责持久化首选项。例如,当用户选择一个排序选项时,Android会选择存储在应用程序 /data 目录下的一个XML 文件中,见下图。

实 际的文件路径为 /data/data/[PACKAGE_NAME]/shared_prefs/[PACKAGE_NAME]_preferences.xml。我们 需要 看看这个文件里边到底存了些什么? 导出这个文件就可以看到了。哦 不对,不用这样 太麻烦了, 我们 去 shell 里边 用 cat 读一下就行了,见下图。

一看便知,是以键值对的方式存取。

转:Android preference首选项框架的更多相关文章

  1. 详解Android首选项框架ListPreference

    详解Android首选项框架ListPreference 原文地址 探索首选项框架 在深入探讨Android的首选项框架之前,首先构想一个需要使用首选项的场景,然后分析如何实现这一场景.假设你正在编写 ...

  2. 详解Android首选项框架的使用

    首选项这个名词对于熟悉Android的朋友们一定不会感到陌生,它经常用来设置软件的运行参数. Android提供了一种健壮并且灵活的框架来处理首选项.它提供了简单的API来隐藏首选项的读取和持久化,并 ...

  3. 首选项框架PreferenceFragment部分源代码分析

    由于要改一些settings里面的bug以及之前在里面有做过勿扰模式,准备对勿扰模式做一个总结,那先分析一下settings的源代码,里面的核心应该就是android3.0 上面的首选项框架Prefe ...

  4. Eclipse 中的 parameter参数,property属性,preference首选项 区别

    parameter参数 1.配置框架 web.xml <init-param> <param-name>contextConfigLocation</param-name ...

  5. Android - Shared Preference (分享首选项) 具体解释

    Shared Preference (分享首选项) 具体解释 本文地址: http://blog.csdn.net/caroline_wendy/article/details/24454963 Sh ...

  6. Android学习笔记(十四)方便实用的首选项-PreferenceActivity

    突然发现已经好多天没更新博客了,最近公司项目正在进行一个大跨度的重构,又碰上有新需求,一连好多天都是很晚才到家.其实这篇博文在草稿箱里面也存了很久了,本来想着不发了,不过感觉PreferenceAct ...

  7. 我的Android 4 学习系列之文件、保存状态和首选项

    目录 使用Shared Preference 保留简单的应用程序数据 保存回话间的Activity实例数据 管理应用程序首选项和创建Preference Screen 保存并加载文件以及管理本地文件系 ...

  8. MTK Android 设置-选择日期格式 [管理和组织首选项,ListPreference,CheckBoxPreference,EditTextPreference,RingtonePreference]

    ###android.preference.ListPreference的一些特性 android:key  选项的名称或键 android:title  选项的标题 android:summary  ...

  9. Xamarin android PreferenceActivity 实现应用程序首选项设置(一)

    应用程序首选项屏幕 类似系统设置界面. PreferenceActivity 是另一种类型的Activity,通过PreferenceActivity 可以以最少量的工作显示某些Preference列 ...

随机推荐

  1. GO的安装以及GoLand破解

    GO的安装以及GoLand破解 GO的安装 GO语言中文网:GO语言中文网 go,GoLand,破解文件:JetBrains GoLand 2019.2.3 x64 提取码:ABCD(汉化文件也在其中 ...

  2. CTF入门学习3->Web通信基础

    Web安全基础 01 Web通信 这个部分重点介绍浏览器与Web服务器的详细通信过程. 01-00 URL协议 只要上网访问服务器,就离不开URL. URL是什么? URL就是我们在浏览器里输入的站点 ...

  3. OpenCV常用操作函数大全

    https://blog.csdn.net/Vici__/article/details/100714822 目录 cv2常用类: 1.图片加载.显示和保存 2.图像显示窗口创建与销毁 3.图片的常用 ...

  4. PAT A1020——已知后序中序遍历求层序遍历

    1020 Tree Traversals Suppose that all the keys in a binary tree are distinct positive integers. Give ...

  5. 洛谷 P5071 - [Ynoi2015] 此时此刻的光辉(莫队)

    洛谷题面传送门 一道其实算得上常规的题,写这篇题解是为了总结一些数论中轻微(?)优化复杂度的技巧. 首先感性理解可以发现该问题强于区间数颜色问题,无法用常用的 log 数据结构维护,因此考虑分块/莫队 ...

  6. 洛谷 P3714 - [BJOI2017]树的难题(点分治)

    洛谷题面传送门 咦?鸽子 tzc 竟然来补题解了?incredible( 首先看到这样类似于路径统计的问题我们可以非常自然地想到点分治.每次我们找出每个连通块的重心 \(x\) 然后以 \(x\) 为 ...

  7. 洛谷 P5502 - [JSOI2015]最大公约数(区间 gcd 的性质+分治)

    洛谷题面传送门 学校模拟赛的某道题让我联想到了这道题-- 先讲一下我的野鸡做法. 首先考虑分治,对于左右端点都在 \([L,R]\) 中的区间我们将其分成三类:完全包含于 \([L,mid]\) 的区 ...

  8. BZOJ 3926 诸神眷顾的幻想乡

    BZOJ 3926 诸神眷顾的幻想乡 开始看错题看成了每个点度数不超过20 后来翻了翻题解原来看错题的不止我一个 既然叶子数量不超过20,考虑树上的任何一条路径,以任何点为根时,如果它不是一条从上到下 ...

  9. R语言与医学统计图形【3】条形图、误差图

    R语言基础绘图系统 基础图形--条形图.误差图 3.条形图 barplot接收的数据是矩阵而非数据框. data <- sample(c(50:80),5) barplot(data,col=h ...

  10. 监督学习&非监督学习

    监督学习 1 - 3 - Supervised Learning  在监督学习中,数据集中的每个例子,算法将预测得到例子的""正确答案"",像房子的价格,或者溜 ...