Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Dev #85

Merged
merged 3 commits into from
Sep 14, 2024
Merged

Dev #85

Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,11 +1,15 @@
package st.slex.csplashscreen.ui.components

import androidx.compose.animation.ExperimentalSharedTransitionApi
import androidx.compose.animation.SharedTransitionLayout
import androidx.compose.runtime.Composable
import androidx.compose.runtime.CompositionLocalProvider
import androidx.compose.runtime.Stable
import androidx.compose.ui.Modifier
import androidx.navigation.NavHostController
import androidx.navigation.compose.NavHost
import st.slex.csplashscreen.core.navigation.Screen
import st.slex.csplashscreen.core.ui.theme.LocalSharedTransitionScope
import st.slex.csplashscreen.feature.collection.navigation.singleCollectionGraph
import st.slex.csplashscreen.feature.favourite.navigation.favouriteGraph
import st.slex.csplashscreen.feature.feature_photo_detail.navigation.imageDetailGraph
Expand All @@ -16,22 +20,27 @@ import st.slex.csplashscreen.feature.user.navigation.userGraph
@Stable
class NavHostControllerHolder(val navController: NavHostController)

@OptIn(ExperimentalSharedTransitionApi::class)
@Composable
@Stable
fun NavigationHost(
holder: NavHostControllerHolder,
modifier: Modifier = Modifier,
startDestination: Screen = Screen.Home
) {
NavHost(
navController = holder.navController,
startDestination = startDestination
) {
homeGraph(modifier)
userGraph(modifier)
imageDetailGraph(modifier)
searchPhotosGraph(modifier)
singleCollectionGraph(modifier)
favouriteGraph(modifier)
SharedTransitionLayout {
CompositionLocalProvider(LocalSharedTransitionScope provides this) {
NavHost(
navController = holder.navController,
startDestination = startDestination
) {
homeGraph(modifier)
userGraph(modifier)
imageDetailGraph(modifier)
searchPhotosGraph(modifier)
singleCollectionGraph(modifier)
favouriteGraph(modifier)
}
}
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package st.slex.csplashscreen.core.navigation

import androidx.compose.animation.AnimatedContentScope
import androidx.compose.runtime.Composable
import androidx.compose.runtime.Stable
import androidx.navigation.NavGraphBuilder
Expand Down Expand Up @@ -32,7 +33,7 @@ sealed interface Screen {
}

inline fun <reified S : Screen> NavGraphBuilder.navScreen(
noinline content: @Composable (S) -> Unit
noinline content: @Composable AnimatedContentScope.(S) -> Unit
) {
composable<S> { backStackEntry ->
content(backStackEntry.toRoute())
Expand Down
Original file line number Diff line number Diff line change
@@ -1,21 +1,25 @@
package st.slex.csplashscreen.core.ui.base

import androidx.compose.runtime.Composable
import androidx.compose.runtime.CompositionLocalProvider
import androidx.lifecycle.ViewModel
import androidx.navigation.NavGraphBuilder
import org.koin.androidx.compose.koinViewModel
import st.slex.csplashscreen.core.navigation.Screen
import st.slex.csplashscreen.core.navigation.navScreen
import st.slex.csplashscreen.core.ui.theme.LocalNavAnimatedVisibilityScope

inline fun <reified Destination : Screen, reified S : ViewModel> NavGraphBuilder.screen(
noinline content: @Composable (Destination, S) -> Unit
) {
navScreen<Destination> { screen ->
val viewModel: S = koinViewModel(
key = screen.hashCode().toString()
)
/*TODO maybe good point to make instance of state, event, action here
and then send in to Content Screen*/
content(screen, viewModel)
CompositionLocalProvider(LocalNavAnimatedVisibilityScope provides this) {
val viewModel: S = koinViewModel(
key = screen.hashCode().toString()
)
/*TODO maybe good point to make instance of state, event, action here
and then send in to Content Screen*/
content(screen, viewModel)
}
}
}
Original file line number Diff line number Diff line change
@@ -1,8 +1,11 @@
package st.slex.csplashscreen.core.ui.components.base

import androidx.compose.animation.ExperimentalSharedTransitionApi
import androidx.compose.animation.SharedTransitionScope
import androidx.compose.animation.fadeIn
import androidx.compose.animation.fadeOut
import androidx.compose.foundation.background
import androidx.compose.foundation.clickable
import androidx.compose.foundation.interaction.MutableInteractionSource
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.BoxScope
import androidx.compose.foundation.layout.Row
Expand All @@ -12,7 +15,6 @@ import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.height
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material.ripple.rememberRipple
import androidx.compose.material3.MaterialTheme
import androidx.compose.runtime.Composable
import androidx.compose.runtime.remember
Expand All @@ -21,11 +23,13 @@ import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
import androidx.compose.ui.layout.ContentScale
import androidx.compose.ui.platform.LocalConfiguration
import androidx.compose.ui.semantics.Role
import androidx.compose.ui.unit.dp
import st.slex.csplashscreen.core.ui.components.ImageComponent
import st.slex.csplashscreen.core.ui.theme.Dimen
import st.slex.csplashscreen.core.ui.theme.rememberNavAnimatedVisibilityScope
import st.slex.csplashscreen.core.ui.theme.rememberSharedTransitionScope

@OptIn(ExperimentalSharedTransitionApi::class)
@Composable
fun PhotosBaseItem(
onContainerClick: () -> Unit,
Expand All @@ -39,44 +43,58 @@ fun PhotosBaseItem(
val itemHeight = remember {
configuration.screenHeightDp.dp / 3
}
Box(
modifier = modifier
.fillMaxWidth()
.height(itemHeight)
.padding(bottom = Dimen.medium)
.clip(RoundedCornerShape(Dimen.medium))
.clickable(
onClick = onContainerClick,
role = Role.Button,
interactionSource = remember { MutableInteractionSource() },
indication = rememberRipple()
),
) {
ImageComponent(
modifier = Modifier.fillMaxSize(),
url = url,
contentScale = ContentScale.Crop
)
Row(
val sharedTransitionScope = rememberSharedTransitionScope()
with(sharedTransitionScope) {
Box(
modifier = Modifier
.align(Alignment.TopStart)
.sharedBounds(
sharedContentState = rememberSharedContentState(key = url),
animatedVisibilityScope = rememberNavAnimatedVisibilityScope(),
enter = fadeIn(),
exit = fadeOut(),
resizeMode = SharedTransitionScope.ResizeMode.ScaleToBounds(),
)
.then(modifier)
.fillMaxWidth()
.height(itemHeight)
.padding(bottom = Dimen.medium)
.clip(RoundedCornerShape(Dimen.medium))
.clickable(
onClick = onHeaderClick,
role = Role.Button,
interactionSource = remember { MutableInteractionSource() },
indication = rememberRipple()
)
.background(
color = MaterialTheme.colorScheme.background.copy(
alpha = 0.7f
)
)
.padding(Dimen.small),
verticalAlignment = Alignment.CenterVertically
onClick = onContainerClick,
// todo check this if needed
// role = Role.Button,
// interactionSource = remember { MutableInteractionSource() },
// indication = rememberRipple()
),
) {
headerContent()
ImageComponent(
modifier = Modifier
.fillMaxSize(),
url = url,
contentScale = ContentScale.Crop
)
Row(
modifier = Modifier
.align(Alignment.TopStart)
.fillMaxWidth()
.clickable(
onClick = onHeaderClick,
// todo check this if needed
// role = Role.Button,
// interactionSource = remember { MutableInteractionSource() },
// indication = rememberRipple()
)
.background(
color = MaterialTheme.colorScheme.background.copy(
alpha = 0.7f
)
)
.padding(Dimen.small),
verticalAlignment = Alignment.CenterVertically
) {
headerContent()
}
content()
}
content()
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
package st.slex.csplashscreen.core.ui.theme

import android.os.Build
import androidx.compose.animation.AnimatedVisibilityScope
import androidx.compose.animation.ExperimentalSharedTransitionApi
import androidx.compose.animation.SharedTransitionScope
import androidx.compose.foundation.isSystemInDarkTheme
import androidx.compose.material3.MaterialTheme
import androidx.compose.material3.darkColorScheme
Expand All @@ -9,6 +12,7 @@ import androidx.compose.material3.dynamicLightColorScheme
import androidx.compose.material3.lightColorScheme
import androidx.compose.runtime.Composable
import androidx.compose.runtime.CompositionLocalProvider
import androidx.compose.runtime.compositionLocalOf
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.unit.dp
Expand Down Expand Up @@ -184,4 +188,17 @@ fun AppTheme(
content = content
)
}
}
}

val LocalNavAnimatedVisibilityScope = compositionLocalOf<AnimatedVisibilityScope?> { null }

@OptIn(ExperimentalSharedTransitionApi::class)
val LocalSharedTransitionScope = compositionLocalOf<SharedTransitionScope?> { null }

@OptIn(ExperimentalSharedTransitionApi::class)
@Composable
fun rememberSharedTransitionScope() = checkNotNull(LocalSharedTransitionScope.current)

@Composable
fun rememberNavAnimatedVisibilityScope() =
checkNotNull(LocalNavAnimatedVisibilityScope.current)
6 changes: 3 additions & 3 deletions fastlane/report.xml
Original file line number Diff line number Diff line change
Expand Up @@ -5,17 +5,17 @@



<testcase classname="fastlane.lanes" name="0: default_platform" time="0.000267292">
<testcase classname="fastlane.lanes" name="0: default_platform" time="0.000270334">

</testcase>


<testcase classname="fastlane.lanes" name="1: clean bundle" time="321.668838943">
<testcase classname="fastlane.lanes" name="1: clean bundle" time="336.868891465">

</testcase>


<testcase classname="fastlane.lanes" name="2: upload_to_play_store" time="27.945471862">
<testcase classname="fastlane.lanes" name="2: upload_to_play_store" time="24.176761763">

</testcase>

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import kotlinx.coroutines.flow.StateFlow
import kotlinx.coroutines.flow.filter
import kotlinx.coroutines.flow.flatMapLatest
import kotlinx.coroutines.flow.map
import st.slex.csplashscreen.core.core.Logger
import st.slex.csplashscreen.core.core.coroutine.AppDispatcher
import st.slex.csplashscreen.core.core.coroutine.CoroutineExt.mapState
import st.slex.csplashscreen.core.photos.ui.model.PhotoModel
Expand All @@ -33,6 +34,7 @@ class SingleCollectionStore(
) {

override fun sendAction(action: Action) {
Logger.d("action: $action", TAG)
when (action) {
is Action.Init -> actionInit(action)
is Action.OnProfileClick -> actionProfileClick(action)
Expand All @@ -46,7 +48,7 @@ class SingleCollectionStore(
collectionId = action.collectionId
)
}
allPhotos.launch { pagingData ->
getPhotos(action.collectionId).launch { pagingData ->
updateState { currentState ->
currentState.copy(
photos = pagingData
Expand All @@ -55,6 +57,18 @@ class SingleCollectionStore(
}
}

private fun getPhotos(
collectionId: String
): StateFlow<PagingData<PhotoModel>> = Pager(pagingConfig) {
PagingSource { page, pageSize ->
interactor.getPhotos(
uuid = collectionId,
page = page,
pageSize = pageSize
).map { it.toPresentation() }
}
}.flow.state()

@OptIn(ExperimentalCoroutinesApi::class)
private val allPhotos: StateFlow<PagingData<PhotoModel>>
get() = state
Expand Down Expand Up @@ -90,5 +104,6 @@ class SingleCollectionStore(
pageSize = 5,
enablePlaceholders = false
)
private const val TAG = "SingleCollectionStore"
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
package st.slex.csplashscreen.feature.home.ui

import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.lazy.rememberLazyListState
import androidx.compose.foundation.pager.HorizontalPager
Expand All @@ -17,7 +16,6 @@ import st.slex.csplashscreen.core.photos.ui.model.PhotoModel
import st.slex.csplashscreen.feature.home.ui.component.tabs.MainScreenTabRow
import st.slex.csplashscreen.feature.home.ui.component.tabs.MainScreenTabs

@OptIn(ExperimentalFoundationApi::class)
@Composable
fun MainScreen(
navToProfile: (username: String) -> Unit,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,12 +28,12 @@ class HomeStore(
initialState = State.INIT
) {

private val collections: StateFlow<PagingData<CollectionModel>>
get() = Pager(config = config) { PagingSource(interactor::getAllCollections) }
private val collections: StateFlow<PagingData<CollectionModel>> =
Pager(config = config) { PagingSource(interactor::getAllCollections) }
.state { collection -> collection.toPresentation() }

private val photos: StateFlow<PagingData<PhotoModel>>
get() = Pager(config = config) { PagingSource(interactor::getAllPhotos) }
private val photos: StateFlow<PagingData<PhotoModel>> =
Pager(config = config) { PagingSource(interactor::getAllPhotos) }
.state { image -> image.toPresentation() }

override fun sendAction(action: Action) {
Expand Down
Loading