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

Gsoc 2023 migrating cast vote activity to jetpack compose #57

Large diffs are not rendered by default.

Original file line number Diff line number Diff line change
@@ -1,15 +1,25 @@
package org.aossie.agoraandroid.ui.activities.castVote

import androidx.compose.runtime.State
import androidx.compose.runtime.mutableStateOf
import androidx.lifecycle.ViewModel
import androidx.lifecycle.viewModelScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.delay
import kotlinx.coroutines.flow.MutableSharedFlow
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.StateFlow
import kotlinx.coroutines.flow.asSharedFlow
import kotlinx.coroutines.flow.asStateFlow
import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext
import org.aossie.agoraandroid.R
import org.aossie.agoraandroid.domain.model.ElectionDtoModel
import org.aossie.agoraandroid.domain.useCases.castVoteActivity.CastVoteActivityUseCases
import org.aossie.agoraandroid.ui.fragments.electionDetails.ElectionDetailsViewModel.UiEvents
import org.aossie.agoraandroid.ui.screens.common.Util.ScreensState
import org.aossie.agoraandroid.utilities.ApiException
import org.aossie.agoraandroid.utilities.AppConstants
import org.aossie.agoraandroid.utilities.NoInternetException
import org.aossie.agoraandroid.utilities.ResponseUI
import java.net.HttpURLConnection
Expand All @@ -23,39 +33,45 @@ constructor(
private val castVoteActivityUseCases: CastVoteActivityUseCases
) : ViewModel() {

private val mVerifyVoterResponse = MutableStateFlow<ResponseUI<Any>?>(null)

val verifyVoterResponse: StateFlow<ResponseUI<Any>?>
get() = mVerifyVoterResponse

private val _getDeepLinkStateFlow = MutableStateFlow<ResponseUI<String>?>(null)

val getDeepLinkStateFlow: StateFlow<ResponseUI<String>?>
get() = _getDeepLinkStateFlow

private val mCastVoteResponse = MutableStateFlow<ResponseUI<Any>?>(null)

val castVoteResponse: StateFlow<ResponseUI<Any>?>
get() = mCastVoteResponse

private val mElection = MutableStateFlow<ElectionDtoModel?>(null)

val election: StateFlow<ElectionDtoModel?>
get() = mElection

private val _progressAndErrorState = mutableStateOf(ScreensState())
val progressAndErrorState: State<ScreensState> = _progressAndErrorState

private val _verifiedVoter = MutableStateFlow(false)
val verifiedVoter = _verifiedVoter.asStateFlow()

private val _uiEventsFlow = MutableSharedFlow<UiEvents>()
val uiEventsFlow = _uiEventsFlow.asSharedFlow()

fun verifyVoter(id: String) {
_verifiedVoter.value = false
viewModelScope.launch {
try {
val electionDtoModel = castVoteActivityUseCases.verifyVotersUseCase(id)
electionDtoModel._id = id
mVerifyVoterResponse.value = ResponseUI.success()
_verifiedVoter.value = true
mElection.value = electionDtoModel
} catch (e: ApiException) {
mVerifyVoterResponse.value = ResponseUI.error(e.message)
showMessage(e.message!!)
delay(2000)
_uiEventsFlow.emit(UiEvents.VerifyVoterError)
} catch (e: NoInternetException) {
mVerifyVoterResponse.value = ResponseUI.error(e.message)
showMessage(e.message!!)
delay(2000)
_uiEventsFlow.emit(UiEvents.VerifyVoterError)
} catch (e: Exception) {
mVerifyVoterResponse.value = ResponseUI.error(e.message)
showMessage(e.message!!)
delay(2000)
_uiEventsFlow.emit(UiEvents.VerifyVoterError)
}
}
}
Expand All @@ -65,16 +81,19 @@ constructor(
ballotInput: String,
passCode: String
) {
showLoading("Casting your vote...")
viewModelScope.launch {
try {
castVoteActivityUseCases.castVoteUseCase(id, ballotInput, passCode)
mCastVoteResponse.value = ResponseUI.success()
showMessage(R.string.vote_successful)
delay(2000)
_uiEventsFlow.emit(UiEvents.VoteCastSuccessFull)
} catch (e: ApiException) {
mCastVoteResponse.value = ResponseUI.error(e.message)
showMessage(e.message!!)
} catch (e: NoInternetException) {
mCastVoteResponse.value = ResponseUI.error(e.message)
showMessage(e.message!!)
} catch (e: Exception) {
mCastVoteResponse.value = ResponseUI.error(e.message)
showMessage(e.message!!)
}
}
}
Expand All @@ -101,4 +120,38 @@ constructor(
}
}
}

private fun showLoading(message: Any) {
_progressAndErrorState.value = progressAndErrorState.value.copy(
loading = Pair(message,true)
)
}

fun showMessage(message: Any) {
_progressAndErrorState.value = progressAndErrorState.value.copy(
message = Pair(message,true),
loading = Pair("",false)
)
viewModelScope.launch {
delay(AppConstants.SNACKBAR_DURATION)
hideSnackBar()
}
}

private fun hideSnackBar() {
_progressAndErrorState.value = progressAndErrorState.value.copy(
message = Pair("",false)
)
}

private fun hideLoading() {
_progressAndErrorState.value = progressAndErrorState.value.copy(
loading = Pair("",false)
)
}

sealed class UiEvents{
object VoteCastSuccessFull:UiEvents()
object VerifyVoterError:UiEvents()
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,6 @@ import org.aossie.agoraandroid.domain.model.ElectionModel
import org.aossie.agoraandroid.domain.useCases.displayElection.DisplayElectionsUseCases
import org.aossie.agoraandroid.ui.screens.common.Util.ScreensState
import org.aossie.agoraandroid.utilities.AppConstants
import org.aossie.agoraandroid.utilities.lazyDeferred
import java.text.SimpleDateFormat
import java.util.Calendar
import java.util.Date
Expand Down Expand Up @@ -71,6 +70,7 @@ constructor(
showMessage(R.string.something_went_wrong_please_try_again_later)
}
}
}

fun getPendingElectionsState(query:String) {
viewModelScope.launch {
Expand Down Expand Up @@ -112,69 +112,6 @@ constructor(
)
}

val finishedElections = MutableStateFlow<List<ElectionModel>>(emptyList())
val search = mutableStateOf("")

private val _progressAndErrorState = MutableStateFlow (ScreensState())
val progressAndErrorState = _progressAndErrorState.asStateFlow()

fun getFinishedElectionsState(query:String){
viewModelScope.launch {
try {
displayElectionsUseCases.getFinishedElections(date).collectLatest { list ->
search.value = query
if(query.isEmpty()) {
finishedElections.emit(list)
}else{
finishedElections.emit(filter(list, query))
}
}
} catch (e: IllegalStateException) {
showMessage(R.string.something_went_wrong_please_try_again_later)
}
}
}

fun getActiveElectionsState(query:String) {
viewModelScope.launch {
try {
displayElectionsUseCases.getActiveElections(date).collectLatest { list ->
search.value = query
if(query.isEmpty()) {
activeElections.emit(list)
}else{
activeElections.emit(filter(list, query))
}
}
} catch (e: IllegalStateException) {
showMessage(R.string.something_went_wrong_please_try_again_later)
}
}
}

private fun showLoading(message: Any) {
_progressAndErrorState.value = progressAndErrorState.value.copy(
loading = Pair(message,true)
)
}

fun showMessage(message: Any) {
_progressAndErrorState.value = progressAndErrorState.value.copy(
message = Pair(message,true),
loading = Pair("",false)
)
viewModelScope.launch {
delay(AppConstants.SNACKBAR_DURATION)
hideSnackBar()
}
}

private fun hideSnackBar() {
_progressAndErrorState.value = progressAndErrorState.value.copy(
message = Pair("",false)
)
}

private fun hideLoading() {
_progressAndErrorState.value = progressAndErrorState.value.copy(
loading = Pair("",false)
Expand Down
Original file line number Diff line number Diff line change
@@ -1,9 +1,11 @@
package org.aossie.agoraandroid.ui.fragments.electionDetails

import android.content.Intent
import android.os.Bundle
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import androidx.compose.runtime.collectAsState
import androidx.compose.runtime.getValue
import androidx.compose.ui.platform.ComposeView
import androidx.fragment.app.Fragment
Expand All @@ -17,14 +19,18 @@ import kotlinx.coroutines.flow.collectLatest
import kotlinx.coroutines.launch
import org.aossie.agoraandroid.R
import org.aossie.agoraandroid.data.db.PreferenceProvider
import org.aossie.agoraandroid.ui.activities.castVote.CastVoteActivity
import org.aossie.agoraandroid.ui.activities.castVote.CastVoteViewModel
import org.aossie.agoraandroid.ui.fragments.BaseFragment
import org.aossie.agoraandroid.ui.fragments.electionDetails.ElectionDetailsViewModel.UiEvents.ElectionDeleted
import org.aossie.agoraandroid.ui.fragments.electionDetails.ElectionDetailsViewModel.UiEvents.InviteVoters
import org.aossie.agoraandroid.ui.fragments.electionDetails.ElectionDetailsViewModel.UiEvents.ViewResults
import org.aossie.agoraandroid.ui.screens.electionDetails.ElectionDetailsScreen
import org.aossie.agoraandroid.ui.screens.electionDetails.events.ElectionDetailsScreenEvent.BallotClick
import org.aossie.agoraandroid.ui.screens.electionDetails.events.ElectionDetailsScreenEvent.CastVoteClick
import org.aossie.agoraandroid.ui.screens.electionDetails.events.ElectionDetailsScreenEvent.ViewVotersClick
import org.aossie.agoraandroid.ui.theme.AgoraTheme
import org.aossie.agoraandroid.utilities.AppConstants
import javax.inject.Inject

/**
Expand All @@ -42,6 +48,9 @@ constructor(
private val electionDetailsViewModel: ElectionDetailsViewModel by viewModels {
viewModelFactory
}
private val castVoteViewModel: CastVoteViewModel by viewModels {
viewModelFactory
}
private lateinit var composeView: ComposeView
override fun onCreateView(
inflater: LayoutInflater,
Expand All @@ -66,10 +75,12 @@ constructor(
composeView.setContent {
val progressErrorState by electionDetailsViewModel.progressAndErrorState
val electionDetails by electionDetailsViewModel.electionState
val verifiedVoterStatus by castVoteViewModel.verifiedVoter.collectAsState()
AgoraTheme {
ElectionDetailsScreen(
screenState = progressErrorState,
electionDetails = electionDetails
electionDetails = electionDetails,
verifiedVoterStatus = verifiedVoterStatus
) { event->
when(event){
BallotClick -> {
Expand All @@ -86,13 +97,25 @@ constructor(
)
findNavController().navigate(action)
}
CastVoteClick -> {
val intent = Intent(requireActivity(), CastVoteActivity::class.java)
intent.putExtra(AppConstants.ELECTION_ID, id!!)
startActivity(intent)
}
else -> electionDetailsViewModel.onEvent(event)
}
}
}
}
}

override fun onResume() {
super.onResume()
id?.let {
castVoteViewModel.verifyVoter(it)
}
}

override fun onNetworkConnected() {
electionDetailsViewModel.getElectionDetailsById(id ?: "")
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@ import kotlinx.coroutines.delay
import kotlinx.coroutines.flow.MutableSharedFlow
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.asSharedFlow
import kotlinx.coroutines.flow.StateFlow
import kotlinx.coroutines.flow.asStateFlow
import kotlinx.coroutines.launch
import org.aossie.agoraandroid.data.db.PreferenceProvider
Expand Down Expand Up @@ -45,9 +44,6 @@ constructor(
.time
private val date: String = formatter.format(currentDate)

private val _progressAndErrorState = MutableStateFlow (ScreensState())
val progressAndErrorState = _progressAndErrorState.asStateFlow()

private val _countMediatorLiveData = MediatorLiveData<MutableMap<String, Int>>()
val countMediatorLiveData = _countMediatorLiveData

Expand Down
Loading
Loading