下拉框_教你封装 Element Tree 树状下拉框
在日常項目開發中,樹狀下拉框的需求還是比較常見的,但是element并沒有這種組件以供使用。在這里,小編就基于element如何封裝一個樹狀下拉框做個詳細的介紹。
通過這篇文章,你可以了解學習到一個樹狀下拉框組件是如何一步一步封裝成功的。
話不多說,先看效果圖:
封裝組件
該組件主要基于element的select組件、tree組件及input組件進行二次封裝的。
組件布局
首先我們需要基于這幾個組件對我們的組件進行布局,話不多說直接上代碼:
"select">"options">"tree-option"????????ref="selectTree"
??????>
注:css添加scoped屬性,是為了讓css只在該組件生效,避免樣式污染
這個時候直接使用肯定是會報錯的,因為我們組件該傳的參數還未傳遞。
組件數據完善
上面我們已經完成了布局,接下來就是為其豐富數據了,因為我們這個組件肯定是復用的,因此我們設計數據的時候,需要把常用的數據屬性提取出來通過props傳遞接收。我提取的主要有幾下幾個數據:
props:{????/*?配置項?*/
????props:{
??????type:?Object,
??????default:()=>{
????????return?{
??????????value:'id',?????????????//?ID字段名
??????????label:?'title',?????????//?顯示名稱
??????????children:?'children'????//?子級字段名
????????}
??????}
????},
????/*?選項列表數據(樹形結構的對象數組)?*/
????options:{
??????type:?Array,???????
??????default:?()=>{?return?[]?}
????},
????/*?初始值?*/
????value:{
??????default:?()=>{?return?null?}
????},
????/*?可清空選項?*/
????clearable:{
??????type:Boolean,
??????default:()=>{?return?true?}
????},
????/*?自動收起?*/
????accordion:{
??????type:Boolean,
??????default:()=>{?return?false?}
????},
????placeholder:{
??????type:String,
??????default:()=>{return?"請選擇"}
????}
??},
大家可能注意到,我所有prop字段都給了type屬性,唯獨value沒有,這是因為在實際使用中下拉框的數據value值可能是字符串(String)也可能是數字(Number),為了項目開發中控制臺不報太多無意義的錯,此處就沒有規定其type。
接收到prop之后,我們就開始對組件進行數據的處理,直接上代碼:
"placeholder"?ref="select">"options">"tree-option"????????ref="selectTree"
????????:accordion="accordion"
????????:data="options"
????????:props="props"
????????:node-key="props.value"
????????:default-expanded-keys="[]"
??????>
當數據過多的時候,滾動條會出現兩條,如下所示:
處理方法如下:
//?初始化滾動條initScroll(){
??this.$nextTick(()=>{
????let?scrollWrap?=?document.querySelectorAll('.el-scrollbar?.el-select-dropdown__wrap')[0]
????let?scrollBar?=?document.querySelectorAll('.el-scrollbar?.el-scrollbar__bar')
????scrollWrap.style.cssText?=?'margin:?0px;?max-height:?none;?overflow:?hidden;'
????scrollBar.forEach(ele?=>?ele.style.width?=?0)
??})
},
在mounted中調用該方法就可以了,效果如下:
點擊選中
數據也渲染顯示出來了,這個時候我們需要實現點擊數據選中功能。
思路很簡單:
- select組件綁定value值
- tree組件綁定節點點擊事件
- 點擊事件中獲取value和label
- 將獲取的值賦給select組件以及返回給父組件
代碼如下:
"valueTitle"?:placeholder="placeholder"?ref="select">"valueTitle"?:label="valueTitle"?class="options">"tree-option"????????ref="selectTree"
????????:accordion="accordion"
????????:data="options"
????????:props="props"
????????:node-key="props.value"
????????:default-expanded-keys="defaultExpandedKey"
????????@node-click="handleNodeClick"
????????>
data()?{
????return?{
??????valueId:this.value,//?初始值
??????valueTitle:'',
??????defaultExpandedKey:[]
????}
},
//?切換選項
handleNodeClick(node){
??this.valueTitle?=?node[this.props.label]//獲取label
??this.valueId?=?node[this.props.value]//獲取value
??this.$emit('getValue',this.valueId)//傳值給父組件
},
這樣點擊選中功能就實現了,但是有個問題,點擊之后,下拉框選項沒有隱藏,我們只需要再調用一下select組件的blur方法即可實現隱藏
數據初始化
細心的小伙伴肯定已經發現了,上面有一個初始值,并且在選擇器中,初始數據也是必不可少的。實現思路如下:
- watch監聽prop中value數據變化
- 將初始值做對應賦值
- 獲取初始值對應的label并做對應賦值
- 設置tree組件的默認選中狀態
- 設置tree組件的默認展開節點
代碼如下:
watch:?{????value(){
??????this.valueId?=?this.value
??????this.initHandle()
????}
},
//?初始化值
initHandle(){
??if(this.valueId){
????//?初始化顯示label
????this.valueTitle?=?this.$refs.selectTree.getNode(this.valueId).data[this.props.label]?????
????this.$refs.selectTree.setCurrentKey(this.valueId)//?設置默認選中
????this.defaultExpandedKey?=?[this.valueId]//?設置默認展開
??}?
},
在mounted中調用執行既可
清除選中
一般輸入框或者選擇器都有清除功能,我們的組件自然也少不了清除功能,實現思路如下:
- 給select組件設置clearable屬性
- 給select組件添加清除監聽事件
- 在監聽事件中清除tree組件選中,并清除父組件中的值
代碼如下:
"valueTitle"?:clearable="clearable"?@clear="clearHandle"?:placeholder="placeholder"?ref="select">//?清除選中
clearHandle(){
??this.valueTitle?=?''
??this.valueId?=?null
??this.defaultExpandedKey?=?[]
??this.clearSelected()
??this.$emit('getValue',null)
},
/*?清空選中樣式?*/
clearSelected(){
??let?allNode?=?document.querySelectorAll('#tree-option?.el-tree-node')
??allNode.forEach((element)=>element.classList.remove('is-current'))
},
篩選數據
當tree中數據量過大時,我們需要篩選數據,實現思路如下:
- 給tree組件添加filter-node-method方法
- 添加一個輸入框,輸入篩選的內容
- 監聽輸入內容變化,并調用tree組件的篩選方法
代碼如下:
"valueTitle"?:clearable="clearable"?@clear="clearHandle"?:placeholder="placeholder"?ref="select">??????class="selectInput"??????placeholder="檢索關鍵字"
??????v-model="filterText">"valueTitle"?:label="valueTitle"?class="options">"tree-option"
????????ref="selectTree"
????????:accordion="accordion"
????????:data="options"
????????:props="props"
????????:node-key="props.value"????
????????:default-expanded-keys="defaultExpandedKey"
????????:filter-node-method="filterNode"
????????@node-click="handleNodeClick">
.selectInput{
????padding:?0?5px;
????box-sizing:?border-box;
}
filterNode(value,?data)?{
??if?(!value)?return?true;
??return?data.name.indexOf(value)?!==?-1;
}
watch:?{
????filterText(val)?{
??????this.$refs.selectTree.filter(val);
????}
},
這樣一個簡單的樹狀下拉框組件就封裝好了。
使用組件
下面給個簡單的使用示例:
??????:props="defaultProps"??????:options="treeData"
??????:value="value"
??????:accordion="true"
??????@getValue="getValue($event)"
??????placeholder="請選擇所屬區域"
????/>選中的id:{{value}}
總結
以上是生活随笔為你收集整理的下拉框_教你封装 Element Tree 树状下拉框的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Android NDK学习(七):NDK
- 下一篇: 什么是Servlet