Signatur
Beschreibung
window.devicePixelRatio gibt an, wie viele physikalische Bildschirmpixel für die Darstellung eines einzelnen CSS-Pixels verwendet werden. Auf einem klassischen Monitor ist der Wert 1, auf hochauflösenden Displays (z. B. Retina, viele Smartphones) typischerweise 2 oder 3. Auch Bruchwerte wie 1.25 oder 1.5 kommen häufig vor, etwa durch die Skalierung des Betriebssystems unter Windows.
Wichtig ist die Eigenschaft vor allem beim Zeichnen auf <canvas>: Ein Canvas mit 300×150 Pixeln Zeichenfläche wirkt auf einem Display mit Faktor 2 unscharf, weil jedes Canvas-Pixel auf 2×2 Gerätepixel hochskaliert wird. Wer die interne Zeichenfläche um devicePixelRatio vergrößert und den Kontext entsprechend skaliert, erhält gestochen scharfe Grafiken. Auch für das Laden passender Bildauflösungen, WebGL-Renderer oder pixelgenaue Screenshots ist der Wert nützlich.
Der Wert ist nicht konstant: Er ändert sich, wenn der Benutzer im Browser zoomt (Strg + +) oder das Fenster auf einen Monitor mit anderer Pixeldichte verschiebt. Ein eigenes Änderungs-Event gibt es nicht; stattdessen überwacht man die Media Query (resolution: Xdppx) mit window.matchMedia().
Für Bilder in HTML/CSS ist die deklarative Lösung meist besser: srcset mit x-Deskriptoren, <picture> oder image-set() in CSS überlassen die Auswahl dem Browser.
Rückgabewert
1, 1.5, 2 oder 3. Die Eigenschaft ist schreibgeschützt (Zuweisungen haben keinen Einfluss auf die Darstellung).Beispiele
Aktuellen Pixelfaktor auslesen
const dpr = window.devicePixelRatio;
console.log(`Pixelverhältnis: ${dpr}`);
if (dpr >= 2) {
console.log('Hochauflösendes Display erkannt');
}
Scharfes Canvas auf HiDPI-Displays
const setupCanvas = (canvas) => {
const dpr = window.devicePixelRatio || 1;
const rect = canvas.getBoundingClientRect();
// Interne Zeichenfläche in Gerätepixeln
canvas.width = Math.round(rect.width * dpr);
canvas.height = Math.round(rect.height * dpr);
const ctx = canvas.getContext('2d');
// Koordinatensystem weiterhin in CSS-Pixeln
ctx.setTransform(dpr, 0, 0, dpr, 0, 0);
return ctx;
};
const canvas = document.querySelector('#chart');
canvas.style.width = '300px';
canvas.style.height = '150px';
const ctx = setupCanvas(canvas);
ctx.font = '16px sans-serif';
ctx.fillText('Gestochen scharfer Text', 10, 40);
Auf Änderungen reagieren (Zoom, Monitorwechsel)
const watchPixelRatio = (callback) => {
let remove = null;
const update = () => {
remove?.();
const mq = window.matchMedia(`(resolution: ${window.devicePixelRatio}dppx)`);
const onChange = () => {
callback(window.devicePixelRatio);
update(); // neue Media Query für den neuen Wert registrieren
};
mq.addEventListener('change', onChange, { once: true });
remove = () => mq.removeEventListener('change', onChange);
};
update();
return () => remove?.();
};
const stop = watchPixelRatio((dpr) => {
console.log(`devicePixelRatio geändert: ${dpr}`);
});
// später: stop();
Passende Bildauflösung wählen
const pickImage = (baseName) => {
const dpr = Math.min(Math.ceil(window.devicePixelRatio), 3);
return `/img/${baseName}@${dpr}x.webp`;
};
const img = new Image();
img.src = pickImage('logo');
console.log(img.src);
// Wichtig · Fallstricke
- Nicht nur ganzzahlig: Werte wie
1.25,1.5oder2.625sind üblich. Beim Berechnen von Canvas-Größen daher mitMath.round()runden, sonst entstehen unscharfe Kanten. - Browser-Zoom verändert den Wert: In Desktop-Browsern (Chrome, Firefox, Edge) steigt
devicePixelRatiobeim Hineinzoomen. Safari verhält sich hier historisch abweichend. Pinch-Zoom auf Mobilgeräten ändert den Wert dagegen in der Regel nicht. - Kein Change-Event: Änderungen lassen sich nur über
matchMedia('(resolution: …dppx)')oder dasresize-Event erkennen; die Media Query muss nach jeder Änderung neu erstellt werden. - Performance: Ein Canvas mit Faktor 3 hat die neunfache Pixelanzahl. Bei aufwendigen Animationen oder WebGL kann es sinnvoll sein, den Wert zu begrenzen (z. B.
Math.min(dpr, 2)). - Datenschutz: Der Wert trägt zum Browser-Fingerprinting bei; manche Datenschutz-Modi (z. B. Firefox
resistFingerprinting) liefern pauschal1. - Kompatibilität: Wird von allen modernen Browsern unterstützt; in Web Workern gibt es die Eigenschaft nicht (dort den Wert per
postMessageübergeben).