Preferenceを使った設定画面の作成|Android開発

AndroidでPreferenceを使って設定を保存する方法です。
PreferenceActivityPreferenceFragmentを使うことで簡単に設定画面を作成できます。

設定画面のレイアウト

画面レイアウトは不要です。代わりに設定項目の一覧を用意します。
res\xmlフォルダを作成し、任意のxmlファイルを用意します。下記サンプルではpref_main.xmlというファイルを用意しました。

PreferenceScreenのサンプル

res\xml\pref_main.xmlの内容です。
CheckBox(ON/OFF)テキスト入力の項目を用意しています。

<?xml version="1.0" encoding="utf-8"?>
<PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android">

    <CheckBoxPreference
        android:key="on_off_preference"
        android:title="Check Status" />

    <EditTextPreference
        android:key="text_value_preference"
        android:title="Text Value" />

</PreferenceScreen>

List表示の書き方

文字列リソース定義(strings.xml)
<string name="value_10">10</string>
<string name="value_20">20</string>
<string name="value_30">30</string>
<string name="value_40">40</string>
<string name="value_50">50</string>

<string-array name="sample_list">
    <item>@string/value_10</item>
    <item>@string/value_20</item>
    <item>@string/value_30</item>
    <item>@string/value_40</item>
    <item>@string/value_50</item>
</string-array>

<string-array name="sample_list_values">
    <item>10</item>
    <item>20</item>
    <item>30</item>
    <item>40</item>
    <item>50</item>
</string-array>
設定画面の記述
<ListPreference
    android:key="key_list_sample"
    android:title="ListPreference"
    android:entries="@array/sample_list"
    android:entryValues="@array/sample_list_values"
    android:defaultValue="30" />
entryValuesinteger-arrayは設定できません。文字列配列(string-array)のみ設定できます。

Activity

PreferenceActivityを継承したActivityを作成します。
今回はSettingsActivityというクラス名にしました。

マニフェストファイル

AndroidManifest.xmlSettingsActivityを追加します。

<application>

    <activity android:name=".SettingsActivity">
    </activity>

</application>

PreferenceFragment

PreferenceFragmentを継承したクラスを上記Activityのインナークラスとして作成します。

サンプル

import android.content.SharedPreferences;
import android.os.Bundle;
import android.preference.PreferenceActivity;
import android.preference.PreferenceFragment;
import android.preference.PreferenceManager;
import android.view.View;

import org.apache.commons.lang3.StringUtils;

public class SettingsActivity extends PreferenceActivity {
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        getFragmentManager().beginTransaction()
                .replace(android.R.id.content, new MainPreferenceFragment())
                .commit();
    }

    /********** PreferenceFragment **********/

    public static class MainPreferenceFragment extends PreferenceFragment
            implements SharedPreferences.OnSharedPreferenceChangeListener {

        public MainPreferenceFragment() {
            // Required empty public constructor
        }

        @Override
        public void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            addPreferencesFromResource(R.xml.pref_main);
        }

        @Override
        public void onViewCreated(View view, Bundle savedInstanceState) {
            super.onViewCreated(view, savedInstanceState);
        }

        @Override
        public void onResume() {
            super.onResume();
            SharedPreferences sp = getPreferenceScreen().getSharedPreferences();
            sp.registerOnSharedPreferenceChangeListener(this);
            setSummaries(sp);
        }

        @Override
        public void onPause() {
            super.onPause();
            getPreferenceScreen().getSharedPreferences()
                .unregisterOnSharedPreferenceChangeListener(this);
        }

        private void setSummaries(final SharedPreferences sp) {
            // 取得方法
            final boolean onOff = sp.getBoolean("on_off_preference", false);
            final String text = sp.getString("text_value_preference", StringUtils.EMPTY);
            findPreference("text_value_preference").setSummary(text);
        }

        @Override
        public void onSharedPreferenceChanged(SharedPreferences sharedPreferences, String key) {
            setSummaries(sharedPreferences);
        }
    }
}
SharedPreferencesPreferenceManager.getDefaultSharedPreferences(getActivity());でも取得可能です。

setSummaries()は現在の入力テキストをサマリとして表示する処理です。onResume()でもコールしているのは画面起動時にサマリ表示するため。設定値が変わらないとonSharedPreferenceChanged()が通知されないからです。

Preference サマリ

実行例

SettingsActivityを起動すると下記の画面が表示されます。

PreferenceFragment

テキスト入力の項目を開いた画面。

EditTextPreference

一度設定画面を閉じて再度開いても設定した値が保存されています。

PreferenceFragment

ListPreferenceのサンプル

ListPreference

設定値の取得

Preferenceで設定した値の取得方法です。
PreferenceManager.getDefaultSharedPreferences()を使い、SharedPreferencesインスタンスを取得してから、get系のメソッドで値を取得します。

設定値の書き込み

Preferenceで設定する項目をソースコードから直接設定する方法です。
SharedPreferences.Editorクラスのput系メソッドで値を更新します。
保存方法は同期と非同期があります。

非同期書き込み

editor.apply();

同期書き込み

editor.commit();

設定値の取得と書き込みのサンプル

設定値を取得し、未設定ならデフォルト値を保存するサンプルです。

public static void setDefault(Context context) {
    SharedPreferences sp = PreferenceManager.getDefaultSharedPreferences(context);
    // 設定値を取得する.
    String url = sp.getString("key_server_address", null);
    if (url == null) {
        // PreferenceFragment を使用せずに値を設定する.
        SharedPreferences.Editor editor = sp.edit();
        // デフォルト値を設定する.
        editor.putString("key_server_address", "192.168.10.1");
        editor.apply(); // 非同期書き込み.
    }
}

ListPreferenceの設定値を整数値として取得するサンプル

設定値は文字列で保存されています。なので設定値を取得後、Integer.parseInt()で変換します。

String valueStr = sp.getString("key_list_sample", res.getString(R.string.value_30));
int value = Integer.parseInt(valueStr);

ソースコード側でPreference Screenで定義した設定を非表示にする方法

PreferenceFragment.onViewCreated()(上記サンプルではMainPreferenceFragmentonViewCreated)で次のようにします。pkey_hideが非表示にしたい設定のキーです。

@Override
public void onViewCreated(View view, Bundle savedInstanceState) {
    super.onViewCreated(view, savedInstanceState);
    getPreferenceScreen().removePreference(findPreference("pkey_hide"));
}
このエントリーをはてなブックマークに追加
にほんブログ村 IT技術ブログへ

コメント

メールアドレスが公開されることはありません。 が付いている欄は必須項目です