问题1:拖拽排序
背景:前几天做了这样一个需求 – 类目(组件选用的el-tree)支持拖拽排序
其实el-tree本就可以实现拖拽,只需要添加一个draggable
树形就可以了,拖拽完成后全量更新数据即可。
但是全量更新数据的性能开销比较大(主要开销在于后端),所以当时技术方案定的是:
- 如果移动到一个空的目录,
preCategoryId = null && nextCategoryId = null
- 如果移动到一个非空目录到最上方,
preCategoryId = null
- 如果移动到一个非空目录到最下饭,
nextCategoryId = null
- 否则传对应
preCategoryId,nextCategoryId
在这个过程中,难点就是去获取preCategoryId、nextCategoryId
,即要获取父节点的数据:
获取参数实现:
// 获取参数
// data:父节点数据
// draggingNode 当前拖拽节点
const getParams = (data: TreeItem, draggingNode: { data: { categoryId: string } }) => {
let preCategoryId: string | undefined = "";
let nextCategoryId: string | undefined = "";
let parentCategoryId: string | undefined = "";
parentCategoryId = data.categoryId;
const index = data.children!.findIndex((i) => i.categoryId === draggingNode.data.categoryId);
if (data.children!.length === 1) {
// 如果移动到一个空的目录,preCategoryId = null && nextCategoryId = null 都为空
preCategoryId = undefined;
nextCategoryId = undefined;
} else if (!index) {
// 如果移动到一个非空目录到最上方,preCategoryId = null
preCategoryId = undefined;
nextCategoryId = data.children![index + 1].categoryId;
} else if (index === data.children!.length - 1) {
// 如果移动到一个非空目录到最下饭,nextCategoryId = null
preCategoryId = data.children![index - 1].categoryId;
nextCategoryId = undefined;
} else {
preCategoryId = data.children![index - 1].categoryId;
nextCategoryId = data.children![index + 1].categoryId;
}
return {
preCategoryId,
nextCategoryId,
parentCategoryId,
};
};
// 根据id获取父节点数据
const getparentDataById = (id: string, tree: Array<TreeItem>): TreeItem => {
let res = null;
for (let i = 0; i < tree.length; i++) {
let ele = tree[i];
ele.categoryId === id ? (res = ele) : "";
if (res) break;
if (ele.children!.length) {
res = getparentDataById(id, ele.children!);
}
}
return res!;
};
问题2: 展开类目
一个需求是:加载页面后,展开当前选中的意图所在的类目,效果:
el-tree
组件提供的属性: :default-expanded-keys="expandedKeys"
, 实现的关键就是根据当前类目的id
查询他所有的祖父元素的id(expandedKeys)
,绑定到属性default-expanded-keys
上就可以了.
// eltree根据id获取所有父节点的id,
function getParentIds(treeData: Array<TreeItem>, id: string) {
let str = "";
const joinStr = ",";
for (var i = 0, len = treeData.length; i < len; i++) {
var item = treeData[i];
if (item.categoryId === id) {
return item.categoryId;
}
if (item.children) {
str = item.categoryId + joinStr + getParentIds(item.children, id);
if (str === item.categoryId + joinStr) {
str = "";
} else {
return str;
}
}
}
return str;
}