Merge branch 'master' of http://git.bimwe.com/tennis/mini-programs
This commit is contained in:
@@ -1,5 +1,5 @@
|
||||
import React, { useState, useEffect } from "react";
|
||||
import Taro from "@tarojs/taro";
|
||||
import Taro, { useDidShow } from "@tarojs/taro";
|
||||
import { View, Text, Image, Button } from "@tarojs/components";
|
||||
import "./index.scss";
|
||||
|
||||
@@ -48,6 +48,7 @@ interface UserInfoCardProps {
|
||||
on_message?: () => void;
|
||||
on_share?: () => void;
|
||||
set_user_info?: (info: Partial<UserInfoType>) => void;
|
||||
onTab?: (tab) => void;
|
||||
}
|
||||
|
||||
// 处理编辑用户信息
|
||||
@@ -65,6 +66,7 @@ export const UserInfoCard: React.FC<UserInfoCardProps> = ({
|
||||
on_message,
|
||||
on_share,
|
||||
set_user_info,
|
||||
onTab,
|
||||
}) => {
|
||||
const { updateUserInfo } = useUserActions();
|
||||
console.log("UserInfoCard 用户信息:", user_info);
|
||||
@@ -78,9 +80,11 @@ export const UserInfoCard: React.FC<UserInfoCardProps> = ({
|
||||
useState(false);
|
||||
|
||||
// 表单状态
|
||||
const [form_data] = useState<Partial<UserInfoType>>({
|
||||
...user_info,
|
||||
});
|
||||
const [form_data, set_form_data] = useState<Partial<UserInfoType>>({});
|
||||
|
||||
useDidShow(() => {
|
||||
set_form_data({ ...user_info })
|
||||
})
|
||||
|
||||
// 职业数据
|
||||
const professions = useProfessions();
|
||||
@@ -181,6 +185,9 @@ export const UserInfoCard: React.FC<UserInfoCardProps> = ({
|
||||
!Array.isArray(field)
|
||||
) {
|
||||
await updateUserInfo({ ...field });
|
||||
set_form_data((prev) => {
|
||||
return { ...prev, ...field }
|
||||
})
|
||||
// 更新本地状态
|
||||
// setFormData((prev) => ({ ...prev, ...field }));
|
||||
// setUserInfo((prev) => ({ ...prev, ...field }));
|
||||
@@ -188,6 +195,9 @@ export const UserInfoCard: React.FC<UserInfoCardProps> = ({
|
||||
// 调用更新用户信息接口,只传递修改的字段
|
||||
const update_data = { [field as string]: value };
|
||||
await updateUserInfo(update_data);
|
||||
set_form_data((prev) => {
|
||||
return { ...prev, ...update_data }
|
||||
})
|
||||
// 更新本地状态
|
||||
// setFormData((prev) => ({ ...prev, [field as string]: value }));
|
||||
// setUserInfo((prev) => ({ ...prev, [field as string]: value }));
|
||||
@@ -323,13 +333,17 @@ export const UserInfoCard: React.FC<UserInfoCardProps> = ({
|
||||
</Text>
|
||||
<Text className="stat_label">粉丝</Text>
|
||||
</View>
|
||||
<View className="stat_item">
|
||||
<View className="stat_item clickable"
|
||||
onClick={() => onTab?.("hosted")}
|
||||
>
|
||||
<Text className="stat_number">
|
||||
{user_info.stats?.hosted_games_count || 0}
|
||||
</Text>
|
||||
<Text className="stat_label">主办</Text>
|
||||
</View>
|
||||
<View className="stat_item">
|
||||
<View className="stat_item clickable"
|
||||
onClick={() => onTab?.("participated")}
|
||||
>
|
||||
<Text className="stat_number">
|
||||
{user_info.stats?.participated_games_count || 0}
|
||||
</Text>
|
||||
@@ -384,12 +398,18 @@ export const UserInfoCard: React.FC<UserInfoCardProps> = ({
|
||||
<Image
|
||||
className="tag_icon"
|
||||
src={require("../../static/userInfo/male.svg")}
|
||||
onClick={() => {
|
||||
handle_open_edit_modal("gender");
|
||||
}}
|
||||
/>
|
||||
)}
|
||||
{user_info.gender === "1" && (
|
||||
<Image
|
||||
className="tag_icon"
|
||||
src={require("../../static/userInfo/female.svg")}
|
||||
onClick={() => {
|
||||
handle_open_edit_modal("gender");
|
||||
}}
|
||||
/>
|
||||
)}
|
||||
</View>
|
||||
@@ -404,7 +424,11 @@ export const UserInfoCard: React.FC<UserInfoCardProps> = ({
|
||||
</View>
|
||||
) : null}
|
||||
{user_info.ntrp_level !== "0" ? (
|
||||
<View className="tag_item">
|
||||
<View
|
||||
className="tag_item"
|
||||
onClick={() => {
|
||||
handle_open_edit_modal("ntrp_level");
|
||||
}}>
|
||||
<Text className="tag_text">{`NTRP ${user_info.ntrp_level}`}</Text>
|
||||
</View>
|
||||
) : is_current_user ? (
|
||||
@@ -418,7 +442,11 @@ export const UserInfoCard: React.FC<UserInfoCardProps> = ({
|
||||
</View>
|
||||
) : null}
|
||||
{user_info.occupation ? (
|
||||
<View className="tag_item">
|
||||
<View
|
||||
className="tag_item"
|
||||
onClick={() => {
|
||||
handle_open_edit_modal("occupation");
|
||||
}}>
|
||||
<Text className="tag_text">
|
||||
{user_info.occupation.split(" ")[2]}
|
||||
</Text>
|
||||
@@ -434,7 +462,9 @@ export const UserInfoCard: React.FC<UserInfoCardProps> = ({
|
||||
</View>
|
||||
) : null}
|
||||
{user_info.country || user_info.province || user_info.city ? (
|
||||
<View className="tag_item">
|
||||
<View
|
||||
className="tag_item"
|
||||
onClick={() => handle_open_edit_modal("location")}>
|
||||
<Text className="tag_text">{`${user_info.province}${user_info.city}`}</Text>
|
||||
</View>
|
||||
) : is_current_user ? (
|
||||
|
||||
@@ -30,4 +30,25 @@
|
||||
font-weight: 500;
|
||||
line-height: 24px;
|
||||
}
|
||||
|
||||
.collapse-btn {
|
||||
width: 100%;
|
||||
font-family: PingFang SC;
|
||||
font-weight: 400;
|
||||
font-style: Regular;
|
||||
font-size: 14px;
|
||||
letter-spacing: 0.38px;
|
||||
color: rgba(0, 0, 0, .3);
|
||||
height: 40px;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
Image {
|
||||
width: 16px;
|
||||
height: 16px;
|
||||
}
|
||||
&:not(.fold) Image {
|
||||
transform: rotate(180deg);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,4 +1,4 @@
|
||||
import { View } from "@tarojs/components";
|
||||
import { View, Text, Image } from "@tarojs/components";
|
||||
import ListCard from "@/components/ListCard";
|
||||
import ListLoadError from "@/components/ListLoadError";
|
||||
import ListCardSkeleton from "@/components/ListCardSkeleton";
|
||||
@@ -8,7 +8,7 @@ import { setStorage, getStorage } from "@/store/storage";
|
||||
import { NTRPTestEntryCard } from "@/components";
|
||||
import { EvaluateScene } from "@/store/evaluateStore";
|
||||
import "./index.scss";
|
||||
import { useRef, useEffect } from "react";
|
||||
import { useRef, useEffect, useState } from "react";
|
||||
|
||||
const ListContainer = (props) => {
|
||||
const {
|
||||
@@ -23,9 +23,14 @@ const ListContainer = (props) => {
|
||||
emptyText,
|
||||
btnText,
|
||||
btnImg,
|
||||
style,
|
||||
collapse = false,
|
||||
defaultShowNum,
|
||||
} = props;
|
||||
const timerRef = useRef<NodeJS.Timeout | null>(null);
|
||||
|
||||
const [showNumber, setShowNumber] = useState(0)
|
||||
|
||||
const userInfo = useUserInfo();
|
||||
|
||||
useReachBottom(() => {
|
||||
@@ -38,6 +43,14 @@ const ListContainer = (props) => {
|
||||
// }, 500);
|
||||
});
|
||||
|
||||
useEffect(() => {
|
||||
setShowNumber(
|
||||
() => {
|
||||
return defaultShowNum === undefined ? data?.length : defaultShowNum
|
||||
|
||||
})
|
||||
}, [data])
|
||||
|
||||
useEffect(() => {
|
||||
return () => {
|
||||
if (timerRef.current) {
|
||||
@@ -97,6 +110,8 @@ const ListContainer = (props) => {
|
||||
);
|
||||
}
|
||||
|
||||
showNumber !== undefined && (list = list.slice(0, showNumber))
|
||||
|
||||
// 渲染数据
|
||||
return (
|
||||
<>
|
||||
@@ -113,7 +128,7 @@ const ListContainer = (props) => {
|
||||
};
|
||||
|
||||
return (
|
||||
<View className="listContentWrapper">
|
||||
<View className="listContentWrapper" style={style}>
|
||||
{renderList(data)}
|
||||
{/* 显示骨架屏 */}
|
||||
{loading && renderSkeleton()}
|
||||
@@ -122,7 +137,20 @@ const ListContainer = (props) => {
|
||||
</View>
|
||||
{renderList(recommendList)} */}
|
||||
{/* 到底了 */}
|
||||
{data?.length > 0 && <View className="bottomTextWrapper">到底了</View>}
|
||||
{collapse ?
|
||||
data?.length > defaultShowNum ?
|
||||
data?.length > showNumber ?
|
||||
<View className="collapse-btn fold" onClick={() => { setShowNumber(data?.length) }}>
|
||||
<Text>更多球局</Text>
|
||||
<Image src={require("@/static/userInfo/fold.svg")}></Image>
|
||||
</View> :
|
||||
<View className="collapse-btn" onClick={() => { setShowNumber(defaultShowNum) }}>
|
||||
<Text>收起</Text>
|
||||
<Image src={require("@/static/userInfo/fold.svg")}></Image>
|
||||
</View>
|
||||
:
|
||||
null
|
||||
: data?.length > 0 && <View className="bottomTextWrapper">到底了</View>}
|
||||
</View>
|
||||
);
|
||||
};
|
||||
|
||||
4
src/static/userInfo/fold.svg
Normal file
4
src/static/userInfo/fold.svg
Normal file
@@ -0,0 +1,4 @@
|
||||
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M12 4L8 8L4 4" stroke="black" stroke-opacity="0.2" stroke-width="1.33333" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M12 8L8 12L4 8" stroke="black" stroke-opacity="0.2" stroke-width="1.33333" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 368 B |
@@ -219,10 +219,10 @@ const DownloadBill: React.FC = () => {
|
||||
transaction_sub_type,
|
||||
date_range,
|
||||
});
|
||||
const { bill_example, fileName } = res.data;
|
||||
const { fileUrl, fileName } = res.data;
|
||||
// 调用下载文件接口
|
||||
wx.downloadFile({
|
||||
url: bill_example, // 文件路径
|
||||
url: fileUrl, // 文件路径
|
||||
success: function (res) {
|
||||
// 只有200状态码表示下载成功
|
||||
if (res.statusCode === 200) {
|
||||
|
||||
@@ -170,9 +170,14 @@ const MyselfPage: React.FC = () => {
|
||||
const handle_wallet = () => {
|
||||
Taro.navigateTo({
|
||||
url: "/user_pages/wallet/index",
|
||||
// url: "/user_pages/other/index?userid=16"
|
||||
});
|
||||
};
|
||||
|
||||
const handleOnTab = (tab) => {
|
||||
setActiveTab(tab)
|
||||
}
|
||||
|
||||
return (
|
||||
<View className="myself_page">
|
||||
{/* 主要内容 */}
|
||||
@@ -184,6 +189,7 @@ const MyselfPage: React.FC = () => {
|
||||
is_current_user={is_current_user}
|
||||
is_following={is_following}
|
||||
on_follow={handle_follow}
|
||||
onTab={handleOnTab}
|
||||
/>
|
||||
{/* 球局订单和收藏功能 */}
|
||||
<View className="quick_actions_section">
|
||||
@@ -219,8 +225,7 @@ const MyselfPage: React.FC = () => {
|
||||
<Text className="tab_text">我主办的</Text>
|
||||
</View>
|
||||
<View
|
||||
className={`tab_item ${
|
||||
active_tab === "participated" ? "active" : ""
|
||||
className={`tab_item ${active_tab === "participated" ? "active" : ""
|
||||
}`}
|
||||
onClick={() => setActiveTab("participated")}
|
||||
>
|
||||
@@ -243,7 +248,10 @@ const MyselfPage: React.FC = () => {
|
||||
btnImg="ICON_ADD"
|
||||
reload={goPublish}
|
||||
isShowNoData={game_records.length === 0}
|
||||
loadMoreMatches={() => {}}
|
||||
loadMoreMatches={() => { }}
|
||||
collapse={true}
|
||||
style={{ paddingBottom: 0, overflow: "hidden" }}
|
||||
defaultShowNum={3}
|
||||
/>
|
||||
</ScrollView>
|
||||
</View>
|
||||
@@ -267,7 +275,10 @@ const MyselfPage: React.FC = () => {
|
||||
error={null}
|
||||
errorImg="ICON_LIST_EMPTY"
|
||||
isShowNoData={ended_game_records.length === 0}
|
||||
loadMoreMatches={() => {}}
|
||||
loadMoreMatches={() => { }}
|
||||
collapse={true}
|
||||
style={{ paddingBottom: "90px", overflow: "hidden" }}
|
||||
defaultShowNum={3}
|
||||
/>
|
||||
</ScrollView>
|
||||
{/* </View> */}
|
||||
|
||||
@@ -16,12 +16,13 @@ import { UserService, UserInfoType } from "@/services/userService";
|
||||
import * as LoginService from "@/services/loginService";
|
||||
import CustomNavbar from "@/components/CustomNavbar";
|
||||
import { useGlobalState } from "@/store/global";
|
||||
import { BackNavbar } from "@/components";
|
||||
|
||||
const OtherUserPage: React.FC = () => {
|
||||
// 获取页面参数
|
||||
const instance = Taro.getCurrentInstance();
|
||||
const user_id = instance.router?.params?.userid;
|
||||
if(!user_id) {
|
||||
if (!user_id) {
|
||||
Taro.showToast({
|
||||
title: "用户不存在",
|
||||
icon: "none",
|
||||
@@ -87,8 +88,7 @@ const OtherUserPage: React.FC = () => {
|
||||
nickname: userData.nickname || "",
|
||||
avatar_url: userData.avatar_url || "",
|
||||
join_date: userData.subscribe_time
|
||||
? `${new Date(userData.subscribe_time).getFullYear()}年${
|
||||
new Date(userData.subscribe_time).getMonth() + 1
|
||||
? `${new Date(userData.subscribe_time).getFullYear()}年${new Date(userData.subscribe_time).getMonth() + 1
|
||||
}月加入`
|
||||
: "",
|
||||
stats: {
|
||||
@@ -200,12 +200,15 @@ const OtherUserPage: React.FC = () => {
|
||||
// 处理发送消息
|
||||
const handle_send_message = () => {
|
||||
Taro.navigateTo({
|
||||
url: `/mode_user/message/chat/index?user_id=${
|
||||
user_info.id || ""
|
||||
url: `/mode_user/message/chat/index?user_id=${user_info.id || ""
|
||||
}&nickname=${user_info.nickname || ""}`,
|
||||
});
|
||||
};
|
||||
|
||||
const handleOnTab = (tab) => {
|
||||
setActiveTab(tab)
|
||||
}
|
||||
|
||||
// 处理球局详情
|
||||
// const handle_game_detail = (game_id: string) => {
|
||||
// Taro.navigateTo({
|
||||
@@ -215,19 +218,28 @@ const OtherUserPage: React.FC = () => {
|
||||
|
||||
return (
|
||||
<View className="other_user_page">
|
||||
<CustomNavbar>
|
||||
{/* <CustomNavbar>
|
||||
<View className="navbar_content">
|
||||
<View className="navbar_back" onClick={() => Taro.navigateBack()}>
|
||||
<View className="back_icon" />
|
||||
</View>
|
||||
<Text className="navbar_title"></Text>
|
||||
<View className="navbar_action">
|
||||
{/* 右侧占位,保持标题居中 */}
|
||||
</View>
|
||||
</View>
|
||||
</CustomNavbar>
|
||||
</CustomNavbar> */}
|
||||
{/* 顶部导航栏 */}
|
||||
<BackNavbar
|
||||
title=""
|
||||
showBackButton={true}
|
||||
showAvatar={false}
|
||||
backgroundColor="unset"
|
||||
onBack={() => {
|
||||
Taro.navigateBack();
|
||||
}}
|
||||
/>
|
||||
{/* 主要内容 */}
|
||||
<View className="main_content" style={{ paddingTop: `${totalHeight}px` }}>
|
||||
<View className="main_content">
|
||||
{/* 用户信息区域 */}
|
||||
<View className="user_info_section">
|
||||
<UserInfoCard
|
||||
@@ -236,6 +248,7 @@ const OtherUserPage: React.FC = () => {
|
||||
is_following={is_following}
|
||||
on_follow={handle_follow}
|
||||
on_message={handle_send_message}
|
||||
onTab={handleOnTab}
|
||||
/>
|
||||
</View>
|
||||
|
||||
@@ -262,9 +275,13 @@ const OtherUserPage: React.FC = () => {
|
||||
recommendList={[]}
|
||||
loading={loading}
|
||||
error={null}
|
||||
isShowNoData={game_records.length === 0}
|
||||
errorImg="ICON_LIST_EMPTY"
|
||||
emptyText="暂无消息,去互动看看吧"
|
||||
loadMoreMatches={() => {}}
|
||||
emptyText="暂无球局信息"
|
||||
loadMoreMatches={() => { }}
|
||||
collapse={true}
|
||||
style={{ paddingBottom: 0, overflow: "hidden" }}
|
||||
defaultShowNum={3}
|
||||
/>
|
||||
</ScrollView>
|
||||
{/* </View> */}
|
||||
@@ -298,9 +315,13 @@ const OtherUserPage: React.FC = () => {
|
||||
recommendList={[]}
|
||||
loading={loading}
|
||||
error={null}
|
||||
isShowNoData={ended_game_records.length === 0}
|
||||
errorImg="ICON_LIST_EMPTY"
|
||||
emptyText="暂无消息,去互动看看吧"
|
||||
loadMoreMatches={() => {}}
|
||||
emptyText="暂无球局信息"
|
||||
loadMoreMatches={() => { }}
|
||||
collapse={true}
|
||||
style={{ paddingBottom: "90px", overflow: "hidden" }}
|
||||
defaultShowNum={3}
|
||||
/>
|
||||
</ScrollView>
|
||||
{/* </View> */}
|
||||
|
||||
@@ -92,9 +92,8 @@ const SetTransactionPassword: React.FC = () => {
|
||||
title: "设置交易密码成功",
|
||||
icon: "success",
|
||||
});
|
||||
Taro.redirectTo({
|
||||
url: "/user_pages/wallet/index",
|
||||
});
|
||||
let delta = handleType === "set" ? 1 : 2;
|
||||
Taro.navigateBack({ delta })
|
||||
} catch (error) {
|
||||
Taro.showToast({
|
||||
title: "设置交易密码失败",
|
||||
|
||||
Reference in New Issue
Block a user