ts class 拖拽实现,支持pc和mobile

看了网上的不少关于拖拽的文章,自己尝试着用es6 的class写了一个拖拽方法,记录一下

配置项
配置项描述默认值
autoAdsord是否开启自动吸边true
adsordConfig吸边的相关配置,接收一个对象, 可以配置等待时间和持续时间{waitTime: 2,durationTime: 1.3}
dragShadow是否开启拖影true
triggerTime启动拖拽的触发时间(长按时长),接收一个number类型,单位是秒2
responseTime拖拽触发后,如果放开的鼠标,在该时间内,可以继续拖拽,接收一个number类型,单位是秒2
class Drag 代码
interface config {
  autoAdsord?: boolean // 自动吸附边缘
  adsordConfig?: adsordConfig // 吸附的相关配置
  triggerTime?: number // 拖拽触发时间
  responseTime?: number // 响应时长,在规定时间内的拖拽行为,都是有效的
  dragShadow: boolean // 是否开启拖影
}
interface adsordConfig {  // 吸附的相关配置
  waitTime: number, // 等待时间
  durationTime: number // 持续时间
}

const defaultConfig: config = { // 默认配置
  autoAdsord: true,
  adsordConfig: {
    waitTime: 2,
    durationTime: 1.3
  },
  triggerTime: 2,
  responseTime: 2,
  dragShadow: true
}

class Drag {
  el: HTMLElement // dom元素
  config: config = defaultConfig // 配置信息
  offsetX: number = 0 // 当前点相距于dom中的X轴位置
  offsetY: number = 0 // 当前点相距于dom中的Y轴位置
  maxW: number = 0 // 最大可移动宽度
  maxH: number = 0 // 最大可移动高度
  equipment: string = 'pc' // 设备类型

  eventDown: string = 'mousedown' // 抓住事件
  eventMove: string = 'mousemove' // 移动事件
  eventUp: string = 'mouseup' // 释放事件

  isDrag: boolean = false // 是否拖拽的标记
  // 用来判断是否要进行拖拽的时间记录器
  isDragTimeId: number | undefined = undefined
  // 用来清除(中断)改变isDrag属性的定时器,为了能自己控制何时来关闭、是否继续关闭
  clearDragTimeId: number | undefined = undefined

  // 自动吸边的定时器,大的外层的
  adsordTimeId: number | undefined = undefined
  // 自动吸边的定时器,小的内层的
  adsordTimeIdInner: number | undefined = undefined

  constructor(el: HTMLElement, config: config = defaultConfig) {
    // dom对象
    this.el = el
    // 初始化配置
    this.config = {
      ...config,
      ...defaultConfig
    }
    // 设备类型
    this.equipment = this.iswap()
    // 将当前dom设置成绝对定位
    this.el.style.position = 'fixed';
    this.el.style.zIndex = '999'
    // 根据设备类型挂载不同的事件
    switch (this.equipment) {
      case 'pc':
        this.eventDown = 'mousedown'
        this.eventMove = 'mousemove'
        this.eventUp = 'mouseup'
        break
      case 'mobile':
        this.eventDown = 'touchstart'
        this.eventMove = 'touchmove'
        this.eventUp = 'touchend'
        break
    }
    this.onDown()
  }
  /******************监听行为***********************/
  // 按下
  onDown() {
    this.el.addEventListener(this.eventDown, this.start)
  }
  // 移动
  onMove() {
    document.addEventListener(this.eventMove, this.move);
  }
  // 抬起
  onUp() {
    // 鼠标放开时,移除事件
    document.addEventListener(this.eventUp, this.stop);
  }
  start = (event: any) => {
    /* button: [(0 鼠标左键) , (1 鼠标滚轮) , (2 鼠标右键)]*/
    // 当鼠标左键按住时 和 设备为mobile时,获取一下初始点的位置,并挂载监听事件
    if ((event as MouseEvent).button == 0 || this.equipment === 'mobile') {
      // 新的点击来了,先清除上轮拖拽留下的关闭isDrag的定时器
      // 理由:为了保证,用户在触发了拖拽之后,短时间内仍然想继续拖拽,这是就不能重置拖拽属性isDrag,
      // 所以通过定时器clearDragTimeId 来控制,在responseTime响应时间的(鼠标、手指)按下行为将清除此定时器,来中断 重置isDrag属性的操作
      clearTimeout(this.clearDragTimeId)

      // 移动前,先清除吸边动画的定时器
      this.config.autoAdsord && this.clearAdsord()
      // 鼠标按下时,获取当前按下的点可移动的最大位置
      this.maxW = document.documentElement.clientWidth - this.el.offsetWidth
      this.maxH = document.documentElement.clientHeight - this.el.offsetHeight
      /* getComputedStyle: 一个可以获取当前元素所有最终使用的CSS属性值。返回的是一个CSS样式声明对象([object CSSStyleDeclaration]),只读。 */
      const lexObj: any = getComputedStyle(this.el);
      // 获取当前触点
      let { pointX, pointY } = this.getPoint(event)
      // 获取点击的位置相对于dom中的位置,如果设置了margin,就把margin的大小也算上
      this.offsetX = pointX - this.el.offsetLeft + parseInt(lexObj['margin-left']);
      this.offsetY = pointY - this.el.offsetTop + parseInt(lexObj['margin-top']);
      // 绑定移动监听
      this.onMove()
      // 绑定结束监听
      this.onUp()
      // 拖拽的触发机制,鼠标或手指悬停 triggerTime 的时长,以便确认是否触发拖拽事件
      this.setIsDarg()
    }
  }
  move = (event: any) => {
    /***************是否移动的前置判断***************************/
    // 取消对move事件进行绑定的定时器,通过判断(鼠标、手指)按下  到  移动的这段时间的长度来确定用户是否要进行拖拽事件
    clearTimeout(this.isDragTimeId)
    // 如果不允许拖拽就停止执行
    if (!this.isDrag) return
    /*******************移动开始**************************************/
    // 移动前,先清除吸边动画的定时器
    this.config.autoAdsord && this.clearAdsord()
    // 将dom对象的事件监听取消
    this.el.style.pointerEvents = 'none'
    // 不允许选中里面的任何元素
    this.el.style.userSelect = 'none'
    // 鼠标变小手
    // 获取当前鼠标所在的位置与按下时的鼠标位置的距离
    let { pointX, pointY } = this.getPoint(event)
    let x = pointX - this.offsetX;
    let y = pointY - this.offsetY;
    if (x < 0) { // 如果鼠标已经移动到dom的【左】边缘了,就别让它再出去了,设置为0
      x = 0;
    } else if (x > this.maxW) {
      // 如果鼠标已经移动到dom的【右】边缘了,就别让它再出去了,设置为可视窗口的宽度减去dom自身的宽度
      x = this.maxW
    }
    if (y < 0) {  // 如果鼠标已经移动到dom的【上】边缘了,就别让它再出去了,设置为0
      y = 0;
    } else if (y > this.maxH) {
      // 如果鼠标已经移动到dom的【下】边缘了,就别让它再出去了,设置为可视窗口的高度减去dom自身的高度
      y = this.maxH
    }
    // 将值应用到绝对定位位置上
    this.el.style.left = x + 'px';
    this.el.style.top = y + 'px';
    // 开启拖影效果
    if (this.config.dragShadow) {
      this.setDragShadow()
    }
  }
  stop = () => {
    clearTimeout(this.isDragTimeId)
    // 样式还原
    this.el.style.pointerEvents = ''
    this.el.style.userSelect = 'text'
    // 移除事件监听
    document.removeEventListener(this.eventMove, this.move);
    document.removeEventListener(this.eventUp, this.stop);
    // 如果配置了自动吸边则吸边
    this.config.autoAdsord && this.setAdsord()

    // 拖拽结束,重置拖拽属性为不可拖拽
    this.clearDragTimeId = setTimeout(() => {
      this.resetIsDarg()
    }, (this.config.responseTime ?? 0) * 1000)
  }
  // 获取当前 触点 的位置
  getPoint(event: MouseEvent | TouchEvent) {
    let pointX = 0
    let pointY = 0
    switch (this.equipment) {
      case 'pc':
        pointX = (event as MouseEvent).pageX
        pointY = (event as MouseEvent).pageY
        break
      case 'mobile':
        var touch = (event as TouchEvent).targetTouches[0];
        pointX = touch.clientX
        pointY = touch.clientY
        break
    }
    return {
      pointX,
      pointY
    }
  }
  /******************吸附事件***********************/
  // 自动吸附
  setAdsord() {
    this.adsordTimeId = setTimeout(() => {
      // 当前位置
      // console.log(el.offsetLeft, el.offsetTop)
      // 计算dom中心点处于屏幕的那一侧,决定吸附哪一边
      // 容器中心点距离屏幕左侧的宽度
      let domCenterX = this.el.offsetWidth / 2 + this.el.offsetLeft
      // 可视窗口中心点的宽度
      let screenCenterX = window.innerWidth / 2
      // 动画的持续时间
      let animationTime = this.config.adsordConfig?.durationTime ?? 0
      this.el.style.transition = animationTime + 's'

      // 决定了dom将要往哪边靠
      if (domCenterX > screenCenterX) {
        //console.log('在右侧')
        this.el.style.left = this.maxW + 'px'
      } else {
        // console.log('在左侧')
        this.el.style.left = '0'
      }

      // 延时执行,动画将会执行animationTime的时间,而在时间到的时候,需要将一些参数重置
      this.adsordTimeIdInner = setTimeout(() => {
        // 取消transition动画
        this.el.style.transition = ''
        // 在向右靠边时,如果窗口发生了变化,需要将当前dom紧贴在右侧
        if (domCenterX > screenCenterX) {
          this.el.style.left = ''
          this.el.style.right = '0'
        }
      }, animationTime * 1000)
    }, (this.config.adsordConfig?.waitTime ?? 0) * 1000)
  }
  // 清除自动吸附
  clearAdsord() {
    clearTimeout(this.adsordTimeIdInner)
    clearTimeout(this.adsordTimeId)
    this.el.style.transition = ''
  }
  /******************是否拖拽***********************/
  // 挂载监听时长,开启拖拽
  setIsDarg() {
    this.isDragTimeId = setTimeout(() => {
      this.isDrag = true
      this.el.style.cursor = 'pointer'
      this.el.style.transform = 'scale(1.1)'
    }, (this.config.triggerTime ?? 0) * 1000)
  }
  // 关闭拖拽
  resetIsDarg() {
    clearTimeout(this.isDragTimeId)
    this.isDrag = false
    this.el.style.cursor = 'auto'
    this.el.style.transform = 'scale(1)'
  }
  /******************判断设备类型***********************/
  // 判断设备类型
  iswap(): string {
    let uA: string = navigator.userAgent.toLowerCase();
    let ipad: boolean = uA.match(/ipad/i) !== null;
    let iphone: boolean = uA.match(/iphone os/i) !== null;
    let midp: boolean = uA.match(/midp/i) !== null;
    let uc7: boolean = uA.match(/rv:1.2.3.4/i) !== null;
    let uc: boolean = uA.match(/ucweb/i) !== null
    let android: boolean = uA.match(/android/i) !== null;
    let windowsce: boolean = uA.match(/windows ce/i) !== null;
    let windowsmd: boolean = uA.match(/windows mobile/i) !== null;
    if (!(ipad || iphone || midp || uc7 || uc || android || windowsce || windowsmd)) {
      // PC 端
      return 'pc'
    } else {
      // 移动端
      return 'mobile'
    }
  }
  /******************拖影特效***********************/
  /*
    不得不说,这个拖影真卡,卡的情况只在打开了控制台的时候,不开控制台,就感觉不到
  */
  // 利用定时器,生成一个图形,过段时间在销毁
  setDragShadow() {
    let newEle = document.createElement("div")
    newEle.style.width = this.el.offsetWidth + 'px'
    newEle.style.height = this.el.offsetWidth + 'px'
    newEle.style.background = 'rgba(0,0,0,0.05)'
    newEle.style.position = 'fixed';
    newEle.style.left = String(parseInt(this.el.style.left)) + 'px';
    newEle.style.top = String(parseInt(this.el.style.top)) + 'px';
    newEle.style.opacity = '1'
    newEle.style.zIndex = '0'
    newEle.style.transition = 1 + 's'
    newEle.style.filter = 'blur(2px)'
    let opacity = 1
    document.body.appendChild(newEle)
    let opacityTimeId = setInterval(() => {
      if (newEle.style.opacity <= '0') {
        clearInterval(opacityTimeId)
        newEle.remove()
      } else {
        newEle.style.opacity = String(Number(newEle.style.opacity) - 0.4)
      }
    }, 100)
  }
  /******************销毁***********************/
  destory() {
    /* 页面离开时,销毁挂载在dom上的监听事件
      其实好像也没必要,dom都不存在了,垃圾回收机制应该也会将与dom相关的,不再被引用的变量、方法一并回收了
    */
    this.el.removeEventListener(this.eventDown, this.start)
  }
}

export default Drag

js
  // 拖拽方法
  const defaultConfig = { // 默认配置
    autoAdsord: true, // 是否开启自动吸边
    adsordConfig: { // 吸边的相关配置,接收一个对象, 可以配置等待时间和持续时间
      waitTime: 1,
      durationTime: 0.5
    },
    triggerTime: 0, // 启动拖拽的触发时间(长按时长),接收一个number类型,单位是秒
    responseTime: 0, // 拖拽触发后,如果放开的鼠标,在该时间内,可以继续拖拽,接收一个number类型,单位是秒
    dragShadow: false // 拖影是否开启
  }

  class Drag {
    el // dom元素
    config = defaultConfig // 配置信息
    offsetX = 0 // 当前点相距于dom中的X轴位置
    offsetY = 0 // 当前点相距于dom中的Y轴位置
    maxW = 0 // 最大可移动宽度
    maxH = 0 // 最大可移动高度
    equipment = 'pc' // 设备类型

    eventDown = 'mousedown' // 抓住事件
    eventMove = 'mousemove' // 移动事件
    eventUp = 'mouseup' // 释放事件

    isDrag = false // 是否拖拽的标记
    // 用来判断是否要进行拖拽的时间记录器
    isDragTimeId = undefined
    // 用来清除(中断)改变isDrag属性的定时器,为了能自己控制何时来关闭、是否继续关闭
    clearDragTimeId = undefined

    // 自动吸边的定时器,大的外层的
    adsordTimeId = undefined
    // 自动吸边的定时器,小的内层的
    adsordTimeIdInner = undefined

    constructor(el, config = defaultConfig) {
      // dom对象
      this.el = el
      // 初始化配置
      this.config = {
        ...defaultConfig,
        ...config
      }
      // 设备类型
      this.equipment = this.iswap()
      // 将当前dom设置成绝对定位
      this.el.style.position = 'fixed';
      this.el.style.zIndex = '999'
      // 根据设备类型挂载不同的事件
      switch (this.equipment) {
        case 'pc':
          this.eventDown = 'mousedown'
          this.eventMove = 'mousemove'
          this.eventUp = 'mouseup'
          break
        case 'mobile':
          this.eventDown = 'touchstart'
          this.eventMove = 'touchmove'
          this.eventUp = 'touchend'
          break
      }
      this.onDown()
    }
    /******************监听行为***********************/
    // 按下
    onDown() {
      this.el.addEventListener(this.eventDown, this.start)
    }
    // 移动
    onMove() {
      document.addEventListener(this.eventMove, this.move, { passive: true });
    }
    // 抬起
    onUp() {
      // 鼠标放开时,移除事件
      document.addEventListener(this.eventUp, this.stop);
    }
    start = (event) => {
      // 拖拽式,禁用body的滚动行为,否则在移动端会变卡
      document.body.addEventListener('touchmove', this.bodyScroll, { passive: false });
      /* button: [(0 鼠标左键) , (1 鼠标滚轮) , (2 鼠标右键)]*/
      // 当鼠标左键按住时 和 设备为mobile时,获取一下初始点的位置,并挂载监听事件
      if ((event).button == 0 || this.equipment === 'mobile') {
        // 新的点击来了,先清除上轮拖拽留下的关闭isDrag的定时器
        // 理由:为了保证,用户在触发了拖拽之后,短时间内仍然想继续拖拽,这是就不能重置拖拽属性isDrag,
        // 所以通过定时器clearDragTimeId 来控制,在responseTime响应时间的(鼠标、手指)按下行为将清除此定时器,来中断 重置isDrag属性的操作
        clearTimeout(this.clearDragTimeId)

        // 移动前,先清除吸边动画的定时器
        this.config.autoAdsord && this.clearAdsord()
        // 鼠标按下时,获取当前按下的点可移动的最大位置
        this.maxW = document.documentElement.clientWidth - this.el.offsetWidth
        this.maxH = document.documentElement.clientHeight - this.el.offsetHeight
        /* getComputedStyle: 一个可以获取当前元素所有最终使用的CSS属性值。返回的是一个CSS样式声明对象([object CSSStyleDeclaration]),只读。 */
        const lexObj = getComputedStyle(this.el);
        // 获取当前触点
        let { pointX, pointY } = this.getPoint(event)
        // 获取点击的位置相对于dom中的位置,如果设置了margin,就把margin的大小也算上
        this.offsetX = pointX - this.el.offsetLeft + parseInt(lexObj['margin-left']);
        this.offsetY = pointY - this.el.offsetTop + parseInt(lexObj['margin-top']);
        // 绑定移动监听
        this.onMove()
        // 绑定结束监听
        this.onUp()
        // 拖拽的触发机制,鼠标或手指悬停 triggerTime 的时长,以便确认是否触发拖拽事件
        this.setIsDarg()
      }
    }
    move = (event) => {
      /***************是否移动的前置判断***************************/
      // 取消对move事件进行绑定的定时器,通过判断(鼠标、手指)按下  到  移动的这段时间的长度来确定用户是否要进行拖拽事件
      clearTimeout(this.isDragTimeId)
      // 如果不允许拖拽就停止执行
      if (!this.isDrag) return
      /*******************移动开始**************************************/
      // 移动前,先清除吸边动画的定时器
      this.config.autoAdsord && this.clearAdsord()
      // 将dom对象的事件监听取消
      this.el.style.pointerEvents = 'none'
      // 不允许选中里面的任何元素
      this.el.style.userSelect = 'none'
      // 鼠标变小手
      // 获取当前鼠标所在的位置与按下时的鼠标位置的距离
      let { pointX, pointY } = this.getPoint(event)
      let x = pointX - this.offsetX;
      let y = pointY - this.offsetY;
      if (x < 0) { // 如果鼠标已经移动到dom的【左】边缘了,就别让它再出去了,设置为0
        x = 0;
      } else if (x > this.maxW) {
        // 如果鼠标已经移动到dom的【右】边缘了,就别让它再出去了,设置为可视窗口的宽度减去dom自身的宽度
        x = this.maxW
      }
      if (y < 0) {  // 如果鼠标已经移动到dom的【上】边缘了,就别让它再出去了,设置为0
        y = 0;
      } else if (y > this.maxH) {
        // 如果鼠标已经移动到dom的【下】边缘了,就别让它再出去了,设置为可视窗口的高度减去dom自身的高度
        y = this.maxH
      }
      // 将值应用到绝对定位位置上
      this.el.style.left = x + 'px';
      this.el.style.top = y + 'px';
      // 开启拖影效果
      // if (this.config.dragShadow) {
      //   this.setDragShadow()
      // }
    }
    stop = () => {
      clearTimeout(this.isDragTimeId)
      // 样式还原
      this.el.style.pointerEvents = ''
      this.el.style.userSelect = 'text'
      // 移除事件监听
      document.removeEventListener(this.eventMove, this.move);
      document.removeEventListener(this.eventUp, this.stop);
      // 如果配置了自动吸边则吸边
      this.config.autoAdsord && this.setAdsord()

      // 拖拽结束,重置拖拽属性为不可拖拽
      this.clearDragTimeId = setTimeout(() => {
        this.resetIsDarg()
      }, (this.config.responseTime ?? 0) * 1000)
      document.body.removeEventListener('touchmove', this.bodyScroll, { passive: false });
    }
    // 获取当前 触点 的位置
    getPoint(event) {
      let pointX = 0
      let pointY = 0
      switch (this.equipment) {
        case 'pc':
          pointX = (event).pageX
          pointY = (event).pageY
          break
        case 'mobile':
          var touch = (event).targetTouches[0];
          pointX = touch.clientX
          pointY = touch.clientY
          break
      }
      return {
        pointX,
        pointY
      }
    }
    /******************吸附事件***********************/
    // 自动吸附
    setAdsord() {
      this.adsordTimeId = setTimeout(() => {
        // 当前位置
        // console.log(el.offsetLeft, el.offsetTop)
        // 计算dom中心点处于屏幕的那一侧,决定吸附哪一边
        // 容器中心点距离屏幕左侧的宽度
        let domCenterX = this.el.offsetWidth / 2 + this.el.offsetLeft
        // 可视窗口中心点的宽度
        let screenCenterX = window.innerWidth / 2
        // 动画的持续时间
        let animationTime = this.config.adsordConfig?.durationTime ?? 0
        this.el.style.transition = animationTime + 's'

        // 决定了dom将要往哪边靠
        if (domCenterX > screenCenterX) {
          //console.log('在右侧')
          this.el.style.left = this.maxW + 'px'
        } else {
          // console.log('在左侧')
          this.el.style.left = '0'
        }

        // 延时执行,动画将会执行animationTime的时间,而在时间到的时候,需要将一些参数重置
        this.adsordTimeIdInner = setTimeout(() => {
          // 取消transition动画
          this.el.style.transition = ''
          // 在向右靠边时,如果窗口发生了变化,需要将当前dom紧贴在右侧
          if (domCenterX > screenCenterX) {
            this.el.style.left = ''
            this.el.style.right = '0'
          }
        }, animationTime * 1000)
      }, (this.config.adsordConfig?.waitTime ?? 0) * 1000)
    }
    // 清除自动吸附
    clearAdsord() {
      clearTimeout(this.adsordTimeIdInner)
      clearTimeout(this.adsordTimeId)
      this.el.style.transition = ''
    }
    /******************是否拖拽***********************/
    // 挂载监听时长,开启拖拽
    setIsDarg() {
      this.isDragTimeId = setTimeout(() => {
        this.isDrag = true
        this.el.style.cursor = 'pointer'
        this.el.style.transform = 'scale(1.1)'
      }, (this.config.triggerTime ?? 0) * 1000)
    }
    // 关闭拖拽
    resetIsDarg() {
      clearTimeout(this.isDragTimeId)
      this.isDrag = false
      this.el.style.cursor = 'auto'
      this.el.style.transform = 'scale(1)'

    }
    /******************判断设备类型***********************/
    // 判断设备类型
    iswap() {
      let uA = navigator.userAgent.toLowerCase();
      let ipad = uA.match(/ipad/i) !== null;
      let iphone = uA.match(/iphone os/i) !== null;
      let midp = uA.match(/midp/i) !== null;
      let uc7 = uA.match(/rv:1.2.3.4/i) !== null;
      let uc = uA.match(/ucweb/i) !== null
      let android = uA.match(/android/i) !== null;
      let windowsce = uA.match(/windows ce/i) !== null;
      let windowsmd = uA.match(/windows mobile/i) !== null;
      if (!(ipad || iphone || midp || uc7 || uc || android || windowsce || windowsmd)) {
        // PC 端
        return 'pc'
      } else {
        // 移动端
        return 'mobile'
      }
    }
    /******************拖影特效***********************/
    /*
      不得不说,这个拖影真卡,卡的情况只在打开了控制台的时候,不开控制台,就感觉不到
    */
    // 利用定时器,生成一个图形,过段时间在销毁
    setDragShadow() {
      let newEle = document.createElement("div")
      newEle.style.width = this.el.offsetWidth + 'px'
      newEle.style.height = this.el.offsetWidth + 'px'
      newEle.style.background = 'rgba(0,0,0,0.05)'
      newEle.style.position = 'fixed';
      newEle.style.left = String(parseInt(this.el.style.left)) + 'px';
      newEle.style.top = String(parseInt(this.el.style.top)) + 'px';
      newEle.style.opacity = '1'
      newEle.style.zIndex = '0'
      newEle.style.transition = 1 + 's'
      newEle.style.filter = 'blur(2px)'
      let opacity = 1
      document.body.appendChild(newEle)
      let opacityTimeId = setInterval(() => {
        if (newEle.style.opacity <= '0') {
          clearInterval(opacityTimeId)
          newEle.remove()
        } else {
          newEle.style.opacity = String(Number(newEle.style.opacity) - 0.4)
        }
      }, 100)
    }
    /**********移动端卡顿处理**********************/
    // 移动端使用时,会因为滚动条的原因,导致拖拽变卡,在这里处理,滚动时,禁用body的滚动的事件,结束时,在开启
    bodyScroll(event) {
      event.preventDefault();
    }
    /******************销毁***********************/
    destory() {
      /* 页面离开时,销毁挂载在dom上的监听事件
        其实好像也没必要,dom都不存在了,垃圾回收机制应该也会将与dom相关的,不再被引用的变量、方法一并回收了
      */
      this.el.removeEventListener(this.eventDown, this.start)
    }
  }
  • 2
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值