列表页面常见需求
操作需求
- 筛选与操作:搜索,select,input搜索,导出,重置等
- Table数据展示和操作交互
- 列表接口交互:前端分页,后端分页,筛选choice
可封装点
- 筛选参数:筛选数据转换为可展示数据,接口交互序列化的统一管理,涉及参数状态保存,URL序列化管理
- table常用UI和交互封装
复杂列可参考的组件粒度
|_component
|_filter // 筛选以及列表操作统一处理
|_list // 列表父组件
|___<xxx-filter>
|___<md-table>
- 筛选和操作少于3个的简单列表,可以根据实际情况把握组件抽取的粒度
- 复杂列表组件分割思路
- filter组件统一处理筛选相关的数据交互,转换,输入输出(Input,Output),filter只需要给list提供最终的筛选值即可,list无需管理具体的筛选项组件的状态变化
- 复杂列表拓展筛选时,只需要在filter组件中消进行修改
- 避免list组件内部过分臃肿,不利于后续拓展
筛选参数交互建议
FilterContainer介绍
- 解决的问题:
- 筛选参数的不同场景,URL参数序列化,URL参数解析,后端数据可视化,组件可是化数据转换为后端交互数据形式。
- 当列表筛选不断修改和变化的时候,与接口进行API交互的时候,需要处理不同数据的序列化
- 接口交互参数的类型是可总结可抽象的
- 有一个容器统一管理所有的filter筛选的数据,以及对应状态
- 简单参数对象序列化:convertParamObjToStr全局方法处理
https://www.yuque.com/docs/share/f93fac68-ca7c-438e-8f25-9fd79d5c238f?#
《API Filter筛选参数交互建议》
export class FilterContainer implements IFilter {
constructor(filterMap?: {}) {
this._initFilters(filterMap);
}
getParamsObj() {
let paramsObj = {};
Object.keys(this).forEach(key => {
const getParamsFunction = this[key].getParamsObj;
if (getParamsFunction && getParamsFunction instanceof Function) {
if (getParamsFunction.call(this[key])) {
paramsObj = { ...paramsObj, ...getParamsFunction.call(this[key]) };
}
} else {
if (this[key] !== undefined) {
paramsObj[key] = this[key];
}
}
})
return paramsObj;
}
private _initFilters(filterMap: {}) {
Object.keys(filterMap).forEach((key, index) => {
this[key] = filterMap[key];
})
}
}
优势
表格布局,数据展示通过class统一配置,具体能力由表格内部提供
- 配置表头,搜索和排序能力由Table组件内部实现,外部交互只需要提供具体筛选状态
- 表格局部loading状态和布局配置项分离,与筛选一起,通过BehaviorSubject控制状态变化
后端分页
- Table组件只需要关心当前页数据渲染,以及table翻页,排序等状态的传递
- 具体的操作由引用方组件去处理
Table封装以及修改
|_table
|_col-handler // table col componentfactory动态生成
|_col // 列表col分类component封装
|_col-btn //操作按钮类
|_col-date //日期展示
|_col-default //默认展示
|_col-edit //编辑类,如select、input等col封装
|_col-portal // 自定义组件
|_col-status // 状态类
|_table// 列表父组件,列表布局处理
|_expand //嵌套表格
|_table-header // 表头操作列
|_col-setup // 配置表头