jQuery $(window).width() 与媒体查询不同
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/19291873/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
$(window).width() not the same as media query
提问by Pattle
I am using Twitter Bootstrap on a project. As well as the default bootstrap styles I have also added some of my own
我在一个项目上使用 Twitter Bootstrap。除了默认的引导程序样式,我还添加了一些我自己的样式
//My styles
@media (max-width: 767px)
{
//CSS here
}
I am also using jQuery to change the order of certain elements on the page when the width of the viewport is less that 767px.
当视口的宽度小于 767px 时,我还使用 jQuery 更改页面上某些元素的顺序。
$(document).load($(window).bind("resize", checkPosition));
function checkPosition()
{
if($(window).width() < 767)
{
$("#body-container .main-content").remove().insertBefore($("#body-container .left-sidebar"));
} else {
$("#body-container .main-content").remove().insertAfter($("#body-container .left-sidebar"));
}
}
The problem I am having is that the width calculated by $(window).width()
and the width calculated by the CSS doesn't seem to be the same. When $(window).width()
returns 767 the css calculates it the viewport width as 751 so there seems to be a 16px different.
我遇到的问题是$(window).width()
CSS 计算的宽度和 CSS 计算的宽度似乎不同。当$(window).width()
返回 767 时,css 将视口宽度计算为 751,因此似乎有 16px 不同。
Does anyone know what is causing this and how I could solve the problem? People have suggested that the width of the scrollbar isn't being taken into considering and using $(window).innerWidth() < 751
is the way to go. However ideally I want to find a solution that calculates the width of the scrollbar and that is consistent with my media query (e.g where both conditions are checking against the value 767). Because surely not all browsers will have a scrollbar width of 16px?
有谁知道是什么导致了这个问题以及我如何解决这个问题?人们建议不要考虑滚动条的宽度,而使用$(window).innerWidth() < 751
是要走的路。然而,理想情况下,我想找到一个计算滚动条宽度并且与我的媒体查询一致的解决方案(例如,两个条件都检查值 767)。因为肯定不是所有浏览器的滚动条宽度都是 16px?
回答by ausi
If you don't have to support IE9 you can just use window.matchMedia()
(MDN documentation).
如果您不必支持 IE9,则可以使用window.matchMedia()
(MDN 文档)。
function checkPosition() {
if (window.matchMedia('(max-width: 767px)').matches) {
//...
} else {
//...
}
}
window.matchMedia
is fully consistent with the CSS media queries and the browser support is quite good: http://caniuse.com/#feat=matchmedia
window.matchMedia
与 CSS 媒体查询完全一致,浏览器支持相当好:http: //caniuse.com/#feat=matchmedia
UPDATE:
更新:
If you have to support more browsers you can use Modernizr's mq method, it supports all browsers that understand media queries in CSS.
如果您必须支持更多浏览器,您可以使用Modernizr 的 mq 方法,它支持所有理解 CSS 媒体查询的浏览器。
if (Modernizr.mq('(max-width: 767px)')) {
//...
} else {
//...
}
回答by NateS
Check a CSS rule that the media query changes. This is guaranteed to always work.
检查媒体查询更改的 CSS 规则。这保证始终有效。
http://www.fourfront.us/blog/jquery-window-width-and-media-queries
http://www.fourfront.us/blog/jquery-window-width-and-media-queries
HTML:
HTML:
<body>
...
<div id="mobile-indicator"></div>
</body>
Javascript:
Javascript:
function isMobileWidth() {
return $('#mobile-indicator').is(':visible');
}
CSS:
CSS:
#mobile-indicator {
display: none;
}
@media (max-width: 767px) {
#mobile-indicator {
display: block;
}
}
回答by Rohan Kumar
It may be due to scrollbar
, use innerWidth
instead of width
like
这可能是由于scrollbar
,使用innerWidth
而不是width
喜欢
if($(window).innerWidth() <= 751) {
$("#body-container .main-content").remove()
.insertBefore($("#body-container .left-sidebar"));
} else {
$("#body-container .main-content").remove()
.insertAfter($("#body-container .left-sidebar"));
}
Also you can get the viewport
like
你也可以得到viewport
像
function viewport() {
var e = window, a = 'inner';
if (!('innerWidth' in window )) {
a = 'client';
e = document.documentElement || document.body;
}
return { width : e[ a+'Width' ] , height : e[ a+'Height' ] };
}
Above code Source
以上代码来源
回答by Rantiev
yes, that's due to scrollbar. Right answer source: enter link description here
是的,这是由于滚动条。正确答案来源:在此处输入链接描述
function viewport() {
var e = window, a = 'inner';
if (!('innerWidth' in window )) {
a = 'client';
e = document.documentElement || document.body;
}
return { width : e[ a+'Width' ] , height : e[ a+'Height' ] };
}
回答by gramgram
It's maybe a better practice not to JS-scope the document's width but some sort of change made by css @media query. With this method you can be sure the JQuery function and css change happens at the same time.
最好不要将文档的宽度设为 JS 范围,而是通过 css @media 查询进行某种更改。使用此方法,您可以确保 JQuery 函数和 css 更改同时发生。
css:
css:
#isthin {
display: inline-block;
content: '';
width: 1px;
height: 1px;
overflow: hidden;
}
@media only screen and (max-width: 990px) {
#isthin {
display: none;
}
}
jquery:
查询:
$(window).ready(function(){
isntMobile = $('#isthin').is(":visible");
...
});
$(window).resize(function(){
isntMobile = $('#isthin').is(":visible");
...
});
回答by user3041539
I was facing the same problem recently - also with Bootstrap 3.
我最近遇到了同样的问题——Bootstrap 3 也是如此。
Neither $.width() nor $.innerWidth() will work for you.
$.width() 和 $.innerWidth() 都不适合你。
The best solution I came up with - and is specifically tailored to BS3 -
is to check the width of a .container
element.
我想出的最佳解决方案 - 并且专门为 BS3 量身定制 -
是检查.container
元素的宽度。
As you probably know how the .container
element works,
it's the only element that will give you the current width set by BS css rules.
您可能知道.container
元素的工作原理,
它是唯一可以为您提供 BS css 规则设置的当前宽度的元素。
So it goes something like
所以它就像
bsContainerWidth = $("body").find('.container').width()
if (bsContainerWidth <= 768)
console.log("mobile");
else if (bsContainerWidth <= 950)
console.log("small");
else if (bsContainerWidth <= 1170)
console.log("medium");
else
console.log("large");
回答by user4451021
Use
用
window.innerWidth
window.innerWidth
This solved my problem
这解决了我的问题
回答by dschenk
Here is an alternative to the methods mentioned earlier that rely on changing something via CSS and reading it via Javascript. This method does not need window.matchMedia
or Modernizr. It also needs no extra HTML element. It works by using a HTML pseudo-element to 'store' breakpoint information:
这是前面提到的依赖于通过 CSS 更改某些内容并通过 Javascript 读取它的方法的替代方法。此方法不需要window.matchMedia
或 Modernizr。它还不需要额外的 HTML 元素。它通过使用 HTML 伪元素来“存储”断点信息:
body:after {
visibility: hidden;
height: 0;
font-size: 0;
}
@media (min-width: 20em) {
body:after {
content: "mobile";
}
}
@media (min-width: 48em) {
body:after {
content: "tablet";
}
}
@media (min-width: 64em) {
body:after {
content: "desktop";
}
}
I used body
as an example, you can use any HTML element for this. You can add any string or number you want into the content
of the pseudo-element. Doesn't have to be 'mobile' and so on.
我body
举了一个例子,你可以为此使用任何 HTML 元素。您可以将您想要的任何字符串或数字添加到content
伪元素的 中。不必是“移动的”等等。
Now we can read this information from Javascript in the following way:
现在我们可以通过以下方式从 Javascript 中读取这些信息:
var breakpoint = window.getComputedStyle(document.querySelector('body'), ':after').getPropertyValue('content').replace(/"/g,'');
if (breakpoint === 'mobile') {
doSomething();
}
This way we are always sure that the breakpoint information is correct, since it is coming directly from CSS and we don't have to hassle with getting the right screen-width via Javascript.
通过这种方式,我们始终可以确保断点信息是正确的,因为它直接来自 CSS,我们不必为通过 Javascript 获得正确的屏幕宽度而烦恼。
回答by fzzylogic
Javascript provides more than one method to check the viewport width. As you noticed, innerWidth doesn't include the toolbar width, and toolbar widths will differ across systems. There is also the outerWidthoption, which will include the toolbar width. The Mozilla Javascript APIstates:
Javascript 提供了不止一种方法来检查视口宽度。正如您所注意到的,innerWidth 不包括工具栏宽度,并且工具栏宽度会因系统而异。还有outerWidth选项,它将包括工具栏宽度。在Mozilla的JavaScript API第状态:
Window.outerWidth gets the width of the outside of the browser window. It represents the width of the whole browser window including sidebar (if expanded), window chrome and window resizing borders/handles.
Window.outerWidth 获取浏览器窗口外部的宽度。它代表整个浏览器窗口的宽度,包括侧边栏(如果展开)、窗口镶边和窗口大小调整边框/手柄。
The state of javascript is such that one cannot rely on a specific meaning for outerWidth in every browser on every platform.
javascript 的状态是这样的,以至于人们不能依赖于每个平台上每个浏览器中的 outerWidth 的特定含义。
outerWidth
is not well supported on oldermobile browsers, though it enjoys support across major desktop browsers and most newer smart phone browsers.
outerWidth
虽然它在主要桌面浏览器和大多数较新的智能手机浏览器中受到支持,但在较旧的移动浏览器上并没有得到很好的支持。
As ausi pointed out, matchMedia
would be a great choice as CSS is better standardised (matchMedia uses JS to read the viewport values detected by CSS). But even with accepted standards, retarded browsers still exist that ignore them (IE < 10 in this case, which makes matchMedia not very useful at least until XP dies).
正如ausi 指出的那样,matchMedia
这将是一个不错的选择,因为CSS 更加标准化(matchMedia 使用JS 来读取CSS 检测到的视口值)。但即使采用了公认的标准,仍然存在忽略它们的延迟浏览器(在这种情况下,IE < 10,这使得 matchMedia 至少在 XP 死亡之前不是很有用)。
In summary, if you are only developing for desktop browsers and newer mobile browsers, outerWidth should give you what you are looking for, with some caveats.
在总之,如果你只为桌面浏览器和新的移动浏览器开发,outerWidth应该给你你在找什么,有一些注意事项。
回答by user2128205
Here's a less involved trick to deal with media queries. Cross browser support is a bit limiting as it doesn't support mobile IE.
这是处理媒体查询的一个不太复杂的技巧。跨浏览器支持有点限制,因为它不支持移动 IE。
if (window.matchMedia('(max-width: 694px)').matches)
{
//do desired changes
}
See Mozilla documentationfor more details.
有关更多详细信息,请参阅Mozilla 文档。