这似乎是一个令人惊奇的问题,但这里有一个几乎重复的问题:如何获取具有 CSS3 变换的元素的 MouseEvent 坐标?但没有人在那里看我的答案,这似乎更笼统,所以我会在这里再次发布,并进行一些修改以使其更清楚:
基本上,它的工作原理是:拆分您尝试为其查找相对坐标的元素,并将其拆分为 9 个较小的元素。使用 document.elementFromPoint 来查找坐标是否在那个小元素之上。如果是,则将该元素拆分为另外 9 个元素,并继续这样做,直到可以得到相当准确的坐标。然后使用 getBoundingClientRect 查找该迷你元素的屏幕坐标。繁荣!
jsfiddle:http: //jsfiddle.net/markasoftware/rA27K/8/
这是 JavaScript 函数:
function convertPointFromPageToNode(elt,coords){
///the original innerHTML of the element
var origHTML=elt.innerHTML;
//now clear it
elt.innerHTML='';
//now save and clear bad styles
var origPadding=elt.style.padding=='0px'?'':elt.style.padding;
var origMargin=elt.style.margin=='0px'?'':elt.style.margin;
elt.style.padding=0;
elt.style.margin=0;
//make sure the event is in the element given
if(document.elementFromPoint(coords.x,coords.y)!==elt){
//reset the element
elt.innerHTML=origHTML;
//and styles
elt.style.padding=origPadding;
elt.style.margin=origMargin;
//we've got nothing to show, so return null
return null;
}
//array of all places for rects
var rectPlaces=['topleft','topcenter','topright','centerleft','centercenter','centerright','bottomleft','bottomcenter','bottomright'];
//function that adds 9 rects to element
function addChildren(elt){
//loop through all places for rects
rectPlaces.forEach(function(curRect){
//create the element for this rect
var curElt=document.createElement('div');
//add class and id
curElt.setAttribute('class','offsetrect');
curElt.setAttribute('id',curRect+'offset');
//add it to element
elt.appendChild(curElt);
});
//get the element form point and its styling
var eltFromPoint=document.elementFromPoint(coords.x,coords.y);
var eltFromPointStyle=getComputedStyle(eltFromPoint);
//Either return the element smaller than 1 pixel that the event was in, or recurse until we do find it, and return the result of the recursement
return Math.max(parseFloat(eltFromPointStyle.getPropertyValue('height')),parseFloat(eltFromPointStyle.getPropertyValue('width')))<=1?eltFromPoint:addChildren(eltFromPoint);
}
//this is the innermost element
var correctElt=addChildren(elt);
//find the element's top and left value by going through all of its parents and adding up the values, as top and left are relative to the parent but we want relative to teh wall
for(var curElt=correctElt,correctTop=0,correctLeft=0;curElt!==elt;curElt=curElt.parentNode){
//get the style for the current element
var curEltStyle=getComputedStyle(curElt);
//add the top and left for the current element to the total
correctTop+=parseFloat(curEltStyle.getPropertyValue('top'));
correctLeft+=parseFloat(curEltStyle.getPropertyValue('left'));
}
//reset the element
elt.innerHTML=origHTML;
//restore element styles
elt.style.padding=origPadding;
elt.style.margin=origMargin;
//the returned object
var returnObj={
x: correctLeft,
y: correctTop
}
return returnObj;
}
重要的!!!您还必须包含此 CSS 才能使其工作:
.offsetrect{
position: absolute;
opacity: 0;
height: 33.333%;
width: 33.333%;
}
#topleftoffset{
top: 0;
left: 0;
}
#topcenteroffset{
top: 0;
left: 33.333%;
}
#toprightoffset{
top: 0;
left: 66.666%;
}
#centerleftoffset{
top: 33.333%;
left: 0;
}
#centercenteroffset{
top: 33.333%;
left: 33.333%;
}
#centerrightoffset{
top: 33.333%;
left: 66.666%;
}
#bottomleftoffset{
top: 66.666%;
left: 0;
}
#bottomcenteroffset{
top: 66.666%;
left: 33.333%;
}
#bottomrightoffset{
top: 66.666%;
left: 66.666%;
}
另外:我通过给“祖父” div 一个 id 并在你的 css 中引用它#div1
而不是div
因为我的代码生成 div 来修改你的一些 css,并且你的 div 样式也适用于我的代码使用的那些并弄乱了它向上
最后一件事:我不知道 CoffeeScript,所以我调整了您的代码以使其成为纯 JavaScript。对于那个很抱歉。