Rimuovi / nascondi una preferenza dallo schermo


134

Ho un'attività che estende PreferenceActivity. Sto caricando le preferenze dal file XML. Ma in alcuni casi ho bisogno di nascondere completamente una delle preferenze dallo schermo in base allo stato della mia app. Esiste un metodo setEnabled, ma non è esattamente quello che voglio. Voglio rimuovere completamente quella preferenza dallo schermo. È possibile ?

Risposte:


171

Sì, se hai un riferimento sia a, sia al Preferencesuo genitore (a PreferenceCategory, o PreferenceScreen)

myPreferenceScreen.removePreference(myPreference);

Grande! Grazie! Funziona e ha perfettamente senso
Bostone,

Avrei potuto rispondere alla mia domanda attraverso questo? stackoverflow.com/a/4704360/956975
marienke

2
Sfortunatamente, rimuove definitivamente la preferenza. È possibile solo nasconderlo?
Dmitry,

Inoltre non funziona per me. La preferenza rimane!
Dmitry,

@Dmitry Puoi semplicemente disattivarlo consetEnabled()
JakeD

212

Se sei Preferencedentro a PreferenceCategory, devi fare questo:

XML:

<PreferenceCategory
    android:key="category_foo"
    android:title="foo">

    <CheckBoxPreference
        android:key="checkPref" />

Giava:

CheckBoxPreference mCheckBoxPref = (CheckBoxPreference) findPreference("checkPref");
PreferenceCategory mCategory = (PreferenceCategory) findPreference("category_foo");
mCategory.removePreference(mCheckBoxPref);

5
Per essere onesti, la risposta sopra dice che hai bisogno del genitore PreferenceCategory.
opaco

49

Nel caso in cui la preferenza sia un figlio diretto della schermata delle preferenze, ecco un codice autonomo:

PreferenceScreen screen = getPreferenceScreen();
Preference pref = getPreferenceManager().findPreference("mypreference");
screen.removePreference(pref);

4
Questo non funzionerà se la preferenza si trova all'interno della categoria. devi findPreferenceper la categoria e rimuovere la preferenza dalla categoria
MBH

1
@MBH: Grazie per aver menzionato questo avvertimento!
1 ''

9

Se vuoi qualcosa che cambierà dinamicamente le preferenze per esempio su SwitchPreference, ho scoperto che il modo migliore è mettere tutte le mie opzioni secondarie in contenitori di due categorie. Inizialmente avrai tutto mostrato, quindi rimuoverai solo i bit che non vuoi. La cosa intelligente è che si innesca semplicemente ricreare quando qualcosa cambia e quindi non è necessario creare manualmente nulla o preoccuparsi di rimettere le cose nell'ordine corretto.

protected void onCreate(Bundle savedInstanceState) {
  super.onCreate(savedInstanceState);
  addPreferencesFromResource(R.xml.preferences);
  PreferenceCategory prefCatOne= (PreferenceCategory)findPreference("prefCatOne");
  PreferenceCategory prefCatTwo= (PreferenceCategory)findPreference("prefCatTwo");
  SwitchPreference mySwitchPref= (SwitchPreference)findPreference("mySwitchPref");
  PreferenceScreen screen = getPreferenceScreen();
  if (mySwitchPref.isChecked()) {
    screen.removePreference(prefCatOne);
  } else {
    screen.removePreference(prefCatTwo);
  }
}

public void onSharedPreferenceChanged(SharedPreferences prefs, String key) {
    if (key.equals("mySwitchPref")) {
        this.recreate();
    }
}

L'unico aspetto negativo che posso vedere con questo è che c'è un flash mentre lo schermo viene ricreato da zero.


Il caso non funziona, almeno non in 22. Ma cambiarlo in una preferenza (anche se è un raggruppamento di preferenze) funziona.
Rob,

Rob, ho appena testato il codice sopra in un AVD API22 e funziona bene. Assicurati che il contenuto XML delle tue preferenze corrisponda al tuo codice. Per l'esempio sopra, SwitchPreference può essere ovunque, ma è necessario che PreferenceCategorys sia figlio diretto di PreferenceScreen.
James,

Ho appena ottenuto la categoria come preferenza, nessun cast e l'ho rimossa. Lavorato.
Rob

8

Nel tuo file XML:

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

    <PreferenceCategory
        android:key="personalisation"
        android:title="your title here">

        <ThemedPreference
            android:key="animation" />

</PreferenceScreen>

Nel tuo codice:

PreferenceScreen pPreferenceScreen = (PreferenceScreen) findPreference("preferenceScreen");

PreferenceCategory pCategory = (PreferenceCategory) findPreference("personalisation");
ThemedPreference pThemePref = (ThemedPreference) findPreference("animation");

pPreferenceScreen.removePreference(pCategory); //remove category
pCategory.removePreference(pThemePref);   // remove preference

8

Se stai usando PreferenceFragmentCompat puoi impostare la visibilità in xml.

Le preferenze nel tuo XML verranno convertite automaticamente nelle versioni di AppCompat. È quindi possibile utilizzare l' attributo ' app: isPreferenceVisible ' nel proprio XML

preferences.xml

<PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools">

    <CheckBoxPreference
        android:defaultValue="false"
        android:key="show.navigation"
        android:title="Show navigation"
        app:isPreferenceVisible="false" />

...

L'attributo è documentato su https://developer.android.com/guide/topics/ui/settings/components-and-attributes

L'aggiunta PreferenceFragmentCompatè documentata su https://developer.android.com/guide/topics/ui/settings/#inflate_the_hierarchy

Esempio:

public class MySettingsActivity extends AppCompatActivity {

    public static class MySettingsFragment extends PreferenceFragmentCompat {
        @Override
        public void onCreatePreferences(Bundle savedInstanceState, String rootKey) {
            setPreferencesFromResource(R.xml.preferences, rootKey);
        }
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        getSupportFragmentManager()
                .beginTransaction()
                .replace(R.id.settings_container, new MySettingsFragment())
                .commit();
    }
} 


3

Nel file XML è possibile effettuare una preferenza nascosta lasciando vuoti il ​​titolo e i tag di riepilogo.

<EditTextPreference
    android:defaultValue="toddlerCam"
    android:key="save_photo_dir"
/>

Questa è la risposta perfetta per me. Lo stavo cercando. Grazie!
夏 期 劇場

2

Ecco un modo generico per farlo che funziona indipendentemente dal fatto che la preferenza sia sotto un PreferenceCategoryo PreferenceScreen.

private void removePreference(Preference preference) {
    PreferenceGroup parent = getParent(getPreferenceScreen(), preference);
    if (parent == null)
        throw new RuntimeException("Couldn't find preference");

    parent.removePreference(preference);
}

private PreferenceGroup getParent(PreferenceGroup groupToSearchIn, Preference preference) {
    for (int i = 0; i < groupToSearchIn.getPreferenceCount(); ++i) {
        Preference child = groupToSearchIn.getPreference(i);

        if (child == preference)
            return groupToSearchIn;

        if (child instanceof PreferenceGroup) {
            PreferenceGroup childGroup = (PreferenceGroup)child;
            PreferenceGroup result = getParent(childGroup, preference);
            if (result != null)
                return result;
        }
    }

    return null;
}


0

Puoi farlo in 2 modi:

1.Se usi la libreria di supporto, puoi costruire una mappa dell'albero delle preferenze e dei loro genitori, quindi rimuovere una preferenza usando il suo genitore. Ecco una funzione per generare una tale mappa:

public static Map<Preference, PreferenceGroup> buildPreferenceParentTree(@NonNull final PreferenceScreen preferenceScreen) {
    final Map<Preference, PreferenceGroup> result = new HashMap<>();
    final Stack<PreferenceGroup> curParents = new Stack<>();
    curParents.add(preferenceScreen);
    while (!curParents.isEmpty()) {
        final PreferenceGroup parent = curParents.pop();
        final int childCount = parent.getPreferenceCount();
        for (int i = 0; i < childCount; ++i) {
            final Preference child = parent.getPreference(i);
            result.put(child, parent);
            if (child instanceof PreferenceGroup)
                curParents.push((PreferenceGroup) child);
        }
    }
    return result;
}
  1. Se usi la nuova API delle preferenze di android-x, puoi semplicemente impostare la visibilità, usando la funzione setVisible su di essa.

Secondo i documenti e la risposta di Tea setVisible() è disponibile dalla versione 24.1.0 della libreria di supporto.
JJD

Hai visto cosa ho scritto? Ho scritto specificamente che ora è possibile ... Inoltre, la prima soluzione aiuta con la rimozione, che è un po 'diversa dal nascondersi ..
Sviluppatore Android

Sì, ho letto la tua risposta. Mi riferivo al tuo secondo punto. Sembra che il setVisibile()metodo sia disponibile da Android-X, che ho cercato di chiarire. Senza offesa per favore.
JJD

Android-X è quello che sostituisce tutte le librerie di supporto. Non ci saranno nuove versioni della libreria di supporto come le conosciamo.
sviluppatore Android

Corretta. Ne sono consapevole . Tuttavia, le persone che sono bloccate con le versioni precedenti possono utilizzare il metodo.
JJD,

0

Se si desidera valutare e sulla base di quella maschera, potrebbe essere un'alternativa

SwitchPreference autenticacionUsuario = 
    (SwitchPreference) findPreference("key_autenticacion_usuario");

final EditTextPreference Username = 
    (EditTextPreference) findPreference("key_username_mqtt");
final EditTextPreference Password = 
    (EditTextPreference) findPreference("key_password_mqtt");

if (!autenticacionUsuario.isChecked()) {
    PreferenceCategory preferenceCategory = 
        (PreferenceCategory) findPreference("category_mqtt");
    preferenceCategory.removePreference(Username);
    preferenceCategory.removePreference(Password);
}

Tutto questo deve essere dentro

public static class PrefsFragment extends PreferenceFragment {

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

1
Siamo spiacenti, ma questo è un sito inglese. Sai rispondere in inglese?
Dave Schweisguth,

Naturalmente la mia intenzione era anche quella di provvedere alle persone che non parlano inglese
Gustavo Eduardo Belduma,

3
@GustavoEduardoBelduma potrebbe essere necessario leggere questo meta.stackoverflow.com/a/297680/545026
Leo supporta Monica Cellio il

0

Se stai facendo quello che penso che stai cercando di fare (perché sto provando a farlo ora), potrebbe essere meglio abilitare / disabilitare la preferenza. Perché rimuoverlo lo elimina dalla schermata delle preferenze e potresti non essere in grado di aggiungerlo nel punto desiderato se lo schermo è stato programmato.

pref.setEnabled (false); pref.setEnabled (true);

anche se questo potrebbe essere deprecato. Funziona per il caso d'uso che sto attraversando in questo momento.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.