Ne rechargez pas l'application lorsque l'orientation change

152

Je n'ai simplement besoin de rien à changer lorsque l'écran est tourné. Mon application affiche une image aléatoire lors du premier chargement et la rotation de l'appareil ne doit pas sélectionner une autre image aléatoire. Comment puis-je (simplement) faire cesser ce comportement?

Jimmy D
la source
1
Il est également possible de verrouiller (et éventuellement de déverrouiller) l'orientation de l'écran à partir du code. Appelez simplement Screen.lockOrientation(this)de github.com/delight-im/Android-BaseLib/blob/master/Source/src/im/… pour cela. Il permet de déverrouiller ce que le manifeste ne fait pas.
caw
@Escobar Ceaser Quelle est la bonne solution à cette question, même si j'ai la même exigence.
Prabs
Je voudrais faire cela par programmation dans le code.
pollaris le

Réponses:

249

Il existe généralement trois façons de procéder:

  1. Comme certaines réponses le suggèrent, vous pouvez distinguer les cas où votre activité est créée pour la première fois et à partir de laquelle elle est restaurée savedInstanceState. Cela se fait en remplaçant onSaveInstanceStateet en vérifiant le paramètre de onCreate.

  2. Vous pouvez verrouiller l'activité dans une orientation en ajoutant android:screenOrientation="portrait"(ou "landscape") à <activity>dans votre manifeste.

  3. Vous pouvez indiquer au système que vous avez l'intention de gérer vous-même les changements d'écran en spécifiant android:configChanges="orientation|screenSize"dans l' <activity>étiquette. De cette façon, l'activité ne sera pas recréée, mais recevra un rappel à la place (que vous pouvez ignorer car cela ne vous est pas utile).

Personnellement, j'irais avec (3). Bien sûr, si le verrouillage de l'application sur l'une des orientations vous convient, vous pouvez également utiliser (2).

Xion
la source
13
Donc, pour le n ° 3, dites-vous que tout ce que j'ai à faire est d'ajouter cette ligne à mon manifeste? Parce que ça ne marche pas.
Jimmy D
2
# 3 Veuillez vérifier sur stackoverflow.com/questions/456211/…
Yeo
16
@EscobarCeaser, pour Android 3.2 et supérieur, vous avez besoin deandroid:configChanges="orientation|screenSize"
Pacerier
9
android:configChanges="orientation|screenSize"travaille pour moi. Merci @Pacerier
Don Larynx
1
s'il vous plaît, mettez à jour votre cas de réponse n ° 3 avec une android:configChanges="orientation|screenSize"valeur pour l'API> = 13, car beaucoup de gens considèrent votre réponse comme principale!
radistao le
215

La réponse de Xion était proche, mais # 3 ( android:configChanes="orientation") ne fonctionnera que si l'application a un niveau d'API de 12 ou moins.

Au niveau d'API 13 ou supérieur, la taille de l'écran change lorsque l'orientation change, ce qui entraîne toujours la destruction de l'activité et le démarrage lorsque l'orientation change.

Ajoutez simplement l'attribut "screenSize" comme je l'ai fait ci-dessous:

<activity
    android:name=".YourActivityName"
    android:configChanges="orientation|screenSize">
</activity>

Désormais, lorsque vous changez d'orientation (et que la taille de l'écran change), l'activité conserve son état et onConfigurationChanged()est appelée. Cela conservera tout ce qui est à l'écran (par exemple: page Web dans une vue Web) lorsque l'orientation change.

J'ai appris cela sur ce site: http://developer.android.com/guide/topics/manifest/activity-element.html

De plus, c'est apparemment une mauvaise pratique, alors lisez le lien ci-dessous sur la gestion des changements d'exécution:

http://developer.android.com/guide/topics/resources/runtime-changes.html

corbin
la source
2
Merci ... son travail après avoir ajouté "screenSize" avec "orientation"
Pratik Butani
Fonctionne dans Samsung Galaxy Nexus android 4.2.1! android:configChanges="orientation|screenSize"
Vincent Ducastel
Incroyable. J'ai travaillé sur du code pendant tant d'heures pour résoudre un problème que j'avais avec le rechargement de l'activité et une vidéo commençant depuis le début. Et voici la solution! ++++ 1
Mathias Asberg
6
Mauvaise pratique? Pfft, les gens de la vraie vie ont des délais et si ça marche, ça marche;)
Kacy
Si c'est une mauvaise pratique, pourquoi a-t-elle reçu autant de votes positifs?
Sharp Edge
26

Il vous suffit d'aller dans les AndroidManifest.xmlétiquettes et à l'intérieur ou dans vos activités, vous devez taper cette ligne de code comme quelqu'un l'a dit:

android:configChanges="orientation|screenSize"

Donc, vous aurez quelque chose comme ça:

<activity android:name="ActivityMenu"
android:configChanges="orientation|screenSize">
</activity>

Esperons que ça marche!

Josue Rocha
la source
son ne charge pas ma mise en page de terrain. : (n'a pas fonctionné pour moi
piyush poriya
16
<activity android:name="com.example.abc" 
 android:configChanges="orientation|screenSize"></activity>

Ajoutez simplement l' android:configChanges="orientation|screenSize"onglet d'activité du fichier manifeste.

Ainsi, l'activité ne redémarrera pas lorsque l'orientation changera.

Aiyaz Parmar
la source
Ça marche. Mais lorsque j'utilise une mise en page distincte pour chaque orientation, layout.xml et layout-land.xml. son application de mise en page paysage pour les deux orientations. Si j'utilise uniquement "orientation", ça donne ce que j'attends mais en rechargeant. Pourriez-vous nous aider?
Karthikeyan Ve
1
@KarthikeyanVe C'est le problème lorsque vous essayez de tricher. Vous devez redémarrer votre activité à la mise en page de changement. Allez-y et utilisez simplement la vraie solution, qui utilise onSaveInstanceState()et onCreate().
Marc Plano-Lesay
@ MarcPlano-Lesay et comment suis-je supposé faire ça?
Ahsan
@Weaboo la solution actuelle est liée à la question: developer.android.com/guide/topics/resources/…
Marc Plano-Lesay
@ MarcPlano-Lesay J'ai une mise en page séparée pour le mode portrait et paysage, si j'ouvre mon application en mode paysage ou portrait, cela fonctionne bien, mais chaque fois que j'essaye de changer d'orientation au moment de l'exécution, cela ferme mon application, mais lorsque je me connecte à mon application puis accédez à MainActivity et essayez de changer d'orientation, il recharge cette activité et fonctionne correctement. Maintenant, la question est pourquoi? Y a-t-il une erreur logique dans mon code? Idk, mais j'ai essayé plusieurs fois de déboguer l'application et je ne trouve rien. De plus, je ne veux pas redémarrer mon activité, pourquoi ne pouvons-nous pas simplement adapter la mise en page respective chaque fois que la configuration change?
Ahsan
10

D'après mon expérience, il est en fait préférable de gérer correctement les changements d'orientation au lieu d'essayer de mettre en place un comportement non par défaut.

Vous devez enregistrer l'image actuellement affichée onSaveInstanceState()et la restaurer correctement lorsque votre application s'exécute à onCreate()nouveau.

dmon
la source
# 3 est une solution parfaitement valable. C'est l' outil exact conçu pour résoudre ce problème exact. Pourquoi dites-vous que c'est du cirage de chaussures?
Pacerier
1
@Pacerier Il suffit de lire la documentation. "Remarque: l'utilisation android:configChangesdoit être évitée et utilisée uniquement en dernier recours. Veuillez lire Gestion des modifications à l'exécution pour plus d'informations sur la manière de gérer correctement un redémarrage en raison d'un changement de configuration."
Marc Plano-Lesay
Pourriez-vous poster un exemple de sauvegarde et de restauration.
pollaris le
6

Cette solution est de loin la meilleure qui fonctionne. Dans votre fichier manifeste, ajoutez

<activity
    android:configChanges="keyboardHidden|orientation|screenSize"
    android:name="your activity name"
    android:label="@string/app_name" 
    android:screenOrientation="landscape">
  </activity

Et dans votre classe d'activité, ajoutez le code suivant

@Override
public void onConfigurationChanged(Configuration newConfig) 
{
    super.onConfigurationChanged(newConfig);
    if (newConfig.orientation == Configuration.ORIENTATION_PORTRAIT) {
        //your code
    } else if (newConfig.orientation == Configuration.ORIENTATION_LANDSCAPE) {
  //your code

    }
}
Un Raj
la source
4

ajouter android:configChanges="keyboardHidden|orientation|screenSize"pour toutes les balises d' activités d'application dans le manifeste.

Oubaida AlQuraan
la source
3

Ajoutez simplement ceci à votre AndroidManifest.xml

<activity android:screenOrientation="landscape">

Je veux dire, il y a une balise d'activité, ajoutez ceci comme un autre paramètre. Si vous avez besoin d'une orientation portrait, changez le paysage en portrait. J'espère que cela t'aides.

Egor
la source
Je ne cherche pas à enlever la possibilité de faire pivoter l'écran. Je ne veux tout simplement pas que mon application se recharge ... comme je l'ai mentionné.
Jimmy D
ps ... cela ne fonctionne pas de toute façon. cela force simplement l'application à s'afficher dans une certaine orientation. la rotation de l'écran recharge toujours l'activité
Jimmy D
3

Dans le fichier le plus important, ajoutez à chaque activité ceci. CA aidera

android:configChanges = "orientation|keyboard|keyboardHidden|screenLayout|screenSize"
Jevgenij Kononov
la source
screenLayout a fonctionné pour moi, a empêché l'actualisation lors du redimensionnement de l'application pour l'écran
partagé
2

Toutes les réponses ci-dessus ne fonctionnent pas pour moi. Donc, j'ai corrigé en mentionnant le labelavec screenOrientationcomme ci-dessous. Maintenant tout va bien

<activity android:name=".activity.VideoWebViewActivity"
        android:label="@string/app_name"
        android:configChanges="orientation|screenSize"/>
Bahu
la source
1

Enregistrez les détails de l'image dans votre onPause()ou onStop()et utilisez-le dans onCreate(Bundle savedInstanceState)pour restaurer l'image.

ÉDITER:

Plus d'informations sur le processus réel sont détaillées ici http://developer.android.com/reference/android/app/Activity.html#ActivityLifecycle car il est différent dans Honeycomb des versions précédentes d'Android.

techiServices
la source
en fait, vous devriez le faire dans la méthode onSaveInstanceState ()
Willi Mentzel
1

utilisez simplement: android:configChanges="keyboardHidden|orientation"

Masoud Banimahd
la source
1

Comme Pacerier l'a mentionné,

android:configChanges="orientation|screenSize"

Don Larynx
la source
-1

Je ne sais pas si la meilleure solution, mais je la décris ici:

Tout d'abord, vous avez besoin d'un certificat avec votre classe.L'application de votre application est dans votre manifeste de ceci:

<application
    android:name=".App"
    ...

Deuxièmement, dans mon application de classe, j'ai aimé ceci:

public class App extends Application {
    public static boolean isOrientationChanged = false;

    @Override
    public void onCreate() {
        super.onCreate();
    }

    @Override
    public void onConfigurationChanged(@NotNull Configuration newConfig) {
        super.onConfigurationChanged(newConfig);
        if (newConfig.orientation == Configuration.ORIENTATION_LANDSCAPE ||
                newConfig.orientation == Configuration.ORIENTATION_PORTRAIT) {
            isOrientationChanged = true;
        }
    }

}

Troisièmement, vous devez définir un indicateur sur Changement d'orientation.Dans mon cas, je le définit toujours lorsque l'activité précédente dans la navigation de l'application est appelée, donc n'appelant qu'une seule fois lorsque l'activité ultérieure est créée.

isOrientationChanged = false;

Ainsi, chaque fois que je change l'orientation de mon écran dans ce contexte, je le règle à chaque fois qu'il change ce paramètre, il vérifie s'il y a un changement d'orientation, si c'est le cas, il le valide en fonction de la valeur de cet indicateur.

En gros, je devais l'utiliser chaque fois que je faisais une demande de mise à niveau asynchrone, qu'il appelait à chaque instant qui changeait d'orientation, bloquant constamment l'application:

if (!isOrientationChanged) {
    presenter.retrieveAddress(this, idClient, TYPE_ADDRESS);
}

Je ne sais pas si c'est la solution la plus élégante et la plus belle, mais au moins ici, c'est fonctionnel :)

michel566
la source
-2

Ajoutez ce code après la onCreateméthode, dans votre activité contenant leWebView

@Override
protected void onSaveInstanceState(Bundle outState) {
    super.onSaveInstanceState(outState);    
}

@Override
protected void onRestoreInstanceState(Bundle state) {
    super.onRestoreInstanceState(state);    
}
Amir Aslam
la source
1
Comment cela fonctionnerait-il? N'êtes-vous pas simplement en train de dire quelque chose de manière explicite au runtime, qu'est-ce qui serait autrement fait par défaut?
Danielson