从FF和Google Chrome的像素坐标中进行选择 [英] Select from pixel coordinates for FF and Google Chrome

查看:150
本文介绍了从FF和Google Chrome的像素坐标中进行选择的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我已经可以做到这一点Safari和IE像这样的小提琴: http://jsfiddle.net/cyk8y/ (代码有点复杂或/和凌乱,但它只是这样,你可以看到我想要的最终结果)。

我从主要代码这里:设置从A到B的选择范围在绝对位置



在回答的评论中, Tim Down 给了我这些链接:从像素位置i创建合拢范围n FF / Webkit 来帮助我使我的代码工作在FF,也许谷歌Chrome。



我试过了,但是我没有成功。 >

有人可以给我一个从FF和/或Google Chrome(和Opera?)的像素坐标中选择的例子。

解决方案

这是我的最新尝试。这似乎表面上工作,但我没有保证:这是一个不平凡的代码块,我没有彻底的测试。



它可能会结束请在我的 Rangy 库中以某种形式进行整理和测试。



现场演示: http://jsfiddle.net/timdown/

提取代码(Firefox和Opera位):

  function getNodeIndex(node){
var i = 0; ((节点= node.previousSibling)){
我++;
}
return i;


函数getLastRangeRect(范围){
var rects = range.getClientRects();
return(rects.length> 0)? rects [rects.length - 1]:null;
}

函数pointIsInOrAboveRect(x,y,rect){
return y< rect.bottom&& x> = rect.left&& x <= rect.right;


函数positionFromPoint(doc,x,y,favourPrecedingPosition){
var el = doc.elementFromPoint(x,y);

var range = doc.createRange();
range.selectNodeContents(el);
range.collapse(true);

var offsetNode = el.firstChild,offset,position,rect;

if(!offsetNode){
offsetNode = el.parentNode;
offset = getNodeIndex(el);
if(!favourPrecedingPosition){
++ offset;
}
} else {
//搜索el
的文本节点children main:while(offsetNode){
if(offsetNode.nodeType == 3) {
//通过字符
查看文本节点(offset = 0,textLen = offsetNode.length; offset< = textLen; ++ offset){
range.setEnd offsetNode,offset);
rect = getLastRangeRect(range);
if(rect&& pointIsInOrAboveRect(x,y,rect)){
//我们已经超越了这个观点。 (rect.right - x> x - rect.left){
-

$ b $(现在我们检查字符的哪一边
//左边或右边)抵消;
}
break main;
}
}
} else {
//处理元素
range.setEndAfter(offsetNode);
rect = getLastRangeRect(range);
if(rect&& pointIsInOrAboveRect(x,y,rect)){
offset = getNodeIndex(offsetNode);
offsetNode = el.parentNode;
if(!favourPrecedingPosition){
++ offset;
}
break main;
}
}

offsetNode = offsetNode.nextSibling;
}
if(!offsetNode){
offsetNode = el;
offset = el.childNodes.length;
}
}

return {
offsetNode:offsetNode,
offset:offset
};
}


I can already do this for safari and IE like in this fiddle: http://jsfiddle.net/cyk8y/ (The code is a bit complicated or/and messy but it's just so you can see the final result I want).

I took the principal code from here: Set a selection range from A to B in absolute position

In the comments of the answer, Tim Down gave me these links: How to get a word under cursor using JavaScript and Creating a collapsed range from a pixel position in FF/Webkit to help me making my code working in FF and maybe Google Chrome.

I tried, but I didn't succeed.

Can someone give me an exemple that select from pixel coordinates that works in FF and/or Google Chrome (and Opera?).

解决方案

Here's the latest attempt of mine to do this. It seems superficially to work, but I'm making no guarantees: it's a non-trivial chunk of code and I haven't tested it thoroughly.

It may well end up in my Rangy library in some form once I've tidied and tested it.

Live demo: http://jsfiddle.net/timdown/ABjQP/8/

Extract of the code (the Firefox and Opera bit):

function getNodeIndex(node) {
    var i = 0;
    while( (node = node.previousSibling) ) {
        i++;
    }
    return i;
}

function getLastRangeRect(range) {
    var rects = range.getClientRects();
    return (rects.length > 0) ? rects[rects.length - 1] : null;
}

function pointIsInOrAboveRect(x, y, rect) {
    return y < rect.bottom && x >= rect.left && x <= rect.right;
}

function positionFromPoint(doc, x, y, favourPrecedingPosition) {
    var el = doc.elementFromPoint(x, y);

    var range = doc.createRange();
    range.selectNodeContents(el);
    range.collapse(true);

    var offsetNode = el.firstChild, offset, position, rect;

    if (!offsetNode) {
        offsetNode = el.parentNode;
        offset = getNodeIndex(el);
        if (!favourPrecedingPosition) {
            ++offset;
        }
    } else {
        // Search through the text node children of el
        main: while (offsetNode) {
            if (offsetNode.nodeType == 3) {
                // Go through the text node character by character
                for (offset = 0, textLen = offsetNode.length; offset <= textLen; ++offset) {
                    range.setEnd(offsetNode, offset);
                    rect = getLastRangeRect(range);
                    if (rect && pointIsInOrAboveRect(x, y, rect)) {
                        // We've gone past the point. Now we check which side
                        // (left or right) of the character the point is nearer to
                        if (rect.right - x > x - rect.left) {
                            --offset;
                        }
                        break main;
                    }
                }
            } else {
                // Handle elements
                range.setEndAfter(offsetNode);
                rect = getLastRangeRect(range);
                if (rect && pointIsInOrAboveRect(x, y, rect)) {
                    offset = getNodeIndex(offsetNode);
                    offsetNode = el.parentNode;
                    if (!favourPrecedingPosition) {
                        ++offset;
                    }
                    break main;
                }
            }

            offsetNode = offsetNode.nextSibling;
        }
        if (!offsetNode) {
            offsetNode = el;
            offset = el.childNodes.length;
        }
    }

    return {
        offsetNode: offsetNode,
        offset: offset
    };
}

这篇关于从FF和Google Chrome的像素坐标中进行选择的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆