Ripristino dello stato di TextView dopo la rotazione dello schermo?


104

Nella mia app ho TextViewe EditText. Entrambi contengono dati. Quando l'orientamento dello schermo cambia i dati nei EditTextresti, ma i TextViewdati vengono cancellati.

Qualcuno può aiutarmi a trovare un modo per conservare anche i dati TextView?

Risposte:


221

Se vuoi forzare il TextViewsalvataggio del suo stato devi aggiungere l' freezesTextattributo:

<TextView 
     ... 
     android:freezesText="true" />

Dalla documentazione in poi freezesText:

Se impostata, la visualizzazione del testo includerà il suo testo completo corrente all'interno del suo ghiacciolo congelato oltre ai metadati come la posizione corrente del cursore. Per impostazione predefinita, questo è disabilitato; può essere utile quando il contenuto di una visualizzazione di testo non è memorizzato in un luogo persistente come un fornitore di contenuti


13
Perché il testo non è "congelato / salvato" per impostazione predefinita come gli altri attributi (selezione del testo, posizione del cursore, ecc.)? In altre parole, in quale scenario qualcuno preferirebbe effettivamente che il testo non venga salvato?
Gautam

3
@Gautam, la mia ipotesi sarebbe che spesso i TextView siano costruiti da stringhe statiche memorizzate in XML, nel qual caso è ridondante per il sistema ricordare i valori.
anderspitman

3
In realtà, una volta assegnato un ID a EditText o TextView, il valore persisterà durante un evento di rotazione dello schermo.
DoctorFox

7
@jegesh - sfortunatamente questo non è il caso di TextViews almeno su alcuni dispositivi (Jellybean)
Bö macht Blau

1
Non funziona per me, almeno non su un dispositivo API 17
Ab

28

Per conservare i dati sul cambio di orientamento è necessario implementare i due metodi:

@Override
protected void onRestoreInstanceState(Bundle savedInstanceState) {
    super.onRestoreInstanceState(savedInstanceState);
    // Read values from the "savedInstanceState"-object and put them in your textview
}

@Override
protected void onSaveInstanceState(Bundle outState) {
    // Save the values you need from your textview into "outState"-object
    super.onSaveInstanceState(outState);
}

5
Perché utilizzare onRestoreInstanceState quando lo stesso bundle è disponibile in onCreate?
Slott

4
@slott Controlla questa documentazione. developer.android.com/training/basics/activity-lifecycle/… Questa è una congettura, ma sospetto che sia perché il sistema tiene traccia se sta creando una nuova attività o se ne sta ricreando una vecchia. onRestorySavedInstance viene chiamato solo in circostanze più rare: modifiche alla configurazione e distruzione delle attività a causa dei limiti di memoria.
Gusdor

6

1) Non tutte le viste con un ID salvano il loro stato. I widget Android, con un ID, il cui stato può essere modificato dall'utente, sembrano salvare il loro stato su un soft kill. Quindi EditText salva il suo stato, ma TextView non salva il suo stato su un soft kill.

"AFAIK, Android si preoccupa solo di salvare lo stato per le cose che dovrebbero cambiare. Ecco perché salva il testo in un EditText (che è probabile che un utente cambi) e forse non salva lo stato per un TextView (che normalmente rimane statico )"

Mark M

Quindi puoi scegliere di salvare lo stato della visualizzazione di testo in onSaveInstanceState e puoi scegliere di ripristinare lo stato della visualizzazione di testo in onCreate.

2) La best practice consiste nel salvare lo stato "interno" di non visualizzazione dell'istanza anche se dichiari

android:configChanges= "orientation|keyboardHidden" 

Dai documenti:

"Tuttavia, la tua applicazione dovrebbe sempre essere in grado di chiudersi e riavviarsi con il suo stato precedente intatto. Non solo perché ci sono altre modifiche alla configurazione che non puoi impedire di riavviare l'applicazione, ma anche per gestire eventi come quando l'utente riceve un telefonata e poi torna alla tua applicazione. "

JAL


6

Android non gestisce questo genere di cose per te. Hai salvato tutti i dati manualmente.

È possibile utilizzare in un'attività per salvare i valori

@Override
    public Object onRetainNonConfigurationInstance() {
        HashMap<String, Object> savedValues = new HashMap<String, Object>();
        savedValues.put("someKey", someData);           
        return savedValues;
    }

e utilizzare qualcosa di simile nel metodo oncreate di un'attività per caricare gli oggetti salvati

HashMap < String, Object> savedValues 
     = (HashMap<String, Object>)this.getLastNonConfigurationInstance();

puoi anche scegliere di disabilitare il cambio di orientamento per un'attività

<activity android:name=".Activity" android:screenOrientation="portrait" >
    <intent-filter>
        <action android:name="android.intent.action.MAIN" />
    </intent-filter>
</activity>

non può sostituire onRetainNonConfigurationInstance () in android.support.v4.app.fragmentActivity; il metodo sostituito è definitivo !!
Akash Dubey

1

Modifica le tue attività in AndroidManifest.xml per sovrascrivere il comportamento di modifica dell'orientamento aggiungendo questo alla tua attività / attività:

android:configChanges="orientation|keyboardHidden"

Dovrebbe essere simile a questo:

    <activity android:name=".activity.LoginActivity"
              android:configChanges="orientation|keyboardHidden"
              android:label="@string/app_name">
    </activity>

27
In generale, questo approccio non è raccomandato dalla documentazione : "L'utilizzo di questo attributo dovrebbe essere evitato e utilizzato solo come ultima risorsa. Si prega di leggere Handling Runtime Changes ..."
idbrii

1

Aggiungili ad AndroidManifest.xml
Metti il ​​nome dell'attività al posto di Activity_Name

<activity android:name="Activity_Name"
        android:screenOrientation="sensor"
        ...
        android:configChanges="orientation|keyboardHidden|screenSize">

Funzionerà anche con il cambio di valore TextField.


1

basta aggiungere

android:configChanges="orientation|screenSize"

alla tua attività in AndroidManifest.xml.


-2

Quando la configurazione cambia, Android riavvia la tua attività per impostazione predefinita. Per cambiare questo è necessario sostituire il onConfigurationChanged()metodo. Inoltre, dovresti aggiungere android:configChangesal tuo file manifest.

Puoi leggere di più qui .


-7

Ho anche usato

android:configChanges="orientation"

e non ha funzionato.

Ma poi ho trovato una soluzione.

Verifica se hai la seguente riga correttamente nel tuo maniest:

<uses-sdk android:minSdkVersion="11" android:targetSdkVersion="11" />

assicurati che non legga qualcosa di simile

<uses-sdk android`:minSdkVersion="11" android:targetSdkVersion="15" />`

L'ho avuto nel secondo modo al primo posto, ma quando ho corretto lo stato è stato preservato.


1
Questa è una cosa completamente diversa. Target SDK serve a rendere la tua app compatibile con la maggior parte degli intervalli di sistemi operativi Android. Questa non è una risposta, in qualche modo potrebbe aver funzionato nel tuo caso, ma questa non è una soluzione appropriata.
Rohan Kandwal
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.