17
17
package androidx.tv.samples
18
18
19
19
import androidx.annotation.Sampled
20
+ import androidx.compose.animation.ExperimentalAnimationApi
21
+ import androidx.compose.animation.core.tween
22
+ import androidx.compose.animation.fadeIn
23
+ import androidx.compose.animation.fadeOut
24
+ import androidx.compose.animation.slideInHorizontally
25
+ import androidx.compose.animation.slideOutHorizontally
26
+ import androidx.compose.animation.togetherWith
20
27
import androidx.compose.foundation.background
21
28
import androidx.compose.foundation.border
22
29
import androidx.compose.foundation.layout.Box
@@ -44,7 +51,7 @@ import androidx.tv.material3.CarouselDefaults
44
51
import androidx.tv.material3.CarouselState
45
52
import androidx.tv.material3.ExperimentalTvMaterial3Api
46
53
47
- @OptIn(ExperimentalTvMaterial3Api ::class )
54
+ @OptIn(ExperimentalTvMaterial3Api ::class , ExperimentalAnimationApi :: class )
48
55
@Sampled
49
56
@Composable
50
57
fun SimpleCarousel () {
@@ -59,16 +66,16 @@ fun SimpleCarousel() {
59
66
modifier = Modifier
60
67
.height(300 .dp)
61
68
.fillMaxWidth(),
69
+ contentTransformEndToStart =
70
+ fadeIn(tween(1000 )).togetherWith(fadeOut(tween(1000 ))),
71
+ contentTransformStartToEnd =
72
+ fadeIn(tween(1000 )).togetherWith(fadeOut(tween(1000 )))
62
73
) { itemIndex ->
63
- CarouselItem (
64
- background = {
65
- Box (
66
- modifier = Modifier
67
- .background(backgrounds[itemIndex])
68
- .border(2 .dp, Color .White .copy(alpha = 0.5f ))
69
- .fillMaxSize()
70
- )
71
- }
74
+ Box (
75
+ modifier = Modifier
76
+ .background(backgrounds[itemIndex])
77
+ .border(2 .dp, Color .White .copy(alpha = 0.5f ))
78
+ .fillMaxSize()
72
79
) {
73
80
var isFocused by remember { mutableStateOf(false ) }
74
81
@@ -82,6 +89,13 @@ fun SimpleCarousel() {
82
89
color = if (isFocused) Color .Red else Color .Transparent ,
83
90
shape = RoundedCornerShape (50 )
84
91
)
92
+ // Duration of animation here should be less than or equal to carousel's
93
+ // contentTransform duration to ensure the item below does not disappear
94
+ // abruptly.
95
+ .animateEnterExit(
96
+ enter = slideInHorizontally(animationSpec = tween(1000 )) { it / 2 },
97
+ exit = slideOutHorizontally(animationSpec = tween(1000 ))
98
+ )
85
99
.padding(vertical = 2 .dp, horizontal = 5 .dp)
86
100
) {
87
101
Text (text = " Play" )
@@ -90,7 +104,7 @@ fun SimpleCarousel() {
90
104
}
91
105
}
92
106
93
- @OptIn(ExperimentalTvMaterial3Api ::class )
107
+ @OptIn(ExperimentalTvMaterial3Api ::class , ExperimentalAnimationApi :: class )
94
108
@Sampled
95
109
@Composable
96
110
fun CarouselIndicatorWithRectangleShape () {
@@ -127,24 +141,30 @@ fun CarouselIndicatorWithRectangleShape() {
127
141
)
128
142
}
129
143
)
130
- }
144
+ },
145
+ contentTransformEndToStart =
146
+ fadeIn(tween(1000 )).togetherWith(fadeOut(tween(1000 ))),
147
+ contentTransformStartToEnd =
148
+ fadeIn(tween(1000 )).togetherWith(fadeOut(tween(1000 )))
131
149
) { itemIndex ->
132
- CarouselItem (
133
- background = {
134
- Box (
135
- modifier = Modifier
136
- .background(backgrounds[itemIndex])
137
- .border(2 .dp, Color .White .copy(alpha = 0.5f ))
138
- .fillMaxSize()
139
- )
140
- }
150
+ Box (
151
+ modifier = Modifier
152
+ .background(backgrounds[itemIndex])
153
+ .border(2 .dp, Color .White .copy(alpha = 0.5f ))
154
+ .fillMaxSize()
141
155
) {
142
156
var isFocused by remember { mutableStateOf(false ) }
143
-
144
157
Button (
145
158
onClick = { },
146
159
modifier = Modifier
147
160
.onFocusChanged { isFocused = it.isFocused }
161
+ // Duration of animation here should be less than or equal to carousel's
162
+ // contentTransform duration to ensure the item below does not disappear
163
+ // abruptly.
164
+ .animateEnterExit(
165
+ enter = slideInHorizontally(animationSpec = tween(1000 )) { it / 2 },
166
+ exit = slideOutHorizontally(animationSpec = tween(1000 ))
167
+ )
148
168
.padding(40 .dp)
149
169
.border(
150
170
width = 2 .dp,
0 commit comments