jquery $ (window) .width () i $ (window) .height () zwracają różne wartości, gdy rozmiar widoku nie został zmieniony

105

Piszę witrynę za pomocą jquery, która wielokrotnie wywołuje $(window).width()i $(window).height()pozycjonuje i rozmiaruje elementy w oparciu o rozmiar widoku.

Podczas rozwiązywania problemów odkryłem, że otrzymuję raporty o nieco innych rozmiarach rzutni w powtarzających się wywołaniach powyższych funkcji jQuery, gdy rozmiar rzutni nie jest zmieniany.

Zastanawiam się, czy jest jakiś szczególny przypadek, o którym ktoś wie, kiedy to się dzieje, lub czy tak po prostu jest. Wygląda na to, że różnica w raportowanych rozmiarach wynosi 20 pikseli lub mniej. Dzieje się tak w Safari 4.0.4, Firefox 3.6.2 i Chrome 5.0.342.7 beta w systemie Mac OS X 10.6.2. Nie testowałem jeszcze innych przeglądarek, ponieważ wydaje się, że nie są one specyficzne dla przeglądarki. Nie byłem również w stanie dowiedzieć się, od czego zależy różnica, jeśli nie jest to rozmiar widocznego obszaru, czy może istnieć inny czynnik, który powoduje różnice w wynikach?

Każdy wgląd byłby doceniony.


aktualizacja:

Nie ma wartości $(window).width()i $(window).height()że się zmieniają. To wartości zmiennych, których używam do przechowywania wartości powyższych.

To nie paski przewijania wpływają na wartości, żadne paski przewijania nie pojawiają się, gdy zmieniają się wartości zmiennych. Oto mój kod do przechowywania wartości w moich zmiennych (co robię, aby były krótsze).

(wszystko to jest w środku $(document).ready())

// początkowo zadeklaruj zmienne jako widoczne dla innych funkcji wewnątrz .ready()

var windowWidth = $(window).width(); //retrieve current window width
var windowHeight = $(window).height(); //retrieve current window height
var documentWidth = $(document).width(); //retrieve current document width
var documentHeight = $(document).height(); //retrieve current document height
var vScrollPosition = $(document).scrollTop(); //retrieve the document scroll ToP position
var hScrollPosition = $(document).scrollLeft(); //retrieve the document scroll Left position


function onm_window_parameters(){ //called on viewer reload, screen resize or scroll

    windowWidth = $(window).width(); //retrieve current window width
    windowHeight = $(window).height(); //retrieve current window height
    documentWidth = $(document).width(); //retrieve current document width
    documentHeight = $(document).height(); //retrieve current document height
    vScrollPosition = $(document).scrollTop(); //retrieve the document scroll ToP position
    hScrollPosition = $(document).scrollLeft(); //retrieve the document scroll Left position

}; //end function onm_window_parameters()

Wstawiłem ostrzeżenie, aby sprawdzić powyższe zmienne pod kątem wartości, które rzekomo mają. Te $(item).param()wartości pozostać spójne, ale moje zmienne zmienić ze względów nie mogę zorientować się.

Szukałem miejsc, w których mój kod może zmieniać wartość danych zmiennych, w przeciwieństwie do pobierania ich ustawionych wartości i nie mogę ich znaleźć. Jeśli to możliwe, mogę gdzieś zamieścić cały shebang.

Manca Weeks
źródło

Odpowiedzi:

98

Myślę, że to, co widzisz, to ukrywanie i pokazywanie pasków przewijania. Oto krótkie demo pokazujące zmianę szerokości .

Na marginesie: czy musisz stale sondować? Możesz być w stanie zoptymalizować swój kod, aby działał w przypadku zmiany rozmiaru, na przykład:

$(window).resize(function() {
  //update stuff
});
Nick Craver
źródło
1
btw, mimo wszystko miałeś rację ... podczas rozwiązywania problemów zauważyłem, że są paski przewijania. pojawiały się tak krótko, że nie można ich było zobaczyć, z wyjątkiem trybu debugowania ze skryptem wstrzymanym w trakcie wykonywania. po usunięciu powyższych zmiennych i funkcji niektóre elementy nadal przeskakiwały z pozycji - miało to związek z kolejnością kroków skryptu - musiałem tylko upewnić się, że zresetowałem div trzymający moje wstawione obrazy do css left: 0 przed wstawieniem obrazu . morał dla tej historii: tylko dlatego, że paski przewijania nie pojawiają się na tyle długo, aby można je było zobaczyć, nie oznacza, że ​​ich tam nie było!
Manca Weeks
Użyłbym również tego pytania: stackoverflow.com/questions/2854407/, więc możesz sprawdzić, kiedy wydarzenie zmiany rozmiaru się zakończy, zanim cokolwiek zrobisz. Twój skrypt będzie uruchamiał to, co kiedykolwiek znajduje się w funkcji .resize () przy każdym pikselu, który zmienisz, więc lepszą praktyką jest zaczekanie.
MarkP
9

Spróbuj użyć

  • $(window).load zdarzenie

lub

  • $(document).ready

    ponieważ wartości początkowe mogą być niestałe z powodu zmian, które zachodzą podczas analizowania lub podczas ładowania DOM.

Albi Patozi
źródło
3

Zwróć uwagę, że jeśli problem jest spowodowany przez pojawiające się paski przewijania, wstaw

body {
  overflow: hidden;
}

w Twoim CSS może być łatwym rozwiązaniem (jeśli nie potrzebujesz przewijania strony).

xixixao
źródło
1

Miałem bardzo podobny problem. Podczas odświeżania strony otrzymywałem niespójne wartości height (). (To nie była moja zmienna powodująca problem, była to rzeczywista wartość wysokości).

Zauważyłem, że w nagłówku mojej strony najpierw wywołałem moje skrypty, a potem plik css. Przełączyłem się tak, że najpierw linkowany jest plik css, a następnie pliki skryptów i wydaje się, że do tej pory problem został rozwiązany.

Mam nadzieję, że to pomoże.

Jared
źródło
Właściwie moim pierwotnym problemem było to, że sposób, w jaki moje elementy ustawiały się wokół strony, powodował, że paski przewijania pojawiały się na ułamek sekundy - wystarczyło, aby pomiar był przekrzywiony, ale nie na tyle, aby oko go złapało ... to się dzieje, gdy umieściłem instrukcje alertów między instrukcjami javascript, aby podzielić kod na różne stany. Zrobiłem to, aby alerty raportowały pomiary na każdym etapie wykonywania kodu. Wtedy zauważyłem, że jeden ze stanów spowodował pojawienie się pasków przewijania - który był stanem, w którym dokonano pomiaru.
Manca Weeks
1
Mogę potwierdzić to samo za pomocą pasków przewijania. Po zmianie rozmiaru przeglądarki odczytałbym $ (window) .height () i mógłbym pokazać coś w rodzaju 500. Następnie odświeżyłbym (bez zmiany rozmiaru przeglądarki) i pokazałbym coś większego, jak 700. W moim przypadku, udało mi się to naprawić, robiąc po prostu przepełnienie: ukryte na ciele, ponieważ nigdy nie chcę, aby paski przewijania się włączały. Kiedy to zrobiłem, raport wzrostu był spójny.
sbuck