7 changed files with 575 additions and 3 deletions
-
1src/js/api.js
-
3src/pages.json
-
58src/pages/menu/forth.vue
-
25src/subpackage/authorization/components/user_info/iconfont.css
-
132src/subpackage/authorization/components/user_info/impower.vue
-
357src/subpackage/authorization/components/user_info/tuniaoui-wx-user-info.vue
-
2src/subpackage/authorization/js/api.js
@ -0,0 +1,25 @@ |
|||||
|
@charset "UTF-8"; |
||||
|
|
||||
|
@font-face { |
||||
|
font-family: "tuniaoFont"; /* Project id 3784643 */ |
||||
|
src: |
||||
|
url('data:application/x-font-woff2;charset=utf-8;base64,d09GMgABAAAAAAN8AAsAAAAAB4gAAAMvAAEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAHFQGYACDBgqCQIIdATYCJAMMCwgABCAFhH8HPRuYBiMRpmvPIfurAzsYPj7DCVbrRAmElfXCs4V6xacO8aHO69VXu54tTy8h0hcJ7ufgieY+3+xscrn9B8wKQQFBywplLZCw9SwcOyZ5pKsoAQAbcICJTr7AjPPqr06NRkeIAemFpXv8cje1+/LkuLvD789WJZUANjOe9F76qptDOSMUui/Ua0WQKpZGXaqf5hHZdAD6x8tRJtRKtQd7j5UKkk6lWywYkGADCZBnGLugJd6CAI4GOjH956Ep4k7imdNkYTGFAkm2nJyPrBNwA7YhWwgQ/K4bLXITD8wl8xxuBN+XwyYJwOAp5jFjOwNbPNwd3l3WiyFAv3sCBLjcAB6gQM3GjLLSbJpDo1ANiqsiFiX7WAQzqTcMA06j/pb/eAbEx8yMAaAChg3sDjs6COwub8IAoAD4PEZkA7iAZClPKdicmJLc2OiZcQC3cV613sc3Ab9W7YItQtio9YgdKGjgr+ANlbg5gPvXFacv8IyvKTH4pcjV7VIcfnuIAUd3VCbxcCIKj++rvr/hpx/iwxd4/5mxDXeILbBp2+ByMIlGMuQEU3gjiVaMcXk8Dn2gWo5wuRwuIldLRqRwWogvmCRXE9/kSvrVQP4iFDVWRSbRakMk/AtcBYVpO6rpah1V9J/m/Wt+q8WfsOV+S5KFTGD5dwW9KFstZUs5smuYK3V495zwUG+r/Izf0PWtbWj/HUQsAL9u+cGK8NCiAgRnaRJ49fqljrxWc4PaKs4pQwBlMLUeAzgcEGLakvg5nCZ3zgTBkZzAEEUuFEeJyMrq4BGhGT6OPjiqGd4eIZkLKGKjgTKuAAgpPIAhjmdQUngnsrJdeKTxBz4pkgjHjJQeFqFMXv8PQqg0QP+F2cbAdoHqFmaM52jYlcbNoeTq4CtPkjzHAE1Zl0QvFEjGmp9fY6vKwBI9kOvIuQhJ4kJWy0k1dVXFVXcpbfTmIIRKA/RfmG0M7G1T3cKM8VwMXGlEnR1KY0uU+CTJnM1ODk1ZdxJdSOjYdGOp+TW2k6szsNg8qIvIuQipetFCVstpQCB1lcXHXUl5ZOpfdBvgMI9QMaJi8TZdzLS36K8/ueDZOWMAAA==') format('woff2'), |
||||
|
url('//at.alicdn.com/t/c/font_3784643_5jru9pe5fad.woff?t=1669045092678') format('woff'), |
||||
|
url('//at.alicdn.com/t/c/font_3784643_5jru9pe5fad.ttf?t=1669045092678') format('truetype'); |
||||
|
} |
||||
|
|
||||
|
[class*='tn-icon-'] { |
||||
|
font-family: 'tuniaoFont' !important; |
||||
|
font-style: normal; |
||||
|
-webkit-font-smoothing: antialiased; |
||||
|
text-align: center; |
||||
|
text-decoration: none; |
||||
|
} |
||||
|
|
||||
|
.tn-icon-close:before { |
||||
|
content: "\e74d"; |
||||
|
} |
||||
|
|
||||
|
.tn-icon-camera-fill:before { |
||||
|
content: "\e75d"; |
||||
|
} |
@ -0,0 +1,132 @@ |
|||||
|
<template> |
||||
|
<wx-user-info-modal |
||||
|
v-model="showAuthorizationModal" |
||||
|
@updated="updatedUserInfoEvent" |
||||
|
:isModal="isModal" |
||||
|
:alway="alway" |
||||
|
></wx-user-info-modal> |
||||
|
</template> |
||||
|
|
||||
|
<script> |
||||
|
import WxUserInfoModal from './tuniaoui-wx-user-info.vue'; |
||||
|
import { AUTHOR_API } from '../../js/api'; |
||||
|
import servers from '../../js/server'; |
||||
|
import { showModal, jsonPar, showLoad, hideLoad } from '@/utils/util'; |
||||
|
export default { |
||||
|
components: { WxUserInfoModal }, |
||||
|
props: { |
||||
|
isModal: { |
||||
|
type: Boolean, |
||||
|
default: true |
||||
|
}, |
||||
|
alway: { |
||||
|
type: Boolean, |
||||
|
default: false |
||||
|
} |
||||
|
}, |
||||
|
watch: { |
||||
|
showAuthorizationModal(nVal, oVal){ |
||||
|
let { initData } = this; |
||||
|
if(!nVal&&oVal)initData?.close(); |
||||
|
} |
||||
|
}, |
||||
|
data() { |
||||
|
return { |
||||
|
showAuthorizationModal: false, |
||||
|
initData: {}, |
||||
|
} |
||||
|
}, |
||||
|
methods: { |
||||
|
show(data){ |
||||
|
this.showAuthorizationModal = true; |
||||
|
this.initData = data; |
||||
|
}, |
||||
|
hide(){ |
||||
|
this.showAuthorizationModal = false; |
||||
|
}, |
||||
|
// 获取到的用户信息 |
||||
|
async updatedUserInfoEvent(info) { |
||||
|
let { initData, userEdit } = this; |
||||
|
try{ |
||||
|
let _imgUrl = await this.uploadImg(info.avatar); |
||||
|
let _editObj = { nickname: info.nickname, avatar_url: _imgUrl }; |
||||
|
await userEdit(_editObj); |
||||
|
initData?.success?.(_editObj); |
||||
|
}catch(err){ |
||||
|
console.warn('authorize components user info impower updatedUserInfoEvent err --->', err) |
||||
|
initData?.fail?.(err); |
||||
|
} |
||||
|
}, |
||||
|
// 上传头像 |
||||
|
async uploadImg(url){ |
||||
|
try{ |
||||
|
showLoad(); |
||||
|
let _imgInfo = await servers.uploadFile({ |
||||
|
url: AUTHOR_API.zs_user_avatar, |
||||
|
filePath: url, |
||||
|
}); |
||||
|
if(_imgInfo.statusCode != 200)throw(_imgInfo); |
||||
|
let _imgRes = jsonPar(_imgInfo.data); |
||||
|
if(_imgRes.code != 0)throw(_imgRes); |
||||
|
hideLoad(); |
||||
|
return _imgRes.data.url || ''; |
||||
|
}catch(err){ |
||||
|
hideLoad(); |
||||
|
showModal({ content: err?.errMsg ?? err?.message ?? '上传图片失败!' }); |
||||
|
console.warn('authorize components user info impower uploadImg err --->', err) |
||||
|
return Promise.reject(err); |
||||
|
} |
||||
|
}, |
||||
|
// 用户信息上传 |
||||
|
userEdit({ nickname, avatar_url }){ |
||||
|
showLoad(); |
||||
|
return servers.post({ |
||||
|
url: AUTHOR_API.changeAvatar, |
||||
|
data: { nickname, avatar_url }, |
||||
|
isDefaultGet: false, |
||||
|
}) |
||||
|
.then(res => { |
||||
|
hideLoad(); |
||||
|
let _data = res?.data || {}; |
||||
|
if(_data.code === 0){ |
||||
|
console.log('userEdit res--->', _data); |
||||
|
return _data?.data; |
||||
|
}else{ |
||||
|
return Promise.reject(_data); |
||||
|
} |
||||
|
}) |
||||
|
.catch(err => { |
||||
|
hideLoad(); |
||||
|
showModal({ content: err.message || '操作失败!' }); |
||||
|
console.warn('authorize components user info impower userEdit err --->', err); |
||||
|
return Promise.reject(err); |
||||
|
}) |
||||
|
}, |
||||
|
// 刷新用户信息 |
||||
|
refreshUserInfo(){ |
||||
|
return servers.post({ |
||||
|
url: ATR_API.userCurrent, |
||||
|
data: {}, |
||||
|
isDefaultGet: false, |
||||
|
}) |
||||
|
.then(res => { |
||||
|
let _data = res?.data || {}; |
||||
|
if(_data.code === 0){ |
||||
|
uni.setStorageSync('userInfo', _data?.data); |
||||
|
this.$store.commit('refreshUserInfo', _data?.data); |
||||
|
return _data?.data; |
||||
|
}else{ |
||||
|
return Promise.reject(_data); |
||||
|
} |
||||
|
}) |
||||
|
.catch(err => { |
||||
|
console.warn('authorize components user info impower refreshUserInfo err --->', err); |
||||
|
// return Promise.reject(err); |
||||
|
}) |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
</script> |
||||
|
|
||||
|
<style lang="scss"> |
||||
|
</style> |
@ -0,0 +1,357 @@ |
|||||
|
<template> |
||||
|
<view |
||||
|
v-if="openModal || alway" |
||||
|
class="wx-authorization-modal" |
||||
|
:class="{ 'modal-class': isModal }" |
||||
|
> |
||||
|
<view |
||||
|
class="wam__mask" |
||||
|
@touchmove.prevent="" |
||||
|
@tap.stop="closeModal" |
||||
|
></view> |
||||
|
|
||||
|
<!-- 内容区域 --> |
||||
|
<view class="wam__wrapper"> |
||||
|
<!-- 关闭按钮 --> |
||||
|
<view class="wam__close-btn" @tap.stop="closeModal"> |
||||
|
<text class="tn-icon-close"></text> |
||||
|
</view> |
||||
|
<!-- 标题 --> |
||||
|
<view class="wam__title">获取您的昵称、头像</view> |
||||
|
<!-- tips --> |
||||
|
<view class="wam__sub-title"> |
||||
|
获取用户头像、昵称,主要用于向用户提供具有辨识度的用户中心界面 |
||||
|
</view> |
||||
|
|
||||
|
<!-- 头像选择 --> |
||||
|
<view class="wam__avatar"> |
||||
|
<view class="button-shadow"> |
||||
|
<button |
||||
|
class="button" |
||||
|
open-type="chooseAvatar" |
||||
|
@chooseavatar="chooseAvatarEvent" |
||||
|
> |
||||
|
<view v-if="userInfo.avatar" class="avatar__image"> |
||||
|
<image class="image" :src="userInfo.avatar" mode="aspectFill"></image> |
||||
|
</view> |
||||
|
<view v-else class="avatar__empty"> |
||||
|
<!-- <image class="image" src="https://cdn.nlark.com/yuque/0/2022/jpeg/280373/1668928062708-assets/web-upload/764843cf-055a-4cb6-b5d3-dca528b33fd4.jpeg" mode="aspectFill"></image> --> |
||||
|
</view> |
||||
|
<view class="avatar--icon"> |
||||
|
<view class="tn-icon-camera-fill"></view> |
||||
|
</view> |
||||
|
</button> |
||||
|
</view> |
||||
|
</view> |
||||
|
|
||||
|
<!-- 昵称输入 --> |
||||
|
<view class="wam__nickname"> |
||||
|
<view class="nickname__data"> |
||||
|
<input class="input" type="nickname" v-model="userInfo.nickname" placeholder="请输入昵称" placeholder-style="color: #AAAAAA;"> |
||||
|
</view> |
||||
|
</view> |
||||
|
|
||||
|
|
||||
|
<!-- 保存按钮 --> |
||||
|
<view |
||||
|
class="wam__submit-btn" |
||||
|
:class="[{ |
||||
|
'disabled': !userInfo.avatar || !userInfo.nickname |
||||
|
}]" |
||||
|
hover-class="tn-btn-hover-class" |
||||
|
:hover-stay-time="150" |
||||
|
@tap.stop="submitUserInfo" |
||||
|
> |
||||
|
保 存 |
||||
|
</view> |
||||
|
</view> |
||||
|
</view> |
||||
|
</template> |
||||
|
|
||||
|
<script> |
||||
|
|
||||
|
export default { |
||||
|
options: { |
||||
|
// 在微信小程序中将组件节点渲染为虚拟节点,更加接近Vue组件的表现(不会出现shadow节点下再去创建元素) |
||||
|
virtualHost: true |
||||
|
}, |
||||
|
props: { |
||||
|
value: { |
||||
|
type: Boolean, |
||||
|
default: false |
||||
|
}, |
||||
|
isModal: { |
||||
|
type: Boolean, |
||||
|
default: true |
||||
|
}, |
||||
|
alway: { |
||||
|
type: Boolean, |
||||
|
default: false |
||||
|
} |
||||
|
}, |
||||
|
data() { |
||||
|
return { |
||||
|
openModal: false, |
||||
|
userInfo: { |
||||
|
avatar: '', |
||||
|
nickname: '' |
||||
|
} |
||||
|
} |
||||
|
}, |
||||
|
watch: { |
||||
|
value: { |
||||
|
handler(val) { |
||||
|
this.openModal = val |
||||
|
}, |
||||
|
immediate: true |
||||
|
} |
||||
|
}, |
||||
|
methods: { |
||||
|
|
||||
|
|
||||
|
// 头像选择 |
||||
|
chooseAvatarEvent(e) { |
||||
|
this.userInfo.avatar = e.detail.avatarUrl |
||||
|
}, |
||||
|
|
||||
|
// 更新用户信息 |
||||
|
submitUserInfo() { |
||||
|
// 判断是否已经选择了用户头像和输入了用户昵称 |
||||
|
if (!this.userInfo.avatar || !this.userInfo.nickname) { |
||||
|
return uni.showToast({ |
||||
|
icon: 'none', |
||||
|
title: '请选择头像和输入用户信息' |
||||
|
}) |
||||
|
} |
||||
|
|
||||
|
// 更新完成事件 |
||||
|
this.$emit('updated', this.userInfo) |
||||
|
|
||||
|
}, |
||||
|
|
||||
|
// 关闭弹框 |
||||
|
closeModal() { |
||||
|
this.$emit('input', false) |
||||
|
}, |
||||
|
|
||||
|
|
||||
|
} |
||||
|
} |
||||
|
</script> |
||||
|
|
||||
|
<style lang="scss" scoped> |
||||
|
|
||||
|
@import './iconfont.css'; |
||||
|
|
||||
|
.modal-class{ |
||||
|
position: fixed; |
||||
|
left: 0; |
||||
|
top: 0; |
||||
|
width: 100vw; |
||||
|
height: 100vh; |
||||
|
z-index: 99998; |
||||
|
.wam { |
||||
|
&__mask { |
||||
|
display: block !important; |
||||
|
position: absolute; |
||||
|
left: 0; |
||||
|
top: 0; |
||||
|
width: 100%; |
||||
|
height: 100%; |
||||
|
background-color: rgba(0, 0, 0, 0.5); |
||||
|
opacity: 0; |
||||
|
animation: showMask 0.25s ease 0.1s forwards; |
||||
|
} |
||||
|
&__close-btn { |
||||
|
display: block !important; |
||||
|
display: none; |
||||
|
position: absolute; |
||||
|
top: 30rpx; |
||||
|
right: 30rpx; |
||||
|
z-index: 99999; |
||||
|
} |
||||
|
&__wrapper{ |
||||
|
position: absolute; |
||||
|
left: 0; |
||||
|
bottom: 0; |
||||
|
width: 100%; |
||||
|
transform-origin: center bottom; |
||||
|
transform: scaleY(0); |
||||
|
animation: showWrapper 0.25s ease 0.1s forwards; |
||||
|
z-index: 99999; |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
} |
||||
|
|
||||
|
.wx-authorization-modal { |
||||
|
// view { |
||||
|
// box-sizing: border-box; |
||||
|
// } |
||||
|
|
||||
|
.image { |
||||
|
width: 100%; |
||||
|
height: 100%; |
||||
|
border-radius: inherit; |
||||
|
} |
||||
|
|
||||
|
|
||||
|
|
||||
|
.wam { |
||||
|
/* mask */ |
||||
|
&__mask { |
||||
|
display: none; |
||||
|
} |
||||
|
|
||||
|
/* close-btn */ |
||||
|
&__close-btn { |
||||
|
display: none; |
||||
|
} |
||||
|
|
||||
|
/* wrapper */ |
||||
|
&__wrapper { |
||||
|
background-color: #FFFFFF; |
||||
|
border-radius: 20rpx 20rpx 0rpx 0rpx; |
||||
|
padding: 40rpx; |
||||
|
padding-top: 60rpx; |
||||
|
padding-bottom: 40rpx; |
||||
|
padding-bottom: calc(constant(safe-area-inset-bottom) + 40rpx); |
||||
|
padding-bottom: calc(env(safe-area-inset-bottom) + 40rpx); |
||||
|
|
||||
|
} |
||||
|
|
||||
|
/* title */ |
||||
|
&__title { |
||||
|
font-size: 34rpx; |
||||
|
} |
||||
|
/* sub-title */ |
||||
|
&__sub-title { |
||||
|
font-size: 26rpx; |
||||
|
color: #AAAAAA; |
||||
|
margin-top: 16rpx; |
||||
|
padding-bottom: 30rpx; |
||||
|
} |
||||
|
|
||||
|
/* 头像选择 */ |
||||
|
&__avatar { |
||||
|
width: 100%; |
||||
|
margin-top: 30rpx; |
||||
|
display: flex; |
||||
|
align-items: center; |
||||
|
justify-content: center; |
||||
|
|
||||
|
.button-shadow { |
||||
|
border: 8rpx solid rgba(255,255,255,0.05); |
||||
|
box-shadow: 0rpx 0rpx 80rpx 0rpx rgba(0, 0, 0, 0.15); |
||||
|
border-radius: 50%; |
||||
|
} |
||||
|
|
||||
|
.button { |
||||
|
position: relative; |
||||
|
width: 160rpx; |
||||
|
height: 160rpx; |
||||
|
border-radius: 50%; |
||||
|
overflow: visible; |
||||
|
background-image: repeating-linear-gradient(45deg, #E4E9EC, #F8F7F8); |
||||
|
color: #FFFFFF; |
||||
|
background-color: transparent; |
||||
|
padding: 0; |
||||
|
margin: 0; |
||||
|
font-size: inherit; |
||||
|
line-height: inherit; |
||||
|
border: none; |
||||
|
&::after { |
||||
|
border: none; |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
.avatar { |
||||
|
&__empty, &__image { |
||||
|
width: 100%; |
||||
|
height: 100%; |
||||
|
border-radius: inherit; |
||||
|
} |
||||
|
|
||||
|
&--icon { |
||||
|
position: absolute; |
||||
|
right: -10rpx; |
||||
|
bottom: -6rpx; |
||||
|
width: 60rpx; |
||||
|
height: 60rpx; |
||||
|
// transform: translate(50%, 50%); |
||||
|
background-color: #1D2541; |
||||
|
color: #FFFFFF; |
||||
|
border-radius: 50%; |
||||
|
border: 6rpx solid #FFFFFF; |
||||
|
line-height: 1; |
||||
|
font-size: 36rpx; |
||||
|
display: flex; |
||||
|
align-items: center; |
||||
|
justify-content: center; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
/* 昵称 */ |
||||
|
&__nickname { |
||||
|
margin-top: 40rpx; |
||||
|
|
||||
|
.nickname { |
||||
|
|
||||
|
&__data { |
||||
|
margin-top: 16rpx; |
||||
|
width: 100%; |
||||
|
padding: 26rpx 20rpx; |
||||
|
border-radius: 10rpx; |
||||
|
background-color: #F8F7F8; |
||||
|
|
||||
|
.input { |
||||
|
color: #080808; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
/* 保存按钮 */ |
||||
|
&__submit-btn { |
||||
|
width: 100%; |
||||
|
background-color: $mColor; |
||||
|
color: #FFFFFF; |
||||
|
margin-top: 60rpx; |
||||
|
border-radius: 10rpx; |
||||
|
padding: 25rpx; |
||||
|
font-size: 32rpx; |
||||
|
display: flex; |
||||
|
align-items: center; |
||||
|
justify-content: center; |
||||
|
|
||||
|
&.disabled { |
||||
|
background-color: #E6E6E6; |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
|
||||
|
} |
||||
|
} |
||||
|
|
||||
|
.tn-btn-hover-class { |
||||
|
box-shadow: inset 10rpx 2rpx 40rpx 0rpx rgba(0, 0, 0, 0.05); |
||||
|
} |
||||
|
|
||||
|
@keyframes showMask { |
||||
|
0% { |
||||
|
opacity: 0; |
||||
|
} |
||||
|
100% { |
||||
|
opacity: 1; |
||||
|
} |
||||
|
} |
||||
|
@keyframes showWrapper { |
||||
|
0% { |
||||
|
transform: scaleY(0); |
||||
|
} |
||||
|
100% { |
||||
|
transform: scaleY(1); |
||||
|
} |
||||
|
} |
||||
|
</style> |
Write
Preview
Loading…
Cancel
Save
Reference in new issue