EditTextPreferenceで整数値を扱う
2021/01/24
Android
Kotlin
SharedPreference
Androidアプリ開発において、EditTextPreferenceでInt型のSharedPreferencesを取り扱う方法です。
環境
- compileSdkVersion 29
- minSdkVersion 21
- androidx.core:core-ktx:1.3.2
- androidx.preference:preference-ktx:1.1.1
- androidx.legacy:legacy-preference-v14:1.0.0
EditTextPreferenceを拡張する
EditTextPreference
をそのまま使うとString型としてSharedPreferenceに保存されます。
ですのでEditTextPreference
を拡張してIntegerを扱えるようにします。
import android.content.Context
import android.util.AttributeSet
import androidx.preference.EditTextPreference
import java.lang.NumberFormatException
class IntegerEditTextPreference : EditTextPreference {
constructor(context: Context?): super(context)
constructor(context: Context?, attrs: AttributeSet?): super(context, attrs)
constructor(context: Context?, attrs: AttributeSet?, defStyle: Int): super(context, attrs, defStyle)
constructor(context: Context?, attrs: AttributeSet?, defStyle: Int, defStyleRes: Int): super(context, attrs, defStyle, defStyleRes)
override fun getPersistedString(defaultReturnValue: String?): String {
return getPersistedInt(0).toString()
}
override fun persistString(value: String?): Boolean {
val intValue = try{
Integer.parseInt(value!!)
}
catch (e: NumberFormatException){
e.printStackTrace()
0
}
return persistInt(intValue)
}
}
値の範囲に制限を付けたり加工したい場合は、persistInt
に放り込む値を加工すれば実現できます。入力が空の場合を考慮して、NumberFormatException
は受けるようにしましょう。
Fragmentの作成
res/xml/preferences.xml
などのリソースファイルでは拡張したEditTextPreference
を利用します。
<?xml version="1.0" encoding="utf-8"?>
<PreferenceScreen
xmlns:android="http://schemas.android.com/apk/res/android"
>
<com.hassakulab.preference.IntegerEditTextPreference
android:key="HOGE"
android:title="SampleIntegerPreference"
android:summary="summary"
/>
</PreferenceScreen>
PreferenceFragment
の実装では、setOnBindEditTextListener
でEditTextの入力内容の制限などをします。
より細かな制御をするなら、TextEdit.addTextChangedListener
でTextWatcher
を実装すると良いでしょう。
リソースファイルでinputType
などを設定してもsetPreferencesFromResource
でViewを生成するタイミングで上書きされるようです。[1]
class SamplePreferenceFragment: PreferenceFragmentCompat(){
override fun onCreatePreferences(savedInstanceState: Bundle?, rootKey: String?) {
setPreferencesFromResource(R.xml.preferences, rootKey)
samplePreference = findPreference("HOGE")!!
samplePreference.setOnBindEditTextListener { editText ->
editText.inputType = InputType.TYPE_CLASS_NUMBER
editText.maxLines = 1
}
}
}
-
なんでこうなるか、ソースを読んで確認してないのでよくわかってないです。本当は確認した方がいい。バージョン依存? android - EditTextPreference - only numeric value inputType - isn't working - Stack Overflow
↩