Browse Source

调整内购界面

zk 1 year ago
parent
commit
64aa73482d

+ 1 - 1
app/src/main/AndroidManifest.xml

@@ -57,7 +57,7 @@
             android:name=".module.cloning.VoiceCloningActivity"
             android:name=".module.cloning.VoiceCloningActivity"
             android:screenOrientation="portrait" />
             android:screenOrientation="portrait" />
         <activity
         <activity
-            android:name=".module.integral.InternalPurchaseActivity"
+            android:name=".module.integral.IntegralPurchaseActivity"
             android:screenOrientation="portrait" />
             android:screenOrientation="portrait" />
 
 
         <provider
         <provider

+ 2 - 4
app/src/main/java/com/atmob/voiceai/data/repositories/CloneRepository.java

@@ -19,10 +19,8 @@ import com.atmob.voiceai.data.api.request.VoiceCloneRequest;
 import com.atmob.voiceai.data.api.response.VoiceCloneListResponse;
 import com.atmob.voiceai.data.api.response.VoiceCloneListResponse;
 import com.atmob.voiceai.data.api.response.VoiceCloneResponse;
 import com.atmob.voiceai.data.api.response.VoiceCloneResponse;
 import com.atmob.voiceai.data.consts.ErrorCode;
 import com.atmob.voiceai.data.consts.ErrorCode;
-import com.atmob.voiceai.data.consts.EventId;
-import com.atmob.voiceai.handlers.EventHandler;
 import com.atmob.voiceai.helper.ErrorHelper;
 import com.atmob.voiceai.helper.ErrorHelper;
-import com.atmob.voiceai.module.integral.InternalPurchaseActivity;
+import com.atmob.voiceai.module.integral.IntegralPurchaseActivity;
 import com.atmob.voiceai.module.subscription.SubscriptionPageActivity;
 import com.atmob.voiceai.module.subscription.SubscriptionPageActivity;
 import com.atmob.voiceai.utils.ReflectionUtil;
 import com.atmob.voiceai.utils.ReflectionUtil;
 import com.atmob.voiceai.utils.ToastUtil;
 import com.atmob.voiceai.utils.ToastUtil;
@@ -134,7 +132,7 @@ public class CloneRepository {
                     if (serverErrorException.getCode() == ErrorCode.ERROR_NOT_SUBSCRIBED) {
                     if (serverErrorException.getCode() == ErrorCode.ERROR_NOT_SUBSCRIBED) {
                         SubscriptionPageActivity.start(ActivityUtil.getTopActivity());
                         SubscriptionPageActivity.start(ActivityUtil.getTopActivity());
                     } else if (serverErrorException.getCode() == ErrorCode.ERROR_INTEGRAL_NOT_ENOUGH) {
                     } else if (serverErrorException.getCode() == ErrorCode.ERROR_INTEGRAL_NOT_ENOUGH) {
-                        InternalPurchaseActivity.start(ActivityUtil.getTopActivity());
+                        IntegralPurchaseActivity.start(ActivityUtil.getTopActivity());
                     } else {
                     } else {
                         ToastUtil.show(serverErrorException.getMsg(), ToastUtil.LENGTH_SHORT);
                         ToastUtil.show(serverErrorException.getMsg(), ToastUtil.LENGTH_SHORT);
                     }
                     }

+ 3 - 4
app/src/main/java/com/atmob/voiceai/data/repositories/MemberRepository.java

@@ -11,7 +11,6 @@ import com.android.billingclient.api.Purchase;
 import com.atmob.app.lib.handler.RxHttpHandler;
 import com.atmob.app.lib.handler.RxHttpHandler;
 import com.atmob.common.logging.AtmobLog;
 import com.atmob.common.logging.AtmobLog;
 import com.atmob.common.runtime.ActivityUtil;
 import com.atmob.common.runtime.ActivityUtil;
-import com.atmob.common.runtime.ContextUtil;
 import com.atmob.voiceai.data.api.AtmobApi;
 import com.atmob.voiceai.data.api.AtmobApi;
 import com.atmob.voiceai.data.api.bean.MemberInfoBean;
 import com.atmob.voiceai.data.api.bean.MemberInfoBean;
 import com.atmob.voiceai.data.api.request.BaseRequest;
 import com.atmob.voiceai.data.api.request.BaseRequest;
@@ -26,7 +25,7 @@ import com.atmob.voiceai.data.api.response.UserInfoResponse;
 import com.atmob.voiceai.data.consts.ErrorCode;
 import com.atmob.voiceai.data.consts.ErrorCode;
 import com.atmob.voiceai.data.consts.EventId;
 import com.atmob.voiceai.data.consts.EventId;
 import com.atmob.voiceai.handlers.EventHandler;
 import com.atmob.voiceai.handlers.EventHandler;
-import com.atmob.voiceai.module.integral.InternalPurchaseActivity;
+import com.atmob.voiceai.module.integral.IntegralPurchaseActivity;
 import com.atmob.voiceai.module.subscription.SubscriptionPageActivity;
 import com.atmob.voiceai.module.subscription.SubscriptionPageActivity;
 import com.atmob.voiceai.sdk.billing.GPBillingClient;
 import com.atmob.voiceai.sdk.billing.GPBillingClient;
 import com.atmob.voiceai.utils.BoxingUtil;
 import com.atmob.voiceai.utils.BoxingUtil;
@@ -156,7 +155,7 @@ public class MemberRepository {
 
 
     public void goGetIntegral() {
     public void goGetIntegral() {
         if (BoxingUtil.boxing(isMember.getValue())) {
         if (BoxingUtil.boxing(isMember.getValue())) {
-            InternalPurchaseActivity.start(ActivityUtil.getTopActivity());
+            IntegralPurchaseActivity.start(ActivityUtil.getTopActivity());
         } else {
         } else {
             SubscriptionPageActivity.start(ActivityUtil.getTopActivity());
             SubscriptionPageActivity.start(ActivityUtil.getTopActivity());
         }
         }
@@ -175,7 +174,7 @@ public class MemberRepository {
             refreshUserData();
             refreshUserData();
         }
         }
         if (BoxingUtil.boxing(isMember.getValue())) {
         if (BoxingUtil.boxing(isMember.getValue())) {
-            InternalPurchaseActivity.start(ActivityUtil.getTopActivity());
+            IntegralPurchaseActivity.start(ActivityUtil.getTopActivity());
         } else {
         } else {
             SubscriptionPageActivity.start(ActivityUtil.getTopActivity());
             SubscriptionPageActivity.start(ActivityUtil.getTopActivity());
         }
         }

+ 2 - 2
app/src/main/java/com/atmob/voiceai/data/repositories/VoiceAIRepository.java

@@ -23,7 +23,7 @@ import com.atmob.voiceai.data.api.response.TextToSpeechResponse;
 import com.atmob.voiceai.data.api.response.VoiceListResponse;
 import com.atmob.voiceai.data.api.response.VoiceListResponse;
 import com.atmob.voiceai.data.api.response.VoiceTypeResponse;
 import com.atmob.voiceai.data.api.response.VoiceTypeResponse;
 import com.atmob.voiceai.data.consts.ErrorCode;
 import com.atmob.voiceai.data.consts.ErrorCode;
-import com.atmob.voiceai.module.integral.InternalPurchaseActivity;
+import com.atmob.voiceai.module.integral.IntegralPurchaseActivity;
 import com.atmob.voiceai.module.subscription.SubscriptionPageActivity;
 import com.atmob.voiceai.module.subscription.SubscriptionPageActivity;
 import com.atmob.voiceai.utils.ThreePair;
 import com.atmob.voiceai.utils.ThreePair;
 import com.atmob.voiceai.utils.VoiceFileUtil;
 import com.atmob.voiceai.utils.VoiceFileUtil;
@@ -190,7 +190,7 @@ public class VoiceAIRepository {
                                 SubscriptionPageActivity.start(ActivityUtil.getTopActivity());
                                 SubscriptionPageActivity.start(ActivityUtil.getTopActivity());
                             } else if (serverErrorException.getCode() == ErrorCode.ERROR_INTEGRAL_NOT_ENOUGH) {
                             } else if (serverErrorException.getCode() == ErrorCode.ERROR_INTEGRAL_NOT_ENOUGH) {
                                 msg = null;
                                 msg = null;
-                                InternalPurchaseActivity.start(ActivityUtil.getTopActivity());
+                                IntegralPurchaseActivity.start(ActivityUtil.getTopActivity());
                             }
                             }
                             textToSpeechState.setValue(new ThreePair<>(TextToSpeechState.ERROR, msg, null));
                             textToSpeechState.setValue(new ThreePair<>(TextToSpeechState.ERROR, msg, null));
                         } else {
                         } else {

+ 81 - 0
app/src/main/java/com/atmob/voiceai/module/integral/IntegralPurchaseActivity.java

@@ -0,0 +1,81 @@
+package com.atmob.voiceai.module.integral;
+
+import android.app.Activity;
+import android.content.Context;
+import android.content.Intent;
+import android.os.Bundle;
+
+import androidx.annotation.Nullable;
+
+import com.atmob.app.lib.base.BaseActivity;
+import com.atmob.voiceai.databinding.ActivityInternalPurchaseBinding;
+import com.atmob.voiceai.dialog.CommonLoadingDialog;
+import com.atmob.voiceai.utils.BoxingUtil;
+
+import dagger.hilt.android.AndroidEntryPoint;
+
+
+@AndroidEntryPoint
+public class IntegralPurchaseActivity extends BaseActivity<ActivityInternalPurchaseBinding> {
+
+
+    private IntegralPurchaseViewModel integralPurchaseViewModel;
+    private CommonLoadingDialog loadingDialog;
+
+    public static void start(Context context) {
+        Intent intent = new Intent(context, IntegralPurchaseActivity.class);
+        if (!(context instanceof Activity)) {
+            intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
+        }
+        context.startActivity(intent);
+    }
+
+
+    @Override
+    protected void onCreate(@Nullable Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+        initView();
+        initObserver();
+    }
+
+    private void initView() {
+
+    }
+
+    private void initObserver() {
+        integralPurchaseViewModel.getShowLoading().observe(this, data -> showLoadingDialog(BoxingUtil.boxing(data.getFirst()), data.getSecond()));
+        integralPurchaseViewModel.getFinishEvent().observe(this, o -> finish());
+    }
+
+    public void showLoadingDialog(boolean show, String msg) {
+        if (show) {
+            if (loadingDialog == null) {
+                loadingDialog = new CommonLoadingDialog(this);
+            }
+            loadingDialog.setMessage(msg);
+            loadingDialog.show();
+        } else if (loadingDialog != null) {
+            loadingDialog.dismiss();
+        }
+    }
+
+    @Override
+    protected void initViewModel() {
+        super.initViewModel();
+        integralPurchaseViewModel = getViewModelProvider().get(IntegralPurchaseViewModel.class);
+        binding.setIntegralViewModel(integralPurchaseViewModel);
+    }
+
+    @Override
+    protected boolean shouldImmersion() {
+        return true;
+    }
+
+    @Override
+    public void onBackPressed() {
+        if (!BoxingUtil.boxing(integralPurchaseViewModel.getIsShowCloseBtn().getValue())) {
+            return;
+        }
+        finish();
+    }
+}

+ 67 - 0
app/src/main/java/com/atmob/voiceai/module/integral/IntegralPurchaseViewModel.java

@@ -0,0 +1,67 @@
+package com.atmob.voiceai.module.integral;
+
+import androidx.lifecycle.LiveData;
+import androidx.lifecycle.MutableLiveData;
+
+import com.atmob.app.lib.base.BaseViewModel;
+import com.atmob.app.lib.livedata.SingleLiveEvent;
+import com.atmob.voiceai.data.consts.EventId;
+import com.atmob.voiceai.handlers.EventHandler;
+
+import java.util.concurrent.TimeUnit;
+
+import javax.inject.Inject;
+
+import atmob.rxjava.utils.RxJavaUtil;
+import dagger.hilt.android.lifecycle.HiltViewModel;
+import kotlin.Pair;
+
+
+@HiltViewModel
+public class IntegralPurchaseViewModel extends BaseViewModel {
+
+
+    private final MutableLiveData<Boolean> showQuerySubLoading = new MutableLiveData<>();
+    private final MutableLiveData<Boolean> isShowCloseBtn = new MutableLiveData<>();
+    private final SingleLiveEvent<?> finishEvent = new SingleLiveEvent<>();
+    private final SingleLiveEvent<Pair<Boolean, String>> showLoading = new SingleLiveEvent<>();
+
+
+    @Inject
+    public IntegralPurchaseViewModel() {
+        init();
+    }
+
+    public LiveData<Pair<Boolean, String>> getShowLoading() {
+        return showLoading;
+    }
+
+    public LiveData<?> getFinishEvent() {
+        return finishEvent;
+    }
+
+    public LiveData<Boolean> getShowQuerySubLoading() {
+        return showQuerySubLoading;
+    }
+
+    public LiveData<Boolean> getIsShowCloseBtn() {
+        return isShowCloseBtn;
+    }
+
+    private void init() {
+        addDisposable(RxJavaUtil.timer(3000, TimeUnit.MILLISECONDS, () -> isShowCloseBtn.setValue(true)));
+    }
+
+    public void onBackClick() {
+        finishEvent.call();
+    }
+
+    public void onRestoreClick() {
+
+    }
+
+    public void onBuyNowClick() {
+
+    }
+
+}

+ 0 - 58
app/src/main/java/com/atmob/voiceai/module/integral/InternalPurchaseActivity.java

@@ -1,58 +0,0 @@
-package com.atmob.voiceai.module.integral;
-
-import android.app.Activity;
-import android.content.Context;
-import android.content.Intent;
-import android.os.Bundle;
-
-import androidx.annotation.Nullable;
-
-import com.atmob.app.lib.base.BaseActivity;
-import com.atmob.voiceai.databinding.ActivityInternalPurchaseBinding;
-
-import dagger.hilt.android.AndroidEntryPoint;
-
-
-@AndroidEntryPoint
-public class InternalPurchaseActivity extends BaseActivity<ActivityInternalPurchaseBinding> {
-
-
-    private InternalPurchaseViewModel internalPurchaseViewModel;
-
-
-    public static void start(Context context) {
-        Intent intent = new Intent(context, InternalPurchaseActivity.class);
-        if (!(context instanceof Activity)) {
-            intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
-        }
-        context.startActivity(intent);
-    }
-
-
-    @Override
-    protected void onCreate(@Nullable Bundle savedInstanceState) {
-        super.onCreate(savedInstanceState);
-        initView();
-        initObserver();
-    }
-
-    private void initView() {
-
-    }
-
-    private void initObserver() {
-
-    }
-
-    @Override
-    protected void initViewModel() {
-        super.initViewModel();
-        internalPurchaseViewModel = getViewModelProvider().get(InternalPurchaseViewModel.class);
-        binding.setInternalPurchaseViewModel(internalPurchaseViewModel);
-    }
-
-    @Override
-    protected boolean shouldImmersion() {
-        return true;
-    }
-}

+ 0 - 16
app/src/main/java/com/atmob/voiceai/module/integral/InternalPurchaseViewModel.java

@@ -1,16 +0,0 @@
-package com.atmob.voiceai.module.integral;
-
-import com.atmob.app.lib.base.BaseViewModel;
-
-import javax.inject.Inject;
-
-import dagger.hilt.android.lifecycle.HiltViewModel;
-
-
-@HiltViewModel
-public class InternalPurchaseViewModel extends BaseViewModel {
-
-    @Inject
-    public InternalPurchaseViewModel() {
-    }
-}

+ 1 - 3
app/src/main/java/com/atmob/voiceai/module/subscription/SubscriptionPageViewModel.java

@@ -108,9 +108,7 @@ public class SubscriptionPageViewModel extends BaseViewModel {
     }
     }
 
 
     private void init() {
     private void init() {
-        addDisposable(RxJavaUtil.timer(3000, TimeUnit.MILLISECONDS, () -> {
-            isShowCloseBtn.setValue(true);
-        }));
+        addDisposable(RxJavaUtil.timer(3000, TimeUnit.MILLISECONDS, () -> isShowCloseBtn.setValue(true)));
     }
     }
 
 
     public void onBackClick() {
     public void onBackClick() {

+ 360 - 3
app/src/main/res/layout/activity_internal_purchase.xml

@@ -1,16 +1,373 @@
 <?xml version="1.0" encoding="utf-8"?>
 <?xml version="1.0" encoding="utf-8"?>
-<layout xmlns:android="http://schemas.android.com/apk/res/android">
+<layout xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:app="http://schemas.android.com/apk/res-auto"
+    xmlns:tools="http://schemas.android.com/tools">
 
 
     <data>
     <data>
 
 
         <variable
         <variable
-            name="internalPurchaseViewModel"
-            type="com.atmob.voiceai.module.integral.InternalPurchaseViewModel" />
+            name="integralViewModel"
+            type="com.atmob.voiceai.module.integral.IntegralPurchaseViewModel" />
+
+        <import type="com.atmob.common.ui.SizeUtil" />
     </data>
     </data>
 
 
     <androidx.constraintlayout.widget.ConstraintLayout
     <androidx.constraintlayout.widget.ConstraintLayout
         android:layout_width="match_parent"
         android:layout_width="match_parent"
         android:layout_height="match_parent">
         android:layout_height="match_parent">
 
 
+        <ImageView
+            android:layout_width="match_parent"
+            android:layout_height="0dp"
+            android:src="@drawable/bg_subscription_page"
+            app:layout_constraintDimensionRatio="1080:2400"
+            app:layout_constraintTop_toTopOf="parent" />
+
+
+        <androidx.core.widget.NestedScrollView
+            android:id="@+id/scroll_view"
+            android:layout_width="match_parent"
+            android:layout_height="match_parent"
+            app:layout_constrainedHeight="true"
+            app:layout_constraintBottom_toBottomOf="parent"
+            app:layout_constraintBottom_toTopOf="@id/space_sub"
+            app:layout_constraintTop_toTopOf="parent">
+
+            <androidx.constraintlayout.widget.ConstraintLayout
+                android:layout_width="match_parent"
+                android:layout_height="wrap_content">
+
+                <Space
+                    android:id="@+id/space_status_bar"
+                    android:layout_width="match_parent"
+                    android:layout_height="@{SizeUtil.getStatusBarHeight(), default=@dimen/app_status_bar_height}"
+                    app:layout_constraintTop_toTopOf="parent" />
+
+                <Space
+                    android:id="@+id/space1"
+                    android:layout_width="match_parent"
+                    android:layout_height="0dp"
+                    app:layout_constraintDimensionRatio="360:58"
+                    app:layout_constraintTop_toBottomOf="@+id/space_status_bar" />
+
+                <TextView
+                    android:id="@+id/tv_title"
+                    android:layout_width="wrap_content"
+                    android:layout_height="wrap_content"
+                    android:text="@string/sub_title"
+                    android:textColor="@color/white"
+                    android:textSize="24sp"
+                    android:textStyle="bold"
+                    app:layout_constraintHorizontal_chainStyle="packed"
+                    app:layout_constraintLeft_toLeftOf="parent"
+                    app:layout_constraintRight_toRightOf="parent"
+                    app:layout_constraintTop_toBottomOf="@+id/space1"
+                    tools:text="Marta AI Voice" />
+
+                <TextView
+                    android:id="@+id/tv_sub_desc"
+                    android:layout_width="wrap_content"
+                    android:layout_height="wrap_content"
+                    android:layout_marginTop="4dp"
+                    android:text="@string/sub_unlock_features"
+                    android:textColor="@color/white80"
+                    android:textSize="14sp"
+                    app:layout_constraintEnd_toEndOf="parent"
+                    app:layout_constraintStart_toStartOf="parent"
+                    app:layout_constraintTop_toBottomOf="@+id/tv_title" />
+
+
+                <Space
+                    android:id="@+id/space2"
+                    android:layout_width="match_parent"
+                    android:layout_height="0dp"
+                    app:layout_constraintDimensionRatio="360:31"
+                    app:layout_constraintTop_toBottomOf="@+id/tv_sub_desc" />
+
+                <ImageView
+                    android:id="@+id/iv_sub_bg"
+                    android:layout_width="match_parent"
+                    android:layout_height="0dp"
+                    android:layout_marginHorizontal="16dp"
+                    android:src="@drawable/bg_sub_rectangle"
+                    app:layout_constraintDimensionRatio="328:188"
+                    app:layout_constraintTop_toBottomOf="@+id/space2" />
+
+                <View
+                    android:id="@+id/v_sub_divider1"
+                    android:layout_width="match_parent"
+                    android:layout_height="1dp"
+                    android:layout_marginHorizontal="9dp"
+                    android:background="@drawable/bg_sub_line"
+                    app:layout_constraintBottom_toBottomOf="@id/iv_sub_bg"
+                    app:layout_constraintEnd_toEndOf="@+id/iv_sub_bg"
+                    app:layout_constraintStart_toStartOf="@+id/iv_sub_bg"
+                    app:layout_constraintTop_toTopOf="@+id/iv_sub_bg"
+                    app:layout_constraintVertical_bias="0.3457446808510638" />
+
+                <ImageView
+                    android:id="@+id/iv_sub_ai"
+                    android:layout_width="0dp"
+                    android:layout_height="0dp"
+                    android:src="@drawable/icon_sub_ai"
+                    app:layout_constraintBottom_toBottomOf="@+id/iv_sub_bg"
+                    app:layout_constraintDimensionRatio="1:1"
+                    app:layout_constraintEnd_toEndOf="@+id/iv_sub_bg"
+                    app:layout_constraintHorizontal_bias="0.0805369127516779"
+                    app:layout_constraintStart_toStartOf="@+id/iv_sub_bg"
+                    app:layout_constraintTop_toTopOf="@+id/iv_sub_bg"
+                    app:layout_constraintVertical_bias="0.1329113924050633"
+                    app:layout_constraintWidth_percent="0.0833333333333333" />
+
+                <ImageView
+                    android:layout_width="0dp"
+                    android:layout_height="0dp"
+                    android:src="@drawable/icon_sub_goods_selected"
+                    app:layout_constraintBottom_toBottomOf="@+id/iv_sub_ai"
+                    app:layout_constraintDimensionRatio="1:1"
+                    app:layout_constraintEnd_toEndOf="@+id/iv_sub_bg"
+                    app:layout_constraintHorizontal_bias="0.9342105263157895"
+                    app:layout_constraintStart_toStartOf="@+id/iv_sub_bg"
+                    app:layout_constraintTop_toTopOf="@+id/iv_sub_ai"
+                    app:layout_constraintWidth_percent="0.0666666666666667" />
+
+                <TextView
+                    android:layout_width="wrap_content"
+                    android:layout_height="wrap_content"
+                    android:layout_marginStart="17dp"
+                    android:text="@string/sub_ultra_realistic"
+                    android:textColor="@color/white"
+                    android:textSize="15sp"
+                    app:layout_constraintBottom_toBottomOf="@+id/iv_sub_ai"
+                    app:layout_constraintStart_toEndOf="@+id/iv_sub_ai"
+                    app:layout_constraintTop_toTopOf="@+id/iv_sub_ai" />
+
+                <ImageView
+                    android:id="@+id/iv_sub_multilingual"
+                    android:layout_width="0dp"
+                    android:layout_height="0dp"
+                    android:src="@drawable/icon_sub_multilingual"
+                    app:layout_constraintBottom_toBottomOf="@+id/iv_sub_bg"
+                    app:layout_constraintDimensionRatio="1:1"
+                    app:layout_constraintStart_toStartOf="@id/iv_sub_ai"
+                    app:layout_constraintTop_toTopOf="@+id/iv_sub_bg"
+                    app:layout_constraintWidth_percent="0.0833333333333333" />
+
+                <TextView
+                    android:layout_width="wrap_content"
+                    android:layout_height="wrap_content"
+                    android:layout_marginStart="17dp"
+                    android:text="@string/sub_multiple_languages"
+                    android:textColor="@color/white"
+                    android:textSize="15sp"
+                    app:layout_constraintBottom_toBottomOf="@+id/iv_sub_multilingual"
+                    app:layout_constraintStart_toEndOf="@+id/iv_sub_multilingual"
+                    app:layout_constraintTop_toTopOf="@+id/iv_sub_multilingual" />
+
+                <ImageView
+                    android:layout_width="0dp"
+                    android:layout_height="0dp"
+                    android:src="@drawable/icon_sub_goods_selected"
+                    app:layout_constraintBottom_toBottomOf="@+id/iv_sub_multilingual"
+                    app:layout_constraintDimensionRatio="1:1"
+                    app:layout_constraintEnd_toEndOf="@+id/iv_sub_bg"
+                    app:layout_constraintHorizontal_bias="0.9342105263157895"
+                    app:layout_constraintStart_toStartOf="@+id/iv_sub_multilingual"
+                    app:layout_constraintTop_toTopOf="@+id/iv_sub_multilingual"
+                    app:layout_constraintWidth_percent="0.0666666666666667" />
+
+                <ImageView
+                    android:id="@+id/iv_sub_voice_download"
+                    android:layout_width="0dp"
+                    android:layout_height="0dp"
+                    android:src="@drawable/icon_sub_voice_download"
+                    app:layout_constraintBottom_toBottomOf="@+id/iv_sub_bg"
+                    app:layout_constraintDimensionRatio="1:1"
+                    app:layout_constraintStart_toStartOf="@id/iv_sub_ai"
+                    app:layout_constraintTop_toTopOf="@+id/iv_sub_bg"
+                    app:layout_constraintVertical_bias="0.8670886075949367"
+                    app:layout_constraintWidth_percent="0.0833333333333333" />
+
+                <TextView
+                    android:layout_width="wrap_content"
+                    android:layout_height="wrap_content"
+                    android:layout_marginStart="17dp"
+                    android:text="@string/sub_download_voice"
+                    android:textColor="@color/white"
+                    android:textSize="15sp"
+                    app:layout_constraintBottom_toBottomOf="@+id/iv_sub_voice_download"
+                    app:layout_constraintStart_toEndOf="@+id/iv_sub_voice_download"
+                    app:layout_constraintTop_toTopOf="@+id/iv_sub_voice_download" />
+
+                <ImageView
+                    android:layout_width="0dp"
+                    android:layout_height="0dp"
+                    android:src="@drawable/icon_sub_goods_selected"
+                    app:layout_constraintBottom_toBottomOf="@+id/iv_sub_voice_download"
+                    app:layout_constraintDimensionRatio="1:1"
+                    app:layout_constraintEnd_toEndOf="@+id/iv_sub_bg"
+                    app:layout_constraintHorizontal_bias="0.9342105263157895"
+                    app:layout_constraintStart_toStartOf="@+id/iv_sub_voice_download"
+                    app:layout_constraintTop_toTopOf="@+id/iv_sub_voice_download"
+                    app:layout_constraintWidth_percent="0.0666666666666667" />
+
+                <View
+                    android:id="@+id/v_sub_divider2"
+                    android:layout_width="match_parent"
+                    android:layout_height="1dp"
+                    android:layout_marginHorizontal="9dp"
+                    android:background="@drawable/bg_sub_line"
+                    app:layout_constraintBottom_toBottomOf="@id/iv_sub_bg"
+                    app:layout_constraintEnd_toEndOf="@+id/iv_sub_bg"
+                    app:layout_constraintStart_toStartOf="@+id/iv_sub_bg"
+                    app:layout_constraintTop_toTopOf="@+id/iv_sub_bg"
+                    app:layout_constraintVertical_bias="0.6542553191489362" />
+
+                <Space
+                    android:id="@+id/space3"
+                    android:layout_width="match_parent"
+                    android:layout_height="0dp"
+                    app:layout_constraintDimensionRatio="360:20"
+                    app:layout_constraintTop_toBottomOf="@+id/iv_sub_bg" />
+
+
+                <ProgressBar
+                    android:id="@+id/common_loading_progress"
+                    isGone="@{!integralViewModel.showQuerySubLoading}"
+                    android:layout_width="0dp"
+                    android:layout_height="0dp"
+                    android:layout_marginTop="30dp"
+                    android:indeterminate="true"
+                    android:indeterminateTint="@color/white30"
+                    app:layout_constraintDimensionRatio="1:1"
+                    app:layout_constraintEnd_toEndOf="parent"
+                    app:layout_constraintStart_toStartOf="parent"
+                    app:layout_constraintTop_toBottomOf="@+id/space3"
+                    app:layout_constraintVertical_chainStyle="packed"
+                    app:layout_constraintWidth_percent="0.0916666666666667" />
+
+                <androidx.recyclerview.widget.RecyclerView
+                    android:id="@+id/rv_goods_list"
+                    android:layout_width="match_parent"
+                    android:layout_height="wrap_content"
+                    android:layout_marginHorizontal="16dp"
+                    android:overScrollMode="never"
+                    app:layout_constraintTop_toBottomOf="@+id/space3"
+                    tools:itemCount="3"
+                    tools:layoutManager="androidx.recyclerview.widget.LinearLayoutManager"
+                    tools:listitem="@layout/item_sub_goods_list"
+                    tools:orientation="vertical" />
+
+                <Space
+                    android:layout_width="match_parent"
+                    android:layout_height="0dp"
+                    app:layout_constraintDimensionRatio="360:19"
+                    app:layout_constraintTop_toBottomOf="@+id/rv_goods_list" />
+
+            </androidx.constraintlayout.widget.ConstraintLayout>
+
+        </androidx.core.widget.NestedScrollView>
+
+        <View
+            android:id="@+id/v_status_bar"
+            android:layout_width="match_parent"
+            android:layout_height="@{SizeUtil.getStatusBarHeight(), default=@dimen/app_status_bar_height}"
+            android:alpha="0"
+            android:background="@color/colorPrimary"
+            app:layout_constraintTop_toTopOf="parent" />
+
+        <View
+            android:id="@+id/v_menu"
+            android:layout_width="match_parent"
+            android:layout_height="0dp"
+            android:alpha="0"
+            android:background="@color/colorPrimary"
+            app:layout_constraintDimensionRatio="360:65"
+            app:layout_constraintTop_toBottomOf="@+id/v_status_bar" />
+
+        <TextView
+            android:id="@+id/tv_bar_title"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:alpha="0"
+            android:text="@string/sub_bar_title"
+            android:textColor="@color/white"
+            android:textSize="17sp"
+            android:textStyle="bold"
+            app:layout_constraintBottom_toBottomOf="@+id/v_menu"
+            app:layout_constraintEnd_toEndOf="@+id/v_menu"
+            app:layout_constraintStart_toStartOf="@+id/v_menu"
+            app:layout_constraintTop_toTopOf="@+id/v_menu" />
+
+        <ImageView
+            android:id="@+id/iv_back"
+            isGone="@{!integralViewModel.isShowCloseBtn}"
+            android:layout_width="0dp"
+            android:layout_height="0dp"
+            android:layout_marginStart="14dp"
+            android:background="@drawable/bg_ripple_common_oval_mask"
+            android:onClick="@{()-> integralViewModel.onBackClick()}"
+            android:src="@drawable/icon_subscription_back"
+            app:layout_constraintBottom_toBottomOf="@+id/v_menu"
+            app:layout_constraintDimensionRatio="1:1"
+            app:layout_constraintStart_toStartOf="parent"
+            app:layout_constraintTop_toTopOf="@+id/v_menu"
+            app:layout_constraintWidth_percent="0.1" />
+
+        <TextView
+            expandTouchSize="@{5}"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:layout_marginEnd="@dimen/app_common_page_horizontal_padding"
+            android:onClick="@{()-> integralViewModel.onRestoreClick()}"
+            android:text="@string/sub_restore"
+            android:textColor="@color/white"
+            android:textSize="14sp"
+            app:layout_constraintBottom_toBottomOf="@+id/iv_back"
+            app:layout_constraintEnd_toEndOf="parent"
+            app:layout_constraintTop_toTopOf="@+id/iv_back" />
+
+
+        <Space
+            android:id="@+id/space_sub"
+            android:layout_width="match_parent"
+            android:layout_height="0dp"
+            app:layout_constraintBottom_toBottomOf="parent"
+            app:layout_constraintDimensionRatio="360:140" />
+
+        <TextView
+            android:id="@+id/tv_sub_now"
+            android:layout_width="0dp"
+            android:layout_height="0dp"
+            android:background="@drawable/bg_voice_ai_btn"
+            android:gravity="center"
+            android:onClick="@{()-> integralViewModel.onBuyNowClick()}"
+            android:text="@string/integral_buy_now"
+            android:textColor="@color/colorPrimary"
+            android:textSize="17sp"
+            android:textStyle="bold"
+            app:layout_constraintBottom_toTopOf="@+id/tv_auto_renewable"
+            app:layout_constraintDimensionRatio="336:48"
+            app:layout_constraintEnd_toEndOf="@+id/space_sub"
+            app:layout_constraintStart_toStartOf="@+id/space_sub"
+            app:layout_constraintTop_toTopOf="@+id/space_sub"
+            app:layout_constraintVertical_chainStyle="packed"
+            app:layout_constraintWidth_percent="0.9333333333333333" />
+
+        <TextView
+            android:id="@+id/tv_auto_renewable"
+            android:layout_width="0dp"
+            android:layout_height="wrap_content"
+            android:layout_marginHorizontal="16dp"
+            android:layout_marginTop="6dp"
+            android:text="@string/integral_tips"
+            android:textColor="@color/white80"
+            android:textSize="12sp"
+            app:layout_constraintBottom_toBottomOf="@+id/space_sub"
+            app:layout_constraintEnd_toEndOf="@+id/space_sub"
+            app:layout_constraintStart_toStartOf="@+id/space_sub"
+            app:layout_constraintTop_toBottomOf="@+id/tv_sub_now" />
+
+
     </androidx.constraintlayout.widget.ConstraintLayout>
     </androidx.constraintlayout.widget.ConstraintLayout>
 </layout>
 </layout>

+ 2 - 0
app/src/main/res/values/strings.xml

@@ -127,4 +127,6 @@
     <string name="sub_multiple_languages">Multiple language support</string>
     <string name="sub_multiple_languages">Multiple language support</string>
     <string name="sub_download_voice">High quality audio downloads</string>
     <string name="sub_download_voice">High quality audio downloads</string>
     <string name="sub_tips">-Credits included in subscriptions do not carry over\n-Migration to other devices can be resumed\n-Automatic renewal</string>
     <string name="sub_tips">-Credits included in subscriptions do not carry over\n-Migration to other devices can be resumed\n-Automatic renewal</string>
+    <string name="integral_buy_now">Buy Now</string>
+    <string name="integral_tips">-Purchased top up credits do not expire,but it can only be used on current devices;\n-Prioritize the use of points earned from subscriptions\n-Purchased top up credits require an active subscription to use.</string>
 </resources>
 </resources>