feat:新增登录验证
This commit is contained in:
@ -7,68 +7,68 @@
|
||||
|
||||
<!-- 内容区域 -->
|
||||
<view class="tabbar-content">
|
||||
<!-- 环境参数详情 -->
|
||||
<view class="parameter-details">
|
||||
<!-- 温度卡片 -->
|
||||
<view class="detail-card temperature-detail-card">
|
||||
<view class="detail-header">
|
||||
<view class="detail-icon-container">
|
||||
<view class="detail-icon temperature-icon">🌡️</view>
|
||||
<text class="detail-label">温度</text>
|
||||
</view>
|
||||
<view class="detail-value-container">
|
||||
<text class="detail-value">{{ temperature }}°C</text>
|
||||
<view class="detail-status" :class="temperature > 0 ? 'active' : 'inactive'"></view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="detail-progress-bar">
|
||||
<view class="detail-progress-fill temperature-progress" :style="{ width: temperatureProgress + '%' }"></view>
|
||||
</view>
|
||||
<!-- <view class="detail-range">
|
||||
<text class="detail-range-text">{{ 0 }}°C - {{ 100 }}°C</text>
|
||||
</view> -->
|
||||
<!-- 环境参数详情 -->
|
||||
<view class="parameter-details">
|
||||
<!-- 温度卡片 -->
|
||||
<view class="detail-card temperature-detail-card" @click="navigateToParameterRecord">
|
||||
<view class="detail-header">
|
||||
<view class="detail-icon-container">
|
||||
<view class="detail-icon temperature-icon">🌡️</view>
|
||||
<text class="detail-label">温度</text>
|
||||
</view>
|
||||
|
||||
<!-- 湿度卡片 -->
|
||||
<view class="detail-card humidity-detail-card">
|
||||
<view class="detail-header">
|
||||
<view class="detail-icon-container">
|
||||
<view class="detail-icon humidity-icon">💧</view>
|
||||
<text class="detail-label">湿度</text>
|
||||
</view>
|
||||
<view class="detail-value-container">
|
||||
<text class="detail-value">{{ humidity }}%</text>
|
||||
<view class="detail-status" :class="humidity > 0 ? 'active' : 'inactive'"></view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="detail-progress-bar">
|
||||
<view class="detail-progress-fill humidity-progress" :style="{ width: humidityProgress + '%' }"></view>
|
||||
</view>
|
||||
<!-- <view class="detail-range">
|
||||
<text class="detail-range-text">{{ 0 }}% - {{ 100 }}%</text>
|
||||
</view> -->
|
||||
</view>
|
||||
|
||||
<!-- 洁净度卡片 -->
|
||||
<view class="detail-card cleanliness-detail-card">
|
||||
<view class="detail-header">
|
||||
<view class="detail-icon-container">
|
||||
<view class="detail-icon cleanliness-icon">✨</view>
|
||||
<text class="detail-label">洁净度</text>
|
||||
</view>
|
||||
<view class="detail-value-container">
|
||||
<text class="detail-value">{{ cleanliness > 0 ? cleanliness + 'μg/m³' : '-μg/m³' }}</text>
|
||||
<view class="detail-status" :class="cleanliness > 0 ? 'active' : 'inactive'"></view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="detail-progress-bar">
|
||||
<view class="detail-progress-fill cleanliness-progress" :style="{ width: cleanlinessProgress + '%' }"></view>
|
||||
</view>
|
||||
<!-- <view class="detail-range">
|
||||
<text class="detail-range-text">{{ 0 }}% - {{ 100 }}%</text>
|
||||
</view> -->
|
||||
<view class="detail-value-container">
|
||||
<text class="detail-value">{{ temperature }}°C</text>
|
||||
<view class="detail-status" :class="temperature > 0 ? 'active' : 'inactive'"></view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="detail-progress-bar">
|
||||
<view class="detail-progress-fill temperature-progress" :style="{ width: temperatureProgress + '%' }"></view>
|
||||
</view>
|
||||
<!-- <view class="detail-range">
|
||||
<text class="detail-range-text">{{ 0 }}°C - {{ 100 }}°C</text>
|
||||
</view> -->
|
||||
</view>
|
||||
|
||||
<!-- 湿度卡片 -->
|
||||
<view class="detail-card humidity-detail-card" @click="navigateToParameterRecord">
|
||||
<view class="detail-header">
|
||||
<view class="detail-icon-container">
|
||||
<view class="detail-icon humidity-icon">💧</view>
|
||||
<text class="detail-label">湿度</text>
|
||||
</view>
|
||||
<view class="detail-value-container">
|
||||
<text class="detail-value">{{ humidity }}%</text>
|
||||
<view class="detail-status" :class="humidity > 0 ? 'active' : 'inactive'"></view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="detail-progress-bar">
|
||||
<view class="detail-progress-fill humidity-progress" :style="{ width: humidityProgress + '%' }"></view>
|
||||
</view>
|
||||
<!-- <view class="detail-range">
|
||||
<text class="detail-range-text">{{ 0 }}% - {{ 100 }}%</text>
|
||||
</view> -->
|
||||
</view>
|
||||
|
||||
<!-- 洁净度卡片 -->
|
||||
<view class="detail-card cleanliness-detail-card" @click="navigateToParameterRecord">
|
||||
<view class="detail-header">
|
||||
<view class="detail-icon-container">
|
||||
<view class="detail-icon cleanliness-icon">✨</view>
|
||||
<text class="detail-label">洁净度</text>
|
||||
</view>
|
||||
<view class="detail-value-container">
|
||||
<text class="detail-value">{{ cleanliness > 0 ? cleanliness + 'μg/m³' : '-μg/m³' }}</text>
|
||||
<view class="detail-status" :class="cleanliness > 0 ? 'active' : 'inactive'"></view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="detail-progress-bar">
|
||||
<view class="detail-progress-fill cleanliness-progress" :style="{ width: cleanlinessProgress + '%' }"></view>
|
||||
</view>
|
||||
<!-- <view class="detail-range">
|
||||
<text class="detail-range-text">{{ 0 }}% - {{ 100 }}%</text>
|
||||
</view> -->
|
||||
</view>
|
||||
</view>
|
||||
|
||||
<!-- 空调设置 -->
|
||||
<view class="air-conditioner-settings">
|
||||
@ -385,6 +385,13 @@ export default {
|
||||
this.loadWsdSettings()
|
||||
// 注意:定时器在 onShow 中启动,避免重复启动
|
||||
},
|
||||
navigateToParameterRecord() {
|
||||
try {
|
||||
uni.switchTab({ url: '/pages/parameter/index' })
|
||||
} catch (e) {
|
||||
uni.showToast({ title: '页面跳转失败', icon: 'none' })
|
||||
}
|
||||
},
|
||||
// 首次进入系统时创建启动事件
|
||||
async createStartupEventIfNeeded() {
|
||||
// 检查是否已经创建过启动事件
|
||||
|
||||
@ -16,15 +16,32 @@
|
||||
<text class="title-text">上动物联</text>
|
||||
</view>
|
||||
</view>
|
||||
|
||||
<!-- 下部区域:按钮和版本号 -->
|
||||
<view class="bottom-section">
|
||||
<!-- 进入系统按钮 -->
|
||||
|
||||
<!-- 登录表单:账号、密码 -->
|
||||
<view class="form-section">
|
||||
<!-- <view class="form-item">
|
||||
<text class="form-label">账号</text>
|
||||
<input class="form-input" v-model="username" placeholder="请输入账号" placeholder-class="placeholder" confirm-type="next" />
|
||||
</view> -->
|
||||
<view class="form-item">
|
||||
<text class="form-label">密码</text>
|
||||
<input class="form-input" v-model="password" password placeholder="请输入密码" placeholder-class="placeholder" confirm-type="done" />
|
||||
</view>
|
||||
<view class="action-container">
|
||||
<button class="enter-button" @click="navigateToTabBar">
|
||||
<text class="button-text">进入系统 →</text>
|
||||
</button>
|
||||
</view>
|
||||
</view>
|
||||
|
||||
<!-- 下部区域:按钮和版本号 -->
|
||||
<view class="bottom-section">
|
||||
<!-- 进入系统按钮 -->
|
||||
<!-- <view class="action-container">
|
||||
<button class="enter-button" @click="navigateToTabBar">
|
||||
<text class="button-text">进入系统 →</text>
|
||||
</button>
|
||||
</view> -->
|
||||
|
||||
<!-- 版本号 -->
|
||||
<view class="version-container">
|
||||
@ -37,84 +54,141 @@
|
||||
|
||||
<script>
|
||||
import { manualReconnect } from '@/utils/sendMqtt.js'
|
||||
import { authApi } from '@/utils/api.js'
|
||||
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
title: 'Hello',
|
||||
username: '',
|
||||
password: '',
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
canLogin() {
|
||||
// return this.username && this.username.trim().length > 0 && this.password && this.password.trim().length > 0
|
||||
return this.password && this.password.trim().length > 0
|
||||
}
|
||||
},
|
||||
onLoad() {},
|
||||
methods: {
|
||||
navigateToTabBar() {
|
||||
console.log('🔧 用户点击进入系统,开始MQTT重连...')
|
||||
|
||||
// 立即显示连接提示
|
||||
uni.showLoading({
|
||||
title: '正在连接MQTT...',
|
||||
// mask: true
|
||||
})
|
||||
|
||||
// 调用MQTT重连函数
|
||||
async navigateToTabBar() {
|
||||
if (!this.canLogin) {
|
||||
uni.showToast({
|
||||
title: '请输入密码',
|
||||
icon: 'none',
|
||||
duration: 1200
|
||||
})
|
||||
return
|
||||
}
|
||||
console.log('🔒 开始登录...')
|
||||
|
||||
// 先登录
|
||||
try {
|
||||
manualReconnect()
|
||||
console.log('✅ MQTT重连函数已调用')
|
||||
|
||||
// 延迟跳转,给MQTT连接一些时间
|
||||
setTimeout(() => {
|
||||
// 更新loading文本
|
||||
uni.showLoading({ title: '正在登录...' })
|
||||
const loginRes = await authApi.login({
|
||||
username: this.username || 'admin',
|
||||
password: this.password
|
||||
})
|
||||
|
||||
console.log('🔒 登录结果:', loginRes)
|
||||
if (loginRes.success) {
|
||||
// 可选:如果返回 token,保存以备后续请求使用
|
||||
if (loginRes && loginRes.token) {
|
||||
const token = loginRes.token;
|
||||
try {
|
||||
uni.setStorageSync('auth_token', token)
|
||||
} catch (e) {}
|
||||
}
|
||||
|
||||
uni.hideLoading()
|
||||
uni.showToast({ title: '登录成功', icon: 'success', duration: 800 })
|
||||
// 立即显示连接提示
|
||||
uni.showLoading({
|
||||
title: '正在跳转系统...',
|
||||
title: '正在连接MQTT...',
|
||||
// mask: true
|
||||
})
|
||||
uni.hideLoading()
|
||||
// 跳转到tabbar的第一个页面(环境参数页面)
|
||||
uni.switchTab({
|
||||
url: '/pages/environment/index',
|
||||
success: () => {
|
||||
console.log('✅ 成功跳转到环境参数页面')
|
||||
uni.showToast({
|
||||
title: '系统连接成功',
|
||||
icon: 'success',
|
||||
duration: 1000
|
||||
|
||||
// 调用MQTT重连函数
|
||||
try {
|
||||
manualReconnect()
|
||||
console.log('✅ MQTT重连函数已调用')
|
||||
|
||||
// 延迟跳转,给MQTT连接一些时间
|
||||
setTimeout(() => {
|
||||
// 更新loading文本
|
||||
uni.showLoading({
|
||||
title: '正在跳转系统...',
|
||||
// mask: true
|
||||
})
|
||||
},
|
||||
fail: (err) => {
|
||||
console.error('❌ 跳转到tabbar失败:', err);
|
||||
// 如果失败,尝试使用redirectTo
|
||||
uni.redirectTo({
|
||||
uni.hideLoading()
|
||||
// 跳转到tabbar的第一个页面(环境参数页面)
|
||||
uni.switchTab({
|
||||
url: '/pages/environment/index',
|
||||
success: () => {
|
||||
console.log('✅ 使用redirectTo成功跳转')
|
||||
console.log('✅ 成功跳转到环境参数页面')
|
||||
uni.showToast({
|
||||
title: '系统连接成功',
|
||||
icon: 'success',
|
||||
duration: 1000
|
||||
})
|
||||
},
|
||||
fail: (redirectErr) => {
|
||||
console.error('❌ redirectTo也失败:', redirectErr)
|
||||
uni.showToast({
|
||||
title: '页面跳转失败',
|
||||
icon: 'error',
|
||||
duration: 1000
|
||||
})
|
||||
fail: (err) => {
|
||||
console.error('❌ 跳转到tabbar失败:', err);
|
||||
// 如果失败,尝试使用redirectTo
|
||||
uni.redirectTo({
|
||||
url: '/pages/environment/index',
|
||||
success: () => {
|
||||
console.log('✅ 使用redirectTo成功跳转')
|
||||
uni.showToast({
|
||||
title: '系统连接成功',
|
||||
icon: 'success',
|
||||
duration: 1000
|
||||
})
|
||||
},
|
||||
fail: (redirectErr) => {
|
||||
console.error('❌ redirectTo也失败:', redirectErr)
|
||||
uni.showToast({
|
||||
title: '页面跳转失败',
|
||||
icon: 'error',
|
||||
duration: 1000
|
||||
})
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
})
|
||||
|
||||
}, 300) // 1秒后开始跳转
|
||||
|
||||
} catch (error) {
|
||||
console.error('❌ MQTT重连失败:', error)
|
||||
uni.hideLoading()
|
||||
uni.showToast({
|
||||
title: 'MQTT连接失败',
|
||||
icon: 'error',
|
||||
duration: 1000
|
||||
})
|
||||
}
|
||||
} else {
|
||||
uni.hideLoading()
|
||||
uni.showToast({
|
||||
title: loginRes?.message || '登录失败',
|
||||
icon: 'none',
|
||||
duration: 1500
|
||||
})
|
||||
|
||||
}, 300) // 1秒后开始跳转
|
||||
|
||||
} catch (error) {
|
||||
console.error('❌ MQTT重连失败:', error)
|
||||
return
|
||||
}
|
||||
} catch (e) {
|
||||
uni.hideLoading()
|
||||
uni.showToast({
|
||||
title: 'MQTT连接失败',
|
||||
icon: 'error',
|
||||
duration: 1000
|
||||
title: e?.message || '登录失败',
|
||||
icon: 'none',
|
||||
duration: 1500
|
||||
})
|
||||
return
|
||||
}
|
||||
|
||||
console.log('🔧 用户点击进入系统,开始MQTT重连...')
|
||||
}
|
||||
},
|
||||
}
|
||||
@ -193,6 +267,7 @@ export default {
|
||||
/* 进入系统按钮 */
|
||||
.action-container {
|
||||
margin-bottom: 40rpx;
|
||||
margin-top: 40px;
|
||||
}
|
||||
|
||||
.enter-button {
|
||||
@ -210,6 +285,42 @@ export default {
|
||||
font-weight: 500;
|
||||
}
|
||||
|
||||
/* 表单样式 */
|
||||
.form-section {
|
||||
width: 100%;
|
||||
max-width: 640rpx;
|
||||
margin-top: 40rpx;
|
||||
}
|
||||
|
||||
.form-item {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
background: #f7f8fa;
|
||||
border-radius: 12rpx;
|
||||
padding: 20rpx 24rpx;
|
||||
margin-bottom: 24rpx;
|
||||
}
|
||||
|
||||
.form-label {
|
||||
width: 120rpx;
|
||||
font-size: 28rpx;
|
||||
color: #333333;
|
||||
}
|
||||
|
||||
.form-input {
|
||||
flex: 1;
|
||||
font-size: 28rpx;
|
||||
color: #111111;
|
||||
}
|
||||
|
||||
.placeholder {
|
||||
color: #999999;
|
||||
}
|
||||
|
||||
.enter-button:disabled {
|
||||
opacity: 0.5;
|
||||
}
|
||||
|
||||
/* 版本号 */
|
||||
|
||||
.version-text {
|
||||
|
||||
@ -5,6 +5,15 @@
|
||||
|
||||
import httpService from './http.js'
|
||||
|
||||
// 认证接口
|
||||
export const authApi = {
|
||||
// 登录
|
||||
login(data) {
|
||||
// 约定字段:username、password
|
||||
return httpService.post('/api/auth/login', data)
|
||||
}
|
||||
}
|
||||
|
||||
// 数据历史接口
|
||||
export const dataHistoryApi = {
|
||||
// 获取历史数据
|
||||
|
||||
@ -282,11 +282,11 @@ const sendMqttData = (data) => {
|
||||
});
|
||||
} else {
|
||||
console.log('✅ MQTT数据发送成功');
|
||||
uni.showToast({
|
||||
title: '数据发送成功',
|
||||
icon: 'success',
|
||||
duration: 1500
|
||||
});
|
||||
// uni.showToast({
|
||||
// title: '数据发送成功',
|
||||
// icon: 'success',
|
||||
// duration: 1500
|
||||
// });
|
||||
}
|
||||
});
|
||||
|
||||
@ -334,11 +334,11 @@ const sendMqttDataRecall = (data) => {
|
||||
duration: 2000
|
||||
});
|
||||
} else {
|
||||
uni.showToast({
|
||||
title: '数据发送成功',
|
||||
icon: 'success',
|
||||
duration: 1500
|
||||
});
|
||||
// uni.showToast({
|
||||
// title: '数据发送成功',
|
||||
// icon: 'success',
|
||||
// duration: 1500
|
||||
// });
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
Reference in New Issue
Block a user