You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何基于Laravel实现带多筛选器与分页的会议搜索页面?

实现多筛选+分页会议搜索页面的剩余工作

你现在已经搭好了基础的页面框架和初始数据渲染,接下来还需要完成这几项关键工作,才能让筛选和分页功能正常联动:


1. 整合筛选表单结构

你当前的每个筛选下拉框都放在单独的<form>标签里,这会导致提交时只能传递单个筛选参数。需要把所有筛选控件放到同一个表单中:

<div class="row">
  <form method="GET" action="{{ route('search.index') }}"> <!-- 假设你的路由命名为search.index -->
    <div class="col-6 col-md-3 mb-4 mb-md-0">
      <select class="custom-select form-control" name="category_id">
        <option value="">All categories</option>
        @foreach ($categories as $category)
          <option value="{{ $category->id }}" {{ request('category_id') == $category->id ? 'selected' : '' }}>
            {{ $category->name }}
          </option>
        @endforeach
      </select>
    </div>
    <div class="col-6 col-md-3 mb-4 mb-md-0">
      <select class="custom-select form-control" name="city">
        <option value="">All cities</option>
        @foreach($cities as $city)
          <option value="{{ $city }}" {{ request('city') == $city ? 'selected' : '' }}>
            {{ $city }}
          </option>
        @endforeach
      </select>
    </div>
    <div class="col-6 col-md-3">
      <select class="custom-select form-control" name="price_range">
        <option value="">Price</option>
        <option value="Free" {{ request('price_range') == 'Free' ? 'selected' : '' }}>Free</option>
        <option value="Paid" {{ request('price_range') == 'Paid' ? 'selected' : '' }}>Paid</option>
      </select>
    </div>
    <div class="col-6 col-md-3">
      <select class="custom-select form-control" name="date_range">
        <option value="">All dates</option> <!-- 建议加默认选项,支持取消日期筛选 -->
        <option value="week" {{ request('date_range') == 'week' ? 'selected' : '' }}>This week</option>
        <option value="month" {{ request('date_range') == 'month' ? 'selected' : '' }}>This month</option>
      </select>
    </div>
    <!-- 可选:添加提交按钮,或用JS自动提交 -->
    <div class="col-12 mt-2">
      <button type="submit" class="btn btn-primary">Apply Filters</button>
    </div>
  </form>
</div>

这里做了几个关键修改:

  • 所有筛选控件归到同一个GET表单下,确保提交时能传递所有筛选参数
  • 给每个下拉框添加name属性,控制器才能获取对应参数
  • 增加选中状态回显,用户筛选后页面刷新能保留当前选中的筛选条件

2. 修改控制器,实现动态筛选逻辑

你当前的控制器只是返回固定的分页数据,需要根据前端传递的筛选参数动态构建查询:

class SearchController extends Controller { 
    public function index(){ 
        $pageLimit = 1; // 建议把这个值放到配置文件或用常量,方便后续修改
        
        // 初始化查询构造器
        $query = Congress::orderBy('created_at', 'desc');
        
        // 分类筛选
        if(request()->has('category_id') && request('category_id') != ''){
            $query->where('category_id', request('category_id'));
        }
        
        // 城市筛选
        if(request()->has('city') && request('city') != ''){
            $query->where('city', request('city'));
        }
        
        // 价格筛选(假设Congress模型有price字段,0代表免费)
        if(request()->has('price_range') && request('price_range') != ''){
            if(request('price_range') == 'Free'){
                $query->where('price', 0);
            } elseif(request('price_range') == 'Paid'){
                $query->where('price', '>', 0);
            }
        }
        
        // 日期筛选
        if(request()->has('date_range') && request('date_range') != ''){
            $now = now();
            if(request('date_range') == 'week'){
                $query->whereBetween('start_date', [$now->startOfWeek(), $now->endOfWeek()]);
            } elseif(request('date_range') == 'month'){
                $query->whereBetween('start_date', [$now->startOfMonth(), $now->endOfMonth()]);
            }
        }
        
        // 执行查询并分页,同时附加所有筛选参数到分页链接
        $congresses = $query->paginate($pageLimit)->appends(request()->all());
        
        // 获取分类和城市数据
        $categories = Category::orderBy('created_at', 'desc')->get();
        $cities = Congress::orderBy('created_at','desc')->pluck("city")->unique();
        
        return view('search')
            ->with('categories', $categories)
            ->with('cities', $cities)
            ->with('congresses', $congresses); 
    } 
}

核心改进点:

  • 使用查询构造器动态拼接筛选条件,只返回符合用户要求的会议数据
  • 分页时用appends(request()->all())把当前筛选参数附加到分页链接中,确保分页切换时不会丢失筛选条件

3. 优化用户体验(可选但推荐)

为了让筛选更流畅,可添加JS监听下拉框变化,自动提交表单,无需用户手动点击提交按钮:

<script>
// 给所有筛选下拉框添加change事件监听
document.querySelectorAll('select[name="category_id"], select[name="city"], select[name="price_range"], select[name="date_range"]').forEach(select => {
    select.addEventListener('change', function() {
        this.form.submit();
    });
});
</script>

4. 边界情况处理

  • 如果Congress模型中start_date是字符串格式,需要先转成日期类型再进行范围查询(可在模型里设置$dates属性,或用whereDate()方法)
  • 处理筛选后无数据的情况,在视图中添加提示:
<div class="row">
  @if($congresses->isEmpty())
    <div class="col-12 text-center py-5">
      <p>No conferences found matching your filters.</p>
    </div>
  @else
    @foreach($congresses as $congress)
      <!-- 你的会议卡片代码 -->
    @endforeach
  @endif
</div>

内容的提问来源于stack exchange,提问作者user9659025

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.28 07:09:34