login.vue 5.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269
  1. <template >
  2. <view class="">
  3. <!-- 获取手机号 -->
  4. <u-modal v-model="phoneShow" content="请授权获取手机号">
  5. <button class="cu-btn btn-bg-color round" style="width: 80%;" slot="confirm-button" open-type="getPhoneNumber" @getphonenumber="getphonenumber" >
  6. 去授权
  7. </button>
  8. </u-modal>
  9. <!-- 获取头像昵称 -->
  10. <view @touchmove.stop.prevent="clear" v-show="dialogShow">
  11. <view class="popup_mask" @touchmove.stop.prevent="clear"></view>
  12. <view class="">
  13. <view class="dt-login-wrap">
  14. <view class="title">请先登录</view>
  15. <view class="content">
  16. <view class="userinfo-avatar">
  17. <open-data type="userAvatarUrl"></open-data>
  18. </view>
  19. <open-data type="userNickName"></open-data>
  20. <text class="subtitle">申请获取您的公开信息(昵称,头像)</text>
  21. </view>
  22. <view class="btn-content setBtnCss">
  23. <button @click="hide" >暂不登录</button>
  24. <button open-type="getUserInfo" @getuserinfo="getuserinfo" >立即登录</button>
  25. </view>
  26. </view>
  27. </view>
  28. </view>
  29. </view>
  30. </template>
  31. <script>
  32. export default {
  33. data() {
  34. return {
  35. //保存时间七天
  36. cacheTime:1*24*60*60*7,
  37. dialogShow: false,
  38. jscode:'',
  39. //邀请码
  40. inviteCode:'',
  41. userInfo:'',
  42. sessionKey:'',
  43. //获取手机号
  44. phoneShow:false
  45. };
  46. },
  47. beforeDestroy() {
  48. if(this.timer){
  49. clearTimeout(this.timer)
  50. this.timer = null
  51. }
  52. },
  53. methods:{
  54. show(){
  55. //获取邀请码
  56. this.inviteCode=this.$cache.get('inviteCode')
  57. this.dialogShow=true
  58. this.$mpi.wxLogin().then(res => {
  59. this.jscode = res.code
  60. })
  61. this.setTimer()
  62. },
  63. hide () {
  64. if(this.timer){
  65. clearTimeout(this.timer)
  66. this.timer = null
  67. }
  68. this.dialogShow=false;
  69. this.$emit('hide')
  70. },
  71. async setTimer(){
  72. let respWx = await this.$mpi.wxLogin()
  73. this.jscode=respWx.code
  74. // 每隔4分钟重新请求 jscode
  75. this.timer = setTimeout(()=>{
  76. this.setTimer()
  77. },240000)
  78. },
  79. async getuserinfo(e) {
  80. console.log("获取用户信息",e);
  81. if(e.detail.errMsg != 'getUserInfo:ok') {
  82. return
  83. }
  84. this.userInfo=e.detail.userInfo
  85. this.dialogShow=false
  86. try{
  87. this.respLogin = await this.$api.wxApp.getOpenId({
  88. code:this.jscode
  89. })
  90. let openId=this.respLogin.data.openid
  91. let unionid=this.respLogin.data.unionid || ''
  92. this.sessionKey=this.respLogin.data.session_key
  93. //通过openid查询数据库中该用户是否存在
  94. let params={
  95. nickName:this.userInfo.nickName,
  96. avatar:this.userInfo.avatarUrl,
  97. gender:this.userInfo.gender,
  98. unionid,
  99. openid:openId,
  100. province:this.userInfo.province,
  101. city:this.userInfo.city
  102. }
  103. //将openid
  104. let resp = await this.$api.loginUser.login(params)
  105. if (resp.success) {
  106. this.$u.toast('登录成功')
  107. //登录成功
  108. let obj={
  109. openId,
  110. sessionKey:this.sessionKey,
  111. userId:resp.data.id,
  112. phone:resp.data.phone
  113. }
  114. //将openid和sessionkey存进缓存中,有效时间为七天
  115. this.$cache.put("userInfo",obj)
  116. this.$u.vuex('vuex_userId',resp.data.id)
  117. if(resp.data.phone){
  118. this.$u.vuex('vuex_phone',resp.data.phone)
  119. }
  120. //移除邀请码
  121. this.$cache.remove('inviteCode')
  122. this.dialogShow=false
  123. this.$emit('signIn', resp)
  124. }else{
  125. uni.showToast({
  126. icon:"none",
  127. title:"登录失败"
  128. })
  129. }
  130. }catch(e){
  131. console.log(e);
  132. uni.showToast({
  133. icon:"none",
  134. title:"登录失败"
  135. })
  136. }finally{
  137. if(this.timer){
  138. clearTimeout(this.timer)
  139. this.setTimer()
  140. }
  141. }
  142. },
  143. clear(){
  144. return
  145. },
  146. //获取手机号
  147. showPhoneModal(){
  148. this.phoneShow=true
  149. },
  150. getphonenumber(e){
  151. this.$emit('getphonenumber')
  152. let params={
  153. sessionKey:this.sessionKey,
  154. encryptedData:e.detail.encryptedData,
  155. iv:e.detail.iv
  156. }
  157. this.$api.wxApp.getOpenData(params).then(res=>{
  158. if (res.success) {
  159. let obj=JSON.parse(res.data)
  160. let phone=obj.phoneNumber
  161. this.cachePhone(phone)
  162. }
  163. })
  164. },
  165. cachePhone(phone){
  166. let userInfo=this.$cache.get('userInfo')
  167. let params={
  168. id:userInfo.userId,
  169. phone
  170. }
  171. this.$api.loginUser.submit(params).then(res=>{
  172. if (res.success) {
  173. userInfo.phone=phone
  174. this.$cache.put('userInfo',userInfo)
  175. this.$u.vuex('vuex_phone',phone)
  176. }
  177. })
  178. }
  179. }
  180. };
  181. </script>
  182. <style lang="scss">
  183. .popup_mask {
  184. position: fixed;
  185. bottom: 0;
  186. top: 0;
  187. left: 0;
  188. right: 0;
  189. background-color: rgba(0, 0, 0, 0.4);
  190. opacity: 1;
  191. z-index: 98;
  192. }
  193. .dt-login-wrap {
  194. position: fixed;
  195. border-radius: 16rpx;
  196. background: #ffffff;
  197. width: 560rpx;
  198. z-index: 99;
  199. bottom: 30%;
  200. left: 50%;
  201. margin-left: -280rpx;
  202. right: 0;
  203. text-align: center;
  204. .title {
  205. padding-top:40upx;
  206. font-size: 34upx;
  207. font-weight: bold;
  208. }
  209. .content{
  210. display: flex;
  211. justify-content: center;
  212. align-items: center;
  213. flex-direction: column;
  214. padding-top: 30rpx;
  215. padding-bottom: 150rpx;
  216. .userinfo-avatar {
  217. overflow:hidden;
  218. display: block;
  219. width: 140rpx;
  220. height: 140rpx;
  221. margin: 20rpx 20rpx 40rpx;
  222. border-radius: 50%;
  223. border: 2px solid #fff;
  224. }
  225. }
  226. .subtitle {
  227. color: #7e7e7e;
  228. font-size: 26upx;
  229. margin-top: 30rpx;
  230. }
  231. .btn-content{
  232. display: flex;
  233. width: 100%;
  234. border-radius: 0;
  235. border-top:1upx solid #ebebeb;
  236. button{
  237. border:none;
  238. width: 50%;
  239. font-size: 30rpx;
  240. background-color: #FFFFFF;
  241. color:#66656a;
  242. }
  243. button:first-child{
  244. border-right: 1rpx solid #ebebeb;
  245. border-radius: 0 0 0 18rpx;
  246. }
  247. button:last-child{
  248. color: #2f7ff5;
  249. border-radius: 0 0 18rpx 0;
  250. }
  251. }
  252. .btn-content button::after{
  253. border: none;
  254. }
  255. }
  256. </style>