feat: 将list相关的代码迁移到game_pages目录
This commit is contained in:
@@ -259,18 +259,18 @@ function StickyButton(props) {
|
||||
) {
|
||||
return {
|
||||
text: "球局已结束,查看其他球局",
|
||||
action: navto.bind(null, "/pages/list/index"),
|
||||
action: navto.bind(null, "/game_pages/list/index"),
|
||||
};
|
||||
}
|
||||
if (waiting_start) {
|
||||
return {
|
||||
text: "等待开始, 查看更多球局",
|
||||
action: navto.bind(null, "/pages/list/index"),
|
||||
action: navto.bind(null, "/game_pages/list/index"),
|
||||
};
|
||||
} else if (is_substituting) {
|
||||
return {
|
||||
text: "候补中,查看其他球局",
|
||||
action: navto.bind(null, "/pages/list/index"),
|
||||
action: navto.bind(null, "/game_pages/list/index"),
|
||||
};
|
||||
} else if (can_pay) {
|
||||
return {
|
||||
@@ -1036,7 +1036,7 @@ function Index() {
|
||||
const pages = Taro.getCurrentPages();
|
||||
if (pages.length <= 1) {
|
||||
Taro.redirectTo({
|
||||
url: "/pages/list/index",
|
||||
url: "/game_pages/list/index",
|
||||
});
|
||||
} else {
|
||||
Taro.navigateBack();
|
||||
|
||||
6
src/game_pages/list/index.config.ts
Normal file
6
src/game_pages/list/index.config.ts
Normal file
@@ -0,0 +1,6 @@
|
||||
export default definePageConfig({
|
||||
navigationBarTitleText: '',
|
||||
enablePullDownRefresh: true,
|
||||
backgroundTextStyle: 'dark',
|
||||
navigationStyle: 'custom',
|
||||
})
|
||||
76
src/game_pages/list/index.module.scss
Normal file
76
src/game_pages/list/index.module.scss
Normal file
@@ -0,0 +1,76 @@
|
||||
.listPage {
|
||||
background-color: #fefefe;
|
||||
|
||||
.listTopSearchWrapper {
|
||||
padding: 0 15px;
|
||||
// position: sticky;
|
||||
// background: #fefefe;
|
||||
// z-index: 999;
|
||||
}
|
||||
|
||||
// .isScroll {
|
||||
// border-bottom: 0.5px solid #0000000F;
|
||||
// }
|
||||
|
||||
.listTopFilterWrapper {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
padding-top: 10px;
|
||||
padding-bottom: 10px;
|
||||
gap: 5px;
|
||||
}
|
||||
|
||||
.menuFilter {
|
||||
padding: 0;
|
||||
}
|
||||
}
|
||||
|
||||
.listNavWrapper {
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.toggleElement {
|
||||
/* 绝对定位使两个元素重叠 */
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
|
||||
/* 过渡动画设置,实现平滑切换 */
|
||||
transition: opacity 0.5s ease, transform 0.5s ease;
|
||||
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
padding: 20px;
|
||||
border-radius: 8px;
|
||||
}
|
||||
|
||||
/* 第一个元素样式 */
|
||||
.firstElement {
|
||||
background-color: #4a90e2;
|
||||
color: white;
|
||||
}
|
||||
|
||||
/* 第二个元素样式 */
|
||||
.secondElement {
|
||||
background-color: #5cb85c;
|
||||
color: white;
|
||||
/* 初始状态:透明且稍微偏移 */
|
||||
opacity: 0;
|
||||
transform: translateY(20px);
|
||||
}
|
||||
|
||||
/* 可见状态 */
|
||||
.visible {
|
||||
opacity: 1;
|
||||
transform: translateY(0);
|
||||
}
|
||||
|
||||
/* 隐藏状态 */
|
||||
.hidden {
|
||||
opacity: 0;
|
||||
transform: translateY(20px);
|
||||
pointer-events: none; /* 隐藏时不响应鼠标事件 */
|
||||
}
|
||||
230
src/game_pages/list/index.tsx
Normal file
230
src/game_pages/list/index.tsx
Normal file
@@ -0,0 +1,230 @@
|
||||
import SearchBar from "@/components/SearchBar";
|
||||
import FilterPopup from "@/components/FilterPopup";
|
||||
import styles from "./index.module.scss";
|
||||
import { useEffect } from "react";
|
||||
import Taro, { usePageScroll } from "@tarojs/taro";
|
||||
import { useListStore } from "@/store/listStore";
|
||||
import { useGlobalState } from "@/store/global";
|
||||
import { View } from "@tarojs/components";
|
||||
import CustomerNavBar from "@/container/listCustomNavbar";
|
||||
import GuideBar from "@/components/GuideBar";
|
||||
import ListContainer from "@/container/listContainer";
|
||||
import DistanceQuickFilter from "@/components/DistanceQuickFilter";
|
||||
import { withAuth } from "@/components";
|
||||
import { updateUserLocation } from "@/services/userService";
|
||||
// import img from "@/config/images";
|
||||
// import ShareCardCanvas from "@/components/ShareCardCanvas/example";
|
||||
|
||||
|
||||
|
||||
|
||||
const ListPage = () => {
|
||||
|
||||
// 从 store 获取数据和方法
|
||||
const store = useListStore() || {};
|
||||
|
||||
const { statusNavbarHeightInfo, getCurrentLocationInfo } = useGlobalState() || {};
|
||||
|
||||
const { totalHeight } = statusNavbarHeightInfo || {};
|
||||
const {
|
||||
isShowFilterPopup,
|
||||
error,
|
||||
matches,
|
||||
recommendList,
|
||||
loading,
|
||||
getMatchesData,
|
||||
updateState,
|
||||
filterCount,
|
||||
updateFilterOptions, // 更新筛选条件
|
||||
filterOptions,
|
||||
clearFilterOptions,
|
||||
distanceData,
|
||||
quickFilterData,
|
||||
distanceQuickFilter,
|
||||
isScrollTop,
|
||||
searchValue,
|
||||
isShowInputCustomerNavBar,
|
||||
initialFilterSearch,
|
||||
loadMoreMatches,
|
||||
dateRangeOptions
|
||||
} = store;
|
||||
|
||||
usePageScroll((res) => {
|
||||
if (res?.scrollTop >= totalHeight) {
|
||||
!isShowInputCustomerNavBar &&
|
||||
updateState({ isShowInputCustomerNavBar: true });
|
||||
} else {
|
||||
isShowInputCustomerNavBar &&
|
||||
updateState({ isShowInputCustomerNavBar: false });
|
||||
}
|
||||
});
|
||||
|
||||
useEffect(() => {
|
||||
getLocation()
|
||||
}, []);
|
||||
|
||||
// 监听距离和排序方式变化,自动调用接口
|
||||
useEffect(() => {
|
||||
// 只有当 distanceQuickFilter 有值时才调用接口
|
||||
if (distanceQuickFilter?.distance !== undefined || distanceQuickFilter?.quick !== undefined) {
|
||||
|
||||
if (distanceQuickFilter?.quick !== "0") {
|
||||
getMatchesData();
|
||||
}
|
||||
}
|
||||
}, [distanceQuickFilter?.distance, distanceQuickFilter?.quick]);
|
||||
|
||||
// 获取位置信息
|
||||
const getLocation = async () => {
|
||||
const location = await getCurrentLocationInfo()
|
||||
|
||||
// 保存位置到全局状态
|
||||
updateState({ location });
|
||||
|
||||
// 同时更新用户位置到后端和 store
|
||||
if (location && location.latitude && location.longitude) {
|
||||
try {
|
||||
await updateUserLocation(location.latitude, location.longitude);
|
||||
} catch (error) {
|
||||
console.error('更新用户位置失败:', error);
|
||||
}
|
||||
}
|
||||
|
||||
// 页面加载时获取数据
|
||||
getMatchesData();
|
||||
return location;
|
||||
}
|
||||
|
||||
const refreshMatches = () => {
|
||||
initialFilterSearch();
|
||||
};
|
||||
|
||||
// const getLoadMoreMatches = () => {
|
||||
// loadMoreMatches()
|
||||
// }
|
||||
|
||||
// 下拉刷新处理函数 - 使用Taro生命周期钩子
|
||||
Taro.usePullDownRefresh(() => {
|
||||
console.log("===触发下拉刷新");
|
||||
clearFilterOptions()
|
||||
|
||||
// 调用 store 的刷新方法
|
||||
// refreshMatches()
|
||||
// .then(() => {
|
||||
// // 刷新完成后停止下拉刷新动画
|
||||
// Taro.stopPullDownRefresh();
|
||||
|
||||
// // 显示刷新成功提示
|
||||
// Taro.showToast({
|
||||
// title: "刷新成功",
|
||||
// icon: "success",
|
||||
// duration: 1500,
|
||||
// });
|
||||
// })
|
||||
// .catch(() => {
|
||||
// // 刷新失败时也停止动画
|
||||
// Taro.stopPullDownRefresh();
|
||||
|
||||
// Taro.showToast({
|
||||
// title: "刷新失败",
|
||||
// icon: "error",
|
||||
// duration: 1500,
|
||||
// });
|
||||
// });
|
||||
});
|
||||
|
||||
const toggleShowPopup = () => {
|
||||
updateState({ isShowFilterPopup: !isShowFilterPopup });
|
||||
};
|
||||
|
||||
/**
|
||||
* @description 更新筛选条件
|
||||
* @param {Record<string, any>} params 筛选项
|
||||
*/
|
||||
const handleUpdateFilterOptions = (params: Record<string, any>) => {
|
||||
updateFilterOptions(params);
|
||||
};
|
||||
|
||||
const handleSearchChange = () => { };
|
||||
|
||||
// 距离筛选
|
||||
const handleDistanceOrQuickChange = (name, value) => {
|
||||
updateState({
|
||||
distanceQuickFilter: {
|
||||
...distanceQuickFilter,
|
||||
[name]: value,
|
||||
},
|
||||
});
|
||||
};
|
||||
|
||||
const handleSearchClick = () => {
|
||||
Taro.navigateTo({
|
||||
url: "/game_pages/search/index",
|
||||
});
|
||||
};
|
||||
|
||||
return (
|
||||
<View>
|
||||
{/* 自定义导航 */}
|
||||
<CustomerNavBar />
|
||||
{/* <ShareCardCanvas /> */}
|
||||
<View className={styles.listPage}>
|
||||
<View
|
||||
className={`${styles.listTopSearchWrapper} ${isScrollTop ? styles.isScroll : ""
|
||||
}`}
|
||||
>
|
||||
<SearchBar
|
||||
handleFilterIcon={toggleShowPopup}
|
||||
isSelect={filterCount > 0}
|
||||
filterCount={filterCount}
|
||||
onChange={handleSearchChange}
|
||||
value={searchValue}
|
||||
onInputClick={handleSearchClick}
|
||||
/>
|
||||
{/* 综合筛选 */}
|
||||
{isShowFilterPopup && (
|
||||
<View>
|
||||
<FilterPopup
|
||||
loading={loading}
|
||||
onCancel={toggleShowPopup}
|
||||
onConfirm={toggleShowPopup}
|
||||
onChange={handleUpdateFilterOptions}
|
||||
filterOptions={filterOptions}
|
||||
onClear={clearFilterOptions}
|
||||
visible={isShowFilterPopup}
|
||||
onClose={toggleShowPopup}
|
||||
statusNavbarHeigh={statusNavbarHeightInfo?.totalHeight}
|
||||
/>
|
||||
</View>
|
||||
)}
|
||||
</View>
|
||||
{/* 筛选 */}
|
||||
<View className={styles.listTopFilterWrapper}>
|
||||
<DistanceQuickFilter
|
||||
cityOptions={distanceData}
|
||||
quickOptions={quickFilterData}
|
||||
onChange={handleDistanceOrQuickChange}
|
||||
cityName="distance"
|
||||
quickName="quick"
|
||||
cityValue={distanceQuickFilter?.distance}
|
||||
quickValue={distanceQuickFilter?.quick}
|
||||
/>
|
||||
</View>
|
||||
|
||||
{/* 列表内容 */}
|
||||
<ListContainer
|
||||
data={matches}
|
||||
recommendList={recommendList}
|
||||
loading={loading}
|
||||
error={error}
|
||||
reload={refreshMatches}
|
||||
loadMoreMatches={loadMoreMatches}
|
||||
/>
|
||||
</View>
|
||||
|
||||
<GuideBar currentPage="list" />
|
||||
</View>
|
||||
);
|
||||
};
|
||||
|
||||
export default withAuth(ListPage);
|
||||
3
src/game_pages/search/index.config.ts
Normal file
3
src/game_pages/search/index.config.ts
Normal file
@@ -0,0 +1,3 @@
|
||||
export default definePageConfig({
|
||||
navigationBarTitleText: ''
|
||||
})
|
||||
121
src/game_pages/search/index.scss
Normal file
121
src/game_pages/search/index.scss
Normal file
@@ -0,0 +1,121 @@
|
||||
.listSearchContainer {
|
||||
padding: 0 15px;
|
||||
padding-top: 16px;
|
||||
|
||||
.icon16 {
|
||||
width: 16px;
|
||||
height: 16px;
|
||||
}
|
||||
|
||||
.topSearch {
|
||||
padding: 10px 16px 5px 12px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
height: 44px;
|
||||
box-sizing: border-box;
|
||||
gap: 10px;
|
||||
border-radius: 44px;
|
||||
border: 0.5px solid rgba(0, 0, 0, 0.06);
|
||||
background: #FFF;
|
||||
box-shadow: 0 4px 48px 0 rgba(0, 0, 0, 0.08);
|
||||
|
||||
.nut-input {
|
||||
padding: 0;
|
||||
height: 100%;
|
||||
}
|
||||
}
|
||||
|
||||
.searchRight {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 12px;
|
||||
|
||||
.searchLine {
|
||||
width: 1px;
|
||||
height: 20px;
|
||||
border-radius: 20px;
|
||||
background: rgba(0, 0, 0, 0.06);
|
||||
}
|
||||
|
||||
.searchText {
|
||||
color: #000000;
|
||||
font-size: 16px;
|
||||
font-weight: 600;
|
||||
line-height: 20px
|
||||
}
|
||||
}
|
||||
|
||||
.searchIcon {
|
||||
width: 20px;
|
||||
height: 20px;
|
||||
}
|
||||
|
||||
.historySearchTitleWrapper {
|
||||
display: flex;
|
||||
padding: 12px 15px;
|
||||
justify-content: space-between;
|
||||
align-items: flex-end;
|
||||
align-self: stretch;
|
||||
|
||||
.historySearchTitle,
|
||||
.historySearchClear {
|
||||
color: #000;
|
||||
font-size: 14px;
|
||||
font-weight: 600;
|
||||
line-height: 20px;
|
||||
}
|
||||
|
||||
.historySearchClear {
|
||||
color: #9a9a9a;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 4px;
|
||||
}
|
||||
}
|
||||
|
||||
.historySearchList {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
flex-wrap: wrap;
|
||||
gap: 8px;
|
||||
|
||||
.historySearchItem {
|
||||
flex-shrink: 0;
|
||||
flex-grow: 0;
|
||||
display: flex;
|
||||
height: 28px;
|
||||
padding: 4px 12px;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
gap: 2px;
|
||||
border-radius: 999px;
|
||||
border: 0.5px solid rgba(0, 0, 0, 0.06);
|
||||
background: rgba(0, 0, 0, 0.03);
|
||||
}
|
||||
}
|
||||
|
||||
.searchSuggestion {
|
||||
padding: 6px 0;
|
||||
|
||||
.searchSuggestionItem {
|
||||
padding: 10px 20px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
|
||||
.searchSuggestionItemLeft {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 12px;
|
||||
color: rgba(60, 60, 67, 0.60);
|
||||
font-size: 14px;
|
||||
font-weight: 400;
|
||||
line-height: 20px;
|
||||
}
|
||||
|
||||
.highlight {
|
||||
color: #000000;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
208
src/game_pages/search/index.tsx
Normal file
208
src/game_pages/search/index.tsx
Normal file
@@ -0,0 +1,208 @@
|
||||
// import CustomerNavbarBack from "@/components/CustomerNavbarBack";
|
||||
import { View, Image, Text } from "@tarojs/components";
|
||||
import { Input } from "@nutui/nutui-react-taro";
|
||||
import { useEffect, useMemo, useRef } from "react";
|
||||
import { useListState } from "@/store/listStore";
|
||||
import img from "@/config/images";
|
||||
import { withAuth } from "@/components";
|
||||
import "./index.scss";
|
||||
import Taro from "@tarojs/taro";
|
||||
|
||||
const ListSearch = () => {
|
||||
const {
|
||||
searchValue,
|
||||
updateState,
|
||||
getSearchHistory,
|
||||
searchHistory = [],
|
||||
clearHistory,
|
||||
searchSuggestion,
|
||||
suggestionList,
|
||||
isShowSuggestion,
|
||||
} = useListState() || {};
|
||||
const ref = useRef<any>(null);
|
||||
|
||||
useEffect(() => {
|
||||
getSearchHistory();
|
||||
return () => {
|
||||
handleClear();
|
||||
};
|
||||
}, []);
|
||||
|
||||
useEffect(() => {
|
||||
if (ref?.current) {
|
||||
ref.current.focus();
|
||||
}
|
||||
}, [ref.current]);
|
||||
|
||||
const regex = useMemo(() => {
|
||||
return new RegExp(searchValue, "gi");
|
||||
}, [searchValue]);
|
||||
|
||||
// 是否显示清空图标
|
||||
const isShowClearIcon = searchValue && searchValue?.length > 0;
|
||||
|
||||
// 是否显示搜索历史
|
||||
const isShowHistory = searchHistory && searchHistory?.length > 0;
|
||||
|
||||
/**
|
||||
* @description 输入
|
||||
* @param value
|
||||
*/
|
||||
const handleChange = (value: string) => {
|
||||
updateState({ searchValue: value });
|
||||
if (value) {
|
||||
searchSuggestion(value);
|
||||
} else {
|
||||
updateState({
|
||||
isShowSuggestion: false,
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* @description 点击清空输入内容
|
||||
*/
|
||||
const handleClear = () => {
|
||||
updateState({ searchValue: "", isShowSuggestion: false });
|
||||
};
|
||||
|
||||
/**
|
||||
* @description 点击历史搜索
|
||||
* @param value
|
||||
*/
|
||||
const handleHistoryClick = (item: { id: number; title: string }) => {
|
||||
updateState({ searchValue: item?.title });
|
||||
handleSearch(item?.title);
|
||||
};
|
||||
|
||||
/**
|
||||
* @description 清空历史搜索
|
||||
*/
|
||||
const handleClearHistory = () => {
|
||||
clearHistory();
|
||||
};
|
||||
|
||||
/**
|
||||
* @description 点击联想词
|
||||
*/
|
||||
const handleSuggestionSearch = (val: string) => {
|
||||
updateState({
|
||||
searchValue: val,
|
||||
isShowSuggestion: false,
|
||||
});
|
||||
handleSearch(val);
|
||||
};
|
||||
|
||||
/**
|
||||
* @description 点击搜索
|
||||
*/
|
||||
const handleSearch = (val?: string) => {
|
||||
if (!val) {
|
||||
return;
|
||||
}
|
||||
Taro.navigateTo({
|
||||
url: `/game_pages/searchResult/index`,
|
||||
});
|
||||
};
|
||||
|
||||
return (
|
||||
<>
|
||||
<View className="listSearchContainer">
|
||||
{/* 搜索 */}
|
||||
<View className="topSearch">
|
||||
<Image className="searchIcon" src={img.ICON_LIST_SEARCH_SEARCH} />
|
||||
<Input
|
||||
placeholder="搜索上海的球局和场地"
|
||||
value={searchValue}
|
||||
defaultValue={searchValue}
|
||||
onChange={handleChange}
|
||||
onClear={handleClear}
|
||||
autoFocus
|
||||
clearable={false}
|
||||
ref={ref}
|
||||
/>
|
||||
<View className="searchRight">
|
||||
{isShowClearIcon && (
|
||||
<Image
|
||||
className="clearIcon icon16"
|
||||
src={img.ICON_LIST_SEARCH_CLEAR}
|
||||
onClick={handleClear}
|
||||
/>
|
||||
)}
|
||||
<View className="searchLine" />
|
||||
<Text className="searchText" onClick={() => handleSearch(searchValue)}>
|
||||
搜索
|
||||
</Text>
|
||||
</View>
|
||||
</View>
|
||||
{/* 联想词 */}
|
||||
{isShowSuggestion && (
|
||||
<View className="searchSuggestion">
|
||||
{(suggestionList || [])?.map((item) => {
|
||||
// 替换匹配文本为高亮版本
|
||||
const highlightedText = item.replace(regex, (match) => {
|
||||
// 如果匹配不到,则返回原文本
|
||||
if (!match) return match;
|
||||
return `<Text class="highlight">${match}</Text>`;
|
||||
});
|
||||
return (
|
||||
<View
|
||||
className="searchSuggestionItem"
|
||||
onClick={() => handleSuggestionSearch(item)}
|
||||
>
|
||||
<View className="searchSuggestionItemLeft">
|
||||
<Image
|
||||
className="icon16"
|
||||
src={img.ICON_LIST_SEARCH_SEARCH}
|
||||
/>
|
||||
<Text
|
||||
dangerouslySetInnerHTML={{ __html: highlightedText }}
|
||||
></Text>
|
||||
</View>
|
||||
<Image
|
||||
className="icon16"
|
||||
src={img.ICON_LIST_SEARCH_SUGGESTION}
|
||||
/>
|
||||
</View>
|
||||
);
|
||||
})}
|
||||
</View>
|
||||
)}
|
||||
{/* 历史搜索 */}
|
||||
{!isShowClearIcon && (
|
||||
<View className="historySearch">
|
||||
<View className="historySearchTitleWrapper">
|
||||
<View className="historySearchTitle">历史搜索</View>
|
||||
<View className="historySearchClear" onClick={handleClearHistory}>
|
||||
<Text>清空</Text>
|
||||
<Image
|
||||
className="clearIcon icon16"
|
||||
src={img.ICON_LIST_SEARCH_CLEAR_HISTORY}
|
||||
/>
|
||||
</View>
|
||||
</View>
|
||||
|
||||
{isShowHistory && (
|
||||
<View className="historySearchList">
|
||||
{(searchHistory || [])?.map((item) => {
|
||||
if (!item?.title) {
|
||||
return null;
|
||||
}
|
||||
return (
|
||||
<Text
|
||||
className="historySearchItem"
|
||||
onClick={() => handleHistoryClick(item)}
|
||||
>
|
||||
{item?.title}
|
||||
</Text>
|
||||
);
|
||||
})}
|
||||
</View>
|
||||
)}
|
||||
</View>
|
||||
)}
|
||||
</View>
|
||||
</>
|
||||
);
|
||||
};
|
||||
export default withAuth(ListSearch);
|
||||
4
src/game_pages/searchResult/index.config.ts
Normal file
4
src/game_pages/searchResult/index.config.ts
Normal file
@@ -0,0 +1,4 @@
|
||||
export default definePageConfig({
|
||||
navigationBarTitleText: '搜索结果',
|
||||
navigationStyle: 'custom',
|
||||
})
|
||||
68
src/game_pages/searchResult/index.scss
Normal file
68
src/game_pages/searchResult/index.scss
Normal file
@@ -0,0 +1,68 @@
|
||||
.searchResultPage {
|
||||
position: relative;
|
||||
|
||||
.searchResultFilterWrapper {
|
||||
position: sticky;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 5px;
|
||||
padding: 5px 15px 10px 15px;
|
||||
position: sticky;
|
||||
top: -1px;
|
||||
background-color: #fefefe;
|
||||
z-index: 123;
|
||||
|
||||
.nut-menu-bar {
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
.nut-menu-container-wrap {
|
||||
left: -15px;
|
||||
}
|
||||
|
||||
.filterIconWrapper {
|
||||
display: flex;
|
||||
width: 28px;
|
||||
height: 28px;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
gap: 10px;
|
||||
flex-shrink: 0;
|
||||
aspect-ratio: 1/1;
|
||||
border-radius: 999px;
|
||||
border: 0.5px solid rgba(0, 0, 0, 0.06);
|
||||
background: #FFF;
|
||||
position: relative;
|
||||
|
||||
&.active {
|
||||
background-color: #000000;
|
||||
}
|
||||
}
|
||||
|
||||
.filterIcon {
|
||||
width: 14px;
|
||||
height: 14px;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.filterCount {
|
||||
background-color: #000000;
|
||||
position: absolute;
|
||||
width: 15px;
|
||||
height: 15px;
|
||||
border: 2px solid #ffffff;
|
||||
border-radius: 50%;
|
||||
right: -5px;
|
||||
bottom: -5px;
|
||||
color: #ffffff;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 11px;
|
||||
}
|
||||
}
|
||||
|
||||
.menuFilter {
|
||||
padding: 0;
|
||||
}
|
||||
}
|
||||
157
src/game_pages/searchResult/index.tsx
Normal file
157
src/game_pages/searchResult/index.tsx
Normal file
@@ -0,0 +1,157 @@
|
||||
import { View, Image, Text } from "@tarojs/components";
|
||||
// import { useSearchResultState } from "@/store/searchResultStore";
|
||||
import { useListStore } from "@/store/listStore";
|
||||
import { useGlobalState } from "@/store/global";
|
||||
import ListContainer from "@/container/listContainer";
|
||||
import img from "@/config/images";
|
||||
import CustomerNavBar from "@/container/listCustomNavbar";
|
||||
import DistanceQuickFilter from "@/components/DistanceQuickFilter";
|
||||
import { withAuth } from "@/components";
|
||||
import { useEffect } from "react";
|
||||
import FilterPopup from "@/components/FilterPopup";
|
||||
import "./index.scss";
|
||||
import Taro from "@tarojs/taro";
|
||||
|
||||
const SearchResult = () => {
|
||||
const {
|
||||
isShowFilterPopup,
|
||||
error,
|
||||
distanceQuickFilter,
|
||||
searchResultData,
|
||||
recommendList,
|
||||
loading,
|
||||
updateState,
|
||||
filterCount,
|
||||
updateFilterOptions, // 更新筛选条件
|
||||
filterOptions,
|
||||
clearFilterOptions,
|
||||
distanceData,
|
||||
quickFilterData,
|
||||
loadMoreMatches,
|
||||
getMatchesData
|
||||
} = useListStore() || {};
|
||||
const { statusNavbarHeightInfo } = useGlobalState() || {};
|
||||
const { totalHeight } = statusNavbarHeightInfo || {};
|
||||
const isSelect = filterCount > 0;
|
||||
|
||||
useEffect(() => {
|
||||
const pages = Taro.getCurrentPages()
|
||||
const currentPage = pages?.[pages.length - 1];
|
||||
updateState({currentPage, isSearchResult: true})
|
||||
// if (location?.address) {
|
||||
// 保存位置
|
||||
// updateState({ location });
|
||||
// 页面加载时获取数据
|
||||
console.log('===搜索结果页===')
|
||||
getMatchesData();
|
||||
// }
|
||||
|
||||
return () => {
|
||||
console.log('===搜索结果组件卸载')
|
||||
updateState({currentPage: '', isSearchResult: false})
|
||||
}
|
||||
}, []);
|
||||
|
||||
/**
|
||||
* @description 更新筛选条件
|
||||
* @param {Record<string, any>} params 筛选项
|
||||
*/
|
||||
const handleUpdateFilterOptions = (params: Record<string, any>) => {
|
||||
updateFilterOptions(params);
|
||||
};
|
||||
|
||||
const toggleShowPopup = () => {
|
||||
updateState({ isShowFilterPopup: !isShowFilterPopup });
|
||||
};
|
||||
|
||||
// 距离筛选
|
||||
const handleDistanceOrQuickChange = (name, value) => {
|
||||
updateState({
|
||||
distanceQuickFilter: {
|
||||
...distanceQuickFilter,
|
||||
[name]: value,
|
||||
},
|
||||
});
|
||||
};
|
||||
|
||||
const refreshMatches = () => {
|
||||
getMatchesData();
|
||||
};
|
||||
|
||||
const handleLeftIconClick = () => {
|
||||
Taro.navigateBack()
|
||||
}
|
||||
|
||||
return (
|
||||
<View className="searchResultPage">
|
||||
{/* 自定义导航 */}
|
||||
<CustomerNavBar
|
||||
config={{
|
||||
showInput: true,
|
||||
inputLeftIcon: img.ICON_LIST_SEARCH_BACK,
|
||||
leftIconClick: handleLeftIconClick
|
||||
}}
|
||||
/>
|
||||
{/* 筛选 */}
|
||||
<View
|
||||
className="searchResultFilterWrapper"
|
||||
style={
|
||||
{
|
||||
top: `${totalHeight}px`
|
||||
}
|
||||
}
|
||||
>
|
||||
<DistanceQuickFilter
|
||||
cityOptions={distanceData}
|
||||
quickOptions={quickFilterData}
|
||||
onChange={handleDistanceOrQuickChange}
|
||||
cityName="distance"
|
||||
quickName="quick"
|
||||
cityValue={distanceQuickFilter?.distance}
|
||||
quickValue={distanceQuickFilter?.quick}
|
||||
/>
|
||||
{/* 筛选 icon */}
|
||||
<View
|
||||
className={`filterIconWrapper ${isSelect && "active"}`}
|
||||
onClick={toggleShowPopup}
|
||||
>
|
||||
<Image
|
||||
src={isSelect ? img.ICON_FILTER_SELECTED : img.ICON_FILTER}
|
||||
className={`filterIcon ${isSelect && "active"}`}
|
||||
/>
|
||||
{isSelect && <Text className="filterCount">{filterCount}</Text>}
|
||||
</View>
|
||||
{/* 筛选弹框 */}
|
||||
{/* 综合筛选 */}
|
||||
{isShowFilterPopup && (
|
||||
<View>
|
||||
<FilterPopup
|
||||
loading={loading}
|
||||
onCancel={toggleShowPopup}
|
||||
onConfirm={toggleShowPopup}
|
||||
onChange={handleUpdateFilterOptions}
|
||||
filterOptions={filterOptions}
|
||||
onClear={clearFilterOptions}
|
||||
visible={isShowFilterPopup}
|
||||
onClose={toggleShowPopup}
|
||||
// statusNavbarHeigh={0}
|
||||
statusNavbarHeigh={statusNavbarHeightInfo?.totalHeight}
|
||||
/>
|
||||
</View>
|
||||
)}
|
||||
</View>
|
||||
|
||||
{/* 列表内容 */}
|
||||
<ListContainer
|
||||
data={searchResultData}
|
||||
recommendList={recommendList}
|
||||
loading={loading}
|
||||
error={error}
|
||||
reload={refreshMatches}
|
||||
loadMoreMatches={loadMoreMatches}
|
||||
/>
|
||||
</View>
|
||||
);
|
||||
};
|
||||
|
||||
export default withAuth(SearchResult);
|
||||
Reference in New Issue
Block a user