羽球联盟 HarmonyOS NEXT 实战系列 (16/20):赛事列表、比赛状态与详情页组织
文章导读
- 赛事模块既要展示概览列表,也要在详情页里承接赛程和比分信息。
EventStatus用稳定枚举表达未开始、进行中、已结束三种状态,列表和详情都能复用。- 详情页把比赛记录按日期分组,避免用户面对一长串无结构信息。
页面效果
赛事页和普通资讯列表最大的不同,在于用户要看的不是一篇正文,而是一组持续变化的结构化数据。列表页更像总览,负责告诉用户赛事地点、时间和当前状态;详情页则要承接对阵、阶段、比分和日期,让用户能顺着比赛进度往下看。

如果赛事模型设计得不够清楚,列表和详情就会互相拖累。列表会塞太多信息,详情又只能展示一段杂糅文本。把结构化信息分层展示,是这个页面体系真正的重点。
实战拆解
EventListPage 负责解决“看见哪些赛事值得点进去”这个问题。页面通过分类 Tab 支持全部、国际赛事、国内赛事、正在进行、已结束五个入口,再结合 freshEvents() 过滤掉已经结束太久的比赛,让列表聚焦在用户更关心的近期内容上。
EventDetailPage 则把单个赛事进一步展开。页面先根据路由参数找到当前赛事,再将 matches 按日期降序排序,并通过 groupedDates() 把同一天的比赛归到一起。这样用户浏览详情时,看到的是清晰的时间分组,而不是一串扁平记录。
这里还有一个很适合写进教程的点:赛事不是文章,也不是商品。它有自己的生命周期和状态流转,因此模型必须包含 status、category、matches 这类更贴近业务的字段。只要模型足够明确,列表卡片和详情页的布局就会顺着业务自然长出来。
关键代码
private sortedMatches(): EventMatch[] {
if (this.sportEvent === null || this.sportEvent!.matches === undefined) {
return [];
}
const arr: EventMatch[] = this.sportEvent!.matches!.slice();
arr.sort((a: EventMatch, b: EventMatch) => b.date.localeCompare(a.date));
return arr;
}
private groupedDates(): string[] {
const seen: Set<string> = new Set<string>();
const dates: string[] = [];
for (const m of this.sortedMatches()) {
if (!seen.has(m.date)) {
seen.add(m.date);
dates.push(m.date);
}
}
return dates;
}
private matchesOf(date: string): EventMatch[] {
return this.sortedMatches().filter((m: EventMatch) => m.date === date);
}
这段逻辑直接决定了详情页读起来像不像一个赛事时间线。先排序、再分组、最后按组渲染,比把所有比赛平铺到一个列表里清晰得多,也更方便以后加比分状态或高亮重点场次。
取舍分析
赛事页的主要取舍,是列表里放多少信息。把比分、赛程、地点、时间、状态、对阵全塞进列表固然“信息丰富”,但会极大牺牲扫读效率。羽球联盟选择让列表保留概览,把细节留给详情页,本质上是在用户浏览成本和信息完整度之间做分层。
另一个取舍在于状态表达方式。页面当然可以直接用中文字符串写“进行中”“已结束”,但一旦进入筛选、颜色映射和组件复用阶段,稳定枚举会更可靠。项目用 pending、ongoing、finished 作为内部状态值,就是为了让模型和 UI 解耦。
设计落点
- 列表页负责概览,详情页负责赛程与比分,不要让两者职责互相挤压。
- 赛事状态必须有稳定枚举,便于筛选、徽章显示和后续扩展。
- 结构化比赛数据应按日期或阶段分组,而不是直接拼成长文本。
易踩坑
- 不要把比分信息塞成一段普通字符串,否则排序、分组和高亮都会变得困难。
- 已结束赛事如果不做时效过滤,列表很快会被旧内容淹没。
- 状态文案可以调整,状态值不要随着中文文案一起漂移。
验证方式
- 在赛事列表切换不同分类,确认国际、国内、进行中、已结束筛选结果正确。
- 点击赛事卡片进入详情,确认日期分组和比赛排序符合预期。
- 对于未开始或暂无记录的赛事,确认详情页能展示合理占位文案。
参考资料
小结
第 16 篇真正强调的是:赛事是一类结构化业务,不适合拿文章页的思路硬套。只要列表概览、状态枚举和详情分组各守其位,赛事模块就会既清晰又容易继续扩展。
更多推荐

所有评论(0)