Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

how do I get the viewport position relative to the screen?

Tags:

javascript

My question

What JavaScript code will tell me where the viewport of the browser is located relative to the screen?

Context

My web application includes an applet that allows taking a snapshot via java.awt.Robot (the applet's jar is of course signed and is privileged to perform this).

The problem is that Robot's createScreenCapture works with rectangles relative to the entire screen, whereas I want to capture a rectangle relative to the viewport.

A browser can obviously be anywhere on the screen, but even if it is maximized (and therefore begins at the top left of the screen, i.e. {0,0}) I still don't know how much the content is pushed down because of the window header or some toolbars.

My research so far

It seems only IE gives the viewport position through window.screenTop/Left.

Chrome supports these, but they hold the browser position.

FF doesn't support these, instead it has screenX/Y, but like Chrome they hold the browser position.

Making sure we all use the same terminology

Screen - AKA the desktop. for example I have a WSXGA+ (1680x1050) display. I use Windows and my taskbar is always shown at the bottom so it consumes about 50 pixels vertically.

Browser - a window that may or may not have various toolbars: address and/or bookmarks bar at the top, status/add-on bars at the bottom, etc.

Viewport - where a URL is actually being rendered.

like image 337
targumon Avatar asked Nov 06 '12 15:11

targumon


2 Answers

Jon Hulka's answer totally earned him his credit - works perfect for me!

If someone else gets here and need a solution that doesn't use applets (my question asked for JavaScript code), they can try the (compromising*) solution below.

*= It assumes browsers don't have too much stuff at the bottom of their windows.

function cacheElemImage(element) {
    var x, y, pos = findPosition(element);
    // screenTop/Left supported on all except FF. screenX/Y supported on all except IE.
    // In addition IE returns viewport top/left while FF & Chrome return browser window top/left.
    // Opera & Safari yet to be tested.
    if (isIE()) {
        x = window.screenLeft;
        y = window.screenTop;
    } else {
        var borderWidth = (window.outerWidth - window.innerWidth) / 2;
        x = window.screenX + borderWidth;
        y = window.screenY + window.outerHeight - window.innerHeight - borderWidth;
    }
    x += pos[0]; // adjust for the element position
    y += pos[1];
    var width  = element.offsetWidth;
    var height = element.offsetHeight;
    cacheImage(x, y, width, height); // call the applet with the Robot
}

function findPosition(oElement) {
    if (typeof(oElement.offsetParent) != 'undefined') {
        for (var posX = 0, posY = 0; oElement; oElement = oElement.offsetParent) {
            posX += oElement.offsetLeft;
            posY += oElement.offsetTop;
        }
        return [posX, posY];
    } else {
        return [oElement.x, oElement.y];
    }
}
like image 183
targumon Avatar answered Oct 23 '22 22:10

targumon


Your applet knows its location via getLocationOnScreen()

Here is a Java applet that prints the screen location of the mouse cursor while you are inside of it:

ScreenTest.java:

import java.awt.Point;
import java.awt.Graphics;
import java.applet.Applet;
import java.awt.event.MouseMotionListener;
import java.awt.event.MouseEvent;
public class ScreenTest extends Applet implements MouseMotionListener
{
    public ScreenTest()
    {
        this.addMouseMotionListener(this);
    }
    public void mouseDragged(MouseEvent e)
    {
    }
    public void mouseMoved(MouseEvent e)
    {
        Graphics g = getGraphics();
        Point loc=getLocationOnScreen();

        String s=(loc.getX()+e.getX())+":"+(loc.getY()+e.getY());
        g.clearRect(0,0,1000,100);
        g.drawString(s, 10, 10);
    }
}

screentest.html:

<html>
    <head></head>
    <body>
        <applet code="ScreenTest.class" name="screenTest" height=100 width=1000></applet>
    </body>
</html>

Here's a simpler example called by javascript. The applet is 1px by 1px in the upper left corner of the page.

ScreenTest2.java:

import java.awt.Point;
import java.applet.Applet;
public class ScreenTest2 extends Applet
{
    public String test(int x, int y)
    {
        Point loc=getLocationOnScreen();
        return (loc.getX()+x)+":"+(loc.getY()+y);
    }
}

screentest2.html:

<html>
    <head></head>
    <body onclick="buttonClick(event);" style="margin:0; border:0; height:800px">
        <applet code="ScreenTest2.class" name="screenTest2" height=1 width=1></applet>
    </body>
    <script>
        function buttonClick(evt)
        {
            alert(screenTest2.test(evt.clientX,evt.clientY));
        }
    </script>
</html>
like image 1
Jon Hulka Avatar answered Oct 23 '22 20:10

Jon Hulka