Update the book lazy on the homepage + homepage error management.
This commit is contained in:
		
							parent
							
								
									58ebd970f2
								
							
						
					
					
						commit
						c9049be239
					
				
					 11 changed files with 204 additions and 122 deletions
				
			
		| 
						 | 
				
			
			@ -124,6 +124,7 @@ dependencies {
 | 
			
		|||
    implementation "com.google.accompanist:accompanist-insets:0.26.5-rc"
 | 
			
		||||
    implementation "com.google.accompanist:accompanist-pager:0.26.5-rc"
 | 
			
		||||
    implementation "com.google.accompanist:accompanist-placeholder-material:0.26.5-rc"
 | 
			
		||||
    implementation "com.google.accompanist:accompanist-swiperefresh:0.26.5-rc"
 | 
			
		||||
 | 
			
		||||
    // Landscapist
 | 
			
		||||
    implementation "com.github.skydoves:landscapist-glide:1.5.2"
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -26,6 +26,7 @@ import com.pixelized.biblib.ui.screen.authentication.viewModel.AuthenticationFor
 | 
			
		|||
import com.pixelized.biblib.ui.screen.authentication.viewModel.AuthenticationViewModel
 | 
			
		||||
import com.pixelized.biblib.ui.theme.color.ShadowPalette
 | 
			
		||||
import com.pixelized.biblib.utils.extention.bibLib
 | 
			
		||||
import com.pixelized.biblib.R
 | 
			
		||||
import kotlinx.coroutines.launch
 | 
			
		||||
 | 
			
		||||
@Stable
 | 
			
		||||
| 
						 | 
				
			
			@ -43,22 +44,16 @@ sealed class AuthenticationUio {
 | 
			
		|||
@Stable
 | 
			
		||||
@Immutable
 | 
			
		||||
sealed class AuthenticationErrorUio(
 | 
			
		||||
    @StringRes val message: Int,
 | 
			
		||||
    @StringRes val action: Int,
 | 
			
		||||
    @StringRes val message: Int = R.string.error_authentication_message,
 | 
			
		||||
    @StringRes val action: Int = R.string.error_authentication_action,
 | 
			
		||||
) {
 | 
			
		||||
    @Stable
 | 
			
		||||
    @Immutable
 | 
			
		||||
    class Login(
 | 
			
		||||
        @StringRes message: Int,
 | 
			
		||||
        @StringRes action: Int,
 | 
			
		||||
    ) : AuthenticationErrorUio(message, action)
 | 
			
		||||
    class Login : AuthenticationErrorUio()
 | 
			
		||||
 | 
			
		||||
    @Stable
 | 
			
		||||
    @Immutable
 | 
			
		||||
    class GoogleLogin(
 | 
			
		||||
        @StringRes message: Int,
 | 
			
		||||
        @StringRes action: Int,
 | 
			
		||||
    ) : AuthenticationErrorUio(message, action)
 | 
			
		||||
    class GoogleLogin : AuthenticationErrorUio()
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@Composable
 | 
			
		||||
| 
						 | 
				
			
			@ -72,8 +67,6 @@ fun AuthenticationScreen(
 | 
			
		|||
    val context = LocalContext.current
 | 
			
		||||
    val scope = rememberCoroutineScope()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    AuthenticationScreenContent(
 | 
			
		||||
        modifier = Modifier.systemBarsPadding(),
 | 
			
		||||
        login = formViewModel.form.login,
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -65,10 +65,7 @@ class AuthenticationViewModel @Inject constructor(
 | 
			
		|||
                Log.e("AuthenticationViewModel", exception.message, exception)
 | 
			
		||||
                _authenticationProcess.value = null
 | 
			
		||||
                _authenticationError.emit(
 | 
			
		||||
                    AuthenticationErrorUio.Login(
 | 
			
		||||
                        message = R.string.error_authentication_message,
 | 
			
		||||
                        action = R.string.error_authentication_action,
 | 
			
		||||
                    )
 | 
			
		||||
                    AuthenticationErrorUio.Login(),
 | 
			
		||||
                )
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
| 
						 | 
				
			
			@ -98,12 +95,7 @@ class AuthenticationViewModel @Inject constructor(
 | 
			
		|||
                    } catch (exception: Exception) {
 | 
			
		||||
                        Log.e("AuthenticationViewModel", exception.message, exception)
 | 
			
		||||
                        _authenticationProcess.value = null
 | 
			
		||||
                        _authenticationError.emit(
 | 
			
		||||
                            AuthenticationErrorUio.GoogleLogin(
 | 
			
		||||
                                message = R.string.error_authentication_message,
 | 
			
		||||
                                action = R.string.error_authentication_action,
 | 
			
		||||
                            )
 | 
			
		||||
                        )
 | 
			
		||||
                        _authenticationError.emit(AuthenticationErrorUio.GoogleLogin())
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -0,0 +1,56 @@
 | 
			
		|||
package com.pixelized.biblib.ui.screen.home
 | 
			
		||||
 | 
			
		||||
import android.util.Log
 | 
			
		||||
import androidx.compose.runtime.getValue
 | 
			
		||||
import androidx.compose.runtime.mutableStateOf
 | 
			
		||||
import androidx.compose.runtime.setValue
 | 
			
		||||
import androidx.lifecycle.ViewModel
 | 
			
		||||
import androidx.lifecycle.viewModelScope
 | 
			
		||||
import com.pixelized.biblib.network.client.IBibLibClient
 | 
			
		||||
import com.pixelized.biblib.repository.apiCache.IAPICacheRepository
 | 
			
		||||
import com.pixelized.biblib.repository.book.IBookRepository
 | 
			
		||||
import dagger.hilt.android.lifecycle.HiltViewModel
 | 
			
		||||
import kotlinx.coroutines.Dispatchers
 | 
			
		||||
import kotlinx.coroutines.flow.Flow
 | 
			
		||||
import kotlinx.coroutines.flow.MutableSharedFlow
 | 
			
		||||
import kotlinx.coroutines.launch
 | 
			
		||||
import kotlinx.coroutines.withContext
 | 
			
		||||
import javax.inject.Inject
 | 
			
		||||
 | 
			
		||||
@HiltViewModel
 | 
			
		||||
class BooksViewModel @Inject constructor(
 | 
			
		||||
    private val repository: IBookRepository,
 | 
			
		||||
    private val client: IBibLibClient,
 | 
			
		||||
    private val cache: IAPICacheRepository,
 | 
			
		||||
) : ViewModel() {
 | 
			
		||||
 | 
			
		||||
    var isLoading: Boolean by mutableStateOf(false)
 | 
			
		||||
        private set
 | 
			
		||||
 | 
			
		||||
    private val _updateError = MutableSharedFlow<BookUpdateErrorUio>()
 | 
			
		||||
    val updateError: Flow<BookUpdateErrorUio> get() = _updateError
 | 
			
		||||
 | 
			
		||||
    init {
 | 
			
		||||
        updateBooks()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    fun updateBooks() {
 | 
			
		||||
        viewModelScope.launch {
 | 
			
		||||
            isLoading = true
 | 
			
		||||
            try {
 | 
			
		||||
                withContext(Dispatchers.IO) {
 | 
			
		||||
                    com.pixelized.biblib.repository.book.updateBooks(
 | 
			
		||||
                        client = client,
 | 
			
		||||
                        cache = cache,
 | 
			
		||||
                        repository = repository,
 | 
			
		||||
                    )
 | 
			
		||||
                }
 | 
			
		||||
            } catch (exception: Exception) {
 | 
			
		||||
                Log.e("BooksViewModel", exception.message, exception)
 | 
			
		||||
                _updateError.emit(BookUpdateErrorUio())
 | 
			
		||||
            } finally {
 | 
			
		||||
                isLoading = false
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
| 
						 | 
				
			
			@ -1,14 +1,11 @@
 | 
			
		|||
package com.pixelized.biblib.ui.screen.home
 | 
			
		||||
 | 
			
		||||
import androidx.activity.compose.BackHandler
 | 
			
		||||
import androidx.compose.animation.*
 | 
			
		||||
import androidx.compose.foundation.layout.Box
 | 
			
		||||
import androidx.compose.foundation.layout.Column
 | 
			
		||||
import androidx.compose.foundation.layout.fillMaxSize
 | 
			
		||||
import androidx.compose.foundation.layout.statusBarsPadding
 | 
			
		||||
import androidx.compose.material.*
 | 
			
		||||
import androidx.compose.runtime.*
 | 
			
		||||
import androidx.compose.ui.Alignment
 | 
			
		||||
import androidx.compose.material.ExperimentalMaterialApi
 | 
			
		||||
import androidx.compose.runtime.Composable
 | 
			
		||||
import androidx.compose.runtime.remember
 | 
			
		||||
import androidx.compose.runtime.rememberCoroutineScope
 | 
			
		||||
import androidx.compose.ui.ExperimentalComposeUiApi
 | 
			
		||||
import androidx.compose.ui.Modifier
 | 
			
		||||
import androidx.compose.ui.focus.FocusManager
 | 
			
		||||
| 
						 | 
				
			
			@ -16,27 +13,13 @@ import androidx.compose.ui.focus.FocusRequester
 | 
			
		|||
import androidx.compose.ui.platform.LocalFocusManager
 | 
			
		||||
import androidx.compose.ui.platform.LocalSoftwareKeyboardController
 | 
			
		||||
import androidx.compose.ui.platform.SoftwareKeyboardController
 | 
			
		||||
import androidx.compose.ui.res.stringResource
 | 
			
		||||
import androidx.compose.ui.tooling.preview.Preview
 | 
			
		||||
import androidx.compose.ui.window.Dialog
 | 
			
		||||
import androidx.hilt.navigation.compose.hiltViewModel
 | 
			
		||||
import com.google.accompanist.pager.ExperimentalPagerApi
 | 
			
		||||
import com.google.accompanist.pager.HorizontalPager
 | 
			
		||||
import com.google.accompanist.pager.PagerState
 | 
			
		||||
import com.google.accompanist.pager.rememberPagerState
 | 
			
		||||
import com.pixelized.biblib.R
 | 
			
		||||
import com.pixelized.biblib.ui.scaffold.*
 | 
			
		||||
import com.pixelized.biblib.ui.screen.home.common.connectivity.ConnectivityHeader
 | 
			
		||||
import com.pixelized.biblib.ui.screen.home.common.connectivity.ConnectivityViewModel
 | 
			
		||||
import com.pixelized.biblib.ui.screen.home.page.Page
 | 
			
		||||
import com.pixelized.biblib.ui.screen.home.page.books.BooksPage
 | 
			
		||||
import com.pixelized.biblib.ui.screen.home.page.news.NewsPage
 | 
			
		||||
import com.pixelized.biblib.ui.screen.home.page.profile.ProfilePage
 | 
			
		||||
import com.pixelized.biblib.ui.screen.home.page.search.Search
 | 
			
		||||
import com.pixelized.biblib.ui.screen.home.page.search.SearchPage
 | 
			
		||||
import com.pixelized.biblib.ui.theme.BibLibTheme
 | 
			
		||||
import com.pixelized.biblib.utils.extention.bibLib
 | 
			
		||||
import kotlinx.coroutines.CoroutineScope
 | 
			
		||||
import kotlinx.coroutines.delay
 | 
			
		||||
import kotlinx.coroutines.launch
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -44,7 +27,6 @@ import kotlinx.coroutines.launch
 | 
			
		|||
@Composable
 | 
			
		||||
fun HomeScreen(
 | 
			
		||||
    homeViewModel: HomeViewModel = hiltViewModel(),
 | 
			
		||||
    connectivityViewModel: ConnectivityViewModel = hiltViewModel(),
 | 
			
		||||
    keyboard: SoftwareKeyboardController? = LocalSoftwareKeyboardController.current,
 | 
			
		||||
    searchScaffoldState: SearchScaffoldState = rememberSearchScaffoldState(),
 | 
			
		||||
) {
 | 
			
		||||
| 
						 | 
				
			
			@ -91,7 +73,6 @@ fun HomeScreen(
 | 
			
		|||
                },
 | 
			
		||||
                content = {
 | 
			
		||||
                    HomeScreenContent(
 | 
			
		||||
                        isNetworkAvailable = { connectivityViewModel.isNetworkAvailable },
 | 
			
		||||
                        pages = Page.all
 | 
			
		||||
                    )
 | 
			
		||||
                },
 | 
			
		||||
| 
						 | 
				
			
			@ -120,7 +101,7 @@ fun HomeScreen(
 | 
			
		|||
 | 
			
		||||
@Composable
 | 
			
		||||
fun ProfileHandler(
 | 
			
		||||
    viewModel: HomeViewModel
 | 
			
		||||
    viewModel: HomeViewModel = hiltViewModel()
 | 
			
		||||
) {
 | 
			
		||||
    if (viewModel.shouldDisplayProfileDialog) {
 | 
			
		||||
        Dialog(
 | 
			
		||||
| 
						 | 
				
			
			@ -129,73 +110,4 @@ fun ProfileHandler(
 | 
			
		|||
            ProfilePage()
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@OptIn(ExperimentalPagerApi::class)
 | 
			
		||||
@Composable
 | 
			
		||||
fun HomeScreenContent(
 | 
			
		||||
    isNetworkAvailable: () -> State<Boolean>,
 | 
			
		||||
    pages: List<Page> = Page.all
 | 
			
		||||
) {
 | 
			
		||||
    val scope: CoroutineScope = rememberCoroutineScope()
 | 
			
		||||
    val pagerState: PagerState = rememberPagerState()
 | 
			
		||||
 | 
			
		||||
    Column {
 | 
			
		||||
        ScrollableTabRow(
 | 
			
		||||
            selectedTabIndex = pagerState.currentPage,
 | 
			
		||||
            edgePadding = MaterialTheme.bibLib.dimen.dp16,
 | 
			
		||||
        ) {
 | 
			
		||||
            pages.forEachIndexed { index, page ->
 | 
			
		||||
                Tab(
 | 
			
		||||
                    selected = pagerState.currentPage == index,
 | 
			
		||||
                    text = { Text(text = stringResource(id = page.label)) },
 | 
			
		||||
                    onClick = { scope.launch { pagerState.animateScrollToPage(index) } },
 | 
			
		||||
                )
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        ConnectivityHeader(
 | 
			
		||||
            isNetworkAvailable = isNetworkAvailable,
 | 
			
		||||
        )
 | 
			
		||||
 | 
			
		||||
        HorizontalPager(
 | 
			
		||||
            modifier = Modifier.fillMaxSize(),
 | 
			
		||||
            state = pagerState,
 | 
			
		||||
            count = pages.size
 | 
			
		||||
        ) {
 | 
			
		||||
            when (pages[it]) {
 | 
			
		||||
                is Page.News -> NewsPage()
 | 
			
		||||
                is Page.Books -> BooksPage()
 | 
			
		||||
                is Page.Author -> NotYetImplemented()
 | 
			
		||||
                is Page.Series -> NotYetImplemented()
 | 
			
		||||
                is Page.Tag -> NotYetImplemented()
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@Composable
 | 
			
		||||
private fun NotYetImplemented() {
 | 
			
		||||
    Box(
 | 
			
		||||
        modifier = Modifier.fillMaxSize(),
 | 
			
		||||
        contentAlignment = Alignment.Center,
 | 
			
		||||
    ) {
 | 
			
		||||
        Text(
 | 
			
		||||
            style = MaterialTheme.typography.body1,
 | 
			
		||||
            color = MaterialTheme.colors.onSurface,
 | 
			
		||||
            text = stringResource(id = R.string.not_implemented_yet)
 | 
			
		||||
        )
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@Composable
 | 
			
		||||
@Preview(showBackground = true)
 | 
			
		||||
private fun HomeScreenContentPreview() {
 | 
			
		||||
    BibLibTheme {
 | 
			
		||||
        val isNetworkAvailable = { mutableStateOf(true) }
 | 
			
		||||
        HomeScreenContent(
 | 
			
		||||
            isNetworkAvailable = isNetworkAvailable,
 | 
			
		||||
            pages = Page.all,
 | 
			
		||||
        )
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
| 
						 | 
				
			
			@ -0,0 +1,129 @@
 | 
			
		|||
package com.pixelized.biblib.ui.screen.home
 | 
			
		||||
 | 
			
		||||
import androidx.annotation.StringRes
 | 
			
		||||
import androidx.compose.animation.AnimatedVisibility
 | 
			
		||||
import androidx.compose.animation.fadeIn
 | 
			
		||||
import androidx.compose.animation.fadeOut
 | 
			
		||||
import androidx.compose.foundation.layout.Box
 | 
			
		||||
import androidx.compose.foundation.layout.Column
 | 
			
		||||
import androidx.compose.foundation.layout.fillMaxSize
 | 
			
		||||
import androidx.compose.foundation.layout.fillMaxWidth
 | 
			
		||||
import androidx.compose.material.*
 | 
			
		||||
import androidx.compose.runtime.Composable
 | 
			
		||||
import androidx.compose.runtime.LaunchedEffect
 | 
			
		||||
import androidx.compose.runtime.Stable
 | 
			
		||||
import androidx.compose.runtime.rememberCoroutineScope
 | 
			
		||||
import androidx.compose.ui.Alignment
 | 
			
		||||
import androidx.compose.ui.Modifier
 | 
			
		||||
import androidx.compose.ui.platform.LocalContext
 | 
			
		||||
import androidx.compose.ui.res.stringResource
 | 
			
		||||
import androidx.hilt.navigation.compose.hiltViewModel
 | 
			
		||||
import com.google.accompanist.pager.ExperimentalPagerApi
 | 
			
		||||
import com.google.accompanist.pager.HorizontalPager
 | 
			
		||||
import com.google.accompanist.pager.PagerState
 | 
			
		||||
import com.google.accompanist.pager.rememberPagerState
 | 
			
		||||
import com.google.accompanist.swiperefresh.SwipeRefresh
 | 
			
		||||
import com.google.accompanist.swiperefresh.rememberSwipeRefreshState
 | 
			
		||||
import com.pixelized.biblib.R
 | 
			
		||||
import com.pixelized.biblib.ui.LocalSnackHostState
 | 
			
		||||
import com.pixelized.biblib.ui.screen.home.common.connectivity.ConnectivityHeader
 | 
			
		||||
import com.pixelized.biblib.ui.screen.home.common.connectivity.ConnectivityViewModel
 | 
			
		||||
import com.pixelized.biblib.ui.screen.home.page.Page
 | 
			
		||||
import com.pixelized.biblib.ui.screen.home.page.books.BooksPage
 | 
			
		||||
import com.pixelized.biblib.ui.screen.home.page.news.NewsPage
 | 
			
		||||
import com.pixelized.biblib.utils.extention.bibLib
 | 
			
		||||
import kotlinx.coroutines.CoroutineScope
 | 
			
		||||
import kotlinx.coroutines.launch
 | 
			
		||||
 | 
			
		||||
@Stable
 | 
			
		||||
data class BookUpdateErrorUio(
 | 
			
		||||
    @StringRes val message: Int = R.string.error_book_update_message,
 | 
			
		||||
    @StringRes val action: Int = R.string.error_book_update_action
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
@OptIn(ExperimentalPagerApi::class)
 | 
			
		||||
@Composable
 | 
			
		||||
fun HomeScreenContent(
 | 
			
		||||
    connectivityViewModel: ConnectivityViewModel = hiltViewModel(),
 | 
			
		||||
    booksViewModel: BooksViewModel = hiltViewModel(),
 | 
			
		||||
    pages: List<Page> = Page.all
 | 
			
		||||
) {
 | 
			
		||||
    val scope: CoroutineScope = rememberCoroutineScope()
 | 
			
		||||
    val pagerState: PagerState = rememberPagerState()
 | 
			
		||||
    val snackBarHostState = LocalSnackHostState.current
 | 
			
		||||
    val context = LocalContext.current
 | 
			
		||||
 | 
			
		||||
    LaunchedEffect(key1 = "BookUpdateError") {
 | 
			
		||||
        booksViewModel.updateError.collect {
 | 
			
		||||
            val result = snackBarHostState.showSnackbar(
 | 
			
		||||
                message = context.getString(it.message),
 | 
			
		||||
                actionLabel = context.getString(it.action),
 | 
			
		||||
            )
 | 
			
		||||
            if (result == SnackbarResult.ActionPerformed) {
 | 
			
		||||
                booksViewModel.updateBooks()
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    Column {
 | 
			
		||||
        ScrollableTabRow(
 | 
			
		||||
            selectedTabIndex = pagerState.currentPage,
 | 
			
		||||
            edgePadding = MaterialTheme.bibLib.dimen.dp16,
 | 
			
		||||
        ) {
 | 
			
		||||
            pages.forEachIndexed { index, page ->
 | 
			
		||||
                Tab(
 | 
			
		||||
                    selected = pagerState.currentPage == index,
 | 
			
		||||
                    text = { Text(text = stringResource(id = page.label)) },
 | 
			
		||||
                    onClick = { scope.launch { pagerState.animateScrollToPage(index) } },
 | 
			
		||||
                )
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        ConnectivityHeader(
 | 
			
		||||
            isNetworkAvailable = { connectivityViewModel.isNetworkAvailable },
 | 
			
		||||
        )
 | 
			
		||||
 | 
			
		||||
        SwipeRefresh(
 | 
			
		||||
            state = rememberSwipeRefreshState(isRefreshing = false),
 | 
			
		||||
            onRefresh = { booksViewModel.updateBooks() }
 | 
			
		||||
        ) {
 | 
			
		||||
            HorizontalPager(
 | 
			
		||||
                modifier = Modifier.fillMaxSize(),
 | 
			
		||||
                state = pagerState,
 | 
			
		||||
                count = pages.size
 | 
			
		||||
            ) {
 | 
			
		||||
                when (pages[it]) {
 | 
			
		||||
                    is Page.News -> NewsPage()
 | 
			
		||||
                    is Page.Books -> BooksPage()
 | 
			
		||||
                    is Page.Author -> Empty()
 | 
			
		||||
                    is Page.Series -> Empty()
 | 
			
		||||
                    is Page.Tag -> Empty()
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            AnimatedVisibility(
 | 
			
		||||
                visible = booksViewModel.isLoading,
 | 
			
		||||
                enter = fadeIn(),
 | 
			
		||||
                exit = fadeOut(),
 | 
			
		||||
            ) {
 | 
			
		||||
                LinearProgressIndicator(
 | 
			
		||||
                    modifier = Modifier.fillMaxWidth()
 | 
			
		||||
                )
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@Composable
 | 
			
		||||
private fun Empty() {
 | 
			
		||||
    Box(
 | 
			
		||||
        modifier = Modifier.fillMaxSize(),
 | 
			
		||||
        contentAlignment = Alignment.Center,
 | 
			
		||||
    ) {
 | 
			
		||||
        Text(
 | 
			
		||||
            style = MaterialTheme.typography.body1,
 | 
			
		||||
            color = MaterialTheme.colors.onSurface,
 | 
			
		||||
            text = stringResource(id = R.string.not_implemented_yet)
 | 
			
		||||
        )
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
| 
						 | 
				
			
			@ -4,12 +4,8 @@ import androidx.compose.runtime.getValue
 | 
			
		|||
import androidx.compose.runtime.mutableStateOf
 | 
			
		||||
import androidx.compose.runtime.setValue
 | 
			
		||||
import androidx.lifecycle.ViewModel
 | 
			
		||||
import androidx.lifecycle.viewModelScope
 | 
			
		||||
import com.pixelized.biblib.repository.googleSignIn.IGoogleSingInRepository
 | 
			
		||||
import dagger.hilt.android.lifecycle.HiltViewModel
 | 
			
		||||
import kotlinx.coroutines.flow.Flow
 | 
			
		||||
import kotlinx.coroutines.flow.MutableSharedFlow
 | 
			
		||||
import kotlinx.coroutines.launch
 | 
			
		||||
import javax.inject.Inject
 | 
			
		||||
 | 
			
		||||
@HiltViewModel
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -25,7 +25,7 @@ import kotlinx.coroutines.launch
 | 
			
		|||
 | 
			
		||||
@Composable
 | 
			
		||||
fun BooksPage(
 | 
			
		||||
    newsViewModel: BooksViewModel = hiltViewModel()
 | 
			
		||||
    newsViewModel: LibraryViewModel = hiltViewModel()
 | 
			
		||||
) {
 | 
			
		||||
    val books = newsViewModel.books
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -13,7 +13,7 @@ import javax.inject.Inject
 | 
			
		|||
 | 
			
		||||
 | 
			
		||||
@HiltViewModel
 | 
			
		||||
class BooksViewModel @Inject constructor(
 | 
			
		||||
class LibraryViewModel @Inject constructor(
 | 
			
		||||
    bookRepository: IBookRepository,
 | 
			
		||||
) : ViewModel() {
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -18,6 +18,7 @@
 | 
			
		|||
 | 
			
		||||
    <string name="error_action_retry">Réessayer</string>
 | 
			
		||||
    <string name="error_authentication_message">L\'authentification à BibLib à échouée.</string>
 | 
			
		||||
    <string name="error_book_update_message">La mise à jour de la librarie à échouée.</string>
 | 
			
		||||
    <string name="error_get_book_detail_message">La récupération des détails a échouée.</string>
 | 
			
		||||
    <string name="error_send_book_message">L\'envoi de l\'eBook a échoué.</string>
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -23,8 +23,10 @@
 | 
			
		|||
    <!-- Error -->
 | 
			
		||||
 | 
			
		||||
    <string name="error_action_retry">Retry</string>
 | 
			
		||||
    <string name="error_authentication_message">Failed to connect to BibLib</string>
 | 
			
		||||
    <string name="error_authentication_message">Failed to connect to BibLib.</string>
 | 
			
		||||
    <string name="error_authentication_action" translatable="false">@string/error_action_retry</string>
 | 
			
		||||
    <string name="error_book_update_message">Failed to update BibLib library.</string>
 | 
			
		||||
    <string name="error_book_update_action" translatable="false">@string/error_action_retry</string>
 | 
			
		||||
    <string name="error_get_book_detail_message">Failed to retrieve book details.</string>
 | 
			
		||||
    <string name="error_get_book_detail_action" translatable="false">@string/error_action_retry</string>
 | 
			
		||||
    <string name="error_send_book_message">Failed to send the book to your kindle.</string>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue