├── .gitattributes ├── README.md ├── LICENSE ├── viewport.genie.bookmarklet.min.js ├── viewport.genie.min.js ├── .gitignore ├── viewport.genie.bookmarklet.js └── viewport.genie.js /.gitattributes: -------------------------------------------------------------------------------- 1 | # Auto detect text files and perform LF normalization 2 | * text=auto 3 | 4 | # Custom for Visual Studio 5 | *.cs diff=csharp 6 | *.sln merge=union 7 | *.csproj merge=union 8 | *.vbproj merge=union 9 | *.fsproj merge=union 10 | *.dbproj merge=union 11 | 12 | # Standard to msysgit 13 | *.doc diff=astextplain 14 | *.DOC diff=astextplain 15 | *.docx diff=astextplain 16 | *.DOCX diff=astextplain 17 | *.dot diff=astextplain 18 | *.DOT diff=astextplain 19 | *.pdf diff=astextplain 20 | *.PDF diff=astextplain 21 | *.rtf diff=astextplain 22 | *.RTF diff=astextplain 23 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | Viewport Genie 2 | ============== 3 | 4 | ### Adds the "real" viewport width and height (in px and em) as an element on the body to help with obtaining values for responsive breakpoints 5 | 6 | Use it in conjunction with mqGenie (https://github.com/stowball/mqGenie) to trigger the correct breakpoints in non-WebKit browsers and Chrome/Blink since 29.0.1547.57. 7 | 8 | --- 9 | 10 | **Usage:** 11 | 12 | Use the bookmarklet to quickly get the viewport size on any page: http://stowball.github.io/Viewport-Genie 13 | 14 | Or include `viewport.genie.min.js` in your page somewhere after the opening `` tag, and trigger it with a querystring parameter of `genie=true` -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2013 Matt Stow 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy of 6 | this software and associated documentation files (the "Software"), to deal in 7 | the Software without restriction, including without limitation the rights to 8 | use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of 9 | the Software, and to permit persons to whom the Software is furnished to do so, 10 | subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS 17 | FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 18 | COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER 19 | IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 20 | CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 21 | -------------------------------------------------------------------------------- /viewport.genie.bookmarklet.min.js: -------------------------------------------------------------------------------- 1 | /* 2 | * Viewport Genie v0.3 3 | * Adds the "real" viewport width and height (in px and em) as an element on the body to help with obtaining values for responsive breakpoints 4 | * 5 | * Use it in conjunction with mqGenie (https://github.com/stowball/mqGenie) to trigger the correct breakpoints in non-WebKit browsers 6 | * 7 | * Copyright (c) 2013 Matt Stow 8 | * 9 | * http://mattstow.com 10 | * 11 | * Licensed under the MIT license 12 | */ 13 | ;(function(e){if(e){var d=/(&|\?)(\w+)=true/gi,k=window.location.href,f,p="",l={};while(f=d.exec(k)){p+=" "+f[2];l[f[2]]=true}if(!l.genie){return}}var g=document.documentElement,i=document.head,h=document.body,c="vp-genie",j=document.getElementById(c),a=document.getElementById(c+"-style"),o,n=g.clientWidth?true:false;var b={init:function(){if(j){h.removeChild(j);i.removeChild(a);return}var m="#"+c+"{background: rgba(255,0,0,.75);border: 1px solid #900;-webkit-box-shadow: 2px 2px 2px rgba(0,0,0,.3);box-shadow: 2px 2px 2px rgba(0,0,0,.3);color: #fff;font-family: monospace;font-size: 13px;left: 0;line-height: 17px;padding: 3px 6px 5px;position: fixed;top: 0;z-index: 9999;}#"+c+" span {white-space: nowrap;}",q=document.createTextNode(m);a=document.createElement("style");a.setAttribute("id",c+"-style");a.type="text/css";if(a.styleSheet){a.styleSheet.cssText=q.nodeValue}else{a.appendChild(q)}i.appendChild(a);j=document.createElement("div");j.setAttribute("id",c);h.appendChild(j);b.calculate();if(window.addEventListener){window.addEventListener("resize",b.calculate,false)}},calculate:function(){if(window.getComputedStyle){o=parseInt(window.getComputedStyle(g).getPropertyValue("font-size"))}else{o=16}var q,m;if(n){q=g.clientWidth;m=g.clientHeight}else{q=window.innerWidth;m=window.innerHeight}j.innerHTML=""+q+"px × "+m+"px"+q/o+"em × "+m/o+"em"}};b.init()})(); -------------------------------------------------------------------------------- /viewport.genie.min.js: -------------------------------------------------------------------------------- 1 | /* 2 | * Viewport Genie v0.3 3 | * Adds the "real" viewport width and height (in px and em) as an element on the body to help with obtaining values for responsive breakpoints when ?genie=true 4 | * 5 | * Use it in conjunction with mqGenie (https://github.com/stowball/mqGenie) to trigger the correct breakpoints in non-WebKit browsers 6 | * 7 | * Copyright (c) 2013 Matt Stow 8 | * 9 | * http://mattstow.com 10 | * 11 | * Licensed under the MIT license 12 | */ 13 | ;(function(e){if(e){var d=/(&|\?)(\w+)=true/gi,k=window.location.href,f,p="",l={};while(f=d.exec(k)){p+=" "+f[2];l[f[2]]=true}if(!l.genie){return}}var g=document.documentElement,i=document.head,h=document.body,c="vp-genie",j=document.getElementById(c),a=document.getElementById(c+"-style"),o,n=g.clientWidth?true:false;var b={init:function(){if(j){h.removeChild(j);i.removeChild(a);return}var m="#"+c+"{background: rgba(255,0,0,.75);border: 1px solid #900;-webkit-box-shadow: 2px 2px 2px rgba(0,0,0,.3);box-shadow: 2px 2px 2px rgba(0,0,0,.3);color: #fff;font-family: monospace;font-size: 13px;left: 0;line-height: 17px;padding: 3px 6px 5px;position: fixed;top: 0;z-index: 9999;}#"+c+" span {white-space: nowrap;}",q=document.createTextNode(m);a=document.createElement("style");a.setAttribute("id",c+"-style");a.type="text/css";if(a.styleSheet){a.styleSheet.cssText=q.nodeValue}else{a.appendChild(q)}i.appendChild(a);j=document.createElement("div");j.setAttribute("id",c);h.appendChild(j);b.calculate();if(window.addEventListener){window.addEventListener("resize",b.calculate,false)}},calculate:function(){if(window.getComputedStyle){o=parseInt(window.getComputedStyle(g).getPropertyValue("font-size"))}else{o=16}var q,m;if(n){q=g.clientWidth;m=g.clientHeight}else{q=window.innerWidth;m=window.innerHeight}j.innerHTML=""+q+"px × "+m+"px"+q/o+"em × "+m/o+"em"}};b.init()})(true); -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | ################# 2 | ## Eclipse 3 | ################# 4 | 5 | *.pydevproject 6 | .project 7 | .metadata 8 | bin/ 9 | tmp/ 10 | *.tmp 11 | *.bak 12 | *.swp 13 | *~.nib 14 | local.properties 15 | .classpath 16 | .settings/ 17 | .loadpath 18 | 19 | # External tool builders 20 | .externalToolBuilders/ 21 | 22 | # Locally stored "Eclipse launch configurations" 23 | *.launch 24 | 25 | # CDT-specific 26 | .cproject 27 | 28 | # PDT-specific 29 | .buildpath 30 | 31 | 32 | ################# 33 | ## Visual Studio 34 | ################# 35 | 36 | ## Ignore Visual Studio temporary files, build results, and 37 | ## files generated by popular Visual Studio add-ons. 38 | 39 | # User-specific files 40 | *.suo 41 | *.user 42 | *.sln.docstates 43 | 44 | # Build results 45 | [Dd]ebug/ 46 | [Rr]elease/ 47 | *_i.c 48 | *_p.c 49 | *.ilk 50 | *.meta 51 | *.obj 52 | *.pch 53 | *.pdb 54 | *.pgc 55 | *.pgd 56 | *.rsp 57 | *.sbr 58 | *.tlb 59 | *.tli 60 | *.tlh 61 | *.tmp 62 | *.vspscc 63 | .builds 64 | *.dotCover 65 | 66 | ## TODO: If you have NuGet Package Restore enabled, uncomment this 67 | #packages/ 68 | 69 | # Visual C++ cache files 70 | ipch/ 71 | *.aps 72 | *.ncb 73 | *.opensdf 74 | *.sdf 75 | 76 | # Visual Studio profiler 77 | *.psess 78 | *.vsp 79 | 80 | # ReSharper is a .NET coding add-in 81 | _ReSharper* 82 | 83 | # Installshield output folder 84 | [Ee]xpress 85 | 86 | # DocProject is a documentation generator add-in 87 | DocProject/buildhelp/ 88 | DocProject/Help/*.HxT 89 | DocProject/Help/*.HxC 90 | DocProject/Help/*.hhc 91 | DocProject/Help/*.hhk 92 | DocProject/Help/*.hhp 93 | DocProject/Help/Html2 94 | DocProject/Help/html 95 | 96 | # Click-Once directory 97 | publish 98 | 99 | # Others 100 | [Bb]in 101 | [Oo]bj 102 | sql 103 | TestResults 104 | *.Cache 105 | ClientBin 106 | stylecop.* 107 | ~$* 108 | *.dbmdl 109 | Generated_Code #added for RIA/Silverlight projects 110 | 111 | # Backup & report files from converting an old project file to a newer 112 | # Visual Studio version. Backup files are not needed, because we have git ;-) 113 | _UpgradeReport_Files/ 114 | Backup*/ 115 | UpgradeLog*.XML 116 | 117 | 118 | 119 | ############ 120 | ## Windows 121 | ############ 122 | 123 | # Windows image file caches 124 | Thumbs.db 125 | 126 | # Folder config file 127 | Desktop.ini 128 | 129 | 130 | ############# 131 | ## Python 132 | ############# 133 | 134 | *.py[co] 135 | 136 | # Packages 137 | *.egg 138 | *.egg-info 139 | dist 140 | build 141 | eggs 142 | parts 143 | bin 144 | var 145 | sdist 146 | develop-eggs 147 | .installed.cfg 148 | 149 | # Installer logs 150 | pip-log.txt 151 | 152 | # Unit test / coverage reports 153 | .coverage 154 | .tox 155 | 156 | #Translations 157 | *.mo 158 | 159 | #Mr Developer 160 | .mr.developer.cfg 161 | 162 | # Mac crap 163 | .DS_Store 164 | -------------------------------------------------------------------------------- /viewport.genie.bookmarklet.js: -------------------------------------------------------------------------------- 1 | /* 2 | * Viewport Genie v0.3 3 | * Adds the "real" viewport width and height (in px and em) as an element on the body to help with obtaining values for responsive breakpoints 4 | * 5 | * Use it in conjunction with mqGenie (https://github.com/stowball/mqGenie) to trigger the correct breakpoints in non-WebKit browsers 6 | * 7 | * Copyright (c) 2013 Matt Stow 8 | * 9 | * http://mattstow.com 10 | * 11 | * Licensed under the MIT license 12 | */ 13 | ;(function(param) { 14 | if (param) { 15 | var rx = /(&|\?)(\w+)=true/gi, 16 | str = window.location.href, 17 | m, 18 | s = '', 19 | gup = {}; 20 | 21 | while (m = rx.exec(str)) { 22 | s += ' ' + m[2]; 23 | gup[m[2]] = true; 24 | } 25 | 26 | if (!gup.genie) 27 | return; 28 | } 29 | 30 | var $html = document.documentElement, 31 | $head = document.head, 32 | $body = document.body, 33 | id = 'vp-genie', 34 | $genie = document.getElementById(id), 35 | $style = document.getElementById(id + '-style'), 36 | fontSize, 37 | property = $html.clientWidth ? true: false; 38 | 39 | var viewportGenie = { 40 | init: function() { 41 | if ($genie) { 42 | $body.removeChild($genie); 43 | $head.removeChild($style); 44 | return; 45 | } 46 | 47 | var css = '#' + id + '{' + 48 | 'background: rgba(255,0,0,.75);' + 49 | 'border: 1px solid #900;' + 50 | '-webkit-box-shadow: 2px 2px 2px rgba(0,0,0,.3);' + 51 | 'box-shadow: 2px 2px 2px rgba(0,0,0,.3);' + 52 | 'color: #fff;' + 53 | 'font-family: monospace;' + 54 | 'font-size: 13px;' + 55 | 'left: 0;' + 56 | 'line-height: 17px;' + 57 | 'padding: 3px 6px 5px;' + 58 | 'position: fixed;' + 59 | 'top: 0;' + 60 | 'z-index: 9999;' + 61 | '}' + 62 | '#' + id + ' span {' + 63 | 'white-space: nowrap;' + 64 | '}', 65 | rules = document.createTextNode(css); 66 | 67 | $style = document.createElement('style'); 68 | $style.setAttribute('id', id + '-style'); 69 | $style.type = 'text/css'; 70 | 71 | if ($style.styleSheet) 72 | $style.styleSheet.cssText = rules.nodeValue; 73 | else 74 | $style.appendChild(rules); 75 | 76 | $head.appendChild($style); 77 | 78 | $genie = document.createElement('div'); 79 | $genie.setAttribute('id', id); 80 | $body.appendChild($genie); 81 | 82 | viewportGenie.calculate(); 83 | if (window.addEventListener) 84 | window.addEventListener('resize', viewportGenie.calculate, false); 85 | 86 | }, 87 | calculate: function() { 88 | if (window.getComputedStyle) 89 | fontSize = parseInt(window.getComputedStyle($html).getPropertyValue('font-size')); 90 | else 91 | fontSize = 16; 92 | 93 | var width, 94 | height; 95 | 96 | if (property) { 97 | width = $html.clientWidth; 98 | height = $html.clientHeight; 99 | } 100 | else { 101 | width = window.innerWidth; 102 | height = window.innerHeight; 103 | } 104 | 105 | $genie.innerHTML = '' + 106 | width + 'px' + 107 | ' × ' + 108 | height + 'px' + 109 | '' + 110 | ' • ' + 111 | '' + 112 | width/fontSize + 'em' + 113 | ' × ' + 114 | height/fontSize + 'em' + 115 | ''; 116 | } 117 | }; 118 | viewportGenie.init(); 119 | })(); -------------------------------------------------------------------------------- /viewport.genie.js: -------------------------------------------------------------------------------- 1 | /* 2 | * Viewport Genie v0.3 3 | * Adds the "real" viewport width and height (in px and em) as an element on the body to help with obtaining values for responsive breakpoints when ?genie=true 4 | * 5 | * Use it in conjunction with mqGenie (https://github.com/stowball/mqGenie) to trigger the correct breakpoints in non-WebKit browsers 6 | * 7 | * Copyright (c) 2013 Matt Stow 8 | * 9 | * http://mattstow.com 10 | * 11 | * Licensed under the MIT license 12 | */ 13 | ;(function(param) { 14 | if (param) { 15 | var rx = /(&|\?)(\w+)=true/gi, 16 | str = window.location.href, 17 | m, 18 | s = '', 19 | gup = {}; 20 | 21 | while (m = rx.exec(str)) { 22 | s += ' ' + m[2]; 23 | gup[m[2]] = true; 24 | } 25 | 26 | if (!gup.genie) 27 | return; 28 | } 29 | 30 | var $html = document.documentElement, 31 | $head = document.head, 32 | $body = document.body, 33 | id = 'vp-genie', 34 | $genie = document.getElementById(id), 35 | $style = document.getElementById(id + '-style'), 36 | fontSize, 37 | property = $html.clientWidth ? true: false; 38 | 39 | var viewportGenie = { 40 | init: function() { 41 | if ($genie) { 42 | $body.removeChild($genie); 43 | $head.removeChild($style); 44 | return; 45 | } 46 | 47 | var css = '#' + id + '{' + 48 | 'background: rgba(255,0,0,.75);' + 49 | 'border: 1px solid #900;' + 50 | '-webkit-box-shadow: 2px 2px 2px rgba(0,0,0,.3);' + 51 | 'box-shadow: 2px 2px 2px rgba(0,0,0,.3);' + 52 | 'color: #fff;' + 53 | 'font-family: monospace;' + 54 | 'font-size: 13px;' + 55 | 'left: 0;' + 56 | 'line-height: 17px;' + 57 | 'padding: 3px 6px 5px;' + 58 | 'position: fixed;' + 59 | 'top: 0;' + 60 | 'z-index: 9999;' + 61 | '}' + 62 | '#' + id + ' span {' + 63 | 'white-space: nowrap;' + 64 | '}', 65 | rules = document.createTextNode(css); 66 | 67 | $style = document.createElement('style'); 68 | $style.setAttribute('id', id + '-style'); 69 | $style.type = 'text/css'; 70 | 71 | if ($style.styleSheet) 72 | $style.styleSheet.cssText = rules.nodeValue; 73 | else 74 | $style.appendChild(rules); 75 | 76 | $head.appendChild($style); 77 | 78 | $genie = document.createElement('div'); 79 | $genie.setAttribute('id', id); 80 | $body.appendChild($genie); 81 | 82 | viewportGenie.calculate(); 83 | if (window.addEventListener) 84 | window.addEventListener('resize', viewportGenie.calculate, false); 85 | 86 | }, 87 | calculate: function() { 88 | if (window.getComputedStyle) 89 | fontSize = parseInt(window.getComputedStyle($html).getPropertyValue('font-size')); 90 | else 91 | fontSize = 16; 92 | 93 | var width, 94 | height; 95 | 96 | if (property) { 97 | width = $html.clientWidth; 98 | height = $html.clientHeight; 99 | } 100 | else { 101 | width = window.innerWidth; 102 | height = window.innerHeight; 103 | } 104 | 105 | $genie.innerHTML = '' + 106 | width + 'px' + 107 | ' × ' + 108 | height + 'px' + 109 | '' + 110 | ' • ' + 111 | '' + 112 | width/fontSize + 'em' + 113 | ' × ' + 114 | height/fontSize + 'em' + 115 | ''; 116 | } 117 | }; 118 | viewportGenie.init(); 119 | })(true); --------------------------------------------------------------------------------