Vue3+Ts封装类似el-drawer的抽屉组件

news2024/12/24 2:13:02

提供9个字段对drawer组件进行控制:

  • modelValue: 对抽屉显示隐藏进行控制,

  • width: 控制抽屉的宽度,

  • title: 控制抽屉的标题,

  • appendToBody: 是否将抽屉添加至body,

  • closeOnClickModal: 是否点击遮罩层关闭抽屉,

  • showConfirm: 是否显示确认按钮,

  • showCancel: 是否显示取消按钮,

  • cancelText: 取消按钮的文本,

  • confirmText: 确认按钮的文本

drawer.vue代码如下

<template>
	<teleport v-if="appendToBody" to="body">
		<transition name="drawer-fade">
			<div v-show="visible" class="drawer-overlay" @click.self="handleCloseModal">
				<div class="drawer-content" :style="drawerStyle" @click.stop>
					<div class="drawer-header">
						<div class="title-content">
							<div class="drawer-close-button" @click="handleClose">X</div>
							<span>{{ title }}</span>
						</div>
						<div class="drawer-btn">
							<div v-if="showCancel" class="drawer-button" @click="handleCancel">{{ cancelText }}</div>
							<div v-if="showConfirm" class="drawer-button" @click="handleSure">{{ confirmText }}</div>
						</div>
					</div>
					<div class="mes-drawer-layout-main">
						<slot></slot>
					</div>
				</div>
			</div>
		</transition>
	</teleport>
	<transition name="drawer-fade" v-else>
		<div v-show="visible" class="drawer-overlay" @click.self="handleCloseModal">
			<div class="drawer-content" :style="drawerStyle" @click.stop>
				<div class="drawer-header">
					<div class="title-content">
						<div class="drawer-close-button" @click="handleClose">X</div>
						<span>{{ title }}</span>
					</div>
					<div class="drawer-btn">
						<div v-if="showCancel" class="drawer-button" @click="handleCancel">{{ cancelText }}</div>
						<div v-if="showConfirm" class="drawer-button" @click="handleSure">{{ confirmText }}</div>
					</div>
				</div>
				<div class="mes-drawer-layout-main">
					<slot></slot>
				</div>
			</div>
		</div>
	</transition>
</template>

<script lang="ts" setup>
import { ref, watch, computed } from "vue";
const props = withDefaults(
	defineProps<{
		modelValue?: boolean;
		width?: string;
		title?: string;
		appendToBody?: boolean;
		closeOnClickModal?: boolean;
		showConfirm?: boolean;
		showCancel?: boolean;
		cancelText?: string;
		confirmText?: string;
	}>(),
	{
		modelValue: false,
		width: "30%",
		title: "",
		appendToBody: true,
		closeOnClickModal: false,
		showConfirm: true,
		showCancel: true,
		cancelText: "取消",
		confirmText: "确认"
	}
);

const emit = defineEmits<{
	(event: "update:modelValue", value: boolean): void;
	(event: "beforeClose"): void;
	(event: "on-cancel"): void;
	(event: "on-sure"): void;
}>();

const visible = ref(props.modelValue);

watch(
	() => props.modelValue,
	newVal => {
		visible.value = newVal;
	}
);

const drawerStyle = computed(() => ({
	width: props.width,
	height: "100%"
}));

function handleCloseModal() {
	if (props.closeOnClickModal) {
		handleClose();
	}
}

function handleClose() {
	emit("beforeClose");
	emit("update:modelValue", false);
}

function handleCancel() {
	emit("on-cancel");
}

function handleSure() {
	emit("on-sure");
}
</script>

<style lang="scss" scoped>
.drawer-overlay {
	z-index: 999;
	position: fixed;
	top: 0;
	right: 0;
	bottom: 0;
	left: 0;
	background-color: rgba(0, 0, 0, 0.5);
	display: flex;
	justify-content: flex-end;
	align-items: center;
	.drawer-content {
		background: #333333;
		box-shadow: 0 2px 8px rgba(0, 0, 0, 0.15);
		transition: transform 0.3s ease;
		position: relative;
		z-index: 1000;
		display: flex;
		flex-direction: column;
		.drawer-header {
			display: flex;
			align-items: center;
			justify-content: space-between;
			height: 56px;
			padding: 0 16px;
			border-bottom: 1px solid #efefef;
			color: #ffffff;
			.title-content {
				display: flex;
				align-items: center;
				span {
					margin-left: 12px;
				}
				.drawer-close-button {
					font-size: 16px;
					cursor: pointer;
				}
			}
			.drawer-btn {
				display: flex;
				justify-content: flex-end;
				padding: 10px;
				.drawer-button {
					margin-left: 10px;
					display: inline-flex;
					justify-content: center;
					align-items: center;
					line-height: 1;
					height: 32px;
					white-space: nowrap;
					cursor: pointer;
					color: #fff;
					text-align: center;
					box-sizing: border-box;
					outline: 0;
					transition: 0.1s;
					font-weight: 500;
					-webkit-user-select: none;
					user-select: none;
					vertical-align: middle;
					-webkit-appearance: none;
					background-color: #2478f2;
					border: 1px solid #dcdfe6;
					border-color: #2478f2;
					padding: 8px 15px;
					font-size: 14px;
					border-radius: 4px;
				}
			}
		}
		.mes-drawer-layout-main {
			padding: 16px;
			box-sizing: border-box;
			flex: 1;
			color: #ffffff;
		}
	}
}
</style>

<style>
.drawer-fade-enter-active,
.drawer-fade-leave-active {
	transition: opacity 0.3s ease;
}

.drawer-fade-enter,
.drawer-fade-leave-to {
	opacity: 0;
}
</style>

 使用方式:

<template>
    <Drawer
	    v-model="showDrawer"
	    width="500px"
	    title="抽屉"
	    @before-close="drawerBeforeClose"
	    @on-sure="handleDrawerSure"
	    @on-cancel="handleDrawerCancel"
    >
        <p>This is the drawer content</p>
    </Drawer>
</template>

<script setup lang="ts">
import { ref } from "vue";
import Drawer from "@/components/Drawer/index.vue";
const showDrawer = ref(false);
const handleShowDetails = () => {
	console.log("跳转到详情页");
	showDrawer.value = true;
};
const drawerBeforeClose = () => {
	console.log("抽屉关闭前");
	showDrawer.value = false;
};
const handleDrawerSure = () => {
	console.log("抽屉确认");
	showDrawer.value = false;
};
const handleDrawerCancel = () => {
	console.log("抽屉取消");
	showDrawer.value = false;
};

</script>

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2044637.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Linux网络:基于OS的网络架构

Linux网络&#xff1a;OS视角下的网络架构 网络分层模型OSI 七层模型TCP/IP 五层模型 协议操作系统与网络网络相关命令ifconfigpingnetstat 本博客将基于操作系统&#xff0c;讲解计算机网络的设计理念&#xff0c;帮助大家理解操作系统与网络之间的关系。 网络分层模型 网络…

DIAdem 与 LabVIEW

DIAdem 和 LabVIEW 都是 NI (National Instruments) 公司开发的产品&#xff0c;尽管它们有不同的核心功能和用途&#xff0c;但它们在工程、测试和测量领域中常常一起使用&#xff0c;以形成一个完整的数据采集、分析、处理和报告生成的解决方案。 1. 功能和用途 LabVIEW (Lab…

杭州造价信息_杭州造价信息网建设工程材料信息价

杭州造价信息&#xff0c;全称为《杭州造价信息》&#xff0c;简称为“杭州市信息价”或“杭州市建材信息价”&#xff0c;是杭州市建设工程主管部门发布的建筑建材市场指导价&#xff0c;也是杭州市建筑工程项目招标与结算的建材价格标准。这一信息由杭州市住建局或共享建材汇…

【深度学习基础】关于卷积神经网络你了解多少?

文章目录 卷积稀疏交互参数共享池化层全连接层转置卷积空洞卷积卷积神经网络与全连接神经网络 本篇博客主要是讲解一些本人对于卷积的理解&#xff0c;包括&#xff1a; 为什么会出现卷积操作&#xff1f;最基本的卷积操作&#xff1f;卷积的优缺点。空洞卷积等等。卷积操作牵扯…

启明智显借 AI 之翼重塑人机交互,强劲赋能智能硬件升级腾飞

在科技日新月异的今天&#xff0c;启明智显作为人机交互&#xff08;HMI&#xff09;与物联网人工智能&#xff08;AIoT&#xff09;硬件领域的领航者&#xff0c;正以前所未有的决心和行动力&#xff0c;推动着智能硬件行业的深刻变革。公司不仅致力于将最先进的人工智能技术融…

Java 中高级面试题:16题

1. Java 中有哪些不同类型的线程优先级&#xff1f;JVM 分配的线程默认优先级是多少&#xff1f; 线程优先级是这样的概念&#xff1a;每个线程都有一个优先级&#xff0c;用外行人的语言来说&#xff0c;可以说每个对象都有优先级&#xff0c;用 1 到 10 之间的数字表示。Jav…

Openleyer 获取features样式

目录 一、需求说明&#xff1a; 二、业务功能分析&#xff1a; 三、地图点击事件 四、地图要素select事件 五、地图双击事件 六、移动到地图点事件 一、需求说明&#xff1a; 若聚合情况下&#xff0c;点击聚合要素&#xff0c;若只有一个要素&#xff0c;则显示详情信息…

【安卓】WebView的用法与HTTP访问网络

文章目录 WebView的用法使用http访问网络使用HttpURLConnection使用OkHttp 前些天发现了一个巨牛的人工智能学习网站&#xff0c;通俗易懂&#xff0c;风趣幽默&#xff0c;忍不住分享一下给大家。 点击跳转到网站。 WebView的用法 新建一个WebViewTest项目&#xff0c;然后修…

管易云与金蝶K3-WISE对接集成发货单查询打通新增其他出库

管易云与金蝶K3-WISE对接集成发货单查询打通新增其他出库 对接系统&#xff1a;管易云 管易云是金蝶旗下专注提供电商企业管理软件服务的子品牌&#xff0c;先后开发了C-ERP、EC-OMS、EC-WMS、E店管家、BBC、B2B、B2C商城网站建设等产品和服务&#xff0c;涵盖电商业务全流程。…

本地连接服务器上docker中的redis

在上一篇本地连接服务器redis这篇文章中详细介绍了。 这里连接服务器中docker中的redis&#xff0c;同样的操作步骤 1.看一下服务器上redis实例的运行状态&#xff1a; [rootiZuf67k70ucx14s6zcv54dZ var]# ps aux | grep redis-server若显示&#xff1a; 则说明服务器上do…

Denser Retriever: RAG中更强大的AI检索器,让您10 分钟内构建聊天机器人应用

一、Denser Retriever 介绍 Denser Retriever 是一个企业级的RAG检索器&#xff0c;将多种搜索技术整合到一个平台中。在MTEB数据集上的实验表明&#xff0c;Denser Retriever可以显著提升向量搜索&#xff08;VS&#xff09;的基线&#xff08;snowflake-arctic-embed-m模型,…

如何在PyCharm使用conda虚拟环境,如何使用远程Linux系统上的conda虚拟环境。

目录 在PyCharm使用conda虚拟环境&#xff08;windows&#xff09; 使用远程Linux系统上的conda虚拟环境 在PyCharm使用conda虚拟环境&#xff08;windows&#xff09; 首先请创建好虚拟环境 点击输入 conda create -n pyspark python3.8 # conda create -n 名字任取 py…

智谱AI与和鲸科技签署战略合作协议,共拓大模型产业应用与人才培养新未来

8月9日&#xff0c;北京智谱华章科技有限公司&#xff08;智谱 AI&#xff09;与上海和今信息科技有限公司&#xff08;和鲸科技&#xff09;在北京签署战略合作协议。智谱 AI 总裁王绍兰与和鲸科技创始人、CEO 范向伟亲临现场&#xff0c;发表致辞并见证签约。智谱 AI AIGC 事…

Python软件包和PIP镜像下载地址

一、Python软件下载地址 1. 官网下载 https://www.python.org/downloads/ 2. 国内第三方镜像 https://mirrors.huaweicloud.com/python/ https://registry.npmmirror.com/binary.html?pathpython/ 从以上国内镜像即可下载安装程序&#xff0c;Windows平台&#xff0c;不论是In…

网络安全 DVWA通关指南 DVWA File Inclusion(文件包含)

DVWA File Inclusion&#xff08;文件包含&#xff09; 文章目录 DVWA File Inclusion&#xff08;文件包含&#xff09;本地文件包含(LFI)漏洞利用 远程文件包含(RFL)漏洞利用 修复建议 LowMediumHighImpossible 本地文件包含(LFI) 文件包含漏洞的产生原因是 PHP 语言在通过引…

我的世界 异地联机教程 无需公网IP、服务器

主要内容 什么是Minecraft&#xff08;JAVA国际版&#xff09; 搭建该服务&#xff0c;需要准备什么 详细步骤 1.启动器 安装MC并运行MC 2.运行 MoleSDN 进行异地联机 3.小伙伴皮蛋加入鼠鼠的MC 完成联机 什么是我的世界 一款3D沙盒电子游戏&#xff0c;由Mojang Studio…

ComfyUI大猫咪写真工作流,哩布线上一键运行

前言 这次教程是用ComfyUI做的大猫咪写真。 视频教程 打开下面这个网站&#xff0c;点击【在线运行工作流】就可以一键运行ComfyUI工作流了 所有的AI设计工具&#xff0c;模型和插件&#xff0c;都已经整理好了&#xff0c;&#x1f447;获取~ 正面关键词&#xff1a; Chin…

基于二叉树的近似最近邻搜索-Annoy

在推荐系统的召回阶段&#xff0c;会实时计算用户的表征向量&#xff08;user/query&#xff09;&#xff0c;然后去物料库去寻找与用户最匹配的N个物料返回给用户&#xff1b;在搜索系统&#xff0c;也同样存在这样的需求&#xff0c;用户的搜素&#xff08;query&#xff09;…

Efficient DETR:别再随机初始化了,旷视提出单解码层的高效DETR | CVPR 2021

Efficient DETR结合密集检测和稀疏集合检测的优点&#xff0c;利用密集先验来初始化对象容器&#xff0c;弥补单层解码器结构与 6 层解码器结构的差距。在MS COCO上进行的实验表明&#xff0c;仅 3 个编码器层和 1 个解码器层即可实现与最先进的目标检测方法竞争的性能&#xf…

指针函数与函数指针的区别

1、指针函数 1-1、定义 指针函数&#xff0c;顾名思义&#xff0c;是一个函数&#xff0c;但其返回类型是指针。这意味着当这个函数被调用时&#xff0c;它会返回一个地址值&#xff0c;这个地址值指向某个类型的数据。 1-2、特点 函数性质&#xff1a;首先&#xff0c;它是…