Voyage entre les Intent
Voyage entre les Intent
Les Activités et les Intent
Nous avons vue que les vues étaient appelées des activités en Android. Afin d’ouvrir une nouvelle activité et transférer des information d’une activité à l’autre nous allons avoir besoin des Intent
qui vont permettre de faire naviguer des informations d’une vue à l’autre.
Nous allons faire une simple application qui dans un premier temps ouvrira une deuxième activité au clique sur un bouton et dans un deuxième temps nous verrons comment envoyer un message sur la deuxième activité puis enfin renvoyer une réponse sur la première.
C’est partie
De la manière que nous l’avons fait créons un projet nommé DeuxActivites.
Dans activity_main.xml
enlevez le TextView et ajoutez un bouton à qui on donnera le nom button_main
<Button
android:id="@+id/button_main"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/button_main"
android:layout_marginBottom="16dp"
android:layout_marginRight="16dp"
android:onClick="launchSecondActivity"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintRight_toRightOf="parent"
/>
Pensez bien à renvoyer le text dans strings.xml
. Pour le moment est souligné en rouge car la méthode n’existe pas. A l’aide de l’ampoule rouge créez la méthode dans MainActivity.java
.
Dans MainActivity.java
ajoutez Log.d(LOG_TAG,"clique sur bouton");
dans la méthode launchSecondActivity()
et ajoutez private static final String LOG_TAG = MainActivity.class.getSimpleName();
en haut de la classe.
Exécutez votre appli. Si tout se déroule bien au clique sur le bouton vous devriez lire dans l’onglet run en bas de l’IDE
D/MainActivity: clique sur bouton
la méthode log est l’équivalent en Java du println que nous utilisons pour faire des impressions en console. La grosse différence est que nous signons nos événements par une String.
Créons la seconde activité
Pour android, il ya deux façons de faire du lien entre les activités:
- explicite: nous connaissons déjà la classe cible de l’intent.
- implicite: nous ne connaissons pas nécessairement le nom de la cible mais nous avons une action générale à effectuer.
Cliquez droit sur le dossier app puis new -> activity -> Empty Activity et nommez la nouvelle activité SecondActivity
.
Dans AndroidManifest nous définissons plus précisément notre activité. Ces information seront utilisées pour afficher la navigation en haut dans la barre de navigation.
dans la Manifest remplacez
<activity android:name=".SecondActivity"></activity>
par
<activity
android:name=".SecondActivity"
android:label="Seconde Activité"
android:parentActivityName=".MainActivity">
</activity>
Puis extrayez le label dans strings.xml
Petite mise en page
dans activity_second.xml
faite la mise en page suivante en ajoutant un TextView
<TextView
android:id="@+id/text_header"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="16dp"
android:layout_marginStart="8dp"
android:text="Message reçu"
android:textAppearance="@style/TextAppearance.AppCompat.Medium"
android:textStyle="bold"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"/>
Définissons l’Intent
Enfin dans MainActivity.java
créez l'intent dan la méthode launchSecondActivity()
L'intent
prend deux paramètres, le context
et la classe de l’activité à charger.
Intent intent = new Intent(this, SecondActivity.class);
Il faut ensuite démarrer l’activité: startActivity(intent);
Vous pouvez maintenant lancer votre activité.
Envoyons un message (partie 2)
Notre objet d’intention peut transmettre des données à l’activité cible de deux manières: dans le champ de données ou dans les extras d' intention . Les données d’intention sont un URI indiquant les données spécifiques sur lesquelles agir. Si les informations que vous souhaitez transmettre à une activité via une intention ne sont pas un URI, ou si vous avez plusieurs informations à envoyer, vous pouvez mettre ces informations supplémentaires dans les extras à la place.
Les extras d' intention sont des paires clé / valeur dans un Bundle (paquet). Un Bundle
est une collection de données, stockées sous forme de paires clé / valeur. Pour transmettre des informations d’une activité à une autre, vous mettez des clés et des valeurs dans l’extra de l’intention de l’activité d’envoi, puis vous les récupérez dans l’activité de réception.
Commencez par ajouter un EditText
à notre premier layout et nommez le edit_text_message
les indications du champ text sont dans l’attribut
android:hint=" ... "
Définissez la clé “Extra” de l’intent et l'EditText
en haut de la classe MainActivity
public static final String EXTRA_MESSAGE = "deuxActivite.extra.MESSAGE";
private EditText mEditTextMessage;
Dans la méthode onCreate()
on va récupérer notre EditText:
mEditTextMessage = findViewById(R.id.edit_text_message);
Et dans la méthode launchSecondActivity()
on va créer notre message “extra” et l’ajouter à l’intent
String message = mEditTextMessage.getText().toString();
Intent intent = new Intent(this, SecondActivity.class);
intent.putExtra(EXTRA_MESSAGE,message);
startActivity(intent);
De l’autre côté
Dans activity_second.xml
ajoutez un TextView
afin de pouvoir répondre. Nommez le text_message
Dans SecondActivity.java
, dans la méthode onCreate(), récupérons notre intent ainsi que son contenu et mettons le dans le TextView:
Intent intent = getIntent();
String message = intent.getStringExtra(MainActivity.EXTRA_MESSAGE);
TextView textView = findViewById(R.id.text_message);
textView.setText(message);
Vous pouvez tester votre appli.
Le sens retour (Partie 3)
Nous allons maintenant faire le sens retour. Ajoutons un champ EditText
et un Button
à notre second layout (activity_second.xml
).
Vous pouvez simplement copier coller les deux éléments de la première activité et corriger les id et actions pour obtenir ceci:
<Button
android:id="@+id/button_second"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginEnd="16dp"
android:layout_marginBottom="16dp"
android:onClick="returnReply"
android:text="@string/repondre"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintRight_toRightOf="parent" />
<EditText
android:id="@+id/edit_text_reponse"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginEnd="8dp"
android:layout_marginBottom="16dp"
android:ems="10"
android:hint="@string/entrez_votre_reponse"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toStartOf="@+id/button_second"
app:layout_constraintHorizontal_bias="0.0"
app:layout_constraintStart_toStartOf="parent"
android:inputType="text" />
Attention ✋ : j’ai intégré les textes dans
strings.xml
votre strings.xml doit ressembler à :<resources> <string name="app_name">DeuxActivites</string> <string name="button_main">Envoyer</string> <string name="activity2_name">Seconde Activité</string> <string name="message_recu">Message reçu</string> <string name="entrez_votre_message">Entrez votre message</string> <string name="repondre">Répondre</string> <string name="entrez_votre_reponse">Entrez votre réponse</string> </resources>
D’ailleurs ce fichier est essentiel si on veut traduire notre application mais on verra ça plus tard.
Dans notre contrôleur nous allons ajouter un Intent
et son extra ainsi que l’action à effectuer:
public class SecondActivity extends AppCompatActivity {
private static final String EXTRA_REPLY = "deuxActivite.extra.REPLY";
private EditText mReply;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_second);
// reception du message du main
Intent intent = getIntent();
String message = intent.getStringExtra(MainActivity.EXTRA_MESSAGE);
TextView textView = findViewById(R.id.text_message);
textView.setText(message);
mReply = findViewById(R.id.edit_text_reponse);
}
public void returnReply(View view) {
// récupération de la réponse de l'utilisateur
String reply = mReply.getText().toString();
// Instanciation d'un nouvel intent
Intent replyIntent = new Intent();
replyIntent.putExtra(EXTRA_REPLY,reply);
// mise à jour de l'état de la réponse
setResult(RESULT_OK,replyIntent);
// on termine l'activité 2
finish();
}
}
Attention ✋ : Vous remarquerez que l’on instancie un nouvel
Intent
et que nous terminons l’activité avecfinish()
Il nous reste à recevoir la réponse
Ajoutez le Textview
pour la réponse par copié collé et modification adéquate.
Vous devriez obtenir le xml suivant à ajouter dans activity_main.xml
:
<TextView
android:id="@+id/text_header_reply"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="16dp"
android:layout_marginStart="8dp"
android:text="@string/reponse_de_la_2eme_vue"
android:textAppearance="@style/TextAppearance.AppCompat.Medium"
android:textStyle="bold"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"/>
<TextView
android:id="@+id/text_message_reply"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/reponse_vue2"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/text_header_reply"/>
Remarque: ne copiez pas mon code et essayer de faire la manipulation vous même.
Modifiez la visibilité des deux TextView
en ajoutant l’attribut android:visibility="invisible"
à chacun d’eux. Ainsi ces textes ne s’afficherons que quand on aura fait notre passage par la deuxième vue.
Dernière chose à faire…
Déclarons et activons tout ça dans le MainActivity.java
Les déclarations d’usage maintenant en haut de notre classe:
private TextView mReplyHeadTextView;
private TextView mReplyTextView;
public static final int TEXT_REQUEST = 1;
en haut de notre classe et une nouveauté TEXT_REQUEST
(suspens…)
mReplyHeadTextView = findViewById(R.id.text_header_reply);
mReplyTextView = findViewById(R.id.text_message_reply);
Dans la méthode onCreate()
.
Modifiez la méthode de lancement de l’activité de startActivity(intent)
en startActivityForResult(intent,TEXT_REQUEST);
.
Maintenant surchargeons la méthode onActivityResult
avec nos conditions. C’est elle qui va récupérer notre réponse s’il y en a une et afficher le message.
@Override
protected void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == TEXT_REQUEST) {
if (resultCode == RESULT_OK) {
String reply = data.getStringExtra(SecondActivity.EXTRA_REPLY);
mReplyHeadTextView.setVisibility(View.VISIBLE);
mReplyTextView.setText(reply);
mReplyTextView.setVisibility(View.VISIBLE);
}
}
Et c’est tout! Maintenant, si vous lancez l’application vous devez pouvoir faire voyager des messages d’un côté à l’autre ☕.