uni-app树形列表(单选,多选)
多选:使用的是插件市场的tree树组件(ly-tree)<ly-tree ref="tree" :treeData="treeData" v-if="ready"nodeKey="id" @node-expand="handleNodeExpand"@node-click="handleNodeClick" :showCheckbox="true" :checkOnClickNode="tr
·
多选:
使用的是插件市场的tree树组件(ly-tree)
<ly-tree ref="tree" :treeData="treeData" v-if="ready"
nodeKey="id" @node-expand="handleNodeExpand"
@node-click="handleNodeClick" :showCheckbox="true" :checkOnClickNode="true" :expandOnClickNode="false"
:defaultExpandAll="true" @check-change="handleCheck"
></ly-tree>
其中@node-expand当树要展开时点击树形图左边的箭头调用;@node-click:点击树上的文件节点时调用;@check-change:点击节点上的复选框和点击树文字都会调用。具体使用时只用@check-change即可。:showCheckbox="true"显示复选框
具体代码处理如下:
<template>
<view v-if="isShowConfirm" class="my-confirm-notice">
<view class="confirm-content-wrap1">
<!-- 标题 -->
<view class="unipop__ui_tit">
<view v-if="titleText" class="unipop__ui_tit_text">{{titleText}}</view>
<image src="../../static/images/workbeach/icon_close.png" class="close_image" @click="close()"></image>
</view>
<!-- 内容 -->
<view class="content_margin">
<view class="flex_row_center label_text">组织机构:
<input type="text" disabled="true" class="inputStyle" ref='groupInput'
@click="popOrganization" placeholder="请选择组织机构" :value='groupName'>
</view>
<view v-show="isShow" class="top_level">
<view class="flex_row_center label_text">
<view style="width: 140rpx;"></view>
<scroll-view style="height: 200px;" class="ly_tree_style" :scroll-y="true">
<ly-tree ref="tree" :treeData="treeData" v-if="ready"
nodeKey="id" @node-expand="handleNodeExpand"
@node-click="handleNodeClick" :showCheckbox="true" :checkOnClickNode="true" :expandOnClickNode="false"
:defaultExpandAll="true" @check-change="handleCheck"
></ly-tree>
</scroll-view>
</view>
</view>
<view class="flex_row_center label_text label_margin">部门名称:
<input type="text" class="inputStyle" placeholder="部门名称" @input="onKeyInput" :value="departName" >
</view>
</view>
<view v-if="btns" class="unipop__ui_btns">
<text v-for="(item,index) in btns" :key="index" class="btn" :style="item.style" @tap="btnTaped(item)">{{item.text}}</text>
</view>
</view>
</view>
</template>
<script>
export default {
data() {
return {
isShowConfirm: false,
titleText: '', // 提示框标题
outerData: null, // 用于记录外部传进来的数据,也可以给外部监听userBehavior,事件的函数提供判断到底是哪个事件触发的
btns: {},
treeData:[],
ready:false,
isShow:false,
defalutValue:'请选择组织机构',
selectCondition:{},
departName:'',
groups:[],
groupName:''
}
},
created() {
console.log('created')
},
mounted() {
console.log('mounted')
this.loadData()
},
methods: {
show (titleText, config) {
this.titleText = titleText || '查询条件'
if (Object.prototype.toString.call(config) === '[object Object]') {
// 确保用户传递的是一个对象
this.outerData = config.data || null
this.btns = this.outerData.btns
console.log('noticeDialog', this.outerData)
}
this.isShowConfirm = true
},
close() {
this.isShowConfirm = false;
this.isShow = false;
this.groupName = '';
this.groups = [];
this.departName = '';
this.selectCondition = {};
},
btnTaped(item) {
let self = this;
console.log(item);
if(item.text == '重置') {
console.log('重置');
this.isShow = false;
this.groupName = '';
this.groups = [];
this.$refs.tree.setCheckAll(false);
this.departName = '';
this.selectCondition = {};
} else {
item.onTap(this.selectCondition);
this.close();
}
},
popOrganization() {
this.isShow = !this.isShow;
},
onKeyInput(event) {
this.departName = event.target.value;
this.selectCondition['deptName'] = this.departName;
},
loadData() {
setTimeout(()=> {
this.treeData = [
{
id:1,label:'客流分析与管理',
children:[
{id:11,label:'IT部'},
{id:12,label:'运维部'},
{id:13,label:'营销部'},
{id:14,label:'实施部'},
{id:15,label:'售后部'},
]
},
{
id:2,label:'一级2',
children:[
{id:21,label:'二级21'},
{id:22,label:'二级22'},
]
},
{
id:3,label:'客流分析与管理',
children:[
{id:31,label:'IT部'},
{id:32,label:'运维部'},
{id:33,label:'营销部'},
{id:34,label:'实施部'},
{id:35,label:'售后部'},
]
},
];
this.ready = true;
},2000);
},
handleNodeExpand(obj) {
console.log('handleNodeExpand='+JSON.stringify(obj))
},
handleNodeClick(obj) {
//console.log('handleNodeClick='+JSON.stringify(obj));
},
handleCheck(obj) {
console.log('handleCheck='+JSON.stringify(obj))
this.getSelectData(obj.node);
},
getSelectData(obj) {
if(obj.checked) {
if(this.groups.indexOf(obj.data) != -1) {
console.log('groups.contains')
} else {
this.groups.push(obj.data);
}
} else {
var index = this.groups.indexOf(obj.data);
console.log('groups.splice==='+index)
if(index != -1) {
this.groups.splice(index,1);
}
}
let groupParam = '';
let groupNames = '';
for(var i=0;i< this.groups.length; i++) {
if(groupParam) {
groupParam = groupParam+','+this.groups[i].id;
} else {
groupParam = this.groups[i].id;
}
if(groupNames) {
groupNames = groupNames+','+this.groups[i].label;
} else {
groupNames = this.groups[i].label;
}
}
this.groupName = groupNames;
this.selectCondition = {'deptIds':groupParam};
console.log('selectCondition='+groupParam)
}
}
}
</script>
<style lang="scss">
.my-confirm-notice {
position: fixed;
top: 0;
left: 0;
right: 0;
bottom: 0;
background-color: rgba(0, 0, 0, 0.5);
z-index: 998;
/* 这里防止当用户长按屏幕,出现的黑色背景色块,以及 iPhone 横平时字体的缩放问题 */
-webkit-text-size-adjust: 100%;
-webkit-tap-highlight-color: rgba(0, 0, 0, 0);
display: flex;
align-items: center;
}
.confirm-content-wrap1 {
position: relative;
left: 0;
right: 0;
// width: 60%;
width: 90%;
height: 247px;
margin: 0 auto;
background-color: #FFFFFF;
border-radius: 10px;
z-index: 999;
user-select: none;
}
.unipop__ui_tit_text {
color: white;
text-align: center;
line-height: 44px;
width: 100%;
font-size: 16px;
}
.close_image {
z-index: 100;position: absolute;float: right;right: 10px;width:30px;height: 30px;
}
.unipop__ui_tit {
background-color: #074498;
width: 100%;
border-top-left-radius: 10px;
border-top-right-radius: 10px;
height: 44px;
display: flex;
align-items: center;
}
.unipop__ui_btns{
height: 80px;
justify-content: space-around;
display: flex;
padding-left: 20px;
padding-right: 20px;
align-items: center;
}
.btn {
width: 81px;
height: 40px;
background-color: #074498;
line-height: 34px;
text-align: center;
font-size: 13px;
border-radius: 6rpx;
}
.content_margin {
padding: 15px 0px 15px 0px;
}
.flex_row_center {
display: flex; flex-direction: row; justify-content: center; align-items: center;
}
.label_text {
font-size: 28rpx;color: #555555;
}
.label_margin {
margin-top: 36rpx;
}
.inputStyle {
border: #bababa 0.5px solid; width: 169px;height: 34px; box-sizing: border-box; font-size: 13px; padding: 3px 2px;
}
.top_level {
position: fixed;z-index: 100;width: 90%;
}
.ly_tree_style {
border: #F5F5F5 1px solid; width: 169px;
}
</style>
单选:
<scroll-view style="height: 200px;" class="ly_tree_style" :scroll-y="true">
<ly-tree ref="tree" :treeData="treeData" v-if="ready" :showRadio="true"
nodeKey="id" :checkOnClickNode="true"
:expandOnClickNode="false" :defaultExpandAll="true"
@node-click="handleNodeClick"
@check='handleCheck'
></ly-tree>
</scroll-view>
其中:@node-click:点击树上的文字节点时调用;@check:点击树上的文字节点或单选框时都会调用。具体使用时只用@check即可。:showRadio="true"显示单选框
具体代码使用如下:
<template>
<view v-if="isShowConfirm" class="my-confirm-notice">
<view class="confirm-content-wrap1">
<!-- 标题 -->
<view class="unipop__ui_tit">
<view v-if="titleText" class="unipop__ui_tit_text">{{titleText}}</view>
<image src="../../static/images/workbeach/icon_close.png" class="close_image" @click="close()"></image>
</view>
<!-- 内容 -->
<view class="content_margin">
<view class="flex_row_center label_text">组织机构:
<input type="text" disabled="true" class="inputStyle" ref='groupInput'
@click="popOrganization" placeholder="请选择组织机构" :value='groupName'>
</view>
<view v-show="isShow" class="top_level">
<view class="flex_row_center label_text">
<view style="width: 140rpx;"></view>
<scroll-view style="height: 200px;" class="ly_tree_style" :scroll-y="true">
<ly-tree ref="tree" :treeData="treeData" v-if="ready" :showRadio="true"
nodeKey="id" :checkOnClickNode="true"
:expandOnClickNode="false" :defaultExpandAll="true"
@check='handleCheck'
></ly-tree>
</scroll-view>
</view>
</view>
<view class="flex_row_center label_text label_margin">
<view style="width: 140rpx;">姓名:</view>
<input type="text" class="inputStyle" placeholder="姓名" @input="onKeyInput" :value="userName" >
</view>
<view class="flex_row_center label_text label_margin">
<view style="width: 140rpx;">状态:</view>
<wyb-drop-down
ref="dropDown"
:options="dropDownOptions"
:heightSize="heightSize"
@select="onItemSelect"
class="dropDownStyle">
<!-- 自定义模式开启时,这里可以放内容 -->
</wyb-drop-down>
</view>
<view class="flex_row_center label_text label_margin">
<view style="width: 140rpx;">入职时间:</view>
<datetimePicker
type="date"
:value="start"
@change="changeStart"
class="dataPickerStyle"/>
</view>
<view class="flex_row_center label_text label_margin">
<view class="dateOperator">-</view>
<datetimePicker
type="date"
:value="end"
@change="changeEnd"
class="dataPickerStyle"/>
</view>
</view>
<view v-if="btns" class="unipop__ui_btns">
<text v-for="(item,index) in btns" :key="index" class="btn" :style="item.style" @tap="btnTaped(item)">{{item.text}}</text>
</view>
</view>
</view>
</template>
<script>
import datetimePicker from '@/components/uni-datetime-picker/uni-datetime-picker.vue'
export default {
components:{datetimePicker},
data() {
return {
isShowConfirm: false,
titleText: '', // 提示框标题
outerData: null, // 用于记录外部传进来的数据,也可以给外部监听userBehavior,事件的函数提供判断到底是哪个事件触发的
btns: [],
treeData:[],
ready:false,
isShow:false,
selectCondition:{},
userName:'',
groups:[],
groupName:'',
start: '',
end:'',
dropDownOptions: [{
header: '状态',
// contents在自定义开启时可以不用传
contents: ['状态', '启用', '禁用'],
custom: false // 该栏目开启自定义模式
}],
heightSize:{
header:40,content:48
},
}
},
mounted() {
console.log('mounted')
this.loadData()
// this.single = new Date();
},
methods: {
show (titleText, config) {
this.titleText = titleText || '查询条件'
if (Object.prototype.toString.call(config) === '[object Object]') {
// 确保用户传递的是一个对象
this.outerData = config || null
this.btns = this.outerData.btns
console.log('noticeDialog', this.outerData)
}
this.isShowConfirm = true
},
close(){
this.isShowConfirm = false;
this.isShow = false;
this.groupName = '';
this.groups = [];
this.userName = '';
this.start = '';
this.end = '';
this.dropDownOptions[0].header = '状态';
this.selectCondition = {};
},
btnTaped(item) {
console.log(item);
if(item.text == '重置') {
this.isShow = false;
this.groupName = '';
this.groups = [];
this.$refs.tree.setCheckAll(false);
this.userName = '';
this.start = '';
this.end = '';
this.dropDownOptions[0].header = '状态';
this.$refs.dropDown.onContentItemsTap(0);
this.selectCondition = {};
} else {
item.onTap(this.selectCondition);
this.close();
}
},
loadData() {
setTimeout(()=> {
this.treeData = [
{
id:1,label:'客流分析与管理',
children:[
{id:11,label:'IT部'},
{id:12,label:'运维部'},
{id:13,label:'营销部'},
{id:14,label:'实施部'},
{id:15,label:'售后部'},
]
},
{
id:2,label:'一级2',
children:[
{id:21,label:'二级21'},
{id:22,label:'二级22'},
]
},
{
id:3,label:'客流分析与管理',
children:[
{id:31,label:'IT部'},
{id:32,label:'运维部'},
{id:33,label:'营销部'},
{id:34,label:'实施部'},
{id:35,label:'售后部'},
]
},
];
this.ready = true;
},2000);
},
popOrganization() {
this.isShow = !this.isShow;
},
onKeyInput(event) {
this.userName = event.target.value;
this.selectCondition['nickName'] = this.userName;
},
handleCheck(obj) {
console.log('handleCheck='+JSON.stringify(obj))
this.getSelectData(obj.node);
},
getSelectData(obj) {
let groupParam = '';
let groupNames = '';
if(obj.checked) {
groupParam = obj.data.id;
groupNames = obj.data.label;
} else {
groupParam = '';
groupNames = '';
}
this.groupName = groupNames;
this.selectCondition = {'deptId':groupParam};
console.log('selectCondition='+groupParam)
},
changeStart(e) {
this.start = e;
console.log("-change事件:", e);
this.selectCondition['paramBeginTime'] = this.start;
},
changeEnd(e) {
this.end = e;
console.log("-change事件:", e);
this.selectCondition['paramEndTime'] = this.end;
},
onItemSelect(e) {
console.log("onItemSelect事件:", e);
this.dropDownOptions[0].header = e.content;
this.selectCondition['status'] = (e.contentIndex-1).toString();
this.$refs.dropDown.close();
}
}
}
</script>
注意:
1。当获取到的json数据不是{"id":1,"label":"****"}的形式时,而是{"deptId":201,"deptName":"B分店",}时,
label可以通过设置props解决:
props: {
// id:'deptId',
label: 'deptName' // 指把数据中的‘categoryName’当做label也就是节点名称
},
<ly-tree ref="tree" :treeData="treeData" v-if="ready" :showRadio="true"
nodeKey="deptId" :checkOnClickNode="true"
:expandOnClickNode="false" :defaultExpandAll="true"
@check='handleCheck' :props="props"
></ly-tree>
程序会将deptName的值,替换成label显示;取值的时候还是取deptName的值,
getSelectData(obj) {
let groupParam = '';
let groupNames = '';
if(obj.checked) {
groupParam = obj.data.deptId;
groupNames = obj.data.deptName;
} else {
groupParam = '';
groupNames = '';
}
this.groupName = groupNames;
this.selectCondition = {'deptId':groupParam};
console.log('selectCondition='+groupParam)
},
但是deptId不可以用同样的方法转成id,它可以在ly-tree的nodeKey属性中直接设置。
2。当单选时,取消选中的值用
this.$refs.tree.setCheckedKeys([]);
当多选时,取消选中的项用:
this.$refs.tree.setCheckAll(false);
更多推荐
已为社区贡献15条内容
所有评论(0)