Skip to content

Commit cf009a9

Browse files
authored
Merge pull request #43 from Nico1eKim/ui/#33-group_note_page
[UI] 기록장 페이지 develop branch로 머지하겠습니다
2 parents 47da341 + 1f96018 commit cf009a9

29 files changed

Lines changed: 1336 additions & 279 deletions

.gitignore

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,4 +13,5 @@
1313
.externalNativeBuild
1414
.cxx
1515
local.properties
16-
.idea/deploymentTargetSelector.xml
16+
.idea/deploymentTargetSelector.xml
17+
.idea/misc.xml

.idea/misc.xml

Lines changed: 0 additions & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

app/src/main/java/com/texthip/thip/ui/common/bottomsheet/CustomBottomSheet.kt

Lines changed: 36 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -7,11 +7,24 @@ import androidx.compose.foundation.background
77
import androidx.compose.foundation.clickable
88
import androidx.compose.foundation.gestures.detectVerticalDragGestures
99
import androidx.compose.foundation.interaction.MutableInteractionSource
10-
import androidx.compose.foundation.layout.*
10+
import androidx.compose.foundation.layout.Box
11+
import androidx.compose.foundation.layout.Column
12+
import androidx.compose.foundation.layout.ColumnScope
13+
import androidx.compose.foundation.layout.fillMaxSize
14+
import androidx.compose.foundation.layout.fillMaxWidth
15+
import androidx.compose.foundation.layout.offset
16+
import androidx.compose.foundation.layout.padding
1117
import androidx.compose.foundation.shape.RoundedCornerShape
1218
import androidx.compose.material3.Button
1319
import androidx.compose.material3.Text
14-
import androidx.compose.runtime.*
20+
import androidx.compose.runtime.Composable
21+
import androidx.compose.runtime.LaunchedEffect
22+
import androidx.compose.runtime.getValue
23+
import androidx.compose.runtime.mutableFloatStateOf
24+
import androidx.compose.runtime.mutableStateOf
25+
import androidx.compose.runtime.remember
26+
import androidx.compose.runtime.rememberCoroutineScope
27+
import androidx.compose.runtime.setValue
1528
import androidx.compose.ui.Alignment
1629
import androidx.compose.ui.Modifier
1730
import androidx.compose.ui.graphics.Color
@@ -23,21 +36,26 @@ import com.texthip.thip.ui.theme.ThipTheme
2336
import com.texthip.thip.ui.theme.ThipTheme.colors
2437
import kotlinx.coroutines.launch
2538

39+
private const val BOTTOM_SHEET_HIDDEN_OFFSET = 300f
40+
private const val BOTTOM_SHEET_VISIBLE_OFFSET = 0f
41+
private const val BOTTOM_SHEET_DISMISS_THRESHOLD = 100f
42+
private const val ANIMATION_DURATION = 300
43+
2644
@Composable
2745
fun CustomBottomSheet(
2846
onDismiss: () -> Unit,
2947
content: @Composable ColumnScope.() -> Unit
3048
) {
3149
val scope = rememberCoroutineScope()
32-
val animatableOffset = remember { Animatable(300f) }
33-
var offsetY by remember { mutableFloatStateOf(0f) }
50+
val animatableOffset = remember { Animatable(BOTTOM_SHEET_HIDDEN_OFFSET) } // 시작 위치 아래
51+
var offsetY by remember { mutableFloatStateOf(BOTTOM_SHEET_VISIBLE_OFFSET) }
3452
var isDismissing by remember { mutableStateOf(false) }
3553

3654
// 등장 애니메이션
3755
LaunchedEffect(Unit) {
3856
animatableOffset.animateTo(
39-
targetValue = 0f,
40-
animationSpec = tween(durationMillis = 300)
57+
targetValue = BOTTOM_SHEET_VISIBLE_OFFSET,
58+
animationSpec = tween(durationMillis = ANIMATION_DURATION)
4159
)
4260
}
4361

@@ -52,7 +70,10 @@ fun CustomBottomSheet(
5270
if (!isDismissing) {
5371
isDismissing = true
5472
scope.launch {
55-
animatableOffset.animateTo(300f, tween(300))
73+
animatableOffset.animateTo(
74+
BOTTOM_SHEET_HIDDEN_OFFSET,
75+
tween(ANIMATION_DURATION)
76+
)
5677
onDismiss()
5778
}
5879
}
@@ -79,23 +100,26 @@ fun CustomBottomSheet(
79100
detectVerticalDragGestures(
80101
onVerticalDrag = { _, dragAmount ->
81102
if (dragAmount > 0) {
82-
offsetY += dragAmount / 2
103+
offsetY += dragAmount / 2 // 아래로 드래그할 때만 적용
83104
}
84105
},
85106
onDragEnd = {
86-
if (offsetY > 100f && !isDismissing) {
107+
if (offsetY > BOTTOM_SHEET_DISMISS_THRESHOLD && !isDismissing) {
87108
isDismissing = true
88109
scope.launch {
89-
animatableOffset.animateTo(300f, tween(300))
110+
animatableOffset.animateTo(
111+
BOTTOM_SHEET_HIDDEN_OFFSET,
112+
tween(ANIMATION_DURATION)
113+
)
90114
onDismiss()
91115
}
92116
} else {
93-
offsetY = 0f
117+
offsetY = BOTTOM_SHEET_VISIBLE_OFFSET
94118
}
95119
}
96120
)
97121
}
98-
.clickable(enabled = true) {}
122+
.clickable(enabled = true) {} // 내부 클릭 무시되지 않도록
99123
) {
100124
Column(modifier = Modifier.fillMaxWidth()) {
101125
content()

app/src/main/java/com/texthip/thip/ui/common/bottomsheet/MenuBottomSheet.kt

Lines changed: 25 additions & 122 deletions
Original file line numberDiff line numberDiff line change
@@ -1,153 +1,56 @@
11
package com.texthip.thip.ui.common.bottomsheet
22

3-
import androidx.compose.animation.core.Animatable
4-
import androidx.compose.animation.core.tween
5-
import androidx.compose.foundation.background
63
import androidx.compose.foundation.clickable
7-
import androidx.compose.foundation.gestures.detectVerticalDragGestures
8-
import androidx.compose.foundation.interaction.MutableInteractionSource
94
import androidx.compose.foundation.layout.Arrangement
10-
import androidx.compose.foundation.layout.Box
115
import androidx.compose.foundation.layout.Column
126
import androidx.compose.foundation.layout.Spacer
13-
import androidx.compose.foundation.layout.fillMaxSize
147
import androidx.compose.foundation.layout.fillMaxWidth
158
import androidx.compose.foundation.layout.height
16-
import androidx.compose.foundation.layout.offset
179
import androidx.compose.foundation.layout.padding
18-
import androidx.compose.foundation.shape.RoundedCornerShape
1910
import androidx.compose.material3.HorizontalDivider
2011
import androidx.compose.material3.Text
2112
import androidx.compose.runtime.Composable
22-
import androidx.compose.runtime.LaunchedEffect
23-
import androidx.compose.runtime.getValue
24-
import androidx.compose.runtime.mutableFloatStateOf
25-
import androidx.compose.runtime.mutableStateOf
26-
import androidx.compose.runtime.remember
27-
import androidx.compose.runtime.rememberCoroutineScope
28-
import androidx.compose.runtime.setValue
29-
import androidx.compose.ui.Alignment
3013
import androidx.compose.ui.Modifier
31-
import androidx.compose.ui.graphics.Color
32-
import androidx.compose.ui.input.pointer.pointerInput
3314
import androidx.compose.ui.res.stringResource
3415
import androidx.compose.ui.tooling.preview.Preview
3516
import androidx.compose.ui.unit.dp
36-
import androidx.compose.ui.zIndex
3717
import com.texthip.thip.R
18+
import com.texthip.thip.ui.group.room.mock.MenuBottomSheetItem
3819
import com.texthip.thip.ui.theme.ThipTheme.colors
3920
import com.texthip.thip.ui.theme.ThipTheme.typography
40-
import kotlinx.coroutines.launch
41-
42-
data class MenuBottomSheetItem(
43-
val text: String,
44-
val color: Color = Color.White,
45-
val onClick: () -> Unit,
46-
)
4721

4822
@Composable
4923
fun MenuBottomSheet(
5024
items: List<MenuBottomSheetItem>,
5125
onDismiss: () -> Unit
5226
) {
53-
val scope = rememberCoroutineScope()
54-
val animatableOffset = remember { Animatable(300f) } // 시작 위치 아래
55-
var offsetY by remember { mutableFloatStateOf(0f) }
56-
var isDismissing by remember { mutableStateOf(false) }
57-
58-
// 등장 애니메이션
59-
LaunchedEffect(Unit) {
60-
animatableOffset.animateTo(
61-
targetValue = 0f,
62-
animationSpec = tween(durationMillis = 300)
63-
)
64-
}
65-
66-
// 바깥 클릭 감지
67-
Box(
68-
modifier = Modifier
69-
.fillMaxSize()
70-
.clickable(
71-
indication = null,
72-
interactionSource = remember { MutableInteractionSource() }
73-
) {
74-
if (!isDismissing) {
75-
isDismissing = true
76-
scope.launch {
77-
animatableOffset.animateTo(300f, tween(300))
78-
onDismiss()
79-
}
80-
}
27+
CustomBottomSheet(
28+
onDismiss = onDismiss,
29+
) {
30+
items.forEachIndexed { index, item ->
31+
if (index > 0) {
32+
Spacer(modifier = Modifier.height(8.dp))
33+
HorizontalDivider(modifier = Modifier.height(1.dp), color = colors.Grey03)
34+
Spacer(modifier = Modifier.height(8.dp))
8135
}
82-
.zIndex(1f) // 다른 컴포넌트 위에 뜨도록
83-
)
8436

85-
86-
// BottomSheet 본체
87-
Box(
88-
modifier = Modifier
89-
.fillMaxSize()
90-
.zIndex(2f), // 시트가 배경보다 위에 뜨도록
91-
contentAlignment = Alignment.BottomCenter
92-
) {
93-
Box(
94-
modifier = Modifier
95-
.fillMaxWidth()
96-
.offset(y = (offsetY + animatableOffset.value).dp)
97-
.background(
98-
color = colors.DarkGrey,
99-
shape = RoundedCornerShape(topEnd = 12.dp, topStart = 12.dp)
100-
)
101-
.padding(20.dp)
102-
.pointerInput(Unit) {
103-
detectVerticalDragGestures(
104-
onVerticalDrag = { _, dragAmount ->
105-
if (dragAmount > 0) {
106-
offsetY += dragAmount / 2 // 아래로 드래그할 때만 적용
107-
}
108-
},
109-
onDragEnd = {
110-
if (offsetY > 100f && !isDismissing) {
111-
isDismissing = true
112-
scope.launch {
113-
animatableOffset.animateTo(300f, tween(300))
114-
onDismiss()
115-
}
116-
} else {
117-
offsetY = 0f
118-
}
37+
Column(
38+
modifier = Modifier
39+
.height(50.dp)
40+
.padding(horizontal = 12.dp, vertical = 8.dp),
41+
verticalArrangement = Arrangement.Center
42+
) {
43+
Text(
44+
text = item.text,
45+
style = typography.menu_m500_s16_h24,
46+
color = item.color,
47+
modifier = Modifier
48+
.fillMaxWidth()
49+
.clickable {
50+
item.onClick()
51+
onDismiss()
11952
}
120-
)
121-
}
122-
.clickable(enabled = true) {} // 내부 클릭 무시되지 않도록
123-
) {
124-
Column(modifier = Modifier.fillMaxWidth()) {
125-
items.forEachIndexed { index, item ->
126-
if (index > 0) {
127-
Spacer(modifier = Modifier.height(8.dp))
128-
HorizontalDivider(modifier = Modifier.height(1.dp), color = colors.Grey03)
129-
Spacer(modifier = Modifier.height(8.dp))
130-
}
131-
132-
Column(
133-
modifier = Modifier
134-
.height(50.dp)
135-
.padding(horizontal = 12.dp, vertical = 8.dp),
136-
verticalArrangement = Arrangement.Center
137-
) {
138-
Text(
139-
text = item.text,
140-
style = typography.menu_m500_s16_h24,
141-
color = item.color,
142-
modifier = Modifier
143-
.fillMaxWidth()
144-
.clickable {
145-
item.onClick()
146-
onDismiss()
147-
}
148-
)
149-
}
150-
}
53+
)
15154
}
15255
}
15356
}

0 commit comments

Comments
 (0)