DOM常见兼容性封装

一、事件

绑定事件处理函数

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
var EventUtil = {
/**
* 绑定事件处理函数
*/

addHandler: function (ele, type, handler) {
if (ele.addEventListener) {
// DOM2
ele.addEventListener(type, handler, false)
} else if (ele.attachEvent) {
// IE
ele.attachEvent('on' + type, function () {
handler.call(ele)
})
} else {
// DOM0
ele['on' + type] = handler
}
}
}

解绑事件处理函数

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
var EventUtil = {
/**
* 解绑事件处理函数
*/

removeHandler: function (ele, type, handler) {
if (ele.removeEventListener) {
// DOM2
ele.removeEventListener(type, handler, false)
} else if (ele.detachEvent) {
// IE
ele.detachEvent('on' + type, handler)
} else {
// DOM0
ele['on' + type] = null
}
}
}

事件对象

1
2
3
4
5
6
7
8
9
var EventUtil = {
/**
* 获取事件对象
*/

getEvent: function (event) {
return event ? event : window.event
}
}

事件源目标

1
2
3
4
5
6
7
8
9
var EventUtil = {
/**
* 获取事件目标
*/

getTarget: function (event) {
return event.target || event.srcElement
}
}

阻止冒泡

1
2
3
4
5
6
7
8
9
10
11
12
13
var EventUtil = {
/**
* 阻止冒泡
*/

stopPropagation: function (e) {
if (e.stopPropagation) {
e.stopPropagation() // 标准
} else {
e.cancelBubble = true // IE
}
}
}

取消默认事件

1
2
3
4
5
6
7
8
9
10
11
12
13
var EventUtil = {
/**
* 取消默认事件
*/

preventDefault: function (e) {
if (e.preventDefault) {
e.preventDefault()
} else {
e.returnValue = false
}
}
}

二、元素偏移量

左侧偏移量

1
2
3
4
5
6
7
8
9
10
11
12
13
/**
* 获取元素的左侧偏移值, content+padding+border
*/

function getElementOffsetLeft (ele) {
let currentLeft = ele.offsetLeft
let parent = ele.offsetParent
while (parent !== null) {
currentLeft += parent.offsetLeft
parent = parent.offsetParent
}
return currentLeft
}

上侧偏移量

1
2
3
4
5
6
7
8
9
10
11
12
13
/**
* 获取元素的上侧偏移值, content+padding+border
*/

function getElementOffsetTop (ele) {
let currentTop = ele.offsetTop
let parent = ele.offsetParent
while (parent !== null) {
currentTop += parent.offsetTop
parent = parent.offsetParent
}
return currentTop
}

三、获取视口宽高

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
/**
* 获取窗口页面可视区域宽高
* getViewportOffset().w
*/

function getViewportOffset () {
let pageWidth = window.innerWidth
let pageHeight = window.innerHeight
if (typeof pageWidth !== 'number') {
if (document.compatMode === 'BackCompat') {
pageWidth = document.body.clientWidth
pageHeight = document.body.clientHeight
} else {
pageWidth = document.documentElement.clientWidth
pageHeight = document.documentElement.clientHeight
}
}
return {
w: pageWidth,
h: pageHeight
}
}

四、滚动条滚动距离

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
/**
* 获取滚动条的滚动距离
* getScrollOffset().y
*/

function getScrollOffset () {
let x, y
if (window.pageXOffset || window.pageYOffset) {
x = window.pageXOffset || window.scrollX
y = window.pageYOffset || window.scrollY
} else {
x = document.body.scrollLeft + document.documentElement.scrollLeft
y = document.body.scrollTop + document.documentElement.scrollTop
}
return {
x, y
}
}

五、解析查询字符串

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
/**
* 解析查询字符串
* parseQueryString('?foo=bar')
* parseQueryString('foo=bar')
*/

function parseQueryString (str) {
let qs = str[0] === '?' ? str.slice(1) : str
let args = {}
let items = qs.length ? qs.split("&") : []

for (let i = 0; i < items.length; i++) {
let item = items[i].split('=')
let key = decodeURIComponent(item[0])
let value = decodeURIComponent(item[1])
if (key.length) {
args[key] = value
}
}
return args
}