|
@@ -8,13 +8,23 @@
|
|
|
|
|
|
|
|
<!-- 核心操作区 -->
|
|
<!-- 核心操作区 -->
|
|
|
<view class="action-section">
|
|
<view class="action-section">
|
|
|
- <button class="scan-button" @click="scanCode">
|
|
|
|
|
|
|
+ <!-- 状态1:扫码开门 -->
|
|
|
|
|
+ <button v-if="!authReady" class="scan-button" @click="scanCode">
|
|
|
<view class="scan-button-inner">
|
|
<view class="scan-button-inner">
|
|
|
<image class="scan-icon" src="/static/icons/scan.svg" mode="aspectFill"></image>
|
|
<image class="scan-icon" src="/static/icons/scan.svg" mode="aspectFill"></image>
|
|
|
<text class="scan-text">扫码开门</text>
|
|
<text class="scan-text">扫码开门</text>
|
|
|
</view>
|
|
</view>
|
|
|
<view class="scan-button-ripple"></view>
|
|
<view class="scan-button-ripple"></view>
|
|
|
</button>
|
|
</button>
|
|
|
|
|
+
|
|
|
|
|
+ <!-- 状态2:API 返回后,展示授权按钮 -->
|
|
|
|
|
+ <button v-else class="auth-button" @click="invokePayScore" :disabled="authBusy">
|
|
|
|
|
+ <view class="auth-button-inner">
|
|
|
|
|
+ <image class="auth-btn-icon" src="/static/icons/pay-socre-logo.png" mode="aspectFit"></image>
|
|
|
|
|
+ <text class="auth-btn-text">{{ authBusy ? '跳转中...' : '确认支付分授权' }}</text>
|
|
|
|
|
+ <text class="auth-btn-sub">点击后调起微信支付分</text>
|
|
|
|
|
+ </view>
|
|
|
|
|
+ </button>
|
|
|
</view>
|
|
</view>
|
|
|
|
|
|
|
|
<!-- 快捷功能区 -->
|
|
<!-- 快捷功能区 -->
|
|
@@ -39,6 +49,11 @@
|
|
|
</view>
|
|
</view>
|
|
|
</view>
|
|
</view>
|
|
|
|
|
|
|
|
|
|
+ <!-- 授权就绪时,取消按钮 -->
|
|
|
|
|
+ <view v-if="authReady" class="cancel-auth-wrap">
|
|
|
|
|
+ <text class="cancel-auth-link" @click="cancelAuth">取消,返回扫码</text>
|
|
|
|
|
+ </view>
|
|
|
|
|
+
|
|
|
<!-- 底部信息卡片 -->
|
|
<!-- 底部信息卡片 -->
|
|
|
<view class="info-card">
|
|
<view class="info-card">
|
|
|
<view class="info-item">
|
|
<view class="info-item">
|
|
@@ -57,21 +72,6 @@
|
|
|
</CustomerServiceButton>
|
|
</CustomerServiceButton>
|
|
|
</view>
|
|
</view>
|
|
|
</view>
|
|
</view>
|
|
|
-
|
|
|
|
|
- <!-- 支付分授权确认弹窗 -->
|
|
|
|
|
- <view v-if="showAuthPopup" class="auth-overlay" @click.stop>
|
|
|
|
|
- <view class="auth-card">
|
|
|
|
|
- <view class="auth-icon-wrap">
|
|
|
|
|
- <image class="auth-icon" src="/static/icons/pay-socre-logo.png" mode="aspectFit"></image>
|
|
|
|
|
- </view>
|
|
|
|
|
- <text class="auth-title">微信支付分授权</text>
|
|
|
|
|
- <text class="auth-desc">需授权微信支付分后开门购物,费用离店后自动结算</text>
|
|
|
|
|
- <view class="auth-actions">
|
|
|
|
|
- <button class="auth-btn cancel" @click="cancelAuth">取消</button>
|
|
|
|
|
- <button class="auth-btn confirm" @click="invokePayScore">确认授权</button>
|
|
|
|
|
- </view>
|
|
|
|
|
- </view>
|
|
|
|
|
- </view>
|
|
|
|
|
</view>
|
|
</view>
|
|
|
</template>
|
|
</template>
|
|
|
|
|
|
|
@@ -83,36 +83,30 @@ import { preCreatePayscoreOrder } from '../../api/payscore'
|
|
|
import { isLoggedIn, getToken } from '../../utils/auth'
|
|
import { isLoggedIn, getToken } from '../../utils/auth'
|
|
|
import { logger } from '../../utils/logger'
|
|
import { logger } from '../../utils/logger'
|
|
|
|
|
|
|
|
-// 授权弹窗状态
|
|
|
|
|
-const showAuthPopup = ref(false)
|
|
|
|
|
|
|
+const authReady = ref(false)
|
|
|
|
|
+const authBusy = ref(false)
|
|
|
const authDeviceId = ref('')
|
|
const authDeviceId = ref('')
|
|
|
const authPackage = ref('')
|
|
const authPackage = ref('')
|
|
|
const authMchId = ref('')
|
|
const authMchId = ref('')
|
|
|
-const authLoading = ref(false)
|
|
|
|
|
|
|
|
|
|
-// 页面显示时检查 token
|
|
|
|
|
onShow(() => {
|
|
onShow(() => {
|
|
|
const token = getToken()
|
|
const token = getToken()
|
|
|
- logger.log('[首页 onShow] token 状态:', token ? '存在' : '不存在')
|
|
|
|
|
|
|
+ logger.log('[首页 onShow] token:', token ? '存在' : '不存在')
|
|
|
})
|
|
})
|
|
|
|
|
|
|
|
const scanCode = async () => {
|
|
const scanCode = async () => {
|
|
|
- // 检查登录状态
|
|
|
|
|
if (!isLoggedIn()) {
|
|
if (!isLoggedIn()) {
|
|
|
uni.showModal({
|
|
uni.showModal({
|
|
|
title: '提示',
|
|
title: '提示',
|
|
|
content: '请先登录后再扫码开门',
|
|
content: '请先登录后再扫码开门',
|
|
|
showCancel: false,
|
|
showCancel: false,
|
|
|
success: () => {
|
|
success: () => {
|
|
|
- uni.reLaunch({
|
|
|
|
|
- url: '/pages/login/login?redirect=/pages/index/index'
|
|
|
|
|
- });
|
|
|
|
|
|
|
+ uni.reLaunch({ url: '/pages/login/login?redirect=/pages/index/index' });
|
|
|
}
|
|
}
|
|
|
});
|
|
});
|
|
|
return;
|
|
return;
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
- // 调用摄像头扫码
|
|
|
|
|
uni.scanCode({
|
|
uni.scanCode({
|
|
|
success: async function (res) {
|
|
success: async function (res) {
|
|
|
logger.log('扫码结果:', res.result);
|
|
logger.log('扫码结果:', res.result);
|
|
@@ -132,19 +126,15 @@ const scanCode = async () => {
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
- if (!deviceId) {
|
|
|
|
|
- throw new Error('无法解析设备ID');
|
|
|
|
|
- }
|
|
|
|
|
|
|
+ if (!deviceId) throw new Error('无法解析设备ID');
|
|
|
|
|
+ logger.log('提取到设备ID:', deviceId);
|
|
|
} catch (error) {
|
|
} catch (error) {
|
|
|
logger.error('解析设备ID失败:', error);
|
|
logger.error('解析设备ID失败:', error);
|
|
|
uni.showToast({ title: '二维码格式错误', icon: 'none' });
|
|
uni.showToast({ title: '二维码格式错误', icon: 'none' });
|
|
|
return;
|
|
return;
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
- logger.log('提取到设备ID:', deviceId);
|
|
|
|
|
-
|
|
|
|
|
- // 预创建支付分订单,获取 package
|
|
|
|
|
- await preparePayScoreAuth(deviceId);
|
|
|
|
|
|
|
+ await prepareAuth(deviceId);
|
|
|
},
|
|
},
|
|
|
fail: function (err) {
|
|
fail: function (err) {
|
|
|
logger.log('扫码取消:', err);
|
|
logger.log('扫码取消:', err);
|
|
@@ -152,15 +142,11 @@ const scanCode = async () => {
|
|
|
});
|
|
});
|
|
|
};
|
|
};
|
|
|
|
|
|
|
|
-/**
|
|
|
|
|
- * 预创建支付分订单,成功后在页面内展示授权按钮
|
|
|
|
|
- */
|
|
|
|
|
-const preparePayScoreAuth = async (deviceId: string) => {
|
|
|
|
|
|
|
+const prepareAuth = async (deviceId: string) => {
|
|
|
uni.showLoading({ title: '准备中...', mask: true });
|
|
uni.showLoading({ title: '准备中...', mask: true });
|
|
|
|
|
|
|
|
try {
|
|
try {
|
|
|
const result = await preCreatePayscoreOrder({ deviceId });
|
|
const result = await preCreatePayscoreOrder({ deviceId });
|
|
|
-
|
|
|
|
|
uni.hideLoading();
|
|
uni.hideLoading();
|
|
|
|
|
|
|
|
if (!result.success || !result.package) {
|
|
if (!result.success || !result.package) {
|
|
@@ -171,13 +157,12 @@ const preparePayScoreAuth = async (deviceId: string) => {
|
|
|
return;
|
|
return;
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
- logger.log('[支付分] 预创建成功, package:', result.package);
|
|
|
|
|
|
|
+ logger.log('[支付分] 预创建成功, package 已就绪');
|
|
|
|
|
|
|
|
- // 存到状态中,等用户点击"确认授权"按钮
|
|
|
|
|
authDeviceId.value = deviceId;
|
|
authDeviceId.value = deviceId;
|
|
|
authPackage.value = result.package;
|
|
authPackage.value = result.package;
|
|
|
authMchId.value = result.mchId || '';
|
|
authMchId.value = result.mchId || '';
|
|
|
- showAuthPopup.value = true;
|
|
|
|
|
|
|
+ authReady.value = true;
|
|
|
} catch (error: any) {
|
|
} catch (error: any) {
|
|
|
uni.hideLoading();
|
|
uni.hideLoading();
|
|
|
logger.error('[支付分] 预创建失败', error);
|
|
logger.error('[支付分] 预创建失败', error);
|
|
@@ -189,59 +174,74 @@ const preparePayScoreAuth = async (deviceId: string) => {
|
|
|
};
|
|
};
|
|
|
|
|
|
|
|
/**
|
|
/**
|
|
|
- * 用户点击"确认授权"按钮,直接触发 wx.openBusinessView
|
|
|
|
|
- * 关键:此调用在用户点击事件的同步调用链中,不会被微信拦截
|
|
|
|
|
|
|
+ * 用户点击按钮 → 直接触发 wx.openBusinessView
|
|
|
|
|
+ * 此函数由 button @click 同步调用,满足微信的用户手势要求
|
|
|
*/
|
|
*/
|
|
|
const invokePayScore = () => {
|
|
const invokePayScore = () => {
|
|
|
- if (authLoading.value) return;
|
|
|
|
|
- authLoading.value = true;
|
|
|
|
|
|
|
+ if (authBusy.value) return;
|
|
|
|
|
+ authBusy.value = true;
|
|
|
|
|
|
|
|
- logger.log('[支付分] 用户点击确认授权,调起 openBusinessView');
|
|
|
|
|
|
|
+ const mchId = authMchId.value;
|
|
|
|
|
+ const pkg = authPackage.value;
|
|
|
|
|
+
|
|
|
|
|
+ logger.log('[支付分] invokePayScore - mchId:', mchId, 'package 长度:', pkg?.length);
|
|
|
|
|
+
|
|
|
|
|
+ // 确保所有参数有效
|
|
|
|
|
+ if (!pkg || !mchId) {
|
|
|
|
|
+ authBusy.value = false;
|
|
|
|
|
+ uni.showModal({
|
|
|
|
|
+ title: '参数异常',
|
|
|
|
|
+ content: 'package 或 mchId 为空,请重新扫码',
|
|
|
|
|
+ showCancel: false,
|
|
|
|
|
+ });
|
|
|
|
|
+ return;
|
|
|
|
|
+ }
|
|
|
|
|
|
|
|
wx.openBusinessView({
|
|
wx.openBusinessView({
|
|
|
businessType: 'payscore',
|
|
businessType: 'payscore',
|
|
|
extraData: {
|
|
extraData: {
|
|
|
- mch_id: authMchId.value,
|
|
|
|
|
- package: authPackage.value,
|
|
|
|
|
|
|
+ mch_id: mchId,
|
|
|
|
|
+ package: pkg,
|
|
|
},
|
|
},
|
|
|
- success: async () => {
|
|
|
|
|
- authLoading.value = false;
|
|
|
|
|
- showAuthPopup.value = false;
|
|
|
|
|
- logger.log('[支付分] 用户确认成功,开始开门');
|
|
|
|
|
- await doOpenDoor(authDeviceId.value);
|
|
|
|
|
|
|
+ success: () => {
|
|
|
|
|
+ authBusy.value = false;
|
|
|
|
|
+ authReady.value = false;
|
|
|
|
|
+ logger.log('[支付分] 确认成功,开门');
|
|
|
|
|
+ doOpenDoor(authDeviceId.value);
|
|
|
},
|
|
},
|
|
|
fail: (err: any) => {
|
|
fail: (err: any) => {
|
|
|
- authLoading.value = false;
|
|
|
|
|
- logger.error('[支付分] openBusinessView 失败', JSON.stringify(err));
|
|
|
|
|
- // 用户取消不弹窗,真正的错误才提示
|
|
|
|
|
- if (err && err.errMsg && err.errMsg.indexOf('cancel') === -1) {
|
|
|
|
|
- uni.showModal({
|
|
|
|
|
- title: '授权失败',
|
|
|
|
|
- content: JSON.stringify(err),
|
|
|
|
|
- showCancel: false,
|
|
|
|
|
- });
|
|
|
|
|
|
|
+ authBusy.value = false;
|
|
|
|
|
+ const errMsg = err?.errMsg || JSON.stringify(err);
|
|
|
|
|
+ logger.error('[支付分] openBusinessView fail:', errMsg);
|
|
|
|
|
+
|
|
|
|
|
+ // 用户取消不弹窗
|
|
|
|
|
+ if (errMsg.includes('cancel')) {
|
|
|
|
|
+ return;
|
|
|
}
|
|
}
|
|
|
|
|
+
|
|
|
|
|
+ uni.showModal({
|
|
|
|
|
+ title: '调起支付分失败',
|
|
|
|
|
+ content: errMsg,
|
|
|
|
|
+ showCancel: false,
|
|
|
|
|
+ });
|
|
|
|
|
+ },
|
|
|
|
|
+ complete: () => {
|
|
|
|
|
+ logger.log('[支付分] openBusinessView complete');
|
|
|
},
|
|
},
|
|
|
});
|
|
});
|
|
|
};
|
|
};
|
|
|
|
|
|
|
|
-/**
|
|
|
|
|
- * 用户取消授权
|
|
|
|
|
- */
|
|
|
|
|
const cancelAuth = () => {
|
|
const cancelAuth = () => {
|
|
|
- showAuthPopup.value = false;
|
|
|
|
|
- logger.log('[支付分] 用户取消授权');
|
|
|
|
|
|
|
+ authReady.value = false;
|
|
|
|
|
+ authBusy.value = false;
|
|
|
|
|
+ logger.log('[支付分] 用户取消,返回扫码');
|
|
|
};
|
|
};
|
|
|
|
|
|
|
|
-/**
|
|
|
|
|
- * 执行开门操作
|
|
|
|
|
- */
|
|
|
|
|
const doOpenDoor = async (deviceId: string) => {
|
|
const doOpenDoor = async (deviceId: string) => {
|
|
|
uni.showLoading({ title: '正在开门...', mask: true });
|
|
uni.showLoading({ title: '正在开门...', mask: true });
|
|
|
|
|
|
|
|
try {
|
|
try {
|
|
|
const response = await scanDoor(deviceId);
|
|
const response = await scanDoor(deviceId);
|
|
|
-
|
|
|
|
|
uni.hideLoading();
|
|
uni.hideLoading();
|
|
|
uni.showToast({ title: '开门成功', icon: 'success' });
|
|
uni.showToast({ title: '开门成功', icon: 'success' });
|
|
|
|
|
|
|
@@ -259,21 +259,10 @@ const doOpenDoor = async (deviceId: string) => {
|
|
|
}
|
|
}
|
|
|
};
|
|
};
|
|
|
|
|
|
|
|
-const goToMy = () => {
|
|
|
|
|
- uni.navigateTo({ url: '/pages/my/my' })
|
|
|
|
|
-}
|
|
|
|
|
-
|
|
|
|
|
-const goToOrders = () => {
|
|
|
|
|
- uni.navigateTo({ url: '/pages/orders/orders' })
|
|
|
|
|
-}
|
|
|
|
|
-
|
|
|
|
|
-const goToCouponCenter = () => {
|
|
|
|
|
- uni.navigateTo({ url: '/pages/couponCenter/couponCenter' })
|
|
|
|
|
-}
|
|
|
|
|
-
|
|
|
|
|
-const onContactSuccess = () => {
|
|
|
|
|
- logger.log('[首页] 客服会话已打开')
|
|
|
|
|
-}
|
|
|
|
|
|
|
+const goToMy = () => uni.navigateTo({ url: '/pages/my/my' })
|
|
|
|
|
+const goToOrders = () => uni.navigateTo({ url: '/pages/orders/orders' })
|
|
|
|
|
+const goToCouponCenter = () => uni.navigateTo({ url: '/pages/couponCenter/couponCenter' })
|
|
|
|
|
+const onContactSuccess = () => logger.log('[首页] 客服会话已打开')
|
|
|
</script>
|
|
</script>
|
|
|
|
|
|
|
|
<style lang="scss">
|
|
<style lang="scss">
|
|
@@ -288,11 +277,9 @@ const onContactSuccess = () => {
|
|
|
box-sizing: border-box;
|
|
box-sizing: border-box;
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
-/* ========== 品牌区 ========== */
|
|
|
|
|
.brand-section {
|
|
.brand-section {
|
|
|
text-align: center;
|
|
text-align: center;
|
|
|
padding: $spacing-xxl 0 $spacing-xl;
|
|
padding: $spacing-xxl 0 $spacing-xl;
|
|
|
- animation: slideUp 0.3s ease;
|
|
|
|
|
|
|
|
|
|
.brand-title {
|
|
.brand-title {
|
|
|
font-size: 56rpx;
|
|
font-size: 56rpx;
|
|
@@ -310,7 +297,7 @@ const onContactSuccess = () => {
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
-/* ========== 核心操作区 ========== */
|
|
|
|
|
|
|
+/* ========== 操作区 ========== */
|
|
|
.action-section {
|
|
.action-section {
|
|
|
display: flex;
|
|
display: flex;
|
|
|
justify-content: center;
|
|
justify-content: center;
|
|
@@ -318,12 +305,11 @@ const onContactSuccess = () => {
|
|
|
padding: $spacing-xl 0;
|
|
padding: $spacing-xl 0;
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+/* 扫码按钮 */
|
|
|
.scan-button {
|
|
.scan-button {
|
|
|
position: relative;
|
|
position: relative;
|
|
|
width: 400rpx;
|
|
width: 400rpx;
|
|
|
height: 400rpx;
|
|
height: 400rpx;
|
|
|
- min-width: 400rpx;
|
|
|
|
|
- min-height: 400rpx;
|
|
|
|
|
border-radius: 50%;
|
|
border-radius: 50%;
|
|
|
background: transparent;
|
|
background: transparent;
|
|
|
border: none;
|
|
border: none;
|
|
@@ -331,9 +317,7 @@ const onContactSuccess = () => {
|
|
|
margin: 0;
|
|
margin: 0;
|
|
|
overflow: hidden;
|
|
overflow: hidden;
|
|
|
|
|
|
|
|
- &::after {
|
|
|
|
|
- border: none;
|
|
|
|
|
- }
|
|
|
|
|
|
|
+ &::after { border: none; }
|
|
|
|
|
|
|
|
&-inner {
|
|
&-inner {
|
|
|
width: 100%;
|
|
width: 100%;
|
|
@@ -383,6 +367,69 @@ const onContactSuccess = () => {
|
|
|
letter-spacing: 4rpx;
|
|
letter-spacing: 4rpx;
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+/* 授权按钮 */
|
|
|
|
|
+.auth-button {
|
|
|
|
|
+ width: 400rpx;
|
|
|
|
|
+ height: 400rpx;
|
|
|
|
|
+ border-radius: 50%;
|
|
|
|
|
+ background: transparent;
|
|
|
|
|
+ border: none;
|
|
|
|
|
+ padding: 0;
|
|
|
|
|
+
|
|
|
|
|
+ &::after { border: none; }
|
|
|
|
|
+
|
|
|
|
|
+ &-inner {
|
|
|
|
|
+ width: 100%;
|
|
|
|
|
+ height: 100%;
|
|
|
|
|
+ border-radius: 50%;
|
|
|
|
|
+ background: linear-gradient(135deg, #07C160 0%, #06AD56 100%);
|
|
|
|
|
+ box-shadow: 0 8rpx 32rpx rgba(7, 193, 96, 0.35);
|
|
|
|
|
+ display: flex;
|
|
|
|
|
+ flex-direction: column;
|
|
|
|
|
+ align-items: center;
|
|
|
|
|
+ justify-content: center;
|
|
|
|
|
+ transition: all 0.3s ease;
|
|
|
|
|
+
|
|
|
|
|
+ &:active {
|
|
|
|
|
+ transform: scale(0.95);
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ &[disabled] .auth-button-inner {
|
|
|
|
|
+ opacity: 0.7;
|
|
|
|
|
+ }
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+.auth-btn-icon {
|
|
|
|
|
+ width: 100rpx;
|
|
|
|
|
+ height: 100rpx;
|
|
|
|
|
+ margin-bottom: $spacing-sm;
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+.auth-btn-text {
|
|
|
|
|
+ font-size: 36rpx;
|
|
|
|
|
+ font-weight: 600;
|
|
|
|
|
+ color: #fff;
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+.auth-btn-sub {
|
|
|
|
|
+ font-size: 22rpx;
|
|
|
|
|
+ color: rgba(255, 255, 255, 0.8);
|
|
|
|
|
+ margin-top: 8rpx;
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+/* 取消授权 */
|
|
|
|
|
+.cancel-auth-wrap {
|
|
|
|
|
+ text-align: center;
|
|
|
|
|
+ margin-top: -$spacing-lg;
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+.cancel-auth-link {
|
|
|
|
|
+ font-size: 26rpx;
|
|
|
|
|
+ color: $color-text-secondary;
|
|
|
|
|
+ padding: $spacing-sm $spacing-lg;
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
/* ========== 快捷功能区 ========== */
|
|
/* ========== 快捷功能区 ========== */
|
|
|
.quick-actions {
|
|
.quick-actions {
|
|
|
display: flex;
|
|
display: flex;
|
|
@@ -481,90 +528,4 @@ const onContactSuccess = () => {
|
|
|
text-align: center;
|
|
text-align: center;
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|
|
|
-
|
|
|
|
|
-/* ========== 授权弹窗 ========== */
|
|
|
|
|
-.auth-overlay {
|
|
|
|
|
- position: fixed;
|
|
|
|
|
- top: 0;
|
|
|
|
|
- left: 0;
|
|
|
|
|
- right: 0;
|
|
|
|
|
- bottom: 0;
|
|
|
|
|
- background: rgba(0, 0, 0, 0.5);
|
|
|
|
|
- display: flex;
|
|
|
|
|
- align-items: center;
|
|
|
|
|
- justify-content: center;
|
|
|
|
|
- z-index: 999;
|
|
|
|
|
- animation: fadeIn 0.2s ease;
|
|
|
|
|
-}
|
|
|
|
|
-
|
|
|
|
|
-.auth-card {
|
|
|
|
|
- width: 600rpx;
|
|
|
|
|
- background: #fff;
|
|
|
|
|
- border-radius: 24rpx;
|
|
|
|
|
- padding: 60rpx 40rpx 40rpx;
|
|
|
|
|
- display: flex;
|
|
|
|
|
- flex-direction: column;
|
|
|
|
|
- align-items: center;
|
|
|
|
|
- animation: scaleIn 0.25s ease;
|
|
|
|
|
-}
|
|
|
|
|
-
|
|
|
|
|
-.auth-icon-wrap {
|
|
|
|
|
- width: 100rpx;
|
|
|
|
|
- height: 100rpx;
|
|
|
|
|
- margin-bottom: 24rpx;
|
|
|
|
|
-}
|
|
|
|
|
-
|
|
|
|
|
-.auth-icon {
|
|
|
|
|
- width: 100%;
|
|
|
|
|
- height: 100%;
|
|
|
|
|
-}
|
|
|
|
|
-
|
|
|
|
|
-.auth-title {
|
|
|
|
|
- font-size: 36rpx;
|
|
|
|
|
- font-weight: 600;
|
|
|
|
|
- color: $color-text-primary;
|
|
|
|
|
- margin-bottom: 16rpx;
|
|
|
|
|
-}
|
|
|
|
|
-
|
|
|
|
|
-.auth-desc {
|
|
|
|
|
- font-size: 26rpx;
|
|
|
|
|
- color: $color-text-secondary;
|
|
|
|
|
- text-align: center;
|
|
|
|
|
- line-height: 1.6;
|
|
|
|
|
- margin-bottom: 40rpx;
|
|
|
|
|
-}
|
|
|
|
|
-
|
|
|
|
|
-.auth-actions {
|
|
|
|
|
- display: flex;
|
|
|
|
|
- gap: 24rpx;
|
|
|
|
|
- width: 100%;
|
|
|
|
|
-}
|
|
|
|
|
-
|
|
|
|
|
-.auth-btn {
|
|
|
|
|
- flex: 1;
|
|
|
|
|
- height: 88rpx;
|
|
|
|
|
- line-height: 88rpx;
|
|
|
|
|
- text-align: center;
|
|
|
|
|
- border-radius: 16rpx;
|
|
|
|
|
- font-size: 30rpx;
|
|
|
|
|
- font-weight: 500;
|
|
|
|
|
- border: none;
|
|
|
|
|
- padding: 0;
|
|
|
|
|
-
|
|
|
|
|
- &::after { border: none; }
|
|
|
|
|
-
|
|
|
|
|
- &.cancel {
|
|
|
|
|
- background: #f5f5f5;
|
|
|
|
|
- color: #666;
|
|
|
|
|
- }
|
|
|
|
|
-
|
|
|
|
|
- &.confirm {
|
|
|
|
|
- background: linear-gradient(135deg, $color-primary-light, $color-primary);
|
|
|
|
|
- color: $color-text-primary;
|
|
|
|
|
- }
|
|
|
|
|
-
|
|
|
|
|
- &:active {
|
|
|
|
|
- opacity: 0.85;
|
|
|
|
|
- }
|
|
|
|
|
-}
|
|
|
|
|
</style>
|
|
</style>
|