You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1094 lines
23 KiB

4 weeks ago
  1. <template>
  2. <view class="login-registration-container">
  3. <!-- 自定义导航栏 -->
  4. <view
  5. class="custom-navbar"
  6. :style="{ paddingTop: safeAreaInsets?.top + 'px' }"
  7. >
  8. <view class="nav-left">
  9. <image
  10. class="icons"
  11. @click="goToBack"
  12. src="../../../static/icons/back.png"
  13. alt="返回首页"
  14. />
  15. </view>
  16. <view class="nav-right">
  17. <image
  18. class="icons"
  19. @click="goToService"
  20. src="../../../static/icons/Headset.png"
  21. alt="联系客服"
  22. />
  23. </view>
  24. </view>
  25. <!-- Logo -->
  26. <!-- <image class="logo" src="/static/logo.png" mode="aspectFit"></image> -->
  27. <!-- 欢迎语 -->
  28. <text class="welcome-text">找回密码</text>
  29. <!-- 邮箱/手机号切换 -->
  30. <view v-if="!isRecovering" class="switch-container">
  31. <text
  32. class="switch-item"
  33. :class="{ active: switchType === 'Email' }"
  34. @click="switchEmail"
  35. >邮箱</text
  36. >
  37. <text
  38. class="switch-item"
  39. :class="{ active: switchType === 'Phone' }"
  40. @click="switchPhone"
  41. >手机号</text
  42. >
  43. </view>
  44. <view v-else class="switch-container-occupy"> </view>
  45. <!-- 输入框 -->
  46. <view v-if="isRecovering" class="input-container">
  47. <view>
  48. <!-- 修改邮箱输入框容器将图标包含在内 -->
  49. <view class="input-with-icon">
  50. <image
  51. class="input-icon"
  52. src="../../../static/icons/Unlock.png"
  53. alt=""
  54. />
  55. <input
  56. class="input-field"
  57. :type="newPasswordLookFirst ? 'text' : 'password'"
  58. placeholder="输入新密码"
  59. v-model="newPasswordFirst"
  60. />
  61. <image
  62. class="input-icon-eye"
  63. @click="newPasswordLookFirst = !newPasswordLookFirst"
  64. :src="
  65. !newPasswordLookFirst
  66. ? '../../../static/icons/unlook.png'
  67. : '../../../static/icons/look.png'
  68. "
  69. alt=""
  70. />
  71. </view>
  72. <view class="input-with-icon">
  73. <image
  74. class="input-icon"
  75. src="../../../static/icons/Unlock.png"
  76. alt=""
  77. />
  78. <input
  79. class="input-field"
  80. :type="newPasswordLookSecond ? 'text' : 'password'"
  81. placeholder="再次确认"
  82. v-model="newPasswordSecond"
  83. />
  84. <image
  85. class="input-icon-eye"
  86. @click="newPasswordLookSecond = !newPasswordLookSecond"
  87. :src="
  88. !newPasswordLookSecond
  89. ? '../../../static/icons/unlook.png'
  90. : '../../../static/icons/look.png'
  91. "
  92. alt=""
  93. />
  94. </view>
  95. </view>
  96. </view>
  97. <view v-else class="input-container">
  98. <view v-if="switchType === 'Email'">
  99. <!-- 修改邮箱输入框容器将图标包含在内 -->
  100. <view class="input-with-icon">
  101. <image
  102. class="input-icon"
  103. src="../../../static/icons/Mail.png"
  104. alt=""
  105. />
  106. <input
  107. class="input-field"
  108. type="text"
  109. placeholder="请输入邮箱"
  110. v-model="email"
  111. />
  112. <view>
  113. <button
  114. class="send-code-btn-email"
  115. :disabled="isCodeBtnDisabled"
  116. :class="{ 'send-code-btn-disabled': isCodeBtnDisabled }"
  117. @click="sendCode"
  118. >
  119. <text
  120. class="send-code-text"
  121. :class="{ 'send-code-btn-disabled-text': isCodeBtnDisabled }"
  122. >{{ codeBtnText }}</text
  123. >
  124. </button>
  125. </view>
  126. </view>
  127. <view class="input-with-icon">
  128. <image
  129. class="input-icon"
  130. src="../../../static/icons/Text-recognition.png"
  131. alt=""
  132. />
  133. <input
  134. class="input-field"
  135. type="text"
  136. placeholder="请输入验证码"
  137. v-model="verifyCode"
  138. />
  139. </view>
  140. </view>
  141. <view v-if="switchType === 'Phone'" class="phone-input-container">
  142. <view class="country-code-selector" @click="showCountryPicker">
  143. <image
  144. class="country-flag-img"
  145. src="../../../static/icons/Iphone.png"
  146. mode="aspectFit"
  147. ></image>
  148. <text class="country-code">{{ selectedCountry.code }}</text>
  149. <!-- <text class="arrow-down"></text> -->
  150. </view>
  151. <input
  152. class="input-field phone-input"
  153. type="number"
  154. placeholder="输入手机号"
  155. v-model="phone"
  156. @input="onPhoneInput"
  157. />
  158. <view>
  159. <button
  160. class="send-code-btn"
  161. :disabled="isCodeBtnDisabled"
  162. :class="{ 'send-code-btn-disabled': isCodeBtnDisabled }"
  163. @click="sendCode"
  164. >
  165. <text
  166. class="send-code-text"
  167. :class="{ 'send-code-btn-disabled-text': isCodeBtnDisabled }"
  168. >{{ codeBtnText }}</text
  169. >
  170. </button>
  171. </view>
  172. </view>
  173. <view v-if="switchType === 'Phone'" class="input-with-icon">
  174. <image
  175. class="input-icon"
  176. src="../../../static/icons/Text-recognition.png"
  177. alt=""
  178. />
  179. <input
  180. class="input-field"
  181. type="text"
  182. placeholder="请输入验证码"
  183. v-model="verifyCode"
  184. />
  185. </view>
  186. </view>
  187. <!-- 用户协议 -->
  188. <view @click="changeCheckbox" class="agreement-container-one">
  189. <text
  190. class="agreement-text-one"
  191. :style="!isRecovering ? 'visibility: hidden' : 'visibility: visible'"
  192. >
  193. 密码最少8位数
  194. </text>
  195. </view>
  196. <!-- 注册按钮 -->
  197. <button class="register-btn" @click="register">
  198. {{ isRecovering ? "确认" : "下一步" }}
  199. </button>
  200. <!-- 或者 -->
  201. <text class="or-text-one" @click="goToRegistration"
  202. >如果您还没有账号点击注册
  203. <image class="to-icon" src="../../../static/icons/To.png"></image>
  204. </text>
  205. <!-- 或者 -->
  206. <text class="or-text" @click="goToLogin"
  207. >已有账号
  208. <text class="link">登录 </text>
  209. </text>
  210. <!-- 同意弹窗 -->
  211. <uniPopup ref="agreementPopup" type="dialog">
  212. <view class="popup-content">
  213. <text class="popup-title">同意并继续</text>
  214. <text class="popup-message">请阅读并同意服务协议和隐私权限</text>
  215. <button class="agree-button" @click="handleAgree">
  216. <text class="agree-text">同意</text>
  217. </button>
  218. </view>
  219. </uniPopup>
  220. <footerBar class="static-footer" :type="type"></footerBar>
  221. </view>
  222. </template>
  223. <script setup>
  224. import { ref } from "vue";
  225. // 导入完整的国家列表
  226. import countryList from "../recoverPassword/list";
  227. import footerBar from "../../../components/footerBar";
  228. import uniPopup from "../../../uni_modules/uni-popup/components/uni-popup/uni-popup.vue";
  229. import { verificationPhone, verificationEmail } from "../login/verification";
  230. import {
  231. SendEmailCodeApi,
  232. SendPhoneCodeApi,
  233. verifyCodeApi,
  234. forgetApi,
  235. } from "../../../api/start/login";
  236. const type = ref("");
  237. const email = ref("");
  238. const password = ref("");
  239. const newPasswordFirst = ref("");
  240. const newPasswordSecond = ref("");
  241. const deepChartID = ref("");
  242. const phone = ref("");
  243. const country = ref("+86");
  244. const agreed = ref(false);
  245. const switchType = ref("Phone"); // 默认是邮箱注册
  246. const { safeAreaInsets } = uni.getSystemInfoSync();
  247. const codeBtnText = ref("获取验证码");
  248. const isCodeBtnDisabled = ref(false); // 添加验证码按钮禁用状态
  249. const checkboxUrl = ref("../../../static/icons/Check-one-false.png");
  250. const verifyCode = ref("");
  251. const isRecovering = ref(false);
  252. const newPasswordLookFirst = ref(false);
  253. const newPasswordLookSecond = ref(false);
  254. const account = ref("");
  255. // 使用从list.js导入的完整国家列表数据
  256. const countries = ref(
  257. countryList.list.map((item) => ({
  258. name: item.name,
  259. code: `+${item.tel}`,
  260. flag: item.flag,
  261. short: item.short,
  262. en: item.en,
  263. }))
  264. );
  265. // 默认选中的国家(中国)
  266. const selectedCountry = ref(
  267. countries.value.find((country) => country.short === "CN") ||
  268. countries.value[0]
  269. );
  270. // 显示国家选择器
  271. function showCountryPicker() {
  272. uni.showActionSheet({
  273. itemList: countries.value.map(
  274. (country) => `${country.name} ${country.code}`
  275. ),
  276. success: function (res) {
  277. selectedCountry.value = countries.value[res.tapIndex];
  278. country.value = selectedCountry.value.code;
  279. },
  280. });
  281. }
  282. function goToBack() {
  283. // 返回上一页
  284. uni.navigateBack(-1);
  285. }
  286. function goToService() {
  287. // 返回上一页
  288. uni.navigateTo({
  289. url: "/pages/customerServicePlatform/csPlatformIndex",
  290. });
  291. }
  292. function switchEmail() {
  293. // 切换到邮箱注册
  294. switchType.value = "Email";
  295. verifyCode.value = "";
  296. }
  297. function switchPhone() {
  298. // 切换到手机注册
  299. switchType.value = "Phone";
  300. verifyCode.value = "";
  301. }
  302. async function register() {
  303. if (isRecovering.value) {
  304. if (!newPasswordFirst.value || !newPasswordSecond.value) {
  305. uni.showToast({
  306. title: "密码不能为空",
  307. icon: "none",
  308. });
  309. return;
  310. }
  311. if (newPasswordFirst.value !== newPasswordSecond.value) {
  312. uni.showToast({
  313. title: "前后密码不一致",
  314. icon: "none",
  315. });
  316. return;
  317. }
  318. const account = changeAccount();
  319. const res = await forgetApi({
  320. account: account,
  321. password: newPasswordSecond.value,
  322. });
  323. console.log("res", res);
  324. if (res.code !== 200) {
  325. uni.showToast({
  326. title: res.message,
  327. icon: "none",
  328. });
  329. return;
  330. }
  331. uni.showToast({
  332. title: res.message,
  333. icon: "none",
  334. });
  335. uni.navigateTo({
  336. url: "/pages/start/login/login",
  337. });
  338. // 密码逻辑
  339. return;
  340. }
  341. if (switchType.value === "Phone") {
  342. // 登录逻辑
  343. if (!phone.value) {
  344. uni.showToast({
  345. title: "请输入手机号码",
  346. icon: "none",
  347. });
  348. return;
  349. }
  350. console.log("123");
  351. const phoneAll = `${country.value}${phone.value}`;
  352. console.log("完整手机号" + phoneAll);
  353. if (!validatePhoneNumber(country.value, phone.value)) {
  354. return;
  355. }
  356. if (!verifyCode.value) {
  357. uni.showToast({
  358. title: "请输入验证码",
  359. icon: "none",
  360. });
  361. return;
  362. }
  363. }
  364. if (switchType.value === "Email") {
  365. // 登录逻辑
  366. if (!email.value) {
  367. uni.showToast({
  368. title: "请输入邮箱地址",
  369. icon: "none",
  370. });
  371. return;
  372. }
  373. const bool = verificationEmail(email.value);
  374. console.log("验证是否成功", bool);
  375. // 检查格式是否正确
  376. if (!bool) {
  377. uni.showToast({
  378. title: "邮箱格式不正确",
  379. icon: "none",
  380. });
  381. return;
  382. }
  383. if (!verifyCode.value) {
  384. uni.showToast({
  385. title: "请输入验证码",
  386. icon: "none",
  387. });
  388. return;
  389. }
  390. // 发送登录请求
  391. console.log("登录:", email.value);
  392. }
  393. const account = changeAccount();
  394. const loginType = changeLoginType();
  395. const res = await verifyCodeApi({
  396. loginType: loginType, //登录方式EMAIL,PHONE
  397. phoneCountry: country.value, //手机号所属地区
  398. account: account, //登陆账号 手机号/邮箱
  399. verifyCode: verifyCode.value,
  400. });
  401. if (res.code !== 200) {
  402. uni.showToast({
  403. title: res.message,
  404. icon: "none",
  405. });
  406. return;
  407. }
  408. isRecovering.value = !isRecovering.value;
  409. }
  410. // 请求账户
  411. function changeAccount() {
  412. if (switchType.value === "User") {
  413. account.value = deepChartID.value;
  414. }
  415. if (switchType.value === "Phone") {
  416. account.value = phone.value;
  417. }
  418. if (switchType.value === "Email") {
  419. account.value = email.value;
  420. }
  421. return account.value;
  422. }
  423. // 改变请求时的type
  424. function changeLoginType() {
  425. if (switchType.value === "User") {
  426. return "DCCODE";
  427. }
  428. if (switchType.value === "Phone") {
  429. return "PHONE";
  430. }
  431. if (switchType.value === "Email") {
  432. return "EMAIL";
  433. }
  434. }
  435. function goToLogin() {
  436. // 跳转到登录页
  437. uni.navigateTo({
  438. url: "/pages/start/login/login",
  439. });
  440. }
  441. function goToRegistration() {
  442. // 跳转到登录页
  443. uni.navigateTo({
  444. url: "/pages/start/Registration/Registration",
  445. });
  446. }
  447. function onPhoneInput(e) {
  448. // 确保只允许输入数字
  449. const value = e.detail.value;
  450. // 使用 isNaN 检查是否为有效数字
  451. if (isNaN(value)) {
  452. phone.value = "";
  453. } else {
  454. phone.value = value;
  455. }
  456. }
  457. // 注册码码验证
  458. function VerCodeVerfifcation() {
  459. if (switchType.value === "Phone") {
  460. if (!phone.value) {
  461. uni.showToast({
  462. title: "请输入手机号",
  463. icon: "none",
  464. });
  465. return false;
  466. }
  467. const bool = verificationPhone(country.value, phone.value);
  468. console.log("验证是否成功", bool);
  469. // 检查格式是否正确
  470. if (!bool) {
  471. uni.showToast({
  472. title: "手机号格式不正确",
  473. icon: "none",
  474. });
  475. return false;
  476. }
  477. }
  478. if (switchType.value === "Email") {
  479. if (!email.value) {
  480. uni.showToast({
  481. title: "请输入邮箱地址",
  482. icon: "none",
  483. });
  484. return false;
  485. }
  486. const bool = verificationEmail(email.value);
  487. console.log("验证是否成功", bool);
  488. // 检查格式是否正确
  489. if (!bool) {
  490. uni.showToast({
  491. title: "邮箱格式不正确",
  492. icon: "none",
  493. });
  494. return false;
  495. }
  496. }
  497. return true;
  498. }
  499. // 发送验证码
  500. function sendCode() {
  501. if (!VerCodeVerfifcation()) {
  502. return;
  503. }
  504. // 如果按钮已禁用,则不执行后续逻辑
  505. if (isCodeBtnDisabled.value) return;
  506. console.log("发送验证码");
  507. // 发送验证码
  508. if (switchType.value === "Email") {
  509. const res = SendEmailCodeApi({
  510. email: email.value,
  511. });
  512. if (!res) {
  513. uni.showToast({
  514. title: "发送失败",
  515. icon: "none",
  516. });
  517. }
  518. }
  519. if (switchType.value === "Phone") {
  520. const res = SendPhoneCodeApi({
  521. phoneCountry: country.value, //手机号地区
  522. phone: phone.value,
  523. });
  524. if (!res) {
  525. uni.showToast({
  526. title: "发送失败",
  527. icon: "none",
  528. });
  529. }
  530. }
  531. // 设置按钮为禁用状态
  532. isCodeBtnDisabled.value = true;
  533. codeBtnText.value = "重新发送";
  534. let time = 6;
  535. const timer = setInterval(() => {
  536. time--;
  537. codeBtnText.value = "重新发送 " + time + "s";
  538. if (time <= 0) {
  539. clearInterval(timer);
  540. codeBtnText.value = "重新发送";
  541. // 倒计时结束后启用按钮
  542. isCodeBtnDisabled.value = false;
  543. }
  544. }, 1000);
  545. return;
  546. }
  547. function openAgreement() {
  548. // 打开用户协议
  549. console.log("打开用户协议");
  550. uni.navigateTo({
  551. url: "/pages/start/agreement/agreement",
  552. });
  553. }
  554. function openPrivacy() {
  555. // 打开隐私政策
  556. console.log("打开隐私政策");
  557. uni.navigateTo({
  558. url: "/pages/start/privacy/privacy",
  559. });
  560. }
  561. function changeCheckbox() {
  562. agreed.value = !agreed.value;
  563. checkboxUrl.value = agreed.value
  564. ? "../../../static/icons/Check-one-true.png"
  565. : "../../../static/icons/Check-one-false.png";
  566. }
  567. // 验证手机号是否正确
  568. function validatePhoneNumber(countryCode, phoneNumber) {
  569. // 检查是否为空
  570. if (!phoneNumber || phoneNumber.trim() === "") {
  571. uni.showToast({
  572. title: "手机号不能为空",
  573. icon: "none",
  574. });
  575. return false;
  576. }
  577. const bool = verificationPhone(countryCode, phoneNumber);
  578. console.log("验证是否成功", bool);
  579. // 检查格式是否正确
  580. if (!bool) {
  581. uni.showToast({
  582. title: "手机号格式不正确",
  583. icon: "none",
  584. });
  585. return false;
  586. }
  587. // 去掉+号后检查长度(手机号通常在7到15位之间)
  588. const cleanNumber = phoneNumber.replace(/^\+/, "");
  589. if (cleanNumber.length < 7 || cleanNumber.length > 15) {
  590. uni.showToast({
  591. title: "手机号长度不正确",
  592. icon: "none",
  593. });
  594. return false;
  595. }
  596. return true;
  597. }
  598. // 添加弹窗引用
  599. const agreementPopup = ref(null);
  600. // 处理同意按钮点击
  601. function handleAgree() {
  602. // 关闭弹窗
  603. agreementPopup.value.close();
  604. // 设置为已同意
  605. agreed.value = true;
  606. checkboxUrl.value = "../../../static/icons/Check-one-true.png";
  607. // 继续登录流程
  608. }
  609. </script>
  610. <style scoped>
  611. .login-registration-container {
  612. display: flex;
  613. flex-direction: column;
  614. align-items: center;
  615. justify-content: center;
  616. padding: 0 70rpx;
  617. height: 100vh;
  618. background-color: #ffffff;
  619. }
  620. /* 自定义导航栏样式 */
  621. .custom-navbar {
  622. position: absolute;
  623. top: 0;
  624. left: 0;
  625. /* z-index: 999; */
  626. width: 90%;
  627. height: 80rpx;
  628. display: flex;
  629. justify-content: space-between;
  630. align-items: center;
  631. padding: 10rpx 40rpx;
  632. margin-bottom: 20rpx;
  633. }
  634. .nav-left,
  635. .nav-right {
  636. flex: 1;
  637. }
  638. .nav-right {
  639. display: flex;
  640. justify-content: flex-end;
  641. }
  642. .nav-left {
  643. display: flex;
  644. justify-content: flex-start;
  645. }
  646. .icons {
  647. margin: 20rpx;
  648. width: 40rpx;
  649. height: 40rpx;
  650. /* margin-right: 10rpx; */
  651. }
  652. .back-btn,
  653. .headphone-btn {
  654. font-size: 36rpx;
  655. font-weight: bold;
  656. color: #333333;
  657. padding: 10rpx;
  658. }
  659. .logo {
  660. width: 120rpx;
  661. height: 120rpx;
  662. margin-bottom: 60rpx;
  663. border-radius: 20%;
  664. }
  665. .welcome-text {
  666. font-size: 48rpx;
  667. font-weight: bold;
  668. color: #333333;
  669. margin-bottom: 60rpx;
  670. /* text-align: left; */
  671. /* align-self: flex-start; */
  672. }
  673. .switch-container {
  674. display: flex;
  675. margin-bottom: 40rpx;
  676. align-self: flex-start;
  677. }
  678. .switch-item {
  679. font-size: 28rpx;
  680. color: #999999;
  681. padding: 10rpx 20rpx;
  682. position: relative;
  683. }
  684. .switch-item::after {
  685. content: "";
  686. position: absolute;
  687. bottom: 0;
  688. left: 50%;
  689. transform: translateX(-50%);
  690. width: 60%;
  691. /* 控制边框宽度 */
  692. height: 2rpx;
  693. background-color: transparent;
  694. }
  695. .switch-item.active {
  696. color: #333333;
  697. font-weight: 700;
  698. }
  699. .switch-item.active::after {
  700. content: "";
  701. position: absolute;
  702. top: 60rpx;
  703. bottom: 0;
  704. left: 50%;
  705. transform: translateX(-50%);
  706. width: 30%;
  707. /* 控制边框宽度 */
  708. height: 7rpx;
  709. background-color: #333333;
  710. }
  711. .input-container {
  712. width: 100%;
  713. }
  714. /* 添加图标输入框样式 */
  715. .input-with-icon {
  716. display: flex;
  717. align-items: center;
  718. width: 100%;
  719. height: 80rpx;
  720. border-bottom: 2rpx solid #e5e5e5;
  721. margin-bottom: 20rpx;
  722. }
  723. .input-icon {
  724. width: 40rpx;
  725. height: 40rpx;
  726. margin: 0 20rpx;
  727. }
  728. .input-icon-eye {
  729. width: 40rpx;
  730. height: 20rpx;
  731. margin: 0 20rpx;
  732. }
  733. .input-field {
  734. flex: 1;
  735. height: 80rpx;
  736. padding: 15rpx 0;
  737. font-size: 28rpx;
  738. color: #333333;
  739. border: none;
  740. background-color: transparent;
  741. }
  742. .phone-input-container {
  743. display: flex;
  744. align-items: center;
  745. width: 95.8%;
  746. height: 80rpx;
  747. /* border-radius: 20rpx; */
  748. /* border: 2rpx solid #e5e5e5; */
  749. /* background-color: #f5f5f5; */
  750. padding: 0 10rpx;
  751. border-bottom: 2rpx solid #e5e5e5;
  752. margin-bottom: 20rpx;
  753. }
  754. .country-code-selector {
  755. display: flex;
  756. align-items: center;
  757. padding: 0 10rpx;
  758. padding-bottom: 1rpx;
  759. height: 100%;
  760. /* border-right: 2rpx solid #e5e5e5; */
  761. /* background-color: #f5f5f5; */
  762. border-radius: 20rpx 0 0 20rpx;
  763. }
  764. .country-code {
  765. font-size: 28rpx;
  766. color: #333333;
  767. margin-right: 10rpx;
  768. }
  769. .country-flag-img {
  770. width: 40rpx;
  771. height: 40rpx;
  772. margin-right: 10rpx;
  773. }
  774. .arrow-down {
  775. font-size: 20rpx;
  776. color: #999999;
  777. }
  778. .phone-input {
  779. flex: 1;
  780. width: auto;
  781. height: 100%;
  782. border: none;
  783. background-color: transparent;
  784. padding: 0 0rpx;
  785. }
  786. .send-code-btn {
  787. width: 200rpx;
  788. height: 60rpx;
  789. display: inline-flex;
  790. padding: 0rpx 10rpx;
  791. justify-content: center;
  792. align-items: center;
  793. gap: 10px;
  794. border-radius: 4px;
  795. background: #000;
  796. }
  797. .send-code-btn-email {
  798. width: 200rpx;
  799. height: 60rpx;
  800. display: inline-flex;
  801. padding: 0rpx 10rpx;
  802. justify-content: center;
  803. align-items: center;
  804. gap: 10px;
  805. border-radius: 4px;
  806. background: #000;
  807. margin-right: 15rpx;
  808. }
  809. .send-code-btn-disabled {
  810. background: #e6e6e6;
  811. /* 禁用状态下的灰色背景 */
  812. }
  813. .send-code-btn-disabled-text {
  814. color: #999999 !important;
  815. }
  816. .send-code-text {
  817. color: #fff;
  818. font-size: 28rpx;
  819. }
  820. .agreement-container-one {
  821. display: flex;
  822. align-items: center;
  823. align-self: flex-start;
  824. margin-bottom: 80rpx;
  825. }
  826. .agreement-container {
  827. display: flex;
  828. align-items: center;
  829. margin-bottom: 40rpx;
  830. margin-top: -75.5rpx;
  831. align-self: flex-start;
  832. }
  833. .checkbox {
  834. width: 30rpx;
  835. height: 30rpx;
  836. margin-left: 20rpx;
  837. /* flex: content; */
  838. }
  839. .agreement-text-one {
  840. font-size: 22rpx;
  841. color: #666666;
  842. text-align: center;
  843. margin-left: 10rpx;
  844. }
  845. .agreement-text {
  846. margin-left: 20rpx;
  847. font-size: 24rpx;
  848. color: #666666;
  849. }
  850. .link {
  851. color: #333333;
  852. font-weight: bold;
  853. text-decoration: underline;
  854. }
  855. .register-btn {
  856. width: 100%;
  857. height: 80rpx;
  858. background-color: #000000;
  859. color: white;
  860. font-size: 32rpx;
  861. font-weight: bold;
  862. border-radius: 40rpx;
  863. margin-bottom: 40rpx;
  864. }
  865. .or-text {
  866. flex-direction: column;
  867. font-size: 24rpx;
  868. color: #999999;
  869. margin-top: 294rpx;
  870. margin-bottom: -22rpx;
  871. }
  872. .to-icon {
  873. width: 10rpx;
  874. height: 16rpx;
  875. }
  876. .or-text-one {
  877. flex-direction: column;
  878. font-size: 24rpx;
  879. color: #999999;
  880. }
  881. .third-party-login {
  882. width: 100%;
  883. margin-bottom: 60rpx;
  884. }
  885. .third-party-text {
  886. color: #ffffff;
  887. font-weight: bold;
  888. white-space: pre;
  889. }
  890. .third-party-btn {
  891. width: 100%;
  892. height: 80rpx;
  893. background-color: rgb(0, 0, 0);
  894. border: 2rpx solid #e5e5e5;
  895. border-radius: 40rpx;
  896. display: flex;
  897. align-items: center;
  898. justify-content: center;
  899. margin-bottom: 20rpx;
  900. font-size: 28rpx;
  901. color: #333333;
  902. }
  903. .google-icon,
  904. .apple-icon {
  905. width: 60rpx;
  906. height: 60rpx;
  907. margin-right: 20rpx;
  908. }
  909. .existing-account {
  910. display: flex;
  911. align-items: center;
  912. }
  913. .account-text {
  914. font-size: 24rpx;
  915. color: #666666;
  916. }
  917. .login-link {
  918. font-size: 24rpx;
  919. font-weight: bold;
  920. color: #333333;
  921. margin-left: 10rpx;
  922. text-decoration: underline;
  923. }
  924. .static-footer {
  925. position: fixed;
  926. bottom: 0;
  927. }
  928. /* 弹窗样式 */
  929. .popup-content {
  930. background-color: #ffffff;
  931. padding: 40rpx;
  932. text-align: center;
  933. border-radius: 10rpx;
  934. width: 550rpx;
  935. }
  936. .popup-title {
  937. font-size: 36rpx;
  938. font-weight: bold;
  939. color: #333;
  940. margin-bottom: 80rpx;
  941. text-align: center; /* 水平居中 */
  942. display: flex; /* 使用flex布局 */
  943. justify-content: center; /* 水平居中 */
  944. align-items: center; /* 垂直居中 */
  945. }
  946. .popup-message {
  947. font-size: 28rpx;
  948. color: #000000;
  949. margin-bottom: 80rpx;
  950. text-align: center; /* 水平居中 */
  951. display: flex; /* 使用flex布局 */
  952. justify-content: center; /* 水平居中 */
  953. align-items: center; /* 垂直居中 */
  954. }
  955. .agree-button {
  956. width: 300rpx;
  957. height: 80rpx;
  958. background-color: #000000;
  959. border-radius: 40rpx;
  960. display: flex; /* 添加flex布局 */
  961. align-items: center; /* 垂直居中 */
  962. justify-content: center; /* 水平居中 */
  963. }
  964. .agree-text {
  965. color: #ffffff;
  966. font-size: 34rpx;
  967. /* 添加垂直居中相关样式 */
  968. display: flex;
  969. align-items: center;
  970. justify-content: center;
  971. line-height: 1; /* 确保文字垂直居中 */
  972. }
  973. .switch-container-occupy {
  974. margin-top: 100rpx;
  975. }
  976. </style>