Setting Preference Summary
https://developer.android.com/guide/topics/ui/settings
1) Build a simple settings screen using the AndroidX Preference Library
2) A settings screen contains a Preference hierarchy. You can define this hierarchy as an XML resource, or you can build a hierarchy in code.
3) The root tag must be a <PreferenceScreen>, and the XML resource must be placed in the res/xml/ directory.
4) Create a hierarchy as an XML
<PreferenceScreen xmlns:app="http://schemas.android.com/apk/res-auto">
<PreferenceCategory app:title="@string/messages_header">
<EditTextPreference
app:key="signature"
app:title="@string/signature_title"
app:useSimpleSummaryProvider="true" />
<ListPreference
app:defaultValue="reply"
app:entries="@array/reply_entries"
app:entryValues="@array/reply_values"
app:key="reply"
app:title="@string/reply_title"
app:useSimpleSummaryProvider="true" />
</PreferenceCategory>
<PreferenceCategory app:title="@string/sync_header">
<SwitchPreferenceCompat
app:key="sync"
app:title="@string/sync_title" />
<SwitchPreferenceCompat
app:dependency="sync"
app:key="attachment"
app:summaryOff="@string/attachment_summary_off"
app:summaryOn="@string/attachment_summary_on"
app:title="@string/attachment_title" />
</PreferenceCategory>
</PreferenceScreen>
To discover more components
https://developer.android.com/guide/topics/ui/settings/components-and-attributes
5) Inflate the hierarchy
class MySettingsFragment : PreferenceFragmentCompat() {
override fun onCreatePreferences(savedInstanceState: Bundle?, rootKey: String?) {
setPreferencesFromResource(R.xml.preferences, rootKey)
}
}
6) Split your hierarchy into multiple screens
<PreferenceScreen
xmlns:app="http://schemas.android.com/apk/res-auto"><Preference
app:title="@string/basic_preferences"
app:summary="Sample preferences using basic attributes"
app:fragment="com.example.SyncFragment"/>
//---
Activity
class MyActivity : AppCompatActivity(),
PreferenceFragmentCompat.OnPreferenceStartFragmentCallback {
...
override fun onPreferenceStartFragment(caller: PreferenceFragmentCompat, pref: Preference): Boolean {
// Instantiate the new Fragment
val args = pref.extras
val fragment = supportFragmentManager.fragmentFactory.instantiate(
classLoader,
pref.fragment)
fragment.arguments = args
fragment.setTargetFragment(caller, 0)
// Replace the existing Fragment with the new Fragment
supportFragmentManager.beginTransaction()
.replace(R.id.settings_container, fragment)
.addToBackStack(null)
.commit()
return true
}
}
7) Finding Preferences
val signaturePreference: EditTextPreference? = findPreference("key")signaturePreference?.setOnPreferenceChangeListener { preference, newValue ->
Toast.makeText(context, newValue.toString(), Toast.LENGTH_LONG).show()
true
}
8) Use a SimpleSummaryProvider to automatically display the saved Preference
value as the summary
app:useSimpleSummaryProvider="true"
code
editTextPreference.summaryProvider = EditTextPreference.SimpleSummaryProvider.getInstance()
Use a custom SummaryProvider
countingPreference?.summaryProvider = SummaryProvider<EditTextPreference> { preference ->
val text = preference.text
if (TextUtils.isEmpty(text)) {
"Not set"
} else {
"Length of saved value: " + text.length
}
}
9) Within an EditTextPreference
dialog, you can customize text field behavior by attaching an OnBindEditTextListener
. This listener is invoked when the dialog is shown to the user.
numberPreference?.setOnBindEditTextListener { editText ->
editText.inputType = InputType.TYPE_CLASS_NUMBER
}
10) A Preference
can have a specific action when tapped
- set an
Intent
on aPreference
to launch a newFragment
,Activity
. you can use an intent tag with Preference, SwitchPreferenceCompat, …etc
<intent
android:targetPackage="com.example"
android:targetClass="com.example.ExampleActivity">
<extra
android:name="example_key"
android:value="example_value"/>
</intent>
- or you can set an
OnPreferenceClickListener
onClickPreference.setOnPreferenceClickListener({
// do something
true
})
11) To retrieve the SharedPreferences
object that is being used, call PreferenceManager.getDefaultSharedPreferences()
val sharedPreferences = PreferenceManager.getDefaultSharedPreferences(this /* Activity context */)
val name = sharedPreferences.getString("signature", "")
12) To listen for changes to Preference
values, you can choose between two interfaces:
val sharedPreferences = PreferenceManager.getDefaultSharedPreferences(context)sharedPreferences.registerOnSharedPreferenceChangeListener { sharedPreferences: SharedPreferences, key: String ->
}
Using a custom Data Store
13) you can also use a custom data store. A custom data store can be useful if your application persists values to a database or if values are device-specific
class DataStore : PreferenceDataStore() {
override fun putString(key: String, value: String?) {
// Save the value somewhere (Database / Server)
}
override fun getString(key: String, defValue: String?): String? {
// Retrieve the value
}
}
14) After you have implemented your data store, you must set the new data store in onCreatePreferences()
so that Preference
objects persist values with the data store instead of using the default SharedPreferences
val preference: Preference? = findPreference("key")
preference?.preferenceDataStore = dataStore
15) To enable a custom data store for an entire hierarchy, call setPreferenceDataStore()
on the PreferenceManager
val preferenceManager = preferenceManager
preferenceManager.preferenceDataStore = dataStore