Passare parametri tra due Activity con Intent espliciti
In questo tutorial approfondiremo il concetto dello scambio di dati tra due Activity. Vedremo come si effettua l'invio di parametri e come si recuperano con java
Così come avviene nel mondo delle pagine web, anche nel mondo Android è possibile inviare dei parametri o dati, ad una Activity o in generale ad un'altra applicazione o componente Android (browser, chiamata telefonica, rubrica etc).
Ogni volta che usi il dispositivo, senza accorgertene, questo accade. Basti pensare ad esempio a quando chiami un numero di telefono. Dopo averlo scritto, invii questo ad una seconda Activity, la quale lo riceverà e inoltrerà la chiamata.
Oppure quando navighi su di una pagina web aprendo il browser dai preferiti, non fai altro che richiamare l'applicazione Browser trasmettendo come parametro il link che intendi aprire.
Oppure quando sei nella tua applicazione social preferita e vuoi condividere un POST, l'applicazione sarà progettata per trasmettere il messaggio a tutte quelle applicazioni, interne al tuo dispositivo, in grado di gestirlo.
Cosa Imparerai
In questo tutorial vedremo come si possano replicare questi comportamenti con i due meccanismi principali che governano lo scambio d'informazioni tra due Activity grazie agli Intent: ossia gli Intent Espliciti e gli Intent Impliciti.
- Le differenze tra Intent Espliciti ed Intent Impliciti
- Come passare dei parametri, in modo esplicito, usando putExtra()
- Come recuperare dei parametri usando getExtras()
Non prendere paura, sono concetti facilmente assimilabili, soprattutto se gli abbini alle azioni che fai ogni giorno con il tuo dispositivo. In questo tutorial in particolare, vedremo di approfondire i primi, che in parte abbiamo già visto in passato.
La distinzione è abbastanza semplice: se sai quale componente o Activity devi chiamare, allora userai un Intent Esplicito, mentre nel caso tu non lo sappia a priori e vuoi che sia il sistema a decidere quale scegliere, pensa all'esempio visto della condivisione di una informazione, allora dovrai usare un Intent Implicito.
Nel primo caso quindi, saremo noi a decidere sia la tipologia di azione che chi dovrà compierla, mentre nel secondo caso, specificheremo solo l'azione, ma non chi dovrà compierla, scelta che farà il sistema sulla base di un meccanismo che adesso vedremo o che dovrai effettuare te, tramite una scelta tra n possibilità.
Vediamo allora in dettaglio, come si usano all'interno delle nostre semplici applicazioni.
Intent Espliciti senza passaggio di parametri
Come dici lo stesso nome, quando vogliamo indicare esplicitamente quale Activity (classe) dovrà ricevere i dati, o quale Activity in generale deve essere richiamata, dovremo usare degli Intent Espliciti.
Il concetto è stato già visto quando abbiamo dovuto aprire una nuova Activity in seguito al tocco eseguito su di un pulsante nella prima Activity (vedi Richiamare un'Activity da un'altra pagina con Intent).
E' proprio lo stesso meccanismo che governa la navigazione tra due pagine web, solo che nel mondo Android le cose sono, ahimè, più laboriose. (Mi verrebbe voglia a volte di scrivere un tutorial su come creare una app in HTML5 e CSS3)
Ipotizzando allora di avere le due pagine/Activity qui sotto, il meccanismo per andare da una Activity all'altra è usare una Intenzione Esplicita, proprio perchè indico in modo Esplicito quale pagina voglio che venga aperta.
Usando allora una variabile di appoggio, che chiamerò "nuovaPagina", potrò scrivere:
Intent nuovaPagina = new Intent(this, Pagina1.class); startActivity(nuovaPagina)
In questo caso gli attori in gioco sono:
- this o getApplicationContext(): I’attuale Activity/Pagina in cui mi trovo
- Pagina1.class : la pagina/Activity a cui voglio arrivare, detta anche Sub-Activity
Il codice mostrato sopra, lo abbiamo già visto in uno dei tutorial precedenti (Richiamare un’activity da un’altra pagina con Intent). Oltre a questo è possibile inviare anche dei parametri, utili per far fare alla seconda Activity o sub-Activity delle operazioni specifiche su questi dati.
Passaggio di parametri/dati tra due Activity con Intent Espliciti
Alla chiamata della nuova Activity, posso anche abbinare dei parametri o dati da passare, esattamente come avviene con GET e POST nelle pagine web, grazie al meccanismo delle query passate come parametri nell'url di una pagina.
Il meccanismo richiede l'uso di un metodo della classe Intent che prende il nome di putExtra() e tipicamente richiede due argomenti: il nome del parametro da passare, quindi sempre una stringa (essendo appunto un nome), e il relativo valore, che puoi essere la classica Stringa o un numero o in generale un oggetto.
Intent nuovaPagina = new Intent(this, Pagina1.class); nuovaPagina.putExtra("NomeDati1", "Valore da passare"); nuovaPagina.putExtra("NomeDati2", "Valore da passare");
Ad esempio se riprendiamo il tutorial sulle ListView, avevamo visto che al tocco sulla singola voce, riuscivamo ad aprire un messaggio in Toast. Ora potremmo aprire al tocco una seconda pagina, quindi richiamare una seconda Activity, passandogli dei dati, che potrò così mostrare in questa.
... mylist.setOnItemClickListener(new AdapterView.OnItemClickListener() { @Override public void onItemClick(AdapterView<?> adattatore, final View componente, int pos, long id){ // recupero il titolo memorizzato nella riga tramite l'ArrayAdapter titoloriga[0] = (String) adattatore.getItemAtPosition(pos); // Log.d("List", "Ho cliccato sull'elemento con titolo" + titoloriga); richiamoPaginaInterna(titoloriga[0]); } }); private void richiamoPaginaInterna(String datopassato) { Intent nuovapagina = new Intent(this, Pagina1.class); nuovapagina.putExtra("Vocecliccata", datopassato); startActivity(nuovapagina); }
Come vedi, ho creato il metodo richiamoPaginaInterna(), passandogli il valore recuperato dalla lista (il titolo), e questo dato lo trasmetterò ad una nuova activity, di nome Pagina1, che potrebbe avere un semplice layout come quello rappresentato qui sotto (activity_page1.xml), che mi servirà per mostrare il dato, ad esempio, all'interno di un campo TextView di nome titolo.
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" > <TextView android:id="@+id/textView" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerHorizontal="true" android:text="Seconda Pagina" android:textAppearance="?android:attr/textAppearanceMedium" /> <TextView android:id="@+id/titolo" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerHorizontal="true" android:layout_marginTop="40dp" android:layout_below="@id/textView" android:text="" android:textAppearance="?android:attr/textAppearanceMedium" /> </RelativeLayout>
Come dicevo, dopo aver inviato i dati, ovviamente, devo avere anche un sistema in grado di riceverli dall'altra parte, ossia dall'Activity Pagina1, a cui arriverò dopo la chiamata.
Ricezione di parametri/dati tra due Activity con Intent Espliciti
Per poter recuperare i dati trasmessi grazie a putExtra() è necessario usare una serie di metodi che ci permetteranno di recuperare, prima di tutto l'Intent che ha trasmesso i dati, e poi il dato stesso, conoscendono il nome, come specificato nel primo parametro del metodo putExtra().
I due metodi che dovrò chiamare per ogni parametro passato dall'Activity chiamante, saranno:
getIntent().getExtras()
NB: Nota la s finale, presente in getExtras(), la quale ci fa capire che con quel metodo recupero tutti i parametri passati.
E se volessi recuperare un singolo parametro specifico tra quelli passati, come dovrò fare?
Sarà necessario aggiungere in coda un altro metodo, in grado di recuperare il dato sulla base del nome che abbiamo deciso di dare ad ognuno dei dati passati, nel nostro caso esattamente NomeDato1 e NomeDato2.
Il metodo in questione è getString("NOMEDATO"), che richiede tra le doppie virgolette proprio il nome del dato, inserito all'interno del metodo putString("").
Pertanto se volessi recuperare in successione i due valori passati all'Activity, dovrei scrivere:
Bundle datipassati = getIntent().getExtras(); String dato1 = datipassati.getString("NomeDati1"); String dato2 = datipassati.getString("NomeDati2");
Oppure, in modo più classico, sfruttando una sola riga:
String dato1 = getIntent().getExtras().getString("NomeDati1"); String dato2 = getIntent().getExtras().getString("NomeDati2");
Nel caso dell'esempio illustrato sopra, dovrei scrivere nell'activity Pagina1, il seguente codice:
public class Pagina1 extends AppCompactActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); // imposto il layout da visualizzare setContentView(R.layout.pagina1); // recupero il campo titolo TextView titolo = (TextView) findViewById(R.id.titolo); // recupero il dato passato String datopassato = getIntent().getExtras().getString("Vocecliccata"); titolo.setText(datopassato); } }
Conclusione
Concludendo, così come accade per le pagine web dinamiche che permettono l'invio di parametri ad un'altra pagina in grado di recuperali e mostrarli, anche nel mondo Android grazie ai metodi putExtra e getExtras() è possibile creare un sistema di scambio di dati tra due Activity, concetto che sta alla base dell'altra tipologia importante di chiamata, ossia l'uso di Intent Impliciti, che forse sono quelli più usati durante lo sviluppo di applicazioni.
2024-12-13 Tipo/Autore: Davide Copelli {ing} Pubblicato da: CorsoAndroid.it