Skip to content

Commit 489d613

Browse files
authored
Merge pull request #46 from ondosee/feature/45-setting-additional-location-limits
🔀 :: (#45) - setting additional location limits
2 parents d3d445e + 013216f commit 489d613

File tree

9 files changed

+167
-6
lines changed

9 files changed

+167
-6
lines changed

app/src/main/java/com/ohnalmwo/ondosee/navigation/OndoseeNavhost.kt

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,10 @@ fun OndoseeNavHost(
3333
navigateToBack = navController::popBackStack
3434
)
3535
locationManagementScreen(navigateToBack = navController::popBackStack)
36-
addLocationScreen(navigateToBack = navController::popBackStack)
36+
addLocationScreen(
37+
navigateToLocationManagement = navController::navigateToLocationManagement,
38+
navigateToBack = navController::popBackStack
39+
)
3740
weeklyWeatherScreen(
3841
hazeState = hazeState,
3942
navigateToLocation = navController::navigateToLocation

core/datastore/src/main/java/com/ohnalmwo/datastore/datasource/location/LocationsDataSourceImpl.kt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ class LocationsDataSourceImpl @Inject constructor(
2020
locations.updateData {
2121
val builder = it.toBuilder()
2222

23-
if (builder.locationList.size < 4 && builder.locationList.none { it.toDomain() == location }) {
23+
if (builder.locationList.size <= 4 && builder.locationList.none { it.toDomain() == location }) {
2424
builder.addLocation(location.toData())
2525
}
2626

Lines changed: 116 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,116 @@
1+
package com.ohnalmwo.design_system.component.dialog
2+
3+
import androidx.compose.foundation.background
4+
import androidx.compose.foundation.layout.Arrangement
5+
import androidx.compose.foundation.layout.Column
6+
import androidx.compose.foundation.layout.Row
7+
import androidx.compose.foundation.layout.fillMaxWidth
8+
import androidx.compose.foundation.layout.height
9+
import androidx.compose.foundation.layout.padding
10+
import androidx.compose.foundation.layout.width
11+
import androidx.compose.foundation.shape.RoundedCornerShape
12+
import androidx.compose.material3.Card
13+
import androidx.compose.material3.Text
14+
import androidx.compose.material3.TextButton
15+
import androidx.compose.runtime.Composable
16+
import androidx.compose.runtime.getValue
17+
import androidx.compose.runtime.mutableStateOf
18+
import androidx.compose.runtime.remember
19+
import androidx.compose.runtime.setValue
20+
import androidx.compose.ui.Alignment
21+
import androidx.compose.ui.Modifier
22+
import androidx.compose.ui.text.font.FontWeight
23+
import androidx.compose.ui.unit.dp
24+
import androidx.compose.ui.window.Dialog
25+
import com.ohnalmwo.design_system.theme.OndoseeTheme.colors
26+
import com.ohnalmwo.design_system.theme.OndoseeTheme.typography
27+
28+
@Composable
29+
fun OndoseeDialog(
30+
openDialog: Boolean,
31+
title: String,
32+
content: String,
33+
firstText: String,
34+
secondText: String?,
35+
onFirstClick: () -> Unit,
36+
onSecondClick: () -> Unit
37+
) {
38+
var openDialog by remember { mutableStateOf(openDialog) }
39+
40+
if (openDialog) {
41+
Dialog(onDismissRequest = { openDialog = false }) {
42+
Card(
43+
modifier = Modifier.width(280.dp),
44+
shape = RoundedCornerShape(12.dp)
45+
) {
46+
Column(modifier = Modifier.background(colors.BACKGROUND)) {
47+
Column(
48+
modifier = Modifier
49+
.fillMaxWidth()
50+
.background(colors.BACKGROUND)
51+
.padding(top = 16.dp, start = 16.dp, end = 16.dp),
52+
verticalArrangement = Arrangement.spacedBy(8.dp),
53+
horizontalAlignment = Alignment.CenterHorizontally
54+
) {
55+
Text(
56+
text = title,
57+
color = colors.THEME_BLACK,
58+
style = typography.textLarge,
59+
fontWeight = FontWeight.Bold,
60+
)
61+
Text(
62+
text = content,
63+
color = colors.SECONDARY,
64+
style = typography.textLarge,
65+
fontWeight = FontWeight.Normal,
66+
)
67+
}
68+
Row(
69+
Modifier
70+
.fillMaxWidth()
71+
.height(64.dp)
72+
.padding(end = 8.dp)
73+
.background(colors.BACKGROUND),
74+
horizontalArrangement = Arrangement.End,
75+
verticalAlignment = Alignment.CenterVertically
76+
) {
77+
TextButton(
78+
modifier = Modifier
79+
.weight(1f)
80+
.height(60.dp),
81+
onClick = {
82+
openDialog = false
83+
onFirstClick()
84+
}
85+
) {
86+
Text(
87+
text = firstText,
88+
color = colors.INFORMATION,
89+
style = typography.textLarge,
90+
fontWeight = FontWeight.Bold,
91+
)
92+
}
93+
secondText?.let {
94+
TextButton(
95+
modifier = Modifier
96+
.weight(1f)
97+
.height(60.dp),
98+
onClick = {
99+
openDialog = false
100+
onSecondClick()
101+
}
102+
) {
103+
Text(
104+
text = secondText,
105+
color = colors.INFORMATION,
106+
style = typography.textLarge,
107+
fontWeight = FontWeight.Medium,
108+
)
109+
}
110+
}
111+
}
112+
}
113+
}
114+
}
115+
}
116+
}

core/design-system/src/main/java/com/ohnalmwo/design_system/theme/ColorTheme.kt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,4 +43,5 @@ abstract class ColorTheme {
4343
abstract val WHITE: Color
4444

4545
abstract val BACKGROUND: Color
46+
abstract val INFORMATION: Color
4647
}

core/design-system/src/main/java/com/ohnalmwo/design_system/theme/color/DarkColor.kt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,4 +41,5 @@ object DarkColor : ColorTheme() {
4141
override val WHITE = Color(0xFFFFFFFF)
4242

4343
override var BACKGROUND = Color(0xFF171717)
44+
override var INFORMATION = Color(0xFF2573F3)
4445
}

core/design-system/src/main/java/com/ohnalmwo/design_system/theme/color/LightColor.kt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,4 +41,5 @@ object LightColor : ColorTheme() {
4141
override val WHITE = Color(0xFFFFFFFF)
4242

4343
override var BACKGROUND = Color(0xFFF9FAFA)
44+
override var INFORMATION = Color(0xFF007AFF)
4445
}

feature/location/src/main/java/com/ohnalmwo/location/AddLocationScreen.kt

Lines changed: 28 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ import androidx.compose.ui.unit.dp
1414
import androidx.hilt.navigation.compose.hiltViewModel
1515
import androidx.lifecycle.compose.collectAsStateWithLifecycle
1616
import com.ohnalmwo.design_system.component.button.OndoseeBackButton
17+
import com.ohnalmwo.design_system.component.dialog.OndoseeDialog
1718
import com.ohnalmwo.design_system.component.textfield.SearchTextField
1819
import com.ohnalmwo.design_system.theme.OndoseeTheme.colors
1920
import com.ohnalmwo.location.component.LocationList
@@ -26,6 +27,7 @@ import kotlinx.coroutines.delay
2627

2728
@Composable
2829
fun AddLocationRoute(
30+
navigateToLocationManagement: () -> Unit,
2931
navigateToBack: () -> Unit,
3032
viewModel: LocationViewModel = hiltViewModel()
3133
) {
@@ -44,6 +46,7 @@ fun AddLocationRoute(
4446
LaunchedEffect(effect) {
4547
effect.collect { action ->
4648
when (action) {
49+
is LocationEffect.NavigateToLocationManagement -> navigateToLocationManagement()
4750
is LocationEffect.NavigateToBack -> navigateToBack()
4851
else -> Unit
4952
}
@@ -54,6 +57,8 @@ fun AddLocationRoute(
5457
state = state,
5558
onSearchValueChange = { viewModel.sendEvent(LocationEvent.OnSearchValueChange(it)) },
5659
onListItemClick = viewModel::setSavedLocations,
60+
setDialog = { viewModel.sendEvent(LocationEvent.SetLogoutDialog(it)) },
61+
navigateToLocationManagement = { viewModel.sendEffect(LocationEffect.NavigateToLocationManagement) },
5762
navigateToBack = { viewModel.sendEffect(LocationEffect.NavigateToBack) }
5863
)
5964
}
@@ -63,6 +68,8 @@ fun AddLocationScreen(
6368
state: LocationState,
6469
onSearchValueChange: (String) -> Unit,
6570
onListItemClick: (LocationInfo) -> Unit,
71+
setDialog: (Boolean) -> Unit,
72+
navigateToLocationManagement: () -> Unit,
6673
navigateToBack: () -> Unit
6774
) {
6875
Column(
@@ -90,8 +97,28 @@ fun AddLocationScreen(
9097
LocationList(
9198
searchQuery = state.search,
9299
locations = state.locations.locations,
93-
onClick = onListItemClick
100+
onClick = {
101+
if (state.localLocations.size >= 5) setDialog(true)
102+
else onListItemClick(it)
103+
}
94104
)
95105
}
96106
}
107+
108+
if (state.openDialog) {
109+
OndoseeDialog(
110+
openDialog = state.openDialog,
111+
title = "위치 목록이 가득 찼습니다.",
112+
content = "다른 위치를 삭제하시겠어요?",
113+
firstText = "위치 목록으로",
114+
secondText = "취소",
115+
onFirstClick = {
116+
setDialog(false)
117+
navigateToLocationManagement()
118+
},
119+
onSecondClick = {
120+
setDialog(false)
121+
}
122+
)
123+
}
97124
}

feature/location/src/main/java/com/ohnalmwo/location/navigation/LocationNavigation.kt

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -44,9 +44,13 @@ fun NavController.navigateToAddLocation(navOptions: NavOptions? = null) {
4444
}
4545

4646
fun NavGraphBuilder.addLocationScreen(
47+
navigateToLocationManagement: () -> Unit,
4748
navigateToBack: () -> Unit
4849
) {
4950
composable<Route.Location.AddLocation> {
50-
AddLocationRoute(navigateToBack = navigateToBack)
51+
AddLocationRoute(
52+
navigateToLocationManagement = navigateToLocationManagement,
53+
navigateToBack = navigateToBack
54+
)
5155
}
5256
}

feature/location/src/main/java/com/ohnalmwo/location/viewmodel/LocationScreenReducer.kt

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ class LocationScreenReducer : Reducer<LocationScreenReducer.LocationState, Locat
1313
data class GetLocationCoordinate(val isLoading: Boolean, val locations: Location) : LocationEvent()
1414
data class GetSavedLocations(val isLoading: Boolean, val localLocations: List<LocationInfo>) : LocationEvent()
1515
data object SetSavedLocations : LocationEvent()
16+
data class SetLogoutDialog(val openDialog: Boolean) : LocationEvent()
1617
data class GetMultipleWeatherSignificant(val isLoading: Boolean, val locationsWeatherSignificant: List<Weather>) : LocationEvent()
1718
data class OnSearchValueChange(val search: String) : LocationEvent()
1819
}
@@ -30,15 +31,17 @@ class LocationScreenReducer : Reducer<LocationScreenReducer.LocationState, Locat
3031
val locations: Location,
3132
val localLocations: List<LocationInfo>,
3233
val locationsWeatherSignificant: List<Weather>,
33-
val search: String
34+
val search: String,
35+
val openDialog: Boolean,
3436
) : Reducer.ViewState {
3537
companion object {
3638
fun initial() = LocationState(
3739
isLoading = true,
3840
locations = Location.default(),
3941
localLocations = emptyList(),
4042
locationsWeatherSignificant = listOf(Weather.default()),
41-
search = ""
43+
search = "",
44+
openDialog = false
4245
)
4346
}
4447
}
@@ -63,6 +66,11 @@ class LocationScreenReducer : Reducer<LocationScreenReducer.LocationState, Locat
6366
is LocationEvent.SetSavedLocations -> {
6467
previousState to LocationEffect.NavigateToBack
6568
}
69+
is LocationEvent.SetLogoutDialog -> {
70+
previousState.copy(
71+
openDialog = event.openDialog
72+
) to null
73+
}
6674
is LocationEvent.GetMultipleWeatherSignificant -> {
6775
previousState.copy(
6876
isLoading = event.isLoading,

0 commit comments

Comments
 (0)