From 73b14fc0aff8c8afa5ff52e29bbf7bcb698a882c Mon Sep 17 00:00:00 2001 From: cyh Date: Tue, 18 Feb 2025 15:27:57 +0800 Subject: [PATCH] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E6=B3=A8=E5=86=8C=E6=BA=90?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../com/yingmao/clash/act/LoginActivity.kt | 71 ++- .../com/yingmao/clash/conf/BZYConstants.kt | 3 +- .../yingmao/clash/fragment/NewAccFragment.kt | 71 +-- .../clash/listener/AsyncBodyCallback.kt | 7 + .../com/yingmao/clash/net/http/HttpApi.kt | 4 + .../java/com/yingmao/clash/vm/LoginAtyVM.kt | 27 ++ .../main/res/layout/layout_activity_login.xml | 413 +++++++++--------- 7 files changed, 342 insertions(+), 254 deletions(-) create mode 100644 app/src/main/java/com/yingmao/clash/listener/AsyncBodyCallback.kt diff --git a/app/src/main/java/com/yingmao/clash/act/LoginActivity.kt b/app/src/main/java/com/yingmao/clash/act/LoginActivity.kt index 15b5bd1..79876eb 100644 --- a/app/src/main/java/com/yingmao/clash/act/LoginActivity.kt +++ b/app/src/main/java/com/yingmao/clash/act/LoginActivity.kt @@ -2,6 +2,7 @@ package com.yingmao.clash.act import android.content.Intent import android.graphics.Color +import android.net.Uri import android.os.Bundle import android.text.Spannable import android.text.SpannableStringBuilder @@ -25,6 +26,8 @@ import com.yingmao.clash.app.MainApplication import com.yingmao.clash.base.BaseActivity import com.yingmao.clash.conf.BZYConstants import com.yingmao.clash.entity.CheckLoginRsp +import com.yingmao.clash.listener.AsyncBodyCallback +import com.yingmao.clash.listener.AsyncCallback import com.yingmao.clash.net.http.HttpReqType import com.yingmao.clash.net.http.HttpStatus import com.yingmao.clash.util.AESUtil @@ -47,6 +50,7 @@ class LoginActivity : BaseActivity(), View.OnClickListener { private lateinit var loginUserName: String private var username_encrypt = "" private var password_encrypt = "" + private var registerHost = "" companion object { private const val LOGIN_TO_REGISTER_REQUEST_CODE = 1 @@ -157,7 +161,10 @@ class LoginActivity : BaseActivity(), View.OnClickListener { if (::rxDialogShapeLoading.isInitialized && rxDialogShapeLoading.isShowing) { rxDialogShapeLoading.cancel() } - Log.e("LoginActivity", resources.getString(R.string.LoginException)+"${httpStatus.msg}") + Log.e( + "LoginActivity", + resources.getString(R.string.LoginException) + "${httpStatus.msg}" + ) // Logger.i("检查登录异常${httpStatus.msg}") RxToast.error(resources.getString(R.string.LoginException)) } @@ -248,8 +255,9 @@ class LoginActivity : BaseActivity(), View.OnClickListener { private fun initUserAgreementView(textView: TextView) { val config = resources.configuration val language = config.locale.language - if(language.equals("en")){ - val spannableStringBuilder = SpannableStringBuilder(resources.getString(R.string.AgreeAgreement)) + if (language.equals("en")) { + val spannableStringBuilder = + SpannableStringBuilder(resources.getString(R.string.AgreeAgreement)) val clickableSpan: MyClickableSpan = object : MyClickableSpan() { override fun onClick(view: View) { val backgroundColorSpan = BackgroundColorSpan(Color.parseColor("#00000000")) @@ -281,7 +289,10 @@ class LoginActivity : BaseActivity(), View.OnClickListener { ) textView.text = spannableStringBuilder val intent = Intent(this@LoginActivity, AgreementAndPrivacyActivity::class.java) - intent.putExtra(BZYConstants.EXTRA_KEY_AGREEMENT, BZYConstants.EXTRA_USER_AGREEMENT) + intent.putExtra( + BZYConstants.EXTRA_KEY_AGREEMENT, + BZYConstants.EXTRA_USER_AGREEMENT + ) startActivity(intent) } } @@ -293,8 +304,9 @@ class LoginActivity : BaseActivity(), View.OnClickListener { ) textView.text = spannableStringBuilder textView.movementMethod = LinkMovementMethod.getInstance() - }else{ - val spannableStringBuilder = SpannableStringBuilder(resources.getString(R.string.AgreeAgreement)) + } else { + val spannableStringBuilder = + SpannableStringBuilder(resources.getString(R.string.AgreeAgreement)) val clickableSpan: MyClickableSpan = object : MyClickableSpan() { override fun onClick(view: View) { val backgroundColorSpan = BackgroundColorSpan(Color.parseColor("#00000000")) @@ -326,7 +338,10 @@ class LoginActivity : BaseActivity(), View.OnClickListener { ) textView.text = spannableStringBuilder val intent = Intent(this@LoginActivity, AgreementAndPrivacyActivity::class.java) - intent.putExtra(BZYConstants.EXTRA_KEY_AGREEMENT, BZYConstants.EXTRA_USER_AGREEMENT) + intent.putExtra( + BZYConstants.EXTRA_KEY_AGREEMENT, + BZYConstants.EXTRA_USER_AGREEMENT + ) startActivity(intent) } } @@ -382,7 +397,7 @@ class LoginActivity : BaseActivity(), View.OnClickListener { .removeValueForKey(BZYConstants.MMKV_KEY_REMEMBER_PASSWORD) MMKV.defaultMMKV().encode(BZYConstants.MMKV_KEY_REMEMBER_IS_CHECKED, false) } - if(TextUtils.isEmpty(username)){ + if (TextUtils.isEmpty(username)) { return } username_encrypt = AESUtil.byteArrayToHexStr( @@ -400,8 +415,44 @@ class LoginActivity : BaseActivity(), View.OnClickListener { } R.id.tv_register -> { - val intent = Intent(applicationContext, RegisterActivity::class.java) - startActivityForResult(intent, LOGIN_TO_REGISTER_REQUEST_CODE) +// val intent = Intent(applicationContext, RegisterActivity::class.java) +// startActivityForResult(intent, LOGIN_TO_REGISTER_REQUEST_CODE) +// + if (TextUtils.isEmpty(registerHost)) { + var mmkvHost = MMKV.defaultMMKV() + .decodeString(BZYConstants.MMKV_KEY_REGISTER_HOST, "") +// com.cncat.vpn.common.log.Log.d("mmkvHost==>${mmkvHost}") + loginViewMode.getRegisterHost(object : AsyncBodyCallback { + override suspend fun suc(str: String) { +// com.cncat.vpn.common.log.Log.d("str==>${str}") + if (str != mmkvHost) { + MMKV.defaultMMKV() + .encode(BZYConstants.MMKV_KEY_REGISTER_HOST, str) + } +// mmkvHost = str + registerHost = str + startActivity(Intent(Intent.ACTION_VIEW, Uri.parse(str))) + } + + override fun err() { + + if (TextUtils.isEmpty(mmkvHost)) { + startActivity( + Intent( + Intent.ACTION_VIEW, + Uri.parse(mmkvHost) + ) + ) + } + + } + + }) + } else { + startActivity(Intent(Intent.ACTION_VIEW, Uri.parse(registerHost))) + } + + } R.id.tv_forget_pwd -> { diff --git a/app/src/main/java/com/yingmao/clash/conf/BZYConstants.kt b/app/src/main/java/com/yingmao/clash/conf/BZYConstants.kt index f7e3fc4..a9a9578 100644 --- a/app/src/main/java/com/yingmao/clash/conf/BZYConstants.kt +++ b/app/src/main/java/com/yingmao/clash/conf/BZYConstants.kt @@ -29,7 +29,8 @@ class BZYConstants { //备用地址 const val MMKV_KEY_ROUTER_HOST ="router_host" const val MMKV_KEY_Airport_Base64 ="airport_base64" - + //注册地址 + const val MMKV_KEY_REGISTER_HOST ="register_host" const val REQUEST_CODE_PAY_WEB_Stripe = 1001 const val REQUEST_CODE_PAY_WEB_BiLai = 1002 diff --git a/app/src/main/java/com/yingmao/clash/fragment/NewAccFragment.kt b/app/src/main/java/com/yingmao/clash/fragment/NewAccFragment.kt index 4461171..932956f 100644 --- a/app/src/main/java/com/yingmao/clash/fragment/NewAccFragment.kt +++ b/app/src/main/java/com/yingmao/clash/fragment/NewAccFragment.kt @@ -93,7 +93,7 @@ class NewAccFragment : BaseFragment(), CoroutineScope by CoroutineScope(Dispatch backIv: ImageView, moreTv: TextView, titleTv: TextView, - container: FrameLayout + container: FrameLayout, ) { titleBarRl.visibility = View.VISIBLE backIv.visibility = View.INVISIBLE @@ -201,7 +201,7 @@ class NewAccFragment : BaseFragment(), CoroutineScope by CoroutineScope(Dispatch // iv_proxy_mode.setImageResource(R.drawable.smart) // tv_proxy_model.text = "智能模式" // } - Log.d("clashRunning==>$clashRunning") + Log.d("clashRunning==>$clashRunning") if (clashRunning) { stateChanged(Clash_Started, false) } else { @@ -215,7 +215,7 @@ class NewAccFragment : BaseFragment(), CoroutineScope by CoroutineScope(Dispatch when (v?.id) { R.id.rl_check_node -> { if (checkExpire()) { - if(isAdded){ + if (isAdded) { RxToast.info(requireActivity().resources.getString(R.string.AccountExpired)) } return @@ -233,7 +233,7 @@ class NewAccFragment : BaseFragment(), CoroutineScope by CoroutineScope(Dispatch if (clashRunning) { val rxDialogSureCancel = RxDialogSureCancel(activity) - if(isAdded){ + if (isAdded) { rxDialogSureCancel.setContent(requireActivity().resources.getString(R.string.StopAccelerating)) } rxDialogSureCancel.setCancelListener { @@ -270,7 +270,7 @@ class NewAccFragment : BaseFragment(), CoroutineScope by CoroutineScope(Dispatch private fun startClash() { if (checkExpire()) { - if(isAdded){ + if (isAdded) { RxToast.info(resources.getString(R.string.AccountExpired)) } @@ -297,9 +297,9 @@ class NewAccFragment : BaseFragment(), CoroutineScope by CoroutineScope(Dispatch newUuid = profile.uuid.toString(); isSubed = true - }?:run { + } ?: run { //为空的情况下选择第一个 - pm.queryAll().forEach { profile-> + pm.queryAll().forEach { profile -> pm.setActive(profile) newUuid = profile.uuid.toString(); @@ -369,7 +369,7 @@ class NewAccFragment : BaseFragment(), CoroutineScope by CoroutineScope(Dispatch // currentNode // ) // setNodeNameAndImg(currentNode!!.name) - if(isAdded){ + if (isAdded) { RxToast.success(resources.getString(R.string.AccelerateSuccess)) } checkGlo() @@ -389,7 +389,7 @@ class NewAccFragment : BaseFragment(), CoroutineScope by CoroutineScope(Dispatch com.cncat.vpn.common.log.Log.d("ACTION_CLASH_REQUEST_STOP") if (::rxDialogShapeLoading.isInitialized) { if (!rxDialogShapeLoading.isShowing) { - if(isAdded){ + if (isAdded) { rxDialogShapeLoading.setMessage(resources.getString(R.string.Disconnecting)) } rxDialogShapeLoading.show() @@ -410,7 +410,6 @@ class NewAccFragment : BaseFragment(), CoroutineScope by CoroutineScope(Dispatch private fun getNodesStatus() { - } @@ -429,10 +428,9 @@ class NewAccFragment : BaseFragment(), CoroutineScope by CoroutineScope(Dispatch // ) // setNodeNameAndImg(currentNode!!.name) if (isShowToast) { - if(isAdded){ + if (isAdded) { RxToast.success(resources.getString(R.string.AccelerateSuccess)) } - } // File("${Core.deviceStorage.noBackupFilesDir}/${BaseService.CONFIG_FILE}").delete() } @@ -450,9 +448,9 @@ class NewAccFragment : BaseFragment(), CoroutineScope by CoroutineScope(Dispatch Clash_Starting -> { if (::rxDialogShapeLoading.isInitialized) { if (!rxDialogShapeLoading.isShowing) { - if(isAdded){ - rxDialogShapeLoading.setMessage(resources.getString(R.string.ConnectingInProgress)) - } + if (isAdded) { + rxDialogShapeLoading.setMessage(resources.getString(R.string.ConnectingInProgress)) + } rxDialogShapeLoading.show() } } @@ -516,24 +514,24 @@ class NewAccFragment : BaseFragment(), CoroutineScope by CoroutineScope(Dispatch // var isExpire = false var endTimeInfo = "--" if (isExpire) { - if(isAdded){ - endTimeInfo =resources.getString(R.string.AccountExpired) + if (isAdded) { + endTimeInfo = resources.getString(R.string.AccountExpired) } } else { val validPeriod = MMKV.defaultMMKV().decodeLong(BZYConstants.MMKV_KEY_VPN_VALID_PERIOD) val decodeString = MMKV.defaultMMKV().decodeString(BZYConstants.languageInfo, "") - if(decodeString.isNullOrEmpty()){ + if (decodeString.isNullOrEmpty()) { //获取当前系统语言 val config = resources.configuration val language = config.locale.language if (language.equals("en")) { val dateFormat = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) { val localEN = Locale.ENGLISH - SimpleDateFormat("MM/dd/yyyy HH:mm",localEN) + SimpleDateFormat("MM/dd/yyyy HH:mm", localEN) } else { val localEN = Locale.ENGLISH - SimpleDateFormat("MM/dd/yyyy HH:mm",localEN) + SimpleDateFormat("MM/dd/yyyy HH:mm", localEN) } endTimeInfo = dateFormat.format(validPeriod) } else { @@ -547,17 +545,17 @@ class NewAccFragment : BaseFragment(), CoroutineScope by CoroutineScope(Dispatch endTimeInfo = dateFormat.format(validPeriod) } - }else{ - if(decodeString == "English"){ + } else { + if (decodeString == "English") { val dateFormat = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) { val locale = Locale.ENGLISH - SimpleDateFormat("MM/dd/yyyy HH:mm",locale) + SimpleDateFormat("MM/dd/yyyy HH:mm", locale) } else { val locale = Locale.ENGLISH - SimpleDateFormat("MM/dd/yyyy HH:mm",locale) + SimpleDateFormat("MM/dd/yyyy HH:mm", locale) } endTimeInfo = dateFormat.format(validPeriod) - }else{ + } else { val dateFormat = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) { SimpleDateFormat("yyyy年MM月dd日 HH:mm") } else { @@ -650,32 +648,35 @@ class NewAccFragment : BaseFragment(), CoroutineScope by CoroutineScope(Dispatch } private fun goRechargeWeb() { - if (activity!=null) { + if (activity != null) { var mact = activity as NewMainActivity mact.goRechargeWeb() } } private fun goNewRecharge() { - if (activity!=null) { + if (activity != null) { var mact = activity as NewMainActivity mact.goBackupRechargeWeb() } } + private fun updateUserInfo() { - if (activity!=null) { + if (activity != null) { var mact = activity as NewMainActivity mact.goCheckLogin() } } + private fun start_u_timer() { - if (activity!=null) { + if (activity != null) { var mact = activity as NewMainActivity mact.startUploadTimer() } } + private fun stop_u_timer() { - if (activity!=null) { + if (activity != null) { var mact = activity as NewMainActivity mact.stopUploadTimer() } @@ -731,13 +732,13 @@ class NewAccFragment : BaseFragment(), CoroutineScope by CoroutineScope(Dispatch private fun setProxyModeView(isGlobal: Boolean) { if (isGlobal) { iv_proxy_mode.setImageResource(R.drawable.ic_s_global) - if(isAdded){ - tv_proxy_model.text = resources.getString(R.string.GlobalMode) - } + if (isAdded) { + tv_proxy_model.text = resources.getString(R.string.GlobalMode) + } } else { iv_proxy_mode.setImageResource(R.drawable.smart) - if(isAdded){ - tv_proxy_model.text =resources.getString(R.string.IntelligentMode) + if (isAdded) { + tv_proxy_model.text = resources.getString(R.string.IntelligentMode) } } diff --git a/app/src/main/java/com/yingmao/clash/listener/AsyncBodyCallback.kt b/app/src/main/java/com/yingmao/clash/listener/AsyncBodyCallback.kt new file mode 100644 index 0000000..c659f2b --- /dev/null +++ b/app/src/main/java/com/yingmao/clash/listener/AsyncBodyCallback.kt @@ -0,0 +1,7 @@ +package com.yingmao.clash.listener + +public interface AsyncBodyCallback { + + suspend fun suc(str:String) + fun err() +} \ No newline at end of file diff --git a/app/src/main/java/com/yingmao/clash/net/http/HttpApi.kt b/app/src/main/java/com/yingmao/clash/net/http/HttpApi.kt index 3af2fb0..c45db22 100644 --- a/app/src/main/java/com/yingmao/clash/net/http/HttpApi.kt +++ b/app/src/main/java/com/yingmao/clash/net/http/HttpApi.kt @@ -166,6 +166,10 @@ interface HttpApi { @GET("/hosttaizi.txt") suspend fun getHostTZ(): String + + + @GET("/ymregister.txt") + suspend fun getRegister(): String // @Headers( // "User-Agent: Octopus_Android" // ) diff --git a/app/src/main/java/com/yingmao/clash/vm/LoginAtyVM.kt b/app/src/main/java/com/yingmao/clash/vm/LoginAtyVM.kt index 706ef3b..67fd4a7 100644 --- a/app/src/main/java/com/yingmao/clash/vm/LoginAtyVM.kt +++ b/app/src/main/java/com/yingmao/clash/vm/LoginAtyVM.kt @@ -7,8 +7,11 @@ import com.tencent.mmkv.MMKV import com.yingmao.clash.app.MainApplication import com.yingmao.clash.base.PublicViewMode import com.cncat.vpn.common.log.Log +import com.yingmao.clash.BuildConfig import com.yingmao.clash.conf.BZYConstants import com.yingmao.clash.entity.CheckLoginRsp +import com.yingmao.clash.listener.AsyncBodyCallback +import com.yingmao.clash.listener.AsyncCallback import com.yingmao.clash.net.http.HttpApi import com.yingmao.clash.net.http.HttpReqType import com.yingmao.clash.net.http.HttpStatus @@ -89,4 +92,28 @@ class LoginAtyVM : PublicViewMode() { ) } } + + fun getRegisterHost(callback: AsyncBodyCallback) { + val rt = + NetService.instances.createFreeBaseUrl("https://yingmao.oss-cn-hongkong.aliyuncs.com/") + doAsyncNoNeedReturn(HttpReqType.GET_HOST) { + try { //TODO bug 会引起崩溃 + + + var host = rt.getRegister() + +// Log.e("data", "2:$host") +// if (!TextUtils.isEmpty(host)) { +// +// MMKV.defaultMMKV().encode(BZYConstants.MMKV_KEY_REGISTER_HOST, host) +// } +// Log.e("data", "22:$host") + + callback.suc(host) + } catch (e: Exception) { + e.printStackTrace() + callback.err() + } + } + } } \ No newline at end of file diff --git a/app/src/main/res/layout/layout_activity_login.xml b/app/src/main/res/layout/layout_activity_login.xml index 027e406..7f6e3c6 100644 --- a/app/src/main/res/layout/layout_activity_login.xml +++ b/app/src/main/res/layout/layout_activity_login.xml @@ -1,257 +1,254 @@ + xmlns:app="http://schemas.android.com/apk/res-auto" + xmlns:tools="http://schemas.android.com/tools" + android:layout_width="match_parent" + android:layout_height="match_parent" + android:background="@drawable/bg_signin"> + android:layout_width="match_parent" + android:layout_height="match_parent" + tools:context=".ui.login.LoginActivity"> + app:layout_constraintStart_toStartOf="parent" + app:layout_constraintTop_toTopOf="parent" /> + android:id="@+id/tv_welcome_back" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:layout_marginTop="@dimen/layout_login_welcome_text_top_margin" + android:text="@string/WelcomeBack" + android:textColor="@color/white" + android:textSize="@dimen/layout_login_welcome_textsize" + android:textStyle="bold" + app:layout_constraintStart_toStartOf="@+id/iv_icon" + app:layout_constraintTop_toBottomOf="@+id/iv_icon" /> + android:id="@+id/tv_username" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:layout_marginTop="@dimen/layout_login_username_title_text_top_margin" + android:text="@string/username" + android:textColor="@color/white" + android:textSize="@dimen/layout_login_username_title_textsize" + app:layout_constraintStart_toStartOf="@+id/iv_icon" + app:layout_constraintTop_toBottomOf="@+id/tv_welcome_back" /> + android:id="@+id/et_username" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_marginStart="@dimen/layout_login_et_start_margin" + android:layout_marginTop="@dimen/layout_login_et_top_margin" + android:layout_marginEnd="@dimen/layout_login_et_end_margin" + android:background="@drawable/login_et_bg_selector" + android:inputType="textPersonName" + android:maxLines="1" + android:textColor="@color/white" + android:textSize="@dimen/layout_login_et_textsize" + android:textStyle="bold" + app:layout_constraintEnd_toEndOf="parent" + app:layout_constraintStart_toStartOf="@+id/iv_icon" + app:layout_constraintTop_toBottomOf="@+id/tv_username" /> + android:id="@+id/tv_username_error" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:layout_marginTop="@dimen/layout_login_username_input_err_tip_text_top_margin" + android:textColor="@color/warring" + android:textSize="@dimen/layout_login_username_input_err_tip_textsize" + app:layout_constraintStart_toStartOf="@+id/iv_icon" + app:layout_constraintTop_toBottomOf="@+id/et_username" /> + android:id="@+id/tv_password" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:layout_marginTop="@dimen/layout_login_pwd_title_text_top_margin" + android:text="@string/password" + android:textColor="@color/white" + android:textSize="@dimen/layout_login_pwd_title_textsize" + app:layout_constraintStart_toStartOf="@+id/iv_icon" + app:layout_constraintTop_toBottomOf="@+id/tv_username_error" /> + android:id="@+id/et_password" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_marginStart="@dimen/layout_login_et_start_margin" + android:layout_marginTop="@dimen/layout_login_et_top_margin" + android:layout_marginEnd="@dimen/layout_login_et_end_margin" + android:background="@drawable/login_et_bg_selector" + android:inputType="textPassword" + android:maxLines="1" + android:textColor="@color/white" + android:textSize="@dimen/layout_login_et_textsize" + android:textStyle="bold" + app:layout_constraintEnd_toEndOf="parent" + app:layout_constraintStart_toStartOf="@+id/iv_icon" + app:layout_constraintTop_toBottomOf="@+id/tv_password" /> + android:id="@+id/cb_password_hide" + android:layout_width="@dimen/layout_login_cb_width" + android:layout_height="@dimen/layout_login_cb_height" + android:layout_marginEnd="@dimen/layout_login_cb_end_margin" + android:button="@null" + android:drawableBottom="@drawable/hide_pwd_cb_selector" + android:gravity="center" + android:paddingBottom="@dimen/layout_login_cb_bottom_padding" + app:layout_constraintBottom_toBottomOf="@+id/et_password" + app:layout_constraintEnd_toEndOf="parent" + app:layout_constraintTop_toTopOf="@+id/et_password" /> + android:id="@+id/tv_password_error" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:layout_marginTop="@dimen/layout_login_username_input_err_tip_text_top_margin" + android:textColor="@color/warring" + android:textSize="@dimen/layout_login_username_input_err_tip_textsize" + app:layout_constraintStart_toStartOf="@+id/iv_icon" + app:layout_constraintTop_toBottomOf="@+id/et_password" /> + android:id="@+id/cb_remember_password" + android:layout_width="wrap_content" + android:layout_height="20dp" + android:button="@null" + android:checked="true" + android:drawablePadding="7dp" + android:gravity="center" + android:text="@string/remember_password" + android:textColor="@color/white_70" + android:textSize="12sp" + app:drawableLeftCompat="@drawable/checked_selector" + app:layout_constraintStart_toStartOf="@+id/tv_password_error" + app:layout_constraintTop_toBottomOf="@+id/tv_password_error" /> + android:id="@+id/ll_user_agreement" + android:layout_width="wrap_content" + android:layout_height="20dp" + android:layout_marginTop="15dp" + android:gravity="center_vertical" + android:orientation="horizontal" + app:layout_constraintStart_toStartOf="@+id/cb_remember_password" + app:layout_constraintTop_toBottomOf="@+id/cb_remember_password"> + android:id="@+id/cb_user_agreement" + android:layout_width="16dp" + android:layout_height="wrap_content" + android:button="@null" + android:checked="true" + android:gravity="center" + app:drawableLeftCompat="@drawable/checked_selector" /> + android:id="@+id/tv_user_agreement" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:layout_marginStart="7dp" + android:gravity="center_vertical" + android:maxLines="2" + android:textColor="@color/white_70" + android:textSize="12sp" /> + android:id="@+id/tv_login" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_marginStart="@dimen/layout_login_tv_login_start_margin" + android:layout_marginTop="30dp" + android:layout_marginEnd="@dimen/layout_login_tv_login_end_margin" + android:background="@drawable/login_btn_bg_selector" + android:gravity="center" + android:paddingTop="@dimen/layout_login_tv_login_top_padding" + android:paddingBottom="@dimen/layout_login_tv_login_bottom_padding" + android:text="@string/login" + android:textColor="@color/black" + android:textSize="@dimen/layout_login_tv_login_textsize" + android:textStyle="bold" + app:layout_constraintTop_toBottomOf="@+id/ll_user_agreement" /> + android:id="@+id/tv_tip_default_psw" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_marginStart="30dp" + android:layout_marginTop="@dimen/dp_10" + android:layout_marginEnd="30dp" + android:ellipsize="end" + android:maxLines="2" + android:text="@string/loginTips" + android:textColor="@color/white" + android:textSize="12sp" + app:layout_constraintEnd_toEndOf="parent" + app:layout_constraintStart_toStartOf="parent" + app:layout_constraintTop_toBottomOf="@id/tv_login" /> + android:id="@+id/tv_hongmeng_tip" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:layout_marginLeft="53dp" + android:layout_marginTop="5dp" + android:maxLines="10" + android:paddingLeft="20dp" + android:paddingRight="20dp" + android:text="@string/LoginTips2" + android:textColor="@color/white" + android:textSize="12sp" + android:visibility="gone" + app:layout_constraintTop_toBottomOf="@id/tv_tip_default_psw" + tools:ignore="MissingConstraints" /> + android:id="@+id/tv_register" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:layout_marginStart="@dimen/layout_login_tv_register_start_margin" + android:layout_marginTop="35dp" + android:layout_marginBottom="@dimen/dp_10" + android:text="@string/register" + android:textColor="@drawable/loginlayout_register_text_color_selector" + android:textSize="@dimen/layout_login_tv_register_textsize" + android:visibility="visible" + app:layout_constraintBottom_toBottomOf="parent" + app:layout_constraintStart_toStartOf="parent" + app:layout_constraintTop_toBottomOf="@+id/tv_hongmeng_tip" /> + android:id="@+id/tv_forget_pwd" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:layout_marginTop="35dp" + android:layout_marginEnd="@dimen/layout_login_forget_tv_end_margin" + android:layout_marginBottom="@dimen/dp_10" + android:text="@string/forget_pwd" + android:textColor="@drawable/loginlayout_forget_text_color_selector" + android:textSize="@dimen/layout_login_forget_tv_textsize" + android:visibility="visible" + app:layout_constraintBottom_toBottomOf="parent" + app:layout_constraintEnd_toEndOf="parent" + app:layout_constraintTop_toBottomOf="@+id/tv_hongmeng_tip" /> \ No newline at end of file