Is there a way that works for all browsers?
original answer
Yes.
window.screen.availHeight
window.screen.availWidth
update 2017-11-10
From Tsunamis in the comments:
To get the native resolution of i.e. a mobile device you have to multiply with the device pixel ratio: window.screen.width * window.devicePixelRatio and window.screen.height * window.devicePixelRatio. This will also work on desktops, which will have a ratio of 1.
And from Ben in another answer:
In vanilla JavaScript, this will give you the AVAILABLE width/height:
window.screen.availHeight
window.screen.availWidth
For the absolute width/height, use:
window.screen.height
window.screen.width
var width = screen.width;
var height = screen.height;
In vanilla JavaScript, this will give you the AVAILABLE width/height:
window.screen.availHeight
window.screen.availWidth
For the absolute width/height, use:
window.screen.height
window.screen.width
Both of the above can be written without the window prefix.
Like jQuery? This works in all browsers, but each browser gives different values.
$(window).width()
$(window).height()
You can also get the WINDOW width and height, avoiding browser toolbars and... (not just screen size).
To do this, use:
window.innerWidth and window.innerHeight properties. See it at w3schools.
In most cases it will be the best way, in example, to display a perfectly centred floating modal dialog. It allows you to calculate positions on window, no matter which resolution orientation or window size is using the browser.
Do you mean display resolution (eg 72 dots per inch) or pixel dimensions (browser window is currently 1000 x 800 pixels)?
Screen resolution enables you to know how thick a 10 pixel line will be in inches. Pixel dimensions tell you what percentage of the available screen height will be taken up by a 10 pixel wide horizontal line.
There's no way to know the display resolution just from Javascript since the computer itself usually doesn't know the actual dimensions of the screen, just the number of pixels. 72 dpi is the usual guess....
Note that there's a lot of confusion about display resolution, often people use the term instead of pixel resolution, but the two are quite different. See Wikipedia
Of course, you can also measure resolution in dots per cm. There is also the obscure subject of non-square dots. But I digress.
Using jQuery you can do:
$(window).width()
$(window).height()
Trying to get this on a mobile device requires a few more steps. screen.availWidth stays the same regardless of the orientation of the device.
Here is my solution for mobile:
function getOrientation(){
return Math.abs(window.orientation) - 90 == 0 ? "landscape" : "portrait";
};
function getMobileWidth(){
return getOrientation() == "landscape" ? screen.availHeight : screen.availWidth;
};
function getMobileHeight(){
return getOrientation() == "landscape" ? screen.availWidth : screen.availHeight;
};
See Get Monitor Screen Resolution with Javascript and the window.screen object
function getScreenWidth()
{
var de = document.body.parentNode;
var db = document.body;
if(window.opera)return db.clientWidth;
if (document.compatMode=='CSS1Compat') return de.clientWidth;
else return db.clientWidth;
}
just for future reference:
function getscreenresolution()
{
window.alert("Your screen resolution is: " + screen.height + 'x' + screen.width);
}
If you want to detect screen resolution, you might want to checkout the plugin res. It allows you to do the following:
var res = require('res')
res.dppx() // 1
res.dpi() // 96
res.dpcm() // 37.79527559055118
Here are some great resolution takeaways from Ryan Van Etten, the plugin's author:
2 unit sets exist and differ at a fixed scale: device units and CSS units.
Resolution is calculated as the number of dots that can fit along a particular CSS length.
Unit conversion: 1in = 2.54cm = 96px = 72pt
CSS has relative and absolute lengths. In normal zoom: 1em = 16px
dppx is equivalent to device-pixel-ratio.
devicePixelRatio definition differs by platform.
Media queries can target min-resolution. Use with care for speed.
Here's the source code for res, as of today:
!function(root, name, make) {
if (typeof module != 'undefined' && module.exports) module.exports = make()
else root[name] = make()
}(this, 'res', function() {
var one = {dpi: 96, dpcm: 96 / 2.54}
function ie() {
return Math.sqrt(screen.deviceXDPI * screen.deviceYDPI) / one.dpi
}
function dppx() {
// devicePixelRatio: Webkit (Chrome/Android/Safari), Opera (Presto 2.8+), FF 18+
return typeof window == 'undefined' ? 0 : +window.devicePixelRatio || ie() || 0
}
function dpcm() {
return dppx() * one.dpcm
}
function dpi() {
return dppx() * one.dpi
}
return {'dppx': dppx, 'dpi': dpi, 'dpcm': dpcm}
});
if you mean browser resolution then
window.innerWidth gives you the browser resolution
you can test with http://howbigismybrowser.com/
try changing your screen resolution by zoom in / out browser and check resolution size with http://howbigismybrowser.com/
Window.innerWidth should be same as screen resolution width
Easy steps to find screen resolution is:
Copy
`My screen resolution is: ${window.screen.width} * ${window.screen.height}`
paste in browser console
hit enter
I've searched far and wide throughout the web thinking that somebody may have had a similar need, but have come short. I'm needing to create a calculator that will adjust the size of a stage for draggable objects based on a Width and Height field (in feet).
I'm needing to maintain a max width and height that would, ideally, be set in a variable for easy modification. This max width and height would be set in pixels. I would set dimensions of the draggable items on the stage in "data-" attributes, I imagine. I'm not looking to match things up in terms of screen resolutions.
What's the best way to approach this? I'm pretty mediocre at math and have come up short in being able to create the functions necessary for scaling a stage of objects and their container like this.
I'm a skilled jQuery user, so if it makes sense to make use of jQuery in this, that'd be great. Thanks in advance.
There are at least a couple of ways to scale things proportionately. Since you will know the projected (room) dimensions and you should know at least one of the scaled dimensions (assuming you know the width of the stage), you can scale proportionately by objectLengthInFeet / roomWidthInFeet * stageWidthInPixels.
Assuming a stage width of 500 pixels for an example, once you know the room dimensions and the width of the stage:
var stageWidth = 500,
roomWidth = parseFloat($('#width').val(), 10) || 0, // default to 0 if input is empty or not parseable to number
roomHeight = parseFloat($('#height').val(), 10) || 0, // default to 0 if input is empty or not parseable to number
setRoomDimensions = function (e) {
roomWidth = parseFloat($('#width').val(), 10);
roomHeight = parseFloat($('#height').val(), 10);
},
feetToPixels = function feetToPixels(feet) {
var scaled = feet / roomWidth * stageWidth;
return scaled;
};
Here's a demo: http://jsfiddle.net/uQDnY/
Hello fellow code people :)
I am a frontend web developer and as such in need of constant knowledge of the actual viewport size in order to see where in responsive designing breakpoints start and end.
I know FF's own 'test window size' function, but came across a very handy extension: FireSizer.
the extension has one itsy bitsy drawback: It gives back the window-size including FF's borders and scrollbar. I need the viewport-size though. So I need the extension hacked, but dont't know enough javaScript to do so. Maybe someone is willing to help em out here?
I would love the extension to actually look for the scrollbar, and subtract from the width
a) 14 if no scrollbar present or
b) 30 if scrollbar present
I found of what I think is the right place to alter the code:
//
// Update the status bar panel with the current window size
//
function FiresizerUpdateStatus() {
var width = window.outerWidth + ''; // <- Think code needs to be edited here
var height = window.outerHeight + '';
document.getElementById("firesizer-statuspanel").label = width + 'x' + height;
}
Thanks for any effort!
AO
#Chen Asraf:
Well thank you very much. I didn't know there was an element to call the document-width. I changed the code to the following, and that did the trick (also when compared to FF's own 'Responsive Design View mode', which is spot on, its off by 2px - which i subtract from clientWidth.)
function FiresizerUpdateStatus() {
var width = window.outerWidth + ''; // changed this line to:
var width = document.documentElement.clientWidth-2 + '';
var height = window.outerHeight + '';
document.getElementById("firesizer-statuspanel").label = width + 'M' + height;
}
Thanks
AO
Possible duplicate of Get the browser viewport dimensions with JavaScript
Seems like you can get the window's inner dimensions by using:
// My window is maximized; screen is 1366x768
alert(document.documentElement.clientWidth);
// ^ returns 1349 (17 missing pixels because of scrollbar)
alert(document.documentElement.clientHeight);
// ^ returns 643 (125 pixels missing because of start bar & Chrome toolbars)
You can then compare the following with whatever else you need (for example, compare client width with window width to find if the difference is big enough to be a scrollbar - just experiment with the sizes)
Okay, so my iPhone 5 arrived (I live in Australia and am lucky to have it before the US) and the first thing I wanted to do was take full advantage of the 88 pixels of extra width for my 2D platformer using the Impact JS engine.
I cannot get my head around how to actually modify the canvas width.
This is what I was using previously:
ig.main('#canvas', MyGame, 60, 240, 160, 2);
Now, I thought it would've been as easy to just increase the 240 by 44 pixels (considering there's 44 pixels on either side in landscape):
ig.main('#canvas', MyGame, 60, 284, 160, 2);
However, I'm still seeing 44 pixels black bars on either side after the above code change.
Not sure whether I have to modify any other Impact engine files in order to get this working. I haven't played around with it enough as I'm at work at the moment and shouldn't really be working on my game. I'm sure there's a few other areas I'll have to modify to get this working.
Btw, I'm using iOSImpact and deploying my game directly to my iPhone 5, so there may be files within there that need to be updated as well.
Also I noticed the following properties for detection between mobile devices. I'd need to throw in an ig.ua.iPhone5 property in here as well.
ig.ua.pixelRatio = window.devicePixelRatio || 1;
ig.ua.viewport = {
width: window.innerWidth,
height: window.innerHeight
};
ig.ua.screen = {
width: window.screen.availWidth * pixelRatio,
height: window.screen.availHeight * pixelRatio
};
ig.ua.iPhone = /iPhone/i.test(navigator.userAgent);
ig.ua.iPhone4 = (iPhone && pixelRatio == 2);
ig.ua.iPhone5 = ??
ig.ua.iPad = /iPad/i.test(navigator.userAgent);
ig.ua.android = /android/i.test(navigator.userAgent);
ig.ua.webos = /hpwos/i.test(navigator.userAgent);
ig.ua.iOS = iPhone || iPad;
ig.ua.mobile = iOS || android || webos;
I did a console.log on the following and this is what it returns:
ig.ua.viewport.width = 640
ig.ua.viewport.height = 960
ig.ua.screen.width = 1280
ig.ua.screen.height = 1920
I'm a little confused with the above results as well, specifically the ig.ua.viewport.width returning 960. I would've thought it should be returning 1136.
Your app has to tell the OS that it supports the taller/wider screen. I think this is done by specifying a startup image of that size. Otherwise, you'll be run in compatibility mode and not get to use the full screen
I'm working on a kind of unique app which needs to generate images at specific resolutions according to the device they are displayed on. So the output is different on a regular Windows browser (96ppi), iPhone (163ppi), Android G1 (180ppi), and other devices. I'm wondering if there's a way to detect this automatically.
My initial research seems to say no. The only suggestion I've seen is to make an element whose width is specified as "1in" in CSS, then check its offsetWidth (see also How to access screen display’s DPI settings via javascript?). Makes sense, but iPhone is lying to me with that technique, saying it's 96ppi.
Another approach might be to get the dimensions of the display in inches and then divide by the width in pixels, but I'm not sure how to do that either.
<div id='testdiv' style='height: 1in; left: -100%; position: absolute; top: -100%; width: 1in;'></div>
<script type='text/javascript'>
var devicePixelRatio = window.devicePixelRatio || 1;
dpi_x = document.getElementById('testdiv').offsetWidth * devicePixelRatio;
dpi_y = document.getElementById('testdiv').offsetHeight * devicePixelRatio;
console.log(dpi_x, dpi_y);
</script>
grabbed from here http://www.infobyip.com/detectmonitordpi.php. Works on mobile devices! (android 4.2.2 tested)
I came up with a way that doesn't require the DOM... at all
The DOM can be messy, requiring you to append stuff to the body without knowing what stuff is going on with width: x !important in your stylesheet. You would also have to wait for the DOM to be ready to use...
/**
* Binary search for a max value without knowing the exact value, only that it can be under or over
* It dose not test every number but instead looks for 1,2,4,8,16,32,64,128,96,95 to figure out that
* you thought about #96 from 0-infinity
*
* #example findFirstPositive(x => matchMedia(`(max-resolution: ${x}dpi)`).matches)
* #author Jimmy Wärting
* #see {#link https://stackoverflow.com/a/35941703/1008999}
* #param {function} fn The function to run the test on (should return truthy or falsy values)
* #param {number} start=1 Where to start looking from
* #param {function} _ (private)
* #returns {number} Intenger
*/
function findFirstPositive (f,b=1,d=(e,g,c)=>g<e?-1:0<f(c=e+g>>>1)?c==e||0>=f(c-1)?c:d(e,c-1):d(c+1,g)) {
for (;0>=f(b);b<<=1);return d(b>>>1,b)|0
}
var dpi = findFirstPositive(x => matchMedia(`(max-resolution: ${x}dpi)`).matches)
console.log(dpi)
There is the resolution CSS media query — it allows you to limit CSS styles to specific resolutions:
http://www.w3.org/TR/css3-mediaqueries/#resolution
However, it’s only supported by Firefox 3.5 and above, Opera 9 and above, and IE 9. Other browsers won’t apply your resolution-specific styles at all (although I haven’t checked non-desktop browsers).
Here is what works for me (but didn't test it on mobile phones):
<body><div id="ppitest" style="width:1in;visible:hidden;padding:0px"></div></body>
Then I put in the .js: screenPPI = document.getElementById('ppitest').offsetWidth;
This got me 96, which corresponds to my system's ppi.
DPI is by definition tied to the physical size of the display. So you won't be able to have the real DPI without knowing exactly the hardware behind.
Modern OSes agreed on a common value in order to have compatible displays: 96 dpi. That's a shame but that's a fact.
You will have to rely on sniffing in order to be able to guess the real screen size needed to compute the resolution (DPI = PixelSize / ScreenSize).
I also needed to display the same image at the same size at different screen dpi but only for Windows IE. I used:
<img src="image.jpg" style="
height:expression(scale(438, 192));
width:expression(scale(270, 192))" />
function scale(x, dpi) {
// dpi is for orignal dimensions of the image
return x * screen.deviceXDPI/dpi;
}
In this case the original image width/height are 270 and 438 and the image was developed on 192dpi screen. screen.deviceXDPI is not defined in Chrome and the scale function would need to be updated to support browsers other than IE
The reply from #Endless is pretty good, but not readable at all,
this is a similar approche with fixed min/max (it should be good ones)
var dpi = (function () {
for (var i = 56; i < 2000; i++) {
if (matchMedia("(max-resolution: " + i + "dpi)").matches === true) {
return i;
}
}
return i;
})();
matchMedia is now well supported and should give good result, see http://caniuse.com/#feat=matchmedia
Be careful the browser won't give you the exact screen dpi but only an approximation
function getPPI(){
// create an empty element
var div = document.createElement("div");
// give it an absolute size of one inch
div.style.width="1in";
// append it to the body
var body = document.getElementsByTagName("body")[0];
body.appendChild(div);
// read the computed width
var ppi = document.defaultView.getComputedStyle(div, null).getPropertyValue('width');
// remove it again
body.removeChild(div);
// and return the value
return parseFloat(ppi);
}
(From VodaFone)
Reading through all these responses was quite frustrating, when the only correct answer is: No, it is not possible to detect the DPI from JavaScript/CSS. Often, the operating system itself does not even know the DPI of the connected screens (and reports it as 96 dpi, which I suspect might be the reason why many people seem to believe that their method of detecting DPI in JavaScript is accurate). Also, when multiple screens are connected to a device forming a unified display, the viewport and even a single DOM element can span multiple screens with different DPIs, which would make these calculations quite challenging.
Most of the methods described in the other answers will almost always result in an output of 96 dpi, even though most screens nowadays have a higher DPI. For example, the screen of my ThinkPad T14 has 157 dpi, according to this calculator, but all the methods described here and my operating system tell me that it has 96 dpi.
Your idea of assigning a CSS width of 1in to a DOM element does not work. It seems that a CSS inch is defined as 96 CSS pixels. By my understanding, a CSS pixel is defined as a pixel multiplied by the devicePixelRatio, which traditionally is 1, but can be higher or lower depending on the zoom level configured in the graphical interface of the operating system and in the browser.
It seems that the approach of using resolution media queries produces at least some results on a few devices, but they are often still off by a factor of more than 2. Still, on most devices this approach also results in a value of 96 dpi.
I think your best approach is to combine the suggestion of the "sniffer" image with a matrix of known DPIs for devices (via user agent and other methods). It won't be exact and will be a pain to maintain, but without knowing more about the app you're trying to make that's the best suggestion I can offer.
Can't you do anything else? For instance, if you are generating an image to be recognized by a camera (i.e. you run your program, swipe your cellphone across a camera, magic happens), can't you use something size-independent?
If this is an application to be deployed in controlled environments, can you provide a calibration utility? (you could make something simple like print business cards with a small ruler in it, use it during the calibration process).
I just found this link: http://dpi.lv/. Basically it is a webtool to discover the client device resolution, dpi, and screen size.
I visited on my computer and mobile phone and it provides the correct resolution and DPI for me. There is a github repo for it, so you can see how it works.
Generate a list of known DPI:
https://stackoverflow.com/a/6793227
Detect the exact device. Using something like:
navigator.userAgent.toLowerCase();
For example, when detecting mobile:
window.isMobile=/iphone|ipod|ipad|android|blackberry|opera mini|opera mobi|skyfire|maemo|windows phone|palm|iemobile|symbian|symbianos|fennec/i.test(navigator.userAgent.toLowerCase());
And profit!
Readable code from #Endless reply:
const dpi = (function () {
let i = 1;
while ( !hasMatch(i) ) i *= 2;
function getValue(start, end) {
if (start > end) return -1;
let average = (start + end) / 2;
if ( hasMatch(average) ) {
if ( start == average || !hasMatch(average - 1) ) {
return average;
} else {
return getValue(start, average - 1);
}
} else {
return getValue(average + 1, end);
}
}
function hasMatch(x) {
return matchMedia(`(max-resolution: ${x}dpi)`).matches;
}
return getValue(i / 2, i) | 0;
})();
Maybe I'm a little bit steering off this topic...
I was working on a html canvas project, which was intended to provide a drawing canvas for people to draw lines on. I wanted to set canvas's size to 198x280mm which is fit for A4 printing.
So I started to search for a resolution to convert 'mm' to 'px' and to display the canvas suitably on both PC and mobile.
I tried solution from #Endless ,code as:
const canvas = document.getElementById("canvas");
function findFirstPositive(b, a, i, c) {
c=(d,e)=>e>=d?(a=d+(e-d)/2,0<b(a)&&(a==d||0>=b(a-1))?a:0>=b(a)?c(a+1,e):c(d,a-1)):-1
for (i = 1; 0 >= b(i);) i *= 2
return c(i / 2, i)|0
}
const dpi = findFirstPositive(x => matchMedia(`(max-resolution: ${x}dpi)`).matches)
let w = 198 * dpi / 25.4;
let h = 280 * dpi / 25.4;
canvas.width = w;
canvas.height = h;
It worked well on PC browser, showing dpi=96 and size was 748x1058 px;work well on PC
However turned to mobile devices, it was much larger than I expected: size: 1902x2689 px.can't work on mobile
After searching for keywords like devicePixelRatio, I suddenly realize that, I don't actually need to show real A4 size on mobile screen (under which situation it's actually hard to use), I just need the canvas's size fit for printing, so I simply set the size to:
let [w,h] = [748,1058];
canvas.width = w;
canvas.height = h;
...and it is well printed:well printed