Bagaimana cara mendeteksi level pembesaran halaman di semua browser modern?


310
  1. Bagaimana saya bisa mendeteksi level pembesaran halaman di semua browser modern? Sementara utas ini memberi tahu cara melakukannya di IE7 dan IE8, saya tidak bisa menemukan solusi lintas-browser yang bagus.

  2. Firefox menyimpan tingkat pembesaran halaman untuk akses masa depan. Pada pemuatan halaman pertama, apakah saya bisa mendapatkan level zoom? Di suatu tempat saya membacanya berfungsi ketika perubahan zoom terjadi setelah halaman dimuat.

  3. Apakah ada cara untuk menjebak 'zoom'acara tersebut?

Saya memerlukan ini karena beberapa perhitungan saya berbasis pixel dan mungkin berfluktuasi ketika diperbesar.


Sampel yang dimodifikasi diberikan oleh @tfl

Halaman ini mengingatkan nilai ketinggian yang berbeda saat diperbesar. [jsFiddle]

<html>
    <head>
        <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.3.1/jquery.min.js" type="text/javascript"/></script>
    </head>
    <body>
        <div id="xy" style="border:1px solid #f00; width:100px;">Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque sollicitudin tortor in lacus tincidunt volutpat. Integer dignissim imperdiet mollis. Suspendisse quis tortor velit, placerat tempor neque. Cum sociis natoque penatibus et magnis dis parturient montes, nascetur ridiculus mus. Praesent bibendum auctor lorem vitae tempor. Nullam condimentum aliquam elementum. Nullam egestas gravida elementum. Maecenas mattis molestie nisl sit amet vehicula. Donec semper tristique blandit. Vestibulum adipiscing placerat mollis.</div>
        <button onclick="alert($('#xy').height());">Show</button>
    </body>
</html>

1
Pada dasarnya saya ingin mengetahui dimensi DIV pada zoom 100%.
Kekurangan

4
Pada dasarnya tidak ada cara untuk mendeteksi zoom pada tahun 2019 : Saya telah menguji semua solusi di bawah ini pada Chrome 78 di Mac Catalina dan tidak ada satupun yang berfungsi.
collimarco

Jawaban:


274

Sekarang berantakan bahkan lebih besar daripada saat pertanyaan ini pertama kali diajukan. Dari membaca semua tanggapan dan posting blog yang bisa saya temukan, inilah ringkasannya. Saya juga mengatur halaman ini untuk menguji semua metode pengukuran tingkat zoom ini .

Sunting (2011-12-12): Saya telah menambahkan proyek yang dapat dikloning: https://github.com/tombigel/detect-zoom

  • IE8 :screen.deviceXDPI / screen.logicalXDPI (atau, untuk level zoom relatif terhadap zoom default, screen.systemXDPI / screen.logicalXDPI)
  • IE7 : var body = document.body,r = body.getBoundingClientRect(); return (r.left-r.right)/body.offsetWidth;(terima kasih untuk contoh ini atau jawaban ini )
  • HANYA FF3.5 : screen.width/ lebar layar kueri media (lihat di bawah) (memanfaatkan fakta yang screen.widthmenggunakan piksel perangkat tetapi lebar MQ menggunakan piksel CSS - berkat lebar Quirksmode )
  • FF3.6 : tidak ada metode yang diketahui
  • FF4 + : pencarian biner media queri (lihat di bawah)
  • WebKit : https://www.chromestatus.com/feature/5737866978131968 (terima kasih kepada Teo dalam komentar)
  • WebKit : mengukur ukuran div yang disukai dengan -webkit-text-size-adjust:none.
  • WebKit : (rusak sejak r72591 ) document.width / jQuery(document).width()(terima kasih kepada Dirk van Oosterbosch di atas ). Untuk mendapatkan rasio dalam hal piksel perangkat (alih-alih relatif terhadap zoom default), kalikan dengan window.devicePixelRatio.
  • WebKit Lama? (tidak diverifikasi): parseInt(getComputedStyle(document.documentElement,null).width) / document.documentElement.clientWidth(dari jawaban ini )
  • Opera : document.documentElement.offsetWidth/ lebar position:fixed; width:100%div. dari sini ( tabel lebar Quirksmode mengatakan itu bug; innerWidth harus berupa CSS px). Kami menggunakan posisi: elemen tetap untuk mendapatkan lebar viewport termasuk ruang di mana scrollbar berada ; document.documentElement.clientWidth tidak termasuk lebar ini. Ini rusak sejak sekitar tahun 2011; Saya tidak tahu cara untuk mendapatkan level zoom di Opera lagi.
  • Lainnya : Solusi flash dari Sebastian
  • Tidak dapat diandalkan: mendengarkan acara mouse dan mengukur perubahan di screenX / perubahan di clientX

Ini adalah pencarian biner untuk Firefox 4, karena saya tidak tahu ada variabel di mana ia diekspos:

<style id=binarysearch></style>
<div id=dummyElement>Dummy element to test media queries.</div>
<script>
var mediaQueryMatches = function(property, r) {
  var style = document.getElementById('binarysearch');
  var dummyElement = document.getElementById('dummyElement');
  style.sheet.insertRule('@media (' + property + ':' + r +
                         ') {#dummyElement ' +
                         '{text-decoration: underline} }', 0);
  var matched = getComputedStyle(dummyElement, null).textDecoration
      == 'underline';
  style.sheet.deleteRule(0);
  return matched;
};
var mediaQueryBinarySearch = function(
    property, unit, a, b, maxIter, epsilon) {
  var mid = (a + b)/2;
  if (maxIter == 0 || b - a < epsilon) return mid;
  if (mediaQueryMatches(property, mid + unit)) {
    return mediaQueryBinarySearch(
        property, unit, mid, b, maxIter-1, epsilon);
  } else {
    return mediaQueryBinarySearch(
        property, unit, a, mid, maxIter-1, epsilon);
  }
};
var mozDevicePixelRatio = mediaQueryBinarySearch(
    'min--moz-device-pixel-ratio', '', a, b, maxIter, epsilon);
var ff35DevicePixelRatio = screen.width / mediaQueryBinarySearch(
    'min-device-width', 'px', 0, 6000, 25, .0001);
</script>

1
Kerja yang sangat bagus, meskipun ini tidak bekerja untuk saya di IE 8.0.7601.17514 (terbaru). Apakah ada peluang untuk membungkus semua ini dalam satu fungsi getZoom () yang berfungsi di semua browser? Mungkin juga dirilis sebagai plugin jQuery? Kerja bagus lagi.
ripper234

1
@yonran plugin hebat !, Tapi itu tidak berfungsi di IE9 seharusnya zoom: screen.deviceXDPI / screen.logicalXDPI,bukanzoom: screen.systemXDPI / screen.logicalXDPI,
Daniel

1
@ Bob, ketika saya pertama kali menulis ini untuk Firefox 4, Firefox tidak punya matchMedia. Paul Irish juga menulis polyfill matchMedia serupa yang merupakan bagian dari Modernizr .
yonran

7
Berita bagus, semuanya! Mereka akhirnya berhasil! API Vieport! chromestatus.com/feature/5737866978131968 Saya mengujinya, barang bagus!
Teo

3
API Viewport hanya berfungsi untuk pinch-zoom; jika Anda memperbesar pada desktop dikatakan skala adalah 1. @Jason T Featheringham ada alasan lain selain "diskriminasi" untuk ingin mengetahui tingkat zoom. Zoom ditetapkan di semua halaman untuk domain, tetapi Anda mungkin ingin menanganinya secara berbeda di halaman game atau popup ekstensi daripada yang Anda lakukan di halaman bantuan.
Pudica

61

Anda dapat mencoba

var browserZoomLevel = Math.round(window.devicePixelRatio * 100);

Ini akan memberi Anda tingkat persentase peramban pada tampilan non-retina. Untuk tampilan DPI / retina tinggi, itu akan menghasilkan nilai yang berbeda (misalnya, 200 untuk Chrome dan Safari, 140 untuk Firefox).

Untuk menangkap acara zoom yang dapat Anda gunakan

$(window).resize(function() { 
// your code 
});

1
Berfungsi sempurna, juga pada perangkat seluler. Menarik juga melihat apa yang dimiliki perangkat seluler devicePixelRatio. Ini juga sangat membantu saya mengalihkan fixedelemen ke elemen yang absolutediposisikan saat acara zoom terjadi, atau ketika nilai awal devicePixelRatioperubahan. Sempurna! Terima kasih!!
lowtechsun

12
Tidak berfungsi seperti yang diharapkan: Ini mengembalikan 200 di Chrome di MacBook dengan retina saat browser tidak diperbesar.
Terite

19
Browser dengan dukungan untuk layar DPI tinggi tidak akan memberikan hasil yang diharapkan saat menggunakan layar seperti itu, begitu pula Safari tanpa memandang layar.
Fredrik C

Hanya untuk siapa pun yang peduli, di IE ini hanya bekerja di IE11 (itu akan mengembalikan NaN di IE10 atau di bawah)
scunliffe

3
Math.round(window.devicePixelRatio * 100)berfungsi di Chrome, IE, Edge, dan Firefox. Safari di iMac selalu menghasilkan 200.
Super Jade

45

Bagi saya, untuk Chrome / Webkit, document.width / jQuery(document).width()tidak berfungsi. Ketika saya membuat jendela saya kecil dan memperbesar ke situs saya sehingga bilah gulir horizontal muncul, document.width / jQuery(document).width()tidak sama dengan 1 pada pembesaran standar. Ini karena document.widthtermasuk bagian dari dokumen di luar viewport.

Menggunakan window.innerWidthdan window.outerWidthbekerja. Untuk beberapa alasan di Chrome, outerWidth diukur dalam piksel layar dan innerWidth diukur dalam piksel css.

var screenCssPixelRatio = (window.outerWidth - 8) / window.innerWidth;
if (screenCssPixelRatio >= .46 && screenCssPixelRatio <= .54) {
  zoomLevel = "-4";
} else if (screenCssPixelRatio <= .64) {
  zoomLevel = "-3";
} else if (screenCssPixelRatio <= .76) {
  zoomLevel = "-2";
} else if (screenCssPixelRatio <= .92) {
  zoomLevel = "-1";
} else if (screenCssPixelRatio <= 1.10) {
  zoomLevel = "0";
} else if (screenCssPixelRatio <= 1.32) {
  zoomLevel = "1";
} else if (screenCssPixelRatio <= 1.58) {
  zoomLevel = "2";
} else if (screenCssPixelRatio <= 1.90) {
  zoomLevel = "3";
} else if (screenCssPixelRatio <= 2.28) {
  zoomLevel = "4";
} else if (screenCssPixelRatio <= 2.70) {
  zoomLevel = "5";
} else {
  zoomLevel = "unknown";
}

1
Sangat bagus. Dan jika Anda hanya perlu tahu apakah itu diperbesar atau tidak di Chrome:isZoomed = (screenCssPixelRatio < .98 || screenCssPixelRatio > 1.02)
Brent Faust

1
Nah, window.outerWidth diubah dengan zoom juga. Juga, tidak pada setiap OS lebar perbatasan jendela adalah 8 piksel (bahkan pada OS yang sama desainnya dapat bervariasi). Namun saya akan menyarankan untuk mengurangi 16, bukan 8, karena Anda memiliki batas jendela dua kali. Juga, beberapa browser memiliki batas pada jendela render aktualnya (seperti FF) dan beberapa tidak (Safari) - tetapi bahkan ini tergantung pada OS yang Anda gunakan browser (misalnya Safari memiliki perbatasan pada Windows). Mencadangkan innerWidth awal (misalnya pada memuat halaman) dan menggunakannya untuk membandingkan pekerjaan yang lebih baik tetapi hanya jika zoom awal 100% ...
StanE

1
Keluaran 0 tidak peduli apa pun untuk saya (2017, feb).
Tiberiu-Ionuț Stan

1
switchPernyataan mungkin lebih baik daripada banyak jika pernyataan lain.
Edric

Tidak berfungsi: hanya diuji pada Chrome di Mac dan selalu mengembalikan rasio yang sama, terlepas dari tingkat zoom
collimarco

16

Rekan kerja saya dan saya menggunakan skrip dari https://github.com/tombigel/detect-zoom . Selain itu, kami juga secara dinamis membuat elemen svg dan memeriksa properti currentScale-nya. Ini berfungsi dengan baik di Chrome dan kemungkinan besar sebagian besar browser juga. Pada FF, fitur "hanya teks zoom" harus dimatikan. SVG didukung di sebagian besar browser. Pada saat penulisan ini, diuji pada IE10, FF19 dan Chrome28.

var svg = document.createElementNS('http://www.w3.org/2000/svg', 'svg');
svg.setAttribute('xmlns', 'http://www.w3.org/2000/svg');
svg.setAttribute('version', '1.1');
document.body.appendChild(svg);
var z = svg.currentScale;
... more code ...
document.body.removeChild(svg);

Metode ini sekarang selalu melaporkan svg.currentScale = 1 di Firefox 29. Mungkin karena mereka mengubah ukuran seluruh angka layar berdasarkan zoom yang merupakan bug . IE11 tampaknya memiliki masalah yang sama pada Desktop dengan ketinggian layar disesuaikan dengan viewport devicePixelRatio yang cukup kacau.
hexalys

11

Saya menemukan artikel ini sangat membantu. Terima kasih banyak untuk yonran. Saya ingin meneruskan beberapa pembelajaran tambahan yang saya temukan saat menerapkan beberapa teknik yang dia sediakan. Dalam FF6 dan Chrome 9, dukungan untuk kueri media dari JS ditambahkan, yang dapat sangat menyederhanakan pendekatan kueri media yang diperlukan untuk menentukan zoom dalam FF. Lihat dokumen di MDN di sini . Untuk keperluan saya, saya hanya perlu mendeteksi apakah browser diperbesar atau tidak, saya tidak memerlukan faktor zoom yang sebenarnya. Saya bisa mendapatkan jawaban saya dengan satu baris JavaScript:

var isZoomed = window.matchMedia('(max--moz-device-pixel-ratio:0.99), (min--moz-device-pixel-ratio:1.01)').matches;

Menggabungkan ini dengan solusi IE8 + dan Webkit, yang juga merupakan satu baris, saya dapat mendeteksi zoom pada sebagian besar browser yang mengenai aplikasi kami dengan hanya beberapa baris kode.


4
Bisakah Anda memberikan kode cara mendeteksi zoom aktual menggunakan kueri media?
TN.

Coba gunakan hanya "(lebar: <X> px) dan (tinggi: <Y> px)" di mana <X> dan <Y> masing-masing adalah window.innerWidth dan window.innerHeight. Ini berfungsi bahkan untuk jumlah zoom yang sangat kecil. Bekerja di Safari juga.
Maks

@max Bisakah Anda memberikan JSFIddle atau kode contoh bagaimana tampilannya disatukan?
lowtechsun

Selalu melaporkan yang benar pada perangkat retina seperti macbook pro.
Matthew Sanders

codepen.io/anon/pen/LgrGjJ menunjukkan pencarian biner dengan kueri media, tapi ini sama dengan kueri devicePixelRatio: ia mempertimbangkan penskalaan tampilan akun.
ZachB

11
zoom = ( window.outerWidth - 10 ) / window.innerWidth

Itu yang kamu butuhkan.


Kenapa kurangi 10dari outerWidth?
callum

Mungkin untuk bilah gulir. Setiap scrollbar juga berbeda, seperti di iOS jauh lebih kecil. Plus solusi ini tampaknya hanya chrome
Sarah

1
Tidak berfungsi jika pengguna memiliki bilah samping seperti bookmark di FF
Gerrit Sedlaczek

7

Saya punya solusi untuk ini sejak Januari 2016. Diuji bekerja di browser Chrome, Firefox dan MS Edge.

Prinsipnya adalah sebagai berikut. Kumpulkan 2 poin MouseEvent yang berjauhan. Setiap acara mouse dilengkapi dengan koordinat layar dan dokumen. Ukur jarak antara 2 titik di kedua sistem koordinat. Meskipun ada variabel offset tetap antara sistem koordinat karena furnitur browser, jaraknya antara titik harus identik jika halaman tidak diperbesar. Alasan untuk menentukan "berjauhan" (saya menempatkan ini sebagai 12 piksel) adalah agar perubahan zoom kecil (misalnya 90% atau 110%) dapat dideteksi.

Referensi: https://developer.mozilla.org/en/docs/Web/Events/mousemove

Langkah:

  1. Tambahkan pendengar langkah mouse

    window.addEventListener("mousemove", function(event) {
        // handle event
    });
  2. Ambil 4 pengukuran dari peristiwa mouse:

    event.clientX, event.clientY, event.screenX, event.screenY
  3. Ukur jarak d_c antara 2 titik di sistem klien

  4. Ukur jarak d_s antara 2 titik di sistem layar

  5. Jika d_c! = D_s maka zoom diterapkan. Perbedaan antara keduanya memberi tahu Anda jumlah zoom.

NB Hanya jarang melakukan perhitungan jarak, misalnya ketika Anda dapat mencicipi acara mouse baru yang jauh dari yang sebelumnya.

Keterbatasan: Menganggap pengguna akan menggerakkan mouse setidaknya sedikit, dan zoom tidak dapat diketahui hingga saat ini.


1
Saya membuat biola: jsfiddle.net/Terite/9b6ko854 dengan "berjauhan" berarti 100 piksel. Sayangnya itu berfungsi tidak stabil di Firefox (52) di MacBook dengan tampilan retina. Juga harus dicatat bahwa antarmuka Windows 7 zoom 125% terdeteksi di Chrome, Firefox dan IE11 (di zoom 125% yang merupakan standar kemudian) sebagai browser zoom.
Terite

Biola Anda berfungsi untuk saya, diuji di Linux dengan Firefox dan Chrome :)
user1191311

Layar retina menambah tingkat kesulitan lain karena mereka melaporkan ukuran piksel salah, antara lain.
user1191311


3

Di Internet Explorer 7, 8 & 9, ini berfungsi:

function getZoom() {
    var screen;

    screen = document.frames.screen;
    return ((screen.deviceXDPI / screen.systemXDPI) * 100 + 0.9).toFixed();
}

"+0.9" ditambahkan untuk mencegah kesalahan pembulatan (jika tidak, Anda akan mendapatkan 104% dan 109% ketika zoom browser masing-masing diatur ke 105% dan 110%).

Di IE6 zoom tidak ada, jadi tidak perlu memeriksa zoom.


1
Menarik. Bagi saya, itu selalu menunjukkan 80% dari zoom ... Saya percaya ini karena saya memiliki pengaturan font besar di tingkat Windows 7 (mencari "ukuran font" di panel kontrol). Ini lebih baik daripada solusi IE8 dalam jawaban @ yonran yang tidak bekerja sama sekali untuk saya. jsbin.com/obowof
ripper234

Saya mendapatkan 101% saat zoom diatur ke 100%.
Allen Wallace

saya juga. gunakan 0,4999 bukannya 0,9
yan bellavance

ieZoomLevel = ((screen.deviceXDPI / screen.systemXDPI) * 100 + 0.4999) .toFixed ();
yan bellavance

3

Yang saya pikirkan adalah:

1) Buat position:fixed <div>dengan width:100%( id = zoomdiv )

2) ketika halaman dimuat:

zoomlevel=$("#zoomdiv").width()*1.0 / screen.availWidth

Dan itu berhasil untuk saya ctrl+dan ctrl-memperbesar.

atau saya dapat menambahkan baris ke $(window).onresize()acara untuk mendapatkan level zoom aktif


Kode:

<script>
    var zoom=$("#zoomdiv").width()*1.0 / screen.availWidth;

    $(window).resize(function(){
        zoom=$("#zoomdiv").width()*1.0 / screen.availWidth;
        alert(zoom);    
    });
</script>
<body>
    <div id=zoomdiv style="width:100%;position:fixed;"></div>
</body>

PS: ini posting pertama saya, maafkan ada kesalahan


3
Sayangnya, ini hanya akan berfungsi jika pengguna memiliki browser yang dimaksimalkan ( screen.availWidthmelaporkan lebar layar dalam piksel layar, bukan jendela browser).
Bailey Parker

3

Ini sangat berguna bagi saya di browser berbasis webkit (Chrome, Safari):

function isZoomed() {
    var width, mediaQuery;

    width = document.body.clientWidth;
    mediaQuery = '(max-width: ' + width + 'px) and (min-width: ' + width + 'px)';

    return !window.matchMedia(mediaQuery).matches;
}

Sepertinya tidak berfungsi di Firefox.

Ini juga berfungsi di WebKit:

var zoomLevel = document.width / document.body.clientWidth;

5
document.widthpengembalian tidak terdefinisi
Adam

Selalu mengembalikan true tidak peduli zoom (2017, feb, retina display).
Tiberiu-Ionuț Stan

3

Pada dasarnya, kami memiliki:

  • window.devicePixelRatioyang memperhitungkan zoom tingkat browser * serta kepadatan zoom / piksel sistem.
    * - pada tingkat zoom Mac / Safari tidak diperhitungkan
  • pertanyaan media
  • vw/ vhUnit CSS
  • resize peristiwa, yang dipicu pada perubahan level zoom, menyebabkan ukuran efektif dari perubahan jendela

itu sudah cukup untuk normal UX . Jika Anda perlu mendeteksi level zoom yang mungkin merupakan tanda desain UI yang buruk.

Zoom lapangan lebih sulit dilacak dan saat ini tidak dipertimbangkan.


1
window.devicePixelRatio adalah jawaban yang bagus yang bekerja di versi terbaru dari peramban utama - Chrome, Safari, FF, Edge, IE
DShultz

@kirilloid apakah Anda menemukan sesuatu yang dapat digunakan untuk menemukan "tingkat zoom" di Safari dengan andal?
onassar


1

Perhitungan Anda masih didasarkan pada sejumlah piksel CSS. Ukurannya hanya berbeda di layar sekarang. Itulah titik pembesaran halaman penuh.

Apa yang Anda inginkan terjadi pada browser di perangkat 192dpi yang karenanya biasanya menampilkan empat piksel perangkat untuk setiap piksel dalam suatu gambar? Dengan zoom 50%, perangkat ini sekarang menampilkan satu piksel gambar dalam satu piksel perangkat.


@ Neil: bagaimana saya bisa mendapatkan dimensi 'CSS piksel'?
kekecewaan

CSS default ke poin, tetapi tentu saja Anda dapat menentukan piksel dengan menggunakan pengubah dimensi px. Adapun properti elemen diambil dalam JavaScript, ini harus sudah dalam piksel CSS. Jadi jika Anda menentukan lebar <div> menjadi 100px, maka itulah yang akan Anda dapatkan dari JavaScript, apa pun tingkat zoomnya.
Neil

1

Di Chrome

var ratio = (screen.availWidth / document.documentElement.clientWidth);
var zoomLevel = Number(ratio.toFixed(1).replace(".", "") + "0");

1
Hanya berfungsi ketika jendela browser memiliki lebar layar penuh.
tenbits

0

Tidak menguji ini untuk IE, tetapi jika Anda membuat elemen elemdengan

min-width: 100%

kemudian

window.document.width / elem.clientWidth

akan memberi Anda tingkat zoom browser Anda (termasuk document.body.style.zoomfaktornya).


Menguji ini tetapi memperbesar sepertinya tidak meningkatkan elem.clientWidth
Tom

0

Ini untuk Chrome , setelah jawaban pengguna 800583 ...

Saya menghabiskan beberapa jam untuk masalah ini dan belum menemukan pendekatan yang lebih baik, tetapi:

  • Ada 16 'zoomLevel' dan bukan 10
  • Ketika Chrome layar penuh / dimaksimalkan rasionya window.outerWidth/window.innerWidth, dan ketika tidak, rasionya tampaknya (window.outerWidth-16)/window.innerWidth, namun case pertama dapat didekati oleh yang kedua.

Jadi saya datang ke berikut ...

Tetapi pendekatan ini memiliki batasan: misalnya jika Anda memainkan akordeon dengan jendela aplikasi (dengan cepat memperbesar dan mengurangi lebar jendela) maka Anda akan mendapatkan celah di antara level zoom meskipun zoom tidak berubah (mungkin di luar Lebar dan di dalam Lebar tidak persis diperbarui dalam waktu yang sama).

var snap = function (r, snaps)
{
    var i;
    for (i=0; i < 16; i++) { if ( r < snaps[i] ) return i; }
};
var w, l, r;
w = window.outerWidth, l = window.innerWidth;
return snap((w - 16) / l,
            [ 0.29, 0.42, 0.58, 0.71, 0.83, 0.95, 1.05, 1.18, 1.38, 1.63, 1.88, 2.25, 2.75, 3.5, 4.5, 100 ],
);

Dan jika Anda menginginkan faktor:

var snap = function (r, snaps, ratios)
{
    var i;
    for (i=0; i < 16; i++) { if ( r < snaps[i] ) return eval(ratios[i]); }
};
var w, l, r;
w = window.outerWidth, l = window.innerWidth;
return snap((w - 16) / l,
            [ 0.29, 0.42, 0.58, 0.71, 0.83, 0.95, 1.05, 1.18, 1.38, 1.63, 1.88, 2.25, 2.75, 3.5, 4.5, 100 ],
            [ 0.25, '1/3', 0.5, '2/3', 0.75, 0.9, 1, 1.1, 1.25, 1.5, 1.75, 2, 2.5, 3, 4, 5 ]
);

Saya punya masalah dengan "window.outerWidth / window.innerWidth" memberi saya nilai yang salah juga dan itu mungkin karena saya berada di iframe. Jadi yang saya lakukan adalah saya menggunakan jendela induk dan itu memberikan jawaban yang benar: window.parent.window.outerWidth / window.parent.window.innerWidth
yan bellavance

0

Saya punya solusi ini untuk seluler saja (diuji dengan Android):

jQuery(function($){

zoom_level = function(){

    $("body").prepend('<div class="overlay" ' +
                'style="position:fixed; top:0%; left:0%; ' +
                'width:100%; height:100%; z-index:1;"></div>');

    var ratio = $("body .overlay:eq(0)").outerWidth() / $(window).width();
    $("body .overlay:eq(0)").remove();

    return ratio;
}

alert(zoom_level());

});

Jika Anda ingin tingkat zoom tepat setelah gerakan pinch, Anda mungkin harus mengatur sedikit waktu tunggu karena penundaan rendering (tapi saya tidak yakin karena saya tidak mengujinya).


0

Jawaban ini didasarkan pada komentar tentang devicePixelRatio yang kembali secara tidak benar pada jawaban pengguna1080381.

Saya menemukan bahwa perintah ini kembali secara tidak benar dalam beberapa kasus juga ketika bekerja dengan desktop, Surface Pro 3, dan Surface Pro 4.

Apa yang saya temukan adalah itu berfungsi pada desktop saya, tetapi SP3 dan SP4 memberikan angka yang berbeda satu sama lain dan desktop.

Namun saya perhatikan bahwa SP3 kembali sebagai 1 setengah kali tingkat zoom yang saya harapkan. Ketika saya melihat pengaturan tampilan, SP3 sebenarnya diatur ke 150% daripada 100% yang saya miliki di desktop saya.

Jadi, solusi untuk komentar harus membagi tingkat zoom yang dikembalikan dengan skala mesin yang sedang Anda gunakan.

Saya bisa mendapatkan skala dalam pengaturan Windows dengan melakukan hal berikut:

ManagementObjectSearcher searcher = new ManagementObjectSearcher("SELECT * FROM Win32_DesktopMonitor");
double deviceScale = Convert.ToDouble(searcher.Get().OfType<ManagementObject>().FirstOrDefault()["PixelsPerXLogicalInch"]);
int standardPixelPerInch = 96;
return deviceScale / standardPixelPerInch;

Jadi dalam kasus SP3 saya, ini adalah bagaimana kode ini terlihat pada zoom 100%:

devicePixelRatio = 1.5
deviceScale = 144
deviceScale / standardPixelPerInch = 1.5
devicePixelRatio / (deviceScale / standardPixelPerInch) = 1

Mengalikan dengan 100 di jawaban asli user1080381 maka akan memberi Anda zoom 100 (%).


0

Apakah saat ini berfungsi namun masih harus dipisahkan oleh browser. Diuji berhasil di Chrome (75) dan Safari (11.1) (belum menemukan cara untuk FF pada saat ini). Ini juga membuat nilai zoom benar pada tampilan retina dan perhitungan dipicu pada acara pengubahan ukuran.

    private pixelRatio() {
      const styleString = "(min-resolution: 2dppx), (-webkit-min-device-pixel-ratio: 1.5),(-moz-min-device-pixel-ratio: 1.5),(min-device-pixel-ratio: 1.5)";
      const chromeRatio = (Math.round((this.window.outerWidth / this.window.innerWidth)*100) / 100);
      const otherRatio = (Math.round(window.devicePixelRatio * 100) / 100);
      const resizeValue = (this.isChrome()) ? chromeRatio : otherRatio;

      return resizeValue || (this.window.matchMedia && this.window.matchMedia(styleString).matches ? 2 : 1) || 1;
    }


  private isChrome():boolean {
    return (!!this.window.chrome && !(!!this.window.opera || this.window.navigator.userAgent.indexOf(' Opera') >= 0))
  }

  private chrome() {
    const zoomChrome = Math.round(((this.window.outerWidth) / this.window.innerWidth)*100) / 100;
    return {
      zoom: zoomChrome,
      devicePxPerCssPx: zoomChrome1 * this.pixelRatio()
    };
  }

-1

ini dia tidak berubah !:

<html>
 <head>
  <title></title>
 </head>
<body>
 <div id="xy" style="width:400px;">
  foobar
 </div>
 <div>
  <button onclick="alert(document.getElementById('xy').style.width);">Show</button>
 </div>
</body>
</html>

buat file html sederhana, klik tombol. terlepas dari apa tingkat zoom: itu akan menunjukkan kepada Anda lebar 400px (setidaknya dengan firefox dan ie8)


@ tfl: itu karena Anda telah memperbaiki lebar dengan gaya inline. Saya telah memodifikasi sampel Anda untuk menunjukkan kasus saya (diposting di dalam pertanyaan asli).
kekalahan

-1

Ini mungkin atau mungkin tidak membantu siapa pun, tetapi saya memiliki halaman yang tidak dapat saya akses ke pusat dengan benar, apa pun trik Css yang saya coba, maka saya menulis halaman JQuery file call Center Page:

Masalah terjadi dengan tingkat zoom browser, halaman akan bergeser berdasarkan jika Anda 100%, 125%, 150%, dll.

Kode di bawah ini dalam file JQuery yang disebut centerpage.js.

Dari halaman saya, saya harus menautkan ke JQuery dan file ini untuk membuatnya berfungsi, meskipun halaman master saya sudah memiliki tautan ke JQuery.

<title>Home Page.</title>
<script src="Scripts/jquery-1.7.1.min.js"></script>
<script src="Scripts/centerpage.js"></script>

centerpage.js:

// centering page element
function centerPage() {
    // get body element
    var body = document.body;

    // if the body element exists
    if (body != null) {
        // get the clientWidth
        var clientWidth = body.clientWidth;

        // request data for centering
        var windowWidth = document.documentElement.clientWidth;
        var left = (windowWidth - bodyWidth) / 2;

        // this is a hack, but it works for me a better method is to determine the 
        // scale but for now it works for my needs
        if (left > 84) {
            // the zoom level is most likely around 150 or higher
            $('#MainBody').removeClass('body').addClass('body150');
        } else if (left < 100) {
            // the zoom level is most likely around 110 - 140
            $('#MainBody').removeClass('body').addClass('body125');
        }
    }
}


// CONTROLLING EVENTS IN jQuery
$(document).ready(function() {
    // center the page
    centerPage();
});

Juga jika Anda ingin memusatkan panel:

// centering panel
function centerPanel($panelControl) {
    // if the panel control exists
    if ($panelControl && $panelControl.length) {
        // request data for centering
        var windowWidth = document.documentElement.clientWidth;
        var windowHeight = document.documentElement.clientHeight;
        var panelHeight = $panelControl.height();
        var panelWidth = $panelControl.width();

        // centering
        $panelControl.css({
            'position': 'absolute',
            'top': (windowHeight - panelHeight) / 2,
            'left': (windowWidth - panelWidth) / 2
        });

        // only need force for IE6
        $('#backgroundPanel').css('height', windowHeight);
    }
}

-1

Pertanyaan ini diposting seperti berabad-abad yang lalu, tetapi hari ini ketika saya sedang mencari jawaban yang sama "Bagaimana mendeteksi acara memperbesar dan memperkecil", saya tidak dapat menemukan satu jawaban yang cocok dengan semua browser.

Seperti pada saat ini: Untuk Firefox / Chrome / IE8 dan IE9, zoom in dan out menghasilkan window.resize event. Ini dapat ditangkap menggunakan:

$(window).resize(function() {
//YOUR CODE.
});

-1

Solusi untuk FireFox 16+ untuk menemukan DPPX (tingkat zoom) murni dengan JavaScript:

var dppx = (function (precision) {
  var searchDPPX = function(level, min, divisor) {
    var wmq = window.matchMedia;
    while (level >= min && !wmq("(min-resolution: " + (level/divisor) + "dppx)").matches) {
      level--;
    }
    return level;
  };

  var maxDPPX = 5.0; // Firefox 22 has 3.0 as maximum, but testing a bit greater values does not cost much
  var minDPPX = 0.1; // Firefox 22 has 0.3 as minimum, but testing a bit smaller values does not cost anything
  var divisor = 1;
  var result;
  for (var i = 0; i < precision; i++) {
    result = 10 * searchDPPX (maxDPPX, minDPPX, divisor);
    maxDPPX = result + 9;
    minDPPX = result;
    divisor *= 10;
  }

  return result / divisor;
}) (5);

Ini tidak berfungsi seperti yang diharapkan di Firefox (52) di MacBook dengan tampilan retina - mengembalikan 2 ketika tidak di zoom. Saya membuat biola: jsfiddle.net/Terite/wadkh3ea
Terite

-1
function supportFullCss3()
{
    var div = document.createElement("div");
    div.style.display = 'flex';
    var s1 = div.style.display == 'flex';
    var s2 = 'perspective' in div.style;

    return (s1 && s2);
};

function getZoomLevel()
{
    var screenPixelRatio = 0, zoomLevel = 0;

    if(window.devicePixelRatio && supportFullCss3())
        screenPixelRatio = window.devicePixelRatio;
    else if(window.screenX == '0')
        screenPixelRatio = (window.outerWidth - 8) / window.innerWidth;
    else
    {
        var scr = window.frames.screen;
        screenPixelRatio = scr.deviceXDPI / scr.systemXDPI;
    }

    //---------------------------------------
    if (screenPixelRatio <= .11){ //screenPixelRatio >= .01 &&
      zoomLevel = "-7";
    } else if (screenPixelRatio <= .25) {
      zoomLevel = "-6";
    }else if (screenPixelRatio <= .33) {
      zoomLevel = "-5.5";
    } else if (screenPixelRatio <= .40) {
      zoomLevel = "-5";
    } else if (screenPixelRatio <= .50) {
      zoomLevel = "-4";
    } else if (screenPixelRatio <= .67) {
      zoomLevel = "-3";
    } else if (screenPixelRatio <= .75) {
      zoomLevel = "-2";
    } else if (screenPixelRatio <= .85) {
      zoomLevel = "-1.5";
    } else if (screenPixelRatio <= .98) {
      zoomLevel = "-1";
    } else if (screenPixelRatio <= 1.03) {
      zoomLevel = "0";
    } else if (screenPixelRatio <= 1.12) {
      zoomLevel = "1";
    } else if (screenPixelRatio <= 1.2) {
      zoomLevel = "1.5";
    } else if (screenPixelRatio <= 1.3) {
      zoomLevel = "2";
    } else if (screenPixelRatio <= 1.4) {
      zoomLevel = "2.5";
    } else if (screenPixelRatio <= 1.5) {
      zoomLevel = "3";
    } else if (screenPixelRatio <= 1.6) {
      zoomLevel = "3.3";
    } else if (screenPixelRatio <= 1.7) {
      zoomLevel = "3.7";
    } else if (screenPixelRatio <= 1.8) {
      zoomLevel = "4";
    } else if (screenPixelRatio <= 1.9) {
      zoomLevel = "4.5";
    } else if (screenPixelRatio <= 2) {
      zoomLevel = "5";
    } else if (screenPixelRatio <= 2.1) {
      zoomLevel = "5.2";
    } else if (screenPixelRatio <= 2.2) {
      zoomLevel = "5.4";
    } else if (screenPixelRatio <= 2.3) {
      zoomLevel = "5.6";
    } else if (screenPixelRatio <= 2.4) {
      zoomLevel = "5.8";
    } else if (screenPixelRatio <= 2.5) {
      zoomLevel = "6";
    } else if (screenPixelRatio <= 2.6) {
      zoomLevel = "6.2";
    } else if (screenPixelRatio <= 2.7) {
      zoomLevel = "6.4";
    } else if (screenPixelRatio <= 2.8) {
      zoomLevel = "6.6";
    } else if (screenPixelRatio <= 2.9) {
      zoomLevel = "6.8";
    } else if (screenPixelRatio <= 3) {
      zoomLevel = "7";
    } else if (screenPixelRatio <= 3.1) {
      zoomLevel = "7.1";
    } else if (screenPixelRatio <= 3.2) {
      zoomLevel = "7.2";
    } else if (screenPixelRatio <= 3.3) {
      zoomLevel = "7.3";
    } else if (screenPixelRatio <= 3.4) {
      zoomLevel = "7.4";
    } else if (screenPixelRatio <= 3.5) {
      zoomLevel = "7.5";
    } else if (screenPixelRatio <= 3.6) {
      zoomLevel = "7.6";
    } else if (screenPixelRatio <= 3.7) {
      zoomLevel = "7.7";
    } else if (screenPixelRatio <= 3.8) {
      zoomLevel = "7.8";
    } else if (screenPixelRatio <= 3.9) {
      zoomLevel = "7.9";
    } else if (screenPixelRatio <= 4) {
      zoomLevel = "8";
    } else if (screenPixelRatio <= 4.1) {
      zoomLevel = "8.1";
    } else if (screenPixelRatio <= 4.2) {
      zoomLevel = "8.2";
    } else if (screenPixelRatio <= 4.3) {
      zoomLevel = "8.3";
    } else if (screenPixelRatio <= 4.4) {
      zoomLevel = "8.4";
    } else if (screenPixelRatio <= 4.5) {
      zoomLevel = "8.5";
    } else if (screenPixelRatio <= 4.6) {
      zoomLevel = "8.6";
    } else if (screenPixelRatio <= 4.7) {
      zoomLevel = "8.7";
    } else if (screenPixelRatio <= 4.8) {
      zoomLevel = "8.8";
    } else if (screenPixelRatio <= 4.9) {
      zoomLevel = "8.9";
    } else if (screenPixelRatio <= 5) {
      zoomLevel = "9";
    }else {
      zoomLevel = "unknown";
    }

    return zoomLevel;
};

6
Mohon juga menjelaskan cara kerja kode Anda. Itu akan sangat membantu jika seorang pemula menemukan jawaban Anda.
displayName

Saya membuat biola: jsfiddle.net/Terite/5n1bk9do As @AlexeySh. disebutkan, itu tidak berfungsi seperti yang diharapkan pada tampilan retina di Chrome (56), Firefox (52). Itu juga menunjukkan 0 dalam zoom di Safari (10).
Terite

-1

Masalahnya terletak pada jenis monitor yang digunakan, monitor 4k vs monitor standar. Sejauh ini Chrome adalah yang paling pintar untuk bisa memberi tahu kami apa tingkat zoom hanya dengan menggunakan window.devicePixelRatio, tampaknya itu bisa mengetahui apa kepadatan pixel dan melaporkan kembali nomor yang sama untuk apa pun.

Browser lain, tidak terlalu banyak. IE dan Edge mungkin yang terburuk, karena mereka menangani level zoom jauh berbeda. Untuk mendapatkan ukuran teks yang sama pada monitor 4k, Anda harus memilih 200%, bukan 100% pada monitor standar.

Pada Mei 2018, inilah yang harus saya deteksi level zoom untuk beberapa browser paling populer, Chrome, Firefox, dan IE11. Saya sudah memberi tahu saya berapa persentase pembesaran. Untuk IE, ia melaporkan 100% bahkan untuk monitor 4k yang sebenarnya 200%, tetapi ukuran teksnya benar-benar sama.

Ini biola: https://jsfiddle.net/ae1hdogr/

Jika ada yang mau menusuk browser lain dan memperbarui biola, silakan lakukan. Tujuan utama saya adalah untuk mendapatkan 3 browser ini tertutup untuk mendeteksi jika orang menggunakan faktor zoom lebih besar dari 100% untuk menggunakan aplikasi web saya dan menampilkan pemberitahuan yang menyarankan faktor zoom lessor.


Safari pada Mac Book Pro (layar retina) mengembalikan 0, Chrome pada layar non retina kembali dengan benar sepertinya 100, 90 dll
OZZIE

Mengembalikan 200 pada layar retina Chrome & Firefox
OZZIE
Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.