diff --git a/app/src/main/java/com/yizhuan/erban/avroom/dialog/RoomOperationDialog.java b/app/src/main/java/com/yizhuan/erban/avroom/dialog/RoomOperationDialog.java index 814d4187f..1a84928c8 100644 --- a/app/src/main/java/com/yizhuan/erban/avroom/dialog/RoomOperationDialog.java +++ b/app/src/main/java/com/yizhuan/erban/avroom/dialog/RoomOperationDialog.java @@ -576,16 +576,17 @@ public class RoomOperationDialog extends BottomSheetDialog { return; } - optAdapter.addData(new OptAction(R.drawable.icon_room_send_broadcast, - ResUtil.getString(R.string.avroom_dialog_roomoperationdialog_031), - () -> { - if (AvRoomDataManager.get().getOnMicUserCount() > 0) { - SendBroadcastDialog.Companion.newInstance().show(context); - } else { - SingleToastUtil.showToast(ResUtil.getString(R.string.avroom_dialog_roomoperationdialog_032)); - } - } - )); + //暂时隐藏 +// optAdapter.addData(new OptAction(R.drawable.icon_room_send_broadcast, +// "发布广播", +// () -> { +// if (AvRoomDataManager.get().getOnMicUserCount() > 0) { +// SendBroadcastDialog.Companion.newInstance().show(context); +// } else { +// SingleToastUtil.showToast("当前房间麦上没有用户,暂不支持发布广播"); +// } +// } +// )); } /** diff --git a/app/src/main/java/com/yizhuan/erban/avroom/firstcharge/FirstChargeDialog.kt b/app/src/main/java/com/yizhuan/erban/avroom/firstcharge/FirstChargeDialog.kt index 0bc1c1178..21b270d01 100644 --- a/app/src/main/java/com/yizhuan/erban/avroom/firstcharge/FirstChargeDialog.kt +++ b/app/src/main/java/com/yizhuan/erban/avroom/firstcharge/FirstChargeDialog.kt @@ -128,17 +128,17 @@ class FirstChargeDialog : BaseViewBindingActivity() { 1 -> { binding.rbPlanB.visibility = View.GONE binding.rbPlanC.visibility = View.GONE - binding.rbPlanA.text = "${goodsList[0].chargeMoney.toLong().div(1000)}$" + binding.rbPlanA.text = "${goodsList[0].chargeMoney.toDouble().div(100)}$" } 2 -> { binding.rbPlanC.visibility = View.GONE - binding.rbPlanA.text = "${goodsList[0].chargeMoney.toLong().div(1000)}$" - binding.rbPlanB.text = "${goodsList[1].chargeMoney.toLong().div(1000)}$" + binding.rbPlanA.text = "${goodsList[0].chargeMoney.toDouble().div(100)}$" + binding.rbPlanB.text = "${goodsList[1].chargeMoney.toDouble().div(100)}$" } 3 -> { - binding.rbPlanA.text = "${goodsList[0].chargeMoney.toLong().div(1000)}$" - binding.rbPlanB.text = "${goodsList[1].chargeMoney.toLong().div(1000)}$" - binding.rbPlanC.text = "${goodsList[2].chargeMoney.toLong().div(1000)}$" + binding.rbPlanA.text = "${goodsList[0].chargeMoney.toDouble().div(100)}$" + binding.rbPlanB.text = "${goodsList[1].chargeMoney.toDouble().div(100)}$" + binding.rbPlanC.text = "${goodsList[2].chargeMoney.toDouble().div(100)}$" } } } diff --git a/app/src/main/java/com/yizhuan/erban/avroom/game/AppConfig.java b/app/src/main/java/com/yizhuan/erban/avroom/game/AppConfig.java index c4943294c..340e487c9 100644 --- a/app/src/main/java/com/yizhuan/erban/avroom/game/AppConfig.java +++ b/app/src/main/java/com/yizhuan/erban/avroom/game/AppConfig.java @@ -8,6 +8,6 @@ public class AppConfig { protected static final String APP_ID = "1578948593831571457"; protected static final String APP_KEY = "J9lHOXvFWkAZiTfl4SK7IGt0wDnW3fWd"; - protected static boolean isTestEnv = false; + protected static boolean isTestEnv = BuildConfig.DEBUG;; } diff --git a/app/src/main/java/com/yizhuan/erban/other/dialog/PrivacyAgreementDialog.java b/app/src/main/java/com/yizhuan/erban/other/dialog/PrivacyAgreementDialog.java index 86edc57f2..d14951ed8 100644 --- a/app/src/main/java/com/yizhuan/erban/other/dialog/PrivacyAgreementDialog.java +++ b/app/src/main/java/com/yizhuan/erban/other/dialog/PrivacyAgreementDialog.java @@ -26,17 +26,9 @@ import com.yizhuan.xchat_android_core.UriProvider; import com.yizhuan.xchat_android_library.utils.ResUtil; import com.yizhuan.xchat_android_library.utils.ScreenUtils; -import java.util.concurrent.TimeUnit; - -import io.reactivex.Observable; -import io.reactivex.android.schedulers.AndroidSchedulers; -import io.reactivex.disposables.Disposable; - public class PrivacyAgreementDialog extends Dialog implements View.OnClickListener { - private final int intervalTimeCount = 2; private OnCallBack onCallBack; - private Disposable disposable; public PrivacyAgreementDialog(@NonNull Context context) { super(context); @@ -52,20 +44,10 @@ public class PrivacyAgreementDialog extends Dialog implements View.OnClickListen super.onCreate(savedInstanceState); setContentView(R.layout.dialog_privacy_agreement); TextView tvConfirm = findViewById(R.id.tv_confirm); - tvConfirm.setEnabled(false); tvConfirm.setOnClickListener(this); - disposable = Observable.intervalRange(0, intervalTimeCount + 1, 0, 1, TimeUnit.SECONDS) - .observeOn(AndroidSchedulers.mainThread()) - .subscribe(aLong -> { - long residueCount = intervalTimeCount - aLong; - if (residueCount == 0) { - tvConfirm.setEnabled(true); - tvConfirm.setText(ResUtil.getString(R.string.other_dialog_privacyagreementdialog_01)); - } else { - tvConfirm.setText(ResUtil.getString(R.string.other_dialog_privacyagreementdialog_02) + residueCount + "s)"); - } - }); findViewById(R.id.btn_cancel).setOnClickListener(this); + tvConfirm.setEnabled(true); + tvConfirm.setText("同意"); TextView tvDesc = findViewById(R.id.tv_desc); String privacyAgreementTip = getContext().getString(R.string.tip_privacy_agreement); String userAgreementTip = getContext().getString(R.string.tip_user_agreement); @@ -116,7 +98,6 @@ public class PrivacyAgreementDialog extends Dialog implements View.OnClickListen if (onCallBack != null) { onCallBack.onFinish(v.getId() == R.id.tv_confirm); } - if (disposable != null) disposable.dispose(); } public interface OnCallBack { diff --git a/app/src/main/java/com/yizhuan/erban/vip/VipBroadcastDialog.kt b/app/src/main/java/com/yizhuan/erban/vip/VipBroadcastDialog.kt index 472872fef..8e0021389 100644 --- a/app/src/main/java/com/yizhuan/erban/vip/VipBroadcastDialog.kt +++ b/app/src/main/java/com/yizhuan/erban/vip/VipBroadcastDialog.kt @@ -82,11 +82,7 @@ class VipBroadcastDialog : BaseDialog() { } } } else { - if (beanResult.code == 8710) { - (requireActivity() as BaseActivity).dialogManager.showOkDialog(beanResult.message) - } else { - beanResult.message.toast() - } + beanResult.message.toast() dismissAllowingStateLoss() } diff --git a/app/src/main/java/com/yizhuan/erban/vip/VipMainActivity.kt b/app/src/main/java/com/yizhuan/erban/vip/VipMainActivity.kt index b1366fa7a..af72f86f7 100644 --- a/app/src/main/java/com/yizhuan/erban/vip/VipMainActivity.kt +++ b/app/src/main/java/com/yizhuan/erban/vip/VipMainActivity.kt @@ -3,6 +3,7 @@ package com.yizhuan.erban.vip import android.annotation.SuppressLint import android.content.Context import android.content.Intent +import android.util.Log import android.view.View import android.widget.LinearLayout import android.widget.TextView @@ -11,6 +12,13 @@ import androidx.constraintlayout.widget.ConstraintLayout import androidx.core.view.isInvisible import androidx.core.view.isVisible import androidx.recyclerview.widget.GridLayoutManager +import com.android.billingclient.api.BillingClient +import com.android.billingclient.api.BillingResult +import com.android.billingclient.api.Purchase +import com.android.billingclient.api.SkuDetails +import com.appsflyer.AFInAppEventParameterName +import com.appsflyer.AFInAppEventType +import com.appsflyer.AppsFlyerLib import com.netease.nim.uikit.StatusBarUtil import com.netease.nim.uikit.common.util.sys.TimeUtil import com.opensource.svgaplayer.SVGADrawable @@ -18,11 +26,12 @@ import com.opensource.svgaplayer.SVGAImageView import com.opensource.svgaplayer.SVGAParser import com.opensource.svgaplayer.SVGAVideoEntity import com.yizhuan.erban.R -import com.yizhuan.erban.avroom.firstcharge.SelectPayTypeDialog import com.yizhuan.erban.base.BaseViewBindingActivity import com.yizhuan.erban.base.TitleBar import com.yizhuan.erban.common.EmptyViewHelper import com.yizhuan.erban.databinding.ActivityVipMainBinding +import com.yizhuan.erban.ui.pay.BillingManager +import com.yizhuan.erban.ui.pay.BillingManager.BillingUpdatesListener import com.yizhuan.erban.ui.setting.ModifyPwdActivity import com.yizhuan.erban.ui.utils.RVDelegate import com.yizhuan.erban.ui.webview.CommonWebViewActivity @@ -30,12 +39,16 @@ import com.yizhuan.erban.ui.widget.magicindicator.buildins.commonnavigator.Commo import com.yizhuan.xchat_android_core.UriProvider import com.yizhuan.xchat_android_core.auth.AuthModel import com.yizhuan.xchat_android_core.pay.PayModel +import com.yizhuan.xchat_android_core.pay.bean.ChargeBean +import com.yizhuan.xchat_android_core.pay.bean.PayRecordId import com.yizhuan.xchat_android_core.statistic.StatisticManager import com.yizhuan.xchat_android_core.statistic.protocol.StatisticsProtocol +import com.yizhuan.xchat_android_core.utils.net.IgnoreException import com.yizhuan.xchat_android_core.utils.toast import com.yizhuan.xchat_android_core.vip.VipAuthInfo import com.yizhuan.xchat_android_core.vip.VipInfo import com.yizhuan.xchat_android_core.vip.VipOpenEvent +import com.yizhuan.xchat_android_library.utils.SingleToastUtil import org.greenrobot.eventbus.EventBus import org.greenrobot.eventbus.Subscribe import org.greenrobot.eventbus.ThreadMode @@ -43,7 +56,7 @@ import java.net.MalformedURLException import java.net.URL class VipMainActivity : BaseViewBindingActivity(), - VipMagicIndicatorAdapter.OnItemSelectListener { + VipMagicIndicatorAdapter.OnItemSelectListener, BillingUpdatesListener { companion object { @@ -54,16 +67,30 @@ class VipMainActivity : BaseViewBindingActivity(), } private const val BIND_CODE_GOLD = 200 + private const val TAG = "ChargeActivity" } private val authAdapter = VipAuthAdapter() private lateinit var rvDelegate: RVDelegate private val vipViewModel: VipViewModel by viewModels() + private lateinit var billingManager: BillingManager + private var bean: ChargeBean ?= null @SuppressLint("SetTextI18n") override fun init() { EventBus.getDefault().register(this) initWhiteTitleBar(getString(R.string.vip_center)) + initBilling() + binding.tvOpenVip.setOnClickListener { + StatisticManager.Instance() + .onEvent( + StatisticsProtocol.EVENT_VIP_OPEN_CLICK, + getString(R.string.me_open_nobleman_click_event) + ) + bean?.let { + buyProduct(it.skuDetails) + } + } mTitleBar.addAction(object : TitleBar.ImageAction(R.drawable.ic_vip_help) { override fun performAction(view: View) { CommonWebViewActivity.start(this@VipMainActivity, UriProvider.getVipHelpUrl()) @@ -77,7 +104,12 @@ class VipMainActivity : BaseViewBindingActivity(), rvDelegate = RVDelegate.Builder() .setLayoutManager(GridLayoutManager(this, 3)) .setRecyclerView(binding.recyclerView) - .setEmptyView(EmptyViewHelper.createEmptyView(context, getString(R.string.me_no_search_results))) + .setEmptyView( + EmptyViewHelper.createEmptyView( + context, + getString(R.string.me_no_search_results) + ) + ) .setAdapter(authAdapter) .build() binding.recyclerView.isNestedScrollingEnabled = false @@ -111,7 +143,8 @@ class VipMainActivity : BaseViewBindingActivity(), it?.let { binding.llMyVipInfo.isVisible = true binding.tvOpenVip.isVisible = false - binding.tvNotOpen.text = "${getString(R.string.me_current_power_value)}${it.currScore}" + binding.tvNotOpen.text = + "${getString(R.string.me_current_power_value)}${it.currScore}" binding.tvCurrValue.text = "${getString(R.string.me_current)}${it.currScore}" binding.tvCurrLevelName.text = it.vipName binding.tvKeepValue.text = "${getString(R.string.me_grading)}${it.levelKeepScore}" @@ -155,7 +188,6 @@ class VipMainActivity : BaseViewBindingActivity(), binding.tvOpenVip.isVisible = true binding.slAuth.isVisible = true binding.tvNotOpen.text = getString(R.string.me_no_aristocracy_yet) - loadData() } } @@ -195,6 +227,10 @@ class VipMainActivity : BaseViewBindingActivity(), } + private fun initBilling() { + billingManager = BillingManager(this, this) + } + override fun initWhiteTitleBar(title: String?) { mTitleBar = findViewById(R.id.title_bar) if (mTitleBar != null) { @@ -248,30 +284,158 @@ class VipMainActivity : BaseViewBindingActivity(), vipViewModel.onItemSelect(position) } + @Subscribe(threadMode = ThreadMode.MAIN) + fun onVipOpenEvent(vipOpenEvent: VipOpenEvent) { + getString(R.string.me_opening_of_the_aristocracy_successful).toast() + vipViewModel.getVipPageInfo() + } + + override fun needSteepStateBar() = true + + override fun setStatusBar() { + super.setStatusBar() + StatusBarUtil.transparencyBar(this) + } + + /*客户端设置成功回调*/ @SuppressLint("CheckResult", "SetTextI18n") - private fun loadData() { + override fun onBillingClientSetupFinished() { + Log.i(TAG, "onBillingClientSetupFinished") PayModel.get().getChargeList(2, AuthModel.get().currentUid) .compose(bindToLifecycle()) .subscribe( { val chargeInfo = it.list.getOrNull(0) chargeInfo?.let { chargeBean -> - binding.tvOpenVip.text = "${chargeBean.getMoney()}${getString(R.string.me_immediately_become_a_Peko_nobleman)}" - binding.tvOpenVip.setOnClickListener { - StatisticManager.Instance() - .onEvent(StatisticsProtocol.EVENT_VIP_OPEN_CLICK, getString(R.string.me_open_nobleman_click_event)) - SelectPayTypeDialog.newInstance( - chargeBean.chargeProdId, - "$${chargeBean.money}", - ) - .show(context) + val productKeys: MutableList = ArrayList() + productKeys.add(chargeBean.getChargeProdId()) + billingManager.querySkuDetailsAsync( + BillingClient.SkuType.INAPP, productKeys + ) { billingResult: BillingResult, skuDetailsList: List? -> + if (billingResult.responseCode != BillingClient.BillingResponseCode.OK) { + Log.w( + TAG, + "Unsuccessful query for type: " + BillingClient.SkuType.INAPP + + ". Error code: " + billingResult.responseCode + ) + } else if (skuDetailsList != null && skuDetailsList.isNotEmpty()) { + val showChargeList: MutableList = ArrayList() + for (skuDetails in skuDetailsList) { + if (skuDetails.sku == chargeBean.getChargeProdId()) { + chargeBean.skuDetails = skuDetails + showChargeList.add(chargeBean) + break + } + } + if (showChargeList.size > 0) { + bean = showChargeList[0] + binding.tvOpenVip.text = "${ + bean?.getMoney()?.toDouble()?.div(100) + }${getString(R.string.me_immediately_become_a_Peko_nobleman)}" + } + } } + } }, { it.printStackTrace() } ) + } + /*商品更新回调*/ + @SuppressLint("CheckResult") + override fun onPurchasesUpdated(purchases: List) { + for (purchase in purchases) { + if (purchase.purchaseState == Purchase.PurchaseState.PURCHASED && + purchase.accountIdentifiers != null + ) { + PayModel.get().verifyOrder( + purchase.accountIdentifiers!!.obfuscatedAccountId, + purchase.skus[0], + purchase.packageName, + purchase.purchaseToken + ) + .compose(bindToLifecycle()) + .subscribe( + { token: String? -> + //L.i("token=" + token); + billingManager.consumeAsync(token) + var skuDetails: SkuDetails? = null + if (bean?.getChargeProdId() == purchase.skus[0]) { + skuDetails = bean?.skuDetails + } + if (skuDetails != null) { + val eventValue: MutableMap = + HashMap() + eventValue[AFInAppEventParameterName.CONTENT_TYPE] = "Gold" + eventValue[AFInAppEventParameterName.QUANTITY] = 1 + eventValue[AFInAppEventParameterName.CONTENT_ID] = purchase.orderId + eventValue[AFInAppEventParameterName.REVENUE] = + skuDetails.priceAmountMicros / 1000000f + eventValue["Price"] = skuDetails.price + eventValue[AFInAppEventParameterName.CURRENCY] = + skuDetails.priceCurrencyCode + AppsFlyerLib.getInstance().logEvent( + applicationContext, + AFInAppEventType.PURCHASE, + eventValue + ) + } + } + ) { throwable: Throwable -> + if (throwable !is IgnoreException) { + SingleToastUtil.showToast(throwable.message) + } + } + } + } + Log.i(TAG, "onPurchasesUpdated") + } + + override fun onConsumeFinished(token: String?, result: Int) { + + } + + override fun onFailedHandle(result: Int) { + + } + + /*购买商品*/ + @SuppressLint("CheckResult") + fun buyProduct(skuDetails: SkuDetails?) { + if (skuDetails != null) { + Log.d(TAG, "BuyProduct:" + skuDetails.sku) + PayModel.get().placeOrder(skuDetails.sku) + .compose(bindToLifecycle()) + .subscribe( + { recordId: PayRecordId -> + billingManager.initiatePurchaseFlow( + skuDetails, + recordId.recordId + ) + } + ) { throwable: Throwable -> + SingleToastUtil.showToast( + throwable.message + ) + } + } else { + Log.w(TAG, "skuDetails ==null") + } + } + + override fun onResume() { + super.onResume() + if (billingManager.isServiceConnected) { + billingManager.onQueryPurchases() + } + } + + override fun onDestroy() { + super.onDestroy() + EventBus.getDefault().unregister(this) + billingManager.destroy() } override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) { @@ -285,21 +449,5 @@ class VipMainActivity : BaseViewBindingActivity(), } } - @Subscribe(threadMode = ThreadMode.MAIN) - fun onVipOpenEvent(vipOpenEvent: VipOpenEvent) { - getString(R.string.me_opening_of_the_aristocracy_successful).toast() - vipViewModel.getVipPageInfo() - } - override fun onDestroy() { - super.onDestroy() - EventBus.getDefault().unregister(this) - } - - override fun needSteepStateBar() = true - - override fun setStatusBar() { - super.setStatusBar() - StatusBarUtil.transparencyBar(this) - } } \ No newline at end of file diff --git a/gradle.properties b/gradle.properties index db7c925e5..ee0dffcd9 100644 --- a/gradle.properties +++ b/gradle.properties @@ -24,5 +24,5 @@ only_arm64=false channel_file=channel.txt -version_name=1.0.1 -version_code=101 \ No newline at end of file +version_name=1.0.2 +version_code=102 \ No newline at end of file