jQuery与YUI中鼠标位置检测比较学习(document.documentElement document.body与pageX pageY以及clientX clientY)

关于鼠标位置的检测,我们先来看看jQuery和YUI中的实现

jQuery中:

 

if ( event.pageX == null && event.clientX != null ) {
var doc = document.documentElement, body = document.body;
event.pageX
= event.clientX + (doc && doc.scrollLeft || body && body.scrollLeft || 0) - (doc && doc.clientLeft || body && body.clientLeft || 0);
event.pageY
= event.clientY + (doc && doc.scrollTop || body && body.scrollTop || 0) - (doc && doc.clientTop || body && body.clientTop || 0);
}

 

 

YUI中:

 

getPageX: function(ev) {
var x = ev.pageX;
if (!x && 0 !== x) {
x
= ev.clientX || 0;
if ( this.isIE ) {
x
+= this._getScrollLeft();
}
}
return x;
},

getPageY:
function(ev) {
var y = ev.pageY;
if (!y && 0 !== y) {
y
= ev.clientY || 0;
if ( this.isIE ) {
y
+= this._getScrollTop();
}
}
return y;
},

_getScrollLeft:
function() {
return this._getScroll()[1];
},

_getScrollTop:
function() {
return this._getScroll()[0];
},

_getScroll:
function() {
var dd = document.documentElement, db = document.body;
if (dd && (dd.scrollTop || dd.scrollLeft)) {
return [dd.scrollTop, dd.scrollLeft];
}
else if (db) {
return [db.scrollTop, db.scrollLeft];
}
else {
return [0, 0];
}
},

 

 

YUI的写法比起jQuery来确是“工程化”了很多,如果是按照代码行数发工资的话,推荐YUI,哈哈。之前翻译PPK的作品的是提到了无论如何都不要检测浏览器的类型,因为没必要,而且浏览器的UA都在胡言乱语。

关于document.documentElement和document.body

document.documentElement和document.body在不同的浏览器和不同的模式下面都会有不同的表现,已经有人做过详尽的测试了,地址在这里http://www.softcomplex.com/docs/get_window_size_and_scrollbar_position.html 经过测试的结论就是,在标准浏览器下面,一般都有相应代替的做法,在IE中,在documentElement存在的情况下一般都能正常显示,不存在时候使用document.body。这两个的来由应该源自HTML和xHTML。

所以在这个问题的处理上jQuery和YUI都采用了相同的办法:doc && doc.scrollLeft || body && body.scrollLeft || 0 。

 

关于pageX pageY和clientX clientY,scrollLeft scrollTop

对于鼠标事件,IE不支持通过pageX,pageY来获得鼠标在文档中的位置,而只有clientX、clientY,这两个参数只能获得鼠标在浏览器的可视范围内的位置。这时候就需要通过其他办法来获得鼠标在文档里面的位置,于是出现了scrollLeft和scrollTop。

有些情况下,“元素中内容(子元素)”的高度会超过“元素本身”的高度,这时候就使用scrollTop来表示超出部分的高度,scrollLeft同理。body元素的scrollTop就是指你的浏览器中被滚动条滚动了的高度。用这个值加上clientY不就是鼠标相对于文档的位置了么。在这里两个框架的也是相同的。event.pageY = event.clientY + (doc && doc.scrollTop || body && body.scrollTop || 0)

 

关于clientLeft和clientTop

然而jQuery中,以及网上搜索到的大量的实例中,还需要减掉clientLeft/Top值。

event.pageX = event.clientX + (doc && doc.scrollLeft || body && body.scrollLeft || 0) - (doc && doc.clientLeft || body && body.clientLeft || 0);

这个值是做什么用的呢?可以先来查看下面的这幅图:

 

clientLeft的值其实就是元素的边框,YUI中没有减掉这个,难道是认为IE的body没有边框?我在IE下测试body确实有2px的clientLeft的值。所以如果要精确的得到鼠标的位置,在IE下面就必须减去这个clientLeft。

posted @ 2010-04-12 15:15 BeiYuu 阅读(...) 评论(...) 编辑 收藏