angular.js、react.js、vue.js
现在前端主流的三大框架中,从17年开始又以vue最为火爆。而三大框架更多的偏向于js交互层面,而在ui层面里呢,饿了么外卖的那个element-ui是使用vue时组件覆盖面较为全面的了。
目前在用到<el-tree></el-tree>便签时,发现了原生并没有支持高亮检索词属性。而树形结构在查找东西时,对于不太熟悉的人来说确实不太友好。所以,就简单通过jquery简陋的做了个动态高亮显示检索词的功能。
使用前提:
<el-tree></el-tree> :filter-node-method属性 filter()属性
整体思路和网上高亮显示检索词的是一样的
第一步:拿到检索关键字、并且拿到检索后显示的数据
第二步:动态写入html '<span style="color:red">' + val + </span>''
第三步:动态的清除html内容中的 '<span style="color:red">'和‘</span>’内容
其中其实比较麻烦的有两点: 一是如何获取到被过滤后的节点,二是修改html内容的时序问题
第一点,其实通过控制台的Elements选项卡中可以拿到。通过class属性可以看出来,其中的过滤是会将不符合添加的叶子节点加上 is-hidden的class 隐藏起来。 故通过
$('.el-tree-node .is-focusable .el-tree-node__content span:nth-child(2)')
可拿到过滤节点的label内容
第二点,其实是代码的插入点 在检索时整个过程用到了三个方法
- vm.watch监听 input框值的变化
- 输入框的input事件(不能用change事件,因为change事件是在值发生变化且失去焦点的情况下),用来根据用户输入的值对节点树着色
- vm.$refs.节点树.filter(val)方法
默认执行顺序为:用户val==>@input事件==》watch监听(val:function() ==>vm.$refs.节点树ref.filter(val))
input框值发生变化,触发input事件,接着触发watch监听,然后在watch监听中,将拿到的val值传入vm.$refs.节点树.filter(val)方法循环遍历过滤节点树节点,最后渲染。但是这样的话,input里面的事件进先执行了,这时候过滤节点还没有渲染就拿不到,也就上不了色了。(但是,你可能会说,为什么不放到watch里面filter方法之后呢,我放了,但是确实不管用... 没有具体研究watch的机制,后面有时间的话会看一下)
于是,我们改变一下时序。通过在@input方法中,将方法体包在延时函数setTimeout()中。于是就变成了
val==》watch监听(清除颜色代码==》val:function() ==>vm.$refs.节点树ref.filter(val))==>@input事件(上色代码)
附两个方法代码参考,有更好的方案欢迎指教~~
//注意有个小坑,就是在上色的时候,<span style="color:red"></span>中的color: red中最好是有个空格,在Chrome下,你写什么就是什么没有关系。但在IE下,它会自动给你拼上空格,这样下面你清除样式的时候就清除不掉了
watch: {
filterText: function(val) {
var arr = $('.el-tree-node .is-focusable .el-tree-node__content span:nth-child(2)');
for(var i=0;i<arr.length;i++){
var values = $(arr[i]).html();
$(arr[i]).html(values.split('<span style="color: red;">').join("").split('</span>').join(""));
$(arr[i]).html(values);
}
this.$refs.menuTree.filter(val);
}
},
@input事件
highLightText:function(){
setTimeout(function(){
var val = vm.filterText;
if(val !== null && val !== ''){
var arr = $('.el-tree-node .is-focusable .el-tree-node__content span:nth-child(2)');
for(var i=0;i<arr.length;i++){
var values = $(arr[i]).html();
var reg=new RegExp(val,"g"); //创建正则RegExp对象
$(arr[i]).html(values.replace(reg,'<span style="color: red;">' + val + '</span>'));
}
}
},100);
},