2012-07-03 8 views
49

Dla reagującego szablonu, mam zapytanie mediów w moim CSS:CSS zapytania mediów i JavaScript szerokość okna nie pasują

@media screen and (max-width: 960px) { 
body{ 
/* something */ 
background:red; 
} 
} 

I zrobiłem funkcję jQuery na zmiany rozmiaru do szerokości log:

$(window).resize(function() { 
console.log($(window).width()); 
console.log($(document).width()); /* same result */ 
/* something for my js navigation */ 
} 

a jest jakaś różnica z detekcją CSS i JS wyniku, mam ten meta:

<meta content="user-scalable=no, initial-scale=1.0, maximum-scale=1.0, width=device-width" name="viewport"/> 

przypuszczam, że to ze względu na sc pałąk (15 pikseli). Jak mogę to zrobić lepiej?

Odpowiedz

74

Masz rację co do paska przewijania, ponieważ CSS używa szerokości urządzenia, ale JS używa szerokości dokumentu.

Należy zmierzyć szerokość rzutni w kodzie JS, zamiast korzystać z funkcji szerokości jQuery.

Ten kod jest od http://andylangton.co.uk/articles/javascript/get-viewport-size-javascript/

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' ] }; 
} 
+0

to działa dla mnie! Dziękuję Ci ! –

+0

Solidne. Znacznie lepiej niż $ (document) .width(); window.matchMedia() jest prawdopodobnie lepszy, ale jego IE10 + – Bosworth99

+2

To nie działa, jeśli okno ma paski przewijania, a zapytania o media sprawdzają maksymalną szerokość, przynajmniej w Chrome. Sprawdzanie niektórych css na elemencie, który znasz jest ustawiony przez konkretne zapytanie o media, wydaje się działać. – mhenry1384

1

Moje doświadczenie było to, że szerokość zapytania mediów śledzi document.body.clientWidth. Ponieważ pionowy pasek przewijania przychodzi i odchodzi, sprawdzenie szerokości dokumentu, okna lub widoku() może spowodować opóźnienie mojej obsługi JavaScript po zmianie reguły zapytania o media w zależności od wysokości okna.

Sprawdzanie document.body.clientWidth pozwoliło, aby mój kod skryptu był konsekwentnie wykonywany w tym samym momencie, w którym obowiązywała reguła zapytania o media.

@media (min-width: 873px) {
        // pewne zasady
}
...

if (document.body.clientWidth> = 873) {
        // jakiś kod
}

Kod Andy Langton mnie w to włożył - dzięki!

+1

Jeśli ciało jest szersze niż ekran, to nie będzie działać. Widziałem rozwiązania, w których niewidoczny element div jest ustawiony na stałe, a jego szerokość jest ustawiona na 100%. Używanie jej clientWidht powinno działać. – LarS

7

Znalazłem następujący kod na http://www.w3schools.com/js/js_window.asp:

var w=window.innerWidth || document.documentElement.clientWidth || document.body.clientWidth; 

Praktycznie jego pracy tak samo jak odpowiedź w odpowiedzi @Michael ptaka, ale to jest bardziej czytelny.

Edytuj: Szukałem metody, aby podać dokładnie taką samą szerokość, jak jest używana do zapytań o media CSS. Ale sugerowany nie działa idealnie w Safari z paskami przewijania, przepraszam. Skończyło się na użyciu modernizr.js w jednej funkcji centralnej, a reszta kodu Właśnie sprawdzam, czy typ wyświetlania to telefon komórkowy, tablet lub komputer.Ponieważ nie jestem zainteresowany szerokości, to działa dobrze dla mnie:

getDisplayType = function() { 
    if (Modernizr.mq('(min-width: 768px)')){ 
    return 'desktop'; 
    } 
    else if (Modernizr.mq('(min-width: 480px)')){ 
    return 'tablet' 
    } 
    return 'mobile'; 
}; 
+1

Jeśli 'document.documentElement' nie istnieje, ten skrypt zakończy się niepowodzeniem. Nie ufaj w3schools, zobacz http://www.w3fools.com/ – ausi

+3

@ausi: Czy byłbyś uprzejmy i dopracowany nieco bardziej niż "nie ufasz w3schools"? Na razie nie widzę problemu. Zobacz także [Problemy z wieloma przeglądarkami z document.documentElement] (http://stackoverflow.com/questions/11391827/any-cross-browser-issues-with-document-documentelement) – LarS

+1

OK, wygląda na to, że nie ma przeglądarki, która nie robi ". t mieć 'document.documentElement'. Tego nie wiedziałem. – ausi

1

Cześć Używam tego mały trick, aby uzyskać JS i CSS pracę razem łatwo na reagujących stron:

przetestować widoczność elementu wyświetlane lub nie w stanie rozmiaru CSS @media. Korzystanie bootstrap CSS i sprawdzić widoczność ukrytego elementu xs-klasy

var msg = "a message for U"; 
 

 
/* At window load check initial size */ 
 
if ($('#test-xsmall').is(':hidden') ) { 
 
    /* This is a CSS Xsmall situation ! */ 
 
    msg = "@media CSS < 768px. JS width = " + $(window).width() + " red ! "; 
 
    $('.redthing-on-xsmall').addClass('redthing').html(msg); 
 

 
} else { 
 
    /* > 768px according to CSS */ 
 
    msg = "@media CSS > 767px. JS width = " + $(window).width() + " not red ! "; 
 
    $('.redthing-on-xsmall').removeClass('redthing').html(msg); 
 
} 
 

 

 
/* And again when window resize */ 
 

 
$(window).on('resize', function() { 
 
    if ($('#test-xsmall').is(':hidden')) { 
 
    msg = "@media CSS < 768px. JS width = " + $(window).width() + " red ! "; 
 
    $('.redthing-on-xsmall').addClass('redthing').html(msg); 
 
    } else { 
 
    msg = "@media CSS > 767px. JS width = " + $(window).width() + " not red ! "; 
 
    $('.redthing-on-xsmall').removeClass('redthing').html(msg); 
 
    } 
 
});
@media (min-width: 768px) { 
 
    .hidden-xs { 
 
    display: block !important; 
 
    } 
 
} 
 
@media (max-width: 767px) { 
 
    .hidden-xs { 
 
    display: none !important; 
 
    } 
 
} 
 
.redthing-on-xsmall { 
 
    /* need a scrollbar to show window width diff between JS and css */ 
 
    min-height: 1500px; 
 
} 
 
.redthing { 
 
    color: red; 
 
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> 
 

 
<!-- the CSS managed Element that is tested by JS --> 
 
<!-- class hidden-xs hides on xsmall screens (bootstrap) --> 
 

 
<span id="test-xsmall" class="hidden-xs">THIS ELEMENT IS MANAGED BY CSS HIDDEN on @media lower than 767px</span> 
 

 

 
<!-- the responsive element managed by Jquery --> 
 
<div class="redthing-on-xsmall">THIS ELEMENT IS MANAGED BY JQUERY RED on @media max width 767px </div>

1

Obejście że zawsze działa i jest zsynchronizowany z zapytaniami mediów CSS.

dodać div do ciała

<body> 
    ... 
    <div class='check-media'></div> 
    ... 
</body> 

Dodaj styl i zmienić je wpisując w zapytaniu konkretne mediów

.check-media{ 
    display:none; 
    width:0; 
} 
@media screen and (max-width: 768px) { 
    .check-media{ 
     width:768px; 
    } 
    ... 
} 

Następnie w JS wyboru stylu, które zmieniają poprzez zawarcie zapytania mediów

if($('.check-media').width() == 768){ 
    console.log('You are in (max-width: 768px)'); 
}else{ 
    console.log('You are out of (max-width: 768px)'); 
} 

Ogólnie można sprawdzić każdy styl, który jest zmieniany, wprowadzając specyfikację ific media query.

3

window.innerWidth jest tym, czego potrzebujesz.

if (window.innerWidth < 768) działa na 768 miejscu przerwy w CSS

-1

Css zapytania mediów jest równa window.innerWidth. Css Media Queries oblicza również pasek przewijania.