DdDrawer 抽屉组件
组件介绍
DdDrawer是一个基于Element UI封装的抽屉式弹窗组件,用于展示详细信息或包含复杂表单的交互界面。相较于传统Modal,抽屉组件在移动端有更好的适配性,同时支持复杂的子组件嵌套和数据交互。
基本用法
<dd-drawer
title="商机详情"
:z-index="1000"
:dialog-visible="drawerName"
@close="drawerNameClose"
>
<!-- 抽屉内容区域 -->
<div slot="content">
<!-- 子组件内容 -->
</div>
</dd-drawer>
属性说明
| 参数名 | 类型 | 默认值 | 说明 |
|---|---|---|---|
| title | String | - | 抽屉标题 |
| dialog-visible | Boolean | false | 控制抽屉显示/隐藏 |
| z-index | Number | 1000 | 抽屉层级 |
| width | String/Number | '80%' | 抽屉宽度 |
| height | String/Number | '100%' | 抽屉高度 |
| close-on-click-modal | Boolean | false | 点击遮罩是否关闭抽屉 |
| modal-append-to-body | Boolean | true | 遮罩是否插入至 body 元素上 |
| append-to-body | Boolean | true | 抽屉自身是否插入至 body 元素上 |
| custom-class | String | '' | 自定义类名 |
| destroy-on-close | Boolean | false | 关闭时是否销毁抽屉中的元素 |
事件说明
| 事件名 | 参数 | 说明 |
|---|---|---|
| close | - | 抽屉关闭时触发 |
| open | - | 抽屉打开时触发 |
子组件分页实现
在DdDrawer中嵌套表格等需要分页的子组件时,推荐通过以下方式实现分页功能:
1. 分页数据绑定
子组件(如表格)应通过list-query属性绑定分页参数,通常包含page和pageSize:
<business-customer-photos
:info="{ customer_id: customerid }"
:customer-id="customerid"
:dialog-visible="dialogVisibles['7']"
@close="handleUpdateDialogVisible(false)"
/>
2. 分页参数管理
在子组件内部维护分页状态,并通过接口参数传递给后端:
// 子组件内部数据
data() {
return {
filterInfo: {
data: {
page: 1,
pageSize: 20,
// 其他查询参数
}
}
}
},
methods: {
getList() {
this.listLoading = true;
// 设置分页参数
this.$set(
this.filterInfo.data,
"SearchDiandiBusinessCustomerPhotos[customer_id]",
this.customerId
);
// 调用接口获取数据
initList(this.filterInfo.data).then((response) => {
this.total = response.data.dataProvider.total;
this.list = response.data.dataProvider.allModels;
this.listLoading = false;
});
}
}
3. 分页控件集成
通过dd-table组件的分页功能自动处理页码切换:
<dd-table
ref="table"
:list="list"
:total="total"
:is-dialog="true"
:list-loading="listLoading"
:columns="tableColumns"
:list-query="filterInfo.data"
@getList="getList"
>
<!-- 表格内容 -->
</dd-table>
4. 完整分页实现示例
以下是一个在DdDrawer中实现子组件分页的完整流程:
- 父组件(抽屉容器):
<dd-drawer title="商机详情" :dialog-visible="drawerName">
<div slot="content">
<el-tabs v-model="activeName">
<el-tab-pane label="相册" name="7">
<business-customer-photos
:customer-id="customerid"
:dialog-visible="dialogVisibles['7']"
/>
</el-tab-pane>
</el-tabs>
</div>
</dd-drawer>
- 子组件(带分页的表格):
<template>
<dd-table
ref="table"
:list="list"
:total="total"
:list-loading="listLoading"
:columns="tableColumns"
:list-query="filterInfo.data"
@getList="getList"
>
<!-- 表格列定义 -->
</dd-table>
</template>
<script>
export default {
props: {
customerId: {
type: [Number, String, null],
default: 0,
},
},
data() {
return {
filterInfo: {
data: {
page: 1,
pageSize: 20,
}
},
list: [],
total: 0,
listLoading: false
};
},
watch: {
customerId: {
handler() {
this.getList();
},
immediate: true,
},
},
methods: {
getList() {
this.listLoading = true;
// 设置查询参数
this.$set(
this.filterInfo.data,
"SearchDiandiBusinessCustomerPhotos[customer_id]",
this.customerId
);
// 调用接口
initList(this.filterInfo.data).then((response) => {
this.total = response.data.dataProvider.total;
this.list = response.data.dataProvider.allModels;
this.listLoading = false;
});
}
}
};
</script>
注意事项
- 当抽屉中包含多个子组件时,建议为每个子组件单独维护分页状态,避免相互干扰
- 使用
destroy-on-close属性可在抽屉关闭时销毁子组件,释放资源 - 对于复杂的分页逻辑,可通过Vuex或EventBus在父子组件间共享分页状态
- 确保分页参数正确传递给后端接口,通常包含
page、pageSize和其他查询条件
高级用法
1. 自定义头部和底部
通过header和footer插槽自定义抽屉的头部和底部内容:
<dd-drawer title="商机详情" :dialog-visible="drawerName">
<div slot="header">
<!-- 自定义头部内容 -->
</div>
<div slot="content">
<!-- 主要内容区域 -->
</div>
<div slot="footer">
<!-- 自定义底部按钮 -->
</div>
</dd-drawer>
2. 动态控制抽屉大小
通过width或height属性动态控制抽屉尺寸:
<dd-drawer
:width="isMobile ? '100%' : '80%'"
title="商机详情"
:dialog-visible="drawerName"
>
<!-- 内容区域 -->
</dd-drawer>
完整示例
结合表格分页的完整抽屉组件用法:
<template>
<dd-drawer
title="客户相册"
:dialog-visible="drawerVisible"
width="80%"
@close="handleClose"
>
<div slot="content">
<dd-table
:list="list"
:total="total"
:list-loading="listLoading"
:columns="columns"
:list-query="queryParams"
@getList="fetchData"
>
<!-- 表格列定义 -->
<template slot="path" slot-scope="{ row }">
<el-image
style="width: 100px; height: 100px"
:src="row.path[0]"
:preview-src-list="row.path"
/>
</template>
<template slot="action" slot-scope="{ row, index }">
<!-- 操作按钮 -->
</template>
</dd-table>
</div>
</dd-drawer>
</template>
<script>
export default {
data() {
return {
drawerVisible: false,
list: [],
total: 0,
listLoading: false,
queryParams: {
page: 1,
pageSize: 20,
customer_id: ''
}
};
},
methods: {
fetchData() {
this.listLoading = true;
// 调用接口获取数据
// ...
},
handleClose() {
this.drawerVisible = false;
}
}
};
</script>
