Motion Layout es una versión especial del diseño de restricción. Con la ayuda del diseño de movimiento, podemos agregar animaciones a los widgets dentro del diseño y cambiar la posición de ese widget de forma dinámica. En este artículo, veremos cómo implementar la animación Motion Layout en botones en Android usando Jetpack compose .
¿Qué vamos a construir en este artículo?
Construiremos una aplicación simple en la que mostraremos dos botones de imagen. Estos botones están alineados verticalmente de forma predeterminada. Al hacer clic en cualquiera de los botones, los botones se animarán y se organizarán de forma horizontal. A continuación se muestra un video de muestra para tener una idea de lo que vamos a hacer en este artículo.
Implementación paso a paso
Paso 1: crea un nuevo proyecto en Android Studio
Para crear un nuevo proyecto en Android Studio, consulte Cómo crear/iniciar un nuevo proyecto en Android Studio . Al elegir la plantilla, seleccione Actividad de composición vacía . Si no encuentra esta plantilla, intente actualizar Android Studio a la última versión. Demostramos la aplicación en Kotlin, así que asegúrese de seleccionar Kotlin como idioma principal al crear un nuevo proyecto.
Paso 2: Agregar dependencia en build.gradle
Navegue a Gradle Scripts > archivo build.gradle y agregue la siguiente dependencia en la sección de dependencias.
implementation "androidx.constraintlayout:constraintlayout-compose:1.0.0-rc01"
Después de agregar esta dependencia, sincronice este proyecto para instalar la dependencia.
Paso 3: Agregar nuevos colores en el archivo Color.kt
Vaya a la aplicación > java > el nombre del paquete de su aplicación > ui.theme > archivo Color.kt y agréguele el siguiente código.
Kotlin
package com.example.newcanaryproject.ui.theme import androidx.compose.ui.graphics.Color val Purple200 = Color(0xFF0F9D58) val Purple500 = Color(0xFF0F9D58) val Purple700 = Color(0xFF3700B3) val Teal200 = Color(0xFF03DAC5) // on below line we are // adding different colors val greenColor = Color(0xFF0F9D58)
Paso 4: trabajar con el archivo MainActivity.kt
Vaya al archivo MainActivity.kt y consulte el siguiente código. A continuación se muestra el código del archivo MainActivity.kt . Se agregan comentarios dentro del código para comprender el código con más detalle.
Kotlin
package com.example.newcanaryproject import android.app.Activity import android.content.Context import android.content.Intent import android.graphics.Typeface import android.os.Bundle import android.speech.RecognizerIntent import android.speech.SpeechRecognizer import android.view.ViewGroup import android.widget.LinearLayout import android.widget.Toast import androidx.activity.ComponentActivity import androidx.activity.compose.setContent import androidx.annotation.Dimension.DP import androidx.compose.animation.Crossfade import androidx.compose.animation.core.animateFloatAsState import androidx.compose.animation.core.tween import androidx.compose.foundation.Image import androidx.compose.foundation.layout.* import androidx.compose.material.* import androidx.compose.material.icons.Icons import androidx.compose.material.icons.filled.Mic import androidx.compose.runtime.* import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.graphics.Color import androidx.compose.ui.graphics.toArgb import androidx.compose.ui.layout.layoutId import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.res.dimensionResource import androidx.compose.ui.res.painterResource import androidx.compose.ui.text.TextStyle import androidx.compose.ui.text.font.FontFamily import androidx.compose.ui.text.font.FontStyle import androidx.compose.ui.text.style.TextAlign import androidx.compose.ui.unit.* import androidx.compose.ui.viewinterop.AndroidView import androidx.constraintlayout.compose.ConstraintSet import androidx.constraintlayout.compose.MotionLayout import com.example.newcanaryproject.ui.theme.* import com.github.mikephil.charting.charts.PieChart import com.github.mikephil.charting.components.Description import com.github.mikephil.charting.components.Legend import com.github.mikephil.charting.data.PieData import com.github.mikephil.charting.data.PieDataSet import com.github.mikephil.charting.data.PieEntry import org.intellij.lang.annotations.JdkConstants.HorizontalAlignment import java.util.* class MainActivity : ComponentActivity() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContent { NewCanaryProjectTheme { // on below line we are specifying // background color for our application Surface( modifier = Modifier.fillMaxSize(), color = MaterialTheme.colors.background ) { // on below line we are specifying theme as scaffold. Scaffold( // in scaffold we are specifying top bar. topBar = { // inside top bar we are specifying background color. TopAppBar(backgroundColor = greenColor, // along with that we are specifying title for our top bar. title = { // in the top bar we are specifying tile as a text Text( // on below line we are specifying // text to display in top app bar. text = "MotionLayout Button", // on below line we are specifying modifier // to fill max width. modifier = Modifier.fillMaxWidth(), // on below line we are // specifying text alignment. textAlign = TextAlign.Center, // on below line we are specifying // color for our text. color = Color.White ) } ) } ) { // on below line we are creating a box Box( // in this box we are specifying a modifier // and specifying a max size modifier = Modifier .fillMaxSize(), // on below line we are specifying center alignment contentAlignment = Alignment.Center, ) { // on below line we are calling // motion layout button method. MotionLayoutButton() } } } } } } } // on below line we are creating // a motion layout button method. @OptIn(ExperimentalUnitApi::class) @Composable fun MotionLayoutButton() { // on below line we are specifying animate button method. var animateButton by remember { mutableStateOf(false) } // on below line we are specifying button animation progress val buttonAnimationProgress by animateFloatAsState( // specifying target value on below line. targetValue = if (animateButton) 1f else 0f, // on below line we are specifying // animation specific duration's 1 sec animationSpec = tween(1000) ) // on below line we are creating a motion layout. MotionLayout( // in motion layout we are specifying 2 constraint // set for two different positions of buttons. // in first constraint set we are specifying width, // height start, end and top position of buttons. ConstraintSet( """ { // on below line we are specifying width,height and margin // from start, top and end for button1 button1: { width: "spread", height: 120, start: ['parent', 'start', 16], end: ['parent', 'end', 16], top: ['parent', 'top', 0] }, // on below line we are specifying width,height // and margin from start, top and end for button2 button2: { width: "spread", height: 120, start: ['parent', 'start', 16], end: ['parent', 'end', 16], top: ['button1', 'bottom', 16] } } """ ), // in second constraint set we are specifying width, // height start, end and top position of buttons. ConstraintSet( """ { // on below line we are specifying width,height and margin // from start, top and end for button1 button1: { width: 150, height: 120, start: ['parent', 'start', 30], end: ['button2', 'start', 10] }, // on below line we are specifying width,height // and margin from start, top and end for button2 button2: { width: 150, height: 120, start: ['button1', 'end', 10], end: ['parent', 'end', 30] } } """ ), // on below line we are specifying // progress for button animation progress = buttonAnimationProgress, // on below line we are specifying modifier // for filling max width anf content height. modifier = Modifier .fillMaxWidth() .wrapContentHeight() ) { // on below line we are creating a button. Button( // on below line we are adding on click. onClick = { // inside on click we are animating button // by simply changing animateButton variable animateButton = !animateButton }, // on below line we are // specifying id for our button 1 modifier = Modifier.layoutId("button1") ) { // on below line we are adding content // inside our button in the form of column. Column( // in this column we are specifying a // modifier with padding from all sides. modifier = Modifier .padding(3.dp) .fillMaxWidth() .fillMaxHeight(), // on below line we are specifying vertical // and horizontal arrangement for our column verticalArrangement = Arrangement.Center, horizontalAlignment = Alignment.CenterHorizontally ) { // on the below line we are specifying an image inside our column Image( // on below line we are specifying // the drawable image for our image. painter = painterResource(id = R.drawable.python), // on below line we are specifying // content description for our image contentDescription = "Python", // on below line we are setting // height and width for our image. modifier = Modifier .height(60.dp) .width(60.dp) ) // on below line we are adding spacer/ Spacer(modifier = Modifier.height(5.dp)) // below spacer we are adding a // simple text for displaying a text Text( text = "Python", color = Color.White, fontSize = TextUnit(value = 18F, type = TextUnitType.Sp) ) } } // on the below line we are creating a button. Button( onClick = { // inside on click we are animating button // by simply changing animateButton variable animateButton = !animateButton }, // on below line we are specifying id for our button 2 modifier = Modifier.layoutId("button2") ) { Column( // in this column we are specifying // a modifier with padding from all sides. modifier = Modifier .padding(3.dp) .fillMaxWidth() .fillMaxHeight(), // on below line we are specifying vertical // and horizontal arrangement for our column verticalArrangement = Arrangement.Center, horizontalAlignment = Alignment.CenterHorizontally ) { // on below line we are specifying image inside our column Image( // on below line we are specifying // the drawable image for our image. painter = painterResource(id = R.drawable.js), // on below line we are specifying // content description for our image contentDescription = "Javascript", // on below line we are setting // height and width for our image. modifier = Modifier .height(60.dp) .width(60.dp) ) // on below line we are adding spacer/ Spacer(modifier = Modifier.height(5.dp)) // below spacer we are adding a // simple text for displaying a text Text( text = "JavaScript", color = Color.White, fontSize = TextUnit(value = 18F, type = TextUnitType.Sp) ) } } } }
Ahora ejecute su aplicación para ver el resultado.
Producción:
Publicación traducida automáticamente
Artículo escrito por chaitanyamunje y traducido por Barcelona Geeks. The original can be accessed here. Licence: CCBY-SA