En esta página:
Demo
En este Post continuaremos con la parte anterior de este tutorial llamada Creando un Bot (Android) para una tienda de Postres (Dialogflow V2 + Kotlin 1.3.72) – Parte 2 en donde creamos el Layout Principal para la actividad principal de la aplicación, con sus elementos, colores, botones y demás elementos correspondientes, en esta parte 3 vamos a escribir el código Kotlin para nuestra aplicación.
Partes
Antes de continuar te invito a leer los siguientes artículos:
- Que es Android y tu Primera aplicación Hola Mundo
- Como Leer un archivo JSON en Android (Android Studio 3.6.1 + Java) – Parte 1
- Que es Kotlin y otros detalles
- Tipos de Variables en Kotlin
- Que es la Inteligencia Artificial y otros Detalles
- Que es Machine Learning, Historia y otros detalles
- Las Novedades más Destacadas que trae Android Studio 4.0
- Puedes leer más artículos en la categoría Android
Asimismo te invito a escuchar el Podcast: “Donde buscar ayuda sobre Programación”:
Spotify | SoundCloud |
Bien ahora continuemos con el Post: Creando un Bot (Android) para una tienda de Postres (Dialogflow V2 + Kotlin 1.3.72) – Parte 3.
En esta Parte 3 comenzaremos trabajando con el archivo MainActivity.kt, este archivo fue generado por Android Studio automáticamente, cuando creamos el nuevo proyecto para esta aplicación.
Actividad Principal
En el directorio principal del proyecto se encuentra el archivo en formato Kotlin llamado MainActivity.kt
1 2 3 4 5 6 7 8 9 10 11 12 |
/app ├── /manifests ├── /java ├── /com.example.tiendapostresbot ├── MainActivity.kt // Abre este Archivo ├── /com.example.tiendapostresbot (androidTest) ├── /com.example.tiendapostresbot (test) ├── /java (generated) ├── /res /Gradle Scripts |
Abro el archivo MainActivity.kt y antes de la clase MainActivity voy a importar los siguientes elementos, asimismo creo 3 variables llamadas, USUARIO, BOT y ENTRADA_DE_VOZ.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 |
package com.example.tiendapostresbot import android.app.Activity import androidx.appcompat.app.AppCompatActivity import android.os.Bundle import android.speech.RecognizerIntent import android.util.Log import android.view.KeyEvent import android.view.View import kotlinx.android.synthetic.main.activity_main.* import android.view.LayoutInflater import com.google.api.gax.core.FixedCredentialsProvider import com.google.auth.oauth2.ServiceAccountCredentials import com.google.auth.oauth2.GoogleCredentials import com.google.cloud.dialogflow.v2.* import java.util.* import android.widget.* import android.widget.Toast import android.content.ActivityNotFoundException import android.content.Intent import android.speech.RecognizerResultsIntent import android.speech.tts.TextToSpeech import android.text.Editable const val USUARIO = 0 const val BOT = 1 const val ENTRADA_DE_VOZ = 2 class MainActivity : AppCompatActivity() { // Acá va el código } |
Dentro de la clase MainActivity y antes del ciclo de vida o método onCreate crearé las variables uuid para generar un string aleatorio, cliente, session y la variable asistente_voz.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
class MainActivity : AppCompatActivity() { // Variables private val uuid = UUID.randomUUID().toString() private var cliente: SessionsClient? = null private var sesion: SessionName? = null private var asistente_voz: TextToSpeech?=null override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_main) } } |
Dentro del método onCreate voy a crear una variable llamada scrollview en ella llamo al ScrollView que definí en la Parte 2 de este tutorial, en el archivo activity_main.xml
1 2 3 4 5 6 7 8 9 10 11 12 13 |
override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_main) // Llamo al ScrollView val scrollview = findViewById<ScrollView>(R.id.scroll_chat) scrollview.post { scrollview.fullScroll(ScrollView.FOCUS_DOWN) } } |
El ScrollView va ser el contenedor en donde se desplazarán los mensajes entre el usuario y el bot, dentro de la aplicación.
Luego creo una variable con el nombre cajaMensajes y en ella llamo al EditTex que es la caja en donde el usuario escribirá el mensaje para enviarlo al chat, este EditText, le dimos el id cajadetexto en la Parte 2 de este tutorial, en el archivo activity_main.xml
El usuario se coloca en el EditText, escribe un mensaje y presiona la tecla Enter para enviarlo, este evento lo manejamos con KeyEvent.ACTION_DOWN de Android y posteriormente con KeyEvent.KEYCODE_DPAD_CENTER en donde llamamos al método enviarMensaje(enviar) el cual crearemos más adelante y le estamos pasando el botón o ImageView que creamos también en la Parte 2 de este tutorial, en el archivo activity_main.xml
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 |
override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_main) val scrollview = findViewById<ScrollView>(R.id.scroll_chat) scrollview.post { scrollview.fullScroll(ScrollView.FOCUS_DOWN) } // Caja para escribir los mensajes en el chat val cajaMensajes = findViewById<EditText>(R.id.cajadetexto) cajaMensajes.setOnKeyListener { view, keyCode, event -> if (event.action === KeyEvent.ACTION_DOWN) { when (keyCode) { KeyEvent.KEYCODE_DPAD_CENTER, KeyEvent.KEYCODE_ENTER -> { // Llamamos al método enviarMensaje() el cual crearemos más adelante enviarMensaje(enviar) true } else -> { } } } false } } |
Para terminar con el código del método o ciclo de vida onCreate(), pasamos setOnClickListener() al botón para enviar los mensajes de texto y también al botón del micrófono que sirve para enviar mensajes de audio en el chat, este botón llama la función enviarMensajeMicrofono() la cual creamos más adelante y por último llamamos a las funciones iniciarAsistente() y iniciarAsistenteVoz(), las cuales crearemos más adelante.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 |
override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_main) val scrollview = findViewById<ScrollView>(R.id.scroll_chat) scrollview.post { scrollview.fullScroll(ScrollView.FOCUS_DOWN) } val cajaMensajes = findViewById<EditText>(R.id.cajadetexto) cajaMensajes.setOnKeyListener { view, keyCode, event -> if (event.action === KeyEvent.ACTION_DOWN) { when (keyCode) { KeyEvent.KEYCODE_DPAD_CENTER, KeyEvent.KEYCODE_ENTER -> { enviarMensaje(enviar) true } else -> { } } } false } // Pasamos un setOnClickListener al botón para enviar mensajes llamando al // método enviarMensaje() el cual crearemos más adelante enviar.setOnClickListener(this::enviarMensaje) // Al botón del microfono también le pasamos un setOnClickListener, este envia mensajes de audio con el // método enviarMensajeMicrofono() el cual crearemos más adelante microfono.setOnClickListener(this::enviarMensajeMicrofono) // Llamamos al método iniciarAsistente() el cual crearemos más adelante iniciarAsistente() // Llamamos al método iniciarAsistenteVoz() el cual crearemos más adelante iniciarAsistenteVoz() } |
Ahora creare la función iniciarAsistente() la cual llamamos en la parte final del método onCreate(), en la función iniciarAsistente() exactamente haré uso de las credenciales del proyecto que crearé más adelante en Dialogflow (Google Cloud Platform) y no quiero salirme del tema, estamos trabajando en el código de la actividad principal (MainActivity.kt).
Puedes ver en el código he colocado comentarios para explicar que hace cada línea del código.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 |
// Función inicarAsistente private fun iniciarAsistente() { try { // Archivo JSON de configuración de la cuenta de Dialogflow (Google Cloud Platform) val config = resources.openRawResource(R.raw.credenciales) // Leemos las credenciales de la cuenta de Dialogflow (Google Cloud Platform) val credenciales = GoogleCredentials.fromStream(config) // Leemos el 'projectId' el cual se encuentra en el archivo 'credenciales.json' val projectId = (credenciales as ServiceAccountCredentials).projectId // Construimos una configuración para acceder al servicio de Dialogflow (Google Cloud Platform) val generarConfiguracion = SessionsSettings.newBuilder() // Configuramos las sesiones que usaremos en la aplicación val configurarSesiones = generarConfiguracion.setCredentialsProvider(FixedCredentialsProvider.create(credenciales)).build() cliente = SessionsClient.create(configurarSesiones) sesion = SessionName.of(projectId, uuid) } catch (e: Exception) { e.printStackTrace() } } |
En el código anterior de la función iniciarAsistente() puedes ver que menciono sobre el archivo de credenciales credenciales.json, este archivo lo crearemos mas adelante, primero terminemos con el código de la actividad principal (MainActivity.kt).
Pasaré a crear la función iniciarAsistenteVoz() la cual llamamos también al final del método o ciclo de vida onCreate(). Dentro de la función iniciarAsistenteVoz() básicamente iniciamos el asistente de voz, cuando el usuario envíe un mensaje de audio al Bot.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
// Función iniciarAsistenteVoz private fun iniciarAsistenteVoz() { asistente_voz = TextToSpeech(applicationContext,object : TextToSpeech.OnInitListener { override fun onInit(status: Int) { if (status != TextToSpeech.ERROR){ asistente_voz?.language=Locale("es") } } }) } |
La siguiente función que crearemos será enviarMensaje(), en ella recepcionamos el mensaje del usuario y lo procesamos, en el código he colocado comentarios para explicar que hace cada línea del código.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 |
private fun enviarMensaje(view: View) { // Obtenemos el mensaje de la caja de texto y lo pasamos a String val mensaje = cajadetexto.text.toString() // Si el usuario no ha escrito un mensaje en la caja de texto y presiona el botón enviar, le mostramos // un Toast con un mensaje 'Ingresa tu mensaje ...' if (mensaje.trim { it <= ' ' }.isEmpty()) { Toast.makeText(this@MainActivity, getString(R.string.placeholder), Toast.LENGTH_LONG).show() } // Si el usuario agrego un mensaje a la caja de texto, llamamos al método agregarTexto() else { agregarTexto(mensaje, USUARIO) cajadetexto.setText("") // Enviamos la consulta del usuario al Bot val ingresarConsulta = QueryInput.newBuilder().setText(TextInput.newBuilder().setText(mensaje).setLanguageCode("es")).build() solicitarTarea(this@MainActivity, sesion!!, cliente!!, ingresarConsulta).execute() } } |
Terminado el ciclo de vida o método onCreate(), llamamos a la función enviarMensajeMicrofono() la cual gestiona el mensaje de audio que el usuario envía presionando el botón del micrófono.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 |
private fun enviarMensajeMicrofono(view:View){ // Llamamos al intento para reconocer voz del usuario y convertirla a texto val intento = Intent(RecognizerIntent.ACTION_RECOGNIZE_SPEECH) // Definimos los modelos de reconocimiento de voz intento.putExtra( RecognizerIntent.EXTRA_LANGUAGE_MODEL, RecognizerIntent.LANGUAGE_MODEL_FREE_FORM ) // Le decimos que haga el reconocimiento de voz en el idioma local 'Locale.getDefault()' intento.putExtra(RecognizerIntent.EXTRA_LANGUAGE, Locale.getDefault()) // Si el usuario no habla algo, le mostramos el mensaje 'Di algo en el micrófono ...' intento.putExtra( RecognizerIntent.EXTRA_PROMPT, getString(R.string.mensajedevoz) ) // Si todo va bien, enviamos el audio del usuario al Bot try { startActivityForResult(intento, ENTRADA_DE_VOZ) } // Si el dispositivo del usuario no es compatible con la función del micrófono // Le mostramos el mensaje 'Tu teléfono no es compatible con la función de micrófono ...' // en un Toast catch (a: ActivityNotFoundException) { Toast.makeText( applicationContext, getString(R.string.mensajedevoznoadmitido), Toast.LENGTH_SHORT ).show() } } |
Bien hasta aquí terminamos la tercera parte del tutorial en donde creamos el código de los primeros 5 métodos del archivo MainActivity.kt y en la Cuarta Parte terminaremos de crear los demás métodos que faltan.
Ten Paciencia, lo que quiero es que entiendas todo el proceso para Crear este Proyecto y no llenarte el capitulo de mucho contenido porque te puedes marear y no tendrás un óptimo aprendizaje.
Nota (s)
- En el siguiente capitulo terminaremos de crear los demás métodos del archivo MainActivity.kt
- El código expuesto en este capitulo del tutorial pueden cambiar, esto no depende de mi, si no de la empresa que dan soporte a Android Studio, y Kotlin que suelen cambiar sus tecnologías en futuras versiones.
- No olvides que debemos usar la Tecnología para hacer cosas Buenas por el Mundo.
Síguenos en nuestras Redes Sociales para que no te pierdas nuestros próximos contenidos.