162: Refactor LobstersItem and add a dedicated comments button r=msfjarvis a=msfjarvis

Refer to updated screenshot test for the UI changes.

bors r+

Co-authored-by: Harsh Shandilya <me@msfjarvis.dev>
This commit is contained in:
bors[bot] 2021-03-19 12:44:59 +00:00 committed by GitHub
commit 4cd00a4b44
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
7 changed files with 129 additions and 68 deletions

Binary file not shown.

Before

Width:  |  Height:  |  Size: 56 KiB

After

Width:  |  Height:  |  Size: 57 KiB

Before After
Before After

View file

@ -20,9 +20,9 @@ class LobstersItemTest : ScreenshotTest {
DarkTestTheme { DarkTestTheme {
LobstersItem( LobstersItem(
post = TEST_POST, post = TEST_POST,
onClick = { /*TODO*/ }, viewPost = { /*TODO*/ },
onLongClick = { /*TODO*/ }, viewComments = { /*TODO*/ },
onSaveButtonClick = { /*TODO*/ }, toggleSave = { /*TODO*/ },
isSaved = true, isSaved = true,
) )
} }

View file

@ -58,9 +58,9 @@ fun HottestPosts(
LobstersItem( LobstersItem(
post = item, post = item,
isSaved = isSaved, isSaved = isSaved,
onClick = { urlLauncher.launch(item.url.ifEmpty { item.commentsUrl }) }, viewPost = { urlLauncher.launch(item.url.ifEmpty { item.commentsUrl }) },
onLongClick = { urlLauncher.launch(item.commentsUrl) }, viewComments = { urlLauncher.launch(item.commentsUrl) },
onSaveButtonClick = { toggleSave = {
isSaved = isSaved.not() isSaved = isSaved.not()
saveAction.invoke(item) saveAction.invoke(item)
}, },

View file

@ -3,17 +3,17 @@ package dev.msfjarvis.lobsters.ui.posts
import androidx.compose.animation.Crossfade import androidx.compose.animation.Crossfade
import androidx.compose.foundation.ExperimentalFoundationApi import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.background import androidx.compose.foundation.background
import androidx.compose.foundation.combinedClickable import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.Arrangement import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Row import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.layout.requiredSize import androidx.compose.foundation.layout.requiredSize
import androidx.compose.foundation.layout.requiredWidth
import androidx.compose.foundation.lazy.LazyColumn import androidx.compose.foundation.lazy.LazyColumn
import androidx.compose.foundation.lazy.items import androidx.compose.foundation.lazy.items
import androidx.compose.foundation.shape.RoundedCornerShape import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material.IconButton
import androidx.compose.material.IconToggleButton import androidx.compose.material.IconToggleButton
import androidx.compose.material.MaterialTheme import androidx.compose.material.MaterialTheme
import androidx.compose.material.Surface import androidx.compose.material.Surface
@ -52,38 +52,67 @@ val TEST_POST = SavedPost(
fun LobstersItem( fun LobstersItem(
post: SavedPost, post: SavedPost,
isSaved: Boolean, isSaved: Boolean,
onClick: () -> Unit, viewPost: () -> Unit,
onLongClick: () -> Unit, viewComments: () -> Unit,
onSaveButtonClick: () -> Unit, toggleSave: () -> Unit,
) { ) {
Surface( Surface(
modifier = Modifier modifier = Modifier
.combinedClickable( .clickable { viewPost.invoke() },
onClick = onClick,
onLongClick = onLongClick,
),
) { ) {
Row( Row(
modifier = Modifier.padding(start = 12.dp, end = 24.dp), modifier = Modifier.padding(start = 12.dp),
verticalAlignment = Alignment.CenterVertically, verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.SpaceBetween, horizontalArrangement = Arrangement.SpaceBetween,
) { ) {
Box(
modifier = Modifier.weight(0.8f),
) {
PostDetails(
post,
)
}
Box(
modifier = Modifier.weight(0.1f),
) {
SaveButton(
isSaved,
toggleSave,
)
}
Box(
modifier = Modifier.weight(0.1f),
) {
CommentsButton(
onClick = viewComments,
)
}
}
}
}
@Composable
fun PostDetails(
post: SavedPost,
) {
Column( Column(
modifier = Modifier.fillMaxWidth(), modifier = Modifier.padding(top = 8.dp, bottom = 8.dp),
) { ) {
Text( Text(
text = post.title, text = post.title,
color = titleColor, color = titleColor,
fontWeight = FontWeight.Bold, fontWeight = FontWeight.Bold,
modifier = Modifier modifier = Modifier
.padding(top = 4.dp), .padding(bottom = 4.dp),
) )
TagRow( TagRow(
tags = post.tags, tags = post.tags,
modifier = Modifier modifier = Modifier
.padding(top = 8.dp, bottom = 8.dp, end = 16.dp), .padding(bottom = 4.dp),
) )
Row { Row(
verticalAlignment = Alignment.CenterVertically,
) {
CoilImage( CoilImage(
data = "${LobstersApi.BASE_URL}/${post.submitterAvatarUrl}", data = "${LobstersApi.BASE_URL}/${post.submitterAvatarUrl}",
contentDescription = stringResource( contentDescription = stringResource(
@ -95,16 +124,23 @@ fun LobstersItem(
transformations(CircleCropTransformation()) transformations(CircleCropTransformation())
}, },
modifier = Modifier modifier = Modifier
.requiredWidth(30.dp) .requiredSize(24.dp)
.padding(4.dp), .padding(bottom = 4.dp),
) )
Text( Text(
text = stringResource(id = R.string.submitted_by, post.submitterName), text = stringResource(id = R.string.submitted_by, post.submitterName),
modifier = Modifier modifier = Modifier
.padding(4.dp), .padding(start = 4.dp),
) )
} }
} }
}
@Composable
fun SaveButton(
isSaved: Boolean,
onSaveButtonClick: () -> Unit,
) {
IconToggleButton( IconToggleButton(
checked = isSaved, checked = isSaved,
onCheckedChange = { onSaveButtonClick.invoke() }, onCheckedChange = { onSaveButtonClick.invoke() },
@ -119,7 +155,22 @@ fun LobstersItem(
) )
} }
} }
} }
@Composable
fun CommentsButton(
onClick: () -> Unit,
) {
IconButton(
onClick = onClick,
modifier = Modifier
.requiredSize(24.dp),
) {
IconResource(
resourceId = R.drawable.ic_insert_comment_24px,
tint = MaterialTheme.colors.secondary,
contentDescription = stringResource(R.string.open_comments),
)
} }
} }
@ -154,9 +205,9 @@ fun Preview() {
LobstersItem( LobstersItem(
post = item, post = item,
isSaved = false, isSaved = false,
onClick = {}, viewPost = {},
onLongClick = {}, viewComments = {},
onSaveButtonClick = {}, toggleSave = {},
) )
} }
} }

View file

@ -59,9 +59,9 @@ fun SavedPosts(
LobstersItem( LobstersItem(
post = item, post = item,
isSaved = true, isSaved = true,
onClick = { urlLauncher.launch(item.url.ifEmpty { item.commentsUrl }) }, viewPost = { urlLauncher.launch(item.url.ifEmpty { item.commentsUrl }) },
onLongClick = { urlLauncher.launch(item.commentsUrl) }, viewComments = { urlLauncher.launch(item.commentsUrl) },
onSaveButtonClick = { saveAction.invoke(item) }, toggleSave = { saveAction.invoke(item) },
) )
} }
} }

View file

@ -0,0 +1,9 @@
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp"
android:height="24dp"
android:viewportWidth="24"
android:viewportHeight="24">
<path
android:fillColor="#000000"
android:pathData="M20,2L4,2c-1.1,0 -2,0.9 -2,2v12c0,1.1 0.9,2 2,2h14l4,4L22,4c0,-1.1 -0.9,-2 -2,-2zM18,14L6,14v-2h12v2zM18,11L6,11L6,9h12v2zM18,8L6,8L6,6h12v2z" />
</vector>

View file

@ -9,4 +9,5 @@
<string name="add_to_saved_posts">Add to saved posts</string> <string name="add_to_saved_posts">Add to saved posts</string>
<string name="remove_from_saved_posts">Remove from saved posts</string> <string name="remove_from_saved_posts">Remove from saved posts</string>
<string name="refresh_posts_content_description">Refresh posts</string> <string name="refresh_posts_content_description">Refresh posts</string>
<string name="open_comments">Open comments</string>
</resources> </resources>