Finding top-level X Window x/y coordinates of CTRL-F text in Firefox

你离开我真会死。 提交于 2020-01-16 19:29:32

问题


I need to programmatically determine the top-level X window coordinates of the text that is found by using CTRL-f in Firefox. For example, starting with this sequence:

  1. Open up Firefox on Linux (MS Windows is not involved here).
  2. Browse to some web page.
  3. Type CTRL-f to start finding text "foo" that exists in the page.
  4. Firefox then highlights the text as expected.
  5. Type Escape key which eliminates the find toolbar at the bottom of the page.

Now, at this point, I want to open up the Scratchpad (Shift-F4), and type some javascript that will dump out to the console the X and Y coordinates of the top left point of the text that is highlighted/selected (again, to clarify, the coordinates need to be the top-level X window coordinates). The coordinates need to be transformed into coordinates relative to the top-level X window (the Firefox window).

I would prefer not to install any Firefox extensions such as Selenium, just use straight javascript. I also do not want to modify the content of the page being loaded and viewed if possible.

The selected text and xy coordinates question seems similar to this. The window.getSelection() method returns the text string, but I'm looking specifically for the X and Y coordinates of that string as it is on the X window.

EDIT #1: Note that the "window coordinates" given by http://javascript.info/tutorial/coordinates is not the same as the top-level X window coordinates. A viable answer to this question includes the full affine transformation javascript code to transform from Element or Node coordinates to top-level X window coordinates (even if it means intermediate transformations into "window coordinates" as given by http://javascript.info/tutorial/coordinates).

EDIT #2: Possible answer is in the works in https://stackoverflow.com/a/14119731/257924 but I am still confirming it. Confirmed via EDIT #3 below:

EDIT #3: A followup to Tim Downs answer: This is what worked, with a caveat:

var sel = window.getSelection();
var result = "no_selection";
if (sel.rangeCount) {
    var range = sel.getRangeAt(0).cloneRange();
    if (range.getBoundingClientRect) {
        range.collapse(true);
        var rect = range.getBoundingClientRect();
        if (rect) {
            x = rect.left;
            y = rect.top;
            x += window.mozInnerScreenX;
            y += window.mozInnerScreenY;
            result = "" + x + " " + y;
        }
    }
}
result

The caveat is that if the user has scaled the page by pressing CTRL-PLUS or CTRL-MINUS in the page, the x and y values will not be correct (scaling issue). But I found that if scaling is not involved, the x and y values were absolute X root window (under X11 under Linux) coordinates, not relative to the origin of the Firefox X root window, which is what I originally asked for.

I've asked a separate related issue about accessing the scaling factor during debugging.


回答1:


You can do this using the getClientRects() method of a range obtained from the selection. See https://stackoverflow.com/a/6847328/96100

To transform the coordinates returned by the rectangle returned by getClientRects() into coordinates relative to the "screen" in Firefox only, you can use window.mozInnerScreenX and window.mozInnerScreenY. Demo below; the results seem plausible in Firefox on Windows.

http://jsfiddle.net/timdown/gaw5W/1/




回答2:


Given that the jsfiddle.net is unresponsive (referenced in Tim's answer), I'm replying with my own solution below that also addresses the issue I described in "EDIT #3" in my question concerning getting the scaling factor.

The following Javascript code demonstrates how to obtain the properly scaled origin coordinate of the selected text. The selected text includes what is selected if you type CTRL-f, type some text that is then selected, and you type Escape.

In order for screenPixelsPerCSSPixel to be available without throwing exceptions, the devtools.chrome.enabled flag in about:config should be set to true, and you will have to use the Scratchpads Environment menu to select the Browser configuration (See Inspecting Firefox Components.interfaces.nsIDOMWindowUtils.screenPixelsPerCSSPixel value in Javascript Scratchpad for details).

To avoid security risks, be sure to turn devtools.chrome.enabled flag back to false after trying the code below.

After the above configuration changes are applied, type the following text into the Scratchpad, place your cursor after "result" at the very end, and type CTRL-L to see the result.

var contentWindow = window.content;
var sel = contentWindow.getSelection();
var result = "no_selection";
if (sel.rangeCount) {
    var range = sel.getRangeAt(0).cloneRange();
    if (range.getClientRects) {
        range.collapse(true);
        var rect = range.getClientRects()[0];
        if (rect) {
            x = rect.left;
            y = rect.top;
            x += contentWindow.mozInnerScreenX;
            y += contentWindow.mozInnerScreenY;
            var util = contentWindow.QueryInterface(Components.interfaces.nsIInterfaceRequestor).getInterface(Components.interfaces.nsIDOMWindowUtils);
            x *= util.screenPixelsPerCSSPixel;
            y *= util.screenPixelsPerCSSPixel;
            result = "" + x + " " + y;
        }
    }
}
result

I verified that the above handles scaling properly in the content window such that the resulting coordinate values embedded in the result string correspond to the absolute X root window coordinates. I have not tested the above on MS Windows.



来源:https://stackoverflow.com/questions/14117682/finding-top-level-x-window-x-y-coordinates-of-ctrl-f-text-in-firefox

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!