From f0f2259aa1700f020ce38ecaf6b684e9ba550423 Mon Sep 17 00:00:00 2001 From: Andrew Ekstedt Date: Thu, 10 Sep 2020 20:07:54 -0700 Subject: [PATCH] Improve support for High DPI displays On high DPI displays, a logical pixel does not necessarily equal a device pixel. Images and such are scaled up to the logical pixel size; unfortunately this introduces ugly aliasing. Web pages can take advantage of high DPI screens by intentionally scaling stuff down to be displayed at a higher resolution. By carefully canceling out the automatic scaling of the game canvas we get nice crisp pixels even on high DPI screens. See the pull request for before/after screenshots. --- js/main.js | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) diff --git a/js/main.js b/js/main.js index 942775e..2367b5f 100644 --- a/js/main.js +++ b/js/main.js @@ -619,18 +619,27 @@ class Player extends PrimaryView { // The main UI is centered in a flex item with auto margins, so the // extra space available is the size of those margins let style = window.getComputedStyle(this.root); + if (style['display'] === 'none') { + // the computed margins can be 'auto' in this case + return; + } let extra_x = parseFloat(style['margin-left']) + parseFloat(style['margin-right']); let extra_y = parseFloat(style['margin-top']) + parseFloat(style['margin-bottom']); // The total available space, then, is the current size of the // canvas plus the size of the margins let total_x = extra_x + this.renderer.canvas.offsetWidth; let total_y = extra_y + this.renderer.canvas.offsetHeight; + let dpr = window.devicePixelRatio || 1.0; // Divide to find the biggest scale that still fits. But don't // exceed 90% of the available space, or it'll feel cramped. - let scale = Math.floor(0.9 * Math.min(total_x / base_x, total_y / base_y)); - if (scale <= 0) { + let scale = Math.floor(0.9 * dpr * Math.min(total_x / base_x, total_y / base_y)); + if (scale <= 1) { scale = 1; } + // High DPI support: scale the canvas down by the inverse of the device + // pixel ratio, thus matching the canvas's resolution to the screen + // resolution and giving us nice, clean pixels. + scale /= dpr; // FIXME the above logic doesn't take into account the inventory, which is also affected by scale this.scale = scale;