Creare un widget orologio personalizzato implementazione della configurazione utente

Lo sviluppo di widget per la piattaforma Android comporta un insieme leggermente diverso di compiti rispetto allo sviluppo di app standard. In questa serie di tutorial, lavoreremo attraverso il processo di sviluppo di un widget orologio analogico personalizzabile. L'orologio sarà basato sulla classe Android AnalogClock e personalizzato con la tua grafica.

Finora in questa serie, abbiamo progettato e implementato il widget in XML e Java e abbiamo un widget orologio funzionante che l'utente può aggiungere alla sua schermata iniziale. In questa parte finale della serie, implementeremo la configurazione utente di base. Nella parte 2 abbiamo creato più progetti di clock, quindi ora consentiremo all'utente di scegliere tra di essi.

Questa è la parte 4 di 4 di una serie sulla creazione di un widget orologio analogico Android personalizzabile in quattro esercitazioni:

  • Impostazione del progetto Android Widget
  • Progettare l'orologio
  • Ricezione di aggiornamenti e avvio
  • Implementazione della configurazione utente

Costruire la configurazione utente nella nostra app di widget coinvolgerà una nuova classe di attività Java, presentando la selezione di scelte all'utente. Quando l'utente seleziona un disegno, aggiorneremo l'aspetto del widget e memorizzeremo la scelta dell'utente in Preferenze condivise dell'applicazione. Estenderemo anche la classe widget per gestire i clic dell'utente sul widget e leggere le Preferenze condivise a scelta dell'utente. Oltre a lavorare con questi due file Java, creeremo un nuovo file di valori e un file di layout XML per la scelta Attività insieme ad alcune immagini da mostrare al suo interno.


Passaggio 1: gestisci i clic sui widget

Innanzitutto, aggiungiamo del codice alla classe del widget per rilevare i clic dell'utente. Nella classe "ClockWidget", all'interno dell'istruzione "if" nel metodo "onReceive", dopo la riga in cui è stato richiamato l'oggetto Visualizzazioni remote, aggiungere il codice seguente per creare un Intento per l'attività di selezione che si intende utilizzare:

 Intent choiceIntent = new Intent (context, ClockChoice.class);

Non preoccuparti per gli errori di Eclipse per ora, scompariranno quando creeremo la nuova classe di attività nel passaggio successivo. Dopo questa riga, crea un In sospeso come segue:

 PendingIntent clickPendIntent = PendingIntent.getActivity (context, 0, choiceIntent, PendingIntent.FLAG_UPDATE_CURRENT);

L'avvio delle attività sui clic del widget è un po 'diverso, come puoi vedere. Si noti che passiamo l'oggetto Context e un riferimento al nuovo Intent. Ora aggiungi il codice seguente specificando che l'In attesa di inclusione deve essere avviato quando si fa clic sul widget:

 views.setOnClickPendingIntent (R.id.custom_clock_widget, clickPendIntent);

Specifichiamo il widget facendo riferimento all'ID del layout principale nel file XML "clock_widget_layout". Abbiamo bisogno di utilizzare le viste remote per fare riferimento agli elementi dell'interfaccia utente in quanto siamo in una classe di widget piuttosto che in una classe di attività. Aggiungeremo più codice a questa classe in seguito.


Passaggio 2: creare un'attività di selezione

Ora per l'attività in cui lasciamo che gli utenti scelgano un design. Crea una nuova classe nel tuo progetto facendo clic destro o selezionando la cartella del pacchetto sorgente e scegliendo "File", quindi seleziona "Nuovo", "Classe" e inserisci "ClockChoice" come nome della classe. Eclipse aprirà la nuova classe quando fai clic su Fine. Ricorda che abbiamo incluso questa attività nel file Manifest del progetto nella Parte 1.

Rendi la tua nuova lezione un'attività e una che gestirà i clic degli utenti estendendo la sua linea di apertura come segue:

 public class ClockChoice estende Activity implements OnClickListener 

Ancora una volta, ignora qualsiasi messaggio di errore, appariranno finché non forniremo il metodo "onClick". Avrai bisogno delle seguenti dichiarazioni di importazione:

 importare android.app.Activity; import android.view.View.OnClickListener;

Fornire il metodo di attività "onCreate" all'interno della classe come segue:

 public void onCreate (Bundle savedInstanceState) super.onCreate (savedInstanceState); setContentView (R.layout.clock_choice); 

Creeremo il file di layout nel passaggio successivo. Avrai bisogno di un'altra importazione:

 importare android.os.Bundle;

Aggiungeremo più codice a questa classe in seguito.


Passaggio 3: Progettazione attività del selettore

Creiamo il layout che abbiamo specificato nella classe Attività sopra. Crea un nuovo file di layout facendo clic con il pulsante destro del mouse o selezionando la cartella "res / layout" e scegliendo "File", quindi facendo clic su "Nuovo", "File" e inserendo "clock_choice.xml" in modo che corrisponda al riferimento nel codice precedente.

Quando Eclipse apre il file, seleziona la scheda "clock_choice.xml" per modificare il codice. Inserisci il seguente schema di layout nel tuo file:

    

Il design include un layout lineare all'interno di una vista di scorrimento. All'interno del layout lineare, per prima cosa aggiungi del testo informativo come segue:

 

Aggiungi la risorsa String indicata qui al tuo file "strings.xml" - assicurandoti di includerla in entrambe le copie del file delle stringhe, in "valori" e "valori-v14":

 Scegliere un'opzione:

Ora mostreremo un'immagine per rappresentare ogni orologio. Queste immagini fungeranno da pulsanti per gli utenti da premere quando si seleziona un disegno. Crea le tue immagini ora, ricordando di includere diverse versioni per ogni densità. Se non vuoi ancora crearne uno, puoi utilizzare le immagini nel link di download nella parte inferiore del tutorial - qui ci sono le versioni a media densità di ciascuna:

Salva ogni versione delle tue immagini nelle cartelle disegnabili per la tua app, ricordando di usare gli stessi nomi in ogni cartella di densità.

Ora torna al file XML di layout "clock_choice". Aggiungi un pulsante Immagine per ogni disegno che stai utilizzando, con il seguente per i tre disegni di esempio che abbiamo utilizzato, dopo la visualizzazione del testo:

   

Ci sono diversi punti da notare qui. Prima di tutto, nota che ogni pulsante Image ha un ID con la stessa sintassi ma un intero incrementale alla fine - lo useremo per scorrere i disegni in Java, quindi se includi più di tre design, assicurati di assegnarli iterando numeri, ad esempio "design_3" ecc. Oltre agli attributi di progettazione, ogni elemento indica anche la risorsa drawable pertinente, quindi modificali se i file di immagine appena creati hanno nomi diversi. Infine, gli attributi della descrizione del contenuto si riferiscono alle risorse stringa, quindi aggiungili ai file "strings.xml" in entrambe le cartelle "values" e "values-v14" come segue:

 Design predefinito Design in pietra Design in metallo

Modificare queste descrizioni se necessario per adattarle ai propri progetti.

Facciamo uso di temi Android per automatizzare alcuni aspetti dell'aspetto dell'attività di Chooser. Aprire il file Manifest del progetto ed estendere l'elemento che rappresenta il selettore di clock Attività come segue:

  

Aggiungendo il tema del dialogo, l'attività viene visualizzata sovrapposta alla schermata iniziale - questo è il suo aspetto con i disegni di esempio che abbiamo utilizzato in questa serie di tutorial:


Questo è ciò che apparirà quando l'utente fa clic sul widget. Se il display del dispositivo è troppo piccolo per ospitare tutti e tre i progetti, scorrerà mentre il layout utilizza una Vista di scorrimento. Quando l'utente seleziona un disegno, l'aspetto del widget si aggiornerà e questa scelta Attività scomparirà.

Inutile dire che potresti voler modificare il numero di possibili disegni all'interno dell'app del tuo orologio. Per semplificare questo processo, faremo in modo che il nostro codice Java legga dinamicamente il numero di progetti. A tal fine, useremo un valore numerico per tenere traccia del numero di progetti che stiamo utilizzando. Creare un nuovo file in ciascuna delle due cartelle dei valori, fare clic con il pulsante destro del mouse o selezionare ogni cartella a turno e scegliere "File", quindi "Nuovo", "File" e inserire "numbers.xml" come nome del file.


Seleziona la scheda "numbers.xml" e inserisci il seguente codice nel tuo nuovo file:

  3 

Modificare il numero se si è utilizzato un numero diverso di disegni, assicurandosi che il valore corrisponda al numero di pulsanti immagine inclusi nel layout e al numero di elementi di orologio analogico presenti nel layout del widget. Ricorda che hai bisogno di una copia del file "numbers.xml" in entrambe le cartelle dei valori, quindi copia e incolla se necessario.

Se modifichi il numero di disegni che stai utilizzando in qualsiasi momento, devi modificare il valore nei file "numbers.xml", aggiungere ciascun disegno come un elemento Analog Clock nel file "clock_widget_layout" dell'app e un Pulsante Immagine per ciascun disegno nel file di selezione delle attività del selettore.


Passaggio 4: gestire la scelta dell'utente

Gestiamo l'interazione dell'utente con la selezione dei design di clock. Apri il tuo file di attività "ClockChoice". All'interno della classe, prima del metodo "onCreate", aggiungi le seguenti variabili di istanza:

 // numero di disegni private int numDesigns; // pulsanti immagine per ogni disegno privato ImageButton [] designBtns; // identificatori per ciascun elemento di clock int [] design;

Useremo queste variabili per scorrere tra i vari disegni. Aggiungi un'altra importazione:

 import android.widget.ImageButton;

All'interno del metodo "onCreate", dopo il codice esistente, creare un'istanza della variabile per tenere traccia del numero di disegni di clock, come segue:

 numDesigns = this.getResources (). getInteger (R.integer.num_clocks);

Qui recuperiamo il valore nel file XML di numeri che abbiamo creato in precedenza: saremo in grado di utilizzare questo valore come riferimento durante l'iterazione dei progetti. Successivamente istanziare gli array per i pulsanti di progettazione e gli elementi di clock:

 designBtns = new ImageButton [numDesigns]; designs = new int [numDesigns];

Il primo array si riferirà ai pulsanti immagine che stiamo usando all'interno di questa attività selettore per rilevare la scelta dell'utente. Il secondo array memorizzerà i riferimenti agli elementi di Analog Clock per ciascun disegno nel file di layout del widget stesso.

Ora aggiungi un ciclo per scorrere i disegni:

 per (int d = 0; d 

All'interno del ciclo, recuperare un riferimento a ciascun elemento Orologio analogico nel layout del widget:

 designs [d] = this.getResources (). getIdentifier ("AnalogClock" + d, "id", getPackageName ());

Se guardi indietro al file "clock_widget_layout", vedrai che ogni elemento Analog Clock ha un ID che comprende "AnalogClock" seguito da un intero incrementale - lo usiamo qui per recuperare un riferimento a ciascuno usando il contatore di loop. Successivamente, sempre all'interno del ciclo, recuperare i valori ID per i pulsanti Immagine nel layout Attività del selettore:

 designBtns [d] = (ImageButton) findViewById (this.getResources (). getIdentifier ("design _" + d, "id", getPackageName ()));

Qui stiamo usando "findViewById" per ottenere un riferimento al relativo elemento Image Button, passando l'ID, che comprende "design_" seguito dal numero intero incrementale. Ora imposta il listener dei clic per ciascuno di questi pulsanti in modo che possiamo gestire i clic in questa classe di attività. Mentre sei ancora dentro il ciclo:

 designBtns [d] .setOnClickListener (questo);

Ora possiamo andare avanti con il metodo click per i pulsanti di progettazione. Dopo il metodo "onCreate" nella classe "ClockChoice", aggiungi un metodo "onClick" come segue:

 public void onClick (Visualizza v) 

Aggiungi la seguente importazione:

 importa android.view.View;

Nel metodo "onClick", dobbiamo prima determinare quale pulsante l'utente ha premuto. Aggiungi il seguente ciclo all'interno del metodo per questo scopo:

 int scelto = -1; per (int c = 0; c 

Qui controlliamo l'ID vista cliccato rispetto agli ID che abbiamo archiviato nell'array del pulsante Immagine. Quando il ciclo termina, l'indice scelto viene memorizzato in una variabile locale. Dopo il ciclo memorizza un riferimento all'ID per l'elemento Analog Clock selezionato:

 int pickedClock = progetta [scelto];

Ora abbiamo bisogno di ottenere un riferimento agli elementi del layout del widget, per i quali abbiamo bisogno delle Remote Views, passando il layout del widget come riferimento:

 RemoteViews remoteViews = new RemoteViews (this.getApplicationContext (). GetPackageName (), R.layout.clock_widget_layout);

Per questo hai bisogno di un'altra dichiarazione di importazione:

 importare android.widget.RemoteViews;

Ricorda che abbiamo incluso ogni disegno di Analog Clock nel file di layout del widget - questo perché non possiamo alterare dinamicamente gli attributi di un orologio analogico come i drawable per il quadrante e le mani, quindi includiamo invece tutti i disegni e tutti i set ma uno per essere invisibile. Prima di impostare il design del clock scelto in modo che sia visibile, imposteremo gli altri come invisibili, che possiamo fare in un loop come segue:

 per (int d = 0; d 

Usiamo la matrice in cui abbiamo memorizzato i valori dell'ID dell'elemento Analog Clock per impostare ognuno di essi invisibile finché non è quello scelto. Ora possiamo impostare il design scelto per essere visibile, dopo questo ciclo:

 remoteViews.setViewVisibility (pickedClock, View.VISIBLE);

Ora, poiché questa è un'app di widget, è necessario aggiornare l'aspetto del widget come segue:

 // ottiene il nome del componente per la classe del widget ComponentName comp = new ComponentName (this, ClockWidget.class); // trova l'app AppWidgetManager AppWidgetManagerWidgetManager = AppWidgetManager.getInstance (this.getApplicationContext ()); // aggiorna appWidgetManager.updateAppWidget (comp, remoteViews);

Questo è simile al modo in cui abbiamo aggiornato il widget nella classe del provider di widget, ma con un paio di passaggi di elaborazione aggiuntivi perché siamo in una classe di attività qui. Dovrai aggiungere queste importazioni:

 import android.appwidget.AppWidgetManager; import android.content.ComponentName;

Ora l'aspetto del widget verrà aggiornato in base alla scelta dell'utente.


Passaggio 5: aggiorna le preferenze condivise

Successivamente, utilizzeremo l'applicazione Preferenze condivise per archiviare la scelta progettuale dell'utente. Eseguire il backup nella parte superiore della classe di attività scelta dell'orologio, aggiungere un'altra variabile di istanza:

 sharedPreferences private clockPrefs;

Ora, alla fine del metodo "onCreate", dopo il codice esistente, aggiungi quanto segue per creare un'istanza della variabile Preferenze condivise:

 clockPrefs = getSharedPreferences ("CustomClockPrefs", 0);

Useremo lo stesso nome di preferenze ogni volta che accediamo ai dati relativi alla scelta dell'utente. Ora spostati verso il basso fino alla fine del metodo "onClick", dopo il codice in cui abbiamo aggiornato il widget. Ottieni l'editor delle preferenze come segue:

 SharedPreferences.Editor custClockEdit = clockPrefs.edit ();

Ora passa i dati riguardanti la scelta dell'utente all'editor e esegui il commit:

 custClockEdit.putInt ("clockdesign", selezionato); custClockEdit.commit ();

Specifichiamo un nome per il valore dei dati e l'ID del progetto scelto. Infine, ancora all'interno di "onClick" aggiungi quanto segue mentre il lavoro dell'Attività è fatto:

 finire();

Passaggio 6: controllare le preferenze condivise

Ora possiamo utilizzare i dati delle preferenze condivise all'interno della classe del widget. Apri la tua classe "ClockWidget", che estende AppWidgetProvider. Gli algoritmi che usiamo qui saranno simili a quelli usati in precedenza per la gestione dei progetti di clock. Aggiungi le seguenti variabili di istanza aggiuntive nella parte superiore:

 // preferenze private SharedPreferences custClockPrefs; // numero di possibili disegni private int numClocks; // ID degli elementi di Clock analogici int [] clockDesigns;

Avrai bisogno della seguente importazione:

 importare android.content.SharedPreferences;

Nel metodo "onReceive", prima il codice esistente, recupera il numero di disegni dalla nostra risorsa valore:

 numClocks = context.getResources (). getInteger (R.integer.num_clocks);

Successivamente istanziare l'array di ID di clock come segue:

 clockDesigns = new int [numClocks];

Ora fai un loop su questo array, impostando ogni elemento come ID per l'elemento Analog Clock relativo nel layout del widget:

 per (int d = 0; d 

Ora spostati sul contenuto dell'istruzione "if" nel metodo "onReceive", dopo la riga in cui abbiamo recuperato le Visualizzazioni remote e prima della riga in cui abbiamo creato l'Intent per la classe di scelta dell'orologio, ottieni le Preferenze condivise e verifica per il valore dei dati impostato per la scelta dell'utente:

 custClockPrefs = context.getSharedPreferences ("CustomClockPrefs", 0); int selectedDesign = custClockPrefs.getInt ("clockdesign", -1);

Il nome delle preferenze condivise e il nome del valore dei dati devono corrispondere a quanto incluso quando si imposta la scelta dell'utente nell'attività di selezione in alto. L'utente potrebbe non aver ancora scelto un design, quindi includere una dichiarazione "if" per verificare:

 if (selectedDesign> = 0) 

All'interno dell'istruzione "if", prima si esegue il ciclo dei disegni, si imposta ogni invisibile se non è il prescelto:

 per (int d = 0; d 

Avrai bisogno di un'altra importazione:

 importa android.view.View;

Ora imposta il design scelto visibile:

 views.setViewVisibility (clockDesigns [selectedDesign], View.VISIBLE);

Ora, quando il widget viene aggiornato, se l'utente ha scelto un disegno, tale disegno verrà visualizzato.


Conclusione

Questo è il widget orologio completato! Puoi eseguirlo su un emulatore o dispositivo per testarlo. Dovrebbe funzionare continuamente, aggiornando il tempo e riflettendo la scelta progettuale dell'utente.


Prenditi un po 'di tempo per guardare indietro sui vari elementi dell'applicazione e assicurati di capire come funzionano insieme l'uno con l'altro. Il processo di sviluppo di qualsiasi altra app per widget comporterà molti degli stessi passaggi. Gli elementi vitali in un'app di widget sono: l'elemento XML "appwidget-provider", il file Manifest, la classe che estende AppWidgetProvider e, naturalmente, gli elementi visivi inclusi layout e risorse.

Se stai cercando di sviluppare ulteriormente le abilità che hai imparato in questa serie, ci sono una serie di opzioni. Se si desidera fornire una configurazione utente avanzata per i propri widget, è possibile utilizzare un'attività delle preferenze insieme all'azione APPWIDGET_CONFIGURE. Se si desidera includere i display dell'orologio digitale insieme alle opzioni analogiche, il processo è un po 'più complesso. È possibile includere la classe Digital Clock predefinita in un'app standard, ma non in un'app widget, quindi è necessario implementare la visualizzazione dell'ora digitale e aggiornarsi autonomamente, utilizzando componenti aggiuntivi quali Servizi e Gestori allarmi.

Sentiti libero di usare il codice sorgente completo e le immagini per questo tutorial fornito nel link per il download.