mirror of
https://gitee.com/ShopeX/ECShopX_mobile-frontend
synced 2026-08-06 12:46:24 +08:00
[TBID:ECX-9542] chore: merge master changes for release
This commit is contained in:
@@ -158,6 +158,18 @@ export function getWxAuth(params) {
|
||||
return req.get(`/trustlogin/params`, params)
|
||||
}
|
||||
|
||||
export function getTrustLoginList(params = {}) {
|
||||
return req.get('/trustlogin/list', { version_tag: 'touch', ...params })
|
||||
}
|
||||
|
||||
export function socialLoginH5(params) {
|
||||
return req.post('/new_login', {
|
||||
...params,
|
||||
auth_type: 'social_oauth',
|
||||
version_tag: 'touch'
|
||||
})
|
||||
}
|
||||
|
||||
export function getIsNew(params) {
|
||||
return req.post(`/member/is_new`, params)
|
||||
}
|
||||
|
||||
@@ -461,6 +461,7 @@ const config = {
|
||||
'edit-password', //修改密码页面
|
||||
'bindPhone', //绑定手机页面
|
||||
'auth-loading', //授权加载页
|
||||
'auth-social-loading', //第三方 OAuth 回调页
|
||||
'forgotpwd', //找回密码页面
|
||||
'forgotpwd-email', //邮箱找回密码(发送重置邮件)
|
||||
'email-activate', //邮箱注册激活落地页
|
||||
|
||||
@@ -74,13 +74,14 @@ export default class SpSearchBar extends Component {
|
||||
}
|
||||
|
||||
handleConfirm = (e) => {
|
||||
e.preventDefault && e.preventDefault()
|
||||
e.stopPropagation && e.stopPropagation()
|
||||
const keywords = e.detail.value.trim()
|
||||
e?.preventDefault?.()
|
||||
e?.stopPropagation?.()
|
||||
const raw = typeof e === 'string' ? e : e?.detail?.value
|
||||
const keywords = (raw == null ? '' : String(raw)).trim()
|
||||
if (keywords) {
|
||||
const value = Taro.getStorageSync(this.props.localStorageKey)
|
||||
let defaultValue = []
|
||||
if (value) {
|
||||
if (value && typeof value === 'string') {
|
||||
const array = value.split(',')
|
||||
if (!array.includes(keywords)) {
|
||||
array.unshift(keywords)
|
||||
@@ -90,8 +91,9 @@ export default class SpSearchBar extends Component {
|
||||
defaultValue.push(keywords)
|
||||
}
|
||||
Taro.setStorage({ key: this.props.localStorageKey, data: defaultValue.toString() })
|
||||
this.props.onConfirm(e.detail.value)
|
||||
}
|
||||
// 空关键词也要回调,便于清空搜索后重新拉全量列表
|
||||
this.props.onConfirm(keywords)
|
||||
this.setState({
|
||||
showSearchDailog: false,
|
||||
isShowAction: false
|
||||
|
||||
1
src/subpages/auth/assets/oauth/apple.svg
Normal file
1
src/subpages/auth/assets/oauth/apple.svg
Normal file
@@ -0,0 +1 @@
|
||||
<svg role="img" viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg"><title>Apple</title><path d="M12.152 6.896c-.948 0-2.415-1.078-3.96-1.04-2.04.027-3.91 1.183-4.961 3.014-2.117 3.675-.546 9.103 1.519 12.09 1.013 1.454 2.208 3.09 3.792 3.039 1.52-.065 2.09-.987 3.935-.987 1.831 0 2.35.987 3.96.948 1.637-.026 2.676-1.48 3.676-2.948 1.156-1.688 1.636-3.325 1.662-3.415-.039-.013-3.182-1.221-3.22-4.857-.026-3.04 2.48-4.494 2.597-4.559-1.429-2.09-3.623-2.324-4.39-2.376-2-.156-3.675 1.09-4.61 1.09zM15.53 3.83c.843-1.012 1.4-2.427 1.245-3.83-1.207.052-2.662.805-3.532 1.818-.78.896-1.454 2.338-1.273 3.714 1.338.104 2.715-.688 3.559-1.701" fill="#000"/></svg>
|
||||
|
After Width: | Height: | Size: 663 B |
4
src/subpages/auth/assets/oauth/facebook.svg
Normal file
4
src/subpages/auth/assets/oauth/facebook.svg
Normal file
@@ -0,0 +1,4 @@
|
||||
<svg width="32" height="32" viewBox="0 0 32 32" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="16" cy="16" r="16" fill="#1877F2"/>
|
||||
<path d="M17.6719 17.5H19.75L20.5 14H17.6719V12.25C17.6719 11.56 17.6719 11 18.8906 11H20.5V8H18.1406C15.3906 8 14 9.26 14 11.87V14H11.75V17.5H14V25H17.6719V17.5Z" fill="white"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 330 B |
6
src/subpages/auth/assets/oauth/google.svg
Normal file
6
src/subpages/auth/assets/oauth/google.svg
Normal file
@@ -0,0 +1,6 @@
|
||||
<svg width="32" height="32" viewBox="0 0 32 32" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M30.0014 16.3109C30.0014 15.1598 29.9061 14.3198 29.6998 13.4487H16.2871V18.6442H24.1601C24.0014 19.9354 23.1442 21.8798 21.2394 23.1864L21.2127 23.3604L25.4536 26.58L25.7474 26.6087C28.4458 24.1665 30.0014 20.5731 30.0014 16.3109Z" fill="#4285F4"/>
|
||||
<path d="M16.2862 30C20.1433 30 23.3814 28.7555 25.7465 26.6089L21.2386 23.1865C20.0322 24.011 18.4132 24.5866 16.2862 24.5866C12.5085 24.5866 9.30219 22.1444 8.15923 18.7688L7.9917 18.7827L3.58202 22.1272L3.52435 22.2843C5.87353 26.8577 10.6989 30 16.2862 30Z" fill="#34A853"/>
|
||||
<path d="M8.16007 18.7688C7.85848 17.8977 7.68395 16.9643 7.68395 15.9999C7.68395 15.0354 7.85849 14.1021 8.1442 13.231L8.13621 13.0455L3.67126 9.64734L3.52518 9.71544C2.55696 11.6132 2.0014 13.7444 2.0014 15.9999C2.0014 18.2555 2.55696 20.3865 3.52518 22.2843L8.16007 18.7688Z" fill="#FBBC05"/>
|
||||
<path d="M16.2863 7.4133C18.9688 7.4133 20.7783 8.54885 21.8101 9.4978L25.8418 5.64C23.3657 3.38445 20.1434 2 16.2863 2C10.699 2 5.87354 5.1422 3.52435 9.71549L8.14339 13.2311C9.30223 9.85555 12.5086 7.4133 16.2863 7.4133Z" fill="#EB4335"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 1.2 KiB |
7
src/subpages/auth/assets/oauth/line.svg
Normal file
7
src/subpages/auth/assets/oauth/line.svg
Normal file
@@ -0,0 +1,7 @@
|
||||
<svg width="32" height="32" viewBox="0 0 32 32" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M30 14.4979C30 8.15789 23.7199 2.99997 15.9999 2.99997C8.28094 2.99997 2 8.15789 2 14.4979C2 20.1816 6.98063 24.9416 13.7084 25.8418C14.1644 25.9412 14.7849 26.146 14.9419 26.5403C15.0831 26.8986 15.0342 27.4598 14.987 27.8215C14.987 27.8215 14.8227 28.8213 14.7873 29.0343C14.7264 29.3925 14.5061 30.4353 15.9999 29.7981C17.4942 29.1609 24.0626 24.9935 26.9998 21.572C29.0287 19.3203 30 17.0353 30 14.4979Z" fill="#2CCF54"/>
|
||||
<path d="M13.1555 11.4244H12.1735C12.0229 11.4244 11.9005 11.5478 11.9005 11.6995V17.866C11.9005 18.0179 12.0229 18.1411 12.1735 18.1411H13.1555C13.306 18.1411 13.4281 18.0179 13.4281 17.866V11.6995C13.4281 11.5478 13.306 11.4244 13.1555 11.4244Z" fill="white"/>
|
||||
<path d="M19.9146 11.4244H18.9326C18.7821 11.4244 18.66 11.5478 18.66 11.6995V15.3631L15.8645 11.5467C15.8128 11.4683 15.7289 11.4295 15.6374 11.4244H14.6557C14.5051 11.4244 14.3828 11.5478 14.3828 11.6995V17.866C14.3828 18.0179 14.5051 18.1411 14.6557 18.1411H15.6374C15.7883 18.1411 15.9104 18.0179 15.9104 17.866V14.2035L18.7093 18.0247C18.7596 18.0967 18.8449 18.1411 18.9326 18.1411H19.9146C20.0655 18.1411 20.1873 18.0179 20.1873 17.866V11.6995C20.1873 11.5478 20.0655 11.4244 19.9146 11.4244Z" fill="white"/>
|
||||
<path d="M10.7883 16.597H8.12004V11.6999C8.12004 11.5477 7.99793 11.4242 7.84764 11.4242H6.86536C6.7148 11.4242 6.59268 11.5477 6.59268 11.6999V17.8653C6.59268 18.015 6.71426 18.1412 6.86509 18.1412H10.7883C10.9389 18.1412 11.0604 18.0175 11.0604 17.8653V16.8727C11.0604 16.7205 10.9389 16.597 10.7883 16.597Z" fill="white"/>
|
||||
<path d="M25.3376 12.9684C25.4882 12.9684 25.6097 12.8453 25.6097 12.6928V11.7001C25.6097 11.5479 25.4882 11.4242 25.3376 11.4242H21.4147C21.264 11.4242 21.142 11.5502 21.142 11.6999V17.8656C21.142 18.0148 21.2637 18.1412 21.4141 18.1412H25.3376C25.4882 18.1412 25.6097 18.0175 25.6097 17.8656V16.8727C25.6097 16.7207 25.4882 16.597 25.3376 16.597H22.6696V15.5547H25.3376C25.4882 15.5547 25.6097 15.4313 25.6097 15.2791V14.2864C25.6097 14.1342 25.4882 14.0105 25.3376 14.0105H22.6696V12.9684H25.3376Z" fill="white"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 2.1 KiB |
78
src/subpages/auth/auth-social-loading.js
Normal file
78
src/subpages/auth/auth-social-loading.js
Normal file
@@ -0,0 +1,78 @@
|
||||
/**
|
||||
* Copyright © ShopeX (http://www.shopex.cn). All rights reserved.
|
||||
* See LICENSE file for license details.
|
||||
*/
|
||||
import React, { useEffect } from 'react'
|
||||
import Taro, { getCurrentInstance } from '@tarojs/taro'
|
||||
import { SpPage, SpLoading } from '@/components'
|
||||
import { classNames } from '@/utils'
|
||||
import api from '@/api'
|
||||
import { useLogin } from '@/hooks'
|
||||
import { useTranslation, $t } from '@/i18n'
|
||||
import { setTokenAndRedirect, getToken, normalizeAuthRedirectParam } from './util'
|
||||
import './auth-social-loading.scss'
|
||||
|
||||
const AuthSocialLoading = () => {
|
||||
const { i18n } = useTranslation()
|
||||
const $instance = getCurrentInstance() || {}
|
||||
|
||||
useEffect(() => {
|
||||
Taro.setNavigationBarTitle({ title: $t('fd477850.88bdcf') })
|
||||
const onLang = () => Taro.setNavigationBarTitle({ title: $t('fd477850.88bdcf') })
|
||||
i18n.on('languageChanged', onLang)
|
||||
return () => i18n.off('languageChanged', onLang)
|
||||
}, [i18n])
|
||||
|
||||
const {
|
||||
params: { code, trustlogin_tag, redi_url: rediUrlParam }
|
||||
} = $instance?.router || { params: {} }
|
||||
|
||||
const redi_url =
|
||||
rediUrlParam ||
|
||||
(typeof sessionStorage !== 'undefined'
|
||||
? sessionStorage.getItem('ecx_social_oauth_redi_url') || ''
|
||||
: '')
|
||||
|
||||
const oauthCode = normalizeAuthRedirectParam(code)
|
||||
|
||||
const { getUserInfo } = useLogin()
|
||||
|
||||
const handleLogin = async () => {
|
||||
const { token } = await api.wx.socialLoginH5({
|
||||
code: oauthCode,
|
||||
trustlogin_tag,
|
||||
auth_type: 'social_oauth'
|
||||
})
|
||||
|
||||
setTokenAndRedirect(token, async () => {
|
||||
await getUserInfo()
|
||||
}, { rediUrl: redi_url })
|
||||
|
||||
try {
|
||||
sessionStorage.removeItem('ecx_social_oauth_redi_url')
|
||||
} catch (e) {
|
||||
// ignore
|
||||
}
|
||||
}
|
||||
|
||||
useEffect(() => {
|
||||
const token = getToken()
|
||||
if (token) {
|
||||
setTokenAndRedirect(token)
|
||||
return
|
||||
}
|
||||
if (!oauthCode || !trustlogin_tag) {
|
||||
Taro.showToast({ title: $t('bf3f9cd5.26b5bd'), icon: 'none' })
|
||||
return
|
||||
}
|
||||
handleLogin()
|
||||
}, [])
|
||||
|
||||
return (
|
||||
<SpPage className={classNames('page-auth-social-loading')}>
|
||||
<SpLoading>{$t('bf3f9cd5.26b5bd')}</SpLoading>
|
||||
</SpPage>
|
||||
)
|
||||
}
|
||||
|
||||
export default AuthSocialLoading
|
||||
7
src/subpages/auth/auth-social-loading.scss
Normal file
7
src/subpages/auth/auth-social-loading.scss
Normal file
@@ -0,0 +1,7 @@
|
||||
/**
|
||||
* Copyright © ShopeX (http://www.shopex.cn). All rights reserved.
|
||||
* See LICENSE file for license details.
|
||||
*/
|
||||
.page-auth-social-loading {
|
||||
min-height: 100vh;
|
||||
}
|
||||
@@ -38,7 +38,7 @@ const PageBindPhone = () => {
|
||||
return () => i18n.off('languageChanged', onLang)
|
||||
}, [i18n])
|
||||
const {
|
||||
params: { unionid, redi_url }
|
||||
params: { unionid, redi_url, user_type, trustlogin_tag }
|
||||
} = $instance?.router
|
||||
|
||||
const { getUserInfo } = useLogin()
|
||||
@@ -96,7 +96,8 @@ const PageBindPhone = () => {
|
||||
username,
|
||||
check_type,
|
||||
vcode,
|
||||
union_id: unionid
|
||||
union_id: unionid,
|
||||
user_type: user_type || trustlogin_tag || 'wechat'
|
||||
})
|
||||
const { is_new } = tokenParseH5(token)
|
||||
|
||||
|
||||
@@ -2,43 +2,145 @@
|
||||
* Copyright © ShopeX (http://www.shopex.cn). All rights reserved.
|
||||
* See LICENSE file for license details.
|
||||
*/
|
||||
import React from 'react'
|
||||
import React, { useEffect, useMemo, useState } from 'react'
|
||||
import Taro, { getCurrentInstance } from '@tarojs/taro'
|
||||
import { View, Text } from '@tarojs/components'
|
||||
import { View, Text, Image } from '@tarojs/components'
|
||||
import { isWxWeb } from '@/utils'
|
||||
import api from '@/api'
|
||||
import { useTranslation, $t } from '@/i18n'
|
||||
import './comp-otherlogin.scss'
|
||||
|
||||
import googleIcon from '../assets/oauth/google.svg'
|
||||
import appleIcon from '../assets/oauth/apple.svg'
|
||||
import facebookIcon from '../assets/oauth/facebook.svg'
|
||||
import lineIcon from '../assets/oauth/line.svg'
|
||||
|
||||
const OAUTH_ICONS = {
|
||||
google: googleIcon,
|
||||
apple: appleIcon,
|
||||
facebook: facebookIcon,
|
||||
line: lineIcon
|
||||
}
|
||||
|
||||
const OAUTH_LABEL_KEYS = {
|
||||
google: 'e7a49201.a1b2c3',
|
||||
apple: 'e7a49201.d4e5f6',
|
||||
facebook: 'e7a49201.g7h8i9',
|
||||
line: 'e7a49201.j0k1l2',
|
||||
weixin: 'e7a49201.p6q7r8'
|
||||
}
|
||||
|
||||
const PROVIDER_ORDER = ['google', 'apple', 'facebook', 'line', 'weixin']
|
||||
|
||||
const isEnabled = (row) => row && (row.status === true || row.status === 'true' || row.status === 1)
|
||||
|
||||
const SOCIAL_OAUTH_REDI_KEY = 'ecx_social_oauth_redi_url'
|
||||
|
||||
const CompOtherLogin = () => {
|
||||
useTranslation()
|
||||
const handleClickWexin = async () => {
|
||||
const [providers, setProviders] = useState([])
|
||||
|
||||
useEffect(() => {
|
||||
const loadProviders = async () => {
|
||||
try {
|
||||
const list = await api.wx.getTrustLoginList({ version_tag: 'touch' })
|
||||
const rows = Array.isArray(list) ? list : []
|
||||
setProviders(rows.filter(isEnabled))
|
||||
} catch (e) {
|
||||
setProviders([])
|
||||
}
|
||||
}
|
||||
loadProviders()
|
||||
}, [])
|
||||
|
||||
const handleClickProvider = async (row) => {
|
||||
const $instance = getCurrentInstance() || {}
|
||||
//跳转
|
||||
const { redirect = '' } = $instance?.router?.params
|
||||
const { redirect = '' } = $instance?.router?.params || {}
|
||||
const redirectUrl =
|
||||
!!redirect && redirect !== 'undefined' ? redirect : process.env.APP_HOME_PAGE
|
||||
let { oauth_url = '' } = await api.wx.getWxAuth({
|
||||
|
||||
if (row.type === 'weixin') {
|
||||
const { oauth_url = '' } = await api.wx.getWxAuth({
|
||||
redirect_url: redirectUrl,
|
||||
trustlogin_tag: 'weixin',
|
||||
version_tag: 'touch'
|
||||
})
|
||||
if (oauth_url) {
|
||||
window.location.replace(oauth_url)
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
const { oauth_url = '' } = await api.wx.getWxAuth({
|
||||
redirect_url: redirectUrl,
|
||||
trustlogin_tag: 'weixin',
|
||||
trustlogin_tag: row.type,
|
||||
version_tag: 'touch'
|
||||
})
|
||||
if (oauth_url) {
|
||||
try {
|
||||
sessionStorage.setItem(SOCIAL_OAUTH_REDI_KEY, redirectUrl || '')
|
||||
} catch (e) {
|
||||
// ignore
|
||||
}
|
||||
window.location.replace(oauth_url)
|
||||
}
|
||||
}
|
||||
|
||||
if (!isWxWeb) {
|
||||
const visibleProviders = useMemo(() => {
|
||||
const filtered = providers.filter((row) => {
|
||||
if (row.type === 'weixin') {
|
||||
return isWxWeb
|
||||
}
|
||||
return PROVIDER_ORDER.includes(row.type)
|
||||
})
|
||||
return filtered.sort(
|
||||
(a, b) => PROVIDER_ORDER.indexOf(a.type) - PROVIDER_ORDER.indexOf(b.type)
|
||||
)
|
||||
}, [providers])
|
||||
|
||||
if (!visibleProviders.length) {
|
||||
return null
|
||||
}
|
||||
|
||||
return (
|
||||
<View className='comp-other-login'>
|
||||
<View className='text'>{$t('8c3959b3.c4a461')}</View>
|
||||
<View className='loginway'>
|
||||
<View className='wechat' onClick={handleClickWexin}>
|
||||
<Text className='iconfont icon-weixin'></Text>
|
||||
</View>
|
||||
<View className='comp-other-login' data-testid='auth-other-login-list'>
|
||||
<View className='oauth-divider'>
|
||||
<View className='oauth-divider__line' />
|
||||
<Text className='oauth-divider__text'>{$t('e7a49201.m3n4o5')}</Text>
|
||||
<View className='oauth-divider__line' />
|
||||
</View>
|
||||
<View className='oauth-buttons'>
|
||||
{visibleProviders.map((row) => {
|
||||
const isWeixin = row.type === 'weixin'
|
||||
const labelKey = OAUTH_LABEL_KEYS[row.type]
|
||||
const label = labelKey ? $t(labelKey) : row.name || row.type
|
||||
|
||||
return (
|
||||
<View
|
||||
key={row.type}
|
||||
className={`oauth-button oauth-button--${row.type}`}
|
||||
data-testid={
|
||||
row.type === 'google'
|
||||
? 'auth-other-login-google'
|
||||
: `auth-other-login-${row.type}`
|
||||
}
|
||||
onClick={() => handleClickProvider(row)}
|
||||
>
|
||||
<View className='oauth-button__icon-wrap'>
|
||||
{isWeixin ? (
|
||||
<Text className='iconfont icon-weixin oauth-button__wechat-icon' />
|
||||
) : (
|
||||
<Image
|
||||
className='oauth-button__icon'
|
||||
src={OAUTH_ICONS[row.type]}
|
||||
mode='aspectFit'
|
||||
/>
|
||||
)}
|
||||
</View>
|
||||
<Text className='oauth-button__label'>{label}</Text>
|
||||
</View>
|
||||
)
|
||||
})}
|
||||
</View>
|
||||
</View>
|
||||
)
|
||||
|
||||
@@ -3,33 +3,82 @@
|
||||
* See LICENSE file for license details.
|
||||
*/
|
||||
.comp-other-login {
|
||||
position: relative;
|
||||
border-top: 1px solid rgba(0, 0, 0, 0.1);
|
||||
margin-top: 10px;
|
||||
.text {
|
||||
color: rgba(197, 202, 213, 1);
|
||||
font-size: 26px;
|
||||
position: relative;
|
||||
margin: -18px auto 0;
|
||||
background-color: white;
|
||||
width: 200px;
|
||||
width: 100%;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
|
||||
.oauth-divider {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 24px;
|
||||
margin: 48px 0 32px;
|
||||
|
||||
&__line {
|
||||
flex: 1;
|
||||
height: 1px;
|
||||
background: #e2e4ea;
|
||||
}
|
||||
|
||||
&__text {
|
||||
flex-shrink: 0;
|
||||
font-size: 26px;
|
||||
line-height: 1;
|
||||
color: #858b9c;
|
||||
}
|
||||
}
|
||||
.loginway {
|
||||
padding: 24px 0 10px 0;
|
||||
@include flex-center();
|
||||
|
||||
.wechat {
|
||||
width: 90px;
|
||||
height: 90px;
|
||||
border: 1px solid #c5cad5;
|
||||
border-radius: 50%;
|
||||
color: rgba(0, 200, 0, 1);
|
||||
.oauth-buttons {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 20px;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
@include flex-center();
|
||||
.oauth-button {
|
||||
position: relative;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
width: 100%;
|
||||
min-height: 96px;
|
||||
padding: 0 32px;
|
||||
border: 1px solid #111a34;
|
||||
border-radius: 4px;
|
||||
background: #fff;
|
||||
box-sizing: border-box;
|
||||
|
||||
.icon-weixin {
|
||||
font-size: 40px;
|
||||
}
|
||||
&__icon-wrap {
|
||||
position: absolute;
|
||||
left: 32px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
&__icon {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
}
|
||||
|
||||
&__wechat-icon {
|
||||
font-size: 40px;
|
||||
color: #00c800;
|
||||
line-height: 1;
|
||||
}
|
||||
|
||||
&__label {
|
||||
font-size: 28px;
|
||||
line-height: 1.3;
|
||||
color: #111a34;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
&--weixin .oauth-button__label {
|
||||
padding-left: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -195,11 +195,13 @@ $border-color: #e2e4ea;
|
||||
}
|
||||
}
|
||||
.other-login {
|
||||
margin-top: 100px;
|
||||
margin-top: 48px;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
text-align: center;
|
||||
width: 100%;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -53,7 +53,7 @@ function getRedirectUrl() {}
|
||||
// options.forceMemberCenter:注册成功等场景固定进会员中心,忽略 redi_url / redirect
|
||||
async function setTokenAndRedirect(token = '', tokenSetSuccessCallback, options) {
|
||||
const opts = typeof options === 'object' && options !== null ? options : {}
|
||||
const { forceMemberCenter = false } = opts
|
||||
const { forceMemberCenter = false, rediUrl: optsRediUrl } = opts
|
||||
|
||||
const hasToken = setToken(token)
|
||||
|
||||
@@ -64,6 +64,8 @@ async function setTokenAndRedirect(token = '', tokenSetSuccessCallback, options)
|
||||
const { redi_url, redirect } = router?.params || {}
|
||||
const url = forceMemberCenter
|
||||
? '/subpages/member/index'
|
||||
: optsRediUrl
|
||||
? normalizeAuthRedirectParam(optsRediUrl)
|
||||
: redi_url
|
||||
? normalizeAuthRedirectParam(redi_url)
|
||||
: redirect
|
||||
|
||||
@@ -1556,6 +1556,12 @@
|
||||
"bf3f9cd5.26b5bd": "جارٍ التحميل...",
|
||||
"fd477850.88bdcf": "جارٍ تسجيل الدخول...",
|
||||
"8c3959b3.c4a461": "طرق تسجيل الدخول الأخرى",
|
||||
"e7a49201.m3n4o5": "أو",
|
||||
"e7a49201.a1b2c3": "تسجيل الدخول بحساب Google",
|
||||
"e7a49201.d4e5f6": "تسجيل الدخول باستخدام Apple ID",
|
||||
"e7a49201.g7h8i9": "تسجيل الدخول بحساب Facebook",
|
||||
"e7a49201.j0k1l2": "تسجيل الدخول باستخدام LINE",
|
||||
"e7a49201.p6q7r8": "تسجيل الدخول باستخدام WeChat",
|
||||
"24f4b47f.c4d0c8": "يجب أن تتكون كلمة المرور من 6–16 رقمًا أو حرفًا",
|
||||
"70e510e9.787a47": "يرجى إدخال رقم جوالك",
|
||||
"70e510e9.1fb0b4": "رقم الجوال هذا غير مسجل",
|
||||
|
||||
@@ -1556,6 +1556,12 @@
|
||||
"bf3f9cd5.26b5bd": "Loading...",
|
||||
"fd477850.88bdcf": "Logging in...",
|
||||
"8c3959b3.c4a461": "Other sign-in methods",
|
||||
"e7a49201.m3n4o5": "Or",
|
||||
"e7a49201.a1b2c3": "Log in with Google",
|
||||
"e7a49201.d4e5f6": "Log in with Apple ID",
|
||||
"e7a49201.g7h8i9": "Log in with Facebook",
|
||||
"e7a49201.j0k1l2": "Log in with LINE",
|
||||
"e7a49201.p6q7r8": "Log in with WeChat",
|
||||
"24f4b47f.c4d0c8": "Password must be 6–16 digits or letters",
|
||||
"70e510e9.787a47": "Please enter your mobile number",
|
||||
"70e510e9.1fb0b4": "This mobile number is not registered",
|
||||
|
||||
@@ -1560,6 +1560,12 @@
|
||||
"bf3f9cd5.26b5bd": "加载中...",
|
||||
"fd477850.88bdcf": "登陆中...",
|
||||
"8c3959b3.c4a461": "其它方式登录",
|
||||
"e7a49201.m3n4o5": "或",
|
||||
"e7a49201.a1b2c3": "使用 Google 帐户登录",
|
||||
"e7a49201.d4e5f6": "用 Apple ID 登录",
|
||||
"e7a49201.g7h8i9": "用 Facebook 帐户登录",
|
||||
"e7a49201.j0k1l2": "用 LINE 登录",
|
||||
"e7a49201.p6q7r8": "使用微信登录",
|
||||
"24f4b47f.c4d0c8": "密码需由6-16位数字或字母组成",
|
||||
"70e510e9.787a47": "请输入您的手机号码",
|
||||
"70e510e9.1fb0b4": "该手机号码未注册",
|
||||
|
||||
@@ -1559,6 +1559,12 @@
|
||||
"bf3f9cd5.26b5bd": "加載中...",
|
||||
"fd477850.88bdcf": "登陸中...",
|
||||
"8c3959b3.c4a461": "其它方式登錄",
|
||||
"e7a49201.m3n4o5": "或",
|
||||
"e7a49201.a1b2c3": "使用 Google 帳戶登入",
|
||||
"e7a49201.d4e5f6": "用 Apple ID 登入",
|
||||
"e7a49201.g7h8i9": "用 Facebook 帳戶登入",
|
||||
"e7a49201.j0k1l2": "用 LINE 登入",
|
||||
"e7a49201.p6q7r8": "使用微信登入",
|
||||
"24f4b47f.c4d0c8": "密碼需由6-16位數字或字母組成",
|
||||
"70e510e9.787a47": "請輸入您的手機號碼",
|
||||
"70e510e9.1fb0b4": "該手機號碼未註冊",
|
||||
|
||||
@@ -28,12 +28,17 @@ function CompNoteItem(props) {
|
||||
const { userInfo = {} } = useSelector((state) => state.user)
|
||||
|
||||
useEffect(() => {
|
||||
if (!info) return
|
||||
setState((draft) => {
|
||||
draft.likes = info.likes
|
||||
draft.likeStatus = info.likeStatus
|
||||
})
|
||||
}, [info])
|
||||
|
||||
if (!info) {
|
||||
return null
|
||||
}
|
||||
|
||||
const handleClick = () => {
|
||||
const { postId, status } = info
|
||||
if (status != '4') {
|
||||
@@ -62,7 +67,7 @@ function CompNoteItem(props) {
|
||||
return (
|
||||
<View className='comp-note-item'>
|
||||
<View className='badges-list'>
|
||||
{info.badges.map((item, index) => (
|
||||
{(info?.badges || []).map((item, index) => (
|
||||
<View className='badge-item' key={`badge-item__${index}`}>
|
||||
{item.badge_name}
|
||||
</View>
|
||||
|
||||
@@ -26,6 +26,7 @@ function UgcIndex() {
|
||||
)
|
||||
const initialState = {
|
||||
keyword: '',
|
||||
searchKeyword: '',
|
||||
tagsList: [],
|
||||
curTagIndex: 0,
|
||||
curFilterIndex: 0,
|
||||
@@ -34,8 +35,11 @@ function UgcIndex() {
|
||||
footerHeight: 0
|
||||
}
|
||||
const [state, setState] = useImmer(initialState)
|
||||
const { keyword, tagsList, curTagIndex, curFilterIndex, leftList, rightList } = state
|
||||
const { keyword, searchKeyword, tagsList, curTagIndex, curFilterIndex, leftList, rightList } =
|
||||
state
|
||||
const listRef = useRef()
|
||||
const searchKeywordRef = useRef('')
|
||||
searchKeywordRef.current = searchKeyword
|
||||
|
||||
useEffect(() => {
|
||||
Taro.setNavigationBarTitle({ title: $t('d668d0e3.888af1') })
|
||||
@@ -57,9 +61,9 @@ function UgcIndex() {
|
||||
|
||||
useEffect(() => {
|
||||
if (tagsList.length > 0) {
|
||||
listRef.current.reset()
|
||||
listRef.current?.reset()
|
||||
}
|
||||
}, [curTagIndex, keyword, curFilterIndex, tagsList])
|
||||
}, [curTagIndex, curFilterIndex, tagsList, searchKeyword])
|
||||
|
||||
// useEffect(() => {
|
||||
// getUgcList()
|
||||
@@ -88,66 +92,70 @@ function UgcIndex() {
|
||||
// 列表
|
||||
const fetch = async ({ pageIndex, pageSize }) => {
|
||||
Taro.showLoading()
|
||||
let params = {
|
||||
page: pageIndex,
|
||||
pageSize,
|
||||
sort: curFilterIndex == 0 ? 'likes desc' : 'created desc',
|
||||
content: keyword
|
||||
try {
|
||||
let params = {
|
||||
page: pageIndex,
|
||||
pageSize,
|
||||
sort: curFilterIndex == 0 ? 'likes desc' : 'created desc'
|
||||
}
|
||||
const keyword = (searchKeywordRef.current || '').trim()
|
||||
if (keyword) {
|
||||
params.content = keyword
|
||||
}
|
||||
|
||||
if (tagsList.length > 0 && tagsList[curTagIndex]) {
|
||||
params = {
|
||||
...params,
|
||||
topics: [tagsList[curTagIndex].tag_id]
|
||||
}
|
||||
}
|
||||
|
||||
const res = (await mdugcApi.postlist(params)) || {}
|
||||
const list = Array.isArray(res.list) ? res.list : []
|
||||
const total = res.total_count
|
||||
|
||||
let nList = pickBy(list, mdugcDoc.UGC_LIST)
|
||||
|
||||
const resLeftList = nList.filter((item, index) => index % 2 == 0)
|
||||
const resRightList = nList.filter((item, index) => index % 2 == 1)
|
||||
|
||||
setState((draft) => {
|
||||
if (pageIndex === 1) {
|
||||
draft.leftList = [resLeftList]
|
||||
draft.rightList = [resRightList]
|
||||
} else {
|
||||
draft.leftList[pageIndex - 1] = resLeftList
|
||||
draft.rightList[pageIndex - 1] = resRightList
|
||||
}
|
||||
})
|
||||
|
||||
return { total: total || 0 }
|
||||
} finally {
|
||||
Taro.hideLoading()
|
||||
}
|
||||
|
||||
if (tagsList.length > 0) {
|
||||
params = {
|
||||
...params,
|
||||
topics: [tagsList[curTagIndex].tag_id]
|
||||
}
|
||||
}
|
||||
|
||||
const { list, total_count: total } = await mdugcApi.postlist(params)
|
||||
|
||||
let nList = pickBy(list, mdugcDoc.UGC_LIST)
|
||||
|
||||
const resLeftList = nList.filter((item, index) => {
|
||||
if (index % 2 == 0) {
|
||||
return item
|
||||
}
|
||||
})
|
||||
const resRightList = nList.filter((item, index) => {
|
||||
if (index % 2 == 1) {
|
||||
return item
|
||||
}
|
||||
})
|
||||
|
||||
setState((draft) => {
|
||||
draft.leftList[pageIndex - 1] = resLeftList
|
||||
draft.rightList[pageIndex - 1] = resRightList
|
||||
})
|
||||
Taro.hideLoading()
|
||||
|
||||
return { total: total || 0 }
|
||||
}
|
||||
|
||||
const handleOnClear = async () => {
|
||||
await setState((draft) => {
|
||||
draft.keyword = ''
|
||||
const refreshBySearch = (val = '') => {
|
||||
const nextKeyword = typeof val === 'string' ? val : ''
|
||||
searchKeywordRef.current = nextKeyword
|
||||
setState((draft) => {
|
||||
draft.keyword = nextKeyword
|
||||
draft.searchKeyword = nextKeyword
|
||||
draft.leftList = []
|
||||
draft.rightList = []
|
||||
})
|
||||
}
|
||||
|
||||
const handleOnClear = () => {
|
||||
refreshBySearch('')
|
||||
}
|
||||
|
||||
const handleSearchCancel = () => {
|
||||
setState((draft) => {
|
||||
draft.keyword = ''
|
||||
draft.leftList = []
|
||||
draft.rightList = []
|
||||
})
|
||||
refreshBySearch('')
|
||||
}
|
||||
|
||||
const handleConfirm = async (val) => {
|
||||
setState((draft) => {
|
||||
draft.keyword = val
|
||||
draft.leftList = []
|
||||
draft.rightList = []
|
||||
})
|
||||
const handleConfirm = (val) => {
|
||||
refreshBySearch(val)
|
||||
}
|
||||
|
||||
const onChangeTag = (index, item) => {
|
||||
|
||||
Reference in New Issue
Block a user