Search code examples
androidandroid-fragmentssettingsnavigation-drawerpreferenceactivity

Android: How to Implement a Settings Page Within a Navigation Drawer?


So I'm in the process of creating an app which utilises a Navigation Drawer which is split into separate fragments to access each of the tabs. Now, the thing I would like to find out how to do, is to equally have a Settings/Preferences Fragment or Activity (unsure which one would be appropriate in this context) to open once the user selects the "Settings" tab within the Navigation Drawer. I've looked all over the internet for a CLEAR explanation on how to do this, as I'm not an expert on app development.

Below is a picture of the Navigation Drawer: Navigation Drawer

If any layout or class code is required, I am happy to provide it. Any help is much appreciated!


Solution

  • You can use the PreferenceFragmentCompat, for example:

    First you create a Fragment who extends PreferenceFragmentCompat and the layout associated under the folder res/xml

    settings.xml

    <android.support.v7.preference.PreferenceScreen
        xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="match_parent"
        android:layout_height="match_parent">
    
        <android.support.v7.preference.PreferenceCategory
            android:key="the_key_to_retrieve_the_preference_in_code"
            android:title="the_preference_title">
    
            <android.support.v7.preference.Preference
                android:key="key"
                android:summary="subtitle"
                android:title="title" />
    
            <android.support.v7.preference.Preference
                android:key="key2"
                android:summary="subtitle2"
                android:title="title2" />
    
            <android.support.v7.preference.CheckBoxPreference
                 android:key="key_for_check_box"
                 android:summary="subtitle"
                 android:title="title" />
    
        </android.support.v7.preference.PreferenceCategory>
    </android.support.v7.preference.PreferenceScreen>
    

    SettingsFragment.java

    public class SettingsFragment extends PreferenceFragmentCompat {
    
        @Override
        public void onCreatePreferences(Bundle savedInstanceState, String rootKey) {
            addPreferencesFromResource(R.xml.settings);
        }
    
        @Override
        public void onActivityCreated(Bundle savedInstanceState) {
            super.onActivityCreated(savedInstanceState);
           // To get a preference
           PreferenceScreen preferenceScreen = getPreferenceScreen();
           Preference preference = preferenceScreen.findPreference("preference_ key_defined_in_the_xml");
    
         //You can set a listener
         preference.setOnPreferenceClickListener(new Preference.OnPreferenceClickListener() {
                @Override
                public boolean onPreferenceClick(Preference preference) {
                    return false;
                }
            });
    
         //change title
         preference.setTitle("my_title");
    
         // etc
        }
    }
    

    Then you create a Activity who will hold the fragment:

    SettingsActivity.java

    public class SettingsActivity extends AppCompatActivity {
        private Toolbar mToolbar;
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.settings_activity);
    
            mToolbar = (Toolbar) findViewById(R.id.toolbar);
    
            setSupportActionBar(mToolbar);
            setActionBarTitle("Settings");
            ActionBar actionBar = getSupportActionBar();
            if (actionBar != null) {
                actionBar.setHomeButtonEnabled(true);
                actionBar.setDisplayHomeAsUpEnabled(true);
            }
        }
    } 
    

    settings_activity.xml

    <?xml version="1.0" encoding="utf-8"?>
    <android.support.design.widget.CoordinatorLayout
        xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:app="http://schemas.android.com/apk/res-auto"
        android:layout_width="match_parent"
        android:layout_height="match_parent">
    
        <android.support.design.widget.AppBarLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content">
    
            <android.support.v7.widget.Toolbar
                android:id="@+id/toolbar"
                android:layout_width="match_parent"
                android:layout_height="?attr/actionBarSize"
                android:background="?attr/colorPrimary"
                android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"
                app:popupTheme="@style/ThemeOverlay.AppCompat.Light" />
        </android.support.design.widget.AppBarLayout>
    
        <fragment
            android:id="@+id/settings_fragment"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            app:layout_behavior="@string/appbar_scrolling_view_behavior"        
            android:name="package.name.SettingsFragment"/>
    
    </android.support.design.widget.CoordinatorLayout>
    

    Be sure to add the new Settings activity to your manifest

    AndroidManifest.xml

    <?xml version="1.0" encoding="utf-8"?>
    <manifest xmlns:android="http://schemas.android.com/apk/res/android"
              package="com.example.app">
    
        <application
                android:name=".MyApplication"
                android:allowBackup="true"
                android:icon="@mipmap/ic_launcher"
                android:label="@string/app_name"
                android:roundIcon="@mipmap/ic_launcher_round"
                android:supportsRtl="true"
                android:theme="@style/AppTheme">
            <activity
                    android:name=".MainActivity"
                    android:label="@string/app_name"
                    android:theme="@style/AppTheme.NoActionBar">
                <intent-filter>
                    <action android:name="android.intent.action.MAIN"/>
    
                    <category android:name="android.intent.category.LAUNCHER"/>
                </intent-filter>
            </activity>
    
            <!-- add the below line to your AndroidManifest.xml -->
            <activity android:name=".SettingsActivity"></activity> 
    
        </application>
    
    </manifest>
    

    That it , then when you click on the item in your NavigationDrawer you set a new Intent and call it:

    Intent intent = new Intent(this /*or the actual context*/, SettingsActivity.class);
    startActivity(intent);
    

    Hope this helps. Sorry for my english.