From 8ca11f3421ef2f883c83abb53ac6b46d6468c16b Mon Sep 17 00:00:00 2001 From: AdityaGaikwad Date: Wed, 8 May 2024 13:27:53 +0530 Subject: [PATCH] problem solved related to count down timer of resend otp with viewmodel architect --- .../woka/onboard/fragments/GetCodeFragment.kt | 50 ++++++------- .../onboard/fragments/GetEmailFragment.kt | 75 +++++++++---------- .../com/woka/onboard/mvvm/OnboardViewModel.kt | 26 +++++++ app/src/main/res/layout/fragment_get_code.xml | 2 +- 4 files changed, 87 insertions(+), 66 deletions(-) diff --git a/app/src/main/java/com/woka/onboard/fragments/GetCodeFragment.kt b/app/src/main/java/com/woka/onboard/fragments/GetCodeFragment.kt index b75f56b..76ba5c6 100644 --- a/app/src/main/java/com/woka/onboard/fragments/GetCodeFragment.kt +++ b/app/src/main/java/com/woka/onboard/fragments/GetCodeFragment.kt @@ -49,8 +49,6 @@ class GetCodeFragment : Fragment() { private lateinit var viewModel: OnboardViewModel private lateinit var progressView: ProgressView - private lateinit var countDownTimer: CountDownTimer - override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) arguments?.let { @@ -81,21 +79,22 @@ class GetCodeFragment : Fragment() { override fun onViewCreated(view: View, savedInstanceState: Bundle?) { super.onViewCreated(view, savedInstanceState) - // count down timer - startCountDown() - // observing live data viewModel.sendOTPLiveData.observe(viewLifecycleOwner){ when(it){ is ApiResult.Error -> { progressView.hide() Toast.makeText(activity, "${it.errorMessage}", Toast.LENGTH_SHORT).show() + + // stating null status for otp sent live data so that when user goes back to the otp screen + // they do not encounter a success status again + viewModel.clearSendOTPData() } is ApiResult.Loading -> { progressView.show("Sending OTP...") } is ApiResult.Success -> { - startCountDown() + viewModel.startOTPTimeCountDown() Toast.makeText(activity, "OTP sent successfully", Toast.LENGTH_SHORT).show() progressView.hide() uniqueString = it.data?.unique_string?:"" @@ -130,14 +129,30 @@ class GetCodeFragment : Fragment() { null -> {} } } + + viewModel.otpResendTimeLiveData.observe(viewLifecycleOwner){ + if (it == 0L){ + // no time is ticking + binding.countdown.visibility = GONE + binding.resend.visibility = VISIBLE + }else{ + // time is ticking + binding.countdown.visibility = VISIBLE + binding.resend.visibility = GONE + + val rms = (it)/1000 // remaining time in second + val time = "%02d:%02d".format(rms/60, rms%60) + val text = "OTP is valid for $time Min" + Log.d("aditya_testing", "onTick: $it") + binding.countdown.text = text + } + } } override fun onDestroyView() { super.onDestroyView() viewModel.clearValidateOTP() viewModel.clearSendOTPData() - - countDownTimer.cancel() } private fun initViews() { @@ -205,25 +220,6 @@ class GetCodeFragment : Fragment() { } } - private fun startCountDown(){ - binding.countdown.visibility = VISIBLE - binding.resend.visibility = GONE - - countDownTimer = object :CountDownTimer(OTP_RESEND_COUNT_DOWN_TIME, 1000){ - override fun onTick(millisUntilFinished: Long) { - val rms = (millisUntilFinished)/1000 // remaining time in second - val time = "%02d:%02d".format(rms/60, rms%60) - val text = "OTP is valid for $time Min" - binding.countdown.text = text - } - - override fun onFinish() { - binding.countdown.visibility = GONE - binding.resend.visibility = VISIBLE - } - }.start() - } - private fun getOTP(): String { binding.apply { return "${et1.text}${et2.text}${et3.text}${et4.text}" diff --git a/app/src/main/java/com/woka/onboard/fragments/GetEmailFragment.kt b/app/src/main/java/com/woka/onboard/fragments/GetEmailFragment.kt index daa4c93..92dae7c 100644 --- a/app/src/main/java/com/woka/onboard/fragments/GetEmailFragment.kt +++ b/app/src/main/java/com/woka/onboard/fragments/GetEmailFragment.kt @@ -90,50 +90,12 @@ class GetEmailFragment : Fragment() { null -> {} } } - - viewModel.sendOTPLiveData.observe(viewLifecycleOwner) { - when (it) { - is ApiResult.Error -> { - progressView.hide() - Toast.makeText(activity, "${it.errorMessage}", Toast.LENGTH_SHORT).show() - } - - is ApiResult.Loading -> { - progressView.show(title = "Sending OTP") - } - - is ApiResult.Success -> { - viewModel.clearSendOTPData() - progressView.hide() - - val args = if (isResetPasswordIntent) { - Bundle().apply { - putBoolean(IS_RESET_PASSWORD_INTENT, isResetPasswordIntent) - } - } else { - Bundle().apply { - putBoolean(IS_UNDER_16, isUnder16) - putString(UNIQUE_STRING_ARG, it.data?.unique_string) - putString(EMAIL_ARG, binding.email.text.toString()) - } - } - - findNavController().navigate( - R.id.action_getEmailFragment_to_getCodeFragment, - args - ) - } - - null -> {} - } - } } override fun onDestroyView() { super.onDestroyView() // removing values from live data for a fresh data when new instance is created viewModel.clearCheckEmailExist() - viewModel.clearSendOTPData() } private fun initViews() { @@ -167,6 +129,43 @@ class GetEmailFragment : Fragment() { return@setOnClickListener } + // listening to otp live data + viewModel.sendOTPLiveData.observe(viewLifecycleOwner) { + when (it) { + is ApiResult.Error -> { + progressView.hide() + Toast.makeText(activity, "${it.errorMessage}", Toast.LENGTH_SHORT).show() + } + + is ApiResult.Loading -> { + progressView.show(title = "Sending OTP") + } + + is ApiResult.Success -> { + progressView.hide() + + val args = if (isResetPasswordIntent) { + Bundle().apply { + putBoolean(IS_RESET_PASSWORD_INTENT, isResetPasswordIntent) + } + } else { + Bundle().apply { + putBoolean(IS_UNDER_16, isUnder16) + putString(UNIQUE_STRING_ARG, it.data?.unique_string) + putString(EMAIL_ARG, binding.email.text.toString()) + } + } + + findNavController().navigate( + R.id.action_getEmailFragment_to_getCodeFragment, + args + ) + } + + null -> {} + } + } + if (!isUnder16) { // parent viewModel.checkEmailExist(binding.email.text.toString(), PARENT_TYPE) diff --git a/app/src/main/java/com/woka/onboard/mvvm/OnboardViewModel.kt b/app/src/main/java/com/woka/onboard/mvvm/OnboardViewModel.kt index 9d8e6a4..7165104 100644 --- a/app/src/main/java/com/woka/onboard/mvvm/OnboardViewModel.kt +++ b/app/src/main/java/com/woka/onboard/mvvm/OnboardViewModel.kt @@ -1,5 +1,6 @@ package com.woka.onboard.mvvm +import android.os.CountDownTimer import androidx.lifecycle.LiveData import androidx.lifecycle.MutableLiveData import androidx.lifecycle.ViewModel @@ -106,4 +107,29 @@ class OnboardViewModel: ViewModel(){ _checkUserNameExistLiveData.postValue(response) } } + + // otp count down timer + private val OTP_RESEND_COUNT_DOWN_TIME = 10 * 60 * 1000L // 10 min + + private var countDownTimer: CountDownTimer? = null + private var _otpResendTimeLiveData = MutableLiveData() + val otpResendTimeLiveData: LiveData + get() = _otpResendTimeLiveData + + fun startOTPTimeCountDown(){ + countDownTimer?.cancel() + countDownTimer = object : CountDownTimer(OTP_RESEND_COUNT_DOWN_TIME, 1000){ + override fun onTick(millisUntilFinished: Long) { + _otpResendTimeLiveData.postValue(millisUntilFinished) + } + override fun onFinish() { + _otpResendTimeLiveData.postValue(0) + } + }.start() + } + + override fun onCleared() { + super.onCleared() + countDownTimer?.cancel() + } } \ No newline at end of file diff --git a/app/src/main/res/layout/fragment_get_code.xml b/app/src/main/res/layout/fragment_get_code.xml index a1f1559..b35e283 100644 --- a/app/src/main/res/layout/fragment_get_code.xml +++ b/app/src/main/res/layout/fragment_get_code.xml @@ -216,7 +216,7 @@ android:id="@+id/countdown" android:layout_width="wrap_content" android:layout_height="wrap_content" - android:visibility="visible" + android:visibility="gone" tools:text="OTP is valid for 10:00 Min" android:textColor="@color/color_primary"