1. Panoramica
Nel codelab precedente, hai utilizzato scorciatoie statiche per implementare intent integrati (BII) di uso comune in un'app di esempio. Gli sviluppatori Android utilizzano Azioni app per estendere la funzionalità dell'app all'Assistente Google.
Le scorciatoie statiche sono incluse in un'app e possono essere aggiornate solo rilasciando nuove versioni dell'app. L'attivazione della funzionalità vocale per gli elementi dinamici di un'app, ad esempio i contenuti generati dagli utenti, viene eseguita utilizzando le scorciatoie dinamiche. Le app inviano scorciatoie dinamiche dopo che gli utenti eseguono azioni pertinenti, ad esempio la creazione di una nuova nota in un'app di monitoraggio delle attività. Con le azioni app, puoi attivare queste scorciatoie per i comandi vocali associandole a un BII, in modo che gli utenti possano accedere ai propri contenuti dall'assistente dicendo, ad esempio, "Hey Google, apri la mia lista della spesa su AppEsempio".
Figura 1. Tre schermate progressive che mostrano un'attività creata dall'utente e l'Assistente Google che lancia una scorciatoia dinamica per l'elemento dell'attività.
Cosa creerai
In questo codelab, abiliterai le scorciatoie dinamiche per la voce in un'app Android con un elenco di cose da fare di esempio, consentendo agli utenti di chiedere all'assistente di aprire gli elementi dell'elenco di attività che creano nell'app. Puoi farlo utilizzando i pattern di architettura Android, in particolare i pattern di repository, service locator e ViewModel.
Prerequisiti
Questo codelab si basa sui concetti delle Azioni app trattati nel codelab precedente, in particolare intent integrati e scorciatoie statiche. Se non hai mai utilizzato le Azioni app, ti consigliamo di completare questo codelab prima di continuare.
Inoltre, prima di procedere, assicurati che l'ambiente di sviluppo abbia la seguente configurazione:
- Un terminale per eseguire i comandi della shell con Git installato.
- L'ultima release stabile di Android Studio.
- Un dispositivo Android fisico o virtuale con accesso a internet.
- Un Account Google con cui è stato eseguito l'accesso ad Android Studio, all'app Google e all'app Assistente Google.
2. Come funziona
L'attivazione di una scorciatoia dinamica per l'accesso vocale prevede i seguenti passaggi:
- Associare una scorciatoia dinamica a un BII idoneo.
- È in corso l'attivazione dell'assistente per importare le scorciatoie aggiungendo la libreria di integrazione delle scorciatoie di Google.
- Inviare una scorciatoia ogni volta che un utente completa l'attività in-app pertinente.
Scorciatoie di associazione
Affinché una scorciatoia dinamica sia accessibile dall'assistente, deve essere associata a un BII pertinente. Quando viene attivato un intent integrato con una scorciatoia, l'assistente associa i parametri nella richiesta dell'utente alle parole chiave definite nella scorciatoia associata. Ad esempio:
- Una scorciatoia associata all'intent integrato
GET_THING
potrebbe consentire agli utenti di richiedere contenuti in-app specifici direttamente dall'assistente. * "Hey Google, apri la mia lista della spesa su ExampleApp." - Una scorciatoia associata all'intent integrato
START_EXERCISE
potrebbe consentire agli utenti di vedere le proprie sessioni di allenamento. * "Hey Google, chiedi ad ExampleApp di avviare il mio solito allenamento."
Per un elenco completo categorizzato di intent integrati, consulta Riferimento per gli intent integrati.
Fornire scorciatoie all'assistente
Dopo aver associato le scorciatoie a un BII, il passaggio successivo consiste nell'abilitare l'assistente a importare queste scorciatoie aggiungendo la libreria Google Shortcuts Integration al progetto. Con questa libreria attiva, l'assistente sarà a conoscenza di ogni scorciatoia inviata dalla tua app, consentendo agli utenti di avviarle usando la frase di attivazione della scorciatoia nell'assistente.
3. Prepara l'ambiente di sviluppo
Questo codelab utilizza un'app di esempio per le liste di cose da fare creata per Android. Con questa app, gli utenti possono aggiungere elementi agli elenchi, cercare elementi degli elenchi di attività per categoria e filtrare le attività in base allo stato di completamento. Scaricare e preparare l'app di esempio completando questa sezione.
Scaricare i file di base
Esegui il comando seguente per clonare il repository GitHub dell'app di esempio:
git clone https://github.com/actions-on-google/app-actions-dynamic-shortcuts.git
Dopo aver clonato il repository, segui questi passaggi per aprirlo in Android Studio:
- Nella finestra di dialogo Ti diamo il benvenuto in Android Studio, fai clic su Importa progetto.
- Seleziona la cartella in cui hai clonato il repository.
In alternativa, puoi visualizzare una versione dell'app di esempio che rappresenta il codelab completato clonando il ramo codelab-complete
del relativo repository GitHub:
git clone https://github.com/actions-on-google/app-actions-dynamic-shortcuts.git --branch codelab-complete
Aggiornare l'ID applicazione Android
L'aggiornamento dell'ID applicazione dell'app identifica in modo univoco l'app sul dispositivo di test ed evita l'errore "Nome pacchetto duplicato" se l'app viene caricata su Play Console. Per aggiornare l'ID applicazione, apri app/build.gradle
:
android {
...
defaultConfig {
applicationId "com.MYUNIQUENAME.android.fitactions"
...
}
}
Sostituisci "MYUNIQUENAME" nel campo applicationId
con un nome univoco.
Aggiungi dipendenze API Shortcuts
Aggiungi le seguenti librerie Jetpack al file di risorse app/build.gradle
:
app/build.gradle
dependencies {
...
// Shortcuts library
implementation "androidx.core:core:1.6.0"
implementation 'androidx.core:core-google-shortcuts:1.0.1'
...
}
Testa l'app sul tuo dispositivo
Prima di apportare altre modifiche all'app, è utile farsi un'idea di cosa può fare l'app di esempio. Per eseguire l'app sull'emulatore, segui questi passaggi:
- In Android Studio, seleziona Esegui > Esegui app o fai clic su Esegui
nella barra degli strumenti.
- Nella finestra di dialogo Seleziona la destinazione del deployment, seleziona un dispositivo e fai clic su OK. La versione del sistema operativo consigliata è Android 10 (livello API 30) o versioni successive, anche se le Azioni app funzionano sui dispositivi fino ad Android 5 (livello API 21).
- Premi a lungo il pulsante Home per configurare l'assistente e verificare che funzioni. Dovrai accedere all'assistente sul tuo dispositivo, se non l'hai ancora fatto.
Per ulteriori informazioni sui dispositivi virtuali Android, vedi Creare e gestire i dispositivi virtuali.
Esplora brevemente l'app per vedere cosa sa fare. Se tocchi l'icona Più, viene creata una nuova voce di attività. Le voci di menu in alto a destra ti consentono di cercare e filtrare le voci delle attività in base allo stato di completamento.
4. Crea una classe di repository di scorciatoie
Diverse classi nella nostra app di esempio chiameranno l'API ShortcutManagerCompat
per eseguire il push e gestire le scorciatoie dinamiche. Per ridurre la ridondanza del codice, implementerai un repository per consentire alle tue classi di progetto di gestire facilmente le scorciatoie dinamiche.
Il pattern di progettazione del repository fornisce un'API chiara per la gestione delle scorciatoie. Il vantaggio di un repository è che i dettagli dell'API sottostante vengono astratti in modo uniforme dietro un'API minima. Implementa il repository seguendo questi passaggi:
- Crea una classe
ShortcutsRepository
per astrarre l'APIShortcutManagerCompat
. - Aggiungi i metodi
ShortcutsRepository
al Service Locator dell'app. - Registra il servizio
ShortcutRepository
nell'applicazione principale.
crea il repository
Crea una nuova classe Kotlin denominata ShortcutsRepository
nel pacchetto com.example.android.architecture.blueprints.todoapp.data.source
. Puoi trovare questo pacchetto organizzato nella cartella app/src/main/java
. Utilizzerai questa classe per implementare un'interfaccia che fornisce un insieme minimo di metodi che coprono il nostro caso d'uso del codelab.
Figura 2. Finestra File del progetto di Android Studio che mostra la posizione della classe ShortcutsRepository.
Incolla il seguente codice nel nuovo corso:
package com.example.android.architecture.blueprints.todoapp.data.source
import android.content.Context
import android.content.Intent
import androidx.annotation.WorkerThread
import androidx.core.content.pm.ShortcutInfoCompat
import androidx.core.content.pm.ShortcutManagerCompat
import com.example.android.architecture.blueprints.todoapp.data.Task
import com.example.android.architecture.blueprints.todoapp.tasks.TasksActivity
private const val GET_THING_KEY = "q"
/**
* ShortcutsRepository provides an interface for managing dynamic shortcuts.
*/
class ShortcutsRepository(val context: Context) {
private val appContext = context.applicationContext
/**
* Pushes a dynamic shortcut. The task ID is used as the shortcut ID.
* The task's title and description are used as shortcut's short and long labels.
* The resulting shortcut corresponds to the GET_THING capability with task's
* title used as BII's "name" argument.
*
* @param task Task object for which to create a shortcut.
*/
@WorkerThread
fun pushShortcut(task: Task) {
// TODO
}
private fun createShortcutCompat(task: Task): ShortcutInfoCompat {
//...
}
/**
* Updates a dynamic shortcut for the provided task. If the shortcut
* associated with this task doesn't exist, this method throws an error.
* This operation may take a few seconds to complete.
*
* @param tasks list of tasks to update.
*/
@WorkerThread
fun updateShortcuts(tasks: List<Task>) {
//...
}
/**
* Removes shortcuts if IDs are known.
*
* @param ids list of shortcut IDs
*/
@WorkerThread
fun removeShortcutsById(ids: List<String>) {
//...
}
/**
* Removes shortcuts associated with the tasks.
*
* @param tasks list of tasks to remove.
*/
@WorkerThread
fun removeShortcuts(tasks: List<Task>) {
//...
}
}
Aggiorna il metodo pushShortcut
per chiamare l'API ShortcutManagerCompat
. Aggiorna la classe ShortcutsRepository
con il seguente codice:
ShortcutsRepository.kt
/**
* Pushes a dynamic shortcut for the task. The task's ID is used as a shortcut
* ID. The task's title and description are used as shortcut's short and long
* labels. The created shortcut corresponds to GET_THING capability with task's
* title used as BII's "name" argument.
*
* @param task Task object for which to create a shortcut.
*/
@WorkerThread
fun pushShortcut(task: Task) {
ShortcutManagerCompat.pushDynamicShortcut(appContext, createShortcutCompat(task))
}
Nell'esempio di codice precedente abbiamo passato appContext
all'API. Si tratta di una proprietà di classe che contiene un contesto dell'applicazione. È importante utilizzare un contesto dell'applicazione (anziché un contesto dell'attività) per evitare perdite di memoria, poiché il contesto potrebbe essere mantenuto più a lungo del ciclo di vita dell'attività host.
Inoltre, l'API richiede che passiamo un oggetto ShortcutInfoCompat
per l'oggetto Tasks. Nel codice di esempio precedente lo facciamo chiamando il metodo privato createShortcutCompat
, che aggiorneremo per creare e restituire un oggetto ShortcutInfoCompat
. Per farlo, aggiorna lo stub createShortcutCompat
con il seguente codice:
ShortcutsRepository.kt
private fun createShortcutCompat(task: Task): ShortcutInfoCompat {
val intent = Intent(appContext, TasksActivity::class.java)
intent.action = Intent.ACTION_VIEW
// Filtering is set based on currentTitle.
intent.putExtra(GET_THING_KEY, task.title)
// A unique ID is required to avoid overwriting an existing shortcut.
return ShortcutInfoCompat.Builder(appContext, task.id)
.setShortLabel(task.title)
.setLongLabel(task.title)
// Call addCapabilityBinding() to link this shortcut to a BII. Enables user to invoke a shortcut using its title in Assistant.
.addCapabilityBinding(
"actions.intent.GET_THING", "thing.name", listOf(task.title))
.setIntent(intent)
.setLongLived(false)
.build()
}
Gli stub di funzione rimanenti in questa classe si occupano dell'aggiornamento e dell'eliminazione delle scorciatoie dinamiche. Attiva queste funzioni aggiornandole con il seguente codice:
ShortcutsRepository.kt
/**
* Updates a Dynamic Shortcut for the task. If the shortcut associated with this task
* doesn't exist, throws an error. This operation may take a few seconds to complete.
*
* @param tasks list of tasks to update.
*/
@WorkerThread
fun updateShortcuts(tasks: List<Task>) {
val scs = tasks.map { createShortcutCompat(it) }
ShortcutManagerCompat.updateShortcuts(appContext, scs)
}
/**
* Removes shortcuts if IDs are known.
* @param ids list of shortcut IDs
*/
@WorkerThread
fun removeShortcutsById(ids: List<String>) {
ShortcutManagerCompat.removeDynamicShortcuts(appContext, ids)
}
/**
* Removes shortcuts associated with the tasks.
*
* @param tasks list of tasks to remove.
*/
@WorkerThread
fun removeShortcuts(tasks: List<Task>) {
ShortcutManagerCompat.removeDynamicShortcuts (appContext,
tasks.map { it.id })
}
Aggiungi classe a Localizzatore servizio
Dopo aver creato la classe ShortcutsRepository
, il passaggio successivo consiste nel rendere disponibili gli oggetti di questa classe al resto dell'app. Questa app gestisce le dipendenze delle classi implementando il pattern service locator. Apri la classe ServiceLocator utilizzando il browser di classi in Android Studio andando a Naviga > Classe e digitando "ServiceLocator". Fai clic sul file Kotlin risultante per aprirlo nel tuo IDE.
Nella parte superiore di ServiceLocator.kt
, incolla il seguente codice per importare i pacchetti ShortcutsRepository
e SuppressLint
:
ServiceLocator.kt
package com.example.android.architecture.blueprints.todoapp
// ...Other import statements
import com.example.android.architecture.blueprints.todoapp.data.source.ShortcutsRepository
import android.annotation.SuppressLint
Aggiungi i membri e i metodi del servizio ShortcutRepository
incollando il codice seguente nel corpo di ServiceLocator.kt
:
ServiceLocator.kt
object ServiceLocator {
// ...
// Only the code immediately below this comment needs to be copied and pasted
// into the body of ServiceLocator.kt:
@SuppressLint("StaticFieldLeak")
@Volatile
var shortcutsRepository: ShortcutsRepository? = null
private fun createShortcutsRepository(context: Context): ShortcutsRepository {
val newRepo = ShortcutsRepository(context.applicationContext)
shortcutsRepository = newRepo
return newRepo
}
fun provideShortcutsRepository(context: Context): ShortcutsRepository {
synchronized(this) {
return shortcutsRepository ?: shortcutsRepository ?: createShortcutsRepository(context)
}
}
}
Registra il servizio scorciatoia
Il passaggio finale consiste nel registrare il nuovo servizio ShortcutsRepository
nell'applicazione. In Android Studio, apri TodoApplication.kt
e copia il seguente codice nella parte superiore del file:
TodoApplication.kt
package com.example.android.architecture.blueprints.todoapp
/// ... Other import statements
import com.example.android.architecture.blueprints.todoapp.data.source.ShortcutsRepository
Aggiungi il seguente codice al corpo della classe per registrare il servizio:
TodoApplication.kt
//...
class TodoApplication : Application() {
//...
val shortcutsRepository: ShortcutsRepository
get() = ServiceLocator.provideShortcutsRepository(this)
//...
}
Crea l'app e assicurati che continui a essere eseguita.
5. Esegui il push di una nuova scorciatoia
Una volta creato il servizio di scorciatoie, puoi iniziare a inviare le scorciatoie. Poiché gli utenti generano contenuti (elementi di attività) in questa app e si aspettano di potervi accedere in un secondo momento, attiveremo l'accesso vocale a questi contenuti inviando una scorciatoia dinamica associata all'intent integrato GET_THING
ogni volta che un utente crea una nuova attività. In questo modo, l'assistente può indirizzare gli utenti direttamente all'elemento dell'attività richiesto quando attivano la BII chiedendo, ad esempio, "Hey Google, apri la mia lista della spesa su SampleApp".
Abiliti questa funzionalità nell'app di esempio completando questi passaggi:
- Importazione del servizio
ShortcutsRepository
nella classeAddEditTaskViewModel
, responsabile della gestione degli oggetti dell'elenco di attività. - Invio di una scorciatoia dinamica quando l'utente crea una nuova attività.
Importa ShortcutsRepository
Dobbiamo prima rendere disponibile il servizio ShortcutsRepository
per AddEditTaskViewModel
. A questo scopo, importa il servizio in ViewModelFactory
, la classe di fabbrica utilizzata dall'app per creare un'istanza degli oggetti ViewModel, tra cui AddEditTaskViewModel
.
Apri il browser del corso in Android Studio: Naviga > Class e digitando "ViewModelFA". Fai clic sul file Kotlin risultante per aprirlo nell'IDE.
Incolla il codice seguente nella parte superiore di ViewModelFactory.kt
per importare i pacchetti ShortcutsRepository
e SuppressLint
:
ViewModelFactory.kt
package com.example.android.architecture.blueprints.todoapp
// ...Other import statements
import com.example.android.architecture.blueprints.todoapp.data.source.ShortcutsRepository
Poi, sostituisci il corpo di ViewModelFactory
con il seguente codice:
ViewModelFactory.kt
/**
* Factory for all ViewModels.
*/
@Suppress("UNCHECKED_CAST")
class ViewModelFactory constructor(
private val tasksRepository: TasksRepository,
private val shortcutsRepository: ShortcutsRepository,
owner: SavedStateRegistryOwner,
defaultArgs: Bundle? = null
) : AbstractSavedStateViewModelFactory(owner, defaultArgs) {
override fun <T : ViewModel> create(
key: String,
modelClass: Class<T>,
handle: SavedStateHandle
) = with(modelClass) {
when {
isAssignableFrom(StatisticsViewModel::class.java) ->
StatisticsViewModel(tasksRepository)
isAssignableFrom(TaskDetailViewModel::class.java) ->
TaskDetailViewModel(tasksRepository)
isAssignableFrom(AddEditTaskViewModel::class.java) ->
AddEditTaskViewModel(tasksRepository, shortcutsRepository)
isAssignableFrom(TasksViewModel::class.java) ->
TasksViewModel(tasksRepository, handle)
else ->
throw IllegalArgumentException("Unknown ViewModel class: ${modelClass.name}")
}
} as T
}
Termina le modifiche ViewModelFactory
salendo di un livello e passa ShortcutsRepository
al costruttore della fabbrica. Apri il browser dei file di Android Studio andando a Naviga > File e digitando "FragmentExt.kt". Fai clic sul file Kotlin risultante nel pacchetto util per aprirlo nel tuo IDE.
Sostituisci il corpo di FragmentExt.kt
con il seguente codice:
fun Fragment.getViewModelFactory(): ViewModelFactory {
val taskRepository = (requireContext().applicationContext as TodoApplication).taskRepository
val shortcutsRepository = (requireContext().applicationContext as TodoApplication).shortcutsRepository
return ViewModelFactory(taskRepository, shortcutsRepository, this)
}
Esegui il push di una scorciatoia
Con la classe di astrazione ShortcutsRepository
disponibile per le classi ViewModel
dell'app di esempio, aggiorni AddEditTaskViewModel
, la classe ViewModel
responsabile della creazione delle note, in modo da eseguire il push di una scorciatoia dinamica ogni volta che un utente crea una nuova nota.
In Android Studio, apri il browser delle classi e digita "AddEditTaskViewModel". Fai clic sul file Kotlin risultante per aprirlo nel tuo IDE.
Innanzitutto, aggiungi il pacchetto ShortcutsRepository
a questo corso con la seguente istruzione di importazione:
package com.example.android.architecture.blueprints.todoapp.addedittask
//Other import statements
import com.example.android.architecture.blueprints.todoapp.data.source.ShortcutsRepository
Aggiungi quindi la proprietà della classe shortcutsRepository
aggiornando il costruttore della classe con il seguente codice:
AddEditTaskViewModel.kt
//...
/**
* ViewModel for the Add/Edit screen.
*/
class AddEditTaskViewModel(
private val tasksRepository: TasksRepository,
private val shortcutsRepository: ShortcutsRepository
) : ViewModel() {
//...
Con la classe ShortcutsRepository
aggiunta, crea una nuova funzione, pushShortcut()
, per chiamare questa classe. Incolla la seguente funzione privata nel corpo di AddEditTaskViewModel
:
AddEditTaskViewModel.kt
//...
private fun pushShortcut(newTask: Task) = viewModelScope.launch {
shortcutsRepository.pushShortcut(newTask)
}
Infine, esegui il push di una nuova scorciatoia dinamica ogni volta che viene creata un'attività. Sostituisci i contenuti della funzione saveTask()
con il seguente codice:
AddEditTaskViewModel.kt
fun saveTask() {
val currentTitle = title.value
val currentDescription = description.value
if (currentTitle == null || currentDescription == null) {
_snackbarText.value = Event(R.string.empty_task_message)
return
}
if (Task(currentTitle, currentDescription).isEmpty) {
_snackbarText.value = Event(R.string.empty_task_message)
return
}
val currentTaskId = taskId
if (isNewTask || currentTaskId == null) {
val task = Task(currentTitle, currentDescription)
createTask(task)
pushShortcut(task)
} else {
val task = Task(currentTitle, currentDescription, taskCompleted, currentTaskId)
updateTask(task)
}
}
Prova il codice
Siamo finalmente pronti a testare il nostro codice! In questo passaggio, invii una scorciatoia dinamica con attivazione vocale e la ispezioni utilizzando l'app Assistente Google.
Creare un'anteprima
La creazione di un'anteprima utilizzando il plug-in dell'Assistente Google consente la visualizzazione delle scorciatoie dinamiche nell'assistente sul dispositivo di test.
Installa il plug-in di test
Se non hai già il plug-in dell'Assistente Google, installalo seguendo questi passaggi in Android Studio:
- Vai a **File > Impostazioni (Android Studio > Preferenze su macOS).
- Nella sezione Plugin, vai a Marketplace e cerca "Assistente Google".
- Se non riesci a trovare il plug-in nel Marketplace, scaricalo manualmente e segui le istruzioni riportate in Installare il plug-in dal disco.
- Installa lo strumento e riavvia Android Studio.
Creare l'anteprima
Per creare un'anteprima in Android Studio, procedi nel seguente modo:
- Fai clic su Strumenti > Assistente Google > "Strumento di test delle Azioni app".
- Nella casella Nome app, definisci un nome come "Elenco di cose da fare".
- Fai clic su Crea anteprima. Se richiesto, leggi e accetta le norme e i Termini di servizio di Azioni app.
Figura 3. Riquadro di creazione dell'anteprima dello strumento App Actions Test Tool.
Durante il test, le scorciatoie dinamiche che invii all'assistente verranno visualizzate nell'assistente organizzate in base al nome dell'app fornito per l'anteprima.
Esegui il push e ispeziona una scorciatoia
Riavvia l'app di esempio sul dispositivo di test ed esegui queste operazioni :
- Crea una nuova attività con il titolo "Avvia il codelab"
- Apri l'app Assistente Google e di' o digita "Le mie scorciatoie".
- Tocca la scheda Esplora. Dovresti visualizzare la scorciatoia di esempio.
- Tocca la scorciatoia per richiamarla. L'avvio dell'app dovrebbe essere visualizzato con il nome della scorciatoia precompilato nella casella dei filtri, in modo da poter trovare facilmente l'elemento dell'attività richiesto.
6. (Facoltativo) Aggiornare ed eliminare una scorciatoia
Oltre a inviare nuove scorciatoie dinamiche in fase di runtime, la tua app può aggiornarle per riflettere lo stato corrente dei contenuti e delle preferenze dell'utente. È buona norma aggiornare le scorciatoie esistenti ogni volta che un utente modifica l'elemento di destinazione, ad esempio rinominando un'attività nella nostra app di esempio. Inoltre, devi eliminare una scorciatoia corrispondente ogni volta che la risorsa di destinazione viene rimossa per evitare di mostrare scorciatoie non funzionanti all'utente.
Aggiornare una scorciatoia
Modifica AddEditTaskViewModel
per aggiornare una scorciatoia dinamica ogni volta che un utente modifica i dettagli di un elemento dell'attività. Per prima cosa, aggiorna il corpo della classe con il codice seguente per aggiungere una funzione di aggiornamento che utilizzi la nostra classe di repository:
AddEditTaskViewModel.kt
private fun updateShortcut(newTask: Task) = viewModelScope.launch {
shortcutsRepository.updateShortcuts(listOf(newTask))
}
A questo punto, modifica la funzione saveTask()
in modo da chiamare il nuovo metodo ogni volta che viene aggiornata un'attività esistente.
AddEditTaskViewModel.kt
// Called when clicking on fab.
fun saveTask() {
// ...
// Note: the shortcuts are created/updated in a worker thread.
if (isNewTask || currentTaskId == null) {
//...
} else {
//...
updateShortcut(task)
}
}
Testa il codice riavviare l'app e seguire questi passaggi:
- Rinomina il titolo dell'elemento dell'attività esistente in "Completa il codelab".
- Apri l'Assistente Google dicendo "Hey Google, le mie scorciatoie".
- Tocca la scheda Esplora. Dovresti vedere un'etichetta breve aggiornata per la scorciatoia di prova.
Rimuovere una scorciatoia
Le scorciatoie delle nostre app di esempio devono essere rimosse ogni volta che un utente elimina un'attività. Nell'app di esempio, la logica di eliminazione delle attività si trova nella classe TaskDetailViewModel
. Prima di aggiornare questo corso, dobbiamo aggiornare di nuovo ViewModelFactory
per trasferire shortcutsRepository
a TaskDetailViewModel
.
Apri ViewModelFactory
e sostituisci i contenuti del relativo metodo costruttore con il seguente codice:
//...
class ViewModelFactory constructor(
private val tasksRepository: TasksRepository,
private val shortcutsRepository: ShortcutsRepository,
owner: SavedStateRegistryOwner,
defaultArgs: Bundle? = null
) : AbstractSavedStateViewModelFactory(owner, defaultArgs) {
override fun <T : ViewModel> create(
key: String,
modelClass: Class<T>,
handle: SavedStateHandle
) = with(modelClass) {
when {
isAssignableFrom(StatisticsViewModel::class.java) ->
StatisticsViewModel(tasksRepository)
isAssignableFrom(TaskDetailViewModel::class.java) ->
TaskDetailViewModel(tasksRepository, shortcutsRepository)
isAssignableFrom(AddEditTaskViewModel::class.java) ->
AddEditTaskViewModel(tasksRepository, shortcutsRepository)
isAssignableFrom(TasksViewModel::class.java) ->
TasksViewModel(tasksRepository, handle)
else ->
throw IllegalArgumentException("Unknown ViewModel class: ${modelClass.name}")
}
} as T
}
Poi apri TaskDetailViewModel
. Importa il modulo ShortcutsRepository
e dichiara una variabile di istanza utilizzando il seguente codice:
TaskDetailViewModel.kt
package com.example.android.architecture.blueprints.todoapp.taskdetail
...
import com.example.android.architecture.blueprints.todoapp.data.source.ShortcutsRepository
/**
* ViewModel for the Details screen.
*/
class TaskDetailViewModel(
//...
private val shortcutsRepository: ShortcutsRepository
) : ViewModel() {
...
}
Infine, modifica la funzione deleteTask()
per chiamare shortcutsRepository
in modo da rimuovere una scorciatoia basata sul suo ID ogni volta che viene eliminata un'attività con un taskId
corrispondente:
TaskDetailViewModel.kt
fun deleteTask() = viewModelScope.launch {
_taskId.value?.let {
//...
shortcutsRepository.removeShortcutsById(listOf(it))
}
}
Per testare il codice, riavvia l'app e segui questi passaggi:
- Elimina l'attività di test.
- Rinomina il titolo dell'elemento dell'attività esistente in "Completa il codelab".
- Apri l'Assistente Google dicendo "Hey Google, le mie scorciatoie".
- Tocca la scheda Esplora. Verifica che la scorciatoia di prova non venga più visualizzata.
7. Passaggi successivi
Complimenti! Grazie a te, gli utenti della nostra app di esempio possono tornare facilmente alle note che creano chiedendo all'assistente, ad esempio, "Hey Google, apri la mia lista della spesa su ExampleApp". Le scorciatoie favoriscono un maggiore coinvolgimento degli utenti consentendo loro di riprodurre facilmente le azioni utilizzate di frequente nella tua app.
Argomenti trattati
In questo codelab hai imparato a:
- Identificare i casi d'uso per il push delle scorciatoie dinamiche in un'app.
- Riduci la complessità del codice utilizzando repository, inserimento di dipendenze e pattern di progettazione di Service locator.
- Trasferisci le scorciatoie dinamiche che supportano i comandi vocali ai contenuti delle app generati dagli utenti.
- Aggiornare e rimuovere le scorciatoie esistenti.
Passaggi successivi
Da qui, puoi provare ad apportare ulteriori perfezionamenti all'app Elenco attività. Per fare riferimento al progetto finito, consulta il ramo del repository –codelab-complete su GitHub.
Ecco alcuni suggerimenti per ulteriori informazioni su come estendere questa app con Azioni app:
- Consulta l'elenco di controllo di esempio con Google Analytics per Firebase per scoprire come monitorare il rendimento delle azioni app.
- Consulta la documentazione di riferimento sugli intent integrati di Azioni app per scoprire altri modi per estendere le tue app all'assistente.
Per continuare il tuo percorso con Actions on Google, consulta queste risorse:
- actions.google.com: sito di documentazione ufficiale per Actions on Google.
- Indice di esempi di App Actions: app e codice di esempio per esplorare le funzionalità di App Actions.
- Repository GitHub di Actions on Google: codice di esempio e librerie.
- r/GoogleAssistantDev: community ufficiale di Reddit per gli sviluppatori che lavorano con l'Assistente Google.
Seguici su Twitter @ActionsOnGoogle per non perderti i nostri ultimi annunci e twitta a #appActions per condividere ciò che hai realizzato.
Sondaggio di feedback
Infine, compila questo sondaggio per fornire un feedback sulla tua esperienza con questo codelab.