【问题标题】:Android - Implementing ListPreferences in my apps PreferencesAndroid - 在我的应用程序中实现 ListPreferences
【发布时间】:2014-09-29 20:55:35
【问题描述】:

如果在我的首选项中从ListPreferences 进行选择,我将如何更改Fragment 中的微调器数组的内容?

在我的应用程序中,我尝试添加包含 ListPreferences 的首选项。我写了设置Activity,它显示了我的数组列表,但是当我选择一个选项时,我的应用程序没有任何变化。我的应用程序从主 Activity 运行 Fragments。我尝试使用用户选择的设置来操作从我的初始Fragment 显示的数据。这是我的代码:

设置活动:

@TargetApi(Build.VERSION_CODES.HONEYCOMB)
@Override
public void onCreate (Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    addPreferencesFromResource(R.xml.settings);
    PreferenceManager.setDefaultValues(SettingsActivity.this, R.xml.settings, false);
    //ListPreference lp = (ListPreference)findPreference("prefSections");
    //lp.setEntries(new String [] {"prefSections", "PrefSectionsValues"});
    getActionBar().setDisplayHomeAsUpEnabled(true);
}

@Override
public boolean onOptionsItemSelected(MenuItem item){
    switch (item.getItemId()){
        case android.R.id.home:
            NavUtils.navigateUpFromSameTask(this);
            return true;
        default:
            return super.onOptionsItemSelected(item);
    }
}

@Override
public void onSharedPreferenceChanged(SharedPreferences sharedPreferences, String key) {

}

最初显示的片段:

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                         Bundle savedInstanceState) {

    container.removeAllViews();

    //Use View "v" containing the layout and container - use v.findViewById in others
    View v = inflater.inflate(R.layout.mylayout, container, false);

    SharedPreferences settingPrefs = PreferenceManager.getDefaultSharedPreferences(getActivity().getBaseContext());
    String settingSection = settingPrefs.getString("prefSectionsValues", "1");
        if (settingSection == "1"){
        ArrayAdapter<String> spinnerArrayAdapter = new ArrayAdapter<String>(this.getActivity(), android.R.layout.simple_spinner_item, displayName);
        spinnerArrayAdapter.setDropDownViewResource(android.R.layout.simple_dropdown_item_1line);
        spLoadFrom.setAdapter(spinnerArrayAdapter);
    } else if (settingSection == "2"){
        ArrayAdapter<String> spinnerArrayAdapter = new ArrayAdapter<String>(this.getActivity(), android.R.layout.simple_spinner_item, displayName2);
        spinnerArrayAdapter.setDropDownViewResource(android.R.layout.simple_dropdown_item_1line);
        spLoadFrom.setAdapter(spinnerArrayAdapter);
    } else if (settingSection == "3"){
        ArrayAdapter<String> spinnerArrayAdapter = new ArrayAdapter<String>(this.getActivity(), android.R.layout.simple_spinner_item, displayName3);
        spinnerArrayAdapter.setDropDownViewResource(android.R.layout.simple_dropdown_item_1line);
        spLoadFrom.setAdapter(spinnerArrayAdapter);
    }else if (settingSection == "4"){
        ArrayAdapter<String> spinnerArrayAdapter = new ArrayAdapter<String>(this.getActivity(), android.R.layout.simple_spinner_item, displayName4);
        spinnerArrayAdapter.setDropDownViewResource(android.R.layout.simple_dropdown_item_1line);
        spLoadFrom.setAdapter(spinnerArrayAdapter);
    }else if (settingSection == "5"){
        ArrayAdapter<String> spinnerArrayAdapter = new ArrayAdapter<String>(this.getActivity(), android.R.layout.simple_spinner_item, displayName5);
        spinnerArrayAdapter.setDropDownViewResource(android.R.layout.simple_dropdown_item_1line);
        spLoadFrom.setAdapter(spinnerArrayAdapter);
    }
    //ArrayAdapter<String> spinnerArrayAdapter = new ArrayAdapter<String>(this.getActivity(), android.R.layout.simple_spinner_item, displayName);
    //spinnerArrayAdapter.setDropDownViewResource(android.R.layout.simple_dropdown_item_1line);
    //spLoadFrom.setAdapter(spinnerArrayAdapter);

    SpinnerListener spListener = new SpinnerListener();

    spLoadFrom.setOnItemSelectedListener(spListener);
    // Inflate the layout for this fragment
return v;
}

arrays.xml:

<?xml version="1.0" encoding="utf-8"?>
<resources>

<string-array name="prefSections">
    <item name="sec">Split by Section</item>
    <item name="secchap">Split by Section with Chapters</item>
    <item name="secchapwhole">Split by Section with Chapters and the entire doc</item>
    <item name="chap">Split by Chapters</item>
    <item name="chapwhole">Split by Chapters and the entire doc</item>
</string-array>
<string-array name="prefSectionsValues">
    <item>1</item>
    <item>2</item>
    <item>3</item>
    <item>4</item>
    <item>5</item>
</string-array>

</resources>

settings.xml:

<?xml version="1.0" encoding="utf-8"?>

<PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android">

<PreferenceCategory android:title="@string/prefUpdateCat">
    <CheckBoxPreference
        android:key="prefUpdate"
        android:summary="On/Off"
        android:title="Check for updates" />
</PreferenceCategory>

<PreferenceCategory android:title="@string/prefSectionsCat">
    <ListPreference
        android:key="pref_Sections"
        android:entries="@array/prefSections"
        android:entryValues="@array/prefSectionsValues"
        android:summary="How it should be displayed"
        android:title="it's displayed..." />
</PreferenceCategory>

</PreferenceScreen>

【问题讨论】:

    标签: android android-fragments settings android-preferences listpreference


    【解决方案1】:

    尝试更改您的 SettingsActivity 类以实现 SharedPreferences.OnSharedPreferenceChangeListener,这将使您在注册用户偏好更改时做出适当的响应。

    public class SettingsActivity extends PreferenceActivity implements SharedPreferences.OnSharedPreferenceChangeListener {
        ...
        ...
    }
    
    
    @Override
    public void onSharedPreferenceChanged(SharedPreferences sharedPreferences,
            String key) {
        Log.d(TAG, "Preferences have been changed");
        //indicate fragment needs to update it's content
    }
    

    此外,您的片段似乎没有得到更新,因为您显示用户偏好的逻辑位于 oncreateview 函数中,该函数仅在创建该片段时被调用。 Read more about that here。基本上,onResume 函数会比 onCreate 更好。只是不要在 onCreate 和 onResume 中复制您的代码,否则它会在第一次创建片段时运行两次。

    Override
    public void onResume() 
    { 
        super.onResume();
        //if spinnerarrayadapter is empty then populate as normal
             //set as adapter for spLoadForm
        //else if user preferences have changed
             //populate spinnerarrayadapter here; 
             //spinnerarrayadapter.notifyDataSetChanged();
    }
    

    您可以使用您在 onSharedPreferenceChange() 函数中设置的静态全局变量来跟踪用户偏好是否已更改。但是对于测试(或者如果您不认为使用内容填充 spinnerarrayadapter 是一个缓慢的过程,当在最终版本产品中多次运行时会影响最终用户体验),您可以将其设为 else 语句。

    希望这会有所帮助。

    【讨论】:

    • 为了跟进,我尝试实现 SharedPreferences 更改的侦听器。我无法弄清楚如何显示片段微调器数组中的变化。我是否走在正确的道路上,认为我需要用事务替换片段?如果是这样,我应该把代码放在哪里?
    • 你之前是在正确的轨道上,一个片段是去这里的方式。尝试覆盖 onResume 函数(请参阅我更新的答案)。当您离开共享偏好后返回片段时,onResume 将被调用。事后看来,这意味着您可以删除 SharedPreferences 侦听器,因为在这种情况下它实际上并没有做任何事情。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-09-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-12-30
    相关资源
    最近更新 更多