Add animation to FABs
This commit is contained in:
+58
-38
@@ -20,6 +20,12 @@
|
|||||||
*/
|
*/
|
||||||
package com.vitorpamplona.amethyst.ui.screen.loggedIn.chatrooms
|
package com.vitorpamplona.amethyst.ui.screen.loggedIn.chatrooms
|
||||||
|
|
||||||
|
import androidx.compose.animation.AnimatedVisibility
|
||||||
|
import androidx.compose.animation.core.animateFloatAsState
|
||||||
|
import androidx.compose.animation.fadeIn
|
||||||
|
import androidx.compose.animation.fadeOut
|
||||||
|
import androidx.compose.animation.slideInVertically
|
||||||
|
import androidx.compose.animation.slideOutVertically
|
||||||
import androidx.compose.foundation.layout.Column
|
import androidx.compose.foundation.layout.Column
|
||||||
import androidx.compose.foundation.layout.Spacer
|
import androidx.compose.foundation.layout.Spacer
|
||||||
import androidx.compose.foundation.layout.height
|
import androidx.compose.foundation.layout.height
|
||||||
@@ -38,6 +44,7 @@ import androidx.compose.runtime.remember
|
|||||||
import androidx.compose.runtime.setValue
|
import androidx.compose.runtime.setValue
|
||||||
import androidx.compose.ui.Modifier
|
import androidx.compose.ui.Modifier
|
||||||
import androidx.compose.ui.graphics.Color
|
import androidx.compose.ui.graphics.Color
|
||||||
|
import androidx.compose.ui.graphics.graphicsLayer
|
||||||
import androidx.compose.ui.text.style.TextAlign
|
import androidx.compose.ui.text.style.TextAlign
|
||||||
import androidx.compose.ui.unit.dp
|
import androidx.compose.ui.unit.dp
|
||||||
import com.vitorpamplona.amethyst.R
|
import com.vitorpamplona.amethyst.R
|
||||||
@@ -76,46 +83,56 @@ fun ChannelFabColumn(
|
|||||||
}
|
}
|
||||||
|
|
||||||
Column {
|
Column {
|
||||||
if (isOpen) {
|
AnimatedVisibility(
|
||||||
FloatingActionButton(
|
visible = isOpen,
|
||||||
onClick = {
|
enter = slideInVertically(initialOffsetY = { it / 2 }) + fadeIn(),
|
||||||
wantsToSendNewMessage = true
|
exit = slideOutVertically(targetOffsetY = { it / 2 }) + fadeOut(),
|
||||||
isOpen = false
|
) {
|
||||||
},
|
Column {
|
||||||
modifier = Size55Modifier,
|
FloatingActionButton(
|
||||||
shape = CircleShape,
|
onClick = {
|
||||||
containerColor = MaterialTheme.colorScheme.primary,
|
wantsToSendNewMessage = true
|
||||||
) {
|
isOpen = false
|
||||||
Text(
|
},
|
||||||
text = stringRes(R.string.messages_new_message),
|
modifier = Size55Modifier,
|
||||||
color = Color.White,
|
shape = CircleShape,
|
||||||
textAlign = TextAlign.Center,
|
containerColor = MaterialTheme.colorScheme.primary,
|
||||||
fontSize = Font12SP,
|
) {
|
||||||
)
|
Text(
|
||||||
|
text = stringRes(R.string.messages_new_message),
|
||||||
|
color = Color.White,
|
||||||
|
textAlign = TextAlign.Center,
|
||||||
|
fontSize = Font12SP,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
Spacer(modifier = Modifier.height(20.dp))
|
||||||
|
|
||||||
|
FloatingActionButton(
|
||||||
|
onClick = {
|
||||||
|
wantsToCreateChannel = true
|
||||||
|
isOpen = false
|
||||||
|
},
|
||||||
|
modifier = Size55Modifier,
|
||||||
|
shape = CircleShape,
|
||||||
|
containerColor = MaterialTheme.colorScheme.primary,
|
||||||
|
) {
|
||||||
|
Text(
|
||||||
|
text = stringRes(R.string.messages_create_public_chat),
|
||||||
|
color = Color.White,
|
||||||
|
textAlign = TextAlign.Center,
|
||||||
|
fontSize = Font12SP,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
Spacer(modifier = Modifier.height(20.dp))
|
||||||
}
|
}
|
||||||
|
|
||||||
Spacer(modifier = Modifier.height(20.dp))
|
|
||||||
|
|
||||||
FloatingActionButton(
|
|
||||||
onClick = {
|
|
||||||
wantsToCreateChannel = true
|
|
||||||
isOpen = false
|
|
||||||
},
|
|
||||||
modifier = Size55Modifier,
|
|
||||||
shape = CircleShape,
|
|
||||||
containerColor = MaterialTheme.colorScheme.primary,
|
|
||||||
) {
|
|
||||||
Text(
|
|
||||||
text = stringRes(R.string.messages_create_public_chat),
|
|
||||||
color = Color.White,
|
|
||||||
textAlign = TextAlign.Center,
|
|
||||||
fontSize = Font12SP,
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
Spacer(modifier = Modifier.height(20.dp))
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
val rotationDegree by animateFloatAsState(
|
||||||
|
targetValue = if (isOpen) 45f else 0f,
|
||||||
|
)
|
||||||
|
|
||||||
FloatingActionButton(
|
FloatingActionButton(
|
||||||
onClick = { isOpen = !isOpen },
|
onClick = { isOpen = !isOpen },
|
||||||
modifier = Size55Modifier,
|
modifier = Size55Modifier,
|
||||||
@@ -125,7 +142,10 @@ fun ChannelFabColumn(
|
|||||||
Icon(
|
Icon(
|
||||||
imageVector = Icons.Outlined.Add,
|
imageVector = Icons.Outlined.Add,
|
||||||
contentDescription = stringRes(R.string.messages_create_public_private_chat_description),
|
contentDescription = stringRes(R.string.messages_create_public_private_chat_description),
|
||||||
modifier = Modifier.size(26.dp),
|
modifier =
|
||||||
|
Modifier.size(26.dp).graphicsLayer {
|
||||||
|
rotationZ = rotationDegree
|
||||||
|
},
|
||||||
tint = Color.White,
|
tint = Color.White,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|||||||
+75
-43
@@ -25,7 +25,12 @@ import android.net.Uri
|
|||||||
import android.os.Build
|
import android.os.Build
|
||||||
import androidx.activity.compose.rememberLauncherForActivityResult
|
import androidx.activity.compose.rememberLauncherForActivityResult
|
||||||
import androidx.activity.result.contract.ActivityResultContracts
|
import androidx.activity.result.contract.ActivityResultContracts
|
||||||
|
import androidx.compose.animation.AnimatedVisibility
|
||||||
import androidx.compose.animation.core.animateFloatAsState
|
import androidx.compose.animation.core.animateFloatAsState
|
||||||
|
import androidx.compose.animation.fadeIn
|
||||||
|
import androidx.compose.animation.fadeOut
|
||||||
|
import androidx.compose.animation.slideInVertically
|
||||||
|
import androidx.compose.animation.slideOutVertically
|
||||||
import androidx.compose.foundation.background
|
import androidx.compose.foundation.background
|
||||||
import androidx.compose.foundation.layout.Box
|
import androidx.compose.foundation.layout.Box
|
||||||
import androidx.compose.foundation.layout.Column
|
import androidx.compose.foundation.layout.Column
|
||||||
@@ -36,6 +41,7 @@ import androidx.compose.foundation.shape.CircleShape
|
|||||||
import androidx.compose.material.icons.Icons
|
import androidx.compose.material.icons.Icons
|
||||||
import androidx.compose.material.icons.filled.AddPhotoAlternate
|
import androidx.compose.material.icons.filled.AddPhotoAlternate
|
||||||
import androidx.compose.material.icons.filled.CameraAlt
|
import androidx.compose.material.icons.filled.CameraAlt
|
||||||
|
import androidx.compose.material.icons.outlined.Close
|
||||||
import androidx.compose.material3.CircularProgressIndicator
|
import androidx.compose.material3.CircularProgressIndicator
|
||||||
import androidx.compose.material3.FloatingActionButton
|
import androidx.compose.material3.FloatingActionButton
|
||||||
import androidx.compose.material3.Icon
|
import androidx.compose.material3.Icon
|
||||||
@@ -186,44 +192,51 @@ fun NewImageButton(
|
|||||||
ShowProgress(postViewModel)
|
ShowProgress(postViewModel)
|
||||||
} else {
|
} else {
|
||||||
Column {
|
Column {
|
||||||
if (isOpen) {
|
// if (isOpen) {
|
||||||
FloatingActionButton(
|
AnimatedVisibility(
|
||||||
onClick = {
|
visible = isOpen,
|
||||||
wantsToPostFromCamera = true
|
enter = slideInVertically(initialOffsetY = { it / 2 }) + fadeIn(),
|
||||||
isOpen = false
|
exit = slideOutVertically(targetOffsetY = { it / 2 }) + fadeOut(),
|
||||||
},
|
) {
|
||||||
modifier = Size55Modifier,
|
Column {
|
||||||
shape = CircleShape,
|
FloatingActionButton(
|
||||||
containerColor = MaterialTheme.colorScheme.primary,
|
onClick = {
|
||||||
) {
|
wantsToPostFromCamera = true
|
||||||
Icon(
|
isOpen = false
|
||||||
imageVector = Icons.Default.CameraAlt,
|
},
|
||||||
contentDescription = stringRes(id = R.string.upload_image),
|
modifier = Size55Modifier,
|
||||||
modifier = Modifier.size(26.dp),
|
shape = CircleShape,
|
||||||
tint = Color.White,
|
containerColor = MaterialTheme.colorScheme.primary,
|
||||||
)
|
) {
|
||||||
|
Icon(
|
||||||
|
imageVector = Icons.Default.CameraAlt,
|
||||||
|
contentDescription = stringRes(id = R.string.upload_image),
|
||||||
|
modifier = Modifier.size(26.dp),
|
||||||
|
tint = Color.White,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
Spacer(modifier = Modifier.height(20.dp))
|
||||||
|
|
||||||
|
FloatingActionButton(
|
||||||
|
onClick = {
|
||||||
|
wantsToPostFromGallery = true
|
||||||
|
isOpen = false
|
||||||
|
},
|
||||||
|
modifier = Size55Modifier,
|
||||||
|
shape = CircleShape,
|
||||||
|
containerColor = MaterialTheme.colorScheme.primary,
|
||||||
|
) {
|
||||||
|
Icon(
|
||||||
|
imageVector = Icons.Default.AddPhotoAlternate,
|
||||||
|
contentDescription = stringRes(id = R.string.upload_image),
|
||||||
|
modifier = Modifier.size(26.dp),
|
||||||
|
tint = Color.White,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
Spacer(modifier = Modifier.height(20.dp))
|
||||||
}
|
}
|
||||||
|
|
||||||
Spacer(modifier = Modifier.height(20.dp))
|
|
||||||
|
|
||||||
FloatingActionButton(
|
|
||||||
onClick = {
|
|
||||||
wantsToPostFromGallery = true
|
|
||||||
isOpen = false
|
|
||||||
},
|
|
||||||
modifier = Size55Modifier,
|
|
||||||
shape = CircleShape,
|
|
||||||
containerColor = MaterialTheme.colorScheme.primary,
|
|
||||||
) {
|
|
||||||
Icon(
|
|
||||||
imageVector = Icons.Default.AddPhotoAlternate,
|
|
||||||
contentDescription = stringRes(id = R.string.upload_image),
|
|
||||||
modifier = Modifier.size(26.dp),
|
|
||||||
tint = Color.White,
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
Spacer(modifier = Modifier.height(20.dp))
|
|
||||||
}
|
}
|
||||||
|
|
||||||
FloatingActionButton(
|
FloatingActionButton(
|
||||||
@@ -234,12 +247,31 @@ fun NewImageButton(
|
|||||||
shape = CircleShape,
|
shape = CircleShape,
|
||||||
containerColor = MaterialTheme.colorScheme.primary,
|
containerColor = MaterialTheme.colorScheme.primary,
|
||||||
) {
|
) {
|
||||||
Icon(
|
AnimatedVisibility(
|
||||||
painter = painterResource(R.drawable.ic_compose),
|
visible = isOpen,
|
||||||
contentDescription = stringRes(id = R.string.new_short),
|
enter = fadeIn(),
|
||||||
modifier = Modifier.size(26.dp),
|
exit = fadeOut(),
|
||||||
tint = Color.White,
|
) {
|
||||||
)
|
Icon(
|
||||||
|
imageVector = Icons.Outlined.Close,
|
||||||
|
contentDescription = stringRes(id = R.string.new_short),
|
||||||
|
modifier = Modifier.size(26.dp),
|
||||||
|
tint = Color.White,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
AnimatedVisibility(
|
||||||
|
visible = !isOpen,
|
||||||
|
enter = fadeIn(),
|
||||||
|
exit = fadeOut(),
|
||||||
|
) {
|
||||||
|
Icon(
|
||||||
|
painter = painterResource(R.drawable.ic_compose),
|
||||||
|
contentDescription = stringRes(id = R.string.new_short),
|
||||||
|
modifier = Modifier.size(26.dp),
|
||||||
|
tint = Color.White,
|
||||||
|
)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user