大额提现子页面 rv

This commit is contained in:
renhaoting 2025-12-12 13:54:09 +08:00
parent f5ceeffaa8
commit f8face95c6
9 changed files with 161 additions and 294 deletions

View File

@ -23,7 +23,6 @@ import com.gamedog.vididin.features.withdraw.dialogs.WithdrawFailDialog
import com.gamedog.vididin.features.withdraw.dialogs.WithdrawInfoConfirmDialog
import com.gamedog.vididin.features.withdraw.dialogs.WithdrawSuccessDialog
import com.gamedog.vididin.features.withdraw.widget.WithDrawItemView
import com.gamedog.vididin.main.interfaces.OnTabStyleListener
import com.gamedog.vididin.netbase.Result
import com.gamedog.vididin.router.Router
import dagger.hilt.android.AndroidEntryPoint
@ -34,7 +33,7 @@ import com.vididin.real.money.game.databinding.ActivityWithdrawBinding as ViewBi
@AndroidEntryPoint
class WithDrawActivity : AppViewsEmptyViewModelActivity<ViewBinding>(), OnTabStyleListener {
class WithDrawActivity : AppViewsEmptyViewModelActivity<ViewBinding>() {
private val viewModel: WithdrawViewModel by viewModels()
private val mItemViewList: MutableList<WithDrawItemView> = mutableListOf()
@ -159,10 +158,6 @@ class WithDrawActivity : AppViewsEmptyViewModelActivity<ViewBinding>(), OnTabSty
//TODO("Not yet implemented")
}
override fun onTabIsDarkFont(isDarkFont: Boolean) {
//TODO("Not yet implemented")
}
private fun requestInit(withdrawNum: Float) {
lifecycleScope.launch {

View File

@ -3,40 +3,18 @@ package com.gamedog.vididin.features.withdraw
import android.app.Activity
import android.content.Intent
import android.view.LayoutInflater
import androidx.activity.viewModels
import androidx.lifecycle.Lifecycle
import androidx.lifecycle.lifecycleScope
import androidx.lifecycle.repeatOnLifecycle
import androidx.recyclerview.widget.LinearLayoutManager
import com.ama.core.architecture.appBase.AppViewsEmptyViewModelActivity
import com.ama.core.architecture.util.SpUtil
import com.gamedog.vididin.VidiConst
import com.vididin.real.money.game.R
import com.gamedog.vididin.VididinEvents
import com.gamedog.vididin.beans.resp.PayoutCheck
import com.gamedog.vididin.beans.resp.PayoutReply
import com.gamedog.vididin.beans.resp.WithdrawRecord
import com.gamedog.vididin.core.login.login.AccountManager
import com.gamedog.vididin.features.withdraw.dialogs.WithdrawFailDialog
import com.gamedog.vididin.features.withdraw.dialogs.WithdrawSuccessDialog
import com.gamedog.vididin.features.withdraw.widget.WithDrawItemView
import com.gamedog.vididin.main.interfaces.OnTabStyleListener
import com.gamedog.vididin.netbase.Result
import com.ama.core.architecture.util.CommonItemDecoration
import dagger.hilt.android.AndroidEntryPoint
import kotlinx.coroutines.launch
import kotlin.getValue
import com.vididin.real.money.game.databinding.ActivityWithdrawSubBinding as ViewBinding
@AndroidEntryPoint
class WithDrawSubActivity : AppViewsEmptyViewModelActivity<ViewBinding>(), OnTabStyleListener {
private val viewModel: WithdrawViewModel by viewModels()
private val mItemViewList: MutableList<WithDrawItemView> = mutableListOf()
private var mCurSelectedIndex: Int = 0
private val mRecordList: MutableList<WithdrawRecord> by lazy {
SpUtil.instance().getList<WithdrawRecord>(SpUtil.KEY_WITHDRAW_HISTORY_LIST).toMutableList()
}
class WithDrawSubActivity : AppViewsEmptyViewModelActivity<ViewBinding>() {
private var mType: Int = 0
private val mAdapter: WithdrawSubAdapter by lazy { WithdrawSubAdapter() }
override fun inflateViewBinding(inflater: LayoutInflater) = ViewBinding.inflate(inflater)
@ -46,277 +24,38 @@ class WithDrawSubActivity : AppViewsEmptyViewModelActivity<ViewBinding>(), OnTab
}
override fun ViewBinding.initViews() {
titlebar.setTitleText(R.string.title_withdraw_sub)
mType = intent.getIntExtra(EXTRA_TYPE, 0)
}
private fun updateUICashTotal() {
binding.tvCashTotal.text = AccountManager.getCash().toString()
recyclerView.layoutManager = LinearLayoutManager(this@WithDrawSubActivity, LinearLayoutManager.HORIZONTAL, false)
recyclerView.adapter = mAdapter
recyclerView.addItemDecoration(CommonItemDecoration.create(18, 0, false))
}
override fun ViewBinding.initListeners() {
registerEvents({ data->
when (data?.mEventType) {
VididinEvents.Event_Account_Cash_Changed -> {
updateUICashTotal()
}
VididinEvents.EVENT_AD_WATCHED_FOR_WITHDRAW -> {
var withdrawNum: Float = (data.mData as Double).toFloat()
requestInit(withdrawNum)
}
}
}, VididinEvents.Event_Account_Cash_Changed, VididinEvents.EVENT_AD_WATCHED_FOR_WITHDRAW)
checkTransactionState()
val dataList = mutableListOf<WithdrawSubItem>()
dataList.add(WithdrawSubItem(0, 1F, false))
dataList.add(WithdrawSubItem(1, 1F, true))
dataList.add(WithdrawSubItem(2, 1F, false))
dataList.add(WithdrawSubItem(3, 1F, false))
mAdapter.submitList(dataList)
}
override fun ViewBinding.initObservers() {
//TODO("Not yet implemented")
}
override fun onTabIsDarkFont(isDarkFont: Boolean) {
//TODO("Not yet implemented")
}
private fun requestInit(withdrawNum: Float) {
lifecycleScope.launch {
repeatOnLifecycle(Lifecycle.State.STARTED) {
viewModel.InitData.collect { result ->
when (result) {
is Result.Loading -> {
}
is Result.Success -> {
val reqInitBean = result.data.data
reqInitBean?.let {
var errorHintRes = 0
if (it.error == 0 && !it.uuid.isNullOrEmpty() && !it.items.isNullOrEmpty()) {
val itemId = if (withdrawNum <= VidiConst.WITHDRAW_SMALL_NUM) 0 else 1
val withDrawItem = it.items?.get(itemId)!!
if (withDrawItem.status == INIT_ACTIVE) {
requestPayout(it.uuid!!, withDrawItem.id, withdrawNum)
} else {
errorHintRes = R.string.withdraw_fail_reach_day_limit
}
} else {
// 0成功1失败2签名验证失败3客户端版本过低4 ts长度错误
when (it.error) {
3-> errorHintRes = R.string.withdraw_fail_version_toolow
}
}
if (errorHintRes > 0) {
showFailDialog(errorHintRes)
}
}
}
is Result.Error -> {
showFailDialog(R.string.withdraw_fail_unkown_error)
}
}
}
}
}
viewModel.withdrawInit()
}
private fun requestPayout(initUUID: String, payItemId: Int, payCashNum: Float) {
val currentTimeMs = System.currentTimeMillis()
lifecycleScope.launch {
repeatOnLifecycle(Lifecycle.State.STARTED) {
viewModel.PayoutResult.collect { result ->
when (result) {
is Result.Loading -> {
}
is Result.Success -> {
var errHintRes = 0
when (result.data?.data?.error) {
/* 错误码
0成功1失败2签名验证失败3客户端版本过低4uuid错误5所在地国家或地区不在提现限制内6提现金额不符对应的产品id7提现产品id不对8达到提现金额限制9提现次数超过限制10今日没有提现机会11提现账号达到次数限制12身份审核条件不满足不能提现13巴西提现参数 document_type 错误
14巴西提现参数 document_id 错误15 巴西提现参数 AccountType 错误16 巴西提现参数 Name 错误17巴西提现参数 Account DocumentId 不同18巴西提现参数account_type为CPF时 对应的 account 错误19巴西提现参数account_type为CNPJ时 对应的 account 错误20巴西提现参数 account_type 错误
21巴西提现参数 document_type 错误22巴西提现参数account_type为CPF时 对应的 document_id 错误23巴西提现参数account_type为CNPJ时 对应的 document_id 错误24 ts长度错误25 没提0.1就提现其它的
*/
0 -> {
saveNewRecord(result.data.data!!, payCashNum, currentTimeMs)
}
5-> {
errHintRes = R.string.withdraw_fail_region_restricit
}
8-> {
errHintRes = R.string.withdraw_fail_amount_limit
}
9-> {
errHintRes = R.string.withdraw_fail_amount_limit
}
}
if (errHintRes > 0) {
showFailDialog(errHintRes)
}
}
is Result.Error -> {
showFailDialog(R.string.withdraw_fail_unkown_error)
}
}
}
}
}
viewModel.withdrawPayout(initUUID, payItemId, payCashNum)
}
private fun requestCheck(recordNo: String, cashNum: Float) {
lifecycleScope.launch {
repeatOnLifecycle(Lifecycle.State.STARTED) {
viewModel.CheckResult.collect { result ->
when (result) {
is Result.Loading -> {
}
is Result.Success -> {
val checkResult = result.data?.data
var errHintRes = 0
when (checkResult?.error) {
0 -> {
when (checkResult.status) {
// 提现状态 1:提现中,2:提现成功,3:提现失败
1 -> {
}
2 -> {
showSuccessDialog(cashNum)
updateRecord(recordNo, checkResult)
}
3 -> {
errHintRes = R.string.withdraw_normal_fail
updateRecord(recordNo, checkResult)
}
}
}
1 -> {
errHintRes = R.string.withdraw_normal_fail
}
2 -> {
errHintRes = R.string.withdraw_fail_version_toolow
}
}
if (errHintRes > 0) {
showFailDialog(errHintRes)
}
}
is Result.Error -> {
showFailDialog(R.string.withdraw_fail_unkown_error)
}
}
}
}
}
viewModel.withdrawCheck(recordNo)
}
private fun showSuccessDialog(cashNum: Float) {
WithdrawSuccessDialog(this@WithDrawSubActivity, cashNum).show()
}
private fun showFailDialog(errorHintRes: Int) {
WithdrawFailDialog(this@WithDrawSubActivity, errorHintRes).show()
}
// ------------------------ new added -------------------------//
// WithdrawRecord
@Synchronized
private fun saveNewRecord(payoutReply: PayoutReply, payCashNum: Float, timeMs: Long) {
val newRecord = WithdrawRecord().apply {
id = payoutReply.id!!
recordNo = payoutReply.record_no
cashNum = payCashNum
operateMs = timeMs
state = 1
failReason = 0
}
mRecordList.add(newRecord)
SpUtil.instance().putList(SpUtil.KEY_WITHDRAW_HISTORY_LIST, mRecordList)
checkTransactionState()
}
@Synchronized
private fun updateRecord(recordNo: String, payCheck: PayoutCheck) {
var needSaveSp = false
mRecordList.forEachIndexed { index, record ->
if (record.recordNo == recordNo) {
if (record.state != payCheck.status) {
needSaveSp =true
record.state = payCheck.status
}
return@forEachIndexed
}
}
if (needSaveSp) {
SpUtil.instance().putList(SpUtil.KEY_WITHDRAW_HISTORY_LIST, mRecordList)
}
}
@Synchronized
private fun checkTransactionState() {
var unCheckCount = 0
mRecordList.forEach { record ->
if (record.state == FINAL_STATE_ONGING) {
unCheckCount++
}
}
if (unCheckCount > 0) {
mRecordList.forEachIndexed { index, record ->
if (record.state == FINAL_STATE_ONGING) {
requestCheck(record.recordNo, record.cashNum)
}
}
binding.root.postDelayed(object : Runnable {
override fun run() {
checkTransactionState()
}
}, CHECK_DURATION)
}
}
companion object {
const val INIT_ACTIVE = 1
const val FINAL_STATE_ONGING = 1
const val CHECK_DURATION = 10*1000L
const val EXTRA_TYPE = "EXTRA_TYPE"
internal fun startActivity(activity: Activity, withdrawType: Int) {
activity.startActivity(Intent(activity.applicationContext, WithDrawSubActivity::class.java))
activity.startActivity(Intent(activity.applicationContext,
WithDrawSubActivity::class.java).apply { putExtra(EXTRA_TYPE, withdrawType) })
}
}
}
data class WithdrawSubItem(
val index: Int,
val cashNum: Float,
var isSelected: Boolean = false,
)

View File

@ -0,0 +1,61 @@
package com.gamedog.vididin.features.withdraw
import android.view.LayoutInflater
import android.view.ViewGroup
import androidx.core.view.isVisible
import androidx.recyclerview.widget.DiffUtil
import androidx.recyclerview.widget.ListAdapter
import androidx.recyclerview.widget.RecyclerView
import com.ama.core.architecture.util.ResUtil
import com.vididin.real.money.game.R
import com.vididin.real.money.game.databinding.LayoutItemWithdrawSubBinding as ViewBinding
class WithdrawSubAdapter() : ListAdapter<WithdrawSubItem, WithdrawSubAdapter.ViewHolder>(DiffCallback()) {
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
val binding = ViewBinding.inflate(LayoutInflater.from(parent.context), parent, false)
return ViewHolder(binding)
}
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
holder.bind(getItem(position))
}
inner class ViewHolder(private val binding: ViewBinding) : RecyclerView.ViewHolder(binding.root) {
fun bind(item: WithdrawSubItem) {
with(binding) {
tvTitle.text = buildString {
append(ResUtil.getString(R.string.cash))
append(item.cashNum)
}
tvDay.text = buildString {
append(ResUtil.getString(R.string.day))
append(" ")
append(item.index + 1)
}
if (item.isSelected) {
root.setBackgroundResource(R.drawable.bg_withdraw_sub_selected)
root.alpha = 1F
ivLefttopChecked.isVisible = true
} else {
root.setBackgroundResource(R.drawable.bg_withdraw_sub_unselected)
root.alpha = 0.7F
ivLefttopChecked.isVisible = false
}
}
}
}
class DiffCallback : DiffUtil.ItemCallback<WithdrawSubItem>() {
override fun areItemsTheSame(oldItem: WithdrawSubItem, newItem: WithdrawSubItem): Boolean {
return oldItem.index == newItem.index
}
override fun areContentsTheSame(oldItem: WithdrawSubItem, newItem: WithdrawSubItem): Boolean {
return newItem == oldItem
}
}
}

View File

@ -0,0 +1,7 @@
<?xml version="1.0" encoding="utf-8"?>
<shape android:shape="rectangle"
xmlns:android="http://schemas.android.com/apk/res/android">
<stroke android:width="2dp" android:color="#ff009b39" />
<gradient android:type="linear" android:useLevel="true" android:startColor="#ffffffff" android:endColor="#ffe8ffef" android:angle="180" />
<corners android:topLeftRadius="10dp" android:topRightRadius="10dp" android:bottomLeftRadius="10dp" android:bottomRightRadius="10dp" />
</shape>

View File

@ -0,0 +1,8 @@
<?xml version="1.0" encoding="utf-8"?>
<shape android:shape="rectangle"
xmlns:android="http://schemas.android.com/apk/res/android">
<stroke android:width="2dp" android:color="#ff009b39" />
<solid android:color="@color/green_39" />
<corners android:topLeftRadius="10dp" android:topRightRadius="0dp"
android:bottomLeftRadius="0dp" android:bottomRightRadius="10dp" />
</shape>

View File

@ -0,0 +1,7 @@
<?xml version="1.0" encoding="utf-8"?>
<shape android:shape="rectangle"
xmlns:android="http://schemas.android.com/apk/res/android">
<stroke android:width="2dp" android:color="#ffeeeeee" />
<solid android:color="#ffffffff" />
<corners android:topLeftRadius="10dp" android:topRightRadius="10dp" android:bottomLeftRadius="10dp" android:bottomRightRadius="10dp" />
</shape>

View File

@ -112,11 +112,12 @@
<com.ama.core.architecture.widget.CustomProgressBar
android:layout_width="match_parent"
android:layout_height="12dp"
android:layout_marginHorizontal="50dp"
android:layout_marginHorizontal="20dp"
android:layout_marginTop="10dp"
/>
<androidx.recyclerview.widget.RecyclerView
android:id="@+id/recycler_view"
android:layout_width="match_parent"
android:layout_height="90dp"
android:layout_marginTop="20dp"

View File

@ -0,0 +1,49 @@
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/root"
android:layout_width="75dp"
android:layout_height="90dp"
android:background="@drawable/bg_withdraw_sub_selected">
<androidx.appcompat.widget.AppCompatImageView
android:id="@+id/iv_lefttop_checked"
android:layout_width="20dp"
android:layout_height="20dp"
android:src="@mipmap/icon_check_mark"
android:background="@drawable/bg_withdraw_sub_selected_left_top"
android:scaleType="center"
/>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:layout_gravity="center"
android:gravity="center">
<androidx.appcompat.widget.AppCompatTextView
android:id="@+id/tv_title"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textColor="@color/green_39"
android:textStyle="bold"
android:textSize="18sp"
android:text="@string/cash00"
/>
<androidx.appcompat.widget.AppCompatTextView
android:id="@+id/tv_day"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="5dp"
android:textColor="@color/gray3"
android:textSize="14sp"
android:text="@string/day"
/>
</LinearLayout>
</FrameLayout>

View File

@ -11,7 +11,7 @@ import androidx.recyclerview.widget.StaggeredGridLayoutManager
class CommonItemDecoration private constructor(
private val horizontalSpace: Int,
private val verticalSpace: Int,
private val includeEdge: Boolean
private val includeEdge: Boolean = false
) : RecyclerView.ItemDecoration() {
override fun getItemOffsets(