条件筛选

This commit is contained in:
hant 2025-07-01 23:49:58 +08:00
parent b1a3c89cf1
commit f6efddc06e
5 changed files with 192 additions and 38 deletions

View File

@ -36,29 +36,20 @@ Page({
selectedParam: '', selectedParam: '',
mainActiveIndex: 0, mainActiveIndex: 0,
selectedSeriesId: null, selectedSeriesId: null,
selectedBrandLabel:"品牌",
brandTree: [], brandTree: [],
sortOptions: [ sortOptions: [
{ text: '默认排序', value: 'default' }, { text: '默认排序', value: 'default' },
{ text: '价格升序', value: 'priceAsc' }, { text: '价格升序', value: 'priceAsc' },
{ text: '价格降序', value: 'priceDesc' } { text: '价格降序', value: 'priceDesc' }
], ],
brandOptions: [
{ text: '全部品牌', value: '' },
{ text: '丰田', value: 'toyota' },
{ text: '本田', value: 'honda' }
],
priceOptions: [ priceOptions: [
{ text: '全部价格', value: '' }, { text: '全部价格', value: '' },
{ text: '5万以下', value: '<5' }, { text: '5万以下', value: '<5' },
{ text: '5-10万', value: '5-10' }, { text: '5-10万', value: '5-10' },
{ text: '10万以上', value: '>10' } { text: '10万以上', value: '>10' }
], ],
paramOptions: [ extendFields: [] // 筛选配置
{ label: '自动挡', value: 'auto' },
{ label: '手动挡', value: 'manual' },
{ label: '新能源', value: 'ev' }
]
}, },
onBrandClick(e) { onBrandClick(e) {
this.setData({ this.setData({
@ -69,13 +60,14 @@ Page({
onSeriesSelect(e) { onSeriesSelect(e) {
const selectedId = e.detail.id; const selectedId = e.detail.id;
const selectedText = e.detail.text; const selectedText = e.detail.text;
this.setData({ selectedSeriesId: selectedId });
wx.showToast({ this.setData({
title: `已选择:${selectedText}`, selectedSeriesId: selectedId,
icon: 'none' selectedBrandLabel: selectedText // ✅ 更新 dropdown 显示的值
}); });
this.reloadList();
this.selectComponent('#dropdownItemBrand').toggle(false); // 关闭
// TODO: 发起请求,用 selectedId 作为筛选条件 // TODO: 发起请求,用 selectedId 作为筛选条件
}, },
onSortChange(e) { onSortChange(e) {
@ -98,7 +90,8 @@ Page({
reloadList() { reloadList() {
// TODO: 根据筛选值重新加载列表 // TODO: 根据筛选值重新加载列表
console.log('筛选值:', this.data.selectedSort, this.data.selectedBrand, this.data.selectedPrice, this.data.selectedParam); console.log('筛选值:', this.data.selectedSort, this.data.selectedBrand,
this.data.selectedPrice, this.data.selectedParam);
}, },
openMap() { openMap() {
const { latitude, longitude, address, name } = this.data.company const { latitude, longitude, address, name } = this.data.company
@ -119,7 +112,7 @@ Page({
url: '/admin/wechat/api/select' url: '/admin/wechat/api/select'
}); });
const brandTree = raw.map(brand => ({ const brandTree = raw.brands.map(brand => ({
text: brand.label, text: brand.label,
children: (brand.children || []).map(series => ({ children: (brand.children || []).map(series => ({
id: series.value, id: series.value,
@ -127,9 +120,85 @@ Page({
})) }))
})); }));
const fields = raw.extend.map(f => {
// 为 range 类型添加 start/end 临时字段
if (f.type === 'range') {
f._rangeStart = '';
f._rangeEnd = '';
} else if (f.type === 'checkbox') {
f.value = []; // 默认空数组
}
return f;
});
this.setData({ extendFields:fields });
this.setData({ brandTree }); this.setData({ brandTree });
this.reloadList();
} catch (err) { } catch (err) {
console.error('加载品牌失败', err); console.error('加载品牌失败', err);
} }
},
onTagToggle(e) {
const name = e.currentTarget.dataset.name;
const value = String(e.currentTarget.dataset.value);
const fields = this.data.extendFields.map(field => {
if (field.name === name) {
let list = (field.value || []).map(String);
const index = list.indexOf(value);
if (index > -1) {
list.splice(index, 1);
} else {
list.push(value);
}
field.value = list;
// ✅ 同步 checked 状态
field.options.forEach(opt => {
opt._checked = list.includes(String(opt.value));
});
}
return field;
});
this.setData({ extendFields: fields });
},
onSliderChange(e) {
const name = e.currentTarget.dataset.name;
const [start, end] = e.detail;
const fields = this.data.extendFields.map(field => {
if (field.name === name) {
field._rangeStart = start;
field._rangeEnd = end;
}
return field;
});
this.setData({ extendFields: fields });
},
onExtendConfirm() {
const filterParams = {};
this.data.extendFields.forEach(field => {
if (field.type === 'checkbox') {
if (field.value?.length > 0) {
filterParams[field.name] = field.value;
}
} else if (field.type === 'range') {
if (field._rangeStart || field._rangeEnd) {
filterParams[field.name] = {
start: field._rangeStart,
end: field._rangeEnd
};
}
}
});
console.log('参数筛选值:', filterParams);
this.selectComponent('#dropdownItemParam').toggle(false); // 关闭
// 这里你可以请求后端过滤后的列表
// request({ url: '/xxx', data: filterParams }).then(...)
} }
}) })

View File

@ -1,10 +1,11 @@
{ {
"usingComponents": { "usingComponents": {
"van-icon": "@vant/weapp/icon/index", "van-icon": "@vant/weapp/icon/index",
"van-button": "@vant/weapp/button/index",
"van-card": "@vant/weapp/card/index",
"van-dropdown-menu": "@vant/weapp/dropdown-menu/index", "van-dropdown-menu": "@vant/weapp/dropdown-menu/index",
"van-dropdown-item": "@vant/weapp/dropdown-item/index", "van-dropdown-item": "@vant/weapp/dropdown-item/index",
"van-tree-select": "@vant/weapp/tree-select/index" "van-tree-select": "@vant/weapp/tree-select/index",
"van-slider": "@vant/weapp/slider/index",
"van-tag": "@vant/weapp/tag/index",
"van-button": "@vant/weapp/button/index"
} }
} }

View File

@ -29,7 +29,7 @@
options="{{sortOptions}}" options="{{sortOptions}}"
bind:change="onSortChange" bind:change="onSortChange"
/> />
<van-dropdown-item title="品牌" use-slot> <van-dropdown-item id="dropdownItemBrand" title="{{selectedBrandLabel}}" use-slot>
<van-tree-select <van-tree-select
height="400" height="400"
items="{{brandTree}}" items="{{brandTree}}"
@ -44,19 +44,55 @@
options="{{priceOptions}}" options="{{priceOptions}}"
bind:change="onPriceChange" bind:change="onPriceChange"
/> />
<van-dropdown-item <van-dropdown-item title="参数"
title="参数"
use-slot use-slot
id="dropdownItemParam"
> >
<!-- 参数自定义筛选项 --> <view class="filter-extend">
<view class="param-options"> <view wx:for="{{extendFields}}" wx:key="id" class="filter-group">
<label wx:for="{{paramOptions}}" wx:key="value"> <view class="filter-label">{{item.label}}</view>
<radio
value="{{item.value}}" <!-- 多选项字段 -->
checked="{{item.value === selectedParam}}" <view wx:if="{{item.type === 'checkbox'}}" class="filter-tags">
bindchange="onParamChange" <view
/> {{item.label}} wx:for="{{item.options}}"
</label> wx:for-item="opt"
wx:key="index"
class="filter-tag-item"
data-name="{{item.name}}"
data-value="{{opt.value}}"
bind:tap="onTagToggle"
>
<van-tag
class="mytag"
type="{{opt._checked ? 'success' : 'default'}}"
round
plain="{{!opt._checked}}"
>
{{opt.key}}
</van-tag>
</view>
</view>
<view wx:if="{{item.type === 'range'}}" class="filter-slider-group">
<view class="slider-label">
{{item.label}}{{item._rangeStart || item.options.start}}{{item.options.unit}} - {{item._rangeEnd || item.options.end}}{{item.options.unit}}
</view>
<van-slider
range
value="{{[item._rangeStart ? item._rangeStart : item.options.start, item._rangeEnd ? item._rangeEnd : item.options.end]}}"
min="{{item.options.start}}"
max="{{item.options.end}}"
data-name="{{item.name}}"
bind:change="onSliderChange"
/>
</view>
</view>
<van-button type="primary" block size="small" bind:tap="onExtendConfirm">确认</van-button>
</view> </view>
</van-dropdown-item> </van-dropdown-item>
</van-dropdown-menu> </van-dropdown-menu>

View File

@ -111,3 +111,51 @@
z-index: 99; z-index: 99;
background-color: #fff; background-color: #fff;
} }
.filter-extend {
padding: 20rpx;
}
.filter-group {
margin-bottom: 24rpx;
}
.filter-label {
font-weight: bold;
margin-bottom: 12rpx;
}
.filter-checkbox {
margin-right: 16rpx;
margin-bottom: 12rpx;
}
.filter-range {
display: flex;
align-items: center;
}
.range-separator {
margin: 0 12rpx;
}
.range-unit {
margin-left: 12rpx;
font-size: 24rpx;
color: #888;
}
.filter-tags {
display: flex;
flex-wrap: wrap;
gap: 10rpx 30rpx;
}
.van-tag{
padding: 10rpx 20rpx !important;
}
.filter-slider-group {
padding: 12rpx 0;
}
.slider-label {
margin-bottom: 8rpx;
font-size: 24rpx;
color: #666;
}

View File

@ -1,4 +1,4 @@
const BASE_URL = 'http://192.168.89.112:8089/'; // 👈 换成你的后端地址 const BASE_URL = 'http://192.168.1.11:8089/'; // 👈 换成你的后端地址
function request({ url, method = 'GET', data = {}, header = {} }) { function request({ url, method = 'GET', data = {}, header = {} }) {
const token = ''; const token = '';