總結 - 常見的JavaScript兼容性問題

添加事件的方法 (元素, 綁定的事件類型, 事件觸發的方法)

addHandler: function (element, type, handler) {
    if (element.addEventListener) { // 判斷是否爲DOM2級方法
      // 最後一個參數指定時間是否在捕獲或者冒泡階段執行
      // true: 事件句柄在捕獲階段執行
      // false: 默認, 事件句柄在冒泡階段執行
      element.addEventListener(type, handler, false)
    } else if (element.attachEvent) { //檢測是否爲IE級方法
      // IE只支持時間冒泡
      element.attachEvent('on' + type, handler)
    } else { //檢測是否爲DOM0級方法
      // element.onclick = handler
      // element[onclick] = handler -> 這種方式能夠向中括號內傳遞變量名
      element['on' + type] = handler
    }
  },

移除以前添加的方法

removeHandler: function (element, type, handler) {
    if (element.removeEventListener) {
      // 若是在element上定義的handler是匿名函數的話, 是沒法被移除的
      // 最後的變量指定是在哪一個階段移除事件, 
      // 若是在兩個階段都有添加事件, 那麼久應該在兩個階段都對事件進行移除
      element.removeEventListener(type, handler, false)
    } else if (element.detachEvent) {
      element.detachEvent(type, handler)
    } else {
      element['on' + type] = null
    }
  },

獲取事件對象, 獲取事件對象目標

// 事件對象, 某個事件觸發的函數中, 參數表示了這個整個事件觸發的一些信息和方法
  // 或者整個事件觸發的一個對象, 裏面包含了這個事件的所有信息. 例如: clickEvent, focusEvent
  getEvent: function (event) {
    return event ? event : window.event
  },
  // target: 表示這個事件發生在哪一個element上.
  getTarget: function (event) {
    return event.target || window.event.target
  },

阻止瀏覽器的默認事件

// 例如a標籤的默認跳轉事件, 表單的回車默認提交事件
  preventDefault: function (event) {
    if (event.preventDefault) {
      event.preventDefault()
    } else {
      event.returnValue = false
    }
  },

阻止事件冒泡

stopPropagation: function (event) {
    if (event.stopPropagation) {
      event.stopPropagation()
    } else {
      event.cancelBubble = true
    }
  },

獲取鼠標離開進入的相關元素

getRelatedTarget: function (event) {
    if (event.relatedTarget) { //判斷是否爲非IE
      // mouseover: 返回離開的節點
      // mouseout: 返回進入的節點
      return event.relatedTarget
    } else if (event.toElement) { // IE兼容寫法
      return event.toElement
    } else if (event.fromElement) { // IE兼容寫法
      return event.fromElement
    } else {
      null
    }
  },

鼠標滾輪方法

// 非IE瀏覽器:
  // 0: 表示主鼠標按鈕
  // 1: 中間的鼠標按鈕
  // 2: 次鼠標按鈕
  // IE8:
  // 0: 沒有按下按鈕
  // 1: 按下了主鼠標按鈕
  // 2: 按下了次鼠標按鈕
  // 3: 同時按下了主、次鼠標按鈕
  // 4: 按下了中間的鼠標按鈕
  // 5: 主鼠標按鈕、中間鼠標按鈕同時按下
  // 6: 次鼠標按鈕、中間鼠標按鈕同時按下
  // 7: 同時按下三個鼠標按鈕
  getButton: function (event) {
    // document.implementation === Domimplementaiton
    // 表明了一個接口, 提供了不依賴與任何document的方法.
    // 這個接口沒有特定的屬性, 而且也沒有繼承任何屬性
    // hasFeature: 用來判斷當前DOM, 是否支持某個特性
    if (document.implementation.hasFeature('MouseEvents', "2.0")) {
      return event.button
    } else {
      switch (event.button) {
        // 由於只有按下鼠標才能執行到這, 因此再提示沒有按下, 也默認爲按下了主按鈕
        case 0:
        case 1:
        case 3:
        case 5:
        case 7:
          return 0;
        case 2:
        case 6:
          return 2;
        case 4:
          return 1;
      }
    }
  },

可以獲取鼠標滾輪增量增(delta)的方法

// 非firefox爲event.wheelDelta屬性, 屬性值爲 +-120
  // firefox瀏覽器下, 屬性值爲 -+3, 與其餘瀏覽器符號相反
  getWheelDelta: function (event) {
    if (event.wheelDelta) { //非firefox瀏覽器
      // 在 opera 9.5版本如下, 是相反的, 引版本太老, 此處未作兼容處理
      return event.wheelDelta
    } else { //firefox瀏覽器
      return -event.detail ### 40
    }
  },

獲取按下字符編碼

// 獲取後的編碼, 能夠經過String.fromCharCode()
  getCharCode: function (event) {
    // 這樣看的話, 應該有瀏覽器中有這個屬性值, 而且不爲undefiend.
    if (typeof event.charCode == "number") {
      return event.charCode
    } else { // 兼容IE寫法
      return event.keyCode
    }
  },

獲取剪貼板數據對象

// 這個方法只是針對, 在文本框中進行剪切(cut)、複製(copy)和粘貼(paste)這三個操做,快捷鍵分別是ctrl+x、ctrl+c、ctrl+v
  // IE瀏覽器只有在文本選定字符的時, copy和cut才發生. 且在非文本框中(如div元素)只能發生copy事件
  // 可以生效的方法`onpast`, `oncopy`, `oncut`, `onbeforepaste`, `onbeforecopy`, `onbeforecut`
  // 在這些事件中才能去到事件對象中的剪切板
  // 事件對象有三個方法: getData()、setData()和clearData ()
  // getData() 參數: "text" 和 "URL"
  // setData() 參數 "text" 和 "URL", 設置的文本, IE成功與否飯後布爾值, 其餘瀏覽器無返回值
  // clearData() 參數: text" 和 "URL", IE成功與否飯後布爾值, 其餘瀏覽器返回undeifned

  clipboardData: function (event) {
    return clipboardData = (event.clipboardData || window.clipboardData);
  },

訪問剪貼板中的數據

getClipboardText: function (event) {
    var clipboardData = (event.clipboardData || window.clipboardData);
    return clipboardData.getData("text");
  },

設置剪貼板中的數據

setClipboardText: function (event, value) {
    if (event.clipboardData) {
      return event.clipboardData.setData("text/plain", value);
    } else if (window.clipboardData) {
      return window.clipboardData.setData("text", value);
    }
  },

獲取頁面滾動的高度

// 專業且通俗一點的說法, 獲取滾動條相對於其頂部的偏移
  getScrollTop: function () {
    return window.pageYOffset || document.documentElement.scrollTop || document.body.scrollTop
  },

根據類名獲取元素

byClassName: function (parent, className) {
    if (parent.getElmentsByClassName) { // 判斷是否支持直接寫法
      return parent.getElmentsByClassName(className)
    } else { // IE
      var arr = []; // 用來存儲最終查找到的類名
      var els = parent.getElementsByTagName('###') // 查找這個父元素下面的全部子元素
      for (var i = 0; i < els.length; i++) {
        var child = els[i]
        var classNames = child.className.split(' ')
        for (var j = 0; j < className.length; j++) {
          if (classNames[j] === className) {
            arr.push(child)
            break
          }
        }
      }
      return arr
    }
  },

獲取元素的行外樣式

getElementStyle: function (element, styleName) {
    if (element.currentStyle) { //IE
      return element.currentStyle[styleName]
    } else { // 非IE
      return getComputedStyle(element, null)[styleName]
    }
  }

聲明:

相關文章
相關標籤/搜索