最近のすべてのブラウザでページのズームレベルを検出する方法を教えてください。これ thread はIE7とIE8でそれを行う方法を教えてくれますが、私は良いクロスブラウザソリューションを見つけることができません。
Firefoxは将来のアクセスのためにページのズームレベルを保存します。最初のページの読み込みで、ズームレベルを取得できますか?私が読んだどこかでズームの変更が発生したときに動作しますafterページがロードされています。
'zoom'
イベントをトラップする方法はありますか?
私の計算のいくつかはピクセルベースで、ズームすると変動する可能性があるので、これが必要です。
@tflによる修正サンプル
このページはズーム時にさまざまな高さの値を警告します。 [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>
今度は、この質問が最初に尋ねられたときよりもさらに大きな混乱です。私が見つけることができたすべての応答とブログ記事を読むことから、これは要約です。私はまた--- ズームレベルを測定するこれらすべての方法をテストするためのこのページ を設定しました。
編集(2011-12-12):複製できるプロジェクトを追加しました。 https://github.com/) tombigel/detect-zoom
screen.deviceXDPI / screen.logicalXDPI
(または、デフォルトのズームに対するズームレベルの場合はscreen.systemXDPI / screen.logicalXDPI
)var body = document.body,r = body.getBoundingClientRect(); return (r.left-r.right)/body.offsetWidth;
( この例 または この答え に感謝します)screen.width
media query screen width(下記参照)(screen.width
はデバイスピクセルを使用しますが、MQ幅はCSSピクセルを使用するという事実を利用します) - Quirksmode widths )に感謝します-webkit-text-size-adjust:none
を使ってdivの適切なサイズを測定します。document.width / jQuery(document).width()
( Dirk van Oosterbosch)に感謝します )。 (デフォルトのズームに対する相対ではなく)デバイスのピクセルで比率を取得するには、window.devicePixelRatio
を掛けます。parseInt(getComputedStyle(document.documentElement,null).width) / document.documentElement.clientWidth
(から この回答 )document.documentElement.offsetWidth
/position:fixed; width:100%
divの幅。 ここから ( Quirksmodeのwidthsテーブル これはバグだと言っています; innerWidthはCSS pxであるべきです)。スクロールバーがであるスペースを含むビューポートの幅を取得するには、position:fixed要素を使用します。 document.documentElement.clientWidthはこの幅を除外します。これは2011年のいつか以来壊れています。私はもうOperaのズームレベルを取得する方法を知りません。私はそれが公開されている任意の変数を知らないので、これはFirefox 4のための二分探索です。
<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>
私にとっては、Chrome/Webkitではdocument.width / jQuery(document).width()
が機能しませんでした。水平スクロールバーが表示されるようにウィンドウを小さくして自分のサイトにズームインしたとき、document.width / jQuery(document).width()
がデフォルトのズームで1に等しくありませんでした。これはdocument.width
がビューポートの外側のドキュメントの一部を含むためです。
window.innerWidth
とwindow.outerWidth
の使用はうまくいきました。何らかの理由でChromeでは、outerWidthは画面のピクセルで測定され、innerWidthは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";
}
あなたが試すことができます
var browserZoomLevel = Math.round(window.devicePixelRatio * 100);
これにより、ブラウザのズーム率レベルがわかります。
ズームイベントをキャッチするにはあなたが使用することができます
$(window).resize(function() {
// your code
});
私の同僚と私は https://github.com/tombigel/detect-zoom からスクリプトを使用しました。さらに、動的にsvg要素を作成し、そのcurrentScaleプロパティを確認しました。それはChromeとおそらくほとんどのブラウザでもうまく動作します。 FFでは、「テキストのみズーム」機能は無効にする必要があります。 SVGは、ほとんどのブラウザで サポートされている です。これを書いている時点では、IE10、FF19、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);
zoom = ( window.outerWidth - 10 ) / window.innerWidth
必要なものはこれだけです。
この記事は非常に役に立ちました。ヨンランに感謝します。彼が提供したテクニックのいくつかを実行している間に私が見つけたいくつかの追加の学習を伝えたいと思いました。 FF6とChrome 9では、JSからのメディアクエリのサポートが追加されました。これはFFのズームインを決定するために必要なメディアクエリアプローチを非常に単純化することができます。 MDN こちら のドキュメントを参照してください。私の目的のために、私はブラウザがズームインされたのかズームアウトされたのかを検出するだけでよく、実際のズーム倍率は必要ありませんでした。私は1行のJavaScriptで私の答えを得ることができました:
var isZoomed = window.matchMedia('(max--moz-device-pixel-ratio:0.99), (min--moz-device-pixel-ratio:1.01)').matches;
これと単一行のIE 8+およびWebkitソリューションを組み合わせると、ほんの数行のコードでアプリにアクセスしている大多数のブラウザのズームを検出できました。
私は2016年1月の時点でこの問題に対する解決策を持っています。Chrome、Firefox、そしてMS Edgeブラウザで動作確認済みです。
その原理は以下の通りです。離れている2つのMouseEventポイントを集める。各マウスイベントには、画面座標とドキュメント座標が付属しています。両方の座標系で2点間の距離を測定します。ブラウザの家具による座標系間の可変固定オフセットがありますが、ページがズームされていない場合、ポイント間の距離は同じである必要があります。 「遠く」(これを12ピクセルとします)を指定する理由は、小さなズームの変化(たとえば90%または110%)を検出できるようにするためです。
参照: https://developer.mozilla.org/en/docs/Web/Events/mousemove
ステップ:
マウス移動リスナを追加する
window.addEventListener("mousemove", function(event) {
// handle event
});
マウスイベントから4つの測定値をキャプチャします。
event.clientX, event.clientY, event.screenX, event.screenY
クライアントシステムの2点間の距離d_cを測定する
スクリーンシステム内の2点間の距離d_sを測定する
D_c!= d_sの場合、ズームが適用されます。 2つの違いはズームの量を教えてくれます。
N.B.めったに距離計算をしない、例えば前のイベントからかけ離れた新しいマウスイベントをサンプリングできるとき。
制限事項:ユーザーはマウスを少なくとも少し動かすことを想定しています。このときまでズームは認識できません。
私が思いついたのは、
1)position:fixed
(id = zoomdiv)で<div>
width:100%
を作る
2)ページが読み込まれたとき:
zoomlevel=$("#zoomdiv").width()*1.0 / screen.availWidth
そしてそれは私にとってctrl+
とctrl-
ズーミングのために働きました。
または私はアクティブなズームレベルを取得するために$(window).onresize()
イベントに行を追加することができます
コード:
<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>
P.S :これは私の最初の投稿です、間違いを許してください
これは、Webキットベースのブラウザ(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;
}
Firefoxでは動作しないようですが。
これはWebKitでも機能します。
var zoomLevel = document.width / document.body.clientWidth;
Internet Explorer 7、8、9では、これは機能します。
function getZoom() {
var screen;
screen = document.frames.screen;
return ((screen.deviceXDPI / screen.systemXDPI) * 100 + 0.9).toFixed();
}
丸め誤差を防ぐために "+ 0.9"が追加されています(そうでなければ、ブラウザのズームがそれぞれ105%と110%に設定されていると104%と109%になります)。
IE6ではズームが存在しないので、ズームを確認する必要はありません。
基本的には、
window.devicePixelRatio
。vw
/vh
CSSユニットresize
イベントにより、ウィンドウの有効サイズ変更が発生します。これはnormal UXに十分なはずです。あなたがズームレベルを検出する必要があるならば、それは悪いUIデザインのサインかもしれません。
ピッチズームは追跡が難しく、現在は考慮されていません。
モバイルデバイス(Chrome for AndroidまたはOpera Mobile)では、window.visualViewport.scaleでズームを検出できます。 https://developer.mozilla.org/en-US/docs/Web/API/Visual_Viewport_API
Safariで検出する:document.documentElement.clientWidth/window.innerWidth(デバイスがズームされていない場合は1を返す)。
Chromeで
var ratio = (screen.availWidth / document.documentElement.clientWidth);
var zoomLevel = Number(ratio.toFixed(1).replace(".", "") + "0");
計算はまだいくつかのCSSピクセルに基づいています。彼らは今、画面上でちょうど異なるサイズです。それが全ページズームのポイントです。
192dpiデバイスのブラウザで何をしたいのでしょうか。そのため、通常は画像の各ピクセルに対して4つのデバイスピクセルが表示されます。 50%ズームで、このデバイスは1つのデバイスピクセルに1つのイメージピクセルを表示します。
これは、Chrome、 user800583を契機にしています答え ...
私はこの問題に数時間を費やしました、そして、より良いアプローチを見つけませんでした、しかし:
window.outerWidth/window.innerWidth
であり、そうでない場合、比率は(window.outerWidth-16)/window.innerWidth
のように見えますが、1番目のケースは2番目のケースに近づくことができます。それで、私は以下に来ました...
しかし、このアプローチには限界があります。たとえば、アプリケーションウィンドウでアコーディオンを演奏する(ウィンドウの幅をすばやく拡大および縮小する)場合、ズームは変更されませんがズームレベル間にギャップが生じます(outerWidthとinnerWidthは変更されません)。正確に同じ時間に更新されます。
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 ],
);
そしてあなたがその要素が欲しいなら:
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 ]
);
この回答は、user1080381の回答に誤って戻ってきたdevicePixelRatioに関するコメントに基づいています。
デスクトップ、Surface Pro 3、およびSurface Pro 4を使用しているときにも、このコマンドが誤って戻ってくることがありました。
私が見つけたのは、それが私のデスクトップ上で動作したということですが、SP3とSP4は互いに、そしてデスクトップとは異なる番号を与えていました。
けれども私はSP3が私が期待していたズームレベルの1.5倍として戻って来ていたことに気づきました。ディスプレイの設定を見たとき、SP3は実際にはデスクトップの100%ではなく150%に設定されていました。
したがって、コメントを解決するには、返されたズームレベルを現在使用しているマシンの縮尺で除算する必要があります。
私は次のようにすることでWindowsの設定でスケールを取得することができました:
ManagementObjectSearcher searcher = new ManagementObjectSearcher("SELECT * FROM Win32_DesktopMonitor");
double deviceScale = Convert.ToDouble(searcher.Get().OfType<ManagementObject>().FirstOrDefault()["PixelsPerXLogicalInch"]);
int standardPixelPerInch = 96;
return deviceScale / standardPixelPerInch;
だから私のSP3の場合、これはこのコードが100%ズームでどのように見えるかです:
devicePixelRatio = 1.5
deviceScale = 144
deviceScale / standardPixelPerInch = 1.5
devicePixelRatio / (deviceScale / standardPixelPerInch) = 1
User1080381の元の答えに100を掛けると、100(%)のズームになります。
私は---のためのこの解決策を持っていますモバイルのみ(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());
});
あなたがピンチ移動の直後にズームレベルを望むなら、あなたはおそらくレンダリングの遅れのために少しタイムアウトを設定しなければならないでしょう。
現在動作していますが、ブラウザごとに分離する必要があります。 Chrome(75)とSafari(11.1)で正常にテストされました(まだFFの方法を見つけていません)。また、Retinaディスプレイで正しいズーム値を取得し、サイズ変更イベントで計算がトリガーされます。
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()
};
}
IEではこれをテストしませんでしたが、次のように要素elem
を作成したとします。
min-width: 100%
それから
window.document.width / elem.clientWidth
ブラウザのズームレベルを指定します(document.body.style.zoom
ファクタを含む)。