Skip to content

Commit

Permalink
Merge pull request #83 from Nexters/feature/image-viewer
Browse files Browse the repository at this point in the history
인증 & 스토리에서 이미지 뷰어 화면 개선
  • Loading branch information
eshc123 authored Dec 22, 2024
2 parents d7e8db5 + b00001d commit 2b4fe3d
Show file tree
Hide file tree
Showing 6 changed files with 136 additions and 40 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
package com.goalpanzi.mission_mate.core.designsystem.util

import android.app.Activity
import android.content.Context
import androidx.core.view.WindowCompat

fun isLightStatusBars(context: Activity): Boolean {
val window = context.window
val insetsController = WindowCompat.getInsetsController(window, window.decorView)
return insetsController.isAppearanceLightStatusBars
}

fun setStatusBar(context: Context, isLight: Boolean) {
if (context is Activity) {
val window = context.window
val insetsController = WindowCompat.getInsetsController(window, window.decorView)
if (insetsController.isAppearanceLightStatusBars != isLight)
insetsController.isAppearanceLightStatusBars = isLight
}
}
Original file line number Diff line number Diff line change
@@ -1,15 +1,20 @@
package com.goalpanzi.mission_mate.feature.board.screen

import android.app.Activity
import androidx.compose.foundation.background
import androidx.compose.foundation.border
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.Spacer
import androidx.compose.foundation.layout.WindowInsets
import androidx.compose.foundation.layout.asPaddingValues
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.height
import androidx.compose.foundation.layout.navigationBarsPadding
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.layout.size
import androidx.compose.foundation.layout.statusBars
import androidx.compose.foundation.layout.statusBarsPadding
import androidx.compose.foundation.layout.wrapContentSize
import androidx.compose.foundation.layout.wrapContentWidth
Expand All @@ -18,10 +23,12 @@ import androidx.compose.material3.Icon
import androidx.compose.material3.IconButton
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.setValue
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.paint
import androidx.compose.ui.graphics.Brush
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.FilterQuality
import androidx.compose.ui.graphics.vector.ImageVector
import androidx.compose.ui.layout.ContentScale
Expand All @@ -33,6 +40,7 @@ import androidx.compose.ui.unit.dp
import coil.compose.AsyncImage
import coil.request.ImageRequest
import com.goalpanzi.mission_mate.core.designsystem.component.StableImage
import com.goalpanzi.mission_mate.core.designsystem.ext.clickableWithoutRipple
import com.goalpanzi.mission_mate.core.designsystem.theme.ColorBlack_FF000000
import com.goalpanzi.mission_mate.core.designsystem.theme.ColorWhite_FFFFFFFF
import com.goalpanzi.mission_mate.core.designsystem.theme.MissionMateTypography
Expand All @@ -53,39 +61,46 @@ fun UserStoryScreen(
) {
val dateTime = LocalDateTime.parse(verifiedAt)
val formatter = DateTimeFormatter.ofPattern("yyyy.MM.dd")
val statusBarPaddingValue = WindowInsets.statusBars.asPaddingValues().calculateTopPadding()
var isVisibleSpacer by remember { mutableStateOf(true) }

Box(
modifier = Modifier
.fillMaxSize()
.background(ColorWhite_FFFFFFFF)
.navigationBarsPadding()
) {
Box(
modifier = Modifier
.fillMaxSize()
.background(ColorBlack_FF000000)
.statusBarsPadding()
) {
AsyncImage(
model = ImageRequest.Builder(LocalContext.current)
.data(URLDecoder.decode(imageUrl, StandardCharsets.UTF_8.toString()))
.build(),
contentDescription = null,
modifier = Modifier.fillMaxSize(),
contentScale = ContentScale.FillBounds,
modifier = Modifier
.fillMaxSize()
.clickableWithoutRipple {
isVisibleSpacer = !isVisibleSpacer
},
contentScale = ContentScale.Fit,
filterQuality = FilterQuality.None
)
}

if (isVisibleSpacer) {
Spacer(
modifier = Modifier
.fillMaxWidth()
.height(statusBarPaddingValue + 80.dp)
.background(ColorBlack_FF000000.copy(alpha = 0.7f))
)
Row(
modifier = Modifier
.fillMaxWidth()
.background(
brush = Brush.verticalGradient(
colors = listOf(
ColorBlack_FF000000.copy(alpha = 0.4f),
Color.Transparent
)
)
)
.statusBarsPadding()
.height(93.dp)
.padding(horizontal = 24.dp, vertical = 14.dp)
) {
Expand Down Expand Up @@ -123,7 +138,10 @@ fun UserStoryScreen(
)

IconButton(
onClick = onClickClose,
onClick = {
onClickClose()
//setStatusBar(context, true)
},
modifier = Modifier.wrapContentSize()
) {
Icon(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,12 +10,16 @@ import androidx.compose.foundation.focusable
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.BoxScope
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.Spacer
import androidx.compose.foundation.layout.WindowInsets
import androidx.compose.foundation.layout.asPaddingValues
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.height
import androidx.compose.foundation.layout.navigationBarsPadding
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.layout.size
import androidx.compose.foundation.layout.statusBars
import androidx.compose.foundation.layout.statusBarsPadding
import androidx.compose.foundation.layout.wrapContentSize
import androidx.compose.foundation.layout.wrapContentWidth
Expand Down Expand Up @@ -53,6 +57,7 @@ import coil.request.ImageRequest
import com.goalpanzi.mission_mate.core.designsystem.component.MissionMateButton
import com.goalpanzi.mission_mate.core.designsystem.component.MissionMateButtonType
import com.goalpanzi.mission_mate.core.designsystem.component.StableImage
import com.goalpanzi.mission_mate.core.designsystem.ext.clickableWithoutRipple
import com.goalpanzi.mission_mate.core.designsystem.theme.ColorBlack_FF000000
import com.goalpanzi.mission_mate.core.designsystem.theme.ColorWhite_FFFFFFFF
import com.goalpanzi.mission_mate.core.designsystem.theme.MissionMateTypography
Expand Down Expand Up @@ -83,7 +88,6 @@ fun VerificationPreviewRoute(
showProgress = true
}
UploadEvent.Success -> {
showProgress = false
onUploadSuccess()
}
UploadEvent.Error -> {
Expand All @@ -94,50 +98,60 @@ fun VerificationPreviewRoute(
}

VerificationPreviewScreen(
isUploading = showProgress,
onClickClose = onClickClose,
uiState = uiState,
onClickUpload = viewModel::uploadImage
)

if (showProgress) {
ProgressBar()
}
}

@Composable
fun VerificationPreviewScreen(
isUploading: Boolean,
onClickClose: () -> Unit,
uiState: VerificationPreviewUiState,
onClickUpload: (File) -> Unit
) {
val context = LocalContext.current
val dateTime = LocalDateTime.now()
val formatter = DateTimeFormatter.ofPattern("yyyy.MM.dd")
val statusBarPaddingValue = WindowInsets.statusBars.asPaddingValues().calculateTopPadding()
var isVisibleSpacer by remember { mutableStateOf(true) }

Box(
modifier = Modifier
.fillMaxSize()
.background(ColorWhite_FFFFFFFF)
.navigationBarsPadding()
) {
Box(
modifier = Modifier
.fillMaxSize()
.statusBarsPadding()
) {
when (uiState) {
VerificationPreviewUiState.Loading -> VerificationPreviewLoading()
is VerificationPreviewUiState.Success -> {
when (uiState) {
VerificationPreviewUiState.Loading -> VerificationPreviewLoading()
is VerificationPreviewUiState.Success -> {
Box(
modifier = Modifier
.fillMaxSize()
.background(ColorBlack_FF000000)
.statusBarsPadding()
) {

AsyncImage(
model = ImageRequest.Builder(context)
.data(uiState.imageUrl)
.build(),
contentDescription = null,
modifier = Modifier.fillMaxSize(),
contentScale = ContentScale.FillBounds,
modifier = Modifier.fillMaxSize().clickableWithoutRipple {
isVisibleSpacer = !isVisibleSpacer
},
contentScale = ContentScale.Fit,
filterQuality = FilterQuality.None
)

}
if (isVisibleSpacer) {
Spacer(
modifier = Modifier
.fillMaxWidth()
.height(statusBarPaddingValue + 80.dp)
.background(ColorBlack_FF000000.copy(alpha = 0.7f))
)
Row(
modifier = Modifier
.fillMaxWidth()
Expand All @@ -149,6 +163,7 @@ fun VerificationPreviewScreen(
)
)
)
.statusBarsPadding()
.height(93.dp)
.padding(horizontal = 24.dp, vertical = 14.dp)
) {
Expand Down Expand Up @@ -186,7 +201,10 @@ fun VerificationPreviewScreen(
)

IconButton(
onClick = onClickClose,
onClick = {
onClickClose()
//setStatusBar(context, true)
},
modifier = Modifier.wrapContentSize()
) {
Icon(
Expand All @@ -196,9 +214,11 @@ fun VerificationPreviewScreen(
)
}
}

UploadButton(
context = context,
filePath = uiState.imageUrl.toUri(),
isUploading = isUploading,
onClickUpload = onClickUpload
)
}
Expand All @@ -211,6 +231,7 @@ fun VerificationPreviewScreen(
fun BoxScope.UploadButton(
context: Context,
filePath: Uri,
isUploading: Boolean,
onClickUpload: (File) -> Unit
) {
val multipleEventsCutter = remember { MultipleEventsCutter.get() }
Expand All @@ -220,19 +241,27 @@ fun BoxScope.UploadButton(
.padding(horizontal = 24.dp, vertical = 36.dp)
.fillMaxWidth()
.navigationBarsPadding(),
buttonType = MissionMateButtonType.ACTIVE,
buttonType = if(isUploading) MissionMateButtonType.DISABLED else MissionMateButtonType.ACTIVE,
onClick = {
multipleEventsCutter.processEvent {
val file = ImageCompressor.getCompressedImage(context, filePath)
onClickUpload(file)
}
}
) {
Text(
text = stringResource(id = R.string.upload),
style = MissionMateTypography.body_xl_bold,
color = ColorWhite_FFFFFFFF
)
if(isUploading){
CircularProgressIndicator(
modifier = Modifier.size(24.dp),
color = ColorWhite_FFFFFFFF,
strokeWidth = 3.dp
)
}else {
Text(
text = stringResource(id = R.string.upload),
style = MissionMateTypography.body_lg_bold,
color = ColorWhite_FFFFFFFF
)
}
}
}

Expand All @@ -257,6 +286,7 @@ fun VerificationPreviewLoading() {
fun ProgressBar() {
Box(
modifier = Modifier
.fillMaxSize()
.statusBarsPadding()
.navigationBarsPadding()
) {
Expand All @@ -270,6 +300,7 @@ fun ProgressBar() {
@Composable
fun VerificationPreviewScreenPreview() {
VerificationPreviewScreen(
isUploading = false,
onClickClose = {},
uiState = VerificationPreviewUiState.Success(
characterUiModel = CharacterUiModel.RABBIT,
Expand All @@ -284,6 +315,7 @@ fun VerificationPreviewScreenPreview() {
@Composable
fun VerificationPreviewScreenLoadingPreview() {
VerificationPreviewScreen(
isUploading = false,
onClickClose = {},
uiState = VerificationPreviewUiState.Loading,
onClickUpload = {}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package com.goalpanzi.mission_mate.feature.board.screen

import android.util.Log
import androidx.lifecycle.SavedStateHandle
import androidx.lifecycle.ViewModel
import androidx.lifecycle.viewModelScope
Expand Down Expand Up @@ -87,3 +88,4 @@ sealed interface UploadEvent {
data object Success : UploadEvent
data object Error : UploadEvent
}

Loading

0 comments on commit 2b4fe3d

Please sign in to comment.