445 lines
11 KiB
Vue
445 lines
11 KiB
Vue
<template>
|
||
<view class="userSetting-container">
|
||
<view class="header">
|
||
<div class="header-left">
|
||
<u-icon
|
||
class="header-left-icon"
|
||
name="arrow-left"
|
||
@click="handleLeftClick"
|
||
></u-icon>
|
||
</div>
|
||
<text class="header-title">设置</text>
|
||
<div></div>
|
||
</view>
|
||
|
||
<view class="user-info-content">
|
||
<!-- 第一个卡片:头像 -->
|
||
<view class="info-card">
|
||
<view class="info-item avatar-item">
|
||
<text class="item-label">头像</text>
|
||
<view class="item-content avatar-content">
|
||
<view>
|
||
<uni-file-picker
|
||
v-model="imageValue"
|
||
limit="1"
|
||
:del-icon="false"
|
||
disable-preview
|
||
:imageStyles="imageStyles"
|
||
file-mediatype="image"
|
||
style="font-size: 12rpx"
|
||
@select="onSelect"
|
||
><text></text>
|
||
</uni-file-picker>
|
||
</view>
|
||
</view>
|
||
</view>
|
||
</view>
|
||
|
||
<!-- 第二个卡片:姓名和性别 -->
|
||
<view class="info-card">
|
||
<view class="info-item">
|
||
<text class="item-label">姓名</text>
|
||
<view class="item-content">
|
||
<input
|
||
class="item-input"
|
||
v-model="userInfo.name"
|
||
placeholder="请输入姓名"
|
||
placeholder-style="color: #CCCCCC;"
|
||
/>
|
||
</view>
|
||
</view>
|
||
|
||
<view class="info-item">
|
||
<text class="item-label">性别</text>
|
||
<view class="item-content" @click="openPicker('gender')">
|
||
<text class="placeholder-text" v-if="!userInfo.genderText"
|
||
>请选择性别</text
|
||
>
|
||
<text v-else>{{ userInfo.genderText }}</text>
|
||
<text class="arrow-icon">></text>
|
||
</view>
|
||
</view>
|
||
</view>
|
||
|
||
<!-- 第三个卡片:归属地 -->
|
||
<view class="info-card">
|
||
<view class="info-item">
|
||
<text class="item-label">归属地</text>
|
||
<view class="item-content" @click="openPicker('region')">
|
||
<text class="placeholder-text" v-if="!userInfo.region"
|
||
>请选择归属地</text
|
||
>
|
||
<text v-else>{{ userInfo.region }}</text>
|
||
<text class="arrow-icon">></text>
|
||
</view>
|
||
</view>
|
||
</view>
|
||
</view>
|
||
|
||
<div class="user-info-footer">
|
||
<u-button class="user-info-footer-button save-button" @click="handleSave">
|
||
保存
|
||
</u-button>
|
||
<u-button
|
||
class="user-info-footer-button logout-button"
|
||
@click="handleLogout"
|
||
>
|
||
退出登录
|
||
</u-button>
|
||
</div>
|
||
|
||
<!-- 性别选择器 -->
|
||
<u-select
|
||
v-model="showGenderSelect"
|
||
mode="single-column"
|
||
:list="genderList"
|
||
@confirm="confirmGender"
|
||
></u-select>
|
||
|
||
<!-- 归属地选择器 -->
|
||
<u-select
|
||
v-model="showRegionSelect"
|
||
mode="single-column"
|
||
:list="regionList"
|
||
@confirm="confirmRegion"
|
||
></u-select>
|
||
|
||
<!-- 消息提示 -->
|
||
<u-toast ref="uToast" />
|
||
</view>
|
||
</template>
|
||
|
||
<script>
|
||
import chinaProvinces from "@/static/common/js/china-provinces.js";
|
||
|
||
export default {
|
||
components: {},
|
||
data() {
|
||
return {
|
||
baseUrl: "",
|
||
// imageValue: ['/static/common/images/avatar_default.jpg'],
|
||
imageUrl: "",
|
||
imageValue: [],
|
||
|
||
imageStyles: {
|
||
width: 52,
|
||
height: 52,
|
||
border: {
|
||
// style: "none",
|
||
radius: "50%",
|
||
},
|
||
},
|
||
|
||
userInfo: {
|
||
name: "",
|
||
gender: "",
|
||
region: "",
|
||
},
|
||
|
||
// 性别选择器
|
||
showGenderSelect: false,
|
||
genderList: [
|
||
{
|
||
label: "男",
|
||
value: 0,
|
||
},
|
||
{
|
||
label: "女",
|
||
value: 1,
|
||
},
|
||
],
|
||
|
||
// 归属地选择器
|
||
showRegionSelect: false,
|
||
regionList: chinaProvinces,
|
||
};
|
||
},
|
||
mounted() {},
|
||
onLoad() {
|
||
this.baseUrl = this.$u.http.config.baseUrl;
|
||
this.getUserInfo();
|
||
},
|
||
methods: {
|
||
handleLeftClick() {
|
||
uni.navigateBack();
|
||
},
|
||
// 获取上传状态
|
||
onSelect(data) {
|
||
// console.log(data, "data");
|
||
const file = (data && data.tempFiles && data.tempFiles[0]) || {};
|
||
const filePath =
|
||
file.path || file.url || (file.image && file.image.location);
|
||
if (!filePath) {
|
||
this.$u.toast("无法获取文件路径");
|
||
return;
|
||
}
|
||
|
||
// 上传到后端(multipart/form-data)
|
||
this.$u.api
|
||
.UploadSingleImage({
|
||
filePath,
|
||
name: "file", // 按后端约定的字段名
|
||
formData: {
|
||
// 可选:向后端传递文件类型等附加信息
|
||
// fileType: file.extname || "",
|
||
},
|
||
})
|
||
.then((res) => {
|
||
if (res.succeed) {
|
||
this.imageUrl = res.data.replace(/\\/g, "/") || "";
|
||
this.imageValue = [
|
||
{
|
||
url: this.baseUrl + "/" + this.imageUrl,
|
||
extname: file.extname || "",
|
||
name: "",
|
||
},
|
||
];
|
||
this.$u.toast("上传成功");
|
||
} else {
|
||
this.$u.toast(res.error || "上传失败");
|
||
}
|
||
});
|
||
// .catch((err) => {
|
||
// this.$u.toast("上传失败");
|
||
// });
|
||
},
|
||
|
||
openPicker(type) {
|
||
if (type === "gender") {
|
||
this.showGenderSelect = true;
|
||
return;
|
||
}
|
||
if (type === "region") {
|
||
this.showRegionSelect = true;
|
||
return;
|
||
}
|
||
},
|
||
// 确认性别
|
||
confirmGender(e) {
|
||
console.log("确认性别", e[0].value);
|
||
this.userInfo.gender = e[0].value;
|
||
this.userInfo.genderText = e[0].label;
|
||
this.showGenderSelect = false;
|
||
},
|
||
// 确认归属地
|
||
confirmRegion(e) {
|
||
console.log("确认归属地", e[0].value);
|
||
this.userInfo.region = e[0].value;
|
||
this.userInfo.regionText = e[0].label;
|
||
this.showRegionSelect = false;
|
||
},
|
||
// 获取用户信息
|
||
getUserInfo() {
|
||
this.$u.api.GetUserApi({ Id: this.vuex_user.Id }).then((res) => {
|
||
const data = res.data[0];
|
||
this.userInfo.name = data.name || "";
|
||
this.userInfo.gender = data.sex || "";
|
||
this.userInfo.region = data.Region || "";
|
||
if (data.headSculptureUrl) {
|
||
this.imageUrl = data.headSculptureUrl;
|
||
this.imageValue = [
|
||
{
|
||
url: data.headSculptureUrl,
|
||
extname: "png",
|
||
name: "",
|
||
},
|
||
];
|
||
} else {
|
||
this.imageUrl = "";
|
||
this.imageValue = [
|
||
{
|
||
url: "/static/common/images/avatar_default.jpg",
|
||
extname: "jpg",
|
||
name: "",
|
||
},
|
||
];
|
||
}
|
||
});
|
||
},
|
||
// 保存用户信息
|
||
handleSave() {
|
||
console.log(this.userInfo, "保存用户信息");
|
||
|
||
// 表单验证
|
||
if (!this.userInfo.name) {
|
||
return this.$u.toast("请输入姓名");
|
||
}
|
||
if (this.userInfo.gender !== 0 && this.userInfo.gender !== 1) {
|
||
return this.$u.toast("请选择性别");
|
||
}
|
||
if (!this.userInfo.region) {
|
||
return this.$u.toast("请选择归属地");
|
||
}
|
||
|
||
const params = {
|
||
id: this.vuex_user.Id,
|
||
name: this.userInfo.name,
|
||
sex: this.userInfo.gender,
|
||
shen: this.userInfo.region,
|
||
headSculptureUrl: this.imageUrl,
|
||
};
|
||
|
||
this.$u.api.UpdateUserApi(params).then((res) => {
|
||
if (res.succeed) {
|
||
this.$refs.uToast.show({
|
||
title: "保存成功",
|
||
type: "success",
|
||
});
|
||
} else {
|
||
this.$refs.uToast.show({
|
||
title: res.error || "保存失败",
|
||
type: "error",
|
||
});
|
||
}
|
||
});
|
||
},
|
||
|
||
// 退出登录
|
||
handleLogout() {
|
||
this.$store.commit("logout");
|
||
uni.reLaunch({
|
||
// 与项目其余位置保持一致的登录页路径
|
||
url: "/pages/login/login/index?type=" + this.vuex_userType,
|
||
});
|
||
},
|
||
},
|
||
};
|
||
</script>
|
||
|
||
<style lang="scss" scoped>
|
||
.userSetting-container {
|
||
min-height: 100vh;
|
||
padding-bottom: calc(112rpx + env(safe-area-inset-bottom));
|
||
padding: 32rpx;
|
||
padding-top: calc(88rpx + 40rpx);
|
||
|
||
background-image: url(/static//common/images/images_bg.png);
|
||
background-repeat: no-repeat;
|
||
background-size: 100% 100%;
|
||
background-position: center;
|
||
|
||
.header {
|
||
position: fixed;
|
||
top: 0;
|
||
left: 0;
|
||
right: 0;
|
||
// background-color: #ffffff;
|
||
height: 88rpx;
|
||
display: flex;
|
||
align-items: center;
|
||
justify-content: space-between;
|
||
padding: 0 30rpx;
|
||
z-index: 99;
|
||
|
||
.header-left {
|
||
font-size: 36rpx;
|
||
}
|
||
|
||
.header-title {
|
||
font-size: 36rpx;
|
||
font-weight: 500;
|
||
color: #333333;
|
||
}
|
||
}
|
||
|
||
.user-info-content {
|
||
.info-card {
|
||
background-color: #ffffff;
|
||
border-radius: 20rpx;
|
||
padding: 0 32rpx;
|
||
margin-bottom: 32rpx;
|
||
|
||
.info-item {
|
||
height: 110rpx;
|
||
display: flex;
|
||
justify-content: space-between;
|
||
align-items: center;
|
||
border-bottom: 1rpx solid #f2f2f2;
|
||
|
||
&:last-child {
|
||
border-bottom: none;
|
||
}
|
||
|
||
.item-label {
|
||
font-family: PingFang SC;
|
||
font-size: 28rpx;
|
||
color: #333333;
|
||
}
|
||
|
||
.item-content {
|
||
flex: 1;
|
||
display: flex;
|
||
justify-content: flex-end;
|
||
align-items: center;
|
||
font-size: 28rpx;
|
||
color: #333333;
|
||
|
||
.item-input {
|
||
text-align: right;
|
||
width: 100%;
|
||
font-size: 28rpx;
|
||
}
|
||
|
||
.placeholder-text {
|
||
color: #cccccc;
|
||
}
|
||
|
||
.arrow-icon {
|
||
margin-left: 10rpx;
|
||
color: #cccccc;
|
||
}
|
||
}
|
||
|
||
&.avatar-item {
|
||
.avatar-content {
|
||
display: flex;
|
||
align-items: center;
|
||
}
|
||
|
||
.avatar-image {
|
||
width: 68rpx;
|
||
height: 68rpx;
|
||
border-radius: 50%;
|
||
}
|
||
}
|
||
}
|
||
}
|
||
}
|
||
|
||
.user-info-footer {
|
||
position: fixed;
|
||
bottom: 32rpx;
|
||
left: 0;
|
||
right: 0;
|
||
padding: 0 32rpx;
|
||
.user-info-footer-button {
|
||
width: 100%;
|
||
height: 85rpx;
|
||
border-radius: 16rpx;
|
||
opacity: 0.9;
|
||
font-weight: bold;
|
||
}
|
||
|
||
.save-button {
|
||
color: #ffffff;
|
||
background: #4f6aff;
|
||
margin-bottom: 32rpx;
|
||
}
|
||
.logout-button {
|
||
color: #ff4f4f;
|
||
background: #ffffff;
|
||
}
|
||
}
|
||
}
|
||
|
||
/* 响应式布局 - PC端样式 */
|
||
@media screen and (min-width: 768px) {
|
||
.userInfo-container {
|
||
.user-info-content {
|
||
max-width: 1200rpx;
|
||
margin: 0 auto;
|
||
}
|
||
}
|
||
}
|
||
</style>
|