Tweak PlaylistPreviewItem
This commit is contained in:
@@ -45,6 +45,7 @@ import it.vfsfitvnm.vimusic.ui.components.themed.*
|
|||||||
import it.vfsfitvnm.vimusic.ui.styling.Dimensions
|
import it.vfsfitvnm.vimusic.ui.styling.Dimensions
|
||||||
import it.vfsfitvnm.vimusic.ui.styling.LocalAppearance
|
import it.vfsfitvnm.vimusic.ui.styling.LocalAppearance
|
||||||
import it.vfsfitvnm.vimusic.ui.styling.px
|
import it.vfsfitvnm.vimusic.ui.styling.px
|
||||||
|
import it.vfsfitvnm.vimusic.ui.views.BuiltInPlaylistItem
|
||||||
import it.vfsfitvnm.vimusic.ui.views.PlaylistPreviewItem
|
import it.vfsfitvnm.vimusic.ui.views.PlaylistPreviewItem
|
||||||
import it.vfsfitvnm.vimusic.ui.views.SongItem
|
import it.vfsfitvnm.vimusic.ui.views.SongItem
|
||||||
import it.vfsfitvnm.vimusic.utils.*
|
import it.vfsfitvnm.vimusic.utils.*
|
||||||
@@ -351,77 +352,35 @@ fun HomeScreen() {
|
|||||||
.fillMaxWidth()
|
.fillMaxWidth()
|
||||||
.height(124.dp * (if (playlistGridExpanded) 3 else 1))
|
.height(124.dp * (if (playlistGridExpanded) 3 else 1))
|
||||||
) {
|
) {
|
||||||
item {
|
item(key = "favorites") {
|
||||||
Box(
|
BuiltInPlaylistItem(
|
||||||
|
icon = R.drawable.heart,
|
||||||
|
colorTint = colorPalette.red,
|
||||||
|
name = "Favorites",
|
||||||
modifier = Modifier
|
modifier = Modifier
|
||||||
.padding(all = 8.dp)
|
.padding(all = 8.dp)
|
||||||
.clickable(
|
.clickable(
|
||||||
indication = rememberRipple(bounded = true),
|
indication = rememberRipple(bounded = true),
|
||||||
interactionSource = remember { MutableInteractionSource() },
|
interactionSource = remember { MutableInteractionSource() },
|
||||||
onClick = {
|
onClick = { builtInPlaylistRoute(BuiltInPlaylist.Favorites) }
|
||||||
builtInPlaylistRoute(BuiltInPlaylist.Favorites)
|
|
||||||
}
|
|
||||||
)
|
)
|
||||||
.background(colorPalette.lightBackground)
|
)
|
||||||
.size(108.dp)
|
|
||||||
) {
|
|
||||||
Image(
|
|
||||||
painter = painterResource(R.drawable.heart),
|
|
||||||
contentDescription = null,
|
|
||||||
colorFilter = ColorFilter.tint(colorPalette.red),
|
|
||||||
modifier = Modifier
|
|
||||||
.align(Alignment.Center)
|
|
||||||
.size(24.dp)
|
|
||||||
)
|
|
||||||
|
|
||||||
BasicText(
|
|
||||||
text = "Favorites",
|
|
||||||
style = typography.xxs.semiBold,
|
|
||||||
maxLines = 2,
|
|
||||||
overflow = TextOverflow.Ellipsis,
|
|
||||||
modifier = Modifier
|
|
||||||
.fillMaxWidth()
|
|
||||||
.align(Alignment.BottomStart)
|
|
||||||
.padding(horizontal = 8.dp, vertical = 4.dp)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (playlistGridExpanded) {
|
if (playlistGridExpanded) {
|
||||||
item {
|
item(key = "cached") {
|
||||||
Box(
|
BuiltInPlaylistItem(
|
||||||
|
icon = R.drawable.download,
|
||||||
|
colorTint = colorPalette.blue,
|
||||||
|
name = "Cached",
|
||||||
modifier = Modifier
|
modifier = Modifier
|
||||||
.padding(all = 8.dp)
|
.padding(all = 8.dp)
|
||||||
.clickable(
|
.clickable(
|
||||||
indication = rememberRipple(bounded = true),
|
indication = rememberRipple(bounded = true),
|
||||||
interactionSource = remember { MutableInteractionSource() },
|
interactionSource = remember { MutableInteractionSource() },
|
||||||
onClick = {
|
onClick = { builtInPlaylistRoute(BuiltInPlaylist.Cached) }
|
||||||
builtInPlaylistRoute(BuiltInPlaylist.Cached)
|
|
||||||
}
|
|
||||||
)
|
)
|
||||||
.background(colorPalette.lightBackground)
|
)
|
||||||
.size(108.dp)
|
|
||||||
) {
|
|
||||||
Image(
|
|
||||||
painter = painterResource(R.drawable.download),
|
|
||||||
contentDescription = null,
|
|
||||||
colorFilter = ColorFilter.tint(colorPalette.blue),
|
|
||||||
modifier = Modifier
|
|
||||||
.align(Alignment.Center)
|
|
||||||
.size(24.dp)
|
|
||||||
)
|
|
||||||
|
|
||||||
BasicText(
|
|
||||||
text = "Cached",
|
|
||||||
style = typography.xxs.semiBold,
|
|
||||||
maxLines = 2,
|
|
||||||
overflow = TextOverflow.Ellipsis,
|
|
||||||
modifier = Modifier
|
|
||||||
.fillMaxWidth()
|
|
||||||
.align(Alignment.BottomStart)
|
|
||||||
.padding(horizontal = 8.dp, vertical = 4.dp)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,10 +1,9 @@
|
|||||||
package it.vfsfitvnm.vimusic.ui.views
|
package it.vfsfitvnm.vimusic.ui.views
|
||||||
|
|
||||||
|
import androidx.annotation.DrawableRes
|
||||||
|
import androidx.compose.foundation.Image
|
||||||
import androidx.compose.foundation.background
|
import androidx.compose.foundation.background
|
||||||
import androidx.compose.foundation.layout.Box
|
import androidx.compose.foundation.layout.*
|
||||||
import androidx.compose.foundation.layout.fillMaxWidth
|
|
||||||
import androidx.compose.foundation.layout.padding
|
|
||||||
import androidx.compose.foundation.layout.size
|
|
||||||
import androidx.compose.foundation.text.BasicText
|
import androidx.compose.foundation.text.BasicText
|
||||||
import androidx.compose.runtime.Composable
|
import androidx.compose.runtime.Composable
|
||||||
import androidx.compose.runtime.collectAsState
|
import androidx.compose.runtime.collectAsState
|
||||||
@@ -14,8 +13,10 @@ import androidx.compose.ui.Alignment
|
|||||||
import androidx.compose.ui.Modifier
|
import androidx.compose.ui.Modifier
|
||||||
import androidx.compose.ui.graphics.Brush
|
import androidx.compose.ui.graphics.Brush
|
||||||
import androidx.compose.ui.graphics.Color
|
import androidx.compose.ui.graphics.Color
|
||||||
|
import androidx.compose.ui.graphics.ColorFilter
|
||||||
import androidx.compose.ui.layout.ContentScale
|
import androidx.compose.ui.layout.ContentScale
|
||||||
import androidx.compose.ui.platform.LocalDensity
|
import androidx.compose.ui.platform.LocalDensity
|
||||||
|
import androidx.compose.ui.res.painterResource
|
||||||
import androidx.compose.ui.text.style.TextOverflow
|
import androidx.compose.ui.text.style.TextOverflow
|
||||||
import androidx.compose.ui.unit.Dp
|
import androidx.compose.ui.unit.Dp
|
||||||
import androidx.compose.ui.unit.dp
|
import androidx.compose.ui.unit.dp
|
||||||
@@ -35,66 +36,126 @@ import kotlinx.coroutines.flow.distinctUntilChanged
|
|||||||
fun PlaylistPreviewItem(
|
fun PlaylistPreviewItem(
|
||||||
playlistPreview: PlaylistPreview,
|
playlistPreview: PlaylistPreview,
|
||||||
modifier: Modifier = Modifier,
|
modifier: Modifier = Modifier,
|
||||||
thumbnailSize: Dp = Dimensions.thumbnails.song,
|
thumbnailSize: Dp = Dimensions.thumbnails.song
|
||||||
) {
|
) {
|
||||||
val (colorPalette, typography) = LocalAppearance.current
|
|
||||||
val density = LocalDensity.current
|
val density = LocalDensity.current
|
||||||
|
|
||||||
val thumbnailSizePx = density.run {
|
val thumbnailSizePx = with(density) {
|
||||||
thumbnailSize.toPx().toInt()
|
thumbnailSize.roundToPx()
|
||||||
}
|
}
|
||||||
|
|
||||||
val thumbnails by remember(playlistPreview.playlist.id) {
|
val thumbnails by remember(playlistPreview.playlist.id) {
|
||||||
Database.playlistThumbnailUrls(playlistPreview.playlist.id).distinctUntilChanged()
|
Database.playlistThumbnailUrls(playlistPreview.playlist.id).distinctUntilChanged()
|
||||||
}.collectAsState(initial = emptyList(), context = Dispatchers.IO)
|
}.collectAsState(initial = emptyList(), context = Dispatchers.IO)
|
||||||
|
|
||||||
|
PlaylistItem(
|
||||||
|
name = playlistPreview.playlist.name,
|
||||||
|
modifier = modifier,
|
||||||
|
thumbnailSize = thumbnailSize,
|
||||||
|
imageContent = {
|
||||||
|
if (thumbnails.toSet().size == 1) {
|
||||||
|
AsyncImage(
|
||||||
|
model = thumbnails.first().thumbnail(thumbnailSizePx),
|
||||||
|
contentDescription = null,
|
||||||
|
contentScale = ContentScale.Crop,
|
||||||
|
modifier = Modifier
|
||||||
|
.fillMaxSize()
|
||||||
|
)
|
||||||
|
} else {
|
||||||
|
Box(
|
||||||
|
modifier = Modifier
|
||||||
|
.fillMaxSize()
|
||||||
|
) {
|
||||||
|
listOf(
|
||||||
|
Alignment.TopStart,
|
||||||
|
Alignment.TopEnd,
|
||||||
|
Alignment.BottomStart,
|
||||||
|
Alignment.BottomEnd
|
||||||
|
).forEachIndexed { index, alignment ->
|
||||||
|
AsyncImage(
|
||||||
|
model = thumbnails.getOrNull(index).thumbnail(thumbnailSizePx),
|
||||||
|
contentDescription = null,
|
||||||
|
contentScale = ContentScale.Crop,
|
||||||
|
modifier = Modifier
|
||||||
|
.align(alignment)
|
||||||
|
.size(thumbnailSize)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Composable
|
||||||
|
fun BuiltInPlaylistItem(
|
||||||
|
@DrawableRes icon: Int,
|
||||||
|
colorTint: Color,
|
||||||
|
name: String,
|
||||||
|
modifier: Modifier = Modifier,
|
||||||
|
thumbnailSize: Dp = Dimensions.thumbnails.song
|
||||||
|
) {
|
||||||
|
PlaylistItem(
|
||||||
|
name = name,
|
||||||
|
modifier = modifier,
|
||||||
|
thumbnailSize = thumbnailSize,
|
||||||
|
withGradient = false,
|
||||||
|
imageContent = {
|
||||||
|
Image(
|
||||||
|
painter = painterResource(icon),
|
||||||
|
contentDescription = null,
|
||||||
|
colorFilter = ColorFilter.tint(colorTint),
|
||||||
|
modifier = Modifier
|
||||||
|
.align(Alignment.Center)
|
||||||
|
.size(24.dp)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Composable
|
||||||
|
fun PlaylistItem(
|
||||||
|
name: String,
|
||||||
|
modifier: Modifier = Modifier,
|
||||||
|
thumbnailSize: Dp = Dimensions.thumbnails.song,
|
||||||
|
withGradient: Boolean = true,
|
||||||
|
imageContent: @Composable BoxScope.() -> Unit
|
||||||
|
) {
|
||||||
|
val (colorPalette, typography) = LocalAppearance.current
|
||||||
|
|
||||||
Box(
|
Box(
|
||||||
modifier = modifier
|
modifier = modifier
|
||||||
.background(colorPalette.lightBackground)
|
.background(colorPalette.lightBackground)
|
||||||
.size(thumbnailSize * 2)
|
.size(thumbnailSize * 2)
|
||||||
) {
|
) {
|
||||||
if (thumbnails.toSet().size == 1) {
|
Box(
|
||||||
AsyncImage(
|
modifier = Modifier
|
||||||
model = thumbnails.first().thumbnail(thumbnailSizePx * 2),
|
.size(thumbnailSize * 2),
|
||||||
contentDescription = null,
|
content = imageContent
|
||||||
contentScale = ContentScale.Crop,
|
)
|
||||||
modifier = Modifier
|
|
||||||
.size(thumbnailSize * 2)
|
|
||||||
)
|
|
||||||
} else {
|
|
||||||
listOf(
|
|
||||||
Alignment.TopStart,
|
|
||||||
Alignment.TopEnd,
|
|
||||||
Alignment.BottomStart,
|
|
||||||
Alignment.BottomEnd
|
|
||||||
).forEachIndexed { index, alignment ->
|
|
||||||
AsyncImage(
|
|
||||||
model = thumbnails.getOrNull(index).thumbnail(thumbnailSizePx),
|
|
||||||
contentDescription = null,
|
|
||||||
contentScale = ContentScale.Crop,
|
|
||||||
modifier = Modifier
|
|
||||||
.align(alignment)
|
|
||||||
.size(thumbnailSize)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
BasicText(
|
BasicText(
|
||||||
text = playlistPreview.playlist.name,
|
text = name,
|
||||||
style = typography.xxs.semiBold.color(Color.White),
|
style = typography.xxs.semiBold.color(Color.White),
|
||||||
maxLines = 2,
|
maxLines = 2,
|
||||||
overflow = TextOverflow.Ellipsis,
|
overflow = TextOverflow.Ellipsis,
|
||||||
modifier = Modifier
|
modifier = Modifier
|
||||||
.fillMaxWidth()
|
.fillMaxWidth()
|
||||||
.align(Alignment.BottomStart)
|
.align(Alignment.BottomStart)
|
||||||
.background(
|
.run {
|
||||||
Brush.verticalGradient(
|
if (withGradient) {
|
||||||
colors = listOf(
|
background(
|
||||||
Color.Transparent,
|
Brush.verticalGradient(
|
||||||
Color.Black.copy(alpha = 0.75f)
|
colors = listOf(
|
||||||
|
Color.Transparent,
|
||||||
|
Color.Black.copy(alpha = 0.75f)
|
||||||
|
)
|
||||||
|
)
|
||||||
)
|
)
|
||||||
)
|
} else {
|
||||||
)
|
this
|
||||||
|
}
|
||||||
|
}
|
||||||
.padding(horizontal = 8.dp, vertical = 4.dp)
|
.padding(horizontal = 8.dp, vertical = 4.dp)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user