Compose مکانیسمهای انیمیشن داخلی زیادی دارد و دانستن اینکه کدام یک را انتخاب کنید میتواند بسیار سخت باشد. در زیر لیستی از موارد رایج استفاده از انیمیشن آورده شده است. برای اطلاعات دقیق تر در مورد مجموعه کامل گزینه های API مختلف در دسترس شما، مستندات کامل Compose Animation را بخوانید.
ویژگی های متداول ترکیب پذیر را متحرک کنید
Compose API های مناسبی را ارائه می دهد که به شما امکان می دهد موارد استفاده رایج از انیمیشن را حل کنید. این بخش نشان میدهد که چگونه میتوانید ویژگیهای متداول یک composable را متحرک کنید.
متحرک ظاهر شدن / ناپدید شدن

از AnimatedVisibility
برای مخفی کردن یا نمایش Composable استفاده کنید. کودکان داخل AnimatedVisibility
می توانند از Modifier.animateEnterExit()
برای انتقال ورود یا خروج خود استفاده کنند.
var visible by remember { mutableStateOf(true) } // Animated visibility will eventually remove the item from the composition once the animation has finished. AnimatedVisibility(visible) { // your composable here // ... }
پارامترهای ورود و خروج AnimatedVisibility
به شما این امکان را می دهد تا نحوه رفتار یک composable را هنگام ظاهر شدن و ناپدید شدن پیکربندی کنید. برای اطلاعات بیشتر مستندات کامل را بخوانید.
یکی دیگر از گزینههای متحرک سازی نمایان شدن یک Composable، متحرک سازی آلفا در طول زمان با استفاده از animateFloatAsState
است:
var visible by remember { mutableStateOf(true) } val animatedAlpha by animateFloatAsState( targetValue = if (visible) 1.0f else 0f, label = "alpha" ) Box( modifier = Modifier .size(200.dp) .graphicsLayer { alpha = animatedAlpha } .clip(RoundedCornerShape(8.dp)) .background(colorGreen) .align(Alignment.TopCenter) ) { }
با این حال، تغییر آلفا با این هشدار همراه است که ترکیبپذیر در ترکیب باقی میماند و همچنان فضایی را که در آن قرار داده شده اشغال میکند. از طرف دیگر، AnimatedVisibility
در نهایت آیتم را از ترکیب حذف می کند.

رنگ پس زمینه را متحرک کنید

val animatedColor by animateColorAsState( if (animateBackgroundColor) colorGreen else colorBlue, label = "color" ) Column( modifier = Modifier.drawBehind { drawRect(animatedColor) } ) { // your composable here }
این گزینه کارایی بیشتری نسبت به استفاده از Modifier.background()
دارد. Modifier.background()
برای یک تنظیم رنگ یک شات قابل قبول است، اما زمانی که یک رنگ را متحرک می کنید در طول زمان، این می تواند باعث ترکیب مجدد بیش از حد لازم شود.
برای متحرک سازی بی نهایت رنگ پس زمینه، به تکرار بخش انیمیشن مراجعه کنید.
متحرک کردن به اندازه یک ترکیب

Compose به شما این امکان را می دهد که اندازه اجزای سازنده را به چند روش مختلف متحرک کنید. از animateContentSize()
برای انیمیشن های بین تغییرات اندازه قابل ترکیب استفاده کنید.
برای مثال، اگر کادری دارید که حاوی متنی است که میتواند از یک خط به چند خط گسترش یابد، میتوانید Modifier.animateContentSize()
برای دستیابی به یک انتقال روانتر استفاده کنید:
var expanded by remember { mutableStateOf(false) } Box( modifier = Modifier .background(colorBlue) .animateContentSize() .height(if (expanded) 400.dp else 200.dp) .fillMaxWidth() .clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { expanded = !expanded } ) { }
همچنین میتوانید از AnimatedContent
با SizeTransform
استفاده کنید تا چگونگی تغییر اندازه را توضیح دهید.
متحرک کردن موقعیت از composable

برای متحرک کردن موقعیت یک composable، از Modifier.offset{ }
ترکیب شده با animateIntOffsetAsState()
استفاده کنید.
var moved by remember { mutableStateOf(false) } val pxToMove = with(LocalDensity.current) { 100.dp.toPx().roundToInt() } val offset by animateIntOffsetAsState( targetValue = if (moved) { IntOffset(pxToMove, pxToMove) } else { IntOffset.Zero }, label = "offset" ) Box( modifier = Modifier .offset { offset } .background(colorBlue) .size(100.dp) .clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { moved = !moved } )
اگر میخواهید هنگام متحرک کردن موقعیت یا اندازه، مطمئن شوید که Composableها روی یا زیر دیگر composableها کشیده نمیشوند، از Modifier.layout{ }
استفاده کنید. این اصلاح کننده تغییرات اندازه و موقعیت را به والدین منتشر می کند، که سپس بر سایر کودکان تأثیر می گذارد.
به عنوان مثال، اگر در حال جابجایی یک Box
در یک Column
هستید و سایر فرزندان باید هنگام حرکت Box
حرکت کنند، اطلاعات افست را با Modifier.layout{ }
به صورت زیر اضافه کنید:
var toggled by remember { mutableStateOf(false) } val interactionSource = remember { MutableInteractionSource() } Column( modifier = Modifier .padding(16.dp) .fillMaxSize() .clickable(indication = null, interactionSource = interactionSource) { toggled = !toggled } ) { val offsetTarget = if (toggled) { IntOffset(150, 150) } else { IntOffset.Zero } val offset = animateIntOffsetAsState( targetValue = offsetTarget, label = "offset" ) Box( modifier = Modifier .size(100.dp) .background(colorBlue) ) Box( modifier = Modifier .layout { measurable, constraints -> val offsetValue = if (isLookingAhead) offsetTarget else offset.value val placeable = measurable.measure(constraints) layout(placeable.width + offsetValue.x, placeable.height + offsetValue.y) { placeable.placeRelative(offsetValue) } } .size(100.dp) .background(colorGreen) ) Box( modifier = Modifier .size(100.dp) .background(colorBlue) ) }

Modifier.layout{ }
متحرک کردن بالشتک از یک composable

برای متحرک سازی padding یک composable، از animateDpAsState
ترکیب شده با Modifier.padding()
استفاده کنید:
var toggled by remember { mutableStateOf(false) } val animatedPadding by animateDpAsState( if (toggled) { 0.dp } else { 20.dp }, label = "padding" ) Box( modifier = Modifier .aspectRatio(1f) .fillMaxSize() .padding(animatedPadding) .background(Color(0xff53D9A1)) .clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { toggled = !toggled } )
متحرک کردن ارتفاع یک ترکیب پذیر
برای متحرک سازی ارتفاع یک composable، از animateDpAsState
ترکیب شده با Modifier.graphicsLayer{ }
استفاده کنید. برای تغییر ارتفاع یکباره، از Modifier.shadow()
استفاده کنید. اگر سایه را متحرک می کنید، استفاده از Modifier.graphicsLayer{ }
گزینه کارآمدتر است.
val mutableInteractionSource = remember { MutableInteractionSource() } val pressed = mutableInteractionSource.collectIsPressedAsState() val elevation = animateDpAsState( targetValue = if (pressed.value) { 32.dp } else { 8.dp }, label = "elevation" ) Box( modifier = Modifier .size(100.dp) .align(Alignment.Center) .graphicsLayer { this.shadowElevation = elevation.value.toPx() } .clickable(interactionSource = mutableInteractionSource, indication = null) { } .background(colorGreen) ) { }
از طرف دیگر، از Card
composable استفاده کنید و ویژگی elevation را روی مقادیر مختلف در هر حالت تنظیم کنید.
مقیاس متن، ترجمه یا چرخش را متحرک کنید

هنگام متحرک سازی مقیاس، ترجمه یا چرخش متن، پارامتر textMotion
در TextStyle
روی TextMotion.Animated
تنظیم کنید. این امر انتقال نرمتر بین انیمیشنهای متنی را تضمین میکند. از Modifier.graphicsLayer{ }
برای ترجمه، چرخش یا مقیاس متن استفاده کنید.
val infiniteTransition = rememberInfiniteTransition(label = "infinite transition") val scale by infiniteTransition.animateFloat( initialValue = 1f, targetValue = 8f, animationSpec = infiniteRepeatable(tween(1000), RepeatMode.Reverse), label = "scale" ) Box(modifier = Modifier.fillMaxSize()) { Text( text = "Hello", modifier = Modifier .graphicsLayer { scaleX = scale scaleY = scale transformOrigin = TransformOrigin.Center } .align(Alignment.Center), // Text composable does not take TextMotion as a parameter. // Provide it via style argument but make sure that we are copying from current theme style = LocalTextStyle.current.copy(textMotion = TextMotion.Animated) ) }
رنگ متن را متحرک کنید

برای متحرک کردن رنگ متن، از color
لامبدا در BasicText
composable استفاده کنید:
val infiniteTransition = rememberInfiniteTransition(label = "infinite transition") val animatedColor by infiniteTransition.animateColor( initialValue = Color(0xFF60DDAD), targetValue = Color(0xFF4285F4), animationSpec = infiniteRepeatable(tween(1000), RepeatMode.Reverse), label = "color" ) BasicText( text = "Hello Compose", color = { animatedColor }, // ... )
بین انواع مختلف محتوا جابجا شوید

از AnimatedContent
برای متحرک سازی بین اجزای سازنده مختلف استفاده کنید، اگر فقط می خواهید یک محو استاندارد بین اجزای سازنده ایجاد کنید، از Crossfade
استفاده کنید.
var state by remember { mutableStateOf(UiState.Loading) } AnimatedContent( state, transitionSpec = { fadeIn( animationSpec = tween(3000) ) togetherWith fadeOut(animationSpec = tween(3000)) }, modifier = Modifier.clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { state = when (state) { UiState.Loading -> UiState.Loaded UiState.Loaded -> UiState.Error UiState.Error -> UiState.Loading } }, label = "Animated Content" ) { targetState -> when (targetState) { UiState.Loading -> { LoadingScreen() } UiState.Loaded -> { LoadedScreen() } UiState.Error -> { ErrorScreen() } } }
AnimatedContent
می توان برای نمایش انواع مختلف انتقال ورود و خروج سفارشی کرد. برای اطلاعات بیشتر، اسناد مربوط به AnimatedContent
را بخوانید یا این پست وبلاگ را در AnimatedContent
بخوانید.
در حین حرکت به مقاصد مختلف متحرک شوید

برای متحرک سازی انتقال بین اجزای سازنده هنگام استفاده از مصنوع ناوبری-نوشتن ، enterTransition
و exitTransition
در یک composable مشخص کنید. همچنین می توانید انیمیشن پیش فرض را برای استفاده برای همه مقاصد در سطح بالای NavHost
تنظیم کنید:
val navController = rememberNavController() NavHost( navController = navController, startDestination = "landing", enterTransition = { EnterTransition.None }, exitTransition = { ExitTransition.None } ) { composable("landing") { ScreenLanding( // ... ) } composable( "detail/{photoUrl}", arguments = listOf(navArgument("photoUrl") { type = NavType.StringType }), enterTransition = { fadeIn( animationSpec = tween( 300, easing = LinearEasing ) ) + slideIntoContainer( animationSpec = tween(300, easing = EaseIn), towards = AnimatedContentTransitionScope.SlideDirection.Start ) }, exitTransition = { fadeOut( animationSpec = tween( 300, easing = LinearEasing ) ) + slideOutOfContainer( animationSpec = tween(300, easing = EaseOut), towards = AnimatedContentTransitionScope.SlideDirection.End ) } ) { backStackEntry -> ScreenDetails( // ... ) } }
انواع مختلفی از انتقالهای ورود و خروج وجود دارد که جلوههای متفاوتی را برای محتوای ورودی و خروجی اعمال میکند، برای اطلاعات بیشتر به مستندات مراجعه کنید.
یک انیمیشن را تکرار کنید

از rememberInfiniteTransition
با animationSpec
infiniteRepeatable
برای تکرار مداوم انیمیشن خود استفاده کنید. RepeatModes
تغییر دهید تا مشخص کنید چگونه باید به جلو و عقب برود.
از finiteRepeatable
برای تکرار چندین بار استفاده کنید.
val infiniteTransition = rememberInfiniteTransition(label = "infinite") val color by infiniteTransition.animateColor( initialValue = Color.Green, targetValue = Color.Blue, animationSpec = infiniteRepeatable( animation = tween(1000, easing = LinearEasing), repeatMode = RepeatMode.Reverse ), label = "color" ) Column( modifier = Modifier.drawBehind { drawRect(color) } ) { // your composable here }
شروع یک انیمیشن در راه اندازی یک composable
LaunchedEffect
زمانی اجرا می شود که یک composable وارد ترکیب شود. با راهاندازی یک کامپوزیشن، یک انیمیشن را شروع میکند، میتوانید از آن برای تغییر حالت انیمیشن استفاده کنید. استفاده از Animatable
با متد animateTo
برای شروع انیمیشن هنگام راه اندازی:
val alphaAnimation = remember { Animatable(0f) } LaunchedEffect(Unit) { alphaAnimation.animateTo(1f) } Box( modifier = Modifier.graphicsLayer { alpha = alphaAnimation.value } )
انیمیشن های متوالی ایجاد کنید

از API های کوروتین Animatable
برای اجرای انیمیشن های متوالی یا همزمان استفاده کنید. فراخوانی animateTo
در Animatable
یکی پس از دیگری باعث می شود که هر انیمیشن قبل از ادامه منتظر بماند تا انیمیشن های قبلی به پایان برسد. این به این دلیل است که یک تابع تعلیق است.
val alphaAnimation = remember { Animatable(0f) } val yAnimation = remember { Animatable(0f) } LaunchedEffect("animationKey") { alphaAnimation.animateTo(1f) yAnimation.animateTo(100f) yAnimation.animateTo(500f, animationSpec = tween(100)) }
ایجاد انیمیشن های همزمان

برای دستیابی به انیمیشنهای همزمان از APIهای اصلی ( Animatable#animateTo()
یا animate
) یا Transition
API استفاده کنید. اگر از چندین تابع راه اندازی در یک زمینه معمولی استفاده کنید، انیمیشن ها را همزمان راه اندازی می کند:
val alphaAnimation = remember { Animatable(0f) } val yAnimation = remember { Animatable(0f) } LaunchedEffect("animationKey") { launch { alphaAnimation.animateTo(1f) } launch { yAnimation.animateTo(100f) } }
میتوانید از updateTransition
API برای استفاده از حالت یکسان برای درایو انیمیشنهای دارایی مختلف به طور همزمان استفاده کنید. مثال زیر دو ویژگی را که با تغییر حالت کنترل میشوند، متحرک میکند، rect
و borderWidth
:
var currentState by remember { mutableStateOf(BoxState.Collapsed) } val transition = updateTransition(currentState, label = "transition") val rect by transition.animateRect(label = "rect") { state -> when (state) { BoxState.Collapsed -> Rect(0f, 0f, 100f, 100f) BoxState.Expanded -> Rect(100f, 100f, 300f, 300f) } } val borderWidth by transition.animateDp(label = "borderWidth") { state -> when (state) { BoxState.Collapsed -> 1.dp BoxState.Expanded -> 0.dp } }
بهینه سازی عملکرد انیمیشن
انیمیشن ها در Compose می توانند مشکلات عملکردی ایجاد کنند. این به دلیل ماهیت انیمیشن است: حرکت یا تغییر سریع پیکسل ها روی صفحه، فریم به فریم برای ایجاد توهم حرکت.
مراحل مختلف Compose را در نظر بگیرید: ترکیب، چیدمان و ترسیم. اگر انیمیشن شما فاز طرحبندی را تغییر دهد، به همه اجزای سازنده آسیبدیده نیاز دارد که به نمایش گذاشته و دوباره ترسیم شوند. اگر انیمیشن شما در مرحله قرعه کشی اتفاق بیفتد، به طور پیش فرض عملکرد بیشتری نسبت به زمانی دارد که انیمیشن را در مرحله طرح بندی اجرا کنید، زیرا به طور کلی کار کمتری برای انجام دادن دارد.
برای اطمینان از اینکه برنامه شما در حین پویانمایی کمترین کار ممکن را انجام می دهد، در صورت امکان نسخه لامبدا یک Modifier
را انتخاب کنید. این کار از ترکیب مجدد صرفنظر می کند و انیمیشن را خارج از مرحله ترکیب بندی انجام می دهد، در غیر این صورت از Modifier.graphicsLayer{ }
استفاده کنید، زیرا این اصلاح کننده همیشه در مرحله ترسیم اجرا می شود. برای اطلاعات بیشتر در این مورد، به بخش خواندن به تعویق در اسناد عملکرد مراجعه کنید.
تغییر زمان انیمیشن
Compose به طور پیش فرض از انیمیشن های فنری برای اکثر انیمیشن ها استفاده می کند. فنرها یا انیمیشن های مبتنی بر فیزیک، طبیعی تر هستند. آنها همچنین قابل وقفه هستند زیرا به جای زمان ثابت، سرعت فعلی جسم را در نظر می گیرند. اگر میخواهید پیشفرض را لغو کنید، همه APIهای انیمیشنی که در بالا نشان داده شدهاند، این توانایی را دارند که animationSpec
را برای سفارشی کردن نحوه اجرای یک انیمیشن تنظیم کنند، چه بخواهید در مدت زمان معینی اجرا شود یا بیشتر پرشور باشد.
در زیر خلاصه ای از گزینه های مختلف animationSpec
آمده است:
-
spring
: انیمیشن مبتنی بر فیزیک، پیشفرض برای همه انیمیشنها. میتوانید سفتی یا نسبت میرایی را تغییر دهید تا به ظاهر و احساس انیمیشن متفاوتی برسید. -
tween
(مخفف بین ): انیمیشن مبتنی بر مدت زمان، بین دو مقدار با تابعEasing
متحرک می شود. -
keyframes
: مشخصاتی برای تعیین مقادیر در نقاط کلیدی خاصی در یک انیمیشن. -
repeatable
: مشخصات مبتنی بر مدت زمان که تعداد معینی بار اجرا می شود، مشخص شده توسطRepeatMode
. -
infiniteRepeatable
: مشخصات مبتنی بر مدت زمان که برای همیشه اجرا می شود. -
snap
: فوراً بدون هیچ گونه انیمیشنی به مقدار نهایی میچسبد.

برای اطلاعات بیشتر در مورد animationSpecs ، مستندات کامل را بخوانید.
منابع اضافی
برای نمونههای بیشتر از انیمیشنهای سرگرمکننده در Compose، به موارد زیر نگاهی بیندازید:
- 5 انیمیشن سریع در Compose
- حرکت چتر دریایی در Compose
- سفارشی کردن
AnimatedContent
در نوشتن - Easing به Easing توابع در Compose
Compose مکانیسمهای انیمیشن داخلی زیادی دارد و دانستن اینکه کدام یک را انتخاب کنید میتواند بسیار سخت باشد. در زیر لیستی از موارد رایج استفاده از انیمیشن آورده شده است. برای اطلاعات دقیق تر در مورد مجموعه کامل گزینه های API مختلف در دسترس شما، مستندات کامل Compose Animation را بخوانید.
ویژگی های متداول ترکیب پذیر را متحرک کنید
Compose API های مناسبی را ارائه می دهد که به شما امکان می دهد موارد استفاده رایج از انیمیشن را حل کنید. این بخش نشان میدهد که چگونه میتوانید ویژگیهای متداول یک composable را متحرک کنید.
متحرک ظاهر شدن / ناپدید شدن

از AnimatedVisibility
برای مخفی کردن یا نمایش Composable استفاده کنید. کودکان داخل AnimatedVisibility
می توانند از Modifier.animateEnterExit()
برای انتقال ورود یا خروج خود استفاده کنند.
var visible by remember { mutableStateOf(true) } // Animated visibility will eventually remove the item from the composition once the animation has finished. AnimatedVisibility(visible) { // your composable here // ... }
پارامترهای ورود و خروج AnimatedVisibility
به شما این امکان را می دهد تا نحوه رفتار یک composable را هنگام ظاهر شدن و ناپدید شدن پیکربندی کنید. برای اطلاعات بیشتر مستندات کامل را بخوانید.
یکی دیگر از گزینههای متحرک سازی نمایان شدن یک Composable، متحرک سازی آلفا در طول زمان با استفاده از animateFloatAsState
است:
var visible by remember { mutableStateOf(true) } val animatedAlpha by animateFloatAsState( targetValue = if (visible) 1.0f else 0f, label = "alpha" ) Box( modifier = Modifier .size(200.dp) .graphicsLayer { alpha = animatedAlpha } .clip(RoundedCornerShape(8.dp)) .background(colorGreen) .align(Alignment.TopCenter) ) { }
با این حال، تغییر آلفا با این هشدار همراه است که ترکیبپذیر در ترکیب باقی میماند و همچنان فضایی را که در آن قرار داده شده اشغال میکند. از طرف دیگر، AnimatedVisibility
در نهایت آیتم را از ترکیب حذف می کند.

رنگ پس زمینه را متحرک کنید

val animatedColor by animateColorAsState( if (animateBackgroundColor) colorGreen else colorBlue, label = "color" ) Column( modifier = Modifier.drawBehind { drawRect(animatedColor) } ) { // your composable here }
این گزینه کارایی بیشتری نسبت به استفاده از Modifier.background()
دارد. Modifier.background()
برای یک تنظیم رنگ یک شات قابل قبول است، اما زمانی که یک رنگ را متحرک می کنید در طول زمان، این می تواند باعث ترکیب مجدد بیش از حد لازم شود.
برای متحرک سازی بی نهایت رنگ پس زمینه، به تکرار بخش انیمیشن مراجعه کنید.
متحرک کردن به اندازه یک ترکیب

Compose به شما این امکان را می دهد که اندازه اجزای سازنده را به چند روش مختلف متحرک کنید. از animateContentSize()
برای انیمیشن های بین تغییرات اندازه قابل ترکیب استفاده کنید.
برای مثال، اگر کادری دارید که حاوی متنی است که میتواند از یک خط به چند خط گسترش یابد، میتوانید Modifier.animateContentSize()
برای دستیابی به یک انتقال روانتر استفاده کنید:
var expanded by remember { mutableStateOf(false) } Box( modifier = Modifier .background(colorBlue) .animateContentSize() .height(if (expanded) 400.dp else 200.dp) .fillMaxWidth() .clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { expanded = !expanded } ) { }
همچنین میتوانید از AnimatedContent
با SizeTransform
استفاده کنید تا چگونگی تغییر اندازه را توضیح دهید.
متحرک کردن موقعیت از composable

برای متحرک کردن موقعیت یک composable، از Modifier.offset{ }
ترکیب شده با animateIntOffsetAsState()
استفاده کنید.
var moved by remember { mutableStateOf(false) } val pxToMove = with(LocalDensity.current) { 100.dp.toPx().roundToInt() } val offset by animateIntOffsetAsState( targetValue = if (moved) { IntOffset(pxToMove, pxToMove) } else { IntOffset.Zero }, label = "offset" ) Box( modifier = Modifier .offset { offset } .background(colorBlue) .size(100.dp) .clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { moved = !moved } )
اگر میخواهید هنگام متحرک کردن موقعیت یا اندازه، مطمئن شوید که Composableها روی یا زیر دیگر composableها کشیده نمیشوند، از Modifier.layout{ }
استفاده کنید. این اصلاح کننده تغییرات اندازه و موقعیت را به والدین منتشر می کند، که سپس بر سایر کودکان تأثیر می گذارد.
به عنوان مثال، اگر در حال جابجایی یک Box
در یک Column
هستید و سایر فرزندان باید هنگام حرکت Box
حرکت کنند، اطلاعات افست را با Modifier.layout{ }
به صورت زیر اضافه کنید:
var toggled by remember { mutableStateOf(false) } val interactionSource = remember { MutableInteractionSource() } Column( modifier = Modifier .padding(16.dp) .fillMaxSize() .clickable(indication = null, interactionSource = interactionSource) { toggled = !toggled } ) { val offsetTarget = if (toggled) { IntOffset(150, 150) } else { IntOffset.Zero } val offset = animateIntOffsetAsState( targetValue = offsetTarget, label = "offset" ) Box( modifier = Modifier .size(100.dp) .background(colorBlue) ) Box( modifier = Modifier .layout { measurable, constraints -> val offsetValue = if (isLookingAhead) offsetTarget else offset.value val placeable = measurable.measure(constraints) layout(placeable.width + offsetValue.x, placeable.height + offsetValue.y) { placeable.placeRelative(offsetValue) } } .size(100.dp) .background(colorGreen) ) Box( modifier = Modifier .size(100.dp) .background(colorBlue) ) }

Modifier.layout{ }
متحرک کردن بالشتک از یک composable

برای متحرک سازی padding یک composable، از animateDpAsState
ترکیب شده با Modifier.padding()
استفاده کنید:
var toggled by remember { mutableStateOf(false) } val animatedPadding by animateDpAsState( if (toggled) { 0.dp } else { 20.dp }, label = "padding" ) Box( modifier = Modifier .aspectRatio(1f) .fillMaxSize() .padding(animatedPadding) .background(Color(0xff53D9A1)) .clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { toggled = !toggled } )
متحرک کردن ارتفاع یک ترکیب پذیر
برای متحرک سازی ارتفاع یک composable، از animateDpAsState
ترکیب شده با Modifier.graphicsLayer{ }
استفاده کنید. برای تغییر ارتفاع یکباره، از Modifier.shadow()
استفاده کنید. اگر سایه را متحرک می کنید، استفاده از Modifier.graphicsLayer{ }
گزینه کارآمدتر است.
val mutableInteractionSource = remember { MutableInteractionSource() } val pressed = mutableInteractionSource.collectIsPressedAsState() val elevation = animateDpAsState( targetValue = if (pressed.value) { 32.dp } else { 8.dp }, label = "elevation" ) Box( modifier = Modifier .size(100.dp) .align(Alignment.Center) .graphicsLayer { this.shadowElevation = elevation.value.toPx() } .clickable(interactionSource = mutableInteractionSource, indication = null) { } .background(colorGreen) ) { }
از طرف دیگر، از Card
composable استفاده کنید و ویژگی elevation را روی مقادیر مختلف در هر حالت تنظیم کنید.
مقیاس متن، ترجمه یا چرخش را متحرک کنید

هنگام متحرک سازی مقیاس، ترجمه یا چرخش متن، پارامتر textMotion
را در TextStyle
روی TextMotion.Animated
تنظیم کنید. این امر انتقال نرمتر بین انیمیشنهای متنی را تضمین میکند. از Modifier.graphicsLayer{ }
برای ترجمه، چرخش یا مقیاس متن استفاده کنید.
val infiniteTransition = rememberInfiniteTransition(label = "infinite transition") val scale by infiniteTransition.animateFloat( initialValue = 1f, targetValue = 8f, animationSpec = infiniteRepeatable(tween(1000), RepeatMode.Reverse), label = "scale" ) Box(modifier = Modifier.fillMaxSize()) { Text( text = "Hello", modifier = Modifier .graphicsLayer { scaleX = scale scaleY = scale transformOrigin = TransformOrigin.Center } .align(Alignment.Center), // Text composable does not take TextMotion as a parameter. // Provide it via style argument but make sure that we are copying from current theme style = LocalTextStyle.current.copy(textMotion = TextMotion.Animated) ) }
رنگ متن را متحرک کنید

برای متحرک کردن رنگ متن، از color
لامبدا در BasicText
composable استفاده کنید:
val infiniteTransition = rememberInfiniteTransition(label = "infinite transition") val animatedColor by infiniteTransition.animateColor( initialValue = Color(0xFF60DDAD), targetValue = Color(0xFF4285F4), animationSpec = infiniteRepeatable(tween(1000), RepeatMode.Reverse), label = "color" ) BasicText( text = "Hello Compose", color = { animatedColor }, // ... )
بین انواع مختلف محتوا جابجا شوید

از AnimatedContent
برای متحرک سازی بین اجزای سازنده مختلف استفاده کنید، اگر فقط می خواهید یک محو استاندارد بین اجزای سازنده ایجاد کنید، از Crossfade
استفاده کنید.
var state by remember { mutableStateOf(UiState.Loading) } AnimatedContent( state, transitionSpec = { fadeIn( animationSpec = tween(3000) ) togetherWith fadeOut(animationSpec = tween(3000)) }, modifier = Modifier.clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { state = when (state) { UiState.Loading -> UiState.Loaded UiState.Loaded -> UiState.Error UiState.Error -> UiState.Loading } }, label = "Animated Content" ) { targetState -> when (targetState) { UiState.Loading -> { LoadingScreen() } UiState.Loaded -> { LoadedScreen() } UiState.Error -> { ErrorScreen() } } }
AnimatedContent
می توان برای نمایش انواع مختلف انتقال ورود و خروج سفارشی کرد. برای اطلاعات بیشتر، اسناد مربوط به AnimatedContent
را بخوانید یا این پست وبلاگ را در AnimatedContent
بخوانید.
در حین حرکت به مقاصد مختلف متحرک شوید

برای متحرک سازی انتقال بین اجزای سازنده هنگام استفاده از مصنوع ناوبری-نوشتن ، enterTransition
و exitTransition
در یک composable مشخص کنید. همچنین می توانید انیمیشن پیش فرض را برای استفاده برای همه مقاصد در سطح بالای NavHost
تنظیم کنید:
val navController = rememberNavController() NavHost( navController = navController, startDestination = "landing", enterTransition = { EnterTransition.None }, exitTransition = { ExitTransition.None } ) { composable("landing") { ScreenLanding( // ... ) } composable( "detail/{photoUrl}", arguments = listOf(navArgument("photoUrl") { type = NavType.StringType }), enterTransition = { fadeIn( animationSpec = tween( 300, easing = LinearEasing ) ) + slideIntoContainer( animationSpec = tween(300, easing = EaseIn), towards = AnimatedContentTransitionScope.SlideDirection.Start ) }, exitTransition = { fadeOut( animationSpec = tween( 300, easing = LinearEasing ) ) + slideOutOfContainer( animationSpec = tween(300, easing = EaseOut), towards = AnimatedContentTransitionScope.SlideDirection.End ) } ) { backStackEntry -> ScreenDetails( // ... ) } }
انواع مختلفی از انتقالهای ورود و خروج وجود دارد که جلوههای متفاوتی را برای محتوای ورودی و خروجی اعمال میکند، برای اطلاعات بیشتر به مستندات مراجعه کنید.
یک انیمیشن را تکرار کنید

از rememberInfiniteTransition
با animationSpec
infiniteRepeatable
برای تکرار مداوم انیمیشن خود استفاده کنید. RepeatModes
تغییر دهید تا مشخص کنید چگونه باید به جلو و عقب برود.
از finiteRepeatable
برای تکرار چندین بار استفاده کنید.
val infiniteTransition = rememberInfiniteTransition(label = "infinite") val color by infiniteTransition.animateColor( initialValue = Color.Green, targetValue = Color.Blue, animationSpec = infiniteRepeatable( animation = tween(1000, easing = LinearEasing), repeatMode = RepeatMode.Reverse ), label = "color" ) Column( modifier = Modifier.drawBehind { drawRect(color) } ) { // your composable here }
شروع یک انیمیشن در راه اندازی یک composable
LaunchedEffect
زمانی اجرا می شود که یک composable وارد ترکیب شود. با راهاندازی یک کامپوزیشن، یک انیمیشن را شروع میکند، میتوانید از آن برای تغییر حالت انیمیشن استفاده کنید. استفاده از Animatable
با متد animateTo
برای شروع انیمیشن هنگام راه اندازی:
val alphaAnimation = remember { Animatable(0f) } LaunchedEffect(Unit) { alphaAnimation.animateTo(1f) } Box( modifier = Modifier.graphicsLayer { alpha = alphaAnimation.value } )
انیمیشن های متوالی ایجاد کنید

از API های کوروتین Animatable
برای اجرای انیمیشن های متوالی یا همزمان استفاده کنید. فراخوانی animateTo
در Animatable
یکی پس از دیگری باعث می شود که هر انیمیشن قبل از ادامه منتظر بماند تا انیمیشن های قبلی به پایان برسد. این به این دلیل است که یک تابع تعلیق است.
val alphaAnimation = remember { Animatable(0f) } val yAnimation = remember { Animatable(0f) } LaunchedEffect("animationKey") { alphaAnimation.animateTo(1f) yAnimation.animateTo(100f) yAnimation.animateTo(500f, animationSpec = tween(100)) }
ایجاد انیمیشن های همزمان

برای دستیابی به انیمیشنهای همزمان از APIهای اصلی ( Animatable#animateTo()
یا animate
) یا Transition
API استفاده کنید. اگر از چندین تابع راه اندازی در یک زمینه معمولی استفاده کنید، انیمیشن ها را همزمان راه اندازی می کند:
val alphaAnimation = remember { Animatable(0f) } val yAnimation = remember { Animatable(0f) } LaunchedEffect("animationKey") { launch { alphaAnimation.animateTo(1f) } launch { yAnimation.animateTo(100f) } }
میتوانید از updateTransition
API برای استفاده از حالت یکسان برای درایو انیمیشنهای دارایی مختلف به طور همزمان استفاده کنید. مثال زیر دو ویژگی را که با تغییر حالت کنترل میشوند، متحرک میکند، rect
و borderWidth
:
var currentState by remember { mutableStateOf(BoxState.Collapsed) } val transition = updateTransition(currentState, label = "transition") val rect by transition.animateRect(label = "rect") { state -> when (state) { BoxState.Collapsed -> Rect(0f, 0f, 100f, 100f) BoxState.Expanded -> Rect(100f, 100f, 300f, 300f) } } val borderWidth by transition.animateDp(label = "borderWidth") { state -> when (state) { BoxState.Collapsed -> 1.dp BoxState.Expanded -> 0.dp } }
بهینه سازی عملکرد انیمیشن
انیمیشن ها در Compose می توانند مشکلات عملکردی ایجاد کنند. این به دلیل ماهیت انیمیشن است: حرکت یا تغییر سریع پیکسل ها روی صفحه، فریم به فریم برای ایجاد توهم حرکت.
مراحل مختلف Compose را در نظر بگیرید: ترکیب، چیدمان و ترسیم. اگر انیمیشن شما فاز طرحبندی را تغییر دهد، به همه اجزای سازنده آسیبدیده نیاز دارد که به نمایش گذاشته و دوباره ترسیم شوند. اگر انیمیشن شما در مرحله قرعه کشی اتفاق بیفتد، به طور پیش فرض عملکرد بیشتری نسبت به زمانی دارد که انیمیشن را در مرحله طرح بندی اجرا کنید، زیرا به طور کلی کار کمتری برای انجام دادن دارد.
برای اطمینان از اینکه برنامه شما در حین پویانمایی کمترین کار ممکن را انجام می دهد، در صورت امکان نسخه لامبدا یک Modifier
را انتخاب کنید. این کار از ترکیب مجدد صرفنظر می کند و انیمیشن را خارج از مرحله ترکیب بندی انجام می دهد، در غیر این صورت از Modifier.graphicsLayer{ }
استفاده کنید، زیرا این اصلاح کننده همیشه در مرحله ترسیم اجرا می شود. برای اطلاعات بیشتر در این مورد، به بخش خواندن به تعویق در اسناد عملکرد مراجعه کنید.
تغییر زمان انیمیشن
Compose به طور پیش فرض از انیمیشن های فنری برای اکثر انیمیشن ها استفاده می کند. فنرها یا انیمیشن های مبتنی بر فیزیک، طبیعی تر هستند. آنها همچنین قابل وقفه هستند زیرا به جای زمان ثابت، سرعت فعلی جسم را در نظر می گیرند. اگر میخواهید پیشفرض را لغو کنید، همه APIهای انیمیشنی که در بالا نشان داده شدهاند، این توانایی را دارند که animationSpec
را برای سفارشی کردن نحوه اجرای یک انیمیشن تنظیم کنند، چه بخواهید در مدت زمان معینی اجرا شود یا بیشتر پرشور باشد.
در زیر خلاصه ای از گزینه های مختلف animationSpec
آمده است:
-
spring
: انیمیشن مبتنی بر فیزیک، پیشفرض برای همه انیمیشنها. میتوانید سفتی یا نسبت میرایی را تغییر دهید تا به ظاهر و احساس انیمیشن متفاوتی برسید. -
tween
(مخفف بین ): انیمیشن مبتنی بر مدت زمان، بین دو مقدار با تابعEasing
متحرک می شود. -
keyframes
: مشخصاتی برای تعیین مقادیر در نقاط کلیدی خاصی در یک انیمیشن. -
repeatable
: مشخصات مبتنی بر مدت زمان که تعداد معینی بار اجرا می شود، مشخص شده توسطRepeatMode
. -
infiniteRepeatable
: مشخصات مبتنی بر مدت زمان که برای همیشه اجرا می شود. -
snap
: فوراً بدون هیچ گونه انیمیشنی به مقدار نهایی میچسبد.

برای اطلاعات بیشتر در مورد animationSpecs ، مستندات کامل را بخوانید.
منابع اضافی
برای نمونههای بیشتر از انیمیشنهای سرگرمکننده در Compose، به موارد زیر نگاهی بیندازید:
- 5 انیمیشن سریع در Compose
- حرکت چتر دریایی در Compose
- سفارشی کردن
AnimatedContent
در نوشتن - Easing به Easing توابع در Compose
Compose مکانیسمهای انیمیشن داخلی زیادی دارد و دانستن اینکه کدام یک را انتخاب کنید میتواند بسیار سخت باشد. در زیر لیستی از موارد رایج استفاده از انیمیشن آورده شده است. برای اطلاعات دقیق تر در مورد مجموعه کامل گزینه های API مختلف در دسترس شما، مستندات کامل Compose Animation را بخوانید.
ویژگی های متداول ترکیب پذیر را متحرک کنید
Compose API های مناسبی را ارائه می دهد که به شما امکان می دهد موارد استفاده رایج از انیمیشن را حل کنید. این بخش نشان میدهد که چگونه میتوانید ویژگیهای متداول یک composable را متحرک کنید.
متحرک ظاهر شدن / ناپدید شدن

از AnimatedVisibility
برای مخفی کردن یا نمایش Composable استفاده کنید. کودکان داخل AnimatedVisibility
می توانند از Modifier.animateEnterExit()
برای انتقال ورود یا خروج خود استفاده کنند.
var visible by remember { mutableStateOf(true) } // Animated visibility will eventually remove the item from the composition once the animation has finished. AnimatedVisibility(visible) { // your composable here // ... }
پارامترهای ورود و خروج AnimatedVisibility
به شما این امکان را می دهد تا نحوه رفتار یک composable را هنگام ظاهر شدن و ناپدید شدن پیکربندی کنید. برای اطلاعات بیشتر مستندات کامل را بخوانید.
یکی دیگر از گزینههای متحرک سازی نمایان شدن یک Composable، متحرک سازی آلفا در طول زمان با استفاده از animateFloatAsState
است:
var visible by remember { mutableStateOf(true) } val animatedAlpha by animateFloatAsState( targetValue = if (visible) 1.0f else 0f, label = "alpha" ) Box( modifier = Modifier .size(200.dp) .graphicsLayer { alpha = animatedAlpha } .clip(RoundedCornerShape(8.dp)) .background(colorGreen) .align(Alignment.TopCenter) ) { }
با این حال، تغییر آلفا با این هشدار همراه است که ترکیبپذیر در ترکیب باقی میماند و همچنان فضایی را که در آن قرار داده شده اشغال میکند. از طرف دیگر، AnimatedVisibility
در نهایت آیتم را از ترکیب حذف می کند.

رنگ پس زمینه را متحرک کنید

val animatedColor by animateColorAsState( if (animateBackgroundColor) colorGreen else colorBlue, label = "color" ) Column( modifier = Modifier.drawBehind { drawRect(animatedColor) } ) { // your composable here }
این گزینه کارایی بیشتری نسبت به استفاده از Modifier.background()
دارد. Modifier.background()
برای یک تنظیم رنگ یک شات قابل قبول است، اما زمانی که یک رنگ را متحرک می کنید در طول زمان، این می تواند باعث ترکیب مجدد بیش از حد لازم شود.
برای متحرک سازی بی نهایت رنگ پس زمینه، به تکرار بخش انیمیشن مراجعه کنید.
متحرک کردن به اندازه یک ترکیب

Compose به شما این امکان را می دهد که اندازه اجزای سازنده را به چند روش مختلف متحرک کنید. از animateContentSize()
برای انیمیشن های بین تغییرات اندازه قابل ترکیب استفاده کنید.
برای مثال، اگر کادری دارید که حاوی متنی است که میتواند از یک خط به چند خط گسترش یابد، میتوانید Modifier.animateContentSize()
برای دستیابی به یک انتقال روانتر استفاده کنید:
var expanded by remember { mutableStateOf(false) } Box( modifier = Modifier .background(colorBlue) .animateContentSize() .height(if (expanded) 400.dp else 200.dp) .fillMaxWidth() .clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { expanded = !expanded } ) { }
همچنین میتوانید از AnimatedContent
با SizeTransform
استفاده کنید تا چگونگی تغییر اندازه را توضیح دهید.
متحرک کردن موقعیت از composable

برای متحرک کردن موقعیت یک composable، از Modifier.offset{ }
ترکیب شده با animateIntOffsetAsState()
استفاده کنید.
var moved by remember { mutableStateOf(false) } val pxToMove = with(LocalDensity.current) { 100.dp.toPx().roundToInt() } val offset by animateIntOffsetAsState( targetValue = if (moved) { IntOffset(pxToMove, pxToMove) } else { IntOffset.Zero }, label = "offset" ) Box( modifier = Modifier .offset { offset } .background(colorBlue) .size(100.dp) .clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { moved = !moved } )
اگر میخواهید هنگام متحرک کردن موقعیت یا اندازه، مطمئن شوید که Composableها روی یا زیر دیگر composableها کشیده نمیشوند، از Modifier.layout{ }
استفاده کنید. این اصلاح کننده تغییرات اندازه و موقعیت را به والدین منتشر می کند، که سپس بر سایر کودکان تأثیر می گذارد.
به عنوان مثال، اگر در حال جابجایی یک Box
در یک Column
هستید و سایر فرزندان باید هنگام حرکت Box
حرکت کنند، اطلاعات افست را با Modifier.layout{ }
به صورت زیر اضافه کنید:
var toggled by remember { mutableStateOf(false) } val interactionSource = remember { MutableInteractionSource() } Column( modifier = Modifier .padding(16.dp) .fillMaxSize() .clickable(indication = null, interactionSource = interactionSource) { toggled = !toggled } ) { val offsetTarget = if (toggled) { IntOffset(150, 150) } else { IntOffset.Zero } val offset = animateIntOffsetAsState( targetValue = offsetTarget, label = "offset" ) Box( modifier = Modifier .size(100.dp) .background(colorBlue) ) Box( modifier = Modifier .layout { measurable, constraints -> val offsetValue = if (isLookingAhead) offsetTarget else offset.value val placeable = measurable.measure(constraints) layout(placeable.width + offsetValue.x, placeable.height + offsetValue.y) { placeable.placeRelative(offsetValue) } } .size(100.dp) .background(colorGreen) ) Box( modifier = Modifier .size(100.dp) .background(colorBlue) ) }

Modifier.layout{ }
متحرک کردن بالشتک از یک composable

برای متحرک سازی padding یک composable، از animateDpAsState
ترکیب شده با Modifier.padding()
استفاده کنید:
var toggled by remember { mutableStateOf(false) } val animatedPadding by animateDpAsState( if (toggled) { 0.dp } else { 20.dp }, label = "padding" ) Box( modifier = Modifier .aspectRatio(1f) .fillMaxSize() .padding(animatedPadding) .background(Color(0xff53D9A1)) .clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { toggled = !toggled } )
متحرک کردن ارتفاع یک ترکیب پذیر
برای متحرک سازی ارتفاع یک composable، از animateDpAsState
ترکیب شده با Modifier.graphicsLayer{ }
استفاده کنید. برای تغییر ارتفاع یکباره، از Modifier.shadow()
استفاده کنید. اگر سایه را متحرک می کنید، استفاده از Modifier.graphicsLayer{ }
گزینه کارآمدتر است.
val mutableInteractionSource = remember { MutableInteractionSource() } val pressed = mutableInteractionSource.collectIsPressedAsState() val elevation = animateDpAsState( targetValue = if (pressed.value) { 32.dp } else { 8.dp }, label = "elevation" ) Box( modifier = Modifier .size(100.dp) .align(Alignment.Center) .graphicsLayer { this.shadowElevation = elevation.value.toPx() } .clickable(interactionSource = mutableInteractionSource, indication = null) { } .background(colorGreen) ) { }
از طرف دیگر، از Card
composable استفاده کنید و ویژگی elevation را روی مقادیر مختلف در هر حالت تنظیم کنید.
مقیاس متن، ترجمه یا چرخش را متحرک کنید

هنگام متحرک سازی مقیاس، ترجمه یا چرخش متن، پارامتر textMotion
در TextStyle
روی TextMotion.Animated
تنظیم کنید. این امر انتقال نرمتر بین انیمیشنهای متنی را تضمین میکند. از Modifier.graphicsLayer{ }
برای ترجمه، چرخش یا مقیاس متن استفاده کنید.
val infiniteTransition = rememberInfiniteTransition(label = "infinite transition") val scale by infiniteTransition.animateFloat( initialValue = 1f, targetValue = 8f, animationSpec = infiniteRepeatable(tween(1000), RepeatMode.Reverse), label = "scale" ) Box(modifier = Modifier.fillMaxSize()) { Text( text = "Hello", modifier = Modifier .graphicsLayer { scaleX = scale scaleY = scale transformOrigin = TransformOrigin.Center } .align(Alignment.Center), // Text composable does not take TextMotion as a parameter. // Provide it via style argument but make sure that we are copying from current theme style = LocalTextStyle.current.copy(textMotion = TextMotion.Animated) ) }
رنگ متن را متحرک کنید

برای متحرک کردن رنگ متن، از color
لامبدا در BasicText
composable استفاده کنید:
val infiniteTransition = rememberInfiniteTransition(label = "infinite transition") val animatedColor by infiniteTransition.animateColor( initialValue = Color(0xFF60DDAD), targetValue = Color(0xFF4285F4), animationSpec = infiniteRepeatable(tween(1000), RepeatMode.Reverse), label = "color" ) BasicText( text = "Hello Compose", color = { animatedColor }, // ... )
بین انواع مختلف محتوا جابجا شوید

از AnimatedContent
برای متحرک سازی بین اجزای سازنده مختلف استفاده کنید، اگر فقط می خواهید یک محو استاندارد بین اجزای سازنده ایجاد کنید، از Crossfade
استفاده کنید.
var state by remember { mutableStateOf(UiState.Loading) } AnimatedContent( state, transitionSpec = { fadeIn( animationSpec = tween(3000) ) togetherWith fadeOut(animationSpec = tween(3000)) }, modifier = Modifier.clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { state = when (state) { UiState.Loading -> UiState.Loaded UiState.Loaded -> UiState.Error UiState.Error -> UiState.Loading } }, label = "Animated Content" ) { targetState -> when (targetState) { UiState.Loading -> { LoadingScreen() } UiState.Loaded -> { LoadedScreen() } UiState.Error -> { ErrorScreen() } } }
AnimatedContent
می توان برای نمایش انواع مختلف انتقال ورود و خروج سفارشی کرد. برای اطلاعات بیشتر، اسناد مربوط به AnimatedContent
را بخوانید یا این پست وبلاگ را در AnimatedContent
بخوانید.
در حین حرکت به مقاصد مختلف متحرک شوید

برای متحرک سازی انتقال بین اجزای سازنده هنگام استفاده از مصنوع ناوبری-نوشتن ، enterTransition
و exitTransition
در یک composable مشخص کنید. همچنین می توانید انیمیشن پیش فرض را برای استفاده برای همه مقاصد در سطح بالای NavHost
تنظیم کنید:
val navController = rememberNavController() NavHost( navController = navController, startDestination = "landing", enterTransition = { EnterTransition.None }, exitTransition = { ExitTransition.None } ) { composable("landing") { ScreenLanding( // ... ) } composable( "detail/{photoUrl}", arguments = listOf(navArgument("photoUrl") { type = NavType.StringType }), enterTransition = { fadeIn( animationSpec = tween( 300, easing = LinearEasing ) ) + slideIntoContainer( animationSpec = tween(300, easing = EaseIn), towards = AnimatedContentTransitionScope.SlideDirection.Start ) }, exitTransition = { fadeOut( animationSpec = tween( 300, easing = LinearEasing ) ) + slideOutOfContainer( animationSpec = tween(300, easing = EaseOut), towards = AnimatedContentTransitionScope.SlideDirection.End ) } ) { backStackEntry -> ScreenDetails( // ... ) } }
انواع مختلفی از انتقالهای ورود و خروج وجود دارد که جلوههای متفاوتی را برای محتوای ورودی و خروجی اعمال میکند، برای اطلاعات بیشتر به مستندات مراجعه کنید.
یک انیمیشن را تکرار کنید

از rememberInfiniteTransition
با animationSpec
infiniteRepeatable
برای تکرار مداوم انیمیشن خود استفاده کنید. RepeatModes
تغییر دهید تا مشخص کنید چگونه باید به جلو و عقب برود.
از finiteRepeatable
برای تکرار چندین بار استفاده کنید.
val infiniteTransition = rememberInfiniteTransition(label = "infinite") val color by infiniteTransition.animateColor( initialValue = Color.Green, targetValue = Color.Blue, animationSpec = infiniteRepeatable( animation = tween(1000, easing = LinearEasing), repeatMode = RepeatMode.Reverse ), label = "color" ) Column( modifier = Modifier.drawBehind { drawRect(color) } ) { // your composable here }
شروع یک انیمیشن در راه اندازی یک composable
LaunchedEffect
زمانی اجرا می شود که یک composable وارد ترکیب شود. با راهاندازی یک کامپوزیشن، یک انیمیشن را شروع میکند، میتوانید از آن برای تغییر حالت انیمیشن استفاده کنید. استفاده از Animatable
با متد animateTo
برای شروع انیمیشن هنگام راه اندازی:
val alphaAnimation = remember { Animatable(0f) } LaunchedEffect(Unit) { alphaAnimation.animateTo(1f) } Box( modifier = Modifier.graphicsLayer { alpha = alphaAnimation.value } )
انیمیشن های متوالی ایجاد کنید

از API های کوروتین Animatable
برای اجرای انیمیشن های متوالی یا همزمان استفاده کنید. فراخوانی animateTo
در Animatable
یکی پس از دیگری باعث می شود که هر انیمیشن قبل از ادامه منتظر بماند تا انیمیشن های قبلی به پایان برسد. این به این دلیل است که یک تابع تعلیق است.
val alphaAnimation = remember { Animatable(0f) } val yAnimation = remember { Animatable(0f) } LaunchedEffect("animationKey") { alphaAnimation.animateTo(1f) yAnimation.animateTo(100f) yAnimation.animateTo(500f, animationSpec = tween(100)) }
ایجاد انیمیشن های همزمان

برای دستیابی به انیمیشنهای همزمان از APIهای اصلی ( Animatable#animateTo()
یا animate
) یا Transition
API استفاده کنید. اگر از چندین تابع راه اندازی در یک زمینه معمولی استفاده کنید، انیمیشن ها را همزمان راه اندازی می کند:
val alphaAnimation = remember { Animatable(0f) } val yAnimation = remember { Animatable(0f) } LaunchedEffect("animationKey") { launch { alphaAnimation.animateTo(1f) } launch { yAnimation.animateTo(100f) } }
میتوانید از updateTransition
API برای استفاده از حالت یکسان برای درایو انیمیشنهای دارایی مختلف به طور همزمان استفاده کنید. مثال زیر دو ویژگی را که با تغییر حالت کنترل میشوند، متحرک میکند، rect
و borderWidth
:
var currentState by remember { mutableStateOf(BoxState.Collapsed) } val transition = updateTransition(currentState, label = "transition") val rect by transition.animateRect(label = "rect") { state -> when (state) { BoxState.Collapsed -> Rect(0f, 0f, 100f, 100f) BoxState.Expanded -> Rect(100f, 100f, 300f, 300f) } } val borderWidth by transition.animateDp(label = "borderWidth") { state -> when (state) { BoxState.Collapsed -> 1.dp BoxState.Expanded -> 0.dp } }
بهینه سازی عملکرد انیمیشن
انیمیشن ها در Compose می توانند مشکلات عملکردی ایجاد کنند. این به دلیل ماهیت انیمیشن است: حرکت یا تغییر سریع پیکسل ها روی صفحه، فریم به فریم برای ایجاد توهم حرکت.
مراحل مختلف Compose را در نظر بگیرید: ترکیب، چیدمان و ترسیم. اگر انیمیشن شما فاز طرحبندی را تغییر دهد، به همه اجزای سازنده آسیبدیده نیاز دارد که به نمایش گذاشته و دوباره ترسیم شوند. اگر انیمیشن شما در مرحله قرعه کشی اتفاق بیفتد، به طور پیش فرض عملکرد بیشتری نسبت به زمانی دارد که انیمیشن را در مرحله طرح بندی اجرا کنید، زیرا به طور کلی کار کمتری برای انجام دادن دارد.
برای اطمینان از اینکه برنامه شما در حین انیمیشن کمترین کار را انجام می دهد ، در صورت امکان نسخه Lambda از یک Modifier
را انتخاب کنید. این بازخوانی را انجام می دهد و انیمیشن را در خارج از مرحله ترکیب انجام می دهد ، در غیر این صورت از Modifier.graphicsLayer{ }
، زیرا این اصلاح کننده همیشه در مرحله قرعه کشی اجرا می شود. برای کسب اطلاعات بیشتر در این مورد ، به بخش Deferring Reads در مستندات عملکرد مراجعه کنید.
زمان انیمیشن را تغییر دهید
آهنگسازی به طور پیش فرض از انیمیشن های بهاری برای اکثر انیمیشن ها استفاده می کند. چشمه ها یا انیمیشن های مبتنی بر فیزیک احساس طبیعی تر می کنند. آنها همچنین به جای زمان ثابت ، سرعت فعلی شی را در نظر می گیرند. اگر می خواهید پیش فرض را نادیده بگیرید ، تمام API های انیمیشن که در بالا نشان داده شده است ، این توانایی را دارند که یک animationSpec
تنظیم کنند تا نحوه اجرای یک انیمیشن را تنظیم کند ، خواه بخواهید آن را در مدت زمان مشخصی اجرا کنید یا تند و تیز تر باشید.
در زیر خلاصه ای از گزینه های مختلف animationSpec
است:
-
spring
: انیمیشن مبتنی بر فیزیک ، پیش فرض برای همه انیمیشن ها. برای دستیابی به ظاهری و احساس انیمیشن متفاوت می توانید سفتی یا میرایی را تغییر دهید. -
tween
(کوتاه برای بین ): انیمیشن مبتنی بر مدت زمان ، انیمیشن بین دو مقدار با یک عملکردEasing
. -
keyframes
: مشخصات مشخص کردن مقادیر در نقاط کلیدی خاص در یک انیمیشن. -
repeatable
: مشخصات مبتنی بر مدت زمان که تعداد مشخصی از بارها و بارها را اجرا می کند ، مشخص شده توسطRepeatMode
. -
infiniteRepeatable
: مشخصات مبتنی بر مدت زمان که برای همیشه اجرا می شود. -
snap
: فوراً به مقدار نهایی بدون هیچ انیمیشن می رسد.

برای اطلاعات بیشتر در مورد AnimationsPecs مستندات کامل را بخوانید.
منابع اضافی
برای مثال های بیشتر از انیمیشن های سرگرم کننده در آهنگسازی ، به موارد زیر نگاهی بیندازید:
- 5 انیمیشن سریع در آهنگسازی
- حرکت چتر دریایی در آهنگسازی
- سفارشی کردن
AnimatedContent
در آهنگسازی - تسکین به عملکردهای تسکین در آهنگسازی
آهنگسازی بسیاری از مکانیسم های انیمیشن داخلی دارد و می تواند بسیار جالب باشد که بدانید کدام یک را انتخاب کنید. در زیر لیستی از موارد استفاده مشترک انیمیشن آورده شده است. برای کسب اطلاعات بیشتر در مورد مجموعه کامل گزینه های مختلف API در دسترس شما ، مستندات کامل انیمیشن آهنگسازی را بخوانید.
خصوصیات ترکیب مشترک را تحریک کنید
آهنگسازی API های مناسب را فراهم می کند که به شما امکان می دهد بسیاری از موارد استفاده از انیمیشن مشترک را حل کنید. این بخش نشان می دهد که چگونه می توانید خصوصیات مشترک یک ترکیب را تحریک کنید.
ظاهر شدن / ناپدید شدن

برای مخفی کردن یا نمایش یک ترکیب AnimatedVisibility
استفاده کنید. کودکان در داخل AnimatedVisibility
می توانند از Modifier.animateEnterExit()
برای انتقال خود یا خروج خود.
var visible by remember { mutableStateOf(true) } // Animated visibility will eventually remove the item from the composition once the animation has finished. AnimatedVisibility(visible) { // your composable here // ... }
پارامترهای Enter and Exit از AnimatedVisibility
به شما امکان می دهد تا نحوه عملکرد یک ترکیب را هنگام ظاهر شدن و ناپدید شدن تنظیم کنید. برای اطلاعات بیشتر مستندات کامل را بخوانید.
گزینه دیگر برای متحرک دید یک ترکیب ، تحریک آلفا به مرور زمان با استفاده از animateFloatAsState
است:
var visible by remember { mutableStateOf(true) } val animatedAlpha by animateFloatAsState( targetValue = if (visible) 1.0f else 0f, label = "alpha" ) Box( modifier = Modifier .size(200.dp) .graphicsLayer { alpha = animatedAlpha } .clip(RoundedCornerShape(8.dp)) .background(colorGreen) .align(Alignment.TopCenter) ) { }
با این حال ، تغییر آلفا با این احتیاط همراه است که این ترکیب در ترکیب باقی مانده و همچنان فضایی را که در آن گذاشته شده است ، ادامه می دهد. این می تواند باعث شود خوانندگان صفحه نمایش و سایر مکانیسم های دسترسی هنوز مورد را در صفحه نمایش در نظر بگیرند. از طرف دیگر ، AnimatedVisibility
در نهایت مورد را از ترکیب خارج می کند.

رنگ پس زمینه

val animatedColor by animateColorAsState( if (animateBackgroundColor) colorGreen else colorBlue, label = "color" ) Column( modifier = Modifier.drawBehind { drawRect(animatedColor) } ) { // your composable here }
این گزینه نسبت به استفاده از Modifier.background()
عملکرد بیشتری دارد. Modifier.background()
برای تنظیم رنگ یک شات قابل قبول است ، اما هنگام متحرک کردن یک رنگ به مرور زمان ، این می تواند باعث ایجاد مجدد بیشتر از حد لازم شود.
برای انیمیشن بی نهایت رنگ پس زمینه ، به تکرار یک بخش انیمیشن مراجعه کنید.
اندازه یک ترکیب را تحریک کنید

آهنگسازی به شما امکان می دهد اندازه آهنگسازان را از چند طریق مختلف تحریک کنید. برای انیمیشن های بین تغییرات اندازه ترکیب ، از animateContentSize()
استفاده کنید.
به عنوان مثال ، اگر جعبه ای دارید که حاوی متن است که می تواند از یک خط به چند خط گسترش یابد ، می توانید از Modifier.animateContentSize()
برای دستیابی به یک انتقال نرم تر:
var expanded by remember { mutableStateOf(false) } Box( modifier = Modifier .background(colorBlue) .animateContentSize() .height(if (expanded) 400.dp else 200.dp) .fillMaxWidth() .clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { expanded = !expanded } ) { }
همچنین می توانید از AnimatedContent
استفاده کنید ، با یک SizeTransform
برای توصیف چگونگی تغییر اندازه.
موقعیت تحریک کننده ترکیب

برای تحریک موقعیت یک ترکیب ، از Modifier.offset{ }
همراه با animateIntOffsetAsState()
استفاده کنید.
var moved by remember { mutableStateOf(false) } val pxToMove = with(LocalDensity.current) { 100.dp.toPx().roundToInt() } val offset by animateIntOffsetAsState( targetValue = if (moved) { IntOffset(pxToMove, pxToMove) } else { IntOffset.Zero }, label = "offset" ) Box( modifier = Modifier .offset { offset } .background(colorBlue) .size(100.dp) .clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { moved = !moved } )
اگر می خواهید اطمینان حاصل کنید که ترکیبات در هنگام انیمیشن موقعیت یا اندازه دیگر از ترکیبات دیگر یا زیر سایر آهنگسازی ها ترسیم نشده اند ، از Modifier.layout{ }
. این اصلاح کننده اندازه و موقعیت را در والدین ایجاد می کند ، که سپس بر سایر کودکان تأثیر می گذارد.
به عنوان مثال ، اگر شما یک Box
در یک Column
حرکت می دهید و کودکان دیگر هنگام حرکت Box
باید حرکت کنند ، اطلاعات افست را با Modifier.layout{ }
به شرح زیر است:
var toggled by remember { mutableStateOf(false) } val interactionSource = remember { MutableInteractionSource() } Column( modifier = Modifier .padding(16.dp) .fillMaxSize() .clickable(indication = null, interactionSource = interactionSource) { toggled = !toggled } ) { val offsetTarget = if (toggled) { IntOffset(150, 150) } else { IntOffset.Zero } val offset = animateIntOffsetAsState( targetValue = offsetTarget, label = "offset" ) Box( modifier = Modifier .size(100.dp) .background(colorBlue) ) Box( modifier = Modifier .layout { measurable, constraints -> val offsetValue = if (isLookingAhead) offsetTarget else offset.value val placeable = measurable.measure(constraints) layout(placeable.width + offsetValue.x, placeable.height + offsetValue.y) { placeable.placeRelative(offsetValue) } } .size(100.dp) .background(colorGreen) ) Box( modifier = Modifier .size(100.dp) .background(colorBlue) ) }

Modifier.layout{ }
تحریم بالشتک یک ترکیب

برای تحریک کردن بالشتک یک ترکیب ، از animateDpAsState
همراه با Modifier.padding()
:
var toggled by remember { mutableStateOf(false) } val animatedPadding by animateDpAsState( if (toggled) { 0.dp } else { 20.dp }, label = "padding" ) Box( modifier = Modifier .aspectRatio(1f) .fillMaxSize() .padding(animatedPadding) .background(Color(0xff53D9A1)) .clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { toggled = !toggled } )
ارتفاع یک آهنگسازی
برای تحریک ارتفاع یک ترکیب ، از animateDpAsState
همراه با Modifier.graphicsLayer{ }
. برای تغییر یک بار ارتفاع ، از Modifier.shadow()
. اگر سایه را متحرک می کنید ، با استفاده از Modifier.graphicsLayer{ }
اصلاح کننده گزینه اجرا کننده تر است.
val mutableInteractionSource = remember { MutableInteractionSource() } val pressed = mutableInteractionSource.collectIsPressedAsState() val elevation = animateDpAsState( targetValue = if (pressed.value) { 32.dp } else { 8.dp }, label = "elevation" ) Box( modifier = Modifier .size(100.dp) .align(Alignment.Center) .graphicsLayer { this.shadowElevation = elevation.value.toPx() } .clickable(interactionSource = mutableInteractionSource, indication = null) { } .background(colorGreen) ) { }
از طرف دیگر ، از Card
Composive استفاده کنید و خاصیت ارتفاع را بر روی مقادیر مختلف در هر حالت تنظیم کنید.
مقیاس متن ، ترجمه یا چرخش

هنگام انیمیشن مقیاس ، ترجمه یا چرخش متن ، پارامتر textMotion
را در TextStyle
به TextMotion.Animated
تنظیم کنید. این امر انتقال نرم و صاف بین انیمیشن های متنی را تضمین می کند. برای ترجمه ، چرخش یا مقیاس متن Modifier.graphicsLayer{ }
استفاده کنید.
val infiniteTransition = rememberInfiniteTransition(label = "infinite transition") val scale by infiniteTransition.animateFloat( initialValue = 1f, targetValue = 8f, animationSpec = infiniteRepeatable(tween(1000), RepeatMode.Reverse), label = "scale" ) Box(modifier = Modifier.fillMaxSize()) { Text( text = "Hello", modifier = Modifier .graphicsLayer { scaleX = scale scaleY = scale transformOrigin = TransformOrigin.Center } .align(Alignment.Center), // Text composable does not take TextMotion as a parameter. // Provide it via style argument but make sure that we are copying from current theme style = LocalTextStyle.current.copy(textMotion = TextMotion.Animated) ) }
رنگ متن متحرک

برای تحریک رنگ متن ، از color
Lambda در ترکیب BasicText
استفاده کنید:
val infiniteTransition = rememberInfiniteTransition(label = "infinite transition") val animatedColor by infiniteTransition.animateColor( initialValue = Color(0xFF60DDAD), targetValue = Color(0xFF4285F4), animationSpec = infiniteRepeatable(tween(1000), RepeatMode.Reverse), label = "color" ) BasicText( text = "Hello Compose", color = { animatedColor }, // ... )
بین انواع مختلف محتوا جابجا شوید

از AnimatedContent
برای جابجایی بین آهنگ های مختلف استفاده کنید ، اگر فقط می خواهید یک محو استاندارد بین Composables ، از Crossfade
استفاده کنید.
var state by remember { mutableStateOf(UiState.Loading) } AnimatedContent( state, transitionSpec = { fadeIn( animationSpec = tween(3000) ) togetherWith fadeOut(animationSpec = tween(3000)) }, modifier = Modifier.clickable( interactionSource = remember { MutableInteractionSource() }, indication = null ) { state = when (state) { UiState.Loading -> UiState.Loaded UiState.Loaded -> UiState.Error UiState.Error -> UiState.Loading } }, label = "Animated Content" ) { targetState -> when (targetState) { UiState.Loading -> { LoadingScreen() } UiState.Loaded -> { LoadedScreen() } UiState.Error -> { ErrorScreen() } } }
AnimatedContent
می توان سفارشی کرد تا انواع مختلفی از انتقال Enter و Exit را نشان دهد. برای اطلاعات بیشتر ، مستندات مربوط به AnimatedContent
را بخوانید یا این پست وبلاگ را در AnimatedContent
بخوانید.
در حالی که به مقصد های مختلف حرکت می کنید ، متحرک شوید

برای تحریک انتقال بین آهنگسازان هنگام استفاده از مصنوعات با استفاده از ناوبری ، enterTransition
و exitTransition
را در یک ترکیب مشخص کنید. همچنین می توانید انیمیشن پیش فرض را برای همه مقصد در سطح بالا NavHost
تنظیم کنید:
val navController = rememberNavController() NavHost( navController = navController, startDestination = "landing", enterTransition = { EnterTransition.None }, exitTransition = { ExitTransition.None } ) { composable("landing") { ScreenLanding( // ... ) } composable( "detail/{photoUrl}", arguments = listOf(navArgument("photoUrl") { type = NavType.StringType }), enterTransition = { fadeIn( animationSpec = tween( 300, easing = LinearEasing ) ) + slideIntoContainer( animationSpec = tween(300, easing = EaseIn), towards = AnimatedContentTransitionScope.SlideDirection.Start ) }, exitTransition = { fadeOut( animationSpec = tween( 300, easing = LinearEasing ) ) + slideOutOfContainer( animationSpec = tween(300, easing = EaseOut), towards = AnimatedContentTransitionScope.SlideDirection.End ) } ) { backStackEntry -> ScreenDetails( // ... ) } }
انواع مختلفی از انتقال Enter و Exit وجود دارد که جلوه های مختلفی را برای محتوای ورودی و خروجی به کار می برد ، برای اطلاعات بیشتر به اسناد مراجعه کنید.
یک انیمیشن را تکرار کنید

برای تکرار مداوم animationSpec
خود ، از rememberInfiniteTransition
infiniteRepeatable
استفاده کنید. RepeatModes
تغییر دهید تا مشخص شود که چگونه باید به عقب و جلو برود.
برای تکرار تعداد مشخصی بار finiteRepeatable
استفاده کنید.
val infiniteTransition = rememberInfiniteTransition(label = "infinite") val color by infiniteTransition.animateColor( initialValue = Color.Green, targetValue = Color.Blue, animationSpec = infiniteRepeatable( animation = tween(1000, easing = LinearEasing), repeatMode = RepeatMode.Reverse ), label = "color" ) Column( modifier = Modifier.drawBehind { drawRect(color) } ) { // your composable here }
یک انیمیشن را در هنگام راه اندازی یک ترکیب شروع کنید
هنگامی که یک ترکیب کننده وارد ترکیب می شوند ، LaunchedEffect
اجرا می شود. این یک انیمیشن را برای راه اندازی یک ترکیب شروع می کند ، می توانید از این کار برای تغییر وضعیت انیمیشن استفاده کنید. استفاده از Animatable
با روش animateTo
برای شروع انیمیشن در راه اندازی:
val alphaAnimation = remember { Animatable(0f) } LaunchedEffect(Unit) { alphaAnimation.animateTo(1f) } Box( modifier = Modifier.graphicsLayer { alpha = alphaAnimation.value } )
انیمیشن های متوالی ایجاد کنید

برای اجرای انیمیشن های متوالی یا همزمان از API های Coroutine Animatable
استفاده کنید. تماس با animateTo
در یک Animatable
یکی پس از دیگری باعث می شود که هر انیمیشن منتظر بماند تا انیمیشن های قبلی قبل از ادامه کار به پایان برسد. این امر به این دلیل است که این یک عملکرد تعلیق است.
val alphaAnimation = remember { Animatable(0f) } val yAnimation = remember { Animatable(0f) } LaunchedEffect("animationKey") { alphaAnimation.animateTo(1f) yAnimation.animateTo(100f) yAnimation.animateTo(500f, animationSpec = tween(100)) }
انیمیشن های همزمان ایجاد کنید

برای دستیابی به انیمیشن های همزمان ، از API های Coroutine ( Animatable#animateTo()
یا animate
) یا API Transition
استفاده کنید. اگر از چندین توابع پرتاب در یک زمینه Coroutine استفاده می کنید ، انیمیشن ها را همزمان راه اندازی می کند:
val alphaAnimation = remember { Animatable(0f) } val yAnimation = remember { Animatable(0f) } LaunchedEffect("animationKey") { launch { alphaAnimation.animateTo(1f) } launch { yAnimation.animateTo(100f) } }
شما می توانید از API updateTransition
استفاده کنید تا از همان حالت استفاده کنید تا همزمان انیمیشن های مختلف املاک را هدایت کنید. مثال زیر دو خاصیت کنترل شده توسط تغییر حالت ، rect
و borderWidth
متحرک می کند:
var currentState by remember { mutableStateOf(BoxState.Collapsed) } val transition = updateTransition(currentState, label = "transition") val rect by transition.animateRect(label = "rect") { state -> when (state) { BoxState.Collapsed -> Rect(0f, 0f, 100f, 100f) BoxState.Expanded -> Rect(100f, 100f, 300f, 300f) } } val borderWidth by transition.animateDp(label = "borderWidth") { state -> when (state) { BoxState.Collapsed -> 1.dp BoxState.Expanded -> 0.dp } }
عملکرد انیمیشن را بهینه کنید
انیمیشن ها در آهنگسازی می توانند باعث ایجاد مشکلات عملکرد شوند. این به دلیل ماهیت آنچه یک انیمیشن است: حرکت یا تغییر پیکسل ها روی صفحه نمایش سریع ، قاب به قاب برای ایجاد توهم حرکت.
مراحل مختلف آهنگسازی را در نظر بگیرید: ترکیب ، چیدمان و قرعه کشی. اگر انیمیشن شما مرحله طرح بندی را تغییر دهد ، به کلیه ترکیبات آسیب دیده نیاز دارد تا بتوانند رله و بازسازی مجدد شوند. اگر انیمیشن شما در مرحله قرعه کشی اتفاق می افتد ، به طور پیش فرض بیشتر از آن است که بخواهید انیمیشن را در مرحله چیدمان اجرا کنید ، زیرا کار کمتری برای انجام کلی خواهد داشت.
برای اطمینان از اینکه برنامه شما در حین انیمیشن کمترین کار را انجام می دهد ، در صورت امکان نسخه Lambda از یک Modifier
را انتخاب کنید. این بازخوانی را انجام می دهد و انیمیشن را در خارج از مرحله ترکیب انجام می دهد ، در غیر این صورت از Modifier.graphicsLayer{ }
، زیرا این اصلاح کننده همیشه در مرحله قرعه کشی اجرا می شود. برای کسب اطلاعات بیشتر در این مورد ، به بخش Deferring Reads در مستندات عملکرد مراجعه کنید.
زمان انیمیشن را تغییر دهید
آهنگسازی به طور پیش فرض از انیمیشن های بهاری برای اکثر انیمیشن ها استفاده می کند. چشمه ها یا انیمیشن های مبتنی بر فیزیک احساس طبیعی تر می کنند. آنها همچنین به جای زمان ثابت ، سرعت فعلی شی را در نظر می گیرند. اگر می خواهید پیش فرض را نادیده بگیرید ، تمام API های انیمیشن که در بالا نشان داده شده است ، این توانایی را دارند که یک animationSpec
تنظیم کنند تا نحوه اجرای یک انیمیشن را تنظیم کند ، خواه بخواهید آن را در مدت زمان مشخصی اجرا کنید یا تند و تیز تر باشید.
در زیر خلاصه ای از گزینه های مختلف animationSpec
است:
-
spring
: انیمیشن مبتنی بر فیزیک ، پیش فرض برای همه انیمیشن ها. برای دستیابی به ظاهری و احساس انیمیشن متفاوت می توانید سفتی یا میرایی را تغییر دهید. -
tween
(کوتاه برای بین ): انیمیشن مبتنی بر مدت زمان ، انیمیشن بین دو مقدار با یک عملکردEasing
. -
keyframes
: مشخصات مشخص کردن مقادیر در نقاط کلیدی خاص در یک انیمیشن. -
repeatable
: مشخصات مبتنی بر مدت زمان که تعداد مشخصی از بارها و بارها را اجرا می کند ، مشخص شده توسطRepeatMode
. -
infiniteRepeatable
: مشخصات مبتنی بر مدت زمان که برای همیشه اجرا می شود. -
snap
: فوراً به مقدار نهایی بدون هیچ انیمیشن می رسد.

برای اطلاعات بیشتر در مورد AnimationsPecs مستندات کامل را بخوانید.
منابع اضافی
برای مثال های بیشتر از انیمیشن های سرگرم کننده در آهنگسازی ، به موارد زیر نگاهی بیندازید:
- 5 انیمیشن سریع در آهنگسازی
- حرکت چتر دریایی در آهنگسازی
- سفارشی کردن
AnimatedContent
در آهنگسازی - تسکین به عملکردهای تسکین در آهنگسازی