JS实现可拖曳、可关闭的弹窗效果

实现可拖拽、可关闭的弹窗效果需要借助JavaScript和CSS的帮助。主要的实现步骤如下:

步骤一:HTML结构

先定义一个弹窗的HTML结构,包括一个模态框、一个标题、一个内容和两个关闭按钮:

<div class="modal">
  <div class="modal-header">
    <h3 class="modal-title">弹窗标题</h3>
    <button class="btn-close">&times;</button>
  </div>
  <div class="modal-body">
    <p>弹窗内容</p>
  </div>
  <button class="btn-close btn-close-modal">&times;</button>
</div>

其中,.modal是弹窗的容器,.modal-header是弹窗标题的容器,.modal-title是弹窗标题,.btn-close是用于关闭弹窗的按钮,.modal-body是弹窗内容的容器,.btn-close-modal是关闭弹窗按钮的一部分,点击弹窗内容部分也可以关闭弹窗。

步骤二:CSS样式

CSS样式主要是用于定义弹窗的基本样式、位置和动画效果。

.modal {
  position: absolute;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
  border: 1px solid #ccc;
  background-color: #fff;
  box-shadow: 0 0 10px #aaa;
  z-index: 100;
  display: none;
}

.modal-header {
  padding: 10px;
  background-color: #eee;
  cursor: move;
}

.modal-body {
  padding: 10px;
}

.btn-close {
  position: absolute;
  top: 5px;
  right: 10px;
  font-size: 24px;
  cursor: pointer;
}

.btn-close:hover {
  color: #f00;
}

.btn-close-modal {
  position: absolute;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  cursor: default;
}

.fade-in {
  animation: fade-in 0.3s;
}

.fade-out {
  animation: fade-out 0.3s;
}

@keyframes fade-in {
  from {
    opacity: 0;
  }
  to {
    opacity: 1;
  }
}

@keyframes fade-out {
  from {
    opacity: 1;
  }
  to {
    opacity: 0;
  }
}

其中,.modalposition设置为绝对定位,topleft设置为50%,以便将弹窗居中显示。transform属性用于偏移弹窗,使其相对于中心点水平和垂直居中。

.modal-header中,padding设置为10像素,background-color设置为灰色,cursor设置为move,以便实现拖动弹窗的效果。

.btn-close中,position设置为绝对定位,topright设置为5像素和10像素,使关闭按钮出现在右上角;font-size设置为24像素,使关闭按钮更加显眼;cursor设置为pointer,使鼠标光标变成小手形状。

.fade-in.fade-out是用于实现弹窗的动画效果,fade-in代表淡入,fade-out代表淡出。在动画过程中,会逐渐改变弹窗的透明度(opacity)。

步骤三:JS实现

创建弹窗

先定义一个Modal类,用于创建一个新的弹窗。该类的构造函数接受一个表示弹窗标题的字符串和一个表示弹窗内容的字符串。

class Modal {
  constructor(title, content) {
    this.title = title;
    this.content = content;
    this.modal = null;
    this.init();
  }

  init() {
    this.createModal();
    this.addEventListeners();
  }

  createModal() {
    this.modal = document.createElement("div");
    this.modal.classList.add("modal");

    const header = document.createElement("div");
    header.classList.add("modal-header");

    const title = document.createElement("h3");
    title.classList.add("modal-title");
    title.textContent = this.title;

    const btnClose = document.createElement("button");
    btnClose.classList.add("btn-close");
    btnClose.innerHTML = "&times;";

    header.appendChild(title);
    header.appendChild(btnClose);

    const body = document.createElement("div");
    body.classList.add("modal-body");
    body.innerHTML = this.content;

    this.modal.appendChild(header);
    this.modal.appendChild(body);

    document.body.appendChild(this.modal);
  }

  ...
}

其中,createModal()方法用于动态创建弹窗。通过document.createElement()方法创建了若干个DOM元素,再通过appendChild()方法组装起来,最终添加到document.body中。

弹窗的显示与隐藏

若要弹窗显示需要先调用一个show()方法,弹窗会通过JS的类名添加类名,从而达到一个动态的效果

show() {
  this.modal.classList.add("fade-in");
  this.modal.style.display = "block";
  document.body.style.overflow = "hidden";
}

当弹窗的关闭按钮或者内容区域被点击时,可以通过调用hide()方法关闭弹窗。这个方法跟show()方法加入的类名相似,只是添加的是类名为fade-out,表示关闭的过程

hide() {
  this.modal.classList.add("fade-out");
  setTimeout(() => {
    this.modal.style.display = "none";
    this.modal.classList.remove("fade-in", "fade-out");
    document.body.style.overflow = "auto";
  }, 300);
}

弹窗的拖动

Modal类中添加一个名为dragElement的方法,用于实现弹窗的拖动。在该方法内,需要操控mousedownmouseupmousemove等事件,从而实现拖动弹窗。

dragElement() {
  const header = this.modal.querySelector(".modal-header");
  let x = 0;
  let y = 0;

  header.addEventListener("mousedown", startDrag);

  function startDrag(e) {
    e.preventDefault();
    x = e.clientX;
    y = e.clientY;
    document.addEventListener("mousemove", onDrag);
    document.addEventListener("mouseup", stopDrag);
  }

  function onDrag(e) {
    e.preventDefault();
    const deltaX = e.clientX - x;
    const deltaY = e.clientY - y;
    const modalRect = this.modal.getBoundingClientRect();

    this.modal.style.top = `${modalRect.top + deltaY}px`;
    this.modal.style.left = `${modalRect.left + deltaX}px`;

    x = e.clientX;
    y = e.clientY;
  }

  function stopDrag() {
    document.removeEventListener("mousemove", onDrag);
    document.removeEventListener("mouseup", stopDrag);
  }
}

其中,mousedown事件监听在标题栏上,当事件触发时,事件回调函数startDrag会记录鼠标按下时的坐标。mousemove事件监听在整个文档上,它的回调函数onDrag会计算出鼠标和标题栏的距离差值,并将其添加到弹窗的topleft样式属性上,从而实现弹窗的拖动效果。

示例一:自定义消息弹窗

// HTML结构
<div id="alert-modal" class="modal" style="display: none;">
  <div class="modal-header">
    <h4 class="modal-title">提示</h4>
    <button class="btn-close">&times;</button>
  </div>
  <div class="modal-body">
    <p id="alert-message"></p>
  </div>
</div>

// CSS样式
.modal {
  position: absolute;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
  border-radius: 8px;
  box-shadow: 0px 0px 10px rgba(0, 0, 0, 0.5);
  background-color: #fff;
  width: 400px;
  z-index: 100;
  display: none;
}
.modal .modal-header {
  padding: 15px;
  border-bottom: 1px solid #eee;
  text-align: center;
  font-size: 20px;
  font-weight: bold;
  position: relative;
}
.modal .modal-header .btn-close {
  position: absolute;
  top: 5px;
  right: 5px;
  font-size: 20px;
  cursor: pointer;
  outline: none;
  border: none;
  background-color: transparent;
}
.modal .modal-body {
  padding: 15px;
}

// JS代码
class AlertModal {
  constructor(message) {
    this.message = message;
    this.init();
  }

  init() {
    this.alertModal = document.getElementById("alert-modal");
    this.alertMessage = document.getElementById("alert-message");
    this.alertMessage.textContent = this.message;
    this.btnClose = this.alertModal.querySelector(".btn-close");
    this.addEventListeners();
  }

  addEventListeners() {
    this.btnClose.addEventListener("click", this.hide.bind(this));
    this.alertModal.addEventListener("click", this.handleModalClick.bind(this));
    window.addEventListener("keyup", this.handleKeyUp.bind(this));
  }

  show() {
    this.alertModal.classList.add("fade-in");
    this.alertModal.style.display = "block";
    document.body.style.overflow = "hidden";
  }

  hide() {
    this.alertModal.classList.add("fade-out");
    setTimeout(() => {
      this.alertModal.style.display = "none";
      this.alertModal.classList.remove("fade-in", "fade-out");
      document.body.style.overflow = "auto";
    }, 300);
  }

  handleModalClick(e) {
    if (e.target === this.alertModal) {
      this.hide();
    }
  }

  handleKeyUp(e) {
    if (e.key === "Escape") {
      this.hide();
    }
  }
}

const btnAlert = document.getElementById("btn-alert");
btnAlert.addEventListener("click", handleAlertClick);

function handleAlertClick() {
  const message = "您好,欢迎访问该网站!";
  const alertModal = new AlertModal(message);
  alertModal.show();
}

示例二:加载中的遮罩弹窗

// HTML结构
<div id="loading-modal" class="modal" style="display: none;">
  <div class="modal-body">
    <div class="loader"></div>
  </div>
</div>

// CSS样式
.modal .modal-body {
  padding: 0;
  background-color: transparent;
}
.modal .modal-body .loader {
  border: 16px solid #f3f3f3; /* Light grey */
  border-top: 16px solid #3498db; /* Blue */
  border-radius: 50%;
  width: 120px;
  height: 120px;
  animation: spin 2s linear infinite;
  margin: auto;
}
@keyframes spin {
  0% {
    transform: rotate(0deg);
  }
  100% {
    transform: rotate(360deg);
  }
}

// JS代码
class LoadingModal {
  constructor() {
    this.init();
  }

  init() {
    this.loadingModal = document.getElementById("loading-modal");
  }

  show() {
    this.loadingModal.style.display = "block";
  }

  hide() {
    this.loadingModal.style.display = "none";
  }
}

const btnLoading = document.getElementById("btn-loading");
btnLoading.addEventListener("click", handleLoadingClick);

function handleLoadingClick() {
  const loadingModal = new LoadingModal();
  loadingModal.show();

  setTimeout(function () {
    loadingModal.hide();
  }, 2000);
}

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:JS实现可拖曳、可关闭的弹窗效果 - Python技术站

(0)
上一篇 2023年6月11日
下一篇 2023年6月11日

相关文章

  • 详解JavaScript的Date对象(制作简易钟表)

    详解JavaScript的Date对象(制作简易钟表) 介绍 JavaScript中内置了一个Date对象,用于处理日期和时间。此对象使得我们能够轻松地获取当前时间和日期,并执行各种与时间相关的操作。 在本攻略中,我们将使用Date对象制作一个简易钟表,来展示Date对象的用法。 步骤 步骤1:创建HTML文档骨架 首先,我们需要创建一个HTML文档骨架,并…

    JavaScript 2023年5月27日
    00
  • Canvas drawImage方法实现图片压缩详解

    Canvas的drawImage方法可以用来实现图片的压缩,下面将详细讲解该方法的使用过程。 drawImage方法简介 Canvas的drawImage方法可以将一个已有的图像绘制到Canvas上。该方法有3种用法: drawImage(image, sx, sy, sWidth, sHeight, dx, dy, dWidth, dHeight) dra…

    JavaScript 2023年6月10日
    00
  • JavaScript中的变量定义与储存介绍

    当我们使用JavaScript编程时,变量是必不可少的元素。变量是用来储存数据的一种容器,包括数字、字符串、布尔值或其他数据类型等。在JavaScript中,变量需要先定义再使用,同时也需要注意变量的作用域。 变量定义 在JavaScript中定义变量需要使用关键字var、let或const。其中,var和let是用来定义可修改的变量,而const用来定义常…

    JavaScript 2023年6月10日
    00
  • javaWeb使用验证码实现简单登录

    JavaWeb使用验证码实现简单登录 需求 在JavaWeb网站中,为登录页面增加验证码功能,防止恶意程序暴力破解密码,提高网站的安全性。 技术栈 前端:HTML、JavaScript 后端:Java、Servlet、JSP 实现步骤 1. 引入验证码jar包 可以使用第三方的验证码生成工具库,这里以Google的kaptcha为例。 在pom.xml文件中…

    JavaScript 2023年6月10日
    00
  • jQuery框架实现元素显示及隐藏三种动画方式

    当我们需要在网站中实现元素的显示与隐藏的动画效果时,可以使用jQuery框架提供的三种动画方式。接下来我将详细讲解JavaScpt框架的三种动画方式的实现方法,让你可以轻松实现网站元素的动画效果。 1. jQuery框架fadeIn/fadeOut实现元素渐隐/渐显 1.1 动画效果简介 当我们需要在网站中实现元素的淡出/淡入效果时,可以使用jQuery框架…

    JavaScript 2023年6月11日
    00
  • javascript 正则表达式用法 小结

    JavaScript 正则表达式用法小结 什么是正则表达式 正则表达式是一种用来匹配字符串的模式。在 JavaScript 中,正则表达式可以用来处理字符串的各种操作,比如查找、替换和提取等等。 正则表达式的基本语法 正则表达式由若干个字符和元字符组成,其中元字符用来指定匹配规则。下面是一些常见的元字符和它们的含义: 元字符 含义 . 匹配任意单个字符。 ^…

    JavaScript 2023年5月28日
    00
  • JS异步代码单元测试之神奇的Promise

    JS异步代码单元测试一直是开发人员要面对的挑战。为了解决这个问题,Promise异步编程模式被引入到JavaScript中,因其简单、灵活和可重用性而受到广泛认可。在本攻略中,我们将深入探讨如何在单元测试中使用Promise,以及如何跟踪异步代码逻辑和处理可能的异步回调。 异步单元测试面临的问题 在传统的单元测试中,我们可以通过直接调用函数、对函数输出结果进…

    JavaScript 2023年5月28日
    00
  • Android中实现WebView和JavaScript的互相调用详解

    在Android中,可以通过WebView组件来实现网页的浏览和展示,同时也可以与JavaScript交互来实现更加丰富的功能。在本篇攻略中,将详细讲解如何在Android中实现WebView和JavaScript的互相调用。 步骤一:设置WebView 首先需要在XML布局文件中定义一个WebView组件,在Java代码中找到它并进行一些设置: <W…

    JavaScript 2023年6月11日
    00
合作推广
合作推广
分享本页
返回顶部